Discuz! Board

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz
楼主: zangcf
打印 上一主题 下一主题

Android graphic path

[复制链接]

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
21#
 楼主| 发表于 2016-4-17 12:32:24 | 只看该作者
BufferQueue state diagram

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?立即注册

x
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
22#
 楼主| 发表于 2016-4-17 12:33:58 | 只看该作者
BufferQueue

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?立即注册

x
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
23#
 楼主| 发表于 2016-4-17 12:34:31 | 只看该作者
GraphicBuffer

frameworks/native/include/ui/GraphicBuffer.h

Represents a buffer, wraps ANativeWindowBuffer
Attributes including width, height, format, usage inherited from ANativeWindowBuffer
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
24#
 楼主| 发表于 2016-4-17 12:35:57 | 只看该作者
SurfaceFlinger处理buffer

這裏先用2張圖來介紹下SurfaceFlinger的整個消息處理機制和工作流程:


本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?立即注册

x
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
25#
 楼主| 发表于 2016-4-17 12:36:40 | 只看该作者
這裏繼續下去對handleMessageRefresh分析,這是SuefaceFlinger的核心處理函數(每个vsync都会调用handleMessageRefresh)
void SurfaceFlinger::handleMessageRefresh() {
    ATRACE_CALL();
    preComposition();
    rebuildLayerStacks();
    setUpHWComposer();
    doDebugFlashRegions();
    doComposition();
    postComposition();
}
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
26#
 楼主| 发表于 2016-4-17 12:37:00 | 只看该作者
handleMessageRefresh
     |—> preComposition
     |—> rebuildLayerStacks
     |—> setUpHWComposer
          |—> HWComposer::createWorkList <== hwc structures are allocated
          |—> Layer::setGeometry()
          |—  set per frame data
          |—  HWComposer::prepare
               |—> hwc prepare
     |—> doComposition
          |---- skip composition on external display if condition meets
          |—> doDisplayComposition
          |    |—> doComposeSurfaces
          |     |—> DisplayDevice::swapBuffers
          |          |—> eglSwapBuffers
          |          |—> FramebufferSurface::advanceFrame
          |—> DisplayDevice::flip(…)     <== just update statistics count
          |--> Call DisplayDevice::compositionComplete(), notify each display
               |--> DisplaySurface::compositionComplete()
                    |--> FramebufferSurface::compositionComplete()
                         |--> HWComposer::fbCompositionComplete()
                              |--> NoOP if HWC >= 1.1
                              |--> used only in framebuffer device case.
          |—> postFrameBuffer
               |—> HWComposer::commit
                    |—> hwc set
                    |—> update retireFenceFd of hwc_display_contents_1
               |—> DisplayDevice:nSwapBuffersCompleted
                    |—> FramebufferSurface:nFrameComitted
               |—> Layer:nLayerDisplayed
               |—   update some statistics
     |—> postComposition
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
27#
 楼主| 发表于 2016-4-17 12:37:28 | 只看该作者
doComposeSurfaces
handleMessageRefresh -> doComposition -> doDisplayComposition -> doComposeSurfaces
    1.Preparation work:
        1) If GLES and hwc compositing, clear frame buffer target first
        2) If GLES only, drawWarmHole first
    2.Render layers to framebuffer
        1) For all layers if using hwc
            (1)do nothing if HWC_OVERLAY layer, display hardware will blend the layer
            (2)render with opengl if HWC_FRAMEBUFFER layer, call layer->draw()
            (3)set the layer’s acquireFence
        2) For all layers if no hwc
            (1)just render with OpenGL, call layer->draw()
            (2)Now all the GLES layers are drawn on frame buffer target, waiting to
            swapBuffers
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
28#
 楼主| 发表于 2016-4-17 12:38:00 | 只看该作者
在DisplayDevice::swapBuffers()->eglSwapBuffers()函数,最终会调用到FramebufferSurface:nFrameAvailable()。
FramebufferSurface:nFrameAvailable()会调用到HwComposer::fbPost()把buffer发给显示设备。
下面会讲这个过程。先来看一下FramebufferSurface和DisplayDevice。
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
29#
 楼主| 发表于 2016-4-17 12:38:52 | 只看该作者
JB版本开始,Android支持外部显示(HDMI和Wifi等)。每个显示设备由DisplayDevice代表,而且关联着FramebufferSurface。SurfaceFlinger会保存所有的DisplayDevice在mDisplays成员变量中。SurfaceFlinger::readyToRun() 函数中会创建所有的DisplayDevice和FramebufferSurface。
HWComposer一般会像如下定义几个显示类型:
HWC_DISPLAY_PRIMARY e.g. built-in LCD screen
HWC_DISPLAY_EXTERNAL e.g. HDMI, WiDi
HWC_DISPLAY_VIRTUAL not a real display对于每一个display type,都会以DisplayDevice对象保存在SurfaceFlinger中。
回复 支持 反对

使用道具 举报

1198

主题

2060

帖子

7058

积分

超级版主

Rank: 8Rank: 8

积分
7058
30#
 楼主| 发表于 2016-4-17 12:41:23 | 只看该作者
How FrameBufferSurface and eglSwapBuffers interact(??)
Back to BufferQueue, usually client application create Surface, it’s provider end of a BufferQueue, SurfaceFlinger acts as consumer of the Surface provided by client. However, SurfaceFlinger also acts as provider as regard to FrameBufferSurface, which is consumed by display.

In SurfaceFlinger::init, the mDisplaySurface in DisplayDevice comes from the same BufferQueue as EGLSurface, look at the code

bq = new BufferQueue(new GraphicBufferAlloc());
fbs = new FramebufferSurface(…, bq);
hw = new DisplayDevice(…, fbs, bq, …);
mDisplays.add(…,hw);
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|Comsenz Inc.

GMT+8, 2025-12-16 09:29 , Processed in 0.018103 second(s), 6 queries , Apc On.

Powered by Discuz! X3.2

© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表