Implement custom previews for context menus to crop cell separators. Issue #1221

This commit is contained in:
Maurice Parker 2019-11-23 22:15:29 -06:00
parent 9f60984ba2
commit 4296c243ff
5 changed files with 66 additions and 12 deletions

View File

@ -93,6 +93,7 @@
51627A6723861DA3007B3B4B /* MasterFeedViewController+Drag.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51627A6623861DA3007B3B4B /* MasterFeedViewController+Drag.swift */; };
51627A6923861DED007B3B4B /* MasterFeedViewController+Drop.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51627A6823861DED007B3B4B /* MasterFeedViewController+Drop.swift */; };
51627A6B238629D8007B3B4B /* MasterFeedDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51627A6A238629D8007B3B4B /* MasterFeedDataSource.swift */; };
51627A93238A3836007B3B4B /* CroppingTargetedPreview.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51627A92238A3836007B3B4B /* CroppingTargetedPreview.swift */; };
516A093723609A3600EAE89B /* SettingsAccountTableViewCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = 516A091D23609A3600EAE89B /* SettingsAccountTableViewCell.xib */; };
516A09392360A2AE00EAE89B /* SettingsAccountTableViewCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 516A09382360A2AE00EAE89B /* SettingsAccountTableViewCell.swift */; };
516A093B2360A4A000EAE89B /* SettingsTableViewCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = 516A093A2360A4A000EAE89B /* SettingsTableViewCell.xib */; };
@ -1271,6 +1272,7 @@
51627A6623861DA3007B3B4B /* MasterFeedViewController+Drag.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "MasterFeedViewController+Drag.swift"; sourceTree = "<group>"; };
51627A6823861DED007B3B4B /* MasterFeedViewController+Drop.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "MasterFeedViewController+Drop.swift"; sourceTree = "<group>"; };
51627A6A238629D8007B3B4B /* MasterFeedDataSource.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MasterFeedDataSource.swift; sourceTree = "<group>"; };
51627A92238A3836007B3B4B /* CroppingTargetedPreview.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CroppingTargetedPreview.swift; sourceTree = "<group>"; };
516A091D23609A3600EAE89B /* SettingsAccountTableViewCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = SettingsAccountTableViewCell.xib; sourceTree = "<group>"; };
516A09382360A2AE00EAE89B /* SettingsAccountTableViewCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsAccountTableViewCell.swift; sourceTree = "<group>"; };
516A093A2360A4A000EAE89B /* SettingsTableViewCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = SettingsTableViewCell.xib; sourceTree = "<group>"; };
@ -1854,14 +1856,17 @@
children = (
51F85BFA2275D85000C787DC /* Array-Extensions.swift */,
51F85BF42273625800C787DC /* Bundle-Extensions.swift */,
51627A92238A3836007B3B4B /* CroppingTargetedPreview.swift */,
512AF9C1236ED52C0066F8BE /* ImageHeaderView.swift */,
512AF9DC236F05230066F8BE /* InteractiveLabel.swift */,
51934CC1230F5963006127BE /* InteractiveNavigationController.swift */,
51A9A5F42380F6A60033AADF /* ModalNavigationController.swift */,
51EAED95231363EF00A9EEE3 /* NonIntrinsicButton.swift */,
5183CCD9226E31A50010922C /* NonIntrinsicImageView.swift */,
5183CCCF226E1E880010922C /* NonIntrinsicLabel.swift */,
51A9A6092382FD240033AADF /* PoppableGestureRecognizerDelegate.swift */,
512363372369155100951F16 /* RoundedProgressView.swift */,
51C45250226506F400C03939 /* String-Extensions.swift */,
51934CC1230F5963006127BE /* InteractiveNavigationController.swift */,
5108F6D723763094001ABC45 /* TickMarkSlider.swift */,
51F85BF82274AA7B00C787DC /* UIBarButtonItem-Extensions.swift */,
51F85BF622749FA100C787DC /* UIFont-Extensions.swift */,
@ -1869,8 +1874,6 @@
51FFF0C3235EE8E5002762AA /* VibrantButton.swift */,
5186A634235EF3A800C97195 /* VibrantLabel.swift */,
5F323808231DF9F000706F6B /* VibrantTableViewCell.swift */,
51A9A5F42380F6A60033AADF /* ModalNavigationController.swift */,
51A9A6092382FD240033AADF /* PoppableGestureRecognizerDelegate.swift */,
);
path = "UIKit Extensions";
sourceTree = "<group>";
@ -3962,6 +3965,7 @@
51C452A222650A1900C03939 /* RSHTMLMetadata+Extension.swift in Sources */,
514B7D1F23219F3C00BAC947 /* AddControllerType.swift in Sources */,
5141E7562374A2890013FF27 /* ArticleIconSchemeHandler.swift in Sources */,
51627A93238A3836007B3B4B /* CroppingTargetedPreview.swift in Sources */,
512AF9DD236F05230066F8BE /* InteractiveLabel.swift in Sources */,
51E3EB3D229AB08300645299 /* ErrorHandler.swift in Sources */,
5183CCE5226F4DFA0010922C /* RefreshInterval.swift in Sources */,

View File

