目录
- 点击事件
- 添加、删除数据
- 更丰富的条目展示(多条目展示)
- 添加header 、footer
- 下拉刷新、上拉加载更多
进阶一:点击事件、长按事件(实现adapter和Activity之间的通信)
RecyclerView要实现点击事件和长按事件可以在适配器中定义接口事件回调
1、定义对象
private OnItemClickListener mOnItemClickListener;
2、写接口,并定义方法
/**
* 通过在adapter定义接口实现回调
*/
public interface OnItemClickListener {
//点击事件
void onItemClick(View view, int position);
//长按点击事件
void onItemLongClick(View view, int position);
}
3、
public void setOnItemClickListener(OnItemClickListener mOnItemClickListener) {
this.mOnItemClickListener = mOnItemClickListener;
}
4、在adapter需要的地方调用事件
if (mOnItemClickListener != null) {
mOnItemClickListener.onItemClick(((ContentViewHolder) holder).llLayout, position - 1);
}
if (mOnItemClickListener != null) {
mOnItemClickListener.onItemLongClick(((ContentViewHolder) holder).llLayout, position - 1);
}
5、Activity调用Adapter中的事件
recyclerViewAdapter.setOnItemClickListener(new RecyclerViewAdapter.OnItemClickListener() {
@Override
public void onItemClick(View view, int position) {
Toast.makeText(RecycleActivity.this, "点击了第" + position + "条", Toast.LENGTH_SHORT).show();
}
@Override
public void onItemLongClick(View view, int position) {
Toast.makeText(RecycleActivity.this, "长按了第" + position + "条", Toast.LENGTH_SHORT).show();
}
});
进阶二:添加数据、删除某条数据
这里需要了解到刷新界面的多种方式
notifyDataSetChanged();//刷新整体布局
notifyItemChanged(position);//刷新指定position,会重新调用onBindViewHolder来进行刷新,如果当前position在屏幕之外,则不会调用,当重新滚动到屏幕内,会重新调用
notifyItemRangeChanged(position, 10);//刷新从position开始之后10条数据
notifyItemInserted(position);//在第position处插入数据,这个插入时会有动画
notifyItemMoved(position,5);//将当前position移动到position为5的地方,并且刷新
notifyItemRangeInserted(3,10);//批量增加
notifyItemRemoved(position);//删除第position条数据
notifyItemRangeRemoved(position, 10);//批量删除
/**
* 删除某条数据
*
* @param position
*/
public void removeData(int position) {
mList.remove(position);
notifyItemRemoved(position);
notifyItemRangeChanged(position, mList.size());
}
/**
* 在指定position添加数据
*
* @param position
*/
public void addData(int position, String msg) {
if (mList == null) {
mList = new ArrayList<>();
}
if (position < mList.size()) {
//说明这里是第一条
mList.add(position, msg);
} else {
mList.add(msg);
position = mList.size() - 1;
}
notifyItemInserted(position);
notifyItemRangeChanged(position, mList.size());
}
问题一:长按事件、点击事件同时发生
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-F5gkIlym-1580817649921)(//upload-images.jianshu.io/upload_images/15649819-5d960683419a4173.gif?imageMogr2/auto-orient/strip|imageView2/2/w/360/format/webp)]
解决思路
在public boolean onLongClick(View v) {return true}
需要消费掉这个长按事件 返回true
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OMX7x7VO-1580817649922)(//upload-images.jianshu.io/upload_images/15649819-c63ab1c56a29a8c6.gif?imageMogr2/auto-orient/strip|imageView2/2/w/360/format/webp)]
进阶三:添加header、footer
思路
1、首先要区分头布局、中间布局、尾布局三种不同的type,通过设置一个int值来判断不同的布局
2、通过getItemViewType来返回type
3、在onCreateViewHolder中根据不同的viewType显示不同的布局
4、在onBindViewHolder根据不同的holder加载不同的数据
注意
1、getItemCount这里需要返回的集合的数量+header数量+footer数量
2、当content布局中加载数据是通过position获取数据时需要将
position-1
1、添加三种不同的type来区分不同的布局
public static final int ITEM_TYPE_CONTENT = 0;
public static final int ITEM_TYPE_FOOTER = 1;
public static final int ITEM_TYPE_HEADER = 2;
2、添加头、尾布局数量
private int footerCount = 1;
private int headerCount = 1;
3、根据position获取Item的类型
@Override
public int getItemViewType(int position) {
if (isHeaderView(position)) {
return ITEM_TYPE_HEADER;
} else if (isFooterView(position)) {
return ITEM_TYPE_FOOTER;
} else {
return ITEM_TYPE_CONTENT;
}
}
4、根据不同的viewType显示不同的布局
@NonNull
@Override
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup viewGroup, int viewType) {
/**
* 主要负责把加载子项的布局
* 将xml定义的布局实例化为view对象
*/
if (viewType == ITEM_TYPE_FOOTER) {
View view = LayoutInflater.from(mContext).inflate(R.layout.recycler_footer_item, viewGroup, false);
return new FooterViewHolder(view);
} else if (viewType == ITEM_TYPE_HEADER) {
View view = LayoutInflater.from(mContext).inflate(R.layout.recycler_header_item, viewGroup, false);
return new HeaderViewHolder(view);
} else if (viewType == ITEM_TYPE_CONTENT) {
View view = LayoutInflater.from(mContext).inflate(R.layout.recyclerview_item, viewGroup, false);
return new ContentViewHolder(view);
}
return