UIView
UIView
objectsUIViewController
UIView
UITabBarController
UIViewController
accessible via a button bar (abottom)UINavigationController
UIViewController
and a navigation bar (atop)pushViewController()
, popViewController()
)"delegate"
didSelect()
[2]didSelect()
"coordinator"
UINavigationController
as argument on construction
and call eg. pushViewController()
to navigate to other view controllers"coordinator protocol"
UIApplication
UIApplication
[1]UIApplicationMain()
or by adding the attribute @UIApplicationMain
to a class derived from UIApplicationDelegate
application(_:didFinishLaunchingWithOptions:)
[4]UIApplicationDelegate
applicationWillEnterForeground()
UIApplicationDelegate
and pass this to UIApplicationMain
UIApplication.shared.delegate
will keep a reference to our delegateUIWindow
UIView
UIApplication.shared.delegate.window
,application(_:didFinishLaunchingWithOptions:)
;
in pure iOS13 apps set in SceneDelegatewindow.rootViewController
is the anchor of all view controllersa tricky part (see eg. [3]) seems to be to hold the correct type of references to the UIViewControllers.
at least one "strong" (normal) reference is needed somewhere.
only "weak" or "unowned" references are not sufficient ("weak" always needs unwrap and may be come nil at any time, "unowned" is kind of always-unwrapped "weak").
currently, we hold strong references to the coordinators which hold strong references to the view controllers
"delegates" are needed to get events from the system
we need some dead-simple way to persist the objects that need persistance
do we need our own delegates? or just call funcions directly as needed? what is the current state?
is the overhead of "coordinator" really needed and helpful?
pushViewController()
and make sure it is persisted as needed
(coordinators would not help on that imu anyway, see bug at [3])AppCoordinator
is also derived from NSObject - is there a know reason for that?however, the coordinator get the UINavigationContoller as argument, so there is some use
remove "coordinator protocol" and do not use?
the tearing up of navigator/coordinator into two files is unfortunate, in swiftUI, this is re-combined to a single file, child-class and a makeCoordinator() called by SwiftUI: https://developer.apple.com/tutorials/swiftui/interfacing-with-uikit
NotificationCenter.default.post()
post events to all observers synchronously on the same thread;
this may not be the thread the observer registered itself [5].
Observers may receive the event in any random thread therefore.
best practise [6] would be that the observers assume,
they receive the notification in any thread
and call DispatchQueue.main.async
where actually needed.
for new code, we should use that approach, it won't hurt.
however, existing code might assume
that the notification arrives in main thread;
therefore, we also call DispatchQueue.main.async
for sending events out.
using always main thread for sending/receiving and adding/remove observers also avoids other multithreading-issues of NotificationCenter itself, see https://lapcatsoftware.com/articles/nsnotificationcenter-is-threadsafe-not.html for details.
tl;dr: post from main thread and also add/remove observers from main thread. on receiving, assume, things will block.
for the addObserver()
variant returning an object
(overview at https://developer.apple.com/documentation/foundation/notificationcenter )
always save the object as NSObjectProtocol
not as Any?
-
otherwise you risk to mix addObserver() functions as also
the non-return variant can be saved as Any?
(Swift allows saving "no return type" as Any?
)
call removeObserver(self)
only in deinit,
otherwise use removeObserver(self, name, obj)
or removeObserver(obj)
[1] https://developer.apple.com/documentation/uikit/uiapplication
[2] delegator/delegate: https://stackoverflow.com/questions/7052926/what-is-the-purpose-of-an-ios-delegate https://developer.apple.com/library/archive/documentation/General/Conceptual/DevPedia-CocoaCore/Delegation.html
[3] weak coordinator bugs: https://github.com/deltachat/deltachat-ios/issues/675, https://github.com/deltachat/deltachat-ios/issues/323
[4] https://developer.apple.com/documentation/uikit/uiapplicationdelegate/1622921-application
[6] https://medium.com/@hadhi631/myths-and-facts-about-nsnotifcation-posting-and-receiving-df7f5729b19f