SurfaceFlinger 接受缓冲区、合成缓冲区并将缓冲区发送到显示屏。WindowManager 向 SurfaceFlinger 提供缓冲区和窗口元数据,SurfaceFlinger 使用这些数据将表面合成到显示屏。
SurfaceFlinger
SurfaceFlinger 可以通过两种方式接受缓冲区:通过 BufferQueue 和 SurfaceControl,或通过 ASurfaceControl。
SurfaceFlinger 接受缓冲区的一种方式是通过 BufferQueue 和 SurfaceControl。当应用进入前台时,它会从 WindowManager 请求缓冲区。然后,WindowManager 从 SurfaceFlinger 请求一个图层。图层是 surface(包含 BufferQueue)和 SurfaceControl(包含图层元数据,例如显示帧)的组合。SurfaceFlinger 创建图层并将其发送到 WindowManager。然后,WindowManager 将 surface 发送到应用,但保留 SurfaceControl 以操纵应用在屏幕上的外观。
Android 10 添加了 ASurfaceControl,这是 SurfaceFlinger 可以接受缓冲区的另一种方式。ASurfaceControl 将 surface 和 SurfaceControl 组合到一个事务包中,该事务包被发送到 SurfaceFlinger。ASurfaceControl 与一个图层相关联,应用通过 ASurfaceTransactions 更新该图层。然后,应用通过回调获取有关 ASurfaceTransactions 的信息,回调传递包含信息的 ASurfaceTransactionStats,例如锁定时间、获取时间等等。
下表包含有关 ASurfaceControl 及其相关组件的更多详细信息。
组件 | 描述 |
---|---|
ASurfaceControl | 封装 SurfaceControl 并使应用能够创建与显示屏上的图层相对应的 SurfaceControl。 可以创建为 ANativeWindow 的子项,也可以创建为另一个 ASurfaceControl 的子项。 |
ASurfaceTransaction | 封装 Transaction 以使客户端能够编辑图层的描述性属性(例如几何形状),并将更新后的缓冲区发送到 SurfaceFlinger。 |
ASurfaceTransactionStats | 通过预注册的回调向应用发送有关已呈现事务的信息,例如锁定时间、获取时间和之前的释放栅栏。 |
虽然应用可以随时提交缓冲区,但 SurfaceFlinger 仅在显示屏刷新之间唤醒以接受缓冲区,刷新频率可能因设备而异。这可以最大限度地减少内存使用,并避免屏幕上出现可见的撕裂现象,这种现象可能在刷新期间更新显示屏时发生。
当显示屏处于刷新之间时,显示屏会向 SurfaceFlinger 发送 VSYNC 信号。VSYNC 信号表示显示屏可以在没有撕裂的情况下刷新。当 SurfaceFlinger 接收到 VSYNC 信号时,SurfaceFlinger 会遍历其图层列表以查找新的缓冲区。如果 SurfaceFlinger 找到新的缓冲区,SurfaceFlinger 会获取该缓冲区;否则,SurfaceFlinger 继续使用之前获取的缓冲区。SurfaceFlinger 必须始终显示某些内容,因此它会保留一个缓冲区。如果从未在图层上提交过缓冲区,则会忽略该图层。
在 SurfaceFlinger 收集完所有可见图层的缓冲区后,它会询问硬件合成器 (HWC) 应如何执行合成。如果 HWC 将图层合成类型标记为客户端合成,则 SurfaceFlinger 会合成这些图层。然后,SurfaceFlinger 将输出缓冲区传递给 HWC。
WindowManager
WindowManager 控制 window 对象,window 对象是 view 对象的容器。Window 对象始终由 surface 对象支持。WindowManager 负责管理窗口的生命周期、输入和焦点事件、屏幕方向、过渡、动画、位置、变换、Z 顺序以及许多其他方面。WindowManager 将所有窗口元数据发送到 SurfaceFlinger,以便 SurfaceFlinger 可以使用这些数据在显示屏上合成 surface。
预旋转
许多硬件叠加层不支持旋转(即使支持,也会消耗处理能力);解决方案是在缓冲区到达 SurfaceFlinger 之前对其进行变换。Android 在 ANativeWindow
中支持查询提示 (NATIVE_WINDOW_TRANSFORM_HINT
),以表示 SurfaceFlinger 最有可能应用于缓冲区的变换。GL 驱动程序可以使用此提示在缓冲区到达 SurfaceFlinger 之前对其进行预变换,以便缓冲区到达时已正确变换。
例如,当收到旋转 90 度的提示时,生成矩阵并将其应用于缓冲区,以防止缓冲区超出页面末尾。为了节省电量,请执行此预旋转。有关详细信息,请参阅 system/core/include/system/window.h
中定义的 ANativeWindow
接口。