#####该文章属于<简书 — 刘小壮>原创,转载请注明:
<简书 — 刘小壮> http://www.jianshu.com/p/173f25d35ddc
##什么是UIStackView?
在iOS9
中苹果在UIKit
框架中引入了一个新的视图类UIStackView
。UIStackView
类可以帮我们布局UI控件,而我们不需要设置任何约束或设置很少的约束就可以,其他都由UIStackView
帮我们自动完成了。
UIStackView
提供了两个方向的约束,垂直布局和水平布局,我们可以通过UILayoutConstraintAxis
枚举值来查看两种布局方式。
如果初学者来学习UIStackView
比较抽象,不太好接触这个新的控件,而且很容易出错,先看一下下面这个GIF来初步了解一下这个控件吧。
##UIStackView
在Interface Builder
中使用UIStackView
就类似于使用一个UI控件一样,通过让将其他视图成为UIStackView
的子视图来进行布局的,UIStackView
也可以嵌套多个UIStackView
。
值得注意的是,UIStackView
虽然继承自UIView
,但是并不参与屏幕的渲染,重写drawRect:
方法也是无效的。
#####UIStackView继承链条,自身特性等信息
#####枚举值Interface Builder
中的UIStackView
控件,右侧设置面板中提供了一些选项,这些设置是对应着代码中的枚举值的:
- Axis
Horizontal -> UILayoutConstraintAxisHorizontal
水平方向布局Vertical -> UILayoutConstraintAxisVertical
垂直方向布局 - Distribution
Fill -> UIStackViewDistributionFill
填充整个UIStackView,并且根据内部子视图尺寸对子视图尺寸进行动态调整。Fill Equally -> UIStackViewDistributionFillEqually
根据视图大小平均分配UIStackView尺寸,等比例填充UIStackView,过程中会根据分配的大小改变子视图尺寸。Fill Proportionally -> UIStackViewDistributionFillProportionally
根据之前的比例填充UIStackView。Equal Spacing -> UIStackViewDistributionEqualSpacing
填充整个UIStackView,子视图没有占满UIStackView将会用空白平均填充子视图中间的间距,超出UIStackView将会根据arrangedSubviews数组下标压缩子视图。Equal Centering -> UIStackViewDistributionEqualCentering
平均分配子视图得到每个视图的中心点,使用这个中心点来布局每个子视图,并且保持spacing距离,超出将会重新布局子视图,并压缩部分子视图。 - Alignment
Fill -> UIStackViewAlignmentFill
视图纵向填充Top -> UIStackViewAlignmentTop
视图向上对其(适用于Horizontal模式)Center -> UIStackViewAlignmentCenter
视图居中对其Bottom -> UIStackViewAlignmentBottom
视图向下对其(适用于Horizontal模式)First Baseline -> UIStackViewAlignmentFirstBaseline
根据上方基线布局所有子视图的y值(适用于Horizontal模式)Last Baseline -> UIStackViewAlignmentLastBaseline
根据下方基线布局所有子视图的y值(适用于Horizontal模式)trailing -> UIStackViewAlignmentTrailing
视图向左对齐(适用于Vertical模式)leading -> UIStackViewAlignmentLeading
视图向右对齐(适用于Vertical模式) - spacing
spacing -> CGFloat spacing
子控件之间的最小距离
可以根据下面的图片结合上面的枚举值联系起来比较好理解
arrangedSubviews数组
UIStackView
使用arrangedSubviews
数组来管理子视图。需要注意的是这个数组是一个readonly
的属性,我们需要调用方法对arrangedSubviews
数组进行操作。
初始化数组:- (instancetype)initWithArrangedSubviews:(NSArray<__kindof UIView *> *)views;
添加子视图:- (void)addArrangedSubview:(UIView *)view;
移除子视图:- (void)removeArrangedSubview:(UIView *)view;
根据下标插入视图:- (void)insertArrangedSubview:(UIView *)view atIndex:(NSUInteger)stackIndex;
##小试牛刀
我们可以从Interface Builder
右侧的操作面板中,选择UIStackView
控件直接拖到XIB
中。可以选择Horizontal
和Vertical
两个方向的UIStackView
,也可以在拖到XIB
中之后手动修改。
然后将两个View
拖到这个UIStackView
中,父视图也可以将UIStackView
作为子视图来进行多层UIStackView
嵌套,这也是苹果推荐的做法。
打开右侧设置面板来设置UIStackView
的一些属性,达到更好的布局效果。
除了上面的方法也可以在XIB
中直接选择多个View
,然后点击右下方的Stack
按钮,系统会自动推断布局方式,帮我们自动布局子视图,我们可以在系统布局之后在手动进行调整。
代码布局其实本质上就是对数组进行操作,数组中存储的是UIStackView
的子视图。然后通过设置UIStackView
的枚举值属性进行页面排布。代码布局的方式这里就不演示了。。。😉
##UIStackView和NSLayoutConstraint布局转换
如果你之前的项目中已经有约束,只需要将添加UIStackView
管理UI控件约束清除。选中需要添加的UI控件,点击右下方的Stack
按钮就可以。