iOS CADisplayLink筆記

什麼是CADisplayLink


CADisplayLink是一個能讓我們以和屏幕刷新率相同的頻率將內容畫到屏幕上的定時器。我們在應用中創建一個新的 CADisplayLink 對象,把它添加到一個runloop中,並給它提供一個 targetselector 在屏幕刷新的時候調用。

一但 CADisplayLink 以特定的模式註冊到runloop之後,每當屏幕需要刷新的時候,runloop就會調用CADisplayLink綁定的target上的selector,這時target可以讀到 CADisplayLink 的每次調用的時間戳,用來準備下一幀顯示需要的數據。例如一個視頻應用使用時間戳來計算下一幀要顯示的視頻數據。在UI做動畫的過程中,需要通過時間戳來計算UI對象在動畫的下一幀要更新的大小等等。
在添加進runloop的時候我們應該選用高一些的優先級,來保證動畫的平滑。可以設想一下,我們在動畫的過程中,runloop被添加進來了一個高優先級的任務,那麼,下一次的調用就會被暫停轉而先去執行高優先級的任務,然後在接着執行CADisplayLink的調用,從而造成動畫過程的卡頓,使動畫不流暢


duration屬性提供了每幀之間的時間,也就是屏幕每次刷新之間的的時間。我們可以使用這個時間來計算出下一幀要顯示的UI的數值。但是 duration只是個大概的時間,如果CPU忙於其它計算,就沒法保證以相同的頻率執行屏幕的繪製操作,這樣會跳過幾次調用回調方法的機會。
frameInterval屬性是可讀可寫的NSInteger型值,標識間隔多少幀調用一次selector 方法,默認值是1,即每幀都調用一次。如果每幀都調用一次的話,對於iOS設備來說那刷新頻率就是60HZ也就是每秒60次,如果將 frameInterval 設爲2 那麼就會兩幀調用一次,也就是變成了每秒刷新30次。
我們通過pause屬性開控制CADisplayLink的運行。當我們想結束一個CADisplayLink的時候,應該調用-(void)invalidate
runloop中刪除並刪除之前綁定的 targetselector
另外CADisplayLink 不能被繼承。


CADisplayLinkNSTimer 有什麼不同

iOS設備的屏幕刷新頻率是固定的,CADisplayLink在正常情況下會在每次刷新結束都被調用,精確度相當高。
NSTimer的精確度就顯得低了點,比如NSTimer的觸發時間到的時候,runloop如果在阻塞狀態,觸發時間就會推遲到下一個runloop週期。並且 NSTimer新增了tolerance屬性,讓用戶可以設置可以容忍的觸發的時間的延遲範圍。
CADisplayLink使用場合相對專一,適合做UI的不停重繪,比如自定義動畫引擎或者視頻播放的渲染。NSTimer的使用範圍要廣泛的多,各種需要單次或者循環定時處理的任務都可以使用。在UI相關的動畫或者顯示內容使用 CADisplayLink比起用NSTimer的好處就是我們不需要在格外關心屏幕的刷新頻率了,因爲它本身就是跟屏幕刷新同步的。


iOS設備的刷新頻率事60HZ也就是每秒60次。那麼每一次刷新的時間就是1/60秒 大概16.7毫秒。當我們的frameInterval值爲1的時候我們需要保證的是 CADisplayLink調用的`target`的函數計算時間不應該大於 16.7否則就會出現嚴重的丟幀現象。
在mac應用中我們使用的不是CADisplayLink而是 CVDisplayLink它是基於C接口的用起來配置有些麻煩但是用起來還是很簡單的。






發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章