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

Android的ListView多选删除操作实现代码

程序员文章站 2024-03-02 22:51:46
最近尝试做了个listview的多选demo,网上看其他人的例子感觉不是很难,自己动手做了下,各种细节问题,没那么简单啊。既然做了,简单写个笔记记录下。 练手demo,...

最近尝试做了个listview的多选demo,网上看其他人的例子感觉不是很难,自己动手做了下,各种细节问题,没那么简单啊。既然做了,简单写个笔记记录下。
练手demo,命名笔记乱,不要介意哦。

Android的ListView多选删除操作实现代码

Android的ListView多选删除操作实现代码

主界面布局activity_main.xml

<relativelayout xmlns:android="http://schemas.android.com/apk/res/android"
 xmlns:tools="http://schemas.android.com/tools"
 android:layout_width="match_parent"
 android:layout_height="match_parent"
 android:id="@+id/rootview"
 android:paddingbottom="@dimen/activity_vertical_margin"
 android:paddingleft="@dimen/activity_horizontal_margin"
 android:paddingright="@dimen/activity_horizontal_margin"
 android:paddingtop="@dimen/activity_vertical_margin"
 tools:context="com.example.listchecked.mainactivity" >

 <listview
  android:id="@+id/listview1"
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_marginbottom="50dp"
  >

 </listview>

 <linearlayout
  android:id="@+id/button_group"
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_alignleft="@+id/listview1"
  android:layout_alignparentbottom="true"
  android:orientation="vertical" >

  <button
   android:id="@+id/del"
   android:layout_width="wrap_content"
   android:layout_height="wrap_content"
   android:text="删除" />
 </linearlayout>

</relativelayout>

列表item的布局

<?xml version="1.0" encoding="utf-8"?>
<linearlayout xmlns:android="http://schemas.android.com/apk/res/android"
 android:layout_width="match_parent"
 android:layout_height="match_parent"
 android:orientation="horizontal"
 android:descendantfocusability="blocksdescendants" >
<!--注意上面这个属性,很关键,不加会导致list无法响应onitemclicklistener中的事件-->

 <relativelayout
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:layout_weight="1" 
  >

  <checkbox
   android:id="@+id/checkbox1"
   android:layout_width="wrap_content"
   android:layout_height="wrap_content"
   android:clickable="false"
   android:focusable="false" />

  <imageview
   android:id="@+id/imageview1"
   android:layout_width="match_parent"
   android:layout_height="match_parent"
   android:scaletype="fitcenter"
   android:src="@drawable/ic_launcher" />

 </relativelayout>

 <linearlayout
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:layout_weight="1"
  android:gravity="center"
  android:orientation="vertical" >

  <textview
   android:id="@+id/title"
   android:layout_width="match_parent"
   android:layout_height="wrap_content"
   android:text="title"
   android:textsize="20sp" />

  <textview
   android:id="@+id/teacher"
   android:layout_width="match_parent"
   android:layout_height="wrap_content"
   android:text="teacher" />

  <textview
   android:id="@+id/time"
   android:layout_width="match_parent"
   android:layout_height="wrap_content"
   android:text="time" />

  <textview
   android:id="@+id/peoplenum"
   android:layout_width="match_parent"
   android:layout_height="wrap_content"
   android:text="peoplenum"
    />

 </linearlayout>

</linearlayout>

这个item的布局就被在细节上坑了一次,item中添加button,checkbox,imagebutton等时,会导致只响应这些控件的事件,item整体的事件就不会响应了,刚开始没有加那条属性,勾选checkbox后,点删除没有反应。这问题要发现也有点难度,之前见大神们推荐过分析布局的工具hierarchyviewer,这个工具,个人感觉和前端开发中的f12类似啊,很方便,可以看到每个布局的情况。也是好奇,点开一看,整个item的布局,从父布局,到子布局,只要checkbox可以接受click,其他全部是false,这就是问题所在了,后来百度了一下,即如上结论。

解决办法就是添加android:descendantfocusability=”blocksdescendants” 到list的item的布局里,添加以后,发现checkbox还是可以被单独点击,不响应list的点击选中事件,很是奇怪,看其他人的例子中就没有这种现象。最后只能设置checkbox不能被点击 android:clickable=”false” 布局问题解决了,下面是java类的源码:
首先是bean类,itembean.java

package com.example.listchecked;


public class itembean {
 private int imgres;
 private string title,teacher,time;
 private int peoplenum,id;
 private boolean ischecked;
 private boolean isshow;

 public boolean isshow() {
  return isshow;
 }
 public void setshow(boolean isshow) {
  this.isshow = isshow;
 }
 public int getid() {
  return id;
 }
 public void setid(int id) {
  this.id = id;
 }
 public boolean ischecked() {
  return ischecked;
 }
 public void setchecked(boolean ischecked) {
  this.ischecked = ischecked;
 }
 public int getimgres() {
  return imgres;
 }
 public void setimgres(int img) {
  this.imgres = img;
 }
 public string gettitle() {
  return title;
 }
 public void settitle(string title) {
  this.title = title;
 }
 public string getteacher() {
  return teacher;
 }
 public void setteacher(string teacher) {
  this.teacher = teacher;
 }
 public string gettime() {
  return time;
 }
 public void settime(string time) {
  this.time = time;
 }
 public int getpeoplenum() {
  return peoplenum;
 }
 public void setpeoplenum(int peoplenum) {
  this.peoplenum = peoplenum;
 }

}

