为iOS Cocoa Touch Tab Bar应用程序添加登录界面

13

我还在逐步了解这些东西。虽然还远远不够,但是......我有一个通过Xcode创建的TabBar应用程序。它可以工作,我有三个选项卡视图,我知道如何操纵等。

我想在整个应用程序前面放置一个“登录”nib文件,要求用户回答(现在是硬编码的)用户名和密码。如果你回答正确,那么就呈现选项卡部分,让他们点击浏览。

我有另一个应用程序,已经完成了用户名和密码部分,但我无法将其逻辑提取出来,放在TabApplication前面。

有人有什么建议吗?

4个回答

17

在您的AppDelegate中,在application didFinishLaunchingWithOptions方法的末尾,您会看到以下内容:

[window addSubview:tabcontroller.view];
[window makeKeyAndVisible];
return YES;

只需初始化您的登录视图控制器并在选项卡控制器之后添加它即可,例如:

initialScreenViewController = [[InitialScreenViewController alloc] init];
[window addSubview:tabcontroller.view];
[window addSubview:initialScreenViewController.view];
[window makeKeyAndVisible];
return YES;

在您的登录视图控制器中,验证用户后,可以通过以下方式隐藏它:

[self.parentViewController.view setHidden:YES];

如果您有一个注销功能,那么它允许您重新显示它。


谢谢,明天我会尝试一下。我通常是C#开发人员,所以这些东西的语法和思想方式仍在我的脑海中形成。谢谢。 - John Batdorf
这是在你使用setHidden行关闭登录之前吗?如果是这样,那么这意味着你的登录视图需要更高,大约20像素左右。还是在你使用setHidden行关闭登录之后? - Matthew Frederick
2
这是最终适用于我的代码: [self.view removeFromSuperview]; - John Batdorf
1
很高兴你解决了它,虽然我不确定为什么我的建议没有起作用,因为我有几个项目使用相同的方法。不过,好消息。 - Matthew Frederick
@Stas 很不幸,我已经有一段时间没有做过这个了,所以我不确定。 - Matthew Frederick
显示剩余4条评论

16

标准的方法如下:

  • 将所有与登录屏幕相关的内容打包到一个视图中,同时创建一个UIViewController子类来管理它。
  • 在应用程序委托的application:didFinishLaunchingWithOptions:方法中以模态方式呈现该视图,调用:

LoginController*loginController= ... ; // create the view controller for the login screen
[self.tabController presentModalViewController:loginController animated:YES];

这样,过渡期间的动画等内容将自动处理。

您可以在成功登录后稍后解除它。可以从LoginController内部完成。

[self.parentViewController dismissModalViewControllerAnimated:YES];

然而,通常在登录完成后我需要进行其他设置。所以,我会先告诉应用程序代理登录已完成,然后执行其他操作。

[self.tabController dismissModalViewControllerAnimated:YES];

我可以从应用程序委托中调用任务,然后在那里执行其他任务。

要向应用程序委托通信,我将使用NSNotification,但这可能对您来说有点困难。

一种可能更容易理解(但我觉得不太好看)的方法是在应用程序委托中定义一个方法,比如说loginDone。然后,在LoginViewController内部,您可以执行以下操作:

MyAppDelegate*appDelegate=[[UIApplication sharedApplication] delegate];
[appDelegate loginDone];

我该如何从LoginControllerView中将其取消? - John Batdorf
在登录完成后,从应用程序委托中执行[self.tabController dismissModalViewControllerAnimated:YES]。你可以在LoginViewController的方法内部执行[self.parentViewController dissmissModalViewControllerAnimcated:YES],但无论如何,你都需要告诉应用程序委托你已经成功登录了。我更喜欢从应用程序委托中解除它。 - Yuji
抱歉,我还在努力理解您的解释。那么,在我的LoginViewController中,一旦用户通过身份验证,我该如何将该事件传递回应用程序委托?谢谢。 - John Batdorf
presentModalViewController 已经被弃用,请使用 [self.tabController presentViewController:self.loginController animated:YES completion:nil]; 代替。在这种情况下,动画效果看起来不太好,因为必须先显示 tabController,只有在它出现在屏幕上后才能呈现 loginController。所以我更喜欢传递 animated:NO - Stas

2
如果您使用默认标签栏应用程序开始,可以按照以下步骤操作:
  • 在MainWindow.xib中创建一个包含所有密码屏幕上要显示的内容的UIView
  • 将所需内容钩连到AppDelegate中的IBOutlets,并编写检查密码是否有效的方法。
  • 在applicationDidFinishLaunching方法中,将[window addSubview:tabBarController.view];替换为[window addSubview:/*您称为带有密码内容的视图的任何内容*/];
  • 如果用户输入正确的密码,请执行以下操作:

[passView removeFromSuperview]; [window addSubview:tabBarController.view];

这样就可以进入常规标签栏应用程序了。


0
我更喜欢这样做:
在 App Delegate 的 `didFinishLaunchingWithOptions` 方法中:
FirstViewController *viewController1 = [[FirstViewController alloc] initWithNibName:@"SecondViewController" bundle:nil];
SecondViewController *viewController2 = [[SecondViewController alloc] initWithNibName:@"SecondViewController" bundle:nil];
ThirdViewController *viewController3 = [[ThirdViewController alloc] initWithNibName:@"SecondViewController" bundle:nil];

UINavigationController *navController1 = [[UINavigationController alloc] initWithRootViewController:viewController1];
UINavigationController *navController2 = [[UINavigationController alloc] initWithRootViewController:viewController2];
UINavigationController *navController3 = [[UINavigationController alloc] initWithRootViewController:viewController3];

self.tabBarController = [[UITabBarController alloc] init];
self.tabBarController.viewControllers = @[navController1, navController2, navController3];

LoginViewController *loginViewController = [[LoginViewController alloc] initWithNibName:@"LoginViewController" bundle:nil];
UINavigationController *loginNavController = [[UINavigationController alloc] initWithRootViewController:loginViewController];

self.window.rootViewController = loginNavController;

然后在收到验证回调之后,您可以在您的应用程序代理中添加以下内容:

- (void)setAuthenticatedState:(BOOL)authenticated
{
    if (authenticated == YES) {
        dispatch_async(dispatch_get_main_queue(), ^(){
            self.window.rootViewController = self.tabBarController;
        });
    }else{
        // Stuff
    }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接