平常对RecyclerView的使用,代码如下,以及sdk中对应方法的注释,(学习sdk看源码注释是最容易的方法了)
1 |
|
想要分析一个View,基本上按measure
layout
draw
分析 基本上就没问题了
Measure
RecyclerView 是 对逐个子view 依次 measure、layout 而不是全部measure完再layout
1 | public LinearLayoutManager() { |
mLayout.onMeasure
1 | public void onMeasure(Recycler recycler, State state, int widthSpec, int heightSpec) { |
dispatchLayoutStep1
1 | /** |
dispatchLayoutStep2
1 | /** |
mLayout.onLayoutChildren
1 | //LinearLayoutManager |
1 | int fill(RecyclerView.Recycler recycler, LayoutState layoutState, |
Layout
1 | protected void onLayout(boolean changed, int l, int t, int r, int b) { |
Tangram
HelloTangram
根据官方给的接入指南,写了个最简单的demo,封装了基础的Activity,建议先过一遍官方demo。
自定义的view
1 | public class TestView1 extends FrameLayout implements ITangramViewLifeCycle { |
Activity
1 | public class L1Activity extends CommonActivity { |
1 | /** |
json文件:data_1.json
1 | [ |
Builder
逐行跟进,先看看TangramBuilder.newInnerBuilder(context)
做了什么,以及这个builder是干嘛的。
1 | public static InnerBuilder newInnerBuilder(@NonNull final Context context) { |
DefaultResolverRegistry
看命名就知道是个负责分解注册的集合类。几个成员如下,先有个印象,后续用到再来分析
1 | public class DefaultResolverRegistry { |
installDefaultRegistry
负责初始化一些built-in的card和cell类型
1 | public static void installDefaultRegistry(@NonNull final DefaultResolverRegistry registry) { |
既然这里用到了,就跟进看看MVResolver和MVHelper是啥吧。
1 | public class MVResolver { |
根据成员和方法,不难看出是个维护 model-view 映射关系的类,内置了一些默认的json文件的key值,如type、style和id等等。
1 | public class MVHelper { |
MVHelper就是对MVResolver的封装,是个helper类嘛。让用户有了在MVResolver建立model-view映射关系时,hook的能力,比如通过cell.serviceManager.getService
来通知用户自定义的Support类(见mountView方法)。
DefaultResolverRegistry.registerCell
1 | public <V extends View> void registerCell(String type, final @NonNull Class<V> viewClz) { |
viewHolderMap存的是用户传入的自定义ViewHolder,一般没有,上述方法最后做的就是把type和viewClz存到对应的map里
1 | mMap.put(gen, type);//BaseReslover.class |
registerCard同理。
InnerBuilder
分析完上面几个类,再回归正题,InnerBuilder这个类。
1 | protected InnerBuilder(@NonNull final Context context, DefaultResolverRegistry registry) { |
可以看做一个代理类了,封装了上面几个成员的各种方法。用到再说。
Engine
进入到InnerBuilder的build方法看下是怎么构造TangramEngine的
1 | public TangramEngine build() { |
TangramEngine
1 | public TangramEngine(/*...*/) { |
1 | public BaseTangramEngine(final Context context, |
看看那Base类的成员
1 | //跟上面Registry一样的class与obj的键值对,保存注册的service |
register方法也就是将clz与obj保存起来,方便后续使用
1 |
|
setData
demo中,数据流的进入通过TangramEngine的setData方法,有了上面的基础,我们现在跟进去看看。
1 |
|
1 | public void setData(@Nullable T data) { |
parse
由之前的分析,Engine中的mDataParser是由Builder传入的,是在其构造函数中new的PojoDataParser实例。
1 | //PojoDataParser.java |
1 | public Card parseSingleGroup(@Nullable JSONObject data, final ServiceManager serviceManager) { |
1 | //CardResolver 父类 ClassResolver |
看到没,直接从mSparseArray中取。这个mSparseArray就是前面Builder.registerCell和Card的时候存到BaseResolver里的那个mSparseArray。
解析完所有card之后,调用engine自己的setData方法
1 | public void setData(@Nullable List<C> data) { |
load
解析完成,就要加载了。回到上面的setData中的this.setData看看。
1 | public void setData(@Nullable List<C> data) { |
1 | //GroupBasicAdapter.java |
调用setLayoutHelpers 就正式进入Vlayout的世界了
1 | public abstract class VirtualLayoutAdapter<VH extends RecyclerView.ViewHolder> extends RecyclerView.Adapter<VH> { |
V-layout的世界
官方使用
1 | public class MyAdapter extends VirtualLayoutAdapter { |
从RecyclerView说起
LayoutManager在measure和layout中扮演的角色
Adapter又起到什么作用
Vlayout是如何介入的
VirtualLayoutManager
VirtualLayoutManager继承自ExposeLinearLayoutManagerEx继承自LinearLayoutManager
1 | ExposeLinearLayoutManagerEx is used to expose layoutChunk method |
结合RecyclerView和LayoutManager流程,就可以知道VirtualLayout是在layoutChunk中动了手脚,把layout行为分发出去。
1 |
|
由此可见,我们是可以自己写LayoutHelper来实现自己的view的layout过程