@ -294,11 +294,22 @@ class MasterFeedViewController: UITableViewController, UndoableCommandRunner {
return nil
}
if node.representedObject is WebFeed {
return makeFeedContextMenu(indexPath: indexPath, includeDeleteRename: true)
return makeFeedContextMenu(node: node, indexPath: indexPath, includeDeleteRename: true)
} else {
return makeFolderContextMenu(indexPath: indexPath)
return makeFolderContextMenu(node: node, indexPath: indexPath)
}
}
override func tableView(_ tableView: UITableView, previewForHighlightingContextMenuWithConfiguration configuration: UIContextMenuConfiguration) -> UITargetedPreview? {
guard let nodeUniqueId = configuration.identifier as? Int,
let node = coordinator.rootNode.descendantNode(where: { $0.uniqueID == nodeUniqueId }),
let indexPath = dataSource.indexPath(for: node),
let cell = tableView.cellForRow(at: indexPath) else {
return nil
}
return UITargetedPreview(view: cell, parameters: CroppingPreviewParameters(view: cell))
}
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
becomeFirstResponder()
@ -572,12 +583,22 @@ extension MasterFeedViewController: UIContextMenuInteractionDelegate {
return nil
}
return UIContextMenuConfiguration(identifier: nil, previewProvider: nil) { suggestedActions in
return UIContextMenuConfiguration(identifier: sectionIndex as NSCopying, previewProvider: nil) { suggestedActions in
let accountInfoAction = self.getAccountInfoAction(account: account)
let deactivateAction = self.deactivateAccountAction(account: account)
return UIMenu(title: "", children: [accountInfoAction, deactivateAction])
}
}
func contextMenuInteraction(_ interaction: UIContextMenuInteraction, previewForHighlightingMenuWithConfiguration configuration: UIContextMenuConfiguration) -> UITargetedPreview? {
guard let sectionIndex = configuration.identifier as? Int,
let cell = tableView.headerView(forSection: sectionIndex) else {
return nil
}
return UITargetedPreview(view: cell, parameters: CroppingPreviewParameters(view: cell))
}
}
// MARK: MasterTableViewCellDelegate
@ -785,8 +806,8 @@ private extension MasterFeedViewController {
}
}
func makeFeedContextMenu(indexPath: IndexPath, includeDeleteRename: Bool) -> UIContextMenuConfiguration {
return UIContextMenuConfiguration(identifier: nil, previewProvider: nil, actionProvider: { [ weak self] suggestedActions in
func makeFeedContextMenu(node: Node, indexPath: IndexPath, includeDeleteRename: Bool) -> UIContextMenuConfiguration {
return UIContextMenuConfiguration(identifier: node.uniqueID as NSCopying, previewProvider: nil, actionProvider: { [ weak self] suggestedActions in
guard let self = self else { return nil }
@ -819,8 +840,8 @@ private extension MasterFeedViewController {
}
func makeFolderContextMenu(indexPath: IndexPath) -> UIContextMenuConfiguration {
return UIContextMenuConfiguration(identifier: nil, previewProvider: nil, actionProvider: { [weak self] suggestedActions in
func makeFolderContextMenu(node: Node, indexPath: IndexPath) -> UIContextMenuConfiguration {
return UIContextMenuConfiguration(identifier: node.uniqueID as NSCopying, previewProvider: nil, actionProvider: { [weak self] suggestedActions in
guard let self = self else { return nil }

View File

@ -286,7 +286,7 @@ class MasterTimelineViewController: UITableViewController, UndoableCommandRunner
guard let article = dataSource.itemIdentifier(for: indexPath) else { return nil }
return UIContextMenuConfiguration(identifier: nil, previewProvider: nil, actionProvider: { [weak self] suggestedActions in
return UIContextMenuConfiguration(identifier: indexPath.row as NSCopying, previewProvider: nil, actionProvider: { [weak self] suggestedActions in
guard let self = self else { return nil }
@ -317,6 +317,15 @@ class MasterTimelineViewController: UITableViewController, UndoableCommandRunner
}
override func tableView(_ tableView: UITableView, previewForHighlightingContextMenuWithConfiguration configuration: UIContextMenuConfiguration) -> UITargetedPreview? {
guard let row = configuration.identifier as? Int,
let cell = tableView.cellForRow(at: IndexPath(row: row, section: 0)) else {
return nil
}
return UITargetedPreview(view: cell, parameters: CroppingPreviewParameters(view: cell))
}
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
becomeFirstResponder()
let article = dataSource.itemIdentifier(for: indexPath)

View File

@ -0,0 +1,20 @@
//
// CroppingPreviewParameters.swift
// NetNewsWire-iOS
//
// Created by Maurice Parker on 11/23/19.
// Copyright © 2019 Ranchero Software. All rights reserved.
//
import UIKit
class CroppingPreviewParameters: UIPreviewParameters {
init(view: UIView) {
super.init()
let newBounds = CGRect(x: 1, y: 1, width: view.bounds.width - 2, height: view.bounds.height - 2)
let visiblePath = UIBezierPath(roundedRect: newBounds, cornerRadius: 10)
self.visiblePath = visiblePath
}
}

@ -1 +1 @@
Subproject commit 3dc1c288bb4e15fedf17fa8fc43c1d5cec36af5e
Subproject commit a041d4fc0e45077d28386e7efe4fca3a175584ad