带HeaderView和FooterView的自定义RecyclerView.Adapter
来源:互联网 发布:房地产横盘 知乎 编辑:程序博客网 时间:2024/06/08 11:43
– 实现类似于listView中的addHeaderView方法和addFooterView方法
序言
今天要给大家介绍的是自定义的RecyclerView.Adapter,名字叫做 BaseHeadFootAdapter,通过这个Adapter你可以像ListView一样在RecyclerView中直接添加HeaderView和FooterView,你只需要写下面几行代码。
//MyBaseHeadFootAdapter继承自BaseHeadFootAdapter adapter=new MyBaseHeadFootAdapter(this,list); adapter.addHeaderView(headView); adapter.addFooterView(footView); recyclerView.setAdapter(adapter);
然后你就可以实现这样的效果
使用
如果你只是单纯的想使用,你可以直接点击进入下面的gitHub,你可以看到如何使用它(博客后边其实也有交代),如果你有任何疑问,欢迎关注我的微博同我交流。如果我的项目对你有一丢丢帮助的话,记得star或者follow我哦!
GitHub地址: 自定义HeadFootAdapter
微博:蝎子莱莱的微博
在使用ListView的过程中有两个方法很常用到,那就是ListView中的addHeaderView()和addFooterView(),他们的作用显而易见,那就是在你的listView中添加特殊的两个布局,一个是在顶端,另一个会在底端。如果你没有使用过它们可能会有点好奇,直接把这些布局放在listView上面不就行了吗,为什么非要把它添加到listView里面去呢?
这是因为有这样一种情况我们经常会遇到,下面是京东的一张截图,如果让你去实现这样一个布局你会怎么做呢?
你可能会这样做:最外面是一个ScrollView,上面是三张图片那个布局,下面是一个ListView。当然,这样是肯定不行的,你会发现ScrollView和ListView是会滑动冲突的,具体的解决方案你可以看这篇方案
四种方案解决ScrollView嵌套ListView问题
里面提到一种方案和我今天说的很类似,但是不一样,上面说你可以将顶部的布局当成是一种item,因为ListView中的adapter是支持多种type的。但是我个人觉得这种方法并不是很优美,只是一个头部VIew却让你的adapter中代码变得很臃肿,我个人更加倾向于将这个布局放在HeaderView中,你不需要改变adapter中的代码,只需要在Activity中引用添加这个View就好了。
但是RecyclerView的出现是对ListView是一个很大的威胁,RecyclerView上有着太多超越ListView的地方,现在更多是推荐使用RecyclerView,二者的区别这里我们不细讨论,你可以参考下面这篇博客
Android控件RecyclerView和ListView的异同
如果你不是很了解RecyclerView,你可以参考下面这篇博文
RecyclerView:更高级更灵活的ListView
但是RecyclerView也不是完美的,在RecyclerView中很多ListView有的功能它反而没有,比如setOnItemClickListener(),当然这个可以你自己来写,难度并不是很大。还有的就是今天我们要说的addHeaderView()和addFooterView(),所以我自己实现了一个RecyclerView的Adapter,通过这个adapter,你可以像ListView一样 直接使用addHeaderView和addFooterView两个方法。
实现
好了,重点来了,说说代码是如何实现的。其实实现非常简单,聪明的你一定也已经想到了。思路就是,其实在RecyclerView中也是支持Adapter中存在多种type的item的,那么我们可以把HeaderView和FooterView当做两种不同的type,我们要做的事情就是想办法将其封装起来,当在项目中使用时,你根本不会感觉到它们的存在,你要做的只是添加addHeaderView()或者addFooterView()而已。
BaseHeadFootAdapter是一个抽象类,你需要继承它并且实现它的几个函数就可以了,这几个函数基本和RecyclerView.Adapter一毛一样(我本来就是做的一点封装)
/** * 将头部布局返回到用户继承之后的子类中, * * 用户可以这个方法里得到headerVIew,对其进行操作 * * 比如说headerView中的各种点击事件以及headerView中各种控件的获取 * * * @param headerView */ protected abstract void onBindHeaderView(View headerView); /** * 将尾部布局返回到用户继承之后的子类中, * * 用户可以这个方法里得到footerVIew,对其进行操作 * * 比如说headerView中的各种点击事件以及headerView中各种控件的获取 * * * @param footerView */ protected abstract void onBindFooterView(View footerView); /** * 获取子类中item的个数 * @return */ protected abstract int getItemNum(); /** * 子类需继承的方法之一,和onBindViewHolder方法是一样的 * * 在这里我进行了封装 * * * @param holder * @param position */ protected abstract void onBindView(RecyclerView.ViewHolder holder, int position); /** * 子类需继承的方法之一,和onCreateViewHolder一样 * * 这里只是进行了封装 * * * @param parent * @param viewType * @return */ protected abstract RecyclerView.ViewHolder onCreateHolder(ViewGroup parent, int viewType);
仔细看着几个方法,其实getItemNum()就是RecyclerView.Adapter
中的getItemCount(),onBindView(···)就是onBindViewHolder(···),
getViewType()就是getItemViewType(),这三个方法也是继承Adapter必须要实现的方法。而另外两个onBindHeaderView(View headerView),onBindFooterView(View footerView)是之前没有的,用户可以在这两个方法中获取自己设置的headerView或者footerView,并且使用它们(比如设置点击事件或者设置view中控件的值)
前面提到的我在这个类中做了封装,这里我们拿onCreateViewHolder举例,看下面的代码
@Override public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { if(viewType==HEAD_TYPE){ return new HeadFooterViewHolder(headerView); }else if(viewType==FOOT_TYPE){ return new HeadFooterViewHolder(footerView); }else //如果不是头布局和尾部局,那么就使用子类中的onCreateHolder方法中指定的ViewHolder return onCreateHolder(parent, viewType); }
其实你就会很清楚,如果是HeaderView我就创建HeaderView的viewHolder,如果是普通的item就使用用户实现的onCreateHolder(···)来创建,因为这个方法是个虚函数,是用户实现的。其他的两个方法也是同样的道理分装起来的,我就不再赘述,感兴趣的话你可以查看我的源码。
使用
使用起来的话也非常简单,你只需要将我的BaseHeadFootAdapter类拷贝的你项目中,并且继承它实现它的几个方法即可。和你使用原生的RecyclerView.Adapter是完全一样的,你的item也可以有多种type,但是要记得type值不要是-100和-101(已经被HeaderView和FooterView占用了)。最后你只需在你自己的Adapter中调用方法即可。
adapter.addHeaderView(headView); adapter.addFooterView(footView);
这样你就可以在你的Adapter(继承自BaseHeadFootAdapter)中对header和FooterView进行操作,下面以HeaderView为例
@Override protected void onBindHeaderView(View headerView) { headerView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { Toast.makeText(context,"head was clicked",Toast.LENGTH_SHORT).show(); } }); }
其实,只要你掌握了RecyclerView的基本用法很快就可以使用这个自定义的Adapter,我gitHub中那个project是一个使用了这个Adapter的例子,你可以参考一下,其中MyBaseHeadFootAdapter是继承自BaseHeadFootAdapter的Adapter类,MyViewHolder是item的viewHolder(和RecyclerView的标准写法是一样的)。
最后,还是将github和我的微博贴出来,欢迎大家和我交流学习。谢谢!
GitHub地址: 自定义HeadFootAdapter
微博:蝎子莱莱的微博
- 带HeaderView和FooterView的自定义RecyclerView.Adapter
- 一个给RecyclerView添加HeaderView FooterView的装饰Adapter类
- RecyclerView添加HeaderView和FooterView
- RecyclerView添加HeaderView和FooterView
- RecyclerView添加HeaderView和FooterView
- RecyclerView 添加headerView 和 footerView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- Android 优雅的为RecyclerView添加HeaderView和FooterView
- tomcat报错org.springframework.web.context.ContextLoaderListener找不到
- 找出整数数组中两两相加等于key的整数对
- 火车站调度问题
- 【超强教程】python在64位操作系统下的安装
- 利用Nginx模拟搭建服务器集群
- 带HeaderView和FooterView的自定义RecyclerView.Adapter
- 下载android环境
- 《R语言实战》读后感
- 删除大整数中的给定个数的数,要求得到的数值最大
- 关于struts2的通配符问题
- [JavaEE - JPA] 3. Spring Framework中的事务管理
- [JavaEE - JPA] 4. EntityManager相关核心概念
- Android中的Binder机制的简要理解
- 实现add方法,add(2,3)、add(2)(3)都返回5