Android-布局优化
文章目录
- 1.减少层级
- 1.1页面层级查看
- 1.2页面层级优化
- 1.2.1合理使用RelativeLayout和LinearLayout
- 1.2.2合理使用Merge
- 2.提高显示速度ViewStub的使用
- 2.1ViewStub介绍
- 2.2ViewStub的加载方式:
- 2.3ViewStub应用场景
- 2.4ViewStub使用注意事项
- 3.布局复用include
- 4.避免过度绘制
- 4.1过度绘制介绍
- 4.2过去绘制的原因
- 4.3过度绘制的检测
- 4.4过度绘制的优化
- 4.4.1布局文件过度绘制优化:较少页面层级,减少不必要的背景设置
- 4.4.2自定义View优化过度绘制的优化
- 5.子线程加载布局文件
- 6.使用x2c对布局进行加载,
1.减少层级
1.1页面层级查看
通过使用布局view层级检测工具hierarchy viewer来查看页面的层级。这个工具在android-sdk/tools/文件夹中,默认无法连接真机,可以通过ViewServer来解决无法连接真机的问题,在需要查看的页面添加:
//就可以解决无法连接真机的问题
@Overrideprotected void onCreate(Bundle saveInstanceState) {super.onCreate(saveInstanceState);if (BuildConfig.DEBUG){ViewServer.get(this).addWindow(this);}}@Overrideprotected void onResume() {super.onResume();if (BuildConfig.DEBUG){ViewServer.get(this).setFocusedWindow(this);}}@Overrideprotected void onDestroy() {if (BuildConfig.DEBUG){ViewServer.get(this).removeWindow(this);}}
点击Evaluate Contrast可以View的颜色绿色、黄色、红色,出现黄色或者红色表示页面层级较深,需要优化。
也可以通过Lint进行代码扫描。
1.2页面层级优化
层级越少,测试和绘制的时间就越短,通常减少层级有以下两个常用方案:
1.2.1合理使用RelativeLayout和LinearLayout
- 层级一样优先使用LinearLayout,因为RelativeLayout默认进行两次measure操作。
- 用LinearLayout有时会使嵌套层级变多,应该使用RelativeLayout,使界面尽量扁平化。
1.2.2合理使用Merge
在Android布局的源码中,如果是Merge标签,那么直接将其中的子元素添加到Merge标签Parent中,这样就保证了不会引入额外的层级。
Merge不是所有地方都可以任意使用,有以下几点要求:
- Merge只能用在布局XML文件的根元素。
- 使用merge来加载一个布局时,必须指定一个ViewGroup作为其父元素,并且要设置加载的attachToRoot参数为true。
- 不能在ViewStub中使用Merge标签。原因就是ViewStub的inf late方法中根本没有attachToRoot的设置。
但从Lint检查的配置上看,超过10层才会报警,实际上在开发时,随着产品设计的丰富和多样性,很容易超过10层,根据实际开发过程中超过15层就要重视并准备做优化, 20层就必须修改了
2.提高显示速度ViewStub的使用
2.1ViewStub介绍
ViewStub是一个轻量级的View,它是一个看不见的,并且不占布局位置,占用资源非常小的视图对象。可以为ViewStub指定一个布局,加载布局时,只有ViewStub会被初始化,然后当ViewStub被设置为可见时,或是调用了ViewStub.inflate()时,ViewStub所指向的布局会被加载和实例化,然后ViewStub的布局属性都会传给它指向的布局。这样,就可以使用ViewStub来设置是否显示某个布局。
2.2ViewStub的加载方式:
ViewStub显示有两种方式:
- 调用:inflate()方法.
- 直接使用ViewStub. setVisibiltity(View.Visible)方法。
2.3ViewStub应用场景
ViewStub的主要使用场景如下:
- 在程序运行期间,某个布局在加载后,就不会有变化,除非销毁该页面再重新加载。
- 想要控制显示与隐藏的是一个布局文件,而非某个View。
2.4ViewStub使用注意事项
使用ViewStub时需要注意以下几点:
ViewStub只能加载一次,之后ViewStub对象会被置为空。换句话说,某个被ViewStub指定的布局被加载后,就不能再通过ViewStub来控制它了。所以它不适用于需要按需显示隐藏的情况。
ViewStub只能用来加载一个布局文件,而不是某个具体的View,当然也可以把View写在某个布局文件中。如果想操作一个具体的View,还是使用visibility属性。
VIewStub中不能嵌套Merge标签
3.布局复用include
在开发过程中,如果一个相同的布局在很多页面(Activity或Fragment)会用到,如果给这些页面的布局文件都统一加上相同的布局代码,维护起来就很麻烦,可读性也差,一旦需要修改,很容易有漏掉的地方。
Android的布局复用可以通过标签来实现,就像提取代码公用部分一样,在编写Android布局文件时,也可以将相同的部分提取出来,在使用时,用添加进去。
4.避免过度绘制
4.1过度绘制介绍
**过度绘制(Overdraw)**是指在屏幕上的某个像素在同一帧的时间内被绘制了多次。在多层次重叠的UI结构(如带背景的TextView)中,如果不可见的UI也在做绘制的操作,就会导致某些像素区域被绘制了多次,从而浪费多余的CPU以及GPU资源。
4.2过去绘制的原因
过度绘制的主要原因:
- XML布局->控件有重叠且都有设置背景
- View自绘-> View.OnDraw里面同一个区域被绘制多次
4.3过度绘制的检测
可以通过手机设置中的开发者选项,打开Show GPU Overdraw选项
打开后可以根据不同的颜色观察UI上的Overdraw情况,蓝色、淡绿、淡红、深红代表4种不同程度的Overdraw情况,不同颜色的含义如下:
- 无色:没有过度绘制,每个像素绘制了1次。
- 蓝色:每个像素多绘制了1次。大片的蓝色还是可以接受的。如果整个窗口是蓝色的,可以尝试优化减少一次绘制。
- 绿色:每个像素多绘制了2次。
- 深红:每个像素多绘制了4次或者更多。严重影响性能,需要优化,避免深红色区域。
我们的目标是尽量减少红色Overdraw,看到更多的蓝色区域。
4.4过度绘制的优化
4.4.1布局文件过度绘制优化:较少页面层级,减少不必要的背景设置
使用Android自带的一些主题时,activity往往会被设置一个默认的背景,这个背景由DecorView持有。当自定义布局有一个全屏的背景时,比如设置了这个界面的全屏黑色背景,DecorView的背景此时对我们来说是无用的,但是它会产生一次Overdraw。可以通过下面的方式消除。
@Override
protected void onCreate(Bundle saveInstanceState) {super.onCreate(saveInstanceState);getWindow().setBackgroundDrawable(null);
}
针对RecyclerView Item中的Avatar ImageView的设置,在getView的代码中,判断是否获取对应的Bitmap,获取Avatar的图像之后,把ImageView的Background设置为Transparent,只有当图像没有获取到时,才设置对应的Background占位图片,这样可以避免因为给Avatar设置背景图而导致的过度渲染。
4.4.2自定义View优化过度绘制的优化
在自定义View的时候,某个区域可能会被绘制多次,造成过度绘制。
可以通过canvas.clipRect()方法指定绘制区域。
clipRect方法还可以帮助节约CPU与GPU资源,在clipRect区域之外的绘制指令都不会被执行,那些部分内容在矩形区域内的组件,仍然会得到绘制。
并且可以使用canvas.quickreject()来判断是否没和某个矩形相交,从而跳过那些非矩形区域内的绘制操作。
5.子线程加载布局文件
使用AsyncLayoutInflater在子线程加载布局文件需要添加依赖:
implementation 'androidx.asynclayoutinflater:asynclayoutinflater:1.0.0'
下面是通过子线程添加布局文件的例子:
override fun onCreate(savedInstanceState: Bundle?) {super.onCreate(savedInstanceState)AsyncLayoutInflater(MainActivity@ this).inflate(R.layout.activity_main, null) { view, resid, parent ->setContentView(view)val contentTextView: TextView =findViewById(R.id.content);contentTextView.text = "通过子线程加载layout布局文件"}
}
6.使用x2c对布局进行加载,
setContentView加载xml布局文件,framework层主要是通过LayoutInflater.inflater方法来解析xml并创建View的,解析XML文件会涉及io读写,view的创建是通过反射来实现的,都是比较耗时的操作。
可以借助x2c来加载布局文件,可以避免反射和io读取
使用x2c加载布局文件需要导入一下依赖:
annotationProcessor 'com.zhangyue.we:x2c-apt:1.1.2'
implementation 'com.zhangyue.we:x2c-lib:1.0.6'
使用x2c加载布局文件实例:
@Xml(layouts = ["activity_main"])
class MainActivity : AppCompatActivity() {override fun onCreate(savedInstanceState: Bundle?) {super.onCreate(savedInstanceState)X2C.setContentView(this, R.layout.activity_main)val contentTextView: TextView =findViewById(R.id.content);contentTextView.text = "通过X2C加载layout布局文件"}
}
x2c原理就是编译时注解:遍历注解,通过动态生成代码的方式,将反射的方式改成new的方式将View进行初始化操作。
x2c可能会存在兼容性问题,出现问题,需要做一些代码的优化。
Android-布局优化相关推荐
- Android布局加载慢,Android布局优化(四)X2C — 提升布局加载速度200%
系列文章 前言 在Android布局优化(一)从布局加载原理说起中我们说到了布局加载的两大性能瓶颈,通过IO操作将XML加载到内存中并进行解析和通过反射创建View.这里介绍一种避免运行时通过IO操作 ...
- 深入探索Android布局优化(上)
前言 成为一名优秀的Android开发,需要一份完备的知识体系,在这里,让我们一起成长为自己所想的那样~. Android的绘制优化其实可以分为两个部分,即布局(UI)优化和卡顿优化,而布局优化的核心 ...
- android listview viewstub,Android布局优化之ViewStub控件
ViewStub是Android布局优化中一个很不错的标签/控件,直接继承自View.虽然Android开发人员基本上都听说过,但是真正用的可能不多. ViewStub可以理解成一个非常轻量级的Vie ...
- 一篇文章搞定《Android布局优化》
------<一篇文章搞定Android布局优化> 前言 为什么要进行布局优化? Android绘制原理 双缓冲机制 布局加载原理 布局加载优化的一些方法介绍 AsyncLayoutInf ...
- android布局优化方案,Android启动优化-布局优化
Android启动优化-布局优化 安卓应用开发发展到今天,已经成为一个非常成熟的技术方向,从目前的情况看,安卓开发还是一个热火朝天的发展,但高级人才却相对较少,如今移动互联网的开发者也逐渐开始注重插入 ...
- android layout include merge,Android 布局优化之include与merge
Android 官方提供了三个用来优化布局的标签,分别是include.merge与ViewStub,其中ViewStub是动态加载视图到内存,大家可以查阅:Android UI布局优化之ViewSt ...
- android 减少布局层级,Android 布局优化
布局优化主要从以下几点进行着手 减少布局层次 和 复杂度 优化绘制流程 按需加载布局 减少布局层次 和 复杂度 首先我们可以通过以下工具分析界面布局的结构 查看布局树工具:Hierarchy View ...
- Android 布局优化
在开发过程中我们经常说性能优化,但性能优化是一个比较宽泛的概念.在Android开发中性能优化可能包括:Java代码优化, 算法优化, SQLite优化, 布局优化等.那么这篇博客就来总结并分享下An ...
- android布局优化 工具,详解Android布局优化
怎样才能写出优秀的Android App,是每一个程序员追求的目标.那么怎么才能写出一个优秀的App呢?相信很多初学者也会有这种迷茫.一句话来回答这个问题:细节很重要.今天我们就从最基础的XML布局来 ...
- Android成长日记-Android布局优化
Android常用布局 1. LinearLayout(线性布局) 2. RelativeLayout(相对布局) 3. TableLayout(表格布局) 4. AbsoluteLayou(绝对布局 ...
最新文章
- 打开完成查看的CAD图纸如何一键进行打印?
- 2-数组中重复的数字
- 【Rain in ACStar HDU-3340】
- C语言的main函数到底怎么写的
- JavaFX 一 出生新手村(阅读小规则)
- AQS的细节--自用,非正常教程
- oracle trigger 延迟执行_一文详解Spring任务执行和调度
- 找不到该项目,请确认该项目的位置的解决办法
- (项目)生鲜超市(六)
- python问题:NameError: name 'reload' is not defined
- xy的联合概率密度函数怎么求_X Y的联合密度函数
- 国家统计局可以获取到全国5级行政区域数据
- wep破解——模拟chopchop攻击
- 无人驾驶时代的室外组网技术研究
- linux 查看java版本
- 计算机ip地址错误,网络ip地址怎么修复_ip地址错误的修复步骤-win7之家
- 2022团队天梯赛答案解析
- srec_cat 常用参数的使用
- QK Read, développer des habitudes de lecture
- 学计算机需要什么基础?