Android surfaceflinger(3)-DisplayDevice封装
来源:互联网 发布:java软件是什么 编辑:程序博客网 时间:2024/06/01 10:38
上一篇文章介绍了HWComposer的创建及初始化,本文将根据上述创建的HWComposer封装出DisplayDevice对象进行分析。
1、引言
在此之前已经分析了HWComposer,接下来继续分析SurfaceFlinger::init的后续操作
void SurfaceFlinger::init() { //详见http://blog.csdn.net/marshal_zsx/article/details/78054285 mHwc = new HWComposer(this,*static_cast<HWComposer::EventHandler *>(this)); // initialize our non-virtual displays for (size_t i=0 ; i<DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES ; i++) { DisplayDevice::DisplayType type((DisplayDevice::DisplayType)i); if (mHwc->isConnected(i) || type==DisplayDevice::DISPLAY_PRIMARY) { // All non-virtual displays are currently considered secure. bool isSecure = true; createBuiltinDisplayLocked(type);//见第2节 wp<IBinder> token = mBuiltinDisplays[i]; sp<IGraphicBufferProducer> producer; sp<IGraphicBufferConsumer> consumer; BufferQueue::createBufferQueue(&producer, &consumer, new GraphicBufferAlloc());//见第3节 sp<FramebufferSurface> fbs = new FramebufferSurface(*mHwc, i,consumer);//见第4节 int32_t hwcId = allocateHwcDisplayId(type); sp<DisplayDevice> hw = new DisplayDevice(this, type, hwcId, mHwc->getFormat(hwcId), isSecure, token, fbs, producer,mRenderEngine->getEGLConfig());//见第5节 mDisplays.add(token, hw); } } // start boot animation startBootAnim();//见下一篇文章}
2、token创建
Android6.0支持多屏显示,为了区分不同的屏幕,需要创建不同的token(即使每一块屏幕唯一对应一个IBinder);并用mBuiltinDisplays数组进行管理,具体代码如下:
void SurfaceFlinger::createBuiltinDisplayLocked(DisplayDevice::DisplayType type) { ALOGW_IF(mBuiltinDisplays[type], "Overwriting display token for display type %d", type); mBuiltinDisplays[type] = new BBinder(); DisplayDeviceState info(type); // All non-virtual displays are currently considered secure. info.isSecure = true; mCurrentState.displays.add(mBuiltinDisplays[type], info);}
3、建立bufferqueue生产者消费者
void BufferQueue::createBufferQueue(sp<IGraphicBufferProducer>* outProducer, sp<IGraphicBufferConsumer>* outConsumer, const sp<IGraphicBufferAlloc>& allocator) { LOG_ALWAYS_FATAL_IF(outProducer == NULL, "BufferQueue: outProducer must not be NULL"); LOG_ALWAYS_FATAL_IF(outConsumer == NULL, "BufferQueue: outConsumer must not be NULL"); sp<BufferQueueCore> core(new BufferQueueCore(allocator)); LOG_ALWAYS_FATAL_IF(core == NULL, "BufferQueue: failed to create BufferQueueCore"); //创建生产者 sp<IGraphicBufferProducer> producer(new BufferQueueProducer(core)); LOG_ALWAYS_FATAL_IF(producer == NULL, "BufferQueue: failed to create BufferQueueProducer"); //创建消费者 sp<IGraphicBufferConsumer> consumer(new BufferQueueConsumer(core)); LOG_ALWAYS_FATAL_IF(consumer == NULL, "BufferQueue: failed to create BufferQueueConsumer"); *outProducer = producer; *outConsumer = consumer;}
4、创建FramebufferSurface
FramebufferSurface::FramebufferSurface(HWComposer& hwc, int disp, const sp<IGraphicBufferConsumer>& consumer) : ConsumerBase(consumer), mDisplayType(disp), mCurrentBufferSlot(-1), mCurrentBuffer(0), mHwc(hwc){ mName = "FramebufferSurface"; mConsumer->setConsumerName(mName); int usage = GRALLOC_USAGE_HW_FB | GRALLOC_USAGE_HW_RENDER | GRALLOC_USAGE_HW_COMPOSER; if(disp != 0) { usage |= GRALLOC_USAGE_HW_FBX; } //mConsumer是父类ConsumerBase的成员变量,故以下是调用IGraphicBufferConsumer对应的方法 mConsumer->setConsumerUsageBits(usage); mConsumer->setDefaultBufferFormat(mHwc.getFormat(disp));//设置buffer格式 mConsumer->setDefaultBufferSize(mHwc.getWidth(disp), mHwc.getHeight(disp));//设置buffer大小 mConsumer->setDefaultMaxBufferCount(NUM_FRAMEBUFFER_SURFACE_BUFFERS);}
5、创建DisplayDevice
DisplayDevice::DisplayDevice( const sp<SurfaceFlinger>& flinger, DisplayType type, int32_t hwcId, int format, bool isSecure, const wp<IBinder>& displayToken, const sp<DisplaySurface>& displaySurface, const sp<IGraphicBufferProducer>& producer, EGLConfig config) : lastCompositionHadVisibleLayers(false), mFlinger(flinger), mType(type), mHwcDisplayId(hwcId), mDisplayToken(displayToken), mDisplaySurface(displaySurface), mDisplay(EGL_NO_DISPLAY), mSurface(EGL_NO_SURFACE), mDisplayWidth(), mDisplayHeight(), mFormat(), mFlags(), mPageFlipCount(), mIsSecure(isSecure), mSecureLayerVisible(false), mLayerStack(NO_LAYER_STACK), mOrientation(), mPowerMode(HWC_POWER_MODE_OFF), mActiveConfig(0){ mNativeWindow = new Surface(producer, false); ANativeWindow* const window = mNativeWindow.get(); /* * Create our display's surface */ EGLSurface surface; EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); if (config == EGL_NO_CONFIG) { config = RenderEngine::chooseEglConfig(display, format); } surface = eglCreateWindowSurface(display, config, window, NULL); eglQuerySurface(display, surface, EGL_WIDTH, &mDisplayWidth); eglQuerySurface(display, surface, EGL_HEIGHT, &mDisplayHeight); mConfig = config; mDisplay = display; mSurface = surface; mFormat = format; mPageFlipCount = 0; mViewport.makeInvalid(); mFrame.makeInvalid(); // virtual displays are always considered enabled mPowerMode = (mType >= DisplayDevice::DISPLAY_VIRTUAL) ? HWC_POWER_MODE_NORMAL : HWC_POWER_MODE_OFF; // Name the display. The name will be replaced shortly if the display // was created with createDisplay(). switch (mType) { case DISPLAY_PRIMARY: mDisplayName = "Built-in Screen"; break; case DISPLAY_EXTERNAL: mDisplayName = "HDMI Screen"; break; default: mDisplayName = "Virtual Screen"; // e.g. Overlay #n break; } //初始化显示方向转换。 setProjection(DisplayState::eOrientationDefault, mViewport, mFrame);}
创建DisplayDevice对象完成后,调用mDisplays.add(token, hw)加入到mDisplays键值容器中,这就形成了每个屏幕都有唯一指定的token。
6、总结与展望
当surfaceflinger初始化完成后,就会去启动开机动画;后面将分析开机动画是如何与surfaceflinger进行交互的。未完待续……
阅读全文
0 0
- Android surfaceflinger(3)-DisplayDevice封装
- Android N之SurfaceFlinger流程解析(3)
- android surfaceflinger
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop .
- android surfaceflinger研究----SurfaceFlinger loop .
- android surfaceflinger研究----SurfaceFlinger loop
- android surfaceflinger研究----SurfaceFlinger loop
- (转)android surfaceflinger研究----显示系统
- Android 7.1 GUI系统-surfaceflinger(四)
- 【Android】Android SurfaceFlinger之SurfaceFlinger启动过程
- Android SurfaceFlinger之SurfaceFlinger启动过程
- leetcode
- HDU2089[不要62]--数位DP
- 关于TLS经验小结(上)
- JDBC 增删改查操作示例
- spring + redis 集群
- Android surfaceflinger(3)-DisplayDevice封装
- [luogu1108&2687][USACO4.3]Buy Low, Buy Lower(STL乱搞+高精度)
- 原型与继承
- 角色设计流程图
- c++实现一元稀疏多项式加减
- maven常见问题
- GitLab服务器经常502(阿里云搭建)
- git 常用命令
- Codeforces Round #448 (Div. 2) B,C,