forked from shadowfacts/Tusker
Revert "Fix crash when opening push notification while VC modally presented"
This reverts commit 0f2a85b1088cd7d8a27924b37715c465c2a52420. This fixes state restoration happening asynchronously and causing the new tab bar animation to run.
This commit is contained in:
parent
b663335c6d
commit
2eead1f9de
@ -295,10 +295,9 @@ extension AppDelegate: UNUserNotificationCenterDelegate {
|
||||
// if the scene is already active, then we animate the account switching if necessary
|
||||
delegate.activateAccount(account, animated: scene.activationState == .foregroundActive)
|
||||
|
||||
rootViewController.select(route: .notifications, animated: false) {
|
||||
let vc = NotificationLoadingViewController(notificationID: notificationID, mastodonController: mastodonController)
|
||||
rootViewController.getNavigationController().pushViewController(vc, animated: false)
|
||||
}
|
||||
rootViewController.select(route: .notifications, animated: false)
|
||||
let vc = NotificationLoadingViewController(notificationID: notificationID, mastodonController: mastodonController)
|
||||
rootViewController.getNavigationController().pushViewController(vc, animated: false)
|
||||
} else {
|
||||
let activity = UserActivityManager.showNotificationActivity(id: notificationID, accountID: accountID)
|
||||
if #available(iOS 17.0, *) {
|
||||
|
@ -83,9 +83,7 @@ class MainSceneDelegate: UIResponder, UIWindowSceneDelegate, TuskerSceneDelegate
|
||||
} else {
|
||||
context = ActiveAccountUserActivityHandlingContext(isHandoff: true, root: rootViewController!)
|
||||
}
|
||||
Task(priority: .userInitiated) {
|
||||
_ = await userActivity.handleResume(manager: UserActivityManager(scene: scene as! UIWindowScene, context: context))
|
||||
}
|
||||
_ = userActivity.handleResume(manager: UserActivityManager(scene: scene as! UIWindowScene, context: context))
|
||||
}
|
||||
|
||||
func windowScene(_ windowScene: UIWindowScene, performActionFor shortcutItem: UIApplicationShortcutItem, completionHandler: @escaping (Bool) -> Void) {
|
||||
@ -193,10 +191,8 @@ class MainSceneDelegate: UIResponder, UIWindowSceneDelegate, TuskerSceneDelegate
|
||||
|
||||
if let activity = launchActivity {
|
||||
func doRestoreActivity(context: UserActivityHandlingContext) {
|
||||
Task(priority: .userInitiated) {
|
||||
_ = await activity.handleResume(manager: UserActivityManager(scene: window!.windowScene!, context: context))
|
||||
context.finalize(activity: activity)
|
||||
}
|
||||
_ = activity.handleResume(manager: UserActivityManager(scene: window!.windowScene!, context: context))
|
||||
context.finalize(activity: activity)
|
||||
}
|
||||
if activity.isStateRestorationActivity {
|
||||
doRestoreActivity(context: StateRestorationUserActivityHandlingContext(root: rootViewController!))
|
||||
|
@ -79,12 +79,10 @@ class AccountSwitchingContainerViewController: UIViewController {
|
||||
stateRestorationLogger.debug("AccountSwitchingContainer: reusing existing VC for \(account.id, privacy: .public)")
|
||||
} else {
|
||||
newRoot = newRootProvider()
|
||||
Task(priority: .userInitiated) {
|
||||
stateRestorationLogger.debug("AccountSwitchingContainer: restoring \(activity.activityType, privacy: .public) for \(account.id, privacy: .public)")
|
||||
let context = StateRestorationUserActivityHandlingContext(root: newRoot)
|
||||
_ = await activity.handleResume(manager: UserActivityManager(scene: view.window!.windowScene!, context: context))
|
||||
context.finalize(activity: activity)
|
||||
}
|
||||
stateRestorationLogger.debug("AccountSwitchingContainer: restoring \(activity.activityType, privacy: .public) for \(account.id, privacy: .public)")
|
||||
let context = StateRestorationUserActivityHandlingContext(root: newRoot)
|
||||
_ = activity.handleResume(manager: UserActivityManager(scene: view.window!.windowScene!, context: context))
|
||||
context.finalize(activity: activity)
|
||||
}
|
||||
} else {
|
||||
newRoot = newRootProvider()
|
||||
@ -161,9 +159,9 @@ extension AccountSwitchingContainerViewController: TuskerRootViewController {
|
||||
root.compose(editing: draft, animated: animated, isDucked: isDucked, completion: completion)
|
||||
}
|
||||
|
||||
func select(route: TuskerRoute, animated: Bool, completion: (() -> Void)?) {
|
||||
func select(route: TuskerRoute, animated: Bool) {
|
||||
loadViewIfNeeded()
|
||||
root.select(route: route, animated: animated, completion: completion)
|
||||
root.select(route: route, animated: animated)
|
||||
}
|
||||
|
||||
func getNavigationDelegate() -> TuskerNavigationDelegate? {
|
||||
|
@ -35,8 +35,8 @@ extension DuckableContainerViewController: AccountSwitchableViewController {
|
||||
(child as! TuskerRootViewController).getNavigationController()
|
||||
}
|
||||
|
||||
func select(route: TuskerRoute, animated: Bool, completion: (() -> Void)?) {
|
||||
(child as? TuskerRootViewController)?.select(route: route, animated: animated, completion: completion)
|
||||
func select(route: TuskerRoute, animated: Bool) {
|
||||
(child as? TuskerRootViewController)?.select(route: route, animated: animated)
|
||||
}
|
||||
|
||||
func performSearch(query: String) {
|
||||
|
@ -546,14 +546,14 @@ extension MainSplitViewController: StateRestorableViewController {
|
||||
}
|
||||
|
||||
extension MainSplitViewController: TuskerRootViewController {
|
||||
func select(route: TuskerRoute, animated: Bool, completion: (() -> Void)?) {
|
||||
func select(route: TuskerRoute, animated: Bool) {
|
||||
guard traitCollection.horizontalSizeClass != .compact else {
|
||||
tabBarViewController?.select(route: route, animated: animated, completion: completion)
|
||||
tabBarViewController?.select(route: route, animated: animated)
|
||||
return
|
||||
}
|
||||
guard presentedViewController == nil else {
|
||||
dismiss(animated: animated) {
|
||||
self.select(route: route, animated: animated, completion: completion)
|
||||
self.select(route: route, animated: animated)
|
||||
}
|
||||
return
|
||||
}
|
||||
@ -579,7 +579,6 @@ extension MainSplitViewController: TuskerRootViewController {
|
||||
let oldItem = sidebar.selectedItem
|
||||
sidebar.select(item: item, animated: false)
|
||||
select(newItem: item, oldItem: oldItem)
|
||||
completion?()
|
||||
}
|
||||
|
||||
func getNavigationDelegate() -> TuskerNavigationDelegate? {
|
||||
|
@ -148,7 +148,7 @@ extension MainTabBarViewController: UITabBarControllerDelegate {
|
||||
}
|
||||
|
||||
extension MainTabBarViewController: TuskerRootViewController {
|
||||
func select(route: TuskerRoute, animated: Bool, completion: (() -> Void)?) {
|
||||
func select(route: TuskerRoute, animated: Bool) {
|
||||
switch route {
|
||||
case .timelines:
|
||||
select(tab: .timelines, dismissPresented: true)
|
||||
@ -169,7 +169,6 @@ extension MainTabBarViewController: TuskerRootViewController {
|
||||
nav.pushViewController(ListTimelineViewController(for: list, mastodonController: mastodonController), animated: animated)
|
||||
}
|
||||
}
|
||||
completion?()
|
||||
}
|
||||
|
||||
func getNavigationDelegate() -> TuskerNavigationDelegate? {
|
||||
|
@ -12,7 +12,8 @@ import ComposeUI
|
||||
@MainActor
|
||||
protocol TuskerRootViewController: UIViewController, StateRestorableViewController, StatusBarTappableViewController {
|
||||
func compose(editing draft: Draft?, animated: Bool, isDucked: Bool, completion: (() -> Void)?)
|
||||
func select(route: TuskerRoute, animated: Bool, completion: (() -> Void)?)
|
||||
func select(route: TuskerRoute, animated: Bool)
|
||||
func getTabController(tab: MainTabBarViewController.Tab) -> UIViewController?
|
||||
func getNavigationDelegate() -> TuskerNavigationDelegate?
|
||||
func getNavigationController() -> NavigationControllerProtocol
|
||||
func performSearch(query: String)
|
||||
|
@ -44,9 +44,9 @@ enum AppShortcutItem: String, CaseIterable {
|
||||
}
|
||||
switch self {
|
||||
case .showHomeTimeline:
|
||||
root.select(route: .timelines, animated: false, completion: nil)
|
||||
root.select(route: .timelines, animated: false)
|
||||
case .showNotifications:
|
||||
root.select(route: .notifications, animated: false, completion: nil)
|
||||
root.select(route: .notifications, animated: false)
|
||||
case .composePost:
|
||||
root.compose(editing: nil, animated: false, isDucked: false, completion: nil)
|
||||
}
|
||||
|
@ -43,9 +43,9 @@ extension NSUserActivity {
|
||||
}
|
||||
|
||||
@MainActor
|
||||
func handleResume(manager: UserActivityManager) async -> Bool {
|
||||
func handleResume(manager: UserActivityManager) -> Bool {
|
||||
guard let type = UserActivityType(rawValue: activityType) else { return false }
|
||||
await type.handle(manager)(self)
|
||||
type.handle(manager)(self)
|
||||
return true
|
||||
}
|
||||
|
||||
|
@ -16,8 +16,7 @@ import ComposeUI
|
||||
protocol UserActivityHandlingContext {
|
||||
var isHandoff: Bool { get }
|
||||
|
||||
func select(route: TuskerRoute) async
|
||||
func select(route: TuskerRoute, completion: (() -> Void)?)
|
||||
func select(route: TuskerRoute)
|
||||
func present(_ vc: UIViewController)
|
||||
|
||||
var topViewController: UIViewController? { get }
|
||||
@ -29,16 +28,6 @@ protocol UserActivityHandlingContext {
|
||||
func finalize(activity: NSUserActivity)
|
||||
}
|
||||
|
||||
extension UserActivityHandlingContext {
|
||||
func select(route: TuskerRoute) async {
|
||||
await withCheckedContinuation { continuation in
|
||||
select(route: route) {
|
||||
continuation.resume()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct ActiveAccountUserActivityHandlingContext: UserActivityHandlingContext {
|
||||
let isHandoff: Bool
|
||||
let root: TuskerRootViewController
|
||||
@ -46,8 +35,8 @@ struct ActiveAccountUserActivityHandlingContext: UserActivityHandlingContext {
|
||||
root.getNavigationDelegate()!
|
||||
}
|
||||
|
||||
func select(route: TuskerRoute, completion: (() -> Void)?) {
|
||||
root.select(route: route, animated: true, completion: completion)
|
||||
func select(route: TuskerRoute) {
|
||||
root.select(route: route, animated: true)
|
||||
}
|
||||
|
||||
func present(_ vc: UIViewController) {
|
||||
@ -82,11 +71,9 @@ class StateRestorationUserActivityHandlingContext: UserActivityHandlingContext {
|
||||
|
||||
var isHandoff: Bool { false }
|
||||
|
||||
func select(route: TuskerRoute, completion: (() -> Void)?) {
|
||||
root.select(route: route, animated: false) {
|
||||
self.state = .selectedRoute
|
||||
completion?()
|
||||
}
|
||||
func select(route: TuskerRoute) {
|
||||
root.select(route: route, animated: false)
|
||||
state = .selectedRoute
|
||||
}
|
||||
|
||||
var topViewController: UIViewController? { root.getNavigationController().topViewController }
|
||||
|
@ -133,8 +133,8 @@ class UserActivityManager {
|
||||
return activity
|
||||
}
|
||||
|
||||
func handleCheckNotifications(activity: NSUserActivity) async {
|
||||
await context.select(route: .notifications)
|
||||
func handleCheckNotifications(activity: NSUserActivity) {
|
||||
context.select(route: .notifications)
|
||||
context.popToRoot()
|
||||
if let notificationsPageController = context.topViewController as? NotificationsPageViewController {
|
||||
notificationsPageController.loadViewIfNeeded()
|
||||
@ -204,22 +204,22 @@ class UserActivityManager {
|
||||
return (timeline, positionInfo)
|
||||
}
|
||||
|
||||
func handleShowTimeline(activity: NSUserActivity) async {
|
||||
func handleShowTimeline(activity: NSUserActivity) {
|
||||
guard let (timeline, positionInfo) = Self.getTimeline(from: activity) else { return }
|
||||
|
||||
var timelineVC: TimelineViewController?
|
||||
if let pinned = PinnedTimeline(timeline: timeline),
|
||||
mastodonController.accountPreferences.pinnedTimelines.contains(pinned) {
|
||||
await context.select(route: .timelines)
|
||||
context.select(route: .timelines)
|
||||
context.popToRoot()
|
||||
let pageController = context.topViewController as! TimelinesPageViewController
|
||||
pageController.selectTimeline(pinned, animated: false)
|
||||
timelineVC = pageController.currentViewController as? TimelineViewController
|
||||
} else if case .list(let id) = timeline {
|
||||
await context.select(route: .list(id: id))
|
||||
context.select(route: .list(id: id))
|
||||
timelineVC = context.topViewController as? TimelineViewController
|
||||
} else {
|
||||
await context.select(route: .explore)
|
||||
context.select(route: .explore)
|
||||
context.popToRoot()
|
||||
timelineVC = TimelineViewController(for: timeline, mastodonController: mastodonController)
|
||||
context.push(timelineVC!)
|
||||
@ -249,11 +249,11 @@ class UserActivityManager {
|
||||
return activity.userInfo?["mainStatusID"] as? String
|
||||
}
|
||||
|
||||
func handleShowConversation(activity: NSUserActivity) async {
|
||||
func handleShowConversation(activity: NSUserActivity) {
|
||||
guard let mainStatusID = Self.getConversationStatus(from: activity) else {
|
||||
return
|
||||
}
|
||||
await context.select(route: .timelines)
|
||||
context.select(route: .timelines)
|
||||
context.push(ConversationViewController(for: mainStatusID, state: .unknown, mastodonController: mastodonController))
|
||||
}
|
||||
|
||||
@ -274,8 +274,8 @@ class UserActivityManager {
|
||||
return activity.userInfo?["query"] as? String
|
||||
}
|
||||
|
||||
func handleSearch(activity: NSUserActivity) async {
|
||||
await context.select(route: .explore)
|
||||
func handleSearch(activity: NSUserActivity) {
|
||||
context.select(route: .explore)
|
||||
context.popToRoot()
|
||||
|
||||
let searchController: UISearchController
|
||||
@ -311,8 +311,8 @@ class UserActivityManager {
|
||||
return activity
|
||||
}
|
||||
|
||||
func handleBookmarks(activity: NSUserActivity) async {
|
||||
await context.select(route: .bookmarks)
|
||||
func handleBookmarks(activity: NSUserActivity) {
|
||||
context.select(route: .bookmarks)
|
||||
}
|
||||
|
||||
// MARK: - My Profile
|
||||
@ -325,8 +325,8 @@ class UserActivityManager {
|
||||
return activity
|
||||
}
|
||||
|
||||
func handleMyProfile(activity: NSUserActivity) async {
|
||||
await context.select(route: .myProfile)
|
||||
func handleMyProfile(activity: NSUserActivity) {
|
||||
context.select(route: .myProfile)
|
||||
}
|
||||
|
||||
// MARK: - Show Profile
|
||||
@ -344,11 +344,11 @@ class UserActivityManager {
|
||||
return activity.userInfo?["profileID"] as? String
|
||||
}
|
||||
|
||||
func handleShowProfile(activity: NSUserActivity) async {
|
||||
func handleShowProfile(activity: NSUserActivity) {
|
||||
guard let accountID = Self.getProfile(from: activity) else {
|
||||
return
|
||||
}
|
||||
await context.select(route: .timelines)
|
||||
context.select(route: .timelines)
|
||||
context.push(ProfileViewController(accountID: accountID, mastodonController: mastodonController))
|
||||
}
|
||||
|
||||
@ -361,11 +361,11 @@ class UserActivityManager {
|
||||
return activity
|
||||
}
|
||||
|
||||
func handleShowNotification(activity: NSUserActivity) async {
|
||||
func handleShowNotification(activity: NSUserActivity) {
|
||||
guard let notificationID = activity.userInfo?["notificationID"] as? String else {
|
||||
return
|
||||
}
|
||||
await context.select(route: .notifications)
|
||||
context.select(route: .notifications)
|
||||
context.push(NotificationLoadingViewController(notificationID: notificationID, mastodonController: mastodonController))
|
||||
}
|
||||
|
||||
|
@ -23,7 +23,7 @@ enum UserActivityType: String {
|
||||
|
||||
extension UserActivityType {
|
||||
@MainActor
|
||||
var handle: (UserActivityManager) -> @MainActor (NSUserActivity) async -> Void {
|
||||
var handle: (UserActivityManager) -> @MainActor (NSUserActivity) -> Void {
|
||||
switch self {
|
||||
case .mainScene:
|
||||
fatalError("cannot handle main scene activity")
|
||||
|
Loading…
x
Reference in New Issue
Block a user