自定义的adapter,mylistadapter.java

package com.example.listchecked;

import java.util.list;

import android.content.context;
import android.view.layoutinflater;
import android.view.view;
import android.view.viewgroup;
import android.widget.baseadapter;
import android.widget.checkbox;
import android.widget.compoundbutton;
import android.widget.compoundbutton.oncheckedchangelistener;
import android.widget.imageview;
import android.widget.textview;

public class mylistadapter extends baseadapter
{
 private layoutinflater inflater;
 private list<itembean> items;
 private itembean item;
 private onshowitemclicklistener onshowitemclicklistener;

 public mylistadapter(list<itembean> list,context context)
 {
 items=list;
 inflater=layoutinflater.from(context);
 }
 @override
 public int getcount() {
 // todo 自动生成的方法存根
 return items.size();
 }

 @override
 public object getitem(int position) {
 // todo 自动生成的方法存根
 return items.get(position);
 }

 @override
 public long getitemid(int position) {
 // todo 自动生成的方法存根
 return items.get(position).getid();
 }

 @override
 public view getview(int position, view convertview, viewgroup parent) {
 // todo 自动生成的方法存根
 viewholder holder;//使用viewholder,大神说能提升性能
 if(convertview==null)
 {
  holder=new viewholder();
  convertview=inflater.inflate(r.layout.item_view, null);
  holder.img=(imageview) convertview.findviewbyid(r.id.imageview1);
  holder.cb=(checkbox) convertview.findviewbyid(r.id.checkbox1);
  holder.title=(textview)convertview.findviewbyid(r.id.title);
  holder.teacher=(textview) convertview.findviewbyid(r.id.teacher);
  holder.time=(textview) convertview.findviewbyid(r.id.time);
  holder.poeple=(textview)convertview.findviewbyid(r.id.peoplenum);
  convertview.settag(holder);
 }else
 {
  holder=(viewholder) convertview.gettag();
 }
 item=items.get(position);
 if(item.isshow())
 {
  holder.cb.setvisibility(view.visible);
 }
 else
 {
  holder.cb.setvisibility(view.gone);
 }
 holder.img.setimageresource(item.getimgres());
 holder.title.settext(item.gettitle());
 holder.teacher.settext("主讲:"+item.getteacher());
 holder.time.settext("课时:"+item.gettime()+"讲");
 holder.poeple.settext("学习人数:"+item.getpeoplenum());

 holder.cb.setoncheckedchangelistener(new oncheckedchangelistener() {


  @override
  public void oncheckedchanged(compoundbutton buttonview, boolean ischecked) {
  if(ischecked)
  {
   item.setchecked(true);
  }
  else
  {
   item.setchecked(false);
  }
  //回调方法,讲item加入已选择的
  onshowitemclicklistener.onshowitemclick(item);
  }
 });
 //监听后设置选择状态
 holder.cb.setchecked(item.ischecked());
 return convertview;
 }

 static class viewholder
 {
 imageview img;
 checkbox cb;
 textview title,teacher,time,poeple;

 }

 public interface onshowitemclicklistener {
 public void onshowitemclick(itembean bean);
 }

 public void setonshowitemclicklistener(onshowitemclicklistener onshowitemclicklistener) {
 this.onshowitemclicklistener = onshowitemclicklistener;
}
}

最后是mainactivity.java

package com.example.listchecked;

import java.util.arraylist;
import java.util.list;

import android.app.activity;
import android.content.context;
import android.os.bundle;
import android.util.log;
import android.view.layoutinflater;
import android.view.view;
import android.view.view.onclicklistener;
import android.widget.adapterview;
import android.widget.adapterview.onitemclicklistener;
import android.widget.button;
import android.widget.linearlayout;
import android.widget.listview;
import android.widget.relativelayout;
import android.widget.toast;

import com.example.listchecked.mylistadapter.onshowitemclicklistener;

public class mainactivity extends activity implements onshowitemclicklistener {

 private listview listview;
 private list<itembean> datalist,selectedlist;
 private mylistadapter myadapter;
 private relativelayout rootview;
 private linearlayout menuview;
 private linearlayout openview;
 private static boolean isshow;

