布局优化 & 过度绘制检测

QuibblerQuibbler 2020-02-20 约 9 分钟 1836 次阅读

布局优化 & 过度绘制检测

1、选择合适布局

一开始就选择一个合适的根布局,是明智的选择。合理的构思有利于减少布局层级。推荐如下优先选择:

FrameLayout > LinearLayout > RelativeLayout

·减少布局层级,层级越深,测量绘制越复杂耗时。布局应当宽而浅,而不是窄而深。

·能用一层RelativeLayout布局最好

·不要嵌套使用RelativeLayout布局,因为RelativeLayout会调用childrenView 的onMeasure()两次

·不要在嵌套的LinearLayout中都使用weight属性

··· ···

2、include重用布局

往往很多地方用到同样的布局,就可以抽取出相同的布局,作为一个单独的layout,在需要用到这种布局的地方使用<include />标签引入公共的layout,可以减少重复的代码量,同一维护修改公共布局。

定义一个公共布局public_layout.xml:

c<?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical">
        
        <ImageView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content" />
    
    </LinearLayout>

其它地方引入该公共布局:

<include layout="@layout/public_layout" />

3、merge标签

使用<include />有一个问题,会增加当前布局的层级。那么就可以在定义公共layout布局的时候,使用<merge />根标签。当使用<include />加载的时候,加载布局会自动“融入”当前布局,不会产生新的层级。提高布局加载性能。

<?xml version="1.0" encoding="utf-8"?>
    <merge xmlns:android="http://schemas.android.com/apk/res/android">
    
        <ImageView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content" />
            
    </merge>

4、ViewStub懒加载

一些View往往一开始不需要,只在出现某些情况的下进行显示。如果单纯的用setVisibility()进行是否显示地控制,浪费了性能。因为无论View的Visibility是GONE还是INVISIBILITY还是VISIBLE,都会进行View的加载和绘制。

ViewStub就是用来解决这个问题的,按需加载,也叫懒加载,只有当需要显示该部分布局的时候才进行加载,渲染显示。ViewStub的详细用法参考另一篇博客《Android中ViewStub控件懒加载布局用法》

<ViewStub
        android:id="@+id/viewstub"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout="@layout/public_layout" />

坑点:

①ViewStub不能为空,否则奔溃。必须为ViewGroup类型,不能为<merge />,ImageView等

ViewStub must have a non-null ViewGroup viewParent

这句话已经明说了,ViewStub只能包含为非空的,ViewGrop 父布局!

②ViewStub只能inflate()一次,多次调用会奔溃。最好直接使用setVisibility()控制显示。如果一开始没有加载,调用setVisibility会自动inflate显示ViewStub布局。

③ViewStub只要加载一次之后,Visibility一直是View.VISIBLE,就不能再通过ViewStub进行判断,而是对所加载的布局进行判断。

④ViewStub加载之后,可以直接在当前布局中通过findViewById()初始化所加载布局的子控件。

5、减少背景绘制

去掉当前Activity的Window的默认背景,设置为null,减少一层绘制。

@Override
    protected void onCreate(Bundle savedInstanceState) {
        ... ...
        Window window = getWindow();
        window.setBackgroundDrawable(null);
    }

减少当前布局Layout 的不必要的background背景色,见View的setWillNotDraw()方法作用一文。

6、慎用alpha

透明度是通过绘制不同层级混合出的效果。.png的图片透明度绘制也会导致overdraw。

7、点9图

Android的2D渲染器会优化draw9patch中的透明区域,从而优化了overdraw。

过度绘制检测

1、检测GPU过渡绘制:Graphic Processing Unit

Android为我们提供了检测工具,布局是否存在过度绘制。

设置 > 选择开发选项(Developer Options) > 调试GPU 过度绘制(Debug GPU Overdraw)

 Android 将按如下方式为界面元素着色,以确定过度绘制的次数:

  • 真彩色:没有过度绘制
  •  蓝色:过度绘制 1 次
  •  绿色:过度绘制 2 次
  •  粉色:过度绘制 3 次
  •  红色:过度绘制 4 次或更多次

2、Hierarchy Viewer分析布局

Hierarchy Viewer 是 Android Device Monitor 中内置的一种工具,可让您测量布局层次结构中每个视图的布局速度。它可以帮助您查找由视图层次结构导致的性能瓶颈。目前已停止维护,推荐使用后面AndroidStudio自带的Layout Inspector。

工具在Android SDK 目录:.\sdk\tools\monitor.bat

打开如果有如下错误,是因为没有设置环境变量 ANDROID_HVPROTO=ddm

打开之后,选择需要调试分析的页面布局:

层级结构一目了然:

3、Layout Inspector 调试布局

使用 Android Studio 中的 Layout Inspector,可以将应用布局与设计模型进行比较、显示应用的放大视图,并在运行时检查其布局的细节。如果布局是在运行时(而不是完全在 XML 中)构建的并且布局表现出意外行为,这会很有用。Layout Inspector 中的大部分功能以前是由 Hierarchy Viewer 和 Pixel Perfect 工具提供的,但这些工具现已弃用。

Layout Inspector 将显示以下内容:

  1. View Tree:布局中视图的层次结构。
  2. Layout Inspector 工具栏:Layout Inspector 的工具。
  3. 屏幕截图:设备上显示的应用布局的屏幕截图,其中显示了每个视图的布局边界。
  4. Properties Table:选定视图的布局属性。


相关推荐

精选
ViewPager和PagerAdapter、FragmentPagerAdapter、FragmentStatePager
Android

ViewPager和PagerAdapter、FragmentPagerAdapter、FragmentStatePager

ViewPager1、ViewPagerandroidx.viewpager.widget.ViewPager,Android中使用非常广泛的控件,可以说是APP必备:首次打开引导页、页面Banner广告等。常用方法:setAdapter() 设置适配器setOffscreenPageLimit() 设置缓存的页面个数,默认是 1setCurrentItem() 跳转到特定的页面setOnPage

1.1k
获取Android内置WebView内核版本
Android

获取Android内置WebView内核版本

获取Android内置WebView内核版本竟然能遇到这样奇葩的事情,网页用的技术过于新颖,以至于只支持高版本Chromium内核的,低版本安卓系统中内置的内核版本较低,无法加载前端页面。1、设置查看在系统设置里 > 应用 > 应用管理 > 显示系统应用,查看WebView组件:2、页面查看通过WebView发起的网络请求,都会带上浏览器的UA,通常页面都可以通过UA判断浏览器的内核版本。这里有两

1.1w
Android 14适配总结
Android

Android 14适配总结

Android 14适配总结毕业工作至今已经适配了三个Android大版本,从Android 11到Android 12、再到Android 13。2023年,Google即将推出的Android 14,上半年已经开始第一批适配。现在,第四个Android版本已经适配完,总结记录一下。1、Android 14计划Google一般会在2月份对外发布预告,同时放出开发者预览版。“拉通”各大平台、厂商以

1.1w