setNeedsLayout
Call this method on your application’s main thread when you want to adjust the layout of a view’s subviews. This method makes a note of the request and returns immediately. Because this method does not force an immediate update, but instead waits for the next update cycle, you can use it to invalidate the layout of multiple views before any of those views are updated. This behavior allows you to consolidate all of your layout updates to one update cycle, which is usually better for performance.
調用此方法可以調整子view的布局,但是又不會立即更新布局。需要等到下次更新周期中才會更新。
此行為允許你將所有布局更新合并到一次更新周期中。
layoutIfNeeded
Use this method to force the view to update its layout immediately. When using Auto Layout, the layout engine updates the position of views as needed to satisfy changes in constraints. Using the view that receives the message as the root view, this method lays out the view subtree starting at the root. If no layout updates are pending, this method exits without modifying the layout or calling any layout-related callbacks.
調用此方法可以強制view立即更新約束。當使用Auto Layout時候,layout引擎會根據需要更新view的位置以滿足約束的變化。所以一般都會和setNeedsLayout一起使用。如果希望立刻生成新的frame需要調用此方法,利用這點一般布局動畫可以在更新布局后直接使用這個方法讓動畫生效。
該方法執(zhí)行后會立刻調用layoutSubviews。
setNeedsUpdateConstraints
When a property of your custom view changes in a way that would impact constraints, you can call this method to indicate that the constraints need to be updated at some point in the future. The system will then call updateConstraints as part of its normal layout pass. Updating constraints all at once just before they are needed ensures that you don’t needlessly recalculate constraints when multiple changes are made to your view in between layout passes.
當一個自定義的view的屬性影響到約束的時候,可以調用此方法告知需要更新約束,但是不會立刻更新。
它可以避免當視圖約束多次改變時,每次都重新計算約束
updateConstraintsIfNeeded
Whenever a new layout pass is triggered for a view, the system invokes this method to ensure that any constraints for the view and its subviews are updated with information from the current view hierarchy and its constraints. This method is called automatically by the system, but may be invoked manually if you need to examine the most up to date constraints.
Subclasses should not override this method.
強制更新當前view以及子view的約束。這個方法一般是系統(tǒng)來調用的,但是如果需要將約束更新到最新,則可以手動調用。
注意:該方法不應該被重寫
該方法執(zhí)行后系統(tǒng)會調用updateConstraints。
layoutSubviews
系統(tǒng)重寫布局
Subclasses can override this method as needed to perform more precise layout of their subviews. You should override this method only if the autoresizing and constraint-based behaviors of the subviews do not offer the behavior you want. You can use your implementation to set the frame rectangles of your subviews directly.
子類可以根據需要重寫此方法,以更精確地布局其子視圖。
注意不要去手動調用這個方法。
updateConstraints
系統(tǒng)更新約束
It is almost always cleaner and easier to update a constraint immediately after the affecting change has occurred. For example, if you want to change a constraint in response to a button tap, make that change directly in the button’s action method.
You should only override this method when changing constraints in place is too slow, or when a view is producing a number of redundant changes.
一般情況下都不要手動重寫這個方法,除非你要修改休書的地方執(zhí)行很慢,或者有冗余的約束。
注意:要在最后一步調用[super updateConstraints]
小結
stackoverflow上有個回答很全面setneedslayout-vs-setneedsupdateconstraints:
- setNeedsUpdateConstraints makes sure a future call to updateConstraintsIfNeeded calls updateConstraints.
- setNeedsLayout makes sure a future call to layoutIfNeeded calls layoutSubviews
When layoutSubviews is called, it also calls updateConstraintsIfNeeded, so calling it manually is rarely needed in my experience
作者的意思就是說updateConstraintsIfNeeded很少需要手動調用
因此一般使用法則是:
- 如果你直接操作約束,就使用
setNeedsLayout - 如果你使用了
setNeedsLayout,還想做一些其他的,比如說獲取到最新的frame,這時候就需要再setNeedsLayout追加一個layoutIfNeeded - 如果你重寫了
updateConstraints方法,這時候才需要調用setNeedsUpdateConstraints