 @override
 protected void oncreate(bundle savedinstancestate) {
 super.oncreate(savedinstancestate);
 isshow=false;
 setcontentview(r.layout.activity_main);
 button delbtn=(button) findviewbyid(r.id.del);
 rootview=(relativelayout) findviewbyid(r.id.rootview);
 menuview=(linearlayout) findviewbyid(r.id.button_group);
 listview=(listview) findviewbyid(r.id.listview1);
 datalist=new arraylist<itembean>();
 selectedlist=new arraylist<itembean>();
 for(int i=0;i<10;i++)
 {
  itembean item=new itembean();
  item.setid(i);
  item.setimgres(r.drawable.ic_launcher);
  item.settitle("第"+item.getid()+"个");
  item.setteacher("杨老师");
  item.settime("34");
  item.setpeoplenum(i+1*100);
  item.setchecked(false);
  item.setshow(isshow);
  datalist.add(item);
 }
 myadapter=new mylistadapter(datalist, this);
 myadapter.setonshowitemclicklistener(mainactivity.this);
 listview.setadapter(myadapter);

 delbtn.setonclicklistener(new onclicklistener() {

  @override
  public void onclick(view v) {
  // todo 自动生成的方法存根
  showmenu();
  isshow=true;
  selectedlist.clear();
  for(itembean item:datalist)
  {

   item.setshow(isshow);
  }
  myadapter.notifydatasetchanged();

  }
 });
 listview.setonitemclicklistener(new onitemclicklistener() {

  @override
  public void onitemclick(adapterview<?> parent, view view,
   int position, long id) {
  // todo 自动生成的方法存根
  if (isshow) {
   itembean item = datalist.get(position);
   boolean ischecked = item.ischecked();
   if (ischecked) {
    item.setchecked(false);
   } else {
    item.setchecked(true);
   }
   myadapter.notifydatasetchanged();
   log.d("select",selectedlist.size()+"");
  }
  }
 });

 }
 //显示选择删除等的菜单
 private void showmenu()
 {
 relativelayout.layoutparams lp=new relativelayout.layoutparams(relativelayout.layoutparams.match_parent,
  relativelayout.layoutparams.wrap_content);
 lp.addrule(relativelayout.align_parent_bottom);
 layoutinflater inflater = (layoutinflater) this.getsystemservice(context.layout_inflater_service);
 openview=(linearlayout) inflater.inflate(r.layout.delmenu_layout, null);
 rootview.removeview(menuview);
 rootview.addview(openview,lp);
 final button sbtn=(button) openview.findviewbyid(r.id.selectall);
 button dbtn=(button) openview.findviewbyid(r.id.del_button);
 button cbtn= (button) openview.findviewbyid(r.id.cancel_button);
 sbtn.setonclicklistener(new onclicklistener() {

  @override
  public void onclick(view v) {
  // todo 自动生成的方法存根
  if ("全选".equals(sbtn.gettext().tostring())) {
   for (itembean bean : datalist) {
    if (!bean.ischecked()) {
     bean.setchecked(true);
     if (!selectedlist.contains(bean)) {
      selectedlist.add(bean);
     }
    }
   }
   myadapter.notifydatasetchanged();
   sbtn.settext("反选");
  } else if ("反选".equals(sbtn.gettext().tostring())) {
   for (itembean bean : datalist) {
    bean.setchecked(false);
    if (!selectedlist.contains(bean)) {
     selectedlist.remove(bean);
    }
   }
   myadapter.notifydatasetchanged();
   sbtn.settext("全选");
  }
  }
 });

 dbtn.setonclicklistener(new onclicklistener() {

  @override
  public void onclick(view v) {
  // todo 自动生成的方法存根
  if (selectedlist!=null && selectedlist.size()>0) {
   datalist.removeall(selectedlist);
   myadapter.notifydatasetchanged();
   selectedlist.clear();
  } else {
   toast.maketext(mainactivity.this, "请选择条目", toast.length_short).show();
  }
  }
 });
 cbtn.setonclicklistener(new onclicklistener() {

  @override
  public void onclick(view v) {
  // todo 自动生成的方法存根
  if (isshow) {
   selectedlist.clear();
   for (itembean bean : datalist) {
    bean.setchecked(false);
    bean.setshow(false);
   }
   myadapter.notifydatasetchanged();
   isshow = false;
   restoreview();
  }
  }
 });

 }
 @override
 public void onshowitemclick(itembean bean) {
 // todo 自动生成的方法存根
 if (bean.ischecked() && !selectedlist.contains(bean)) {
  selectedlist.add(bean);
 } else if (!bean.ischecked() && selectedlist.contains(bean)) {
  selectedlist.remove(bean);
 }
 }

 private void restoreview()
 {
 rootview.addview(menuview);
 if(openview!=null)
 {
  rootview.removeview(openview);
  openview=null;
 }

 }
}

最后还有那个小菜单的布局,还是放上吧

<?xml version="1.0" encoding="utf-8"?>
<linearlayout xmlns:android="http://schemas.android.com/apk/res/android"

 android:layout_width="match_parent"
 android:layout_height="match_parent"
 android:orientation="horizontal" >

 <button
  android:id="@+id/selectall"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_weight="1"
  android:text="全选" />

 <button
  android:id="@+id/del_button"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_weight="1"
  android:text="删除" />

 <button
  android:id="@+id/cancel_button"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_weight="1"
  android:text="取消" />

</linearlayout>

全部代码都放上了,如果不想复制粘贴,github地址:https://github.com/2767321434/listchecked

以上就是本文的全部内容,希望对大家学习android软件编程有所帮助。