布局页面是如何渲染出来的| 青训营笔记

103 阅读2分钟

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

布局加载流程探究

(根据Android studio的自带Basic Activity模板)

创建好一个xml格式的布局

image-20220816165919179.png 在对应布局的Activity或Fragment加载xml文件(这里Activity使用了viewBinding,使用binding.root代替表示根布局)

image-20220816165718232.png

经过以上流程,xml文件就被activity加载,并在需要的时候显示到页面上

对setContentView进行探究

可见setContentView在MainActivity的父类AppCompatActivity中进行了重写,拓展

image-20220816170020236.png

发现getDelegate()会返回一个AppCompatDelegate类

image.png 这是AppCompatDelegate的创建途径,可见代码将一个Activity activity,一个一个AppCompatCallback callback传输了进去

image.png

在AppCompatDelegateImpl中,可以找到setContentView的方法实现

image.png

各行语句作用的分析

语句一:确保(或创建)mSubDecor

mSubDecor是一个全局的ViewGroup类属性

image.png

语句二:

image.png 通过已经初始化的mSubDecor,取得对应的contentParent,这是一个ViewGroup类

语句三:

image.png

image.png

这将contentParent中的所有之layouit清除

语句四:

image.png

使用LayoutInflater对布局进行解析,同时传入contentParent之中

语句五:

image.png 回调AppCompatWindow的变化消息

对inflate(resId, contentParent)进行探究

发现传入resource ID和根布局后,使用了

image.png

即为

image.png

其中,对resource进行加载的部分为以下

将RSE ID 转化为XmlResourceParser

XmlResourceParser:为XML资源返回的XML解析接口。这是一个标准的XmlPullParser接口,但也扩展了AttributeSet,并为客户端添加了一个额外的close()方法,以指示何时完成了对资源的读取。

image.png

对XmlResourceParser进行后续加载的语句

image.png

在这个方法中按照深度逐层遍历

image.png

生成的view添加到rInflateChildren包装成为ViewGroup.LayoutParams params

最后将params加载到根布局之中

image.png

对生成view的createViewFromTag解析

final View view = createViewFromTag(parent, name, context, attrs);

在createViewFromTag发现多种view构造方法

image.png

发现对常见底层view进行创建的createView(按名称实例化视图的低级函数)

viewContext–用作视图构造函数上下文参数的上下文

name–要实例化的类的全名。

attrs–为该实例提供的XML属性。

返回:查看新实例化的视图,或null。

核心函数:将viewContext和xml参数传入,创建了一个view

image.png

至此,布局数据的加载完毕。已经全部添加在对应活动的根布局之中