Android6.0 显示系统(六) 图像的输出过程 联系客服

发布时间 : 星期一 文章Android6.0 显示系统(六) 图像的输出过程更新完毕开始阅读a52b43e680c758f5f61fb7360b4c2e3f5627255b

} }

mCurrentOpacity = getOpacityForFormat(mActiveBuffer->format); if (oldOpacity != isOpaque(s)) {

recomputeVisibleRegions = true; }

// FIXME: postedRegion should be dirty & bounds Region dirtyRegion(Rect(s.active.w, s.active.h));

// transform the dirty region to window-manager space outDirtyRegion = (s.transform.transform(dirtyRegion)); }

return outDirtyRegion; }

LatchBuffer函数调用updateTextImage来得到需要的图像。这里参数r是Reject对象,其作用是判断在缓冲区的尺寸是否符合要求。调用updateTextImage函数如果得到的结果是PRESENT_LATER,表示推迟处理,然后调用signalLayerUpdate函数来发送invalidate消息,这次绘制过程就不处理这个Surface的图像了。 如果不需要推迟处理,把mQueuedFrames的值减1.

最后LatchBuffer函数调用mSurfaceFlingerConsumer的getCurrentBuffer来取回当前的图像缓冲区指针,保存在mActiveBuffer中。

2.5 小结

这样经过handleTransaction handlePageFlip两个函数处理,SurfaceFlinger中无论是Layer属性的变化还是图像的变化都处理好了,只等VSync信号到来就可以输出了。

三、rebuildLayerStacks函数

前面介绍,VSync信号到来后,先是调用了rebuildLayerStacks函数 [cpp] view plain copy 在CODE上查看代码片派生到我的代码片 void SurfaceFlinger::rebuildLayerStacks() { // rebuild the visible layer list per screen

if (CC_UNLIKELY(mVisibleRegionsDirty)) { ATRACE_CALL();

mVisibleRegionsDirty = false; invalidateHwcGeometry();

//计算每个显示设备上可见的Layer

const LayerVector& layers(mDrawingState.layersSortedByZ); for (size_t dpy=0 ; dpy

Vector< sp > layersSortedByZ;

const sp& hw(mDisplays[dpy]); const Transform& tr(hw->getTransform()); const Rect bounds(hw->getBounds()); if (hw->isDisplayOn()) {

//计算每个layer的可见区域,确定设备需要重新绘制的区域 SurfaceFlinger::computeVisibleRegions(layers,

hw->getLayerStack(), dirtyRegion, opaqueRegion);

const size_t count = layers.size(); for (size_t i=0 ; i

const sp& layer(layers[i]);

const Layer::State& s(layer->getDrawingState()); if (s.layerStack == hw->getLayerStack()) {

//只需要和显示设备的LayerStack相同的layer Region drawRegion(tr.transform(

layer->visibleNonTransparentRegion)); drawRegion.andSelf(bounds); if (!drawRegion.isEmpty()) {

//如果Layer的显示区域和显示设备的窗口有交集 //把Layer加入列表中

layersSortedByZ.add(layer); } } } }

//设置显示设备的可见Layer列表

hw->setVisibleLayersSortedByZ(layersSortedByZ); hw->undefinedRegion.set(bounds);

hw->undefinedRegion.subtractSelf(tr.transform(opaqueRegion)); hw->dirtyRegion.orSelf(dirtyRegion); } } }

rebuildLayerStacks函数的作用是重建每个显示设备的可见layer对象列表。对于按显示轴(Z轴)排列的Layer对象,排在最前面的当然会优先显示,但是Layer图像可能有透明域,也可能有尺寸没有覆盖整个屏幕,因此下面的layer也有显示的机会。rebuildLayerStacks函数对每个显示设备,先计算和显示设备具有相同layerStack值的Layer对象在该显示设备上的可见区域。然后将可见区域和显示设备的窗口区域有交集的layer组成一个新的列表,最后把这个列表设置到显示设备对象中。

