【iOS】UIViewController的生命周期

文章目录

  • 前言
  • 一、UIViewController生命周期有关函数
  • 二、执行顺序
  • 注意点
    • loadview:


前言

在iOS开发中UIViewController扮演者非常重要的角色,它是视图view和数据model的桥梁,通过UIViewController的管理有条不紊的将数据展示在视图上。作为UIKit中最基本的一个类,一般复杂的项目都离不开UIViewController作为基类。所以了解UIViewController的整个生命周期是有必要的。


一、UIViewController生命周期有关函数

以下是UIViewController生命周期方法的调用函数:

  • init(coder:) 或 init(nibName:bundle:)(根据视图的加载方式而定,可能不会同时调用)

init方法和initCoder方法相似,知识被调用的环境不一样。如果用代码初始化,会调用init方法,从nib文件或者归档(xib、storyboard)进行初始化会调用initCoder。initCoder是NSCoding协议中的方法,NSCoding是负责编码解码,归档处理的协议。

  • loadView():当View需要被展示而它却是nil时,ViewController会调用该方法。
    如果代码维护View的话需要重写此方法,使用xib维护View的话不用重写。
  • viewDidLoad():我们最常用的方法,类成员对象和变量的初始化我们都会放在这个方法中。在创建类后无论视图展现还是消失,这个方法也只会在布局是调用一次。
  • viewWillAppear():是在视图将要展现出来的时候调用。
  • viewDidAppear():方法是视图已经出现。
  • viewWillLayoutSubviews(), viewDidLayoutSubviews():这些方法用于处理视图布局的变化,通常在这里执行与布局相关的操作。viewWillLayoutSubviews()在子视图重新布局之前被调用,而viewDidLayoutSubviews()在子视图重新布局之后被调用。
  • viewWillDisappear():方法是视图即将消失。 -viewDidDisappear():视图已经消失。
  • traitCollectionDidChange()(如果视图控制器的特征集合发生变化)
  • didReceiveMemoryWarning()(如果系统内存不足)

二、执行顺序

我们用一个程序示例来看我们的执行顺序:我们创建AB两个viewcontroller,然后设置一个按钮让他们之间可以进行切换

#import "AViewController.h"
#import "BViewController.h"
@interface AViewController ()

@end

@implementation AViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    self.view.backgroundColor = [UIColor redColor];
    _btn1 = [UIButton buttonWithType:UIButtonTypeSystem];
    [_btn1 setTitle:@"next_push" forState:UIControlStateNormal];
    _btn1.frame = CGRectMake(self.view.frame.size.width / 2 - 50, self.view.frame.size.height / 2 - 50, 200, 100);
    [self.view addSubview:_btn1];
    [_btn1 addTarget:self action:@selector(next_present) forControlEvents:UIControlEventTouchUpInside];
}

- (void)next_present {
    BViewController *B = [[BViewController alloc] init];
    NSLog(@"---------A->B---------");
    B.modalPresentationStyle = UIModalPresentationFullScreen;
    [self presentViewController:B animated:YES completion:nil];
}

- (void)loadView {
    [super loadView];
    NSLog(@"%s", __func__);
}

- (void)viewWillAppear:(BOOL)animated {
    NSLog(@"%s", __func__);

}

- (void)viewWillLayoutSubviews {
    NSLog(@"%s", __func__);

}

- (void)viewDidLayoutSubviews {
    NSLog(@"%s", __func__);

}

- (void)viewDidAppear:(BOOL)animated {
    NSLog(@"%s", __func__);

}

- (void)viewWillDisappear:(BOOL)animated {
    NSLog(@"%s", __func__);

}

- (void)viewDidDisappear:(BOOL)animated {
    NSLog(@"%s", __func__);

}
@end
#import "BViewController.h"

@interface BViewController ()

@end

@implementation BViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    self.view.backgroundColor = [UIColor greenColor];
    _btn1 = [UIButton buttonWithType:UIButtonTypeSystem];
    [_btn1 setTitle:@"present" forState:UIControlStateNormal];
    _btn1.frame = CGRectMake(self.view.frame.size.width / 2 - 50, self.view.frame.size.height / 2 - 50, 200, 100);
    [self.view addSubview:_btn1];
    [_btn1 addTarget:self action:@selector(next_present) forControlEvents:UIControlEventTouchUpInside];
}

- (void)next_present {
    NSLog(@"---------B->A---------");
    [self dismissViewControllerAnimated:YES completion:nil];
    
}

- (void)loadView {
    [super loadView];
    NSLog(@"%s", __func__);
}

- (void)viewWillAppear:(BOOL)animated {
    NSLog(@"%s", __func__);

}

- (void)viewWillLayoutSubviews {
    NSLog(@"%s", __func__);

}

- (void)viewDidLayoutSubviews {
    NSLog(@"%s", __func__);

}

