iOS中多控制器管理(上) UINavigationController

多控制器管理

    当app中有多个控制器的时候,我们就需要对这些控制器进行管理,为了便于控制器管理,iOS提供了两个比较特殊的控制器:UINavigationController 和 UITabBarViewController .

UINavigationController

    利用UINavigationController, 可以轻松地管理多个控制器, 轻松完成控制器之间的切换.

UINavigationController的使用步骤

    1> 初始化UINavigationController ;

    初始化UINavigationController时, 可以通过initWithRootViewController:方法传入一个控制器作为根控制器, 这个根控制器永远处于栈底(如果栈中只有一个对象,那么根控制器也处于栈顶)

    2> 设置UIWindow的rootViewController为UINavigationController ;

    3> 根据具体情况,通过push方法添加对应个数的子控制器 .

UINavigationController的子控制器

    UINavigationController以栈的形式保存子控制器

@property(nonatomic,copy) NSArray *viewControllers;
@property(nonatomic,readonly) NSArray *childViewControllers;

    使用push方法能将某个控制器压入栈

-(void)pushViewController:(UIViewController *)viewController animated:(BOOL)animated;

    使用pop方法可以移除控制器

    1> 将栈顶的控制器移除

-(UIViewController *)popViewControllerAnimated:(BOOL)animated;

    2> 回到指定的子控制器

-(NSArray *)popToViewController:(UIViewController *)viewController animated:(BOOL)animated;

    3> 回到根控制器(栈底控制器)

-(NSArray *)popToRootViewControllerAnimated:(BOOL)animated;

如何修改导航栏的内容

    导航栏的内容由栈顶控制器的navigationItem属性决定

    UINavigationItem有以下属性影响着导航栏的内容

    1> 左上角的返回按钮

@property(nonatomic,retain) UIBarButtonItem *backBarButtonItem;

    2> 中间的标题视图

@property(nonatomic,retain) UIView *titleView;

    3> 中间的标题文字

@property(nonatomic,copy)   NSString *title;

    4> 左上角的视图

@property(nonatomic,retain) UIBarButtonItem *leftBarButtonItem;

    5> 右上角的视图

@property(nonatomic,retain) UIBarButtonItem *rightBarButtonItem;

Segue

    Storyboard上每一根用来界面跳转的线,都是一个UIStoryboardSegue对象,简称Segue.

Segue的属性    

每一个Segue对象,都有3个属性.

    1> 唯一标识

@property (nonatomic, readonly) NSString *identifier;

    2> 来源控制器

@property (nonatomic, readonly) id sourceViewController;

    3> 目标控制器

@property (nonatomic, readonly) id destinationViewController;

Segue的类型

    根据Segue的执行(跳转)时刻, Segue可分为两大类型:

    1> 自动型: 点击某个控件后(如按钮), 自动执行Segue ,自动完成界面跳转.

    2> 手动型: 需要通过手写代码手动执行Segue, 才能完成界面跳转.

自动型Segue

    如果点击某个控件后, 不需要做任何判断,  一定要跳转到下一个界面, 建议使用"自动型Segue".

手动型Segue

    手动型Segue需要设置一个标识;

    在恰当的时候, 使用perform方法执行对应的Segue;

[self performSegueWithIdentifier:@"login2contacts" sender:nil];
//这个self是来源控制器 Segue必须由来源控制起来执行,也就是说,这个perform方法必须由来源控制器来调用

    如果点击某个控件后, 需要做一些判断,也就是说:满足一定条件后才跳转到下一个界面,建议使用"手动型Segue".

performSegueWithIdentifier:sender:

    利用performSegueWithIdentifier:sender:方法可以执行某个Segue,完成界面跳转.接下来研究performSegueWithIdentifier:sender:方法的完整执行过程.

    1> 根据identifier去storyboard中找到对应的线,新建UIStoryboardSegue对象.

         设置Segue对象的sourceViewController(来源控制器)

         创建并且设置Segue对象的destinationViewController(目标控制器)

    2> 调用sourceViewController的下面方法,做一些跳转前的准备工作并且传入创建好的Segue对象.

-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender;
// 这个sender是当初performSegueWithIdentifier:sender:中传入的sender

    3> 调用Segue对象的-(void)perform;方法开始执行界面跳转操作.

    (1)如果segue的style是push

    1> 取得sourceViewController所在的UINavigationController;

    2> 调用UINavigationController的push方法将destinationViewController压入栈中,完成跳转.

    (2)如果segue的style的modal

        调用sourceViewController的presenViewController方法将destinationViewController展示出来.

控制器的数据传递

    控制器之间的数据传递主要有两种情况:顺传和逆传.

顺传:数据的传递方向与控制器的跳转方向一致;

数据的传递方式: 

    在来源控制器(sourceViewController)的prepareForSegue:sender:方法中根据segue参数取得目标控制器(destinationViewController),直接给控制器传递数据(要在目标控制器(destinationViewController)的viewDidLoad方法中取得数据,来赋值给界面上的UI控件).

逆传:数据的传递方向与控制器的跳转方向相反.

数据的传递方式:

    让来源控制器(sourceViewController)称为目标控制器(destinationViewController)的代理,在目标控制器(destinationViewController)中调用来源控制器(sourceViewController)的代理方法,通过代理方法的参数传递数据给来源控制器(sourceViewController).



你可能感兴趣的:(导航栏,segue)