繁体   English   中英

Swift:展示了两个视图控制器

[英]Swift: Two View Controllers presented

为问题的模棱两可道歉; 我将尝试在这里更清楚地解释。

问题

我在AppDelegate.swift中有一些执行条件导航的代码; 如果用户已登录(因此currentUser不是nil ),应用程序将在View中启动,即Main storyboard 中的 View Controller。 否则,如果用户未登录,应用程序将在Welcome中启动,在Auth storyboard 中查看 Controller。

以下是来自AppDelegate.swiftViewController.swift (即View )和WelcomeViewController的代码。

笔记:

View是我为ViewController设置的 Storyboard ID; Welcome是我为 WelcomeViewController 设置的WelcomeViewController ID。

AppDelegate.swift

import UIKit
import Firebase

@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {

    var window: UIWindow?

    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {

        // Configures the Firebase library.
        FirebaseApp.configure()

        // Performs conditional navigation on the condition of currentUser's status.
        self.window = UIWindow(frame: UIScreen.main.bounds)
        let user = Auth.auth().currentUser
        if user != nil {
            let storyboard = UIStoryboard(name: "Main", bundle: nil)
            let rootViewController = storyboard.instantiateViewController(identifier: "View")
            window?.rootViewController = rootViewController
            UIView.animate(withDuration: 0.5) {
                self.window?.makeKeyAndVisible()
            }
        } else {
            let storyboard = UIStoryboard(name: "Auth", bundle: nil)
            let rootViewController = storyboard.instantiateViewController(identifier: "Welcome")
            window?.rootViewController = rootViewController
            UIView.animate(withDuration: 0.5) {
                self.window?.makeKeyAndVisible()
            }
        }

        return true
    }

}

ViewController.swift

import UIKit

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        // Do any additional setup after loading the view.
        print("ViewController presented.")
    }

}

WelcomeViewController.swift

import UIKit

class WelcomeViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        // Do any additional setup after loading the view.
        print("WelcomeViewController presented.")
    }

}

期望

该应用程序是新安装在模拟器上的,因此应该没有currentUser (并且在调试时证明是真的)。 因此,我希望在控制台中将其视为 output:

WelcomeViewController presented.

相反,这会显示在控制台中:

WelcomeViewController presented.
ViewController presented.

尝试

到目前为止,我认为问题可能是由于Main storyboard 是自项目创建以来设置的默认 Storyboard 。 因此,我尝试取消选中两个视图控制器的“初始视图控制器”复选框。 就像我预期的那样,出现了以下内容:

WelcomeViewController presented.
2020-06-20 11:39:38.724658+0800 AppName[11439:237509] [WindowScene] Failed to instantiate the default view controller for UIMainStoryboardFile 'Main' - perhaps the designated entry point is not set?

我应该怎么做才能确保ViewController不出现并替换WelcomeViewController 感谢所有帮助,谢谢!

为什么不将 WelcomeViewController 设置为您的“初始视图控制器”,然后用 AppDelegate 文件替换其 viewDidLoad 代码:

class WelcomeViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        // Do any additional setup after loading the view.
        print("WelcomeViewController presented.")

        let user = Auth.auth().currentUser
        if user != nil {
            let storyboard = UIStoryboard(name: "Main", bundle: nil)
            let rootViewController = storyboard.instantiateViewController(identifier: "View")
            window?.rootViewController = rootViewController
            UIView.animate(withDuration: 0.5) {
                self.window?.makeKeyAndVisible()
            }
        } 
    }

}

如果你想从 AppDelegate 设置视图 controller,你也可以看看这个:

编辑:您可以使用 UINavigationController 作为您的初始视图 controller,如本答案所示:

在 appdelegate 中设置初始视图控制器 - swift然后您只需在此处设置正确的视图 controller :

navigationController.viewControllers = [rootViewController]
self.window?.rootViewController = navigationController

解决方案

我设法找到了我在这里面临的问题的解决方案。 上面的代码有两个错误,我在这里解释一下:

错误一:代码应该在SceneDelegate而不是AppDelegate (iOS 13)

Xcode 11,随着 iOS 13 的发布,引入了SceneDelegate.swift 我应该把我的代码放在SceneDelegate.swift而不是AppDelegate.swift 因为我没有这样做,所以代码没有像我希望的那样运行在运行 iOS 13.5 的模拟器上。

这是我在SceneDelegate.swift中的更正代码:

import UIKit
import Firebase

class SceneDelegate: UIResponder, UIWindowSceneDelegate {

    var window: UIWindow?

    func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
        // Use this method to optionally configure and attach the UIWindow `window` to the provided UIWindowScene `scene`.
        // If using a storyboard, the `window` property will automatically be initialized and attached to the scene.
        // This delegate does not imply the connecting scene or session are new (see `application:configurationForConnectingSceneSession` instead).
        guard let _ = (scene as? UIWindowScene) else { return }

        // Performs conditional navigation on the condition of currentUser's status.
        let user = Auth.auth().currentUser
        if user != nil {
            let storyboard = UIStoryboard(name: "Main", bundle: nil)
            let rootViewController = storyboard.instantiateViewController(identifier: "View")
            window?.rootViewController = rootViewController
            UIView.animate(withDuration: 0.5) {
                self.window?.makeKeyAndVisible()
            }
        } else {
            let storyboard = UIStoryboard(name: "Auth", bundle: nil)
            let rootViewController = storyboard.instantiateViewController(identifier: "Welcome")
            window?.rootViewController = rootViewController
            UIView.animate(withDuration: 0.5) {
                self.window?.makeKeyAndVisible()
            }
        }
    }

}

错误2(重要:):新UIWindow的定义

在我上面的代码中,有一条错误的行导致创建了一个新的UIWindow

self.window = UIWindow(frame: UIScreen.main.bounds)

通过删除这行代码,问题得到解决。 这是修正后的代码:

let user = Auth.auth().currentUser
if user != nil {
    let storyboard = UIStoryboard(name: "Main", bundle: nil)
    let rootViewController = storyboard.instantiateViewController(identifier: "View")
    window?.rootViewController = rootViewController
    UIView.animate(withDuration: 0.5) {
        self.window?.makeKeyAndVisible()
    }
} else {
    let storyboard = UIStoryboard(name: "Auth", bundle: nil)
    let rootViewController = storyboard.instantiateViewController(identifier: "Welcome")
    window?.rootViewController = rootViewController
    UIView.animate(withDuration: 0.5) {
        self.window?.makeKeyAndVisible()
    }
}

我希望这可以帮助其他面临这个问题的人!

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM