Android图形系统(八)-app与SurfaceFlinger共享UI元数据过程

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Android图形系统(八)-app与SurfaceFlinger共享UI元数据过程相关的知识,希望对你有一定的参考价值。

参考技术A android应用程序与SurfaceFlinger服务是运行在不同的进程中的,因此,它们采用Binder进程间通信机制来进行通信。

但是我们知道一个Android应用程序可能会有很多个窗口,而每一个窗口都有自己的UI元数据,因此,Android应用程序需要传递给SurfaceFlinger服务的UI元数据是相当可观的。在这种情况下,通过Binder来在Android应用程序与SurfaceFlinger服务之间传递UI元数据是不合适的,因此这里选择了Android系统的匿名共享内存的方案。在每一个Android应用程序与SurfaceFlinger服务之间的连接上加上一块用来传递UI元数据的匿名共享内存。而这块区域被包装为SharedClient。

在每一个SharedClient里面,有至多31个SharedBufferStack,那什么又是SharedBufferStack?

SharedBufferStack就是共享缓冲区堆栈,每一个SharedBufferStack与一个Surface一一对应,每一个Surface又对应一个窗口,那就是一个应用程序内部最多可创建31个窗口。SharedBufferStack 内部包含N个缓冲buffer, 开篇介绍的双缓冲(front buffer , back buffer) ,三缓冲(front buffer , back buffer, tripple buffer),有了它SurfaceFlinger服务就可以使用N个缓冲区技术来绘制UI了。

下面我们再来了解下SharedBufferStack的结构:

SharedBufferStack中分为空闲buffer和已使用的buffer。其中SharedBufferStack中的每一个已经使用了的缓冲区都对应有一个GraphicBuffer,用来描述真正的UI数据。

客户端一次申请GraphicBuffer且将UI元数据写入GraphicBuffer的流程:

当Android应用程序需要更新一个Surface的时候,它就会找到与它所对应的SharedBufferStack,并且从它的空闲缓冲区列表的尾部取出一个空闲的Buffer。我们假设这个取出来的空闲Buffer的编号为index。接下来Android应用程序就请求SurfaceFlinger服务为这个编号为index的Buffer分配一个图形缓冲区GraphicBuffer。SurfaceFlinger服务分配好图形缓冲区GraphicBuffer之后,会将它的编号设置为index,然后再将这个图形缓冲区GraphicBuffer返回给Android应用程序访问。Android应用程序得到了SurfaceFlinger服务返回的图形缓冲区GraphicBuffer之后,就在里面写入UI数据。写完之后,就将与它所对应的缓冲区,即编号为index的Buffer,插入到对应的SharedBufferStack的已经使用了的缓冲区列表的头部去。这一步完成了之后,Android应用程序就通知SurfaceFlinger服务去绘制那些保存在已经使用了的缓冲区所描述的图形缓冲区GraphicBuffer了。

那么我们也知道一个绘图表面,在SurfaceFlinger服务和Android应用程序中分别对应Layer对象和Surface对象,其中这两个对象在内部分别使用一个SharedBufferServer对象和一个SharedBufferClient对象来操作这个绘图表面的UI元数据缓冲堆栈。操作过程如下:

在Android应用程序这一侧,当它需要渲染一个Surface时,它就会首先找到对应的SharedBufferClient对象,然后再调用它的成员函数dequeue来请求分配一个UI元数据缓冲区。有了这个UI元数据缓冲区之后,Android应用程序再调用这个SharedBufferClient对象的成员函数setDirtyRegion、setCrop和setTransform来设置对应的Surface的裁剪区域、纹理坐标以及旋转方向。此外,Android应用程序还会请求SurfaceFlinger服务为这个Surface分配一个图形缓冲区,以便可以往这个图形缓冲区写入实际的UI数据。最后,Android应用程序就可以调用这个SharedBufferClient对象的成员函数queue把前面已经准备好了的UI元数据缓冲区加入到它所描述的一个UI元数据缓冲区堆栈的待渲染队列中,以便SurfaceFlinger服务可以在合适的时候对它进行渲染。当SurfaceFlinger服务需要渲染一个Surface的时候,它就会找到对应的一个SharedBufferServer对象,然后调用它的成员函数getQueueCount来检查它所描述的一个UI元数据缓冲区堆栈的待渲染队列的大小。如果这个大小大于0,那么SurfaceFlinger服务就会继续调用它的成员函数retireAndLock来取出队列中的第一个UI元数据缓冲区,以及调用它的成员函数getDirtyRegion、getCrop和getTransform来获得要渲染的Surface的裁剪区域、纹理坐标和旋转方向。最后,SurfaceFlinger服务就可以结合这些信息来将保存这个Surface的图形缓冲区中的UI数据渲染在显示屏中。

