一、简述
iOS11中页面布局引入了页面安全区域safeAreaInsets
的概念,因此页面中导航条和Tabbar的样式设置会影响到页面布局。以下三个属性的配置决定了你的页面布局展示样式。
- translucent 导航条的半透明度设置;
- edgesForExtendedLayout 视图控制器布局时边缘延伸方式;
- extendedLayoutIncludesOpaqueBars 视图控制器布局时是否包括不透明条;
二、相关属性解释:
-
translucent:iOS7之前默认值为NO,iOS7之后
translucent
会根据导航条的背景和barStyle推测,然后确定真实的值。如果barStyle设置为UIBarStyleBlackTranslucent,则始终为YES。
- 如果导航栏没有定义背景图或背景图的alpha的值小于1.0,则
translucent
默认为YES; - 如果导航栏背景图是完全不透明时,则
translucent
默认为NO; - 如果
translucent
设置为YES(半透明)时,那么导航栏的自定义背景图完全不透明,UIKit会将系统定义的不透明度应用于背景图; - 如果
translucent
设置为NO时,并且背景图像不不透明,UIKit将添加不透明背景;
UIKit将使用导航栏的Nar的barTintColor为图像提供不透明背景,如果barTintColor为nil,则为UIBarStyleBlack提供黑色背景或者为UIBarStyleDefault提供白色背景。
-
edgesForExtendedLayout:视图控制器布局时边缘延伸方式,默认值为UIRectEdgeAll;无论
translucent
的值为true还是false,都将生效。 -
extendedLayoutIncludesOpaqueBars:表示视图控制器布局时是否包括不透明条,默认是NO,只有在
translucent = false
时生效。extendedLayoutIncludesOpaqueBars = NO
控制器的布局起始位置在导航栏下方,extendedLayoutIncludesOpaqueBars = YES
控制器的布局将延伸到导航栏下方,从屏幕顶部开始布局。
三、设置验证
- 实验1:
self.navigationController.navigationBar.translucent = YES;
self.edgesForExtendedLayout = UIRectEdgeAll;
self.extendedLayoutIncludesOpaqueBars = NO;
页面状态:
- 导航栏样式为半透明;
-
控制器viewController的布局延伸到导航栏下面,从设备最顶部开始计算;
实验1
- 实验2:
self.navigationController.navigationBar.translucent = YES;
self.edgesForExtendedLayout = UIRectEdgeNone;
self.extendedLayoutIncludesOpaqueBars = NO;
页面状态:
- 导航栏样式为半透明;
-
控制器viewController的布局从导航栏下边缘开始计算;
实验2
- 实验3-1:
self.navigationController.navigationBar.translucent = YES;
self.edgesForExtendedLayout = UIRectEdgeAll;
self.extendedLayoutIncludesOpaqueBars = YES;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局延伸到导航栏下面,从设备最顶部开始计算;
- 实验3-2:
self.navigationController.navigationBar.translucent = YES;
self.edgesForExtendedLayout = UIRectEdgeNone;
self.extendedLayoutIncludesOpaqueBars = YES;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局从导航栏下边缘开始计算;
- 实验3-3:
self.navigationController.navigationBar.translucent = YES;
self.edgesForExtendedLayout = UIRectEdgeAll;
self.extendedLayoutIncludesOpaqueBars = NO;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局延伸到导航栏下面,从设备最顶部开始计算;
- 实验3-4:
self.navigationController.navigationBar.translucent = YES;
self.edgesForExtendedLayout = UIRectEdgeNone;
self.extendedLayoutIncludesOpaqueBars = NO;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局从导航栏下边缘开始计算;
通过3-1和3-3来看与"情况1"的结果是相同的,3-2和3-4的结果与"情况2"相同,说明在
translucent = YES
的情况下extendedLayoutIncludesOpaqueBars
属性值的设置无效,控制器延伸布局最终看的是edgesForExtendedLayout
。
- 实验4-1:
self.navigationController.navigationBar.translucent = NO;
self.edgesForExtendedLayout = UIRectEdgeAll;
self.extendedLayoutIncludesOpaqueBars = NO;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局从导航栏下边缘开始计算;
- 实验4-2:
self.navigationController.navigationBar.translucent = NO;
self.edgesForExtendedLayout = UIRectEdgeNone;
self.extendedLayoutIncludesOpaqueBars = NO;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局从导航栏下边缘开始计算;
由4-1和4-2的相同结果可以看出,在
translucent = NO
状态栏为不透明状态,此时设置edgesForExtendedLayout
将无意义,所以在状态栏不透明时控制器的布局方式默认为
从导航栏下边缘开始计算。
- 实验5-1:
self.navigationController.navigationBar.translucent = NO;
self.edgesForExtendedLayout = UIRectEdgeAll;
self.extendedLayoutIncludesOpaqueBars = YES;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局延伸到导航栏下面,从设备最顶部开始计算;
- 实验5-2:
self.navigationController.navigationBar.translucent = NO;
self.edgesForExtendedLayout = UIRectEdgeAll;
self.extendedLayoutIncludesOpaqueBars = NO;
页面状态:
- 导航栏样式为半透明;
- 控制器viewController的布局从导航栏下边缘开始计算;
1、通过实验5和实验3可以得出结论:属性
extendedLayoutIncludesOpaqueBars
的设置只有在translucent
为NO时(导航栏不透明时)会生效。
2、如果设置edgesForExtendedLayout
的值为UIRectEdgeNone
时,extendedLayoutIncludesOpaqueBars
的设置将会被忽略。控制器布局主要看edgesForExtendedLayout
的设置。
注:UITabBar的情况与UINavigationBar的设置大致上相同。
网友评论