2014-01-15 9 views
6

我想有一個UIView子類,實現除了重繪類似setNeedsDisplay的方法,(即,通常會被通過drawRect:調用)將出現在後臺線程有時soonish,而不是在當前更新週期結束時。它可能被稱爲setNeedsAsynchronousDisplay。或者現有的setNeedsDisplay可能會被劫持,並且在循環結束時不會導致重繪,或者其他什麼,只要它允許重繪不會發生在主線程阻塞屏幕上,直到更新交互完成爲止。擁有的UIView的drawRect發生在後臺線程

在重繪發生之前,視圖可以繼續使用其當前繪製的表示。

沿着這些線合理可行嗎?

謝謝!

回答

10

是的,這是可能的。您可能需要將內容視圖作爲背景中的圖像生成,並將圖像推送到nsdictionary或數組中。

所以,雖然您的背景正在生成圖像,您可以通過渲染圖像直接顯示圖像,提供的圖像已經生成。

顯示如何操作的WWDC視頻:WWDC 2012 session 211 - Building Concurrent User Interfaces on IOS。以下是視頻說明:

爲了獲得絕佳的用戶體驗,在呈現複雜的UI元素和處理數據時保持應用程序響應非常重要。瞭解如何在UIKit圖層上使用併發性來執行繪圖和其他常見操作,而不會阻止用戶交互。

+0

謝謝,這聽起來很不錯。 – Benjohn

+0

觀看視頻後,我非常興奮,甚至試圖自己創建一個。對於沒有像按鈕或高亮狀態那樣的許多交互的單元視圖更實際。如果您自己創建了一個,請告訴我。 –

+0

謝謝@Ehan,這聽起來很有幫助。我今天會看看。 – Benjohn

-3

編號查看繪圖必須發生在前臺。蘋果在他們的文檔中對此非常清楚。

編輯:你是對的,你可以在後臺做核心圖形繪製,只要它不在UIView對象的繪圖方法中。您必須在後臺執行繪圖,然後在繪圖完成後向主線程發送消息以更新視圖對象。

我會建議不要試圖覆蓋setNeedsDisplay。相反,請添加新的setNeedsAsynchronousDisplay方法。在該方法中,使用GCD調用將代碼隊列渲染到異步隊列。渲染完成後,渲染代碼會在主線程上發送setNeedsDisplay消息給self。

然後在你的子類的drawRect方法中,檢查預渲染圖像並將它們繪製到視圖的上下文中而不是普通代碼中。

這樣做的一個缺點是,僅僅通過實現drawRect,你可能會減慢渲染速度,因爲系統會調用它來代替渲染視圖內容的其他更有效的東西。

+0

謝謝@Duncan C,但我不相信iOS 4的核心圖形操作(但不是它們的UI包裝)的情況。請參閱[Apple的技術說明](https://developer.apple.com/library/ios/qa/qa1637/_index.html)。我懷疑UIView更新確實需要在主線程中,但這並不意味着繪圖不能在另一個表面的背景中發生,然後被交換。我在想法/建議/最佳實踐/完整的解決方案。 – Benjohn

+0

我從來沒有用過「drawRect inContext」,也許值得一試。 –