computeVisibleRegions函数首先计算每个Layer在设备上的可见区域visibleRegion。计算方法就是用整个Layer的区域减去上层所有不透明区域aboveOpaqueLayers。而上层所有不透明区域值是一个逐层累计的过程,每层都需要把自己的不透明区域累加到aboveOpaqueLayers中。

而每层的不透明区域的计算方法:如果Layer的alpha的值为255,并且layer的isOpaque函数为true,则本层的不透明区域等于Layer所在区域,否则为0.这样一层层算下来,就很容易得到每层的可见区域大小了。

其次,计算整个显示设备需要更新的区域outDirtyRegion。outDirtyRegion的值也是累计所有层的需要重回的区域得到的。如果Layer中的显示内容发生了变化,则整个可见区域visibleRegion都需要更新,同时还要包括上一次的可见区域,然后在去掉被上层覆盖后的区域得到的就是Layer需要更新的区域。如果Layer显示的内容没有变化,但是考虑到窗口大小的变化或者上层窗口的变化,因此Layer中还是有区域可以需要重绘的地方。这种情况下最简单的算法是用Layer计算出可见区域减去以前的可见区域就可以了。但是在computeVisibleRegions函数还引入了被覆盖区域,通常被覆盖区域和可见区域并不重复,因此函数中计算暴露区域是用可见区域减去被覆盖区域的。

四、setUpHWComposer函数

setUpHWComposer函数的作用是更新HWComposer对象中图层对象列表以及图层属性。 [cpp] view plain copy 在CODE上查看代码片派生到我的代码片 void SurfaceFlinger::setUpHWComposer() {

for (size_t dpy=0 ; dpy

bool dirty = !mDisplays[dpy]->getDirtyRegion(false).isEmpty();

bool empty = mDisplays[dpy]->getVisibleLayersSortedByZ().size() == 0; bool wasEmpty = !mDisplays[dpy]->lastCompositionHadVisibleLayers; bool mustRecompose = dirty && !(empty && wasEmpty); mDisplays[dpy]->beginFrame(mustRecompose);

if (mustRecompose) {

mDisplays[dpy]->lastCompositionHadVisibleLayers = !empty; } }

HWComposer& hwc(getHwComposer());//得到系统HWComposer对象 if (hwc.initCheck() == NO_ERROR) { // build the h/w work list

if (CC_UNLIKELY(mHwWorkListDirty)) { mHwWorkListDirty = false;

for (size_t dpy=0 ; dpy hw(mDisplays[dpy]); const int32_t id = hw->getHwcDisplayId(); if (id >= 0) {

const Vector< sp >& currentLayers( hw->getVisibleLayersSortedByZ());

const size_t cowww.tt951.comunt = currentLayers.size();

//根据Layer数量在HWComposer中创建hwc_layer_list_t列表 if (hwc.createWorkList(id, count) == NO_ERROR) { ...... }

} } }

// set the per-frame data

for (size_t dpy=0 ; dpy hw(mDisplays[dpy]); const int32_t id = hw->getHwcDisplayId(); if (id >= 0) { ......

for (size_t i=0 ; cur!=end && i& layer(currentLayers[i]);

//将Layer的mActiveBuffer设置到HWComposer中 layer->setPerFrameData(hw, *cur); } } }

// If possible, attempt to use the cursor overlay on each display. for (size_t dpy=0 ; dpy hw(mDisplays[dpy]); const int32_t id = hw->getHwcDisplayId(); if (id >= 0) {

const Vector< sp >& currentLayers( hw->getVisibleLayersSortedByZ()); const size_t count = currentLayers.size();

HWComposer::LayerListIterator cur = hwc.begin(id); const HWComposer::LayerListIterator end = hwc.end(id); for (size_t i=0 ; cur!=end && i& layer(currentLayers[i]); if (layer->isPotentialCursor()) { cur->setIsCursorLayerHint(); break; } } } }

status_t err = hwc.prepare();

ALOGE_IF(err, \

for (size_t dpy=0 ; dpy hw(mDisplays[dpy]); hw->prepareFrame(hwc);