1. 布局过程
在使用了Auto Layout情况下,View显示到屏幕上分为3个阶段:
- 约束计算:发生自子View->父View。通过显式调用
setNeedsUpdateConstraints
来触发这个过程,实际上更改约束会自动触发这个过程。在自定义View中,可以覆盖updateConstraints
来添加或变更约束。 - 布局:发生自父View->子View。将1中计算的结果,应用到View的frame上。通过显式调用
setNeedsLayout
来触发这个过程,这个函数很廉价,因为所有的布局请求都会合并成一个layout过程去做。当然,可以通过调用layoutIfNeeded
来迫使系统立刻更新布局。在自定义View中,可以通过覆盖layoutSubviews
方法来hook这个过程。 - 展示:这个过程与是否使用了Auto Layout无关。发生自父View->子View。通过显式调用
setNeedsDisplay
来触发这个过程,视图的绘制过程也会被合并。类似地,可以覆盖drawRect:
来hook这个过程。
以上三个阶段是依次发生的,每一步都会依赖它的前一步。要注意,以上三个阶段这是一个迭代的过程,比如布局阶段可能触发了另一个约束计算的过程,这个计算过程又触发了新的布局过程等等。
2. Intrinsic Content Size
Intrinsic这个词的意思,「本质的、固有的」。一个View的Intrinsic Content Size意指这个View想要舒舒服服地显示出来,需要多大的size。对于一个numberOfLines
为0的Label来说,它的preferredMaxLayoutWidth
确定、font确定,则它的intrinsicContentSize
就定下来了。不是所有的View都有intrinsicContentSize
,在自定义的View中,可以覆盖intrinsicContentSize
方法来返回Intrinsic Content Size,并可以通过调用invalidateIntrinsicContentSize
来通知布局系统在下一个布局过程采用新的Intrinsic Content Size。
3. Compression Resistance 和 Content Hugging
首先明确:这两个属性都是讨论的前提是View在相应的维度有Intrinsic Content Size。实际上,这两个属性和Intrinsic Content Size都是被翻译成约束来实现的。举个例子(请务必多读几遍这个例子):假设一个Label的Intrinsic Content Size是{100, 30},它在水平和竖直方向上的Compression Resistance优先级是750,在水平和竖直方向的Content Hugging优先级是250,那么这些被转成了如下约束:
H:[label(<=100@250)]
H:[label(>=100@750)]
V:[label(<=30@250)]
V:[label(>=30@750)]
4. Alignment Rect
Auto Layout操作的是View的Alignment Rect,不是View的Frame。这是个伟大的概念,用于把View的布局和显示解耦,虽然大部分情况它们是相等的。同样,View的Intrinsic Content Size也指的是Alignment Rect。在View有阴影、自定义Badge时,这个概念会很有用。在自定义的View中,可以通过覆盖alignmentRectInsets
,来返回在特定的Frame下,Alignment Rect的edge insets是多少。还可以覆盖alignmentRectForFrame:
和frameForAlignmentRect:
来实现更精细的控制,蛋这两个方法必须互为反函数。
5. 其它
- 如果自定义的View是基于Auto Layout封装,那么它就不能在未开启Auto Layout的Window上使用,因此最好覆盖View的
requiresConstraintBasedLayout
,返回YES来宣称这件事。 - 程序挂掉:'NSInternalInconsistencyException', reason: 'Auto Layout still required after executing -layoutSubviews. 原因通常因为是我们在第2个阶段(布局阶段)更改了约束,这通常是在被覆盖的
layoutSubviews
方法里做的,这触发了第1个阶段,但是却没有再次触发布局阶段。通常的解决办法是在更改约束后再次调用[super layoutSubviews]
来显式触发布局过程。 - Auto Layout的性能:http://floriankugler.com/2013/04/22/auto-layout-performance-on-ios/
原文链接:http://blog.liushuaiko.be/blog/2016/07/09/advanced-autolayout/
donate1.png
网友评论