被面试问到”OverDraw”和Android 中UI 的卡顿,但是我没有回答出来,遂开始寻找答案。感叹以前开发实在不够认真,Overdraw与卡顿这么影响使用的问题怎么能现在出在乎呢? 所以写下今天的博客提醒自己:要认真!
参考1(需要科学上wan):Optimizing Layout in Android-Reducing OverDraw
参考2.Android性能优化之如何避免Overdraw
Q:什么是Overdraw
- 假设一帧的时间(16.67ms)为单位时间,在单位时间内,我们UI的图片由于“重叠布局”,会被多次重绘,这会大量消耗不必要的CPU和GPU 的性能。
- 假如这个操作超过单位时间,就会出现掉帧—这就是卡顿
- OverDraw 就是过度绘制
我们需要减少卡顿,减少计算机开销,这就是需要减少过度绘制(reduce OverDraw)
Q:如何测量Overdraw
- 打开开发者选项-调试GPU过度绘制(Show GPU Overdraw)
序号 | 颜色 | 含义 | 修改 |
---|---|---|---|
1 | 没有颜色 | 像素画一次 | 最佳 |
2 | 蓝紫色 | 像素绘制两次,overdraw1次 | 好 |
3 | 绿色 | 像素绘制三次,overdraw2次 | 可以接受 |
4 | 浅红色 | 像素绘制四次,overdraw3次 | 小范围可以接受 |
5 | 暗红色 | 像素绘制五次,overDraw4次 | 这是错误,需要修复 |
我拿支付宝,微信,bilibili….看看情况
这里写图片描述
小结
- bilibili 和支付宝明显比较卡顿,微信较好。Orverdraw 要尽量避免
- Overdraw 就是过渡绘制,原因是重复绘制影响了cpu和gpu的性能
解决方法
一.选择合理控件容器
- 在同等数量的容器情况下:FrameLayout>LinearLayout>RelativeLayout。因为前者的纯洁,表达能力较低;
- 但是,假如使用复杂控件能减少层级,我们应该选用更低层级的控件;
二.去掉window 的默认背景
- 在setContentView()之后
getWindow().setBackgroundDrawable(null);
-在theme中添加
android:windowbackground="null";
三.去掉其他不必要的背景
给Layout 或者子View设置背景,会造成重叠,而且会被覆盖,这造成overDraw.
在使用selector将normal的color 设置@android:color/transparent”
四.ClipRect #QuickReject
canvas的函数 | 含义 |
---|---|
clipRect() | 帮助系统识别可见的区域,控制可见区域被绘制,其他忽略 |
quickreject() | 判断是否没和某个矩形相交,从而跳过那些非矩形区域 |
五.ViewStub
ViewStub:高效占位符
这个空间layout的时候占位,开销小,只有在ViewStub.inflate()的时候被实例化
使用方法
<ViewStub
android:id="@+id/stub_view"
android:inflatedId="@+id/panel_stub"
android:layout="@layout/progress_overlay"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom" />
((ViewStub) findViewById(R.id.stub_view)).setVisibility(View.VISIBLE);
View importPanel = ((ViewStub) findViewById(R.id.stub_view)).inflate();
六:merge
去除一个view层级:一般配合include使用,可以去除一个FrameLayout
七.draw9patch
将背景drawable 制作成9patch,并且将和前景重叠的部分设置为透明。android
会优化9patch中的透明部分,从而优化这次overDraw
八.慎用Alpha
Alpha转化需要对当前View绘制两个,overDraw
view.setLayerType(LAYER_TYPE_HARDWARE);
doSmoeThing();
view.setLayerType(LAYER_TYPE_NONE);
通过setLayerType方式可以将当前界面缓存GPU 中,这样不需要每次绘制原始界面。
九避免“overDesign”
避免重复设计。
许多APP(说的就是你:支付宝)披着过度设计的华丽外衣,却忘了简单易用才是王道的本质,造成OverDraw