- (void)viewDidAppear:(BOOL)animated {
    NSLog(@"%s", __func__);

}

- (void)viewWillDisappear:(BOOL)animated {
    NSLog(@"%s", __func__);

}

- (void)viewDidDisappear:(BOOL)animated {
    NSLog(@"%s", __func__);

}
@end

【iOS】UIViewController的生命周期_第1张图片
输出结果:

2023-09-14 19:51:33.418677+0800 viewcontroller[1460:34333] -[AViewController loadView]
2023-09-14 19:51:33.427277+0800 viewcontroller[1460:34333] -[AViewController viewWillAppear:]
2023-09-14 19:51:33.431473+0800 viewcontroller[1460:34333] -[AViewController viewWillLayoutSubviews]
2023-09-14 19:51:33.431545+0800 viewcontroller[1460:34333] -[AViewController viewDidLayoutSubviews]
2023-09-14 19:51:33.471238+0800 viewcontroller[1460:34333] -[AViewController viewDidAppear:]
2023-09-14 19:51:37.265104+0800 viewcontroller[1460:34333] ---------A->B---------
2023-09-14 19:51:37.265809+0800 viewcontroller[1460:34333] -[BViewController loadView]
2023-09-14 19:51:37.271287+0800 viewcontroller[1460:34333] -[AViewController viewWillDisappear:]
2023-09-14 19:51:37.271519+0800 viewcontroller[1460:34333] -[BViewController viewWillAppear:]
2023-09-14 19:51:37.273548+0800 viewcontroller[1460:34333] -[BViewController viewWillLayoutSubviews]
2023-09-14 19:51:37.273784+0800 viewcontroller[1460:34333] -[BViewController viewDidLayoutSubviews]
2023-09-14 19:51:37.778294+0800 viewcontroller[1460:34333] -[BViewController viewDidAppear:]
2023-09-14 19:51:37.778492+0800 viewcontroller[1460:34333] -[AViewController viewDidDisappear:]
2023-09-14 19:51:38.082287+0800 viewcontroller[1460:34333] ---------B->A---------
2023-09-14 19:51:38.085170+0800 viewcontroller[1460:34333] -[BViewController viewWillDisappear:]
2023-09-14 19:51:38.085375+0800 viewcontroller[1460:34333] -[AViewController viewWillAppear:]
2023-09-14 19:51:38.590085+0800 viewcontroller[1460:34333] -[AViewController viewDidAppear:]
2023-09-14 19:51:38.590266+0800 viewcontroller[1460:34333] -[BViewController viewDidDisappear:]
2023-09-14 19:51:38.849236+0800 viewcontroller[1460:34333] ---------A->B---------
2023-09-14 19:51:38.849726+0800 viewcontroller[1460:34333] -[BViewController loadView]
2023-09-14 19:51:38.852811+0800 viewcontroller[1460:34333] -[AViewController viewWillDisappear:]
2023-09-14 19:51:38.853034+0800 viewcontroller[1460:34333] -[BViewController viewWillAppear:]
2023-09-14 19:51:38.854313+0800 viewcontroller[1460:34333] -[BViewController viewWillLayoutSubviews]
2023-09-14 19:51:38.854562+0800 viewcontroller[1460:34333] -[BViewController viewDidLayoutSubviews]
2023-09-14 19:51:39.358408+0800 viewcontroller[1460:34333] -[BViewController viewDidAppear:]
2023-09-14 19:51:39.358612+0800 viewcontroller[1460:34333] -[AViewController viewDidDisappear:]
2023-09-14 19:51:39.548182+0800 viewcontroller[1460:34333] ---------B->A---------
2023-09-14 19:51:39.550289+0800 viewcontroller[1460:34333] -[BViewController viewWillDisappear:]
2023-09-14 19:51:39.550558+0800 viewcontroller[1460:34333] -[AViewController viewWillAppear:]
2023-09-14 19:51:40.055798+0800 viewcontroller[1460:34333] -[AViewController viewDidAppear:]
2023-09-14 19:51:40.056047+0800 viewcontroller[1460:34333] -[BViewController viewDidDisappear:]

由此可以得出我们ViewController的生命周期执行顺序:

  • 当仅仅弹出单个视图控制器
loadView->willAppear->willLayoutsubviews->didLayoutSubviews->didAppear
  • 当两个视图控制器来回切换,我们的第一个视图控制器不会直接调用disAppear函数,而是当第二个视图控制器didAppaer之后才会调用disAppear函数,反之也是如此

注意点

loadview:

每次访问UIViewController的view(比如vc.view、self.view)而且view为nil,loadView方法就会被调用。这也是为什么我们重写loadview方法时必须要加上 [super loadView];,因为调用这个方法可以自动生成我们的view。如果我们找不到view,我们的程序就会一直调用loadview方法来寻找我们的view。

你可能感兴趣的:(ios,cocoa,macos)