當(dāng)窗口的內(nèi)容或者狀態(tài)發(fā)生變化時(shí),Surface Flinger就會在監(jiān)聽線程中監(jiān)聽到相關(guān)的事件,并進(jìn)行處理。首先判斷事件是不是控制臺信號,如果是控制臺信號,就調(diào)用handleConsoleEvents()方法進(jìn)行控制臺信號的處理,獲取渲染的區(qū)域;當(dāng)交易處理完成時(shí),Surface Flinger會在handleTransaction()方法中遍歷Z-order上的Layer,移去已經(jīng)被銷毀的Layer;接下來Surface Flinger會遍歷LayerVector,計(jì)算每個(gè)Layer的可視區(qū)域,如果需要重繪,在handleRepaint()方法中會進(jìn)行Layer組合,當(dāng)組合完成后,會發(fā)送消息compositionComplete()通知硬件Layer組合已經(jīng)完成,然后進(jìn)行Surface的渲染。
下面是Surface Flinger的監(jiān)聽線程處理事件的實(shí)現(xiàn)過程:
代碼:Surface Flinger的監(jiān)聽線程處理事件的實(shí)現(xiàn)過程
bool SurfaceFlinger::threadLoop()
{
waitForEvent(); //超時(shí)時(shí)間為5s
if (UNLIKELY(mConsoleSignals)) {
handleConsoleEvents();
}
if (LIKELY(mTransactionCount==0)) {
const uint32_t mask=eTransactionNeeded | eTraversalNeeded;
uint32_t transactionFlags=getTransactionFlags(mask);
if (LIKELY(transactionFlags)) {
handleTransaction(transactionFlags);
}
}
handlePageFlip();
const DisplayHardware& hw(graphicPlane(0).displayHardware());
if (LIKELY(hw.canDraw() && !isFrozen())) {
handleRepaint();
hw.compositionComplete();
unlockClients(); //客戶端解鎖
postFramebuffer(); //前后端緩沖切換,顯示
} else {
unlockClients();
usleep(16667);
}
return true;
}
關(guān)于Surface,還有一個(gè)十分重要的概念就是layer_state_t,根據(jù)窗口狀態(tài)的變化,Layer處于不同的狀態(tài)。layer_state_t的值包括ePositionChanged、eLayerChanged、eSizeChanged、eAlphaChanged、eMatrixChanged、eTransparentRegionChanged、eVisibilityChanged等。當(dāng)發(fā)生eLayerChanged變化時(shí),說明緩沖需要切換。另外,不論layer_state_t值發(fā)生了何種變化,都需要重新遍歷Layer,進(jìn)行相應(yīng)的重繪。
一般而言,屏幕的渲染需要重繪Surface的所有像素,但是出于提高效率和速率的需要,在現(xiàn)代的設(shè)計(jì)上,會通過分析只重繪發(fā)生變化的區(qū)域。這部分的內(nèi)容主要位于framebuffer.cpp的fb_post()函數(shù)中。在“LayerBuffer”和“LayerDim”模式的Layer中也有采用。
在Surface上層,主要由窗口管理器來控制著窗口的變化。窗口管理器創(chuàng)建Surface的過程如圖-1所示。
流程說明:
當(dāng)Windows Manager要?jiǎng)?chuàng)建Surface時(shí),首先會創(chuàng)建一個(gè)Java Surface對象,Java Surface對象通過Java JNI會獲得一個(gè)SurfaceComposerClient句柄,然后通過SurfaceComposerClient向Surface Flinger請求創(chuàng)建一個(gè)原生層的C++ Surface對象和一個(gè)SurfaceControl對象。在Surface Flinger中,根據(jù)標(biāo)志位(PUSH_BUFFERS、FX_SURFACE_NORMAL、FX_SURFACE_BLUR、FX_SURFACE_DIM)的不同,調(diào)用相應(yīng)的方法創(chuàng)建相應(yīng)類型的Layer。每個(gè)Surface都有一個(gè)唯一的標(biāo)識符SurfaceID。
為了執(zhí)行窗口的操作,需要調(diào)用Surface.openTransaction()方法打開交易(Transaction)。在原生層,SurfaceFlinger會調(diào)用openGlobalTransaction()方法增加交易記數(shù)(mTransactionCount),并將交易ID保存在gActiveConnections向量中。
Windows Manager通過調(diào)用Surface. setPosition()方法可以設(shè)置Surface的位置,當(dāng)SurfaceComposerClient收到設(shè)置Surface位置的請求時(shí),會將layer_state_t狀態(tài)設(shè)為ISurfaceComposer::ePositionChanged,Surface Flinger在收到位置變化的消息后,會在其監(jiān)聽線程中進(jìn)行處理。
Windows Manager通過調(diào)用Surface. setLayer ()方法可以設(shè)置Surface的Layer,當(dāng)SurfaceComposerClient收到設(shè)置Surface的Layer請求時(shí),會將layer_state_t狀態(tài)設(shè)為ISurfaceComposer::eLayerChanged,Surface Flinger在收到Layer變化的消息后,會在其監(jiān)聽線程中進(jìn)行處理。

圖-1 Surface的創(chuàng)建過程
如果希望隱藏已經(jīng)創(chuàng)建的Surface,需要調(diào)用Surface.hide()來調(diào)用原生層的SurfaceComposerClient::hide()方法,SurfaceComposerClient會將其標(biāo)志位和掩碼均設(shè)為ISurfaceComposer::eLayerHidden,并向Surface Flinger發(fā)送ISurfaceComposer:: eVisibility Changed消息。
當(dāng)交易結(jié)束時(shí),Windows Manager需要通過Surface.closeTransaction()方法通知原生層交易結(jié)束。
需要說明的是,交易過程中的Java Surface對原生層C++ Surface的調(diào)用,是通過SurfaceControl對象來進(jìn)行的。