软件绘制 硬件加速绘制 【DisplayList RenderNode】

news2024/12/23 14:44:49

Android4.0以后,系统默认开启硬件加速来渲染视图
异同点
共同点
两者都是从SF获取一块内存,绘制都是在APP端,绘制好后都是通知SF去进行合成图层
真正的区别
真正的区别:绘制是通过CPU还是GPU完成的视图绘制。
对应区别在代码中的体现是ViewRootImpl中:

private void draw(boolean fullRedrawNeeded) {
...
if (!dirty.isEmpty() || mIsAnimating || accessibilityFocusDirty) {
    //是否使用硬件加速 在前面setView的时候已经创建好了mAttachInfo.mHardwareRenderer
    if (mAttachInfo.mHardwareRenderer != null && mAttachInfo.mHardwareRenderer.isEnabled()) {
            dirty.setEmpty();
            mBlockResizeBuffer = false;
              //硬件加速绘制  使用HardwareRenderer进行绘制
            mAttachInfo.mHardwareRenderer.draw(mView, mAttachInfo, this);
     } else {
             //软件绘制
            if (!drawSoftware(surface, mAttachInfo, xOffset, yOffset, scalingRequired, dirty)) {
                return;
            }

如果开启了硬件加速则调用mHardwareRenderer.draw绘制;

没有开启则只是调用drawSoftware方法

软件绘制:

drawSoftware: 利用Surface的lockCanvas向SF申请一块匿名共享内存,并获取一个普通的SkiaCanvas之后方便使用Skia库图形绘制,onDraw中对这个Canvas的操作就是对那块匿名共享内存的操作,使用之前的Skia图形库进行渲染接着SF之后去这块内存中拿到图层数据进行合成。

大致线路:

  • 获取匿名共享内存
    canvas = mSurface.lockCanvas(dirty);
  • 对共享内存进行操作,之后通过Ski
    mView.draw(canvas);
  • 通知SurfaceFlinger进行合成图层Layer
    surface.unlockCanvasAndPost(canvas);

软件绘制的Skia图形库渲染是CPU工作完成;8.0之后,Skia间接调用OpenGl,OpenGL间接操作GPU可降低CPU压力

硬件加速绘制:

  • 构建阶段:确定需要绘制的脏区域及如何绘制(绘制指令如何保存)
  • 绘制阶段,单独渲染线程,取出保存的绘制指令转换为OpenGl指令
  • 通过swapBuffer让GPU绘制
  • 向SF发起合成的操作

构建阶段

大致流程:

  • 递归遍历所有视图获取视图绘制操作,每个绘制的操作都是一个DrawOP

比如drawText,DrawLine会被抽象成drawTextOp,DrawLineOp

  • 而View是一个RenderNode节点存储着当前View和子View的DrawOp,递归所有视图获取所有RenderNode的DrawOp,也叫DisplayList;通知RenderThread渲染

具体流程:

  • 在View的构造方法中会创建RenderNode,硬件加速中用来标识这个View
  • RenderNode进行调用canvas的操作时,会申请一个DisplayListCanvas并把具体的操作缓存到里面,也叫这个View的DrawOp树

如果是ViewGroup则递归调用子View来缓存子View的DrawOp树

  • 接着将View缓存中的DrawOp树同步到RenderNode中,递归所有View执行这个操作,那么就可以知道当前根视图树的所有绘制操作也叫DisplayList。
  • 向RenderThread发送一个执行DrawFrameTask的任务进行渲染(RenderThread是一个单例线程)

绘制阶段:

构建完所有的DrawOp后,交给RenderThrea去处理,区别来了:软件绘制是在主线程,硬件加速是在单独的RenderThread中去完成绘制的
摘一个网上的图:

大致流程

DrawOp树合并

  • 绘制特殊Layer:调用GPU进行绘制,GPU向共享内存写内容
    将填充好的rawBuffer提交给SF合成

获取共享内存

  • DrawOp树最后是缓存在了DisplayList中,不像软件绘制是直接将绘制数据同步到匿名共享内存中。
    获取时机
  • 在performTraversals中提前获取共享内存,不像软件绘制那样等到performDraw再lockCanvas获取。
    多个Surface的情况渲染线程先渲染哪个呢?
  • 通过EGL Api获取一个EGLSurface封装原Surface的绘图数据,并设定为当前渲染窗口绑定到RenderThread中,RenderThread就会渲染绑定的Surface。

后续操作

进行DrawOp的合并

  • 这里感觉像是和离屏渲染那个差不多,合并绘制纹理阴影之类的,因为画家算法是从远到近绘制的,绘制完之后如果之后的图层会影响之前的图层是无法进行操作的,所以礼品渲染将这块需要稍后可能会处理的图层单独放到一个离屏缓冲区中之后再添加。

  • 特殊Layer的绘制 ;

  • Layer就是Surface,比如SurfaceView和TextureView

  • 使用OPENGL绘制后通知SurfaceFliger进行Layer图层的合成操作

  • OpenGl利用GPU操作渲染数据,并将数据同步给SF
    在这里插入图片描述

绘制流程

  • 参考文章

深度好文:理解Android硬件加速原理

理解Android硬件加速原理的小白文

android硬件加速

GPU渲染简介

GPU和CPU的渲染和渲染管道出图原理
文章转载于:北洋的文章

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1139406.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

SpringBoot整合Gateway 的Demo(附源码)

源码&#xff0c;可直接下载 Gateway模块 Gateway 的父pom.xml <?xml version"1.0" encoding"UTF-8"?> <project xmlns"http://maven.apache.org/POM/4.0.0" xmlns:xsi"http://www.w3.org/2001/XMLSchema-instance"xsi:sc…

学习嵌入式可以胜任哪一些行业?

今日话题&#xff0c;学习嵌入式可以胜任哪一些行业&#xff1f;学习嵌入式开发可以胜任许多行业&#xff0c;因为嵌入式技术在各个领域都有广泛的应用。嵌入式系统用于医疗设备、患者监测系统、药物分发设备等。智能手机、智能家居设备、游戏机等消费电子产品都包含嵌入式系统…

RocketMQ mmap原理和使用

传统文件IO 普通的IO操作的一个弊端&#xff0c;必然涉及到两次数据拷贝操作&#xff0c;对磁盘读写性能是有影响的。 那么如果我们要将一些数据写入到磁盘文件里去呢&#xff1f; 那这个就是一样的过程了&#xff0c;必须先把数据写入到用户进程空间里去&#xff0c;然后从这里…

网络时代下的声音之路:如何在中央新闻媒体发布网评稿

在当今数字时代&#xff0c;信息传播已经变得更加便捷和广泛。各大中央新闻媒体平台为民众提供了一个发布观点、表达意见的平台。在这个背景下&#xff0c;撰写并发布网评稿成为了一种重要的社会参与方式。根据媒介易软文发稿平台的总结&#xff0c;下面是探讨如何在各大中央新…

基于单片机的IC卡门禁系统设计

收藏和点赞&#xff0c;您的关注是我创作的动力 文章目录 概要 一、主要研究内容及总体设计方案1.1 系统方案设计1.2系统工作原理 二、硬件设计2.1 主控电路 三、软件设计3.2主程序设计实物附录1 原理图附录2 源程序清单 四、 结论五、 文章目录 概要 本论文重点通过对射频技术…

电脑上怎么录制视频教程带画笔工具?

无论你是创建教程、还是演示文稿&#xff0c;可能都希望使用带有画笔工具的录屏软件来帮助你创建吸引观众注意力的重要内容。幸运的是&#xff0c;有一些很棒的录屏软件可供你选择&#xff0c;本文就为你推荐一款带有画笔工具的最佳录屏软件&#xff0c;继续阅读查看吧&#xf…

明基、书客、小米的护眼台灯谁的更值得入手?三款台灯真实测评!

目前中国青少年近视占比是越来越高了&#xff0c;尤其是初中生更是重灾区。而现在看来小学阶段近视风险也有上升的趋势。所以&#xff0c;孩子在正式步入小学时&#xff0c;学习桌上不可或缺的就要放上一台好的且不错的护眼台灯。不过如今市面上的护眼台灯种类多到让人眼花缭乱…

Maven第三章:IDEA集成与常见问题

Maven第三章:IDEA集成与常见问题 前言 本章内容重点:了解如何将Maven集成到IDE(如IntelliJ IDEA或Eclipse)中,以及使用过程中遇到的常见的问题、如何解决,如何避免等,可以大大提高开发效率。 IEAD导入Maven项目 File ->Open 选择上一章创建的Maven项目 my-app查看po…

echarts多y轴优化方案

优化方向&#xff1a;点击图例&#xff0c;对y轴进行屏蔽&#xff0c;自动计算y轴位置 效果如下&#xff1a; 对应实现思路&#xff1a;通过监听图例点击事件&#xff0c;渲染y轴显示隐藏和y轴对应位置。 <script setup lang"ts"> import { onMounted, ref,…

简述JVM

文章目录 JVM简介JVM运行时数据区堆(线程共享)方法区/元空间/元数据区(线程共享)栈程序计数器 JVM类加载类加载过程双亲委派模型 垃圾回收机制(GC)判断对象是否为垃圾判断是否被引用指向 如何清理垃圾, 释放对象? JVM简介 JVM 是 Java Virtual Machine 的简称, 意为Java虚拟机…

代码随想录打卡第五十二天|123.买卖股票的最佳时机III ● 188.买卖股票的最佳时机IV

123.买卖股票的最佳时机III 题目&#xff1a; 给定一个数组&#xff0c;它的第 i 个元素是一支给定的股票在第 i 天的价格。设计一个算法来计算你所能获取的最大利润。你最多可以完成两笔交易。注意&#xff1a;你不能同时参与多笔交易&#xff08;你必须在再次购买前出售掉之…

iPhone无法连接电脑?怎么回事?解决方法来了!

苹果用户将手机和电脑连接后&#xff0c;可以轻松实现两者之间的数据传输。但是&#xff0c;在连接设备的过程中可能会出现没有任何反应的情况。这是怎么回事&#xff1f;本文将为大家介绍解决iPhone无法连接电脑的常见方法。如果您的iphone无法连接电脑&#xff0c;请尝试以下…

导入Embassy库进行爬虫

Embassy是一个基于Lua的轻量级爬虫框架&#xff0c;可以方便地进行网页抓取和数据提取。它提供了简单易用的接口和丰富的功能&#xff0c;可以帮助开发者快速构建爬虫应用。 要使用Embassy进行爬虫&#xff0c;首先需要安装Embassy库。可以通过Lua的包管理工具luarocks来安装E…

如何用MFI确定波浪理论第一浪,anzo capital实操演示

通过上文投资者学会了如何确定波浪理论第一浪&#xff0c;但在后台有投资者咨询 &#xff1a;如何用MFI确定波浪理论第一浪&#xff0c;anzo capital昂首资本秉承着有求必应的态度&#xff0c;今天实操进行演示。 在图中&#xff0c;发散用蓝色标注&#xff0c;收敛用绿色。价…

深入理解Linux网络笔记(四):内核是如何发送网络包的

本文为《深入理解Linux网络》学习笔记&#xff0c;使用的Linux源码版本是3.10&#xff0c;网卡驱动默认采用的都是Intel的igb网卡驱动 Linux源码在线阅读&#xff1a;https://elixir.bootlin.com/linux/v3.10/source 3、内核是如何发送网络包的 1&#xff09;、网络包发送过程…

聚观早报 |2024款飞凡R7官宣;小米14新配色材质

【聚观365】10月27日消息 2024款飞凡R7官宣 小米14新配色材质 金山办公2023第三季度业绩 IBM2023第三季度业绩 新东方2024财年第一季度业绩 2024款飞凡R7官宣 飞凡汽车官宣&#xff0c;2024款飞凡R7将于11月上市&#xff0c;新车将搭载飞凡巴赫座舱&#xff0c;同时超过1…

LabVIEW应用开发——基本函数(一)

前面我们介绍了一些控件的介绍和属性的配置&#xff0c;想要完成一个软件只会拖控件肯定是不行的&#xff0c;没办法实现既有的功能。比如我们要实现从串口中读到数据&#xff0c;根据一定的协议解析&#xff0c;然后转换成各个参数的值的显示&#xff0c;包括时间、电压、电流…

Simulink中如何使用数组以及创建数组、对数组索引、赋值

一、总体概述 1、数组的创建&#xff1a;Mux/constant 2、数组的切片&#xff1a;Demux 3、数组的索引&#xff1a;Selector 4、数组的赋值&#xff1a;Assignment 5、数组的运算&#xff1a;数组可只直接使用运算模块、点乘、矩阵运算 二、详细步骤 1、数组的创建 &am…

【Docker】Linux网络命名空间

命名空间 Namespace是Linux提供的一种对于系统全局资源的隔离机制&#xff1b;从进程的视角来看&#xff0c;同一个namespace中的进程看到的是该namespace自己独立的一份全局资源&#xff0c;这些资源的变化只在本namespace中可见&#xff0c;对其他namespace没有影响。容器就…

stm32的ADC采样率如何通过Time定时器进行控制

ADC采样率是个跟重要的概念. 手册上说可以通过Timer定时器进行触发ADC采样. 可我这边悲剧的是, 无论怎么样. ADC都会进行采样. 而且就算是TIM停掉也是一样会进行采样. 这就让我摸不着头脑了… 我想通过定时器动态更改ADC的采样频率. 结果不随我愿… 这到底是什么问题呢? 一…