繁体   English   中英

如何以编程方式为 UINavigationController 子类化 UINavigationBar?

[英]How to subclass UINavigationBar for a UINavigationController programmatically?

我正在使用自定义 drawRect function 在 iOS4 的应用程序中的UINavigationBar上绘图,它不使用图像,仅使用 CoreGraphics。

由于您无法在 iOS5 的UINavigationBar类别中实现 drawRect,因此 Apple 建议继承UINavigationBar

navigationBar属性为只读时,如何用UINavigationController中的子类替换UINavigationBar (因此它将与 iOS4 和 iOS5 兼容)?

@property(nonatomic, readonly) UINavigationBar *navigationBar

我根本没有在我的应用程序中使用 XIB,因此将UINavigationBar添加到 NIB 并通过 InterfaceBuilder 更改 class 不是一种选择。

在 iOS 6 中,他们向UINavigationController添加了一种新方法,该方法在 iOS 5 中也可收回:

- (id)initWithNavigationBarClass:(Class)navigationBarClass
                    toolbarClass:(Class)toolbarClass;

现在,当导航 controller 被实例化时,您只需传递您的自定义 class。

从 iOS6 开始,使用UINavigationControllers方法initWithNavigationBarClass:toolbarClass:

- (id)initWithNavigationBarClass:(Class)navigationBarClass 
                    toolbarClass:(Class)toolbarClass;

从文档:

初始化并返回使用您的自定义栏子类的新创建的导航 controller。

为 iOS6 更新了答案。

iOS 4 中唯一支持的方法是使用 Interface Builder 方法。 除了设置 UINavigationBar 子类(您仍然可以以编程方式设置所有视图)之外,您不必使用 IB 来做任何事情。

- (id)initWithNavigationBarClass:(Class)navigationBarClass toolbarClass:(Class)toolbarClass;

我在上述方法中遇到了一个问题。 有一个“initWithRootViewController”方法来初始化 UINavigationController。 但是,如果我使用“initWithNavigationBarClass”来初始化 UINavigationController,那么我无法为 UINavigationController 设置“rootViewController”。

此链接更改 UINavigationController 的 rootViewController帮助我在使用“initWithNavigationBarClass”初始化 UINavigationController 后添加了 rootViewController。 基本上,诀窍是继承 UINavigationController。 虽然我还没有在 IB 中测试过它,但它在代码中运行良好。

对于那些仍然想使用initWithRootViewController的人来说,对上述答案的一种修正。 子类UINavigationController然后:

- (id) initWithRootViewController:(UIViewController *)rootViewController
{
    self = [super initWithNavigationBarClass:[CustomNavigationBar class] toolbarClass:nil];
    if (self)
    {
        self.viewControllers = [NSArray arrayWithObjects:rootViewController, nil];
    }

    return self;
}

iOS 4 中的答案 2-4 有问题(来自 AnswerBot 的答案),并且需要一种以编程方式加载 UINavigationController 的方法(尽管 NIB 方法有效)......所以我这样做了:

Created a Blank XIB file (don't set file owner), add a UINavigationController (give it your custom UINavigationController's class), change the UINavigationBar to your custom class (here it's CustomNavigationBar), then create the following custom class header (CustomNavigationController.h在这种情况下):

#import <UIKit/UIKit.h>

@interface CustomNavigationController : UINavigationController
+ (CustomNavigationController *)navigationController;
+ (CustomNavigationController *)navigationControllerWithRootViewController:(UIViewController *)rootViewController;
@end

和自定义实现(CustomNavigationController.mm)

#import "CustomNavigationController.h"

@interface CustomNavigationController ()

@end

@implementation CustomNavigationController
+ (CustomNavigationController *)navigationController
{
    NSArray *nib = [[NSBundle mainBundle] loadNibNamed:@"CustomNavigationController" owner:self options:nil];
    CustomNavigationController *controller = (CustomNavigationController *)[nib objectAtIndex:0];
    return controller;
}


+ (CustomNavigationController *)navigationControllerWithRootViewController:(UIViewController *)rootViewController
{
    CustomNavigationController *controller = [CustomNavigationController navigationController];
    [controller setViewControllers:[NSArray arrayWithObject:rootViewController]];
    return controller;
}

- (id)init
{
    self = [super init];
    [self autorelease]; // We are ditching the one they allocated.  Need to load from NIB.
    return [[CustomNavigationController navigationController] retain]; // Over-retain, this should be alloced
}

- (id)initWithRootViewController:(UIViewController *)rootViewController
{
    self = [super init];
    [self autorelease];
    return [[CustomNavigationController navigationControllerWithRootViewController:rootViewController] retain];
}
@end

然后您可以只初始化 class 而不是 UINavigationController,您将拥有自定义导航栏。 如果您想在 xib 中执行此操作,请在您的 XIB 中更改 UINavigationController 和 UINavigationBar 的 class 和 UINavigationBar。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM