【问题标题】:Present modal view controller over view controller at launch在启动时在视图控制器上显示模态视图控制器
【发布时间】:2015-03-05 03:53:45
【问题描述】:

在我的AppDelegate.m 中,我有以下代码在启动时为用户设置初始视图控制器,具体取决于钥匙串中是否存储了凭据。

如果用户确实存储了凭据,则应用程序将使用故事板 ID balancescreen 实例化主用户界面。这适用于下面的代码。

如果用户没有存储凭据,我想在 balancescreen 的顶部显示带有情节提要 ID loginscreen 的登录视图控制器,modally。 strong> 当输入正确的凭据时,视图控制器将被关闭(我已经处理过这个),用户显示主界面。 这就是我需要帮助的地方,找到解决方案来做到这一点而不会出现应用程序故障。

这是我目前拥有的代码:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

    // grabs password for the only account
    // (there shall always only be one set of credentials stored so this will work)

    NSString *password = [SSKeychain passwordForService:@"MyOpal" account:[[SSKeychain accountsForService:@"MyOpal"][0] valueForKey:@"acct"]];


    // if password has a length (aka user has previously used the application with credentials in keychain), direct to the app
    // if password has no length (aka does not exist because user has not used the application before), direct to login screen

    if (password.length > 0) {

        self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds];
        UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
        UIViewController *viewController = [storyboard instantiateViewControllerWithIdentifier:@"balancescreen"];

        self.window.rootViewController = viewController;
        [self.window makeKeyAndVisible];


    } else {

        // do something here to present login view controller modally over the top of the main interface (with storyboard id, 'balance screen')
        // therefore, when the user logs in, the login view controller will dismiss, with the user greeted at the main interface


    }

    return YES;
}

编辑:这是我的故事板设置:

【问题讨论】:

  • 任何答案对您的问题有帮助吗?

标签: ios objective-c iphone modalviewcontroller appdelegate


【解决方案1】:

不要更改应用程序中的 rootViewController。使 rootViewController 接收导航到登录或应用程序的请求。

更改窗口的 rootViewController 是不好的做法,因为您需要手动执行动画。故事板流程如下所示:

【讨论】:

  • 那么我应该先加载rootViewController,然后让它决定进入登录视图还是主界面?
  • 我推荐这种方式有两个原因:代码更简洁,如果用户退出,您可能希望再次显示登录。所以你可以把它转发给根控制器。更改主窗口根控制器不是好的做法,除非确实需要,否则应避免。
【解决方案2】:

试试这个:

if (password.length > 0) {

    self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds];
    UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
    UIViewController *viewController = [storyboard instantiateViewControllerWithIdentifier:@"balancescreen"];

    self.window.rootViewController = viewController;
    [self.window makeKeyAndVisible];


} else {

    // go on as before
    self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds];
    UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
    UIViewController *viewController = [storyboard instantiateViewControllerWithIdentifier:@"balancescreen"];

    // instantiate the LoginViewController
    LoginViewController *loginViewController = [storyboard instantiateViewControllerWithIdentifier:@"LoginViewController"];

    self.window.rootViewController = viewController;
    [self.window makeKeyAndVisible];

    // present the LoginViewController modoally with viewController as presenter
    [viewController presentViewController:loginViewController animated:NO completion:nil];

}

显然,我假设您处理登录的UIViewController 称为LoginViewController。如果不是这种情况,请继续在您的代码中调整其名称:)

无论如何,对于这种情况,我宁愿建议您不要以模态方式显示登录。更好的方法是实际更改应用程序主 UIWindowrootViewController 属性。

在你的情况下可能看起来像这样:

    UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"Main" bundle:nil];

    if (password.length > 0) {
       UIViewController *viewController = [storyboard instantiateViewControllerWithIdentifier:@"balancescreen"];
       self.window.rootViewController = viewController;
    } 
    else {
       LoginViewController *loginViewController = [storyboard instantiateViewControllerWithIdentifier:@"LoginViewController"];
       self.window.rootViewController = loginViewController;
    }
    [self.window makeKeyAndVisible];

【讨论】:

  • 您好,感谢您的回答。我决定听从你的建议,不以模式显示登录,因为这似乎是一个更明智的选择;但是,您更改 rootViewController 的代码似乎不起作用。有什么想法吗?
  • 这是输出:2015-01-07 20:54:50.647 MyOpal[6456:545342] Failed to instantiate the default view controller for UIMainStoryboardFile 'Main' - perhaps the designated entry point is not set?
  • 您是否在故事板中正确设置了LoginViewController 并在我的代码中调整了故事板 ID?
  • 我已经调整了故事板 ID,看看我的故事板设置,我在我的问题中包含了一张图片。
  • 我将此添加到您的第二个解决方案中:self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds];
猜你喜欢
  • 2015-03-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-06-08
  • 1970-01-01
  • 1970-01-01
  • 2012-12-03
相关资源
最近更新 更多