Android性能优化之绘制优化

1 卡顿主要场景

这四种卡顿场景可以归纳为两类

界面绘制:主要原因是绘制的层级深、页面复杂、刷新不合理,由于这些原因导致的卡顿的场景更多出现在UI和启动后的初始界面以及跳转到页面的绘制上

数据处理:导致这种卡顿的主要原因是数据处理量太大,分如下三种情况

1 数据处理在UI线程

2 数据处理占用CPU高,导致主线程拿不到时间片

3 内存增加导致GC频繁,从而卡顿

2 Android系统显示原理

显示的过程:android应用程序把经过测量、布局、绘制后的surface缓存数据,通过surfaceflinger把数据渲染到显示屏幕上,通过android的刷新机制来刷新数据。应用层复杂绘制,系统层复杂渲染,通过进程间通信把应用层需要绘制的数据传递到系统层服务,系统层服务通过刷新机制把数据更新到屏幕

3 绘制原理

应用层绘制一个页面的过程:CPU准备数据-->GPU从数据缓存列表获取数据-->Display设备绘制

1)应用层

2)系统层

3)刷新机制

4 卡顿的根本原因

影响绘制的根本原因有以下两方面:

1 )绘制任务太重,绘制一帧内容耗时太长

2 )主线程太忙了,导致VSync信号来时还没有准备好数据导致丢帧

主线程的工作:

UI生命周期控制

系统事件处理

消息处理

界面布局

界面绘制

界面刷新

除了这些以外,尽量避免将其他处理放到主线程中,特别是复杂的数据计算和网络请求

5 性能分析工具

Hierarchy view--layout层次分析

GPU Profile--系统自带的,开发者选项中开启

Lint

TraceView:可以分析到应用具体每一个方法的执行时间

用法:在需要开始监控的地方调用startMethodTracing().

在需要结束监控的地方调用stopMethodTracing()

系统会在sd卡中创建<trace-bame>.trace文件

使用traceview打开该文件进行分析

Systrace--收集android关键自系统(如surfaceflinger、WindowManagerService等framework部分关键模块、服务、view系统)的运行信息,功能包括跟着系统的I/O操作、内核工作队列、CPU负载等,在UI显示性能分析上提供很好的数据,特别是在动画播放不流畅、渲染卡等问题上,可以很直观地查看CPU周期消耗的具体时间,显示每个线程和进程的跟踪信息,使用不同颜色来突出问题的严重性

6 布局优化

方法

1)减少层级:合理使用relativelayout和LinearLayout,合理使用merge

2)提高显示速度:viewstub

3)布局复用:include 

小结:

影响布局效率主要有以下几点

布局的层级越少,加载速度越快

减少同一层级控件的数量,加载速度会变快

一个控件的属性越少,解析越快

对优化的总结:

尽量多使用relativelayout和LinearLayout,不要使用绝对布局absolutelayout

将可以服用的组件抽出来并通过<include/>标签使用

使用<ViewStub/>标签加载一些不常用的布局

使用<merge/>标签减少布局的嵌套层次

尽可能少用wrap_content,wrap_content会增加布局measure时的计算成本,已知宽高为固定值时,不用wrap_content

删除控件中的无用属性

7 避免过度绘制

定义:在屏幕上的某个像素在同一帧的时间内别绘制了多次

导致过度绘制的主要原因:

xml布局->控件有重叠且有设置背景

view自绘->View.onDraw里面同一个区域被绘制多次

过度绘制检测工具:开发者选项中打开显示GPU过度重绘

7.1 如何避免过度绘制

1)布局行的优化:移除xml中非必须的背景,或者根据条件设置

移除window默认的背景

按需显示占位背景图片

2)自定义view优化

可以通过cancas.clipRect()来帮助系统识别那些可见的区域

通过canvas.quickreject()来判断是否没有和某个矩形相交,从而跳过哪些非矩形区域内的绘制操作