layoutSubViews 方法
layoutSubviews 方法是用來設(shè)定subview的位置的方法, 是不能手動調(diào)用的。只能通過調(diào)用setNeedsLayout 方法,來讓系統(tǒng)自動調(diào)用layoutSubviews方法
If you want to update the layout of your views immediately, call the layoutIfNeeded method.
setNeedDisplay 方法
setNeedsDisplay 調(diào)用時, 系統(tǒng)會自動調(diào)用 drawRect 方法。
當(dāng)在操作UI時,比如改變了Frame,更新了UIView/CALayer 的層次的時,或者手動調(diào)用了UIVier/CALayer 的setNeedsLayout/setNeedsDisplay方法
后,這個UIView/CALayer就被標(biāo)記為待處理,并提交到了一個全局的容器里去。
蘋果注冊了一個Observer監(jiān)聽 BeforeWaiting(即將進入休眠)和 Exit(即將退出Loop)事件,回調(diào)去執(zhí)行一個很長的函數(shù):
_ZN2CA11Transaction17observer_callbackEP19__CFRunLoopObservermPv()。這個函數(shù)里會遍歷所有待處理的UIView/CALayer
以執(zhí)行實際的繪制和調(diào)整,并更新UI界面。
這個函數(shù)內(nèi)部的調(diào)用棧大概是這樣的:
_ZN2CA11Transaction17observer_callbackEP19__CFRunLoopObservermPv()
QuartzCore:CA::Transaction::observer_callback:
CA::Transaction::commit();
CA::Context::commit_transaction();
CA::Layer::layout_and_display_if_needed();
CA::Layer::layout_if_needed();
[CALayer layoutSublayers];
[UIView layoutSubviews];
CA::Layer::display_if_needed();
[CALayer display];
[UIView drawRect];