Skip to content

Commit cec3c1b

Browse files
committed
Improve DetailCoordinator presented item replacement for multiple items
1 parent b220861 commit cec3c1b

File tree

3 files changed

+42
-10
lines changed

3 files changed

+42
-10
lines changed

Zotero/Controllers/Architecture/Coordinator.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ enum SourceView {
1616
protocol Coordinator: AnyObject {
1717
var parentCoordinator: Coordinator? { get }
1818
var childCoordinators: [Coordinator] { get set }
19-
var navigationController: UINavigationController? { get }
19+
var navigationController: UINavigationController? { get set }
2020

2121
func start(animated: Bool)
2222
func childDidFinish(_ child: Coordinator)

Zotero/Scenes/Detail/DetailCoordinator.swift

Lines changed: 17 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -288,10 +288,10 @@ final class DetailCoordinator: Coordinator {
288288
navigationController.present(controller, animated: true, completion: nil)
289289
}
290290

291-
func createPDFController(key: String, library: Library, url: URL, page: Int? = nil, preselectedAnnotationKey: String? = nil) -> NavigationViewController {
292-
let navigationController = NavigationViewController()
291+
func createPDFController(key: String, library: Library, url: URL, page: Int? = nil, preselectedAnnotationKey: String? = nil) -> DetailNavigationViewController {
292+
let navigationController = DetailNavigationViewController()
293293
navigationController.modalPresentationStyle = .fullScreen
294-
294+
295295
let coordinator = PDFCoordinator(
296296
key: key,
297297
library: library,
@@ -301,6 +301,7 @@ final class DetailCoordinator: Coordinator {
301301
navigationController: navigationController,
302302
controllers: controllers
303303
)
304+
navigationController.coordinator = coordinator
304305
coordinator.parentCoordinator = self
305306
childCoordinators.append(coordinator)
306307
coordinator.start(animated: false)
@@ -312,10 +313,14 @@ final class DetailCoordinator: Coordinator {
312313
guard let navigationController else { return }
313314
controllers.userControllers?.openItemsController.open(.pdf(libraryId: library.identifier, key: key), for: sessionIdentifier)
314315

315-
let viewControllerProvider: () -> UIViewController = {
316+
let viewControllerProvider: () -> DetailNavigationViewController = {
316317
self.createPDFController(key: key, library: library, url: url)
317318
}
318319
if let presentedViewController = navigationController.presentedViewController {
320+
if let presentedDetailNavigationController = presentedViewController as? DetailNavigationViewController {
321+
presentedDetailNavigationController.replaceContents(with: viewControllerProvider(), animated: false)
322+
return
323+
}
319324
guard let window = presentedViewController.view.window else { return }
320325
show(viewControllerProvider: viewControllerProvider, by: navigationController, in: window, animated: false)
321326
return
@@ -468,8 +473,8 @@ extension DetailCoordinator: DetailItemsCoordinatorDelegate {
468473
tags: [Tag],
469474
title: NoteEditorState.TitleData?,
470475
saveCallback: @escaping NoteEditorSaveCallback
471-
) -> NavigationViewController {
472-
let navigationController = NavigationViewController()
476+
) -> DetailNavigationViewController {
477+
let navigationController = DetailNavigationViewController()
473478
navigationController.modalPresentationStyle = .fullScreen
474479
navigationController.isModalInPresentation = true
475480

@@ -484,6 +489,7 @@ extension DetailCoordinator: DetailItemsCoordinatorDelegate {
484489
sessionIdentifier: sessionIdentifier,
485490
controllers: controllers
486491
)
492+
navigationController.coordinator = coordinator
487493
coordinator.parentCoordinator = self
488494
childCoordinators.append(coordinator)
489495
coordinator.start(animated: false)
@@ -948,10 +954,14 @@ extension DetailCoordinator: DetailNoteEditorCoordinatorDelegate {
948954
controllers.userControllers?.openItemsController.open(.note(libraryId: library.identifier, key: key), for: sessionIdentifier)
949955
}
950956

951-
let viewControllerProvider: () -> UIViewController = {
957+
let viewControllerProvider: () -> DetailNavigationViewController = {
952958
self.createNoteController(library: library, kind: kind, text: text, tags: tags, title: title, saveCallback: amendedSaveCallback)
953959
}
954960
if let presentedViewController = navigationController.presentedViewController {
961+
if let presentedDetailNavigationController = presentedViewController as? DetailNavigationViewController {
962+
presentedDetailNavigationController.replaceContents(with: viewControllerProvider(), animated: false)
963+
return
964+
}
955965
guard let window = presentedViewController.view.window else { return }
956966
show(viewControllerProvider: viewControllerProvider, by: navigationController, in: window, animated: false)
957967
return

Zotero/Scenes/General/Views/NavigationViewController.swift

Lines changed: 24 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,32 @@ class NavigationViewController: UINavigationController {
1313
var statusBarVisible: Bool = true
1414

1515
override var prefersStatusBarHidden: Bool {
16-
return !self.statusBarVisible
16+
return !statusBarVisible
1717
}
1818

1919
deinit {
20-
self.dismissHandler?()
20+
dismissHandler?()
21+
}
22+
}
23+
24+
class DetailNavigationViewController: NavigationViewController {
25+
weak var coordinator: Coordinator?
26+
public func replaceContents(with replacement: DetailNavigationViewController, animated: Bool) {
27+
// Set replacement properties to self.
28+
// Swap coordinators and dismiss handlers, so that the original coordinator is properly deinitialized, along with the original view controllers.
29+
// Swap also the navigation controller property of the two coordinators.
30+
// Store original
31+
let originalCoordinator = coordinator
32+
let originalDismissHandler = dismissHandler
33+
// Swap replacement to original
34+
coordinator = replacement.coordinator
35+
coordinator?.navigationController = self
36+
dismissHandler = replacement.dismissHandler
37+
statusBarVisible = replacement.statusBarVisible
38+
setViewControllers(replacement.viewControllers, animated: animated)
39+
// Swap original to replacement
40+
replacement.coordinator = originalCoordinator
41+
replacement.coordinator?.navigationController = replacement
42+
replacement.dismissHandler = originalDismissHandler
2143
}
2244
}

0 commit comments

Comments
 (0)