11

为了在应用程序加载时而不是在用户登录后显示我的登录屏幕,我决定在用户​​成功登录时在 NSUserDefaults 中添加一个 auth 对象。当应用程序启动时,检查 auth 参数,并相应地设置视图控制器(如果用户是 auth,它将显示一个提要,如果不是,它将显示一个登录屏幕)在后一种情况下,我有应用程序用户登录后,委托将根视图控制器重置为提要。这是不好的做法还是有更好的方法?

应用程序委托中:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary     *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    IIViewDeckController* deckController = [self generateControllerStack];
    self.rightController = deckController.rightController;
    self.centerController = deckController.centerController;

    NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];

    if([[defaults objectForKey:@"auth"] isEqualToNumber:[NSNumber numberWithInt:1]]){
        self.window.rootViewController = deckController;
    }else{
        UIStoryboard *sb = [UIStoryboard storyboardWithName:@"MainStoryboard"
                                                 bundle:nil];
        UIViewController* vc = [sb instantiateViewControllerWithIdentifier:@"loginViewController"];
        self.window.rootViewController = vc;
    }
    [self.window makeKeyAndVisible];
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleBlackOpaque animated:NO];
    return YES;
}

- (void) setRoots
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    IIViewDeckController* deckController = [self generateControllerStack];
    self.rightController = deckController.rightController;
    self.centerController = deckController.centerController;
    self.window.rootViewController = deckController;
    [self.window makeKeyAndVisible];
}

登录视图控制器中:

- (IBAction)loginClick:(id)sender {
    if([_emailField.text length]>0&&[_passField.text length]>0){
        NSString *user = _emailField.text;
        NSString *pass = _passField.text;
        [[API sharedInstance] login:user andPass:pass onCompletion:^(NSDictionary *json){
            NSLog(@"%@", json);
            if(![json objectForKey:@"error"]){
                [API sharedInstance].authorized = 1;
                NSNumber *auth = [NSNumber numberWithInt:1];
                NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
                [defaults setObject:auth forKey:@"auth"];
                [defaults synchronize];

                captureYouAppDelegate *app = [[UIApplication sharedApplication] delegate];
                [app setRoots]; 
            }else{
                [API sharedInstance].authorized = 0;
            }
        }];
    }else{
        if([_emailField.text length]<1){
            [_emailField becomeFirstResponder];
        }else{
            [_passField becomeFirstResponder];
        }
    }
}

我想知道是否有比这样做更好或更简单的方法。谢谢!

4

4 回答 4

6

只是为了澄清。我之前重置了 UIWindow 的 rootViewController 没有任何问题,但是在允许设备旋转的同时尝试这样做时遇到了一些问题——旋转刚刚停止工作。

我在尝试调试时直接从 Apple 的文档中找到了以下内容。下面的链接有一些关于使用 UIWindow 的指南。这些都与设备旋转有关,但仍然很高兴知道。

简短的回答,使用根控制器并添加子视图控制器。然后,您可以毫无问题地更换子 VC。

• 您已将视图控制器的 UIView 属性作为子视图添加到 UIWindow。

不鼓励开发人员将任何视图控制器的视图属性添加为 UIWindow 的子视图。应用程序的根视图控制器应在 Interface Builder 中或在运行时从 application:didFinishLaunchingWithOptions: 返回之前分配给应用程序窗口的 rootViewController 属性。如果您需要同时显示来自多个视图控制器的内容,您应该定义自己的容器视图控制器并将其用作根视图控制器。请参阅创建自定义容器视图控制器。

查看此技术问答了解更多详细信息。

于 2014-12-05T15:58:49.513 回答
4

我不认为重置window.rootViewController是一个坏习惯。但是,无需重新创建窗口。
如果您不想使用以前的视图控制器,只需将窗口替换rootViewController为新的视图控制器即可。如果您确实想切换回之前的视图控制器,使用-presentViewController: animated: completion:来展示您的视图控制器可能是更好的选择。

于 2013-08-14T08:18:13.820 回答
0

无需再次分配窗口可以直接设置这个

window.rootViewController = yourVC;
于 2013-08-14T08:35:01.183 回答
0

一步一步我在 UINavigationController 的帮助下展示了使用 rootviewcontroller 的良好实践

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {  
    // Override point for customization after application launch.

    self.splash = [[SplashViewController alloc] initWithNibName: @"SplashViewController" bundle: nil];  
    self.window.rootViewController = self.splash;  
    [self.window makeKeyAndVisible];  
    DLog(@"finished initializing .....");  
    [self setRootViewController];  

    return YES;  
}



- (void) setRootViewController  
{  
    DLog(@"setRootViewController");  
    if (self.sessionManager.isLoggedIn)  
    {  
            [self navigateToHomeController];  

    } else {  
            [self navigateToLoginController];  
      }  
}


- (void) navigateToHomeController  
{  
    UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"kStoryBoard" bundle: nil];  
    UINavigationController* homeNavigationController =  [storyboard instantiateViewControllerWithIdentifier:@"kHomeNavController"];  
    NSArray* controllers = [homeNavigationController viewControllers];  
    if([controllers lastObject])  
    {  
        if ([[controllers objectAtIndex:0] isKindOfClass:[HomeViewController class]]) {  
            HomeViewController* homeController = (HomeViewController*) [controllers objectAtIndex:0];  
            self.window.rootViewController = [[OLNavigationViewController alloc] initWithRootViewController: homeController]; 
        }  
    }  
}



- (void) navigateToLoginController  
{  
    UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"kStoryBoard" bundle: nil];  
    UINavigationController* loginNavigationController = [storyboard instantiateViewControllerWithIdentifier:@"kLoginNavController"];  
    if ([loginNavigationController isKindOfClass:[OLLoginViewController class]]) {  
        OLLoginViewController* loginController = (OLLoginViewController*) loginNavigationController;  
        loginController.shouldHideToolBar = YES;  
        self.window.rootViewController = [[UINavigationController alloc] initWithRootViewController: loginController];  
    }
}
于 2016-07-07T05:38:21.023 回答