「iOS」viewController的生命周期

iOS学习

ViewController生命周期有关方法

  1. init - 初始化程序;
  2. loadView - 在UIViewController对象的view被访问且为空的时候调用;
  3. viewDidLoad - 视图加载完成后调用;
  4. viewWillAppear - UIViewController对象的视图即将加入窗口时调用;
  5. viewDidAppear - UIViewController对象的视图已经加入窗口时调用;
  6. viewWillDisappear - UIViewController对象的视图即将消失时调用;
  7. viewDidDisappear - UIViewController对象的视图已经消失时调用;
  8. didReceiveMemoryWarning - 出现内存警告。由于此处ViewController的view已经被释放了,ViewController中的空间可以在此处释放掉。
  9. dealloc - 视图被销毁,此次需要对在init和viewDidLoad中创建的对象进行释放;

需要注意的是:

loadView和viewDidLoad的区别就是,loadView时view还没有生成,viewDidLoad时,view已经生成了,loadView只会被调用一次,而viewDidLoad可能会被调用多次(View可能会被多次加载),当view被添加到其他view中之前,会调用viewWillAppear,之后会调用viewDidAppear。

当view从其他view中移除之前,调用viewWillDisAppear,移除之后会调用viewDidDisappear。

当view不再使用时,受到内存警告时,ViewController会将view释放并将其指向为nil。


案例

创建A,B两个视图。

其中A视图代码:

objectivec 复制代码
#import "ViewController.h"
#import "secondVC.h"

@interface ViewController ()

@end

@implementation ViewController



- (void)viewDidLoad {
    [super viewDidLoad];
    NSLog(@"view1 Did Load");

    // Do any additional setup after loading the view.
    self.btn = [UIButton buttonWithType:UIButtonTypeSystem];
    [self.btn setTitle:@"切换视图" forState:UIControlStateNormal];
    self.btn.frame = CGRectMake(100, 100, 100, 50);
    self.btn.center = self.view.center;
    [self.btn addTarget:self action:@selector(pressbtn) forControlEvents:UIControlEventTouchUpInside];
    [self.view addSubview:self.btn];
    
}

-(void)pressbtn
{
    secondVC *secondvc = [[secondVC alloc] init];
    [self presentViewController:secondvc animated:YES completion:nil];
}
-(void)viewWillAppear:(BOOL)animated
{
    NSLog(@"view1将要显示");
}

-(void)viewDidAppear:(BOOL)animated
{
    NSLog(@"view1已经显示");
}

-(void)viewWillDisappear:(BOOL)animated
{
    NSLog(@"view1将要消失");
}

-(void)viewDidDisappear:(BOOL)animated
{
    NSLog(@"view1已经消失");
}
@end

B视图代码:

objectivec 复制代码
#import "secondVC.h"

@interface secondVC ()

@end

@implementation secondVC

-(void)loadView
{
    self.view = [[UIView alloc] init];
    NSLog(@"view2正在加载");
}

- (void)viewDidLoad {
    [super viewDidLoad];
    NSLog(@"view2 Did Load");

    // Do any additional setup after loading the view.
    self.view.backgroundColor = [UIColor blueColor];
    UIView *view = [[UIView alloc] init];
    view.backgroundColor = [UIColor redColor];
    view.frame = CGRectMake(150, 300, 100, 100);
    [self.view addSubview:view];
    
    UIButton *btn = [UIButton buttonWithType:UIButtonTypeSystem];
    [btn setTitle:@"切换视图" forState:UIControlStateNormal];
    btn.frame = CGRectMake(100, 700, 100, 80);
    [btn addTarget:self action:@selector(press) forControlEvents:UIControlEventTouchUpInside];
    [self.view addSubview:btn];
    
}

-(void)viewWillAppear:(BOOL)animated
{
    NSLog(@"view2将要显示");
}

-(void)viewDidAppear:(BOOL)animated
{
    NSLog(@"view2已经显示");
}

-(void)viewWillDisappear:(BOOL)animated
{
    NSLog(@"view2将要消失");
}

-(void)viewDidDisappear:(BOOL)animated
{
    NSLog(@"view2已经消失");
}

-(void)press
{
    [self dismissViewControllerAnimated:YES completion:nil];
}

@end

最后我们得到运行结果:

第一个视图显示:

切换第二个视图:

返回第一个视图:

使用模态切换的方式切换视图时,会将第一个视图重新下载一遍。即重新执行一遍
viewDidLoad 方法。

而使用push方法切换视图时,则会发现,在第一个视图完全消失后,第二个视图才会加载好。这里直接给出运行结果。


注意

如果需要使用loadView方法,要注意对view进行初始化,否则会进入死循环。

原因:若 loadView 没有加载 view,即为 nil,viewDidLoad 会一直调用 loadView 加载 view,因此构成了死循环,程序即卡死。

解决方法:

  1. 对view进行初始化赋值
  2. 使用[Supper LoadView]方法
  3. 在 ViewDidLoad 里创建 view,省略loadView方法。
相关推荐
初级代码游戏19 分钟前
iOS开发 SwiftUI 15:手势 拖动 缩放 旋转
ios·swiftui·swift
2601_949146532 小时前
APP语音通知接口集成实战:移动端应用接入语音提醒API的开发手册
macos·objective-c·cocoa
森之鸟3 小时前
iOS云打包之Shorebird
ios
GuokLiu3 小时前
260203-OpenWebUI-在Windows上和RHEL上部署Caddy的步骤+在iPhone上操作的步骤
windows·ios·iphone
小鹿软件办公4 小时前
Apple 发布 macOS 11、watchOS 10 和 watchOS 9 更新
macos·objective-c·cocoa
2501_9159214320 小时前
傻瓜式 HTTPS 抓包,简单抓取iOS设备数据
android·网络协议·ios·小程序·https·uni-app·iphone
恋猫de小郭1 天前
Flutter 在 Android 出现随机字体裁剪?其实是图层合并时的边界计算问题
android·flutter·ios
2501_915918411 天前
把 iOS 性能监控融入日常开发与测试流程的做法
android·ios·小程序·https·uni-app·iphone·webview
Digitally1 天前
如何轻松地将大型音频文件从 iPhone 发送到不同的设备
ios·iphone
catchadmin1 天前
PHP 现在可以零成本构建原生 iOS 和 Android 应用 NativePHP for Mobile v3 发布
android·ios·php