对RecyclerView的ViewType的使用以及添加Foot和Head的心得
来源:互联网 发布:适合程序员的壁纸 编辑:程序博客网 时间:2024/06/05 03:09
楼主小菜鸡,最近写recycleView碰到了对foot和head的需求.楼主以前用recycleView都是像ListView一样的写法,对viewType的使用还不够深入,这次掉坑里狠狠地悟了一波.先说说坑:之前写foot还挺简单的,但是当写head的时候碰到一个问题.head的position会和Normal的position发生一定的冲突.(主要还是代码不够严谨)这个bug卡了很久,最后一点点细细地解耦核查,总算是解决了,这里发个博客记录一下.这里我将head和foot作为View通过set方法.从外部传进来,将其ViewHolder也作为外部类来传进来,同时也方便复用.重点是代码简洁许多.直接上代码吧,总结放结尾好了.setFoot这样看起来挺像listView的:)
public class TestAdapter extends RecyclerView.Adapter {
private static final int TYPE_NORMAL = 0; //Item Viewprivate static final int TYPE_FOOTER = 1; //FootViewprivate static final int TYPE_HEADER = 2; //HeadViewpublic static final int SKIP_TRACKS_TYPE = 233;private int load_more_status = 0;//上拉加载更多状态-默认为0private List<Track> tracks = new ArrayList<>();private Album album;//头部的数据private View mHeaderView;//头部的控件,用set方法在外部设置private View mFooterView;//尾部的控件,用set方法在外部设置public void setHeaderView(View headerView) { mHeaderView = headerView; notifyItemInserted(0);}public View getHeaderView() { return mHeaderView;}public View getFooterView() { return mFooterView;}public void setFooterView(View mFooterView) { this.mFooterView = mFooterView;}private int getHeadViewCount() { return mHeaderView == null ? 0 : 1;}private int getFootViewCount() { return mFooterView == null ? 0 : 1;}private int width;private AlbumsRecyclerItemClickListener itemClickListener;public TestAdapter(List<Track> tracks, Album album, AlbumsRecyclerItemClickListener itemClickListener, int width) { this.width = width; this.album = album; this.itemClickListener = itemClickListener; this.tracks = tracks;}@Overridepublic RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {//在oncreate的时候分辨type来分配holder if (viewType == TYPE_HEADER) return new AlbumsTrackHeadViewHolder(mHeaderView); if (viewType == TYPE_FOOTER) return new AlbumsTrackFootViewHolder(mFooterView); View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.item_recycler_album_track, parent, false); return new AlbumsTrackViewHolder(view);}@Overridepublic void onBindViewHolder(RecyclerView.ViewHolder holder, final int position) {//之前看了某同学的代码,他这边用的是viewType == TYPE来进行判断.结果可能不够严谨,在强转的时候发生了错误.这边用instanceof就解决了这个问题 if (holder instanceof AlbumsTrackHeadViewHolder) { setHeadHolder(holder); return; } if (holder instanceof AlbumsTrackFootViewHolder) { setFootHolder(holder); return; } setNormalHolder(holder);}@Overridepublic int getItemViewType(int position) { if (position < getHeadViewCount()) return TYPE_HEADER; if (position >= tracks.size() + getHeadViewCount()) return TYPE_FOOTER; return TYPE_NORMAL;}@Overridepublic int getItemCount() { return tracks.size() + getHeadViewCount() + getFootViewCount();}private int getRealPosition(RecyclerView.ViewHolder holder) { int position = holder.getLayoutPosition(); return mHeaderView == null ? position : position - 1;}public void changeMoreStatus(int status) { load_more_status = status; notifyDataSetChanged();}public void addMoreItem(List<Track> newDatas) { tracks.addAll(newDatas); notifyDataSetChanged();}private void setNormalHolder(RecyclerView.ViewHolder holder) {//设置主体的内容 AlbumsTrackViewHolder albumHolder = (AlbumsTrackViewHolder) holder; final int pos = getRealPosition(albumHolder); if (tracks.size() != 0) { albumHolder.tvTitle.setText(tracks.get(pos).getTrackTitle()); final String intro = tracks.get(pos).getTrackIntro(); if (intro.equals("")) { albumHolder.tvContent.setVisibility(View.GONE); } else { albumHolder.tvContent.setVisibility(View.VISIBLE); albumHolder.tvContent.setText(intro); } if (tracks.get(pos).getCoverUrlMiddle().length() != 0) { Glide.with(albumHolder.ivTitlePic.getContext()).load(tracks.get(pos).getCoverUrlMiddle()).into(albumHolder.ivTitlePic); } albumHolder.tvPlayCount.setText(TextUtils.getThousand(tracks.get(pos).getPlayCount())); albumHolder.tvEstimatedTrackCount.setText(TextUtils.getMinutes(tracks.get(pos).getDuration())); albumHolder.llItemAlbum.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { } }); }}private void setHeadHolder(RecyclerView.ViewHolder holder) {//设置head的具体内容 AlbumsTrackHeadViewHolder headViewHolder = (AlbumsTrackHeadViewHolder) holder; headViewHolder.tvTrackHeadTitle.setText(album.getAlbumTitle()); headViewHolder.tvTrackHeadIntroduce.setText(album.getAlbumIntro()); Glide.with(headViewHolder.ivTrackHeadIcon.getContext()).load(album.getCoverUrlMiddle()).into(headViewHolder.ivTrackHeadIcon);}private void setFootHolder(RecyclerView.ViewHolder footViewHolder) {//设置foot的具体内容 AlbumsTrackFootViewHolder headViewHolder = (AlbumsTrackFootViewHolder) footViewHolder; switch (load_more_status) { case AlbumRecyclerAdapter.PULLUP_LOAD_MORE: headViewHolder.tvFootLording.setText("上拉加载更多..."); break; case AlbumRecyclerAdapter.LOADING_MORE: headViewHolder.progressBar.setVisibility(View.VISIBLE); headViewHolder.tvFootLording.setText("正在加载更多数据..."); break; case AlbumRecyclerAdapter.NO_CONTENT: headViewHolder.tvFootLording.setText("已无更多内容"); headViewHolder.progressBar.setVisibility(View.INVISIBLE); break; }}private class AlbumsTrackViewHolder extends RecyclerView.ViewHolder { private TextView tvTitle; private TextView tvContent; private TextView tvPlayCount; private TextView tvEstimatedTrackCount; private ImageView ivTitlePic; private LinearLayout llItemAlbum; AlbumsTrackViewHolder(View itemView) { super(itemView); if (itemView == mHeaderView) return; if (itemView == mFooterView) return; llItemAlbum = (LinearLayout) itemView.findViewById(R.id.llItemAlbum); ivTitlePic = (ImageView) itemView.findViewById(R.id.ivTitlePic); tvTitle = (TextView) itemView.findViewById(R.id.tvTitle); tvContent = (TextView) itemView.findViewById(R.id.tvContent); tvPlayCount = (TextView) itemView.findViewById(R.id.tvPlayCount); tvEstimatedTrackCount = (TextView) itemView.findViewById(R.id.tvEstimatedCount); tvEstimatedTrackCount.setMaxWidth((int) (width * 0.8)); tvPlayCount.setMaxWidth((int) (width * 0.8)); }}
}
总结:第一.既然加了Foot和Head.一定不要忘了修改整体count的数量.否则肯定会出现数组越界报错.
第二.head和foot都是通过判断position的位置来进行锁定的,所以在getItemViewType的时候一定要仔细.同时,不要忘了,既然都是通过position来锁定位置,那么主体的内容就不能直接通过position来粗暴地确定了(会被head或者foot给挤开).
在之前就是因为我的不严谨导致了头部占了第一位,然后主体内容变成了第二个,然后到底部就数组越界了.担心算错position,最好封装一个方法用于确定主体里要用到的数据的position.有什么写的不好地方欢迎大家指出,我们共同成长:)
阅读全文
0 0
- 对RecyclerView的ViewType的使用以及添加Foot和Head的心得
- android recyclerview 关于viewtype的使用
- php的head.php和foot.php
- android 使用RecyclerView ViewType创建不同的item
- 为RecyclerView瀑布流添加foot时的一些问题
- RecyclerView的使用心得
- ListView的多种ViewType
- 让UIRTableView 的head和foot 不浮动在页面上
- 不滚动的listView(解决带head foot 计算)
- RecyclerView 添加head view头部 和foot view尾部、设置水平horizontal时左侧布局和右侧布局
- RecyclerView的使用心得记录
- RecyclerView和CardView的使用以及注意
- 关于UICollectionViewController的header和foot视图
- Android 多种ViewType的ListView
- 对RecyclerView的item添加点击事件
- RecyclerView添加head和footer
- RecyclerView的使用(3)之添加Header和Footer
- RecyclerView的使用(3)之添加Header和Footer
- iOS 绘制 cell --- 新手学习笔记
- mybatis动态sql中的trim标签的使用
- C/C++的inline函数解释
- MachineLearning-DeepLearning-Neural Network
- RecylerView:no adapter attached;skipping layout
- 对RecyclerView的ViewType的使用以及添加Foot和Head的心得
- 线程互斥锁与死锁
- 适合初学者看的RxJava2教程
- javascript 常用DOM操作整理
- UrlRewrite重写url
- Oracle使用子查询创建表
- Hibernate HQL 查询Set数据
- linux vmware虚拟机中的ubuntu扩大磁盘分区
- ORA -02020 错