IOS开发-OC UINavigationController使用

发布时间 2023-07-17 11:10:45作者: SadicZhou

1.什么是UINavigationController

UINavigationController是iOS中的一个重要的导航控制器类,它可以用来管理页面之间的导航跳转。

UINavigationController的主要特征包括:

- 管理导航栈(navigation stack),实现页面的推入和弹出。
- 包含一个navigation bar,显示导航项和标题。
- 可以通过push和pop方法来进行页面跳转。
- 新页面是被push到栈顶,返回则通过pop返回。
- 支持自定义navigation bar的样式。
- 支持手势返回功能。

2.使用UINavigationController的基本流程:

1. 创建UINavigationController,初始化时指定根视图控制器。

2. 将UINavigationController设置为window的rootViewController。

3. 通过pushViewController方法进行页面跳转。

4. 通过popViewController方法返回上一页。

5. 通过设置navigationBar的属性来自定义样式。

6. 子页面通过navigationItem属性设置导航栏内容。

UINavigationController是iOS中最常用的页面导航方案,可以方便地实现页面进出栈的管理,是开发iOS App必学的一个重要类。掌握使用UINavigationController可以轻松实现iOS App的多页面导航功能。

3.具体实现:

1.创建UINavigationController,初始化时指定根视图控制器。

这一步一般是在AppDelegate文件的application钩子中完成

  //创建ui navigation控制器
     //UINavigationController和tabbercontroller一样本身没有视图和逻辑,所以需要设置一个根视图,这里将opeview页面设置为根视图
    UINavigationController *navigationController=[[UINavigationController alloc]initWithRootViewController:networklisten];
    [navigationController pushViewController:openview animated:YES];

2. 将UINavigationController设置为window的rootViewController。

这一步同样在AppDelegate文件的application钩子中完成,先定义window对象

在AppDelegate的头文件中定义

@property (strong,nonatomic)UIWindow *window;

然后将window的rootViewController设置为UINavigationController,并执行window的makeKyeAndVisible方法

 self.window.rootViewController = navigationController;//将根视图控制室设置为UINavigationController
    [self.window makeKeyAndVisible];

 

 3. 通过pushViewController方法进行页面跳转。

  [self.navigationController pushViewController:nonetview animated:YES];

这里有一个很重要的细节:

如果要从A页面跳到B页面首先要确保A页面已经在UINavigationController里面,否则通过self.navigationController获取的就不是UINavigationController的实例而是nil,其次是确保B页面不在UINavigationController里面。

4. 通过popViewController方法返回上一页。

-(void)back{
    [self.navigationController popViewControllerAnimated:YES];
}

5. 通过设置navigationBar的属性来自定义样式。6. 子页面通过navigationItem属性设置导航栏内容。

这个的实现方法有很多,我一般是在viewWillAppear钩子里直接隐藏掉系统的navigationBar,然后自定义一个。

-(void) viewWillAppear:(BOOL)animated{
    self.navigationController.navigationBarHidden = YES;
    [self initbar];
}

  

-(void)initbar{
   _barview = [[UIView alloc] initWithFrame:CGRectMake(0.0,0.0,self.view.frame.size.width,100)];
    _barview.backgroundColor = [UIColor colorWithRed:240/255.0 green:239/255.0 blue:244/255.0 alpha:1.0];
    [self.view addSubview:_barview];
    _goback = [[UIButton alloc] initWithFrame:CGRectMake(20, 65, 15, 20)];
    [_goback setImage:[UIImage imageNamed:@"left"] forState:UIControlStateNormal];
    [self.view addSubview:_goback];
    _goback.userInteractionEnabled=YES;
    UITapGestureRecognizer *backGesture =[[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(back)];//创建手势
    [_goback addGestureRecognizer:backGesture];
   _tit =[[UILabel alloc] initWithFrame:CGRectMake((self.view.frame.size.width-80)/2, 63, 80, 19)];
    _tit.text=@"添加家庭";
    _tit.font=[UIFont boldSystemFontOfSize:17];
    _tit.textAlignment = NSTextAlignmentCenter;
    [self.view addSubview:_tit];
}

 

这里再教大家如何从一个页面直接返回一个指定的页面并传递参数

如:我现在要返回tabbar中的location页面并携带参数wearid

1.定义一个可变数组marr来存放当前所有的页面栈,通过self.navigationController.viewControllers来获取

2.遍历marr数组,通过isKindOfClass方法来判断是否是自己要跳过去的页面栈

3.如果找到了用对应的页面类型来接收一下marr[i],这里我要跳转的定位页面在tabbar的第一个bar所以我先用setSelectedIndex方法来设置它选择的tabbar为第一个,然后再用UITabBarController类型来接受它,这样才能通过selectedViewController属性来获取到激活的页面也就是location页面,再用location页面接收获取到的激活的页面,再写入要传递参数;最后

调用popToViewController方法跳转过去即可。

setSelectedIndex
  NSMutableArray *marr = [[NSMutableArray alloc]initWithArray:self.navigationController.viewControllers];for(int i=0;i<marr.count;i++){
           if([marr[i] isKindOfClass:[UITabBarController class]]){
               [marr[i] setSelectedIndex:0];
               UITabBarController *bar =marr[i];
               location * loc =bar.selectedViewController;
               [loc setWearid:_listdata[indexPath.row][@"wearerId"]];
               self.navigationController.navigationBarHidden = YES;
               [self.navigationController popToViewController:marr[i] animated:YES];
               return;
           }
       }
  

 

再教大家如何从页面栈中移除指定的页面 

1.获取所有页面栈

2.遍历可变数组,移除要移除的页面栈

3.将self.navigationController.viewControllers设置为完成移除操作之后的可变数组marr

NSMutableArray *marr = [[NSMutableArray alloc]initWithArray:self.navigationController.viewControllers];
for (UIViewController *vc in marr) {
    if ([vc isKindOfClass:[XXX class]]) {
        [marr removeObject:vc];
        break;
    }
}
 self.navigationController.viewControllers = marr;

//也可以直接根据下标移除
 [marr removeObjectAtIndex:1];

如何返回根视图(第一个页面)

[self.navigationController popToRootViewControllerAnimated:true];