Android View绘制 | 青训营笔记

72 阅读2分钟

这是我参与「第四届青训营 」笔记创作活动的第3天

1.布局加载解析过程

布局加载的主要开发步骤是:编写布局文件->注册Mainfest->设置布局文件

在设置布局文件中有两个需要去注意的函数:setContentView(R.layout.xxxx)finViewById(R.layout.xxxx)

  • setContentView:通过ensureSubDecor()创建了DecorView,通过DecorView找到android.R.id.content的ViewGroup,然后移除ViewGroup上所有的View。最后通过LayoutInflater来加载xml文件。
  • LayoutInflater:解析了xml文件,并通过creteViewFromTag(parent,name,context,attrs)传入xml文件生成View实例,并将View实例添加到了其ViewGroup中。
  • creteViewFromTag:使用简单工厂模式通过name创建各种view,并将各种属性传入进去,比如高度、宽度和字体大小等。

2.为什么Activity在onResume()之后才显示?

其中根据布局加载解析过程的内容我们可以得出,在onCreate()的时候,我们是通过setContentView()创建了DecorView,并将layout中的各种View以及其中的属性添加到了DecotView中。其实整体的功能还是着重在解析这一部分,并没有进行绘制。

那么在onResume()中发生了什么呢?

借用ViewRootImpl的能力去触发绘制(ViewRootImpl.requestLayout

3.View绘制流程

1661876902560.png

  • Measure:测量宽度和高度,真正绘制的时候需要去知道这个View多高多宽。
  • Layout:决定要绘制到哪个地方。
  • Draw:要画成什么样子。

3.总结整体绘制流程

96b1de9af31d21c52c07cb172845583.png

其中WindowMangerImpl->addView->WindowManagerGlobal->addView 这四部分只是作为了解流程。

真正绘制的过程是从ViewRootImpl.requestLayout开始的,在调用该方法后只是去请求绘制。等编舞者(Choreogrepher)拿到回调的时候(postCallBack)才会去做相应的绘制,最后执行到performTraversals()的时候才会做真正的绘制。

4.vsync信号

1661877652062.png

在一个vsync信号里面:

  • cpu去执行measure、layout、draw。

  • gpu去负责画面的合成。