概念
当android系统绘制屏幕的时候,先画父view,然后子view,再是更深的子view等等。这会导致所有的view都被绘制到了屏幕上并且这些view都被他们的子view覆盖住了。
在Debug GPU overdraw菜单里选择“Show Overdraw areas”选项。选择之后,会在app的不同区域覆盖不同的颜色来表示overdraw的次数。比较屏幕上这些不同的颜色,可以快速方便的定位overdraw问题:
白色:没有overdraw
蓝色:1x overdraw
绿色:2x overdraw
浅红色:3x overdraw
深红色:4x或者更多overdraw
以上就是过度绘制的概念。光知道这些当然是没什么作用的,还是需要结合实际的例子才能够懂得一些。
对比分析
很简单我们拿我们 Testerhome的app 来简单的分析下。
我们开启 GPU过渡绘制后,查看界面
- banner 区域的多重绘制可以理解,因为确实是需要在viewpager上面重新绘制一个textview
- recyclerview 中显示红色就有点难以理解了。
当然我们比较下我们熟悉的微信吧。
很明显微信上面是没有这个问题的。既然发现问题,我们就来分析下到底是什么导致了这个现象吧,我们从github上拉下最新的的代码A-Native-TesterHome, 我们需要理解一点,过渡绘制导致的原因基本是父类的布局设置了一个背景,子类的布局又重新在上面绘制了一层。
我们进入到list_item_topic.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:fresco="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/rl_topic_item"
android:background="@drawable/item_selector"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="8dp"
android:paddingLeft="16dp"
android:paddingRight="16dp"
android:paddingTop="8dp">
<com.facebook.drawee.view.SimpleDraweeView
android:id="@+id/sdv_topic_user_avatar"
android:layout_width="56dp"
android:layout_height="56dp"
android:layout_marginRight="16dp"
fresco:roundAsCircle="true" />
以上我们可以发现RelativityLayout中设置了background了,从名字我们也能够看出了这个是在item被选中的时候,能够显示出被选中的状态。具体:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="@drawable/item_selected_drawable" android:state_pressed="true" />
<item android:drawable="@color/white" />
</selector>
那么我们能够修改吗 ? 当然我们肯定不能够直接把background注释掉,因为那样子就没有点击的效果了。我们可以把尝试把 default的注释掉,也就是:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="@drawable/item_selected_drawable" android:state_pressed="true" />
<!--<item android:drawable="@color/white" />-->
</selector>
下来我们来看看修改后的结果吧
嗯。问题看来就是这么解决的了
本来想通过hierarchyviewer 看看修改前后绘制需要的时间,结果试了下发现没什么变化。估计是我的使用方法不正确。这里就不献丑来。
参考文章
Android UI性能优化详解
强烈推荐看这篇文章,干货多。
PS:以上这个只是简单的一个过度绘制修改,当然还有通过hierarchyviewer来简化一些布局等等。