另外想深入了解BufferQueue的生产者消费者模型,详细可以阅读下如下这篇博文,感觉还不错: https://blog.csdn.net/stn_lcd/article/details/73801313

参考:
https://blog.csdn.net/Luoshengyang/article/details/7867340

Android特性与系统架构

一.Android特性
应用程序框架支持组件的重用与替换
Dalvik 虚拟机专为移动设备优化
集成的浏览器基于开源的WebKit 引擎
优化的图形库包括定制的2D 图形库,基于OpenGL ES 1.0的3D 图形库
SQLite 用作结构化的数据存储
多媒体支持包括常见的音频、视频和静态图像格式(如MPEG4, H.264, MP3, AAC, AMR, JPG, PNG , GIF)
GSM 电话技术(依赖于硬件)
蓝牙Bluetooth, EDGE, 3G, 和WiFi(依赖于硬件)
照相机,GPS,指南针,和加速度计(accelerometer)(依赖于硬件)
丰富的开发环境包括设备模拟器,调试工具,内存及性能分析图表,和Eclipse 集成开发环境插件
二.Android的系统架构

                               技术分享



1.      应用程序

                               技术分享


    同Android系统一起发布的核心应用程序,如email 客户端,SMS 短消息程序,日历,地图,浏览器,联系人管理程序等。(JAVA 编写)

2.      应用程序框架

 

                               技术分享

     开发者可以用它开发应用,其中包括:

丰富而又可扩展的视图(Views):可以用来构建应用程序, 它包括列表(lists),网格(grids), 文本框(text boxes),按钮( buttons), 甚至可嵌入的web 浏览器。

内容提供器(Content Providers):使得应用程序可以访问另一个应用程序的数据(如联系人数据库), 或者共享它们自己的数据

资源管理器(Resource Manager):提供非代码资源的访问,如本地字符串,图形,布局文件( layoutfiles )

通知管理器(Notification Manager): 使得应用程序可以在状态栏中显示自定义的提示信息

活动管理器( Activity Manager):用来管理应用程序生命周期并提供常用的导航回退功能

 

  1.      类库

 

                                             技术分享

         一些C/C++核心库,方便开发者进行应用的开发。

系统C 库(libc):专门为基于embedded linux的设备定制的

媒体库:支持多种常用的音频、视频格式回放和录制,同时支持静态图像文件。编码格式包括MPEG4, H.264, MP3, AAC, AMR, JPG, PNG

SurfaceManager :对显示子系统的管理,并且为多个应用程序提供了2D和3D 图层的无缝融合

webkit/LibWebCore :Web 浏览引擎,支持Android 浏览器和一个可嵌入的web 视图

SGL:底层的2D图形引擎

3D libraries : 基于OpenGL ES 1.0 APIs 实现的3D引擎

FreeType :位图(bitmap)和矢量(vector)字体显示

SQLite :轻型关系型数据库引擎

 

4.      Android 运行时环境

                                                                          技术分享



Android 核心库:提供了JAVA库的大多数功能
Dalvik 虚拟机:依赖于linux 内核的一些功能,比如线程机制和底层内存管理机制。同时虚拟机是基于寄存器的,Dalvik 采用简练、高效的byte code 格式运行,它能够在低资耗和没有应用相互干扰的情况下并行执行多个应用,每一个Android 应用程序都在它自己的进程中运行,都拥有一个独立的Dalvik 虚拟机实例。Dalvik 虚拟机中可执行文件为.dex文件,该格式文件针对小内存使用做了优化。所有的类都经由JAVA 编译器编译,然后通过SDK中的"dx" 工具转化成.dex 格式由虚拟机执行。
5.      Linux 内核

                              技术分享


          Linux 内核作为硬件和软件栈之间的抽象层。Android 的核心系统服务: 安全机制、内存管理、进程管理、网络、硬件驱动


以上是关于Android图形系统(八)-app与SurfaceFlinger共享UI元数据过程的主要内容,如果未能解决你的问题,请参考以下文章

从整体上看Android图像显示系统

Android图形系统(六)-app与SurfaceFlinger服务连接过程

Android性能优化第(八)篇---App启动速度优化之耗时检测处理

Android 图形系统详解

文献列表

Android入门