Android 圖形架構

weixin_34007291發表於2017-07-11

每一個開發者都應該瞭解的關於 Surface,SurfaceHolder,EGLSurface,SurfaceView,GLSurfaceView,SurfaceTexture,TextureView,SurfaceFlinger,和 Vulkan 的東西。

本頁描述 Android 系統級圖形架構的必要元素及應用框架和多媒體系統如何使用它們。重點是圖形資料的緩衝區如何在系統中移動。如果你曾經想知道為什麼 SurfaceView 和 TextureView 有著那樣的行為,或 Surface 和 EGLSurface 如何互動,那你就來對地方了。

假設讀者熟悉 Android 裝置和應用開發。你不需要關於應用框架的詳細知識,這裡只會提到少量的 API 呼叫,但這裡的資料與其它公開的文件不重疊。目標是提供關於渲染一幀用以輸出中牽涉的重要事件的詳情,以幫助你在設計應用時做出明智的選擇。為了實現這一點,我們從底層開始,描述 UI 類如何工作,而不是它們如何使用。

這一節包含幾頁,覆蓋了從背景資料到 HAL 細節到使用案例的所有東西。這裡從解釋 Android 圖形緩衝區開始,描述合成和顯示機制,然後是提供了資料合成器的更高層機制。我們建議你按下面列出的順序閱讀,而不是直接跳到聽起來很有趣的主題。

底層元件

  • BufferQueue 和 gralloc。BufferQueue 連線生成圖形資料緩衝區的東西(生產者)和接收資料來顯示或進一步處理的東西(消費者)。緩衝區分配通過 gralloc 記憶體分配器執行, gralloc 記憶體分配器通過一個特定於供應商的 HAL 介面實現。

  • SurfaceFlinger,Hardware Composer,和虛擬顯示裝置。SurfaceFlinger 接受來自於多個源的資料緩衝區,組合它們,然後傳送給顯示裝置。Hardware Composer HAL (HWC) 決定通過可用硬體和虛擬顯示裝置以最高效的方式組合緩衝區使合成的輸出在系統內可用(記錄螢幕或通過網路傳送螢幕)。

  • Surface,Canvas,和 SurfaceHolder。Surface 生產常常由 SurfaceFlinger 消費的緩衝區佇列。當在一個 Surface 上渲染時,結果最終被放入緩衝區中,並被傳送給消費者。Canvas APIs 為直接在一個 Surface (OpenGL ES 的低階替代品)繪製提供了一個軟體實現(通過硬體加速支援)。與 View 有關的任何事情都涉及到 SurfaceHolder,通過它的 API 可以獲取或設定 Surface 引數,比如大小和格式等。

  • EGLSurface 和 OpenGL ES。OpenGL ES (GLES) 定義了一個與 EGL 結合使用的圖形渲染 API,一個知道如何通過作業系統建立和訪問視窗的庫(繪製紋理多邊形,使用 GLES 呼叫;在螢幕上放置渲染結果,使用EGL呼叫;)。這頁還描述了 ANativeWindow,Java Surface 類的 C/C++ 等價物,用於在本地層程式碼中建立一個 EGL 視窗。

  • Vulkan。Vulkan 是一個低開銷,跨平臺的高效能 3D 圖形 API。像 OpenGL ES 一樣,Vulkan 提供了在應用中建立高品質實時圖形的工具。Vulkan 的優勢包括降低 CPU 開銷並支援 SPIR-V Binary Intermediate 語言。

高層元件

  • SurfaceView 和 GLSurfaceView。SurfaceView 結合了一個 Surface 和一個 View。SurfaceView 的 View 元件由 SurfaceFlinger 合成 (而不是應用),可以在一個分開的執行緒/程式中渲染,並與應用的 UI 渲染隔離。GLSurfaceView 提供了輔助類來管理 EGL contexts,執行緒間通訊,及與 Activity 生命週期的互動(但使用 GLES 不是必需的)。

  • SurfaceTexture。SurfaceTexture 結合了一個 Surface 和 GLES texture 來建立一個 BufferQueue,你的應用是該 BufferQueue 的消費者。當生產者入隊了一個新 buffer,它通知你的應用,這反過來釋放了之前持有的 buffer,從佇列中獲取新的 buffer,執行 EGL 呼叫使得 buffer 可以作為 GLES 的一個外部 texture 使用。Android 7.0 新增了對安全 texture video playback的支援,使得 GPU 可以後處理受保護的視訊內容。

  • TextureView。TextureView 結合了一個 View 和一個 SurfaceTexture。TextureView 包裝了一個 SurfaceTexture 並負責響應回撥和獲取新 buffers。當繪製時,TextureView 使用最近接收的 buffer 的內容作為它的資料來源,根據 View 的狀態繪製它。View 合成總是由 GLES 執行,意味著更新內容可能導致其它的 View 元素也被重繪。

原文

相關文章