vlayout(VirtualLayout)是阿里开源的一个针对 RecyclerView 的 LayoutManager 扩展,主要提供一整套布局方案和布局间的组件复用。
下面主要简述一下个人读官方文档和实践demo的心得,demo的GitHub地址放在文末,欢迎各位大佬指教~
1.初始化RecycleView,
基于上下文,初始化一个VirtualLayoutManager;
recyclerView.setLayoutManager(layoutManager);
将这个VirtualLayoutManager设置进去recyclerView;
2.利用第一步的VirtualLayoutManager创建一个DelegateAdapter ;
DelegateAdapter delegateAdapter = new DelegateAdapter(layoutManager, hasConsistItemType);
3.1.
准备一个Adapter列表:
List<Adapter> adapterList = new ArrayList<>();
添加(add)各种Adapter,
add的参数即自定义adapter,
这里的自定义adapter是SubAdapter;(代码来自官网demo)
adapterList.add(new SubAdapter(new LinearLayoutHelper(20), 20));
adapterList.add(new SubAdapter(new StickyLayoutHelper(true), 1));
adapterList.add(new SubAdapter(new LinearLayoutHelper(20), 20));
adapterList.add(new SubAdapter(new GridLayoutHelper(4), 80));
// adapterList.add(new SubAdapter(new FixLayoutHelper(0, 0), 1));
adapterList.add(new SubAdapter(new FixLayoutHelper(TOP_RIGHT, 0, 0), 1));
3.2.
自定义adapter的设计:
注意,
自定义adapter继承自DelegateAdapter.Adapeter,
泛型可以是自定义的ViewHolder;
构造函数一般接收两个参数,
即LayoutHelper
以及一个数据参数(用于adapter的数据支持)
;
private static class SubAdapter extends DelegateAdapter.Adapter<SubViewHolder> {
private LayoutHelper mLayoutHelper;
private int mItemCount;
private SubAdapter(LayoutHelper layoutHelper, int itemCount) {
mLayoutHelper = layoutHelper;
mItemCount = itemCount;
}
@Override
public LayoutHelper onCreateLayoutHelper() {
return mLayoutHelper;
}
@Override
public SubViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
LayoutInflater inflater = LayoutInflater.from(parent.getContext());
return new SubViewHolder(inflater.inflate(R.layout.item, parent, false));
}
@Override
public void onBindViewHolder(SubViewHolder holder, int position) {
// do nothing
}
@Override
protected void onBindViewHolderWithOffset(SubViewHolder holder, int position, int offsetTotal) {
super.onBindViewHolderWithOffset(holder, position, offsetTotal);
holder.setText(String.valueOf(offsetTotal));
holder.itemView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT));
}
@Override
public int getItemCount() {
return mItemCount;
}
}
对应的ViewHolder设计:
private static class SubViewHolder extends RecyclerView.ViewHolder {
public static volatile int existing = 0;
public static int createdTimes = 0;
public SubViewHolder(View itemView) {
super(itemView);
createdTimes++;
existing++;
}
public void setText(String title) {
((TextView) itemView.findViewById(R.id.title)).setText(title);
}
@Override
protected void finalize() throws Throwable {
existing--;
super.finalize();
}
}
以上,通过给,
继承自DelegateAdapter.Adapter
的自定义Adapter
,
设置不同的LayoutHelper
,实现了各种各样的布局adapter
,
然后我们把这些各种各样的布局adapter
,
加入到一个List<Adapter> adapterList
中去,
接下来我们把这个adapterList
,
设置到delegateAdapter
中去:
delegateAdapter.addAdapters(adapterList);// 不加会 android.content.res.Resources$NotFoundException: Resource ID!!!!
delegateAdapter.addAdapters(adapterList);
这里便是VLayout的美妙之处,
我们可以通过继承DelegateAdapter.Adapter
,
创建一个自定义的Adapter
,顺带配备对应的ViewHolder
即业务容器
;
给这个自定义Adapter
的onCreateLayoutHelper()
传入
各种各样
的不同类型
的不同构造形参
的LayoutHelper
,
配合传给自定义Adapter的数据支持参数位
,
又可以实现各种各样的布局效果
;
而这些个各种各样
的不同的布局
(adapterList
),
又可以加到同一个delegateAdapter
中,
借助delegateAdapter
、VirtualLayoutManager
,
将各种各样
的这些个布局
,
整到同一个RecycleView
中!
4.最后画龙点睛:
recycler.setAdapter(delegateAdapter);
-
adapter的设计跟RecycleView的adapter设计差不多,
都是onCreateViewHolder
/ViewHolder
/onBindViewHolder
/getItemCount
四部曲罢了:DelegateAdapter.Adapter
无非就是多了个决定布局类型
的onCreateLayoutHelper()
方法罢了; 注意
getItemCount
可以用来控制显示的数量,
可以是数据List的Size,
也可以通过设定Adapter构造方法,在被调用时通过new过程获取;
其他的就在自定义的Adapter中、在自定义ViewHolder中添加业务逻辑/业务方法函数即可;
比如可以在onBindViewHolder()
的return
之前加套if
逻辑组,
通过给不同的LayoutHelper
设定不同的item
颜色等等;-
LayoutHelper
实例可以通过Java代码在LayoutHelper
层进行UI设计约束
;
item
层可以通过在adapter.java
中用java代码或者在xml
中进行UI设计约束
;
其中xml
记得巧用drawable文件
设计: