iOS Navigation导航栏

作者: xyzcwb | 来源:发表于2017-05-18 10:18 被阅读0次

    在iOS开发过程中,导航栏是最为经常用到的控件,处理不好总会出现一些瑕疵或者bug,写这篇文章旨在为自己记录平时所用有关Navigation一些操作或者说是小技巧。
    下文涉及到的push逻辑都是从A页面push到B页面,我会直接以A、B介绍

    一、关于返回Item

    默认从A—>B(push),B中返回按钮的title显示的是A的标题,当A的标题过长,会显示返回(back)。A标题长同时B标题也长,就会出现B标题被挤到右边了,这就尴尬了。如下图


    B标题未正常显示

    网上有说在A的viewWillDisappear将A的标题设置成空的,在viewDidAppear方法中再将标题设置原来的,但是这个在手势侧滑过程中显示会有问题,这里就不做演示了。
    这里提供一个解决方案:让A控制器继承自BaseViewController(自己创建的控制器),在BaseViewController做以下操作:

    - (void)viewDidLoad {
        [super viewDidLoad];
        UIBarButtonItem *backItem = [[UIBarButtonItem alloc] initWithTitle:@"返回"
                                                                     style:UIBarButtonItemStyleDone
                                                                    target:self
                                                                    action:nil];
        self.navigationItem.backBarButtonItem = backItem;
    }
    
    正常显示

    有时我们并不需要显示title,在上图中的“返回”设置成 nil 就可以解决问题。当然我们刚才并没有改变返回的图片都是用系统默认的,如果只是单纯的显示自定义的返回图标(需求就是这么样,有什么办法),那么问题来了,怎么设置比较合理。以
    下给出几种方案:

    1、设置navigationItem的leftBarButtonItem(不推荐)
    UIBarButtonItem *backItem = [[UIBarButtonItem alloc] initWithImage:[UIImage imageNamed:@"navigation_back"]
                                                                 style:UIBarButtonItemStylePlain
                                                                target:self
                                                                action:@selector(p_actionBack)];
    self.navigationItem.leftBarButtonItem = backItem;
    
    自定义返回按钮

    只是添加leftBarButtonItem侧滑手势被禁止了,图标离左侧有一定距离,经过如下修改:

    - (void)p_addBackItem {
        //间隙
        UIBarButtonItem *spaceItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFixedSpace target:self action:nil];
        //spaceItem宽度为负值,相当于左移
        spaceItem.width = -8;
        UIBarButtonItem *backItem = [[UIBarButtonItem alloc] initWithImage:[UIImage imageNamed:@"navigation_back"]
                                                                     style:UIBarButtonItemStylePlain
                                                                    target:self
                                                                    action:@selector(p_actionBack)];
        self.navigationItem.leftBarButtonItems = @[spaceItem, backItem];
        //设置代理,添加leftBarButtonItem系统的侧滑手势会被禁
        if ([self.navigationController respondsToSelector:@selector(interactivePopGestureRecognizer)]) {
           self.navigationController.interactivePopGestureRecognizer.delegate = self;
        }
    }
     - (void)p_actionBack {
        [self.navigationController popViewControllerAnimated:YES];
    }
    
    #pragma mark - UIGestureRecognizerDelegate
    - (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer {
        return YES;
    }
    
    自定义
    2、将title移出视图外,从而达到隐藏的效果(推荐,作用范围全局)

    注意:这个需要在AppDelegate设置才有效

    - (void)initBars {
        UIImage *backImage = [UIImage imageNamed:@"navigation_back"];
        UINavigationBar *navigationbar = [UINavigationBar appearance];
        [navigationbar setBackIndicatorImage:backImage];
        [navigationbar setBackIndicatorTransitionMaskImage:backImage];
        [[UIBarButtonItem appearance] setBackButtonTitlePositionAdjustment:UIOffsetMake(0, -60)
                                                             forBarMetrics:UIBarMetricsDefault];
    }
    
    设置偏移量,替换系统返回按钮
    上一页标题过长

    对比可以发现,第一张图是标题比较短的时候显示正常,第二张图是标题比较长的时候标题被往右挤了。


    视图下查看 这个方法只是将返回Item的title移出,宽度并没有改变,所以在使用这个方法时一定要注意,我一般是配合一开始提到的搭配使用。如果有更好的解决方法可以留言告知,不胜感激。

    二、Navigation显示或隐藏

    项目中一般有一两个页面比较特殊,需要隐藏导航栏或者导航栏需要根据滑动渐变,如登录页面需要隐藏导航栏。隐藏简单,拿起键盘就是干。

    1、隐藏导航栏

    使用[self.navigationController setNavigationBarHidden:NO animated:YES] 侧滑手势会被禁,所以需要加代理开启手势

    - (void)viewDidLoad {
        [super viewDidLoad];
        //设置代理
        if ([self.navigationController respondsToSelector:@selector(interactivePopGestureRecognizer)]) {
            self.navigationController.interactivePopGestureRecognizer.delegate = self;
        }
    }
    - (void)viewWillAppear:(BOOL)animated {
        [super viewWillAppear:animated];
        //会导致侧滑手势被禁
        [self.navigationController setNavigationBarHidden:YES animated:animated];
    }
    - (void)viewWillDisappear:(BOOL)animated {
        [super viewWillDisappear:animated];
        //如果该控制器没有上级控制器,建议将使用[self.navigationController setNavigationBarHidden:NO animated:animated] 效果会更好点
        [self.navigationController setNavigationBarHidden:NO animated:NO];
    }
    #pragma mark - UIGestureRecognizerDelegate
    - (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer {
        return YES;
    }
    
    2、导航栏渐变

    介绍两个方法:

    //隐藏导航栏,但不隐藏上面的Item
    [self.navigationController.navigationBar setBackgroundImage:[[UIImage alloc] init]
                                                  forBarMetrics:UIBarMetricsDefault];
    //隐藏导航栏底部那条线
    [self.navigationController.navigationBar setShadowImage:[[UIImage alloc] init]];
    

    这个不做演示,推荐一个三方 LTNavigationBar

    三、自定义TitleView

    直接上代码

    UIView *titleView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 100, 40)];
    UISwitch *switchView = [[UISwitch alloc] initWithFrame:CGRectMake(0, 0, 40, 40)];
    switchView.center = titleView.center;
    [titleView addSubview:switchView];
    self.navigationItem.titleView = titleView;
    
    自定义TitleView

    相关文章

      网友评论

        本文标题:iOS Navigation导航栏

        本文链接:https://www.haomeiwen.com/subject/orfsxxtx.html