ios - 从 UITabBarController 内部呈现 UINavigationController

标签 ios swift cocoa-touch uikit

我有一个关于从 AppDelegate 实例化特定 View Controller 的快速问题。我正在构建一个简单的聊天应用程序,当用户通过远程通知打开应用程序时需要响应。我的应用程序所需的行为是,当用户点击此通知时,应用程序将打开到该特定的聊天屏幕。

应用程序的基本流程如下:

  • 最高级别的 UI 组件是 UITabBarController
  • 此标签栏内是一个导航 Controller
  • 导航 Controller 内部是一个 View Controller (我们称之为“列表”),它列出了所有可用的聊天窗口
  • 一旦用户点击我的表格 View 中列出聊天的一行,就会推送一个新的 View Controller 。该 View Controller 是聊天窗口,它自动隐藏标签栏,但保留导航 Controller 的后退按钮
  • 当用户点击后退按钮时,它将返回到聊天列表,并且标签栏将重新出现

我使用以下代码来显示正确的聊天屏幕。我可以点击后退按钮,它将按预期返回到聊天列表。唯一的问题是导航 Controller 没有嵌入到选项卡 Controller 中。此代码是从 func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler finishHandler:

调用的
let mainStoryboard : UIStoryboard = UIStoryboard(name: "Main", bundle: nil)
let initialVC : UIViewController = mainStoryboard.instantiateViewController(withIdentifier: "ChatVC") as UIViewController
let detailVC : UIViewController = mainStoryboard.instantiateViewController(withIdentifier: "ChatDetailVC") as UIViewController
let navContr = UINavigationController(rootViewController:initialVC)
self.window = UIWindow(frame: UIScreen.main.bounds)
self.window?.rootViewController = navContr
self.window?.makeKeyAndVisible()
initialVC.navigationController?.pushViewController(detailVC, animated: true)

如何配置我的代码以使选项卡 Controller 位于堆栈的顶层?它在我的 Storyboard中被标记为“TabController”。

最佳答案

您只需要创建一个标志来确定用户是来自通知点击还是正常启动

struct NotificationEvent {
    static var isFromNotification = false
}

Controller 的堆栈是-

TabBarController->UINavigationController->ChatListViewController->ChatDetailViewController

在 AppDelegate 中 func userNotificationCenter -

let storyboard = UIStoryboard(name: "Main", bundle: nil)
let vc = storyboard.instantiateViewController(withIdentifier: "TabViewController") as! TabViewController//Your Tabbarcontroller
NotificationEvent.isFromNotification = true//recognize is from notification 
window?.rootViewController = vc

ChatListViewController

class ChatListViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()
        if NotificationEvent.isFromNotification  {
            openChatDetailScreen()//Jumps to that chat screen
            NotificationEvent.isFromNotification = false
        }
    }
    @IBAction func tapsOnChatList(_ sender: UIButton) {//consider it as didselect method in your tableView
        openChatDetailScreen()
    }

    func openChatDetailScreen() {
        let vc = self.storyboard?.instantiateViewController(withIdentifier: "ChatDetailViewController") as! ChatDetailViewController
        navigationController?.pushViewController(vc, animated: true)
    }
}

或者,而不是 NotificationEvent.isFromNotification,您还可以使用 UIApplicationLaunchOptionsKey.remoteNotification/observer 检查特定 View Controller 中的通知事件。

关于ios - 从 UITabBarController 内部呈现 UINavigationController,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47973537/

相关文章:

ios - 使数组中的 3 个随机元素不可见

iPhone 编程 - 在 View Controller 之间传递 NSMutableArray

ios - 更新 RealmSwift 中的对象?

iOS:从主屏幕上的书签启动自定义应用程序

ios - 如何在 iOS7 中搜索 NSString 句子中用逗号分隔的特定单词?

ios - 实现可以在 Bolts Framework 中取消的任务 (BFTask)

ios - Delphi XE4 和 Xamarin Monotouch 在针对 iOS 的方式上有何不同?

ios - 将转义的 unicode char[] 转换为 NSString

android - 是否可以通过页内链接在 iOS 和 Android 中调用 native 共享功能?

swift - 如何在谷歌地图顶部添加标签栏?