關於backBarButtonItem的N種方法


今天在做項目的時候遇到一點小問題,后來自己解決了,也順便思考了一下更深層次的東西,在這里分享一下~~

替換返回按鈕的文字

很多app的要求所有的返回按鈕的title都是“返回”,如果上一層題目文字太多,下一層的返回按鈕文字就會顯示不完全,而且這樣可以使軟件顯得整潔。

方法一:

最普通的想法,A界面的navigationItem.backBarButtonItem修改的是B(A的下一級)界面的返回按鈕,所以可以寫一個BaseViewController,讓所有的UIViewController繼承它,像這樣

- (void)viewDidLoad {
    [super viewDidLoad];
    self.navigationItem.backBarButtonItem = [[UIBarButtonItem alloc] initWithTitle:@"返回" style:UIBarButtonItemStylePlain target:nil action:nil];
}

方法二:

思路是:在開啟程序時,使用Method Swizzling,將系統自帶的backBarButtonItem方法替換成我們自定義的方法。

具體實現就是創建個 UINavigationItem + BackItem 的類別,當系統執行+load方法時,將backBarButtonItem方法和myCustomBackButton方法交換,利用iOS關聯方法(objc_getAssociatedObject,objc_setAssociatedObject)static區創建個backItemButton用來展示。這個方法的好處就是將類別導入到工程里不用任何代碼就可以實現,上代碼吧:

+(void)load{
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        Method originalMethodImp = class_getInstanceMethod(self, @selector(backBarButtonItem));
        Method destMethodImp = class_getInstanceMethod(self, @selector(myCustomBackButton));
        method_exchangeImplementations(originalMethodImp, destMethodImp);
    });
}

static char kCustomBackButtonKey;

-(UIBarButtonItem *)myCustomBackButton{
    UIBarButtonItem *item = [self myCustomBackButton];
    if (item) {
        return item;
    }
    item = objc_getAssociatedObject(self, &kCustomBackButtonKey);
    if (!item) {
        item = [[UIBarButtonItem alloc] initWithTitle:@"返回" style:UIBarButtonItemStylePlain target:nil action:NULL];
        objc_setAssociatedObject(self, &kCustomBackButtonKey, item, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
    }
    return item;
}

- (void)dealloc
{
    objc_removeAssociatedObjects(self);
}

返回按鈕只顯示自定義圖片

方法一:

最開始我的方案是實現UINavigationController的代理判斷是否是棧底,如果不是就修改leftBarButtonItem的樣式。

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    UIViewController *root = navigationController.viewControllers[0];
    
    if (root != viewController) {
        UIBarButtonItem *itemleft = [[UIBarButtonItem alloc] initWithImage:[UIImage imageNamed:@"backBtn"] style:UIBarButtonItemStylePlain target:self action:@selector(popAction:)];
        viewController.navigationItem.leftBarButtonItem = itemleft;
    }
}


- (void)popAction:(UIBarButtonItem *)barButtonItem
{
    [self.navigationController popViewControllerAnimated:YES];
}

iOS7.0出了之后,這並不是一個好的解決方案。因為iOS7.0之后如果把backItemButton替換成leftItemButon,interactivePopGestureRecognizer手勢就沒有了。雖然可以使用

self.navigationController.interactivePopGestureRecognizer.delegate = (id<UIGestureRecognizerDelegate>)self;

方法二:

這個方法和上邊‘替換返回按鈕的文字’方法二大致一樣,這句話要替換:

item = [[UIBarButtonItem alloc] initWithImage:[UIImage imageNamed:@"back"] style:UIBarButtonItemStylePlain target:nil action:nil];

這句話要加上,用來去除系統自帶的返回按鈕上的尖腳號。

[[UINavigationBar appearance] setBackIndicatorImage:[[UIImage alloc]init]];
[[UINavigationBar appearance] setBackIndicatorTransitionMaskImage:[[UIImage alloc] init]];

技術上的問題其實有好多方法可以去解決,而且在效率相差不大的情況下,關鍵是我們的使用習慣,所以整理一下現在的思路,方便以后使用。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM