博客转移到个人站点:
http://www.wangchengmeng.club/2018/02/04/RecyclerView%E4%BC%98%E9%9B%85%E7%9A%84%E6%B7%BB%E5%8A%A0Header%E5%92%8CFooter/
欢迎来吐槽
装饰模式:再现有类的基础上,对它进行包装从而对功能对增强。这里简单实现对RecyclerView的Adapter进行装饰,从而简单实现对RecylerView增加Header和Footer。
核心思想也是利用getItemViewType()方法,可以返回多种不同类型的View。
不影响原有的功能,使使用起来跟原生的Adapter方式一样,新建一个WrapperAdapter,继承自RecyclerView.Adapter<RecyclerView.ViewHolder>
1.声明一个枚举:包含三种类型
private enum ITEM_TYPE {
HEADER, //头部
FOOTER, //尾部
NORMAL//正文
}
2.构造函数,将使用的adapter作为参数传递进来:
public WrapperAdapter(RecyclerView.Adapter adapter) {
mAdapter = adapter;
}
3.添加-删除Header和Footer的方法
public void addFooter(View footerView) {
mFooterView = footerView;
notifyDataSetChanged();
}
public void removeFooter() {
if (hasFooter()) {
mFooterView = null;
notifyDataSetChanged();
}
}
public void addHeader(View headerView) {
mHeaderView = headerView;
}
private boolean hasHeader() {
return null != mHeaderView;
}
private boolean hasFooter() {
return null != mFooterView;
}
4.getItemViewType方法:
@Override
public int getItemViewType(int position) {
int count = mAdapter.getItemCount();//获取除 中间部分的数据条数
if (hasHeader()) {
count++; //如果带了header 那就+1
}
if (hasHeader() && position == 0) {
return ITEM_TYPE.HEADER.ordinal(); //返回header类型
} else if (hasFooter() && position == count) {
return ITEM_TYPE.FOOTER.ordinal(); //返回footer类型
} else {
return ITEM_TYPE.NORMAL.ordinal(); //返回normal类型
}
}
5.获取数据的数量:
@Override
public int getItemCount() {
int count = mAdapter.getItemCount();
if (hasHeader()) {
count++;
}
if (hasFooter()) {
count++;
}
return count; //获取数据的数目,要加上对应的带header和footer的条数
}
6.返回ViewHolder:
@Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
//根绝不同的类型处理对应的ViewHolder
if (viewType == ITEM_TYPE.HEADER.ordinal()) {
return new RecyclerView.ViewHolder(mHeaderView) {
};
} else if (viewType == ITEM_TYPE.FOOTER.ordinal()) {
return new RecyclerView.ViewHolder(mFooterView) {
};
} else {
return mAdapter.onCreateViewHolder(parent, viewType);
}
}
7.数据处理的逻辑:
@Override
public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
if (hasHeader() && position == 0) {
//header的逻辑分离开来,在外部处理
return;
}
int count = mAdapter.getItemCount();
if (hasHeader()) {
count++;
}
if (hasFooter()) {
count++;
}
if (hasFooter() && position == count - 1) {
//footer的逻辑分离开来,在外部处理
return;
}
//normal的逻辑还是不变,跟原生的一样处理,在传递进来的adapter中
if (hasHeader()) {
mAdapter.onBindViewHolder(holder, position - 1);
} else {
mAdapter.onBindViewHolder(holder, position);
}
}
一个简单的添加header和footer就这样装饰出来了,对一个现有的类对它进行一个功能争强,可以利用持有它的引用,原来的操作不变的基础上添加对应的功能。