通过其父ViewController将值代理到ViewController的最佳实践?

时间:2009-07-26 07:00:02

标签: iphone uikit

我有一个包含UITabBarController的视图控制器(我们称之为MainViewController),其中每个TabBarItem连接到其各自的UIViewController派生类。对于某些UIViewControllers,我想通过MainViewController传递值。这种代理的最佳方式是什么?

现在,我最终必须在MainViewController中为代理目的创建一个属性。但理想情况下,我宁愿MainViewController不知道它必须传递值的UIViewController的特定类型以及它传递的特定类型的值,因为该值从未在MainViewController中使用,我认为耦合是不必要的。

e.g。

假设标签栏项目2连接到UIEmployeeInfoViewController类。 UIEmployeeInfoViewController对名为EmployeeInfo的类型的对象感兴趣。

这是我目前的解决方案,但这是我试图避免寻求更好的方法:


1) Somewhere where UIMainViewController is being create...

UIMainViewController *mainViewController = [[UIMainViewController alloc] initWith...];

// a property called employeeInfo is created in UIMainViewController class so it can be forwarded later
mainViewController.employeeInfo = employeeInfoObj;  

...


2) Code to make UIMainViewController pass the employeeInfo along to UIEmployeeInfoViewController when the tabbar item is tapped:

- (BOOL)tabBarController:(UITabBarController *)tabBarController shouldSelectViewController:(UIViewController *)viewController
{
    if ([viewController class] == [UIEmployeeInfoViewController class])
    {
           // Need to create coupling to UIEmployeeInfoViewController class
           // and to EmployeeInfo class as well
           ((UIEmployeeInfoViewController *)viewController).employeeInfo = self.employeeInfo;
    }


    return YES;
}

1 个答案:

答案 0 :(得分:0)

好的,首先,请不要在类前面添加字符UI。它是为UIKit保留的。 Objective-C没有命名空间,因此使用众所周知的前缀(特别是Apple使用的前缀)是一个坏主意。

这里有几个选择。

你可以创建一个UIViewController子类,你的所有类都是从它派生的,并在创建时获取一些共享控制器对象(比如UIMainViewController *),并让这些类查询共享对象而不是相反。这扭转了依赖性的本质。

@interface CoreViewController : UIViewController {
  MainViewController *mainViewController;
}

@property (nonatomic, retain, readonly) MainViewController *mainViewController;

@end 

@implementation CoreViewController

@synthesize mainViewController;

- (id) initWithMainViewController:(MainViewController *)mainVC {
  self = [super initWithNibName:nil bundle:nil];

  if (self) {
    mainViewController = [mainVC retain];
  }

  return self;
}

- (void) dealloc {
  [mainViewController retain];

  [super dealloc];
}

@end

然后通过从self.mainViewController中提取数据来获取数据。根据您的应用程序的性质,这可能是一个非常强大的耦合,另一种选择是将所有这种共享状态推送到一个单独的东西中。这样做的好处是,您可以让所有对象在单例监视器上注册KVO观察者以进行更改,而不是显式检查它。