欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android RecyclerView点击事件

程序员文章站 2023-12-20 11:25:22
一、概述 随着android l版本的发布,recyclerview已经逐渐地取代了listview,用来显示较多的数据集,recyclerview相比listvie...

一、概述

随着android l版本的发布,recyclerview已经逐渐地取代了listview,用来显示较多的数据集,recyclerview相比listview在性能上有了大幅度的提升,可以说recyclerview是abslistview的升级版本。recyclerview自带了viewholder使用,与listview缓存convertview不同的是,recyclerview缓存的是viewholder,操作对象也是viewholder。虽然listview也带有缓存convertview的功能,但是当使用listview时,显示、缓存、回收、布局等都是耦合在一起的;而recyclerview对其进行了解耦,操作更灵活,使得开发者可以更好的自定义各种各样的效果,另外recyclerview假如了局部刷新。关系如下图所示:

Android RecyclerView点击事件

二、基本使用

recyclerview提供了下面几种角色
1.recyclerview.adapter    适配器
2.recyclerview.layoutmanager  布局器,用于管理布局显示,官方提供以下几种方式

linearlayoutmanager   显示垂直或水平滚动的列表项
gridlayoutmanager      以网格方式显示
staggeredgridlayoutmanager   以交错网格显示

同时,开发者也可以自定义layoutmanager,继承recyclerview.layoutmanager。

3.recycler.itemdecoration 每个item附加的子视图,可用来绘制divider,设置padding等
4.recyclerview.itemanimator 负责添加、删除数据时的动画效果

具体的使用方法见 官方文档

项目中使用

activity中

protected void oncreate(bundle savedinstancestate) { 
  super.oncreate(savedinstancestate); 
  setcontentview(r.layout.activity_main); 
 
  initview(); 
 } 
 
 private void initview() { 
  recyclerview = (recyclerview) findviewbyid(r.id.rv); 
  // use this setting to improve performance if you know that changes 
  // in content do not change the layout size of the recyclerview 
  recyclerview.sethasfixedsize(true); 
  // use a linear layout manager 
  linearlayoutmanager ll = new linearlayoutmanager(this); 
  recyclerview.setlayoutmanager(ll); 
  initializedata(); 
  recycleradapter = new recycleradapter(persons); 
  recyclerview.setadapter(recycleradapter); 
 
 } 
 
 
 private void initializedata(){ 
  persons = new arraylist<>(); 
  persons.add(new person("emma wilson", "23 years old", r.mipmap.ic_launcher)); 
  persons.add(new person("lavery maiss", "25 years old", r.mipmap.ic_launcher)); 
  persons.add(new person("lillie watts", "35 years old", r.mipmap.ic_launcher)); 
 } 

自定义adapter

public class recycleradapter extends recyclerview.adapter<recycleradapter.viewholder>{ 
 private list<person> list; 
 
 public recycleradapter(list<person> list) { 
  this.list = list; 
 } 
 
 //为viewholder设置数据 
 @override 
 public viewholder oncreateviewholder(viewgroup parent, int viewtype) { 
  view view = layoutinflater.from(parent.getcontext()).inflate(r.layout.item, parent, false); 
  viewholder viewholder = new viewholder(view); 
  return viewholder; 
 } 
 
 @override 
 public void onattachedtorecyclerview(recyclerview recyclerview) { 
  super.onattachedtorecyclerview(recyclerview); 
 } 
 
 //用于创建viewholder 
 @override 
 public void onbindviewholder(viewholder holder, int position) { 
  person person = list.get(position); 
  holder.nametv.settext(person.name); 
  holder.agetv.settext(person.age); 
  holder.imageview.setimageresource(person.photoid); 
 } 
 
 @override 
 public int getitemcount() { 
  return list.size(); 
 } 
 
 // 删除指定的item 
 public void removedata(int position) 
 { 
  list.remove(position); 
  // 通知recyclerview控件某个item已经被删除 
  notifyitemremoved(position); 
 
 } 
 // 在指定位置添加一个新的item 
 public void additem(person person,int positiontoadd) 
 { 
  list.add(person); 
  // 通知recyclerview控件插入了某个item 
  notifyiteminserted(positiontoadd); 
 } 
 
 public class viewholder extends recyclerview.viewholder { 
  textview nametv; 
  textview agetv; 
  imageview imageview; 
  public viewholder(view itemview) { 
   super(itemview); 
   nametv = (textview) itemview.findviewbyid(r.id.name); 
   agetv = (textview) itemview.findviewbyid(r.id.age); 
   imageview = (imageview) itemview.findviewbyid(r.id.avater); 
  } 
 } 
} 

item动画如有需要可以自己手动添加,这个不是今天的重点,这里附上两个不错的开源项目 这里 和 这里

recyclerview的点击事件

官方文档中并没有给我们类似listview的onitemclicklistener回调方法,由于recyclerview比listview更高级,所以它并没有行或者列的概念,子view可以任意布局,每个子view处理自己的onclick事件,也就是说在adapter中给子view的rootview设置点击回调。
我们今天所要实现的是另外一种方式,类似listview的onitemclicklistener的方式。通过文档我们知道recyclerview留给开发者一个recyclerview.onitemtouchlistener接口,我们要做的就是实现它,实现点击的回调和长按回调。当然了,这种方式只是一个开始,我们还可以拓展为各种复杂的手势操作的回调

public class recycleritemclicklistener implements recyclerview.onitemtouchlistener{ 
 private view childview; 
 private recyclerview touchview; 
 public recycleritemclicklistener(context context, final onitemclicklistener mlistener) { 
  mgesturedetector = new gesturedetector(context, new gesturedetector.simpleongesturelistener(){ 
   @override 
   public boolean onsingletapup(motionevent ev) { 
    if (childview != null && mlistener != null) { 
     mlistener.onitemclick(childview, touchview.getchildposition(childview)); 
    } 
    return true; 
   } 
   @override 
   public void onlongpress(motionevent ev) { 
    if (childview != null && mlistener != null) { 
     mlistener.onlongclick(childview, touchview.getchildposition(childview)); 
    } 
   } 
  }); 
 } 
 
 gesturedetector mgesturedetector; 
 
 public interface onitemclicklistener { 
  public void onitemclick(view view, int position); 
  public void onlongclick(view view, int posotion); 
 } 
 
 @override 
 public boolean onintercepttouchevent(recyclerview recyclerview, motionevent motionevent) { 
  mgesturedetector.ontouchevent(motionevent); 
  childview = recyclerview.findchildviewunder(motionevent.getx(), motionevent.gety()); 
  touchview = recyclerview; 
  return false; 
 } 
 
 @override 
 public void ontouchevent(recyclerview recyclerview, motionevent motionevent) { 
 
 } 
} 

我们在onintercepttouchevent的方法中注册了手势操作,当有特定的手势的时候我们就可以通过simplegesturelistener回调接口接收到,其中我们实现了 点击和长按,然后回调我们自己定义的接口。使用也很简单

recyclerview.addonitemtouchlistener(new recycleritemclicklistener(this, 
    new recycleritemclicklistener.onitemclicklistener() { 
   @override 
   public void onitemclick(view view, int position) { 
    log.d(tag, "onitemclick : postion " + position); 
   } 
 
   @override 
   public void onlongclick(view view, int posotion) { 
    log.d(tag, "onlongclick position : " + posotion); 
   } 
  })); 

对于手势操作我们可以定义更多用于对itemview的操作回调。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。

上一篇:

下一篇: