ios程序启动原理与窗口、控制加载、控制器view加载、导航控制器加载
来源:互联网 发布:mac照片和iphoto 编辑:程序博客网 时间:2024/06/10 05:55
一、程序启动过程
main —>UIApplicationMain
intmain(intargc, char * argv[])
{
@autoreleasepool{
returnUIApplicationMain(argc, argv,nil,NSStringFromClass([CXAppDelegateclass]));
}
{
@autoreleasepool{
returnUIApplicationMain(argc, argv,nil,NSStringFromClass([CXAppDelegateclass]));
}
}
程序启动的入口,如果传入nil参数,默认为UIApplication类名字的字符串,可以用 NSStringFromClass([UIApplicationclass]) 和 @“UIApplication"来代替nil
UIApplicationMain底层的加载过程
1、创建UIApplication对象
2、创建UIApplicationDelegate对象,并且赋值给UIApplication对象的代理属性
3、开启主运行循环
4、加载into.plist文件,判断是否指定main.storyboard,如果指定,就去加载。
二、UIWindow
1、常见的窗口:键盘,UIActionSheet,UIAlertView
特殊的窗口:状态栏
2、窗口的层级(windowLevel)
UIWindowLevelNormal<UIWindowLevelStatusBar<UIWindowLevelAlert
窗口默认都是UIWindowLevelNormal层级,键盘的层级永远是最高的,在显示之前会获取当前最高层级数,然后键盘的层级+1
一个应用程序只能有一个主窗口
3、窗口中底层的实现方法
// 1、创建窗口,创建的window需要用强指针来引用以避免刚创建就被销毁
self.window = [[UIWindowalloc] initWithFrame:[UIScreen mainScreen].bounds];
// 2、创建窗口的根控制器
UIViewController *rootVc = [[UIViewControlleralloc]init];
rootVc.view.backgroundColor = [UIColorredColor];
// 3、把控制器作为窗口的根控制器
// rootViewController的好处:1、可以让窗口旋转;2.让代码结构清晰(自定义跟控制器,控制器的事情写在控制器里面)
window.rootViewController = rootVc;
// 4、把窗口显示在屏幕上,并且成为应用程序的主窗口
[window makeKeyAndVisible];
makeKeyAndVisible底层实现:
1、成为application的主窗口 application.keyWindow = self.window;
2、让窗口显示出来 self.window.hidden = NO;
3、把窗口根控制器的view添加到窗口上
[self.window addSubview:window.rootViewController.view];
三、三种创建控制器的方法
1、直接创建
UIViewController*vc = [[UIViewControlleralloc]init];
2、通过storyboard创建
// 1.创建窗口
self.window = [[UIWindowalloc] initWithFrame:[UIScreen mainScreen].bounds];
// 2.1加载main.storyboard,并且实例化一个控制器
UIStoryboard *storyboard = [UIStoryboardstoryboardWithName:@"Main"bundle:nil];
// 2.2 实例化控制器(instantiateInitialViewController:会去加载箭头指向的控制器)
ViewController *vc = [storyboard instantiateInitialViewController];
// ViewController *vc = [storyboard instantiateViewControllerWithIdentifier:@"vc"];
// instantiateViewControllerWithIdentifier:会去storyboard中有木有vc这个标识的控制器
// 3.设置窗口的跟控制器
self.window.rootViewController= vc;
// 4.显示窗口
// 3.设置窗口的跟控制器
self.window.rootViewController= vc;
// 4.显示窗口
[self.windowmakeKeyAndVisible];
3、通过xib文件创建
// 1、设置xib的file’owner的class属性为控制器Class
2、加载xib需要file’owner和xib的view连线
self.window= [[UIWindowalloc]initWithFrame:[UIScreenmainScreen].bounds];
// Nib = xib
// 通过xib创建控制器
// 创建控制器,必须要有view,没有view就会报错
ViewController*vc = [[ViewControlleralloc]initWithNibName:@"VC"bundle:nil];
self.window.rootViewController= vc;
// Nib = xib
// 通过xib创建控制器
// 创建控制器,必须要有view,没有view就会报错
ViewController*vc = [[ViewControlleralloc]initWithNibName:@"VC"bundle:nil];
self.window.rootViewController= vc;
[self.windowmakeKeyAndVisible];
四、控制器view的创建
1、loadView()
loadView作用:创建控制器的view
loadView什么时候去调用:第一次使用控制器的view的时候就会调用loadView
只要重写了loadView这个方法,就必须自己创建控制器的view,系统就不会帮你创建控制器view
2、loadView底层做法
0、判断控制器是否有重写loadView方法,如果有就只会加载loadView
1、判断下有没有指定storyboard,如果有,就去加载storyboard描述的控制器的view
2、判断下有没有指定nibName,如果有,就去加载nibName描述的控制器的view
2.0如何判断有没有指定nibName,[self nibName]
2.1判断下nibName是否为空,如果为空,他会尝试找下有没有跟控制器同名,但是不带Controller的xib
2.2跟控制器同名的xib,nibName = ViewController,但是这一步有条件,前提条件你没有重写loadView
CXViewController -> CXView.xib -> CXViewController.xib
2.3如果都没有找到,直接创建几乎透明的view(clear color)
[ViewControlleralloc]init]; 的底层会去调用 [ViewControlleralloc]initWithNibName:nilbundle:nil] 方法,从步骤2开始逐步执行判断
3、view为懒加载,当需要在屏幕上显示view的时候才会去调用loadView方法加载view
[[ViewControlleralloc]init].view.backgroundColor= [UIColorredColor];
当程序执行该代码时会先去判断view是否为空,如果不为空则直接返回已创建的view,如果为空,则会调用loadView方法加载view
/*********伪代码 *********/
- (UIView*)view
{
if (_view == nil) {
[self loadView];
[self viewDidLoad];
}
return _view;
{
if (_view == nil) {
[self loadView];
[self viewDidLoad];
}
return _view;
}
/*********伪代码 *********/
当view为空时,且重写了loadView方法并为view的背景赋值时
- (void)loadView
{
// 因为重写了loadView方法,所以程序不会自动加载view,必须手动创建一个view给控制器
self.view= [[UIViewalloc]initWithFrame:[UIScreenmainScreen].bounds];
self.view.backgroundColor= [UIColoryellowColor];
self.view.backgroundColor= [UIColoryellowColor];
}
在viewDidLoad()方法里重新为控制器的view赋值,该方法会在控制器加载完所有的控件时候调用
- (void)viewDidLoad {
[super viewDidLoad];
self.view.backgroundColor= [UIColorblueColor];
NSLog(@"控制器的view加载完成了");
[super viewDidLoad];
self.view.backgroundColor= [UIColorblueColor];
NSLog(@"控制器的view加载完成了");
}
以上方法执行完,view的颜色将会是redColor
五、导航控制器
UINavigationController的view结构
导航控制器的view 在最底层,导航子控制器的view在第二层,导航条在最上面
当有控制器入栈时,控制器的view会添加到导航子控制器的view上
1、创建导航控制器必须要有一个导航控制器的根控制器,因为导航条的内容必须要依赖栈顶控制器,默认第一个根控制器就是栈顶控制器
//创建导航控制器的跟控制器
UIViewController *vc = [[ViewControlleralloc]init];
vc.view.backgroundColor = [UIColorredColor];
//创建导航控制器view,提示:导航控制器也需要一个跟控制器
UINavigationController *nav = [[UINavigationControlleralloc] initWithRootViewController:vc];
//导航控制器成为window的根控制器
self.window.rootViewController= nav;
[self.windowmakeKeyAndVisible];
2、initWithRootViewController:底层会调用pushViewController。
pushViewController:底层会把控制器压入栈,并且把控制器的view添加到导航子控制器的view上面。
如果导航子控制器上已有其他控制器的view,这时会推出其他控制器的view,并把自己的view添加上去(推出的view暂时不会被销毁,只有控制器出栈的时候才会销毁)
3、等需要push控制器的view完全显示的时候,会拿到push控制的navigationController属性赋值导航控制器
vc.navigationController = nav;
所以在被push的控制器里面可以访问到导航控制器
self.navigationController
4、导航控制器的viewControllers用来保存导航控制器里面所有的子控制器,让属性是个NSArray类型,0号索引永远是栈底
5、导航控制器永远显示出来的界面是栈顶控制器的view
6、 [self.navigationControllerpopViewControllerAnimated:YES];
调用这个方法,并不会马上出栈,等控制器的view完全移除父控件,才会出栈,控制器出栈后,就会被销毁
六、导航条的内容
1、导航条的内容由栈顶控制器的UINavigationItem决定,为什么要这样设计,因为导航控制器只有一个导航条,如果每个子控制器都能设置,就不知道听谁的了,所以由显示出来的控制器决定。
2、UINavigationItem:是一个模型,用来决定导航条的内容。
3、UIBarButtonItem:是一个模型,用来决定导航条上按钮的内容。
4、导航条上面的子控件的位置由系统决定,但是尺寸是由我们自己决定
4.1、[button sizeToFit]默认计算按钮尺寸,根据按钮的内容计算出最合适的尺寸
5、在ios7之后,默认就会导航条上的按钮的图片渲染成蓝色
5.1、如何保持图片最原始的效果,不要渲染
[image imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
5.2、Item就是模型,MVC,修改模型就能改界面
0 0
- ios程序启动原理与窗口、控制加载、控制器view加载、导航控制器加载
- 程序启动器、窗口、控制器加载、控制器View加载、导航控制器
- 控制器view加载原理
- [iOS 转] xib文件加载控制器View的一些原理
- 如何加载控制器View
- ios-day11-04(控制器view的创建与延迟加载)
- iOS中视图控制器View的加载与生命周期
- ios深入了解控制器view的加载
- iOS 控制器View加载顺序详细版
- iOS--控制器加载自定义view的xib
- 控制器View的加载 && 创建
- xib文件加载控制器View的一些原理
- XMG 导航控制器push的时候下一个控制器的时候view的加载
- iOS中关于控制器view加载顺序的个人总结
- iOS 【通过sb加载描述window根控制器的view】
- iOS 【通过xib加载描述window根控制器的view】
- iOS之深入了解控制器View的加载
- iOS之深入了解控制器View的加载
- wav文件格式详解
- iOS学习之UINavigationController详解与使用(二)页面切换和segmentedController
- UITableView划动删除的实现
- Java开发中的乱码问题
- 用MATLAB信号处理工具箱进行FIR滤波器设计的三种方法
- ios程序启动原理与窗口、控制加载、控制器view加载、导航控制器加载
- Caused by: java.lang.OutOfMemoryError: Java heap space错误原因及解决方法
- iOS学习之UINavigationController详解与使用(三)ToolBar
- C语言中Const的用法
- Qt学习笔记外观篇(二):QStyle
- JAVA基础(11) 系统日志
- new balance 574In various strategies
- 11个实用的Apache .htaccess配置
- C++学习之道:glog