本內(nèi)容基于自己對于代碼的理解以及網(wǎng)上大牛的博客參考寫的,作為回顧時的參考之用。
SurfaceFlinger在經(jīng)過事務(wù)處理以及Page Flip之后,所有的數(shù)據(jù)都準(zhǔn)備好,最后一步就是把內(nèi)容刷新到屏幕上署咽。
1. handleMessageRefresh
void SurfaceFlinger::handleMessageRefresh() {
ATRACE_CALL();
#ifdef ENABLE_FENCE_TRACKING
nsecs_t refreshStartTime = systemTime(SYSTEM_TIME_MONOTONIC);
#else
nsecs_t refreshStartTime = 0;
#endif
static nsecs_t previousExpectedPresent = 0;
nsecs_t expectedPresent = mPrimaryDispSync.computeNextRefresh(0);
static bool previousFrameMissed = false;
bool frameMissed = (expectedPresent == previousExpectedPresent);
if (frameMissed != previousFrameMissed) {
ATRACE_INT("FrameMissed", static_cast<int>(frameMissed));
}
previousFrameMissed = frameMissed;
if (CC_UNLIKELY(mDropMissedFrames && frameMissed)) {
// Latch buffers, but don't send anything to HWC, then signal another
// wakeup for the next vsync
preComposition();
repaintEverything();
} else {
preComposition();
rebuildLayerStacks();
//setUpHWComposer先會遍歷各個設(shè)備DisplayDevice,然后根據(jù)可見layer數(shù)量嗜价,調(diào)用createWorkList創(chuàng)建hwc_layer_list_t列表艇抠,
//然后在每個設(shè)備上遍歷可見layer,將layer的mActiveBuffer設(shè)置到HWComposer中去久锥,最后調(diào)用了HWComposer的prepare函數(shù)家淤。
setUpHWComposer();
doDebugFlashRegions();
//合成所有層的圖像, 經(jīng)過這一步后,就顯示新的內(nèi)容了瑟由。
doComposition();
postComposition(refreshStartTime);
}
previousExpectedPresent = mPrimaryDispSync.computeNextRefresh(0);
}
setUpHWComposer 參考Android6.0 圖像合成過程詳解(一) setUpHWComposer函數(shù)
doComposition請Android6.0 圖像合成過程詳解(二) doComposition函數(shù)
2. preComposition
void SurfaceFlinger::preComposition()
{
mPowerHintThread->requestPowerHint(); //電源管理相關(guān)
bool needExtraInvalidate = false;
const LayerVector& layers(mDrawingState.layersSortedByZ);
const size_t count = layers.size();
for (size_t i=0 ; i<count ; i++) {
if (layers[i]->onPreComposition()) { //調(diào)用Layer的 onPreComposition
needExtraInvalidate = true;
}
}
if (needExtraInvalidate) {
signalLayerUpdate(); //如果需要invalidate的話絮重,觸發(fā)下一個VSYNC
}
}
- Layer.cpp
bool Layer::onPreComposition() {
mRefreshPending = false;
//自動刷新或還有QUEUED的Frame, 以及設(shè)置了side band
return mQueuedFrames > 0 || mSidebandStreamChanged || mAutoRefresh;
}
3. rebuildLayerStacks
void SurfaceFlinger::rebuildLayerStacks() {
// rebuild the visible layer list per screen
if (CC_UNLIKELY(mVisibleRegionsDirty)) { //重建屏幕的Layer Stack
ATRACE_CALL();
mVisibleRegionsDirty = false;
invalidateHwcGeometry();
const LayerVector& layers(mDrawingState.layersSortedByZ);
for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
Region opaqueRegion;
Region dirtyRegion;
Vector< sp<Layer> > layersSortedByZ;
const sp<DisplayDevice>& hw(mDisplays[dpy]);
const Transform& tr(hw->getTransform());
const Rect bounds(hw->getBounds());
if (hw->isDisplayOn()) {
//對該DISPLAY的所有Layer計算可視化區(qū)域
SurfaceFlinger::computeVisibleRegions(layers,
hw->getLayerStack(), dirtyRegion, opaqueRegion);
const size_t count = layers.size();
for (size_t i=0 ; i<count ; i++) {
const sp<Layer>& layer(layers[i]);
const Layer::State& s(layer->getDrawingState());
if (s.layerStack == hw->getLayerStack()) {
Region drawRegion(tr.transform(
layer->visibleNonTransparentRegion));
drawRegion.andSelf(bounds);
if (!drawRegion.isEmpty()) {
layersSortedByZ.add(layer);
}
}
}
}
//設(shè)置 on-screen上的變量, layers, dirty區(qū)域
hw->setVisibleLayersSortedByZ(layersSortedByZ);
hw->undefinedRegion.set(bounds); //整個屏幕size
hw->undefinedRegion.subtractSelf(tr.transform(opaqueRegion)); //這個沒有內(nèi)容的區(qū)域歹苦,一般就是黑色區(qū)域了
hw->dirtyRegion.orSelf(dirtyRegion); //dirty 區(qū)域
}
}
}
4. computeVisibleRegions
計算該Display上的可視區(qū)域
void SurfaceFlinger::computeVisibleRegions(
const LayerVector& currentLayers, uint32_t layerStack,
Region& outDirtyRegion, Region& outOpaqueRegion)
{
ATRACE_CALL();
//
Region aboveOpaqueLayers;
//
Region aboveCoveredLayers;
Region dirty;
outDirtyRegion.clear();
size_t i = currentLayers.size();
while (i--) { //按照Z軸從大到小青伤,也就是從頂至下計算
const sp<Layer>& layer = currentLayers[i];
// start with the whole surface at its current location
const Layer::State& s(layer->getDrawingState());
// only consider the layers on the given layer stack
//只考慮一個DISPLAY device上所有的Layer
if (s.layerStack != layerStack)
continue;
/*
* opaqueRegion: area of a surface that is fully opaque.
*/
Region opaqueRegion; //具體一層Layer的完全不透明區(qū)域
/*
* visibleRegion: area of a surface that is visible on screen
* and not fully transparent. This is essentially the layer's
* footprint minus the opaque regions above it.
* Areas covered by a translucent surface are considered visible.
*/
Region visibleRegion; //具體一層Layer的可見區(qū)域
/*
* coveredRegion: area of a surface that is covered by all
* visible regions above it (which includes the translucent areas).
*/
Region coveredRegion;//具體一層Layer的被覆蓋的區(qū)域
/*
* transparentRegion: area of a surface that is hinted to be completely
* transparent. This is only used to tell when the layer has no visible
* non-transparent regions and can be removed from the layer list. It
* does not affect the visibleRegion of this layer or any layers
* beneath it. The hint may not be correct if apps don't respect the
* SurfaceView restrictions (which, sadly, some don't).
*/
Region transparentRegion; //具體一層的透明區(qū)域
// handle hidden surfaces by setting the visible region to empty
if (CC_LIKELY(layer->isVisible())) {
//是否是半透明狀態(tài)
const bool translucent = !layer->isOpaque(s);
//計算Layer的可視區(qū)域
Rect bounds(s.active.transform.transform(layer->computeBounds()));
// 具體一層Layer的初始化可視區(qū)域
visibleRegion.set(bounds);
if (!visibleRegion.isEmpty()) {//如果該Layer層可視區(qū)域不為空
// Remove the transparent area from the visible region
if (translucent) { //如果是半透明的區(qū)域, 計算透明區(qū)域大小
const Transform tr(s.active.transform);
if (tr.preserveRects()) { //如果矩陣是一些常規(guī)矩陣,比如平移殴瘦、縮放狠角、旋轉(zhuǎn)這些
// transform the transparent region
//獲得透明的區(qū)域
transparentRegion = tr.transform(s.activeTransparentRegion);
} else {
//矩陣變換太復(fù)雜,不用優(yōu)化了. 囧 ...
// transformation too complex, can't do the
// transparent region optimization.
transparentRegion.clear();
}
}
// compute the opaque region
const int32_t layerOrientation = s.active.transform.getOrientation();
if (s.alpha==255 && !translucent &&
((layerOrientation & Transform::ROT_INVALID) == false)) {
// the opaque region is the layer's footprint
opaqueRegion = visibleRegion; //完全不透明的區(qū)域
}
}
}
// Clip the covered region to the visible region
// 當(dāng)前區(qū)域被前面的Layer覆蓋的區(qū)域
coveredRegion = aboveCoveredLayers.intersect(visibleRegion);
// Update aboveCoveredLayers for next (lower) layer
//之前的Layer和自己所占的總的區(qū)域蚪腋,相對于下一個Layer,就是已經(jīng)覆蓋的總區(qū)域
aboveCoveredLayers.orSelf(visibleRegion);
// subtract the opaque region covered by the layers above us
//除了之前的Layer覆蓋的區(qū)域外丰歌,我這層Layer還剩多少可視區(qū)域
visibleRegion.subtractSelf(aboveOpaqueLayers);
// compute this layer's dirty region
if (layer->contentDirty) { //這個值在 Layer的doTransaction中可能為True, 當(dāng)新舊的sequence不一致時
// we need to invalidate the whole region
dirty = visibleRegion; // invalidate整個區(qū)域
// as well, as the old visible region
dirty.orSelf(layer->visibleRegion); //整個Dirty的區(qū)域要加上上一個可視區(qū)域,這個在之前有講屉凯,自己想一下為什么
layer->contentDirty = false;
} else {
/* compute the exposed region:
* the exposed region consists of two components:
* 1) what's VISIBLE now and was COVERED before
* 2) what's EXPOSED now less what was EXPOSED before
*
* note that (1) is conservative, we start with the whole
* visible region but only keep what used to be covered by
* something -- which mean it may have been exposed.
*
* (2) handles areas that were not covered by anything but got
* exposed because of a resize.
*/
const Region newExposed = visibleRegion - coveredRegion;
const Region oldVisibleRegion = layer->visibleRegion;
const Region oldCoveredRegion = layer->coveredRegion;
const Region oldExposed = oldVisibleRegion - oldCoveredRegion;
//只計算局部dirty區(qū)域
dirty = (visibleRegion&oldCoveredRegion) | (newExposed-oldExposed);
}
//Layer的區(qū)域減掉上層Layer的覆蓋的區(qū)域
dirty.subtractSelf(aboveOpaqueLayers);
// accumulate to the screen dirty region
//outDirtyRegion是整個屏幕的臟區(qū)域立帖,這個肯定是累加的
outDirtyRegion.orSelf(dirty);
// Update aboveOpaqueLayers for next (lower) layer
aboveOpaqueLayers.orSelf(opaqueRegion);
// Store the visible region in screen space
// 保存到這些區(qū)域到 Layer中,以便下一次合成使用
layer->setVisibleRegion(visibleRegion);
layer->setCoveredRegion(coveredRegion);
layer->setVisibleNonTransparentRegion(
visibleRegion.subtract(transparentRegion));
}
//完全不透明的區(qū)域
outOpaqueRegion = aboveOpaqueLayers;
}