如何为所有导航控制器和视图控制器设置自定义导航栏(标题+标题视图)?

3

我有一个带有选项卡的应用程序,选项卡中包含导航控制器和视图控制器。它们都使用相同的导航控制器导航栏:返回按钮+标志图像。目前,我将此代码放置在每个视图控制器中:

- (void)viewDidLoad
{
  [super viewDidLoad];
  self.navigationItem.title = @"Back";
  UIImage *headerImage = [UIImage imageNamed:@"Logo.png"];
  self.navigationItem.titleView = [[[UIImageView alloc] initWithImage:headerImage] autorelease];
}

我认为这不是最好的方法。我在考虑使用UIViewController的类别并重写viewDidLoad方法,但每个视图控制器都有一些额外的代码需要在viewDidLoad中执行,因此我认为覆盖不是解决方案。还有其他方法吗?


你的目标是 iOS 5 吗?在 iOS 中,你可以全局设置这些值(例如在你的 appDelegate 中)。 - Holger Frohloff
目前没有 :) 但请告诉我如何在iOS 5中实现这个功能... - Centurion
1
看一下UIAppearance:http://developer.apple.com/library/ios/#documentation/uikit/reference/UIAppearance_Protocol/Reference/Reference.html 我写了一个小例子作为答案。如果对你有用,请告诉我。 - Holger Frohloff
2个回答

9
您可以创建一个UIViewController的子类,例如MyViewControllerWithBackButtonAndLogo(您可以想出一个更好的名称),然后实现viewDidLoad来设置导航项。使所有视图控制器都继承自此基类。然后只需确保视图控制器在其自己的实现中调用[super viewDidLoad]

另外请注意,要设置返回按钮标题,不应更改导航项的title属性,而应设置适当的backBarButtonItem


这是一个非常聪明的答案 - 我真希望我能想到它,哈哈!总的来说,我会说这只是一种解决方法,但绝不是一种hacky的解决方法。个人而言,我希望能够将这些自定义与特定的导航控制器相关联,以便其堆栈中的所有视图都具有您的添加内容。我觉得这应该属于导航控制器的职责范畴,但我可能还不太了解这个类...无论如何,感谢您的分享! - SilithCrowe
是否可能在子类中实现相同的viewDidLoad方法,同时适用于UITableViewController和UIViewController?这样,所有控制器(视图和表格)都将具有相同的导航栏。 - JastinBall

0
在正确的架构中,UIViewController(或其子类)不应关心它显示的上下文是什么(例如在UINavigationController、UITabController、模态或非模态中)。考虑使用协调器模式,由协调器负责执行此类配置。
示例:
class FlowCoordinator {
    ...

    // The coordinator knows about the navigation controller
    // Individual view controllers do not.
    private let navigationController: UINavigationController

    func presentViewController(viewController: UIViewController) {
        // This setup can be common for all view controllers in this flow
        viewController.navigationItem.titleView = ...
        viewController.backBarButtonItem = ...
        viewController.navigationItem.title = ...
        navigationController.pushViewController(viewController)
    }

    ...
}

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