如何让懒惰的UITabBarController加载视图控制器? [英] How to make UITabBarController load view controllers lazily?
问题描述
我有一个UITabBarController创建的programaticaly管理UIViewController的4个子类。类似于:
I have a UITabBarController created programaticaly that manages 4 subclasses of UIViewController. Something like:
//Create Controller 1
self.terminal = [[[TerminalController alloc] initWithNibName:@"TerminalView" bundle:nil] autorelease];
UINavigationController* navTerminal = [[[UINavigationController alloc] initWithRootViewController:terminal] autorelease];
navTerminal.title = __(@"Terminal");
navTerminal.navigationBar.barStyle = UIBarStyleBlackOpaque;
navTerminal.tabBarItem.image = [UIImage imageNamed:@"tab_terminal.png"];
//Create Controller 2
self.history = [[[HistoryController alloc] initWithNibName:@"HistoryView" bundle:nil] autorelease];
UINavigationController* navHistory = [[[UINavigationController alloc] initWithRootViewController:history] autorelease];
navHistory.title = __(@"History");
navHistory.navigationBar.barStyle = UIBarStyleBlackOpaque;
navHistory.tabBarItem.image = [UIImage imageNamed:@"tab_history.png"];
//Create Controller 3
self.settings = [[[SettingsController alloc] initWithNibName:@"SettingsView" bundle:nil] autorelease];
UINavigationController* navSettings = [[[UINavigationController alloc] initWithRootViewController:settings] autorelease];
navSettings.title = __(@"Settings");
navSettings.navigationBar.barStyle = UIBarStyleBlackOpaque;
navSettings.tabBarItem.image = [UIImage imageNamed:@"tab_settings.png"];
//Create Controller 4
HelpController* help = [[[HelpController alloc] initWithNibName:@"HelpView" bundle:nil] autorelease];
UINavigationController* navHelp = [[[UINavigationController alloc] initWithRootViewController:help] autorelease];
navHelp.title = __(@"Help");
navHelp.navigationBar.barStyle = UIBarStyleBlackOpaque;
navHelp.tabBarItem.image = [UIImage imageNamed:@"tab_help.png"];
//Create Tab Bar an add it's view to window.
self.tabBar = [[[UITabBarController alloc] initWithNibName:nil bundle:nil] autorelease];
tabBar.viewControllers = [[[NSArray alloc] initWithObjects:navTerminal, navHistory, navSettings, navHelp, nil] autorelease];
tabBar.delegate = self;
[window addSubview:tabBar.view];
有没有办法告诉UITabBarController懒惰地加载视图控制器? ej,当用户点击其中一个标签栏项目或者调用tabBarController setSelectedIndex时?
Is there a way to tell the UITabBarController to load the view controllers lazily? ej, when the user clicks one of the tab bar items or when tabBarController setSelectedIndex is called?
推荐答案
我这样做非常在我的一个应用程序中的东西。诀窍是让你的视图控制器不是UITabBarController的子类,而是UIViewController,并实现UITabBarDelegate。我在IB中为此创建了视图,布置了标签栏(带有正确的按钮,图像,标签等)和占位符UIView,用于正确放置交换的子视图。视图切换发生在tabBar:didSelectItem:它看起来像这样:
I'm doing this very thing in one of my apps. The trick is to make your view controller NOT be a subclass of UITabBarController, but rather UIViewController, and implement UITabBarDelegate. I created the view for this in IB, laying out the tab bar (with the proper # of buttons, images, tags, etc.) and a placeholder UIView which is used to properly place the subviews that are swapped in and out. View switching happens on tabBar:didSelectItem: It looks something like this:
// MyTabBarController.h
@class MyFirstViewController;
@class MySecondViewController;
@class MyThirdViewController;
@interface MyTabBarController : UIViewController <UITabBarDelegate> {
IBOutlet UIView *placeholderView;
IBOutlet UITabBar *tabBar;
MyFirstViewController *firstViewController;
MySecondViewController *secondViewController;
MyThirdViewController *thirdViewController;
UIViewController *currentViewController;
}
@property (nonatomic, retain) MyFirstViewController *firstViewController;
@property (nonatomic, retain) MySecondViewController *secondViewController;
@property (nonatomic, retain) MyThirdViewController *thirdViewController;
- (void) switchToView:(UIViewController*)aViewController;
@end
// MyTabBarController.m
#import "MyTabBarController.h"
#import "MyFirstViewController.h"
#import "MySecondViewController.h"
#import "MyThirdViewController.h"
enum {
kView_First = 1,
kView_Second,
kView_Third
};
@implementation MyTabBarController
@synthesize firstViewController, secondViewController, thirdViewController;
- (void) viewDidLoad {
// Default to first view.
tabBar.selectedItem = [tabBar.items objectAtIndex:0];
MyFirstViewController *viewController = [[MyFirstViewController alloc] initWithNibName:@"FirstView" bundle:nil];
self.firstViewController = viewController;
[viewController release];
[self switchToView:firstViewController];
}
- (void)viewWillAppear:(BOOL)animated {
// Tell our subview.
if( currentViewController != nil ) {
[currentViewController viewWillAppear:animated];
}
}
- (void)tabBar:(UITabBar *)tabBar didSelectItem:(UITabBarItem *)item {
switch (item.tag) {
case kView_First: {
if (firstViewController == nil) {
MyFirstViewController *viewController = [[MyFirstViewController alloc]
initWithNibName:@"FirstView" bundle:nil];
self.firstViewController = viewController;
[viewController release];
}
[self switchToView:firstViewController];
}
break;
case kView_Second:
if (secondViewController == nil) {
MySecondViewController *viewController = [[MySecondViewController alloc]
initWithNibName:@"SecondView" bundle:nil];
self.secondViewController = viewController;
[viewController release];
}
[self switchToView:secondViewController];
break;
case kView_Third: {
if (timesViewController == nil) {
MyThirdViewController *viewController = [[MyThirdViewController alloc]
initWithNibName:@"ThirdView" bundle:nil];
self.thirdViewController = viewController;
[viewController release];
}
[self switchToView:thirdViewController];
}
break;
}
}
- (void) switchToView:(UIViewController*)aViewController {
if( aViewController == currentViewController ) return;
UIView *aView= aViewController.view;
[aViewController viewWillAppear:NO];
if( currentViewController != nil ) {
[currentViewController viewWillDisappear:NO];
[currentViewController.view removeFromSuperview];
}
aView.frame = placeholderView.frame;
[self.view insertSubview:aView aboveSubview:placeholderView];
if( currentViewController != nil ) {
[currentViewController viewDidDisappear:NO];
}
[aViewController viewDidAppear:NO];
currentViewController = aViewController;
}
@end
代码肯定会变得更干,但是你明白了。
The code could surely be made more DRY, but you get the idea.
这篇关于如何让懒惰的UITabBarController加载视图控制器?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!