MultiChoiceArrayAdapter其实就是可以多选的ArrayAdapter了,ArrayAdpter我们已经很熟悉了。MultiChoiceArrayAdapter这个类是抽象类,所以使用前必须要继承。下面是使用MultiChoiceArrayAdapter的步骤:

0.用自定义的控件来写一个layout

1.写一个类来继承MultiChoiceArrayAdapter

2.实例化这个类

3.用setAdapterView()来设置要加载适配器的控件。

4.写上保存的方法

@Override
protected void onSaveInstanceState(Bundle outState) {
actionModeAdapter.save(outState);
}

零、写布局文件

listview_actionmode_layout.xml

没什么特别的,就一个listview

<?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="vertical" > <ListView
android:id="@+id/actionMode_listView"
android:layout_width="match_parent"
android:layout_height="wrap_content">
</ListView> </LinearLayout>

item.xml

注意这里要用自己定义的实现了Checkable接口的控件

<?xml version="1.0" encoding="utf-8"?>
<com.manuelpeinado.multichoiceadapter.view.CheckableLinearLayout
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:background="@drawable/custom_list_item_background" android:orientation="horizontal">
<!-- 上面必须要用自定义的layout,否则不会有选中的效果!!! --> <LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="16dp"
android:orientation="horizontal" > <TextView
android:id="@+id/item_textView"
android:layout_width="200dp"
android:layout_height="wrap_content"
android:layout_marginLeft="30dp"
android:layout_gravity="center_vertical"
android:textColor="#000000"
android:layout_weight="1"
android:textAppearance="?android:attr/textAppearanceLarge" /> </LinearLayout>
</com.manuelpeinado.multichoiceadapter.view.CheckableLinearLayout>

二、继承MultiChoiceAdapter

这个是重点,每个方法中实现了不同的功能。其中discardSelectedItems()是自己写的,用来移除已经选中的items。

注意:onCreateActionMode()必须返回true,否则报错!

    private class TestAdapter extends MultiChoiceArrayAdapter<String>{

        String tag = getClass().getSimpleName().toString();

        /**
* @param savedInstanceState
* @param context
* @param resource:Item的布局文件,即 R.layout.xxx
* @param textViewResourceId:显示文字的textview的id,即R.id.xxxx
* @param objects:一个String数组
*/
public TestAdapter(Bundle savedInstanceState, Context context,
int resource, int textViewResourceId, String[] objects) {
//为了避免错误,这里将String数组转为ArrayList对象
this(savedInstanceState,context,resource,textViewResourceId,
new ArrayList<String>(Arrays.asList(objects)));
} /**
* @param savedInstanceState
* @param context
* @param resource:Item的布局文件,即 R.layout.xxx
* @param textViewResourceId:显示文字的textview的id,即R.id.xxxx
* @param items:一个list<String>对象
*/
public TestAdapter(Bundle savedInstanceState, Context context,
int resource, int textViewResourceId, List<String> items) {
super(savedInstanceState, context, resource, textViewResourceId, items);
} /**
* 传入actionMode对象,进行设置图标和操作
* 注意要返回true!
*/
@Override
public boolean onCreateActionMode(ActionMode mode, Menu menu) {
Log.i(tag, "onCreateActionMode");
MenuInflater inflater = mode.getMenuInflater();
inflater.inflate(R.menu.my_action_mode, menu);
//这里必须要写true,否则会报空指针!!!
return true;
}
/**
* 进行AndroidMode上图标操作的设置
*/
@Override
public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
if (item.getItemId() == R.id.menu_share) {
Toast.makeText(getContext(), "分享了" + getCheckedItemCount()+"个item", Toast.LENGTH_SHORT).show();
return true;
}
if (item.getItemId() == R.id.menu_discard) {
//丢弃选中的items
discardSelectedItems();
return true;
}
return false;
} @Override
public boolean onPrepareActionMode(ActionMode arg0, Menu arg1) {
Log.i(tag, "onPrepareActionMode");
return false;
} /**
* (非必须)
* 设置点击、选中效果,非必须。如果你在item的layout设置了 android:background那么下面就不用进行设置背景了
* 个人推荐在item的layout中设置背景色,example:android:background="@drawable/custom_list_item_background"
*/
/*@Override
protected View getViewImpl(int position, View convertView, ViewGroup parent) {
//Log.i(tag, "getViewImpl");
View view = super.getViewImpl(position, convertView, parent);
view.setBackgroundResource(R.drawable.custom_list_item_background);
return view;
}*/ /**
* 从适配器中移除某些item
*/
private void discardSelectedItems() {
//得到选中的items
Set<Long> selection = getCheckedItems();
String[] items = new String[selection.size()];
int i = 0;
for (long position : selection) {
items[i++] = getItem((int)position);
} //通过判断名字来remove掉这些items
for (String item : items) {
/**
* 这里用remove时要注意传入适配器的不能是String[] items对象。否则会报错
* 这里我已经在构造函数中进行了处理,传入String数组也不会出错了~
*/
remove(item);
} finishActionMode();
} }

这里在继承的时候其实就顺带实现了ActionMode的callback接口的内容了,如果对ActionMode熟悉的人一定很容易理解。

二、实例化这个类

TestAdapter actionModeAdapter;
    String[] data = {"android","ios","wp","c++",
"java","c#","javascript","vb",
"delphi","PB","ASP","SQL"}; ListView actionModelistView = (ListView)findViewById(R.id.actionMode_listView); actionModeAdapter = new TestAdapter(savedInstanceState, this,R.layout.item, R.id.item_textView, data);

三、设置控件和监听器

    @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.listview_actionmode_layout); String[] data = {"android","ios","wp","c++",
"java","c#","javascript","vb",
"delphi","PB","ASP","SQL"}; ListView actionModelistView = (ListView)findViewById(R.id.actionMode_listView); actionModeAdapter = new TestAdapter(savedInstanceState, this,R.layout.item, R.id.item_textView, data);
actionModeAdapter.setAdapterView(actionModelistView);
actionModeAdapter.setOnItemClickListener(new MyItemClick(actionModeAdapter)); //listView.setAdapter(adapter);//不这么用啦 } /**
* @author:Jack Tony
* @tips :点击事件的监听器
* @date :2014-10-20
*/
private class MyItemClick implements OnItemClickListener{ private TestAdapter mAdapter; public MyItemClick(TestAdapter adapter) {
mAdapter = adapter;
} @Override
public void onItemClick(AdapterView<?> arg0, View arg1, int position, long arg3) {
Toast.makeText(getApplicationContext(), "点击了: " + mAdapter.getItem(position), Toast.LENGTH_SHORT).show();
} }

四、保存的方法

    @Override
protected void onSaveInstanceState(Bundle outState) {
actionModeAdapter.save(outState);
}

于是大功告成!下面是全部代码:

ArrayAdapterTestActivity.java (这个类没用兼容模式,如果用兼容模式请参考顶部的注释,其实就是导入不同的包即可)

package com.kale.multichoiceadaptertest;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Set; import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
import android.util.Log;
import android.view.ActionMode;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ListView;
import android.widget.Toast; import com.manuelpeinado.multichoiceadapter.normal.MultiChoiceArrayAdapter; /**
* 如果是4.0以上的版本可以直接用activity,不用actionbarActivity,导入的时候导入
* import android.view.ActionMode;
* import com.manuelpeinado.multichoiceadapter.normal.MultiChoiceArrayAdapter;
* 把
* import android.support.v7.view.ActionMode;
* import com.manuelpeinado.multichoiceadapter.compat.MultiChoiceArrayAdapter;
* 删掉
*/ /**
* @author:Jack Tony
* @tips :ActionMode和ArrayAdapter配合实现多选
* @date :2014-10-21
*/
public class ArrayAdapterTestActivity extends Activity{ TestAdapter actionModeAdapter; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.listview_actionmode_layout); String[] data = {"android","ios","wp","c++",
"java","c#","javascript","vb",
"delphi","PB","ASP","SQL"}; ListView actionModelistView = (ListView)findViewById(R.id.actionMode_listView); actionModeAdapter = new TestAdapter(savedInstanceState, this,R.layout.item, R.id.item_textView, data);
actionModeAdapter.setAdapterView(actionModelistView);
actionModeAdapter.setOnItemClickListener(new MyItemClick(actionModeAdapter)); //listView.setAdapter(adapter);//不这么用啦 } @Override
protected void onSaveInstanceState(Bundle outState) {
actionModeAdapter.save(outState);
} private class TestAdapter extends MultiChoiceArrayAdapter<String>{ String tag = getClass().getSimpleName().toString(); /**
* @param savedInstanceState
* @param context
* @param resource:Item的布局文件,即 R.layout.xxx
* @param textViewResourceId:显示文字的textview的id,即R.id.xxxx
* @param objects:一个String数组
*/
public TestAdapter(Bundle savedInstanceState, Context context,
int resource, int textViewResourceId, String[] objects) {
//为了避免错误,这里将String数组转为ArrayList对象
this(savedInstanceState,context,resource,textViewResourceId,
new ArrayList<String>(Arrays.asList(objects)));
} /**
* @param savedInstanceState
* @param context
* @param resource:Item的布局文件,即 R.layout.xxx
* @param textViewResourceId:显示文字的textview的id,即R.id.xxxx
* @param items:一个list<String>对象
*/
public TestAdapter(Bundle savedInstanceState, Context context,
int resource, int textViewResourceId, List<String> items) {
super(savedInstanceState, context, resource, textViewResourceId, items);
} /**
* 传入actionMode对象,进行设置图标和操作
* 注意要返回true!
*/
@Override
public boolean onCreateActionMode(ActionMode mode, Menu menu) {
Log.i(tag, "onCreateActionMode");
MenuInflater inflater = mode.getMenuInflater();
inflater.inflate(R.menu.my_action_mode, menu);
//这里必须要写true,否则会报空指针!!!
return true;
} /**
* 进行AndroidMode上图标操作的设置
*/
@Override
public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
if (item.getItemId() == R.id.menu_share) {
Toast.makeText(getContext(), "分享了" + getCheckedItemCount()+"个item", Toast.LENGTH_SHORT).show();
return true;
}
if (item.getItemId() == R.id.menu_discard) {
//丢弃选中的items
discardSelectedItems();
return true;
}
return false;
} @Override
public boolean onPrepareActionMode(ActionMode arg0, Menu arg1) {
Log.i(tag, "onPrepareActionMode");
return false;
} /**
* (非必须)
* 设置点击、选中效果,非必须。如果你在item的layout设置了 android:background那么下面就不用进行设置背景了
* 个人推荐在item的layout中设置背景色,example:android:background="@drawable/custom_list_item_background"
*/
/*@Override
protected View getViewImpl(int position, View convertView, ViewGroup parent) {
//Log.i(tag, "getViewImpl");
View view = super.getViewImpl(position, convertView, parent);
view.setBackgroundResource(R.drawable.custom_list_item_background);
return view;
}*/ /**
* 从适配器中移除某些item
*/
private void discardSelectedItems() {
//得到选中的items
Set<Long> selection = getCheckedItems();
String[] items = new String[selection.size()];
int i = 0;
for (long position : selection) {
items[i++] = getItem((int)position);
} //通过判断名字来remove掉这些items
for (String item : items) {
/**
* 这里用remove时要注意传入适配器的不能是String[] items对象。否则会报错
* 这里我已经在构造函数中进行了处理,传入String数组也不会出错了~
*/
remove(item);
} finishActionMode();
} } /**
* @author:Jack Tony
* @tips :点击事件的监听器
* @date :2014-10-20
*/
private class MyItemClick implements OnItemClickListener{ private TestAdapter mAdapter; public MyItemClick(TestAdapter adapter) {
mAdapter = adapter;
} @Override
public void onItemClick(AdapterView<?> arg0, View arg1, int position, long arg3) {
Toast.makeText(getApplicationContext(), "点击了: " + mAdapter.getItem(position), Toast.LENGTH_SHORT).show();
} } }

开源项目MultiChoiceAdapter详解(一)——概要介绍

开源项目MultiChoiceAdapter详解(二)——MultiChoiceArrayAdapter的使用

开源项目MultiChoiceAdapter详解(三)——MulitChoiceNormalArrayAdapter的使用

开源项目MultiChoiceAdapter详解(四)——MultiChoiceBaseAdapter的使用

开源项目MultiChoiceAdapter详解(五)——可扩展的MultiChoiceBaseAdapter

开源项目MultiChoiceAdapter详解(六)——GridView和MultiChoiceBaseAdapter配合使用

开源项目MultiChoiceAdapter详解(二)——MultiChoiceArrayAdapter的使用的更多相关文章

  1. 开源项目MultiChoiceAdapter详解(六)——GridView和MultiChoiceBaseAdapter配合使用

    这篇其实没啥重要的,主要就算是个总结吧. 一.布局文件 这里实现的是类似于上图的多图选择的效果.关键在于item布局文件的写法.这也就是这个框架奇葩的一点,莫名其妙的要在一个自定义控件里面再放一个自定 ...

  2. 开源项目MultiChoiceAdapter详解(五)——可扩展的MultiChoiceBaseAdapter

    上次写到了开源项目MultiChoiceAdapter详解(四)——MultiChoiceBaseAdapter的使用,其实我们仍旧可以不使用ActionMode的,所以这里就写一个自己扩展的方法. ...

  3. 开源项目MultiChoiceAdapter详解(四)——MultiChoiceBaseAdapter的使用

    MultiChoiceBaseAdapter是一个可以多选的BaseAdapter,使用的方式相比来说扩展性更强! 使用方式: 1.布局文件 2.写一个类继承MultiChoiceBaseAdapte ...

  4. 开源项目MultiChoiceAdapter详解(三)——MulitChoiceNormalArrayAdapter的使用

    MulitChoiceNormalArrayAdapter是我自己定义的一个类,其实就是实现了MulitChoiceArrayAdapter,为什么做这个简单的实现类呢,因为这样我们在不用Action ...

  5. 开源项目MultiChoiceAdapter详解(一)——概要介绍

    项目地址:https://github.com/ManuelPeinado/MultiChoiceAdapter 这个项目主要是提供了一个多选适配器,使用者可以用它来替换传统的适配器,用途还算比较广泛 ...

  6. 开源项目PullToRefresh详解(二)——PullToRefreshGridView

    这里介绍的是PullToRefreshGridView的使用方法,和之前的PullToRefreshListView方法如出一辙,因为这个开源项目模块化很棒,所以很容易实现.等于说我们可以按照之前使用 ...

  7. 开源项目PullToRefresh详解(一)——PullToRefreshListView

       开源项地址:https://github.com/chrisbanes/Android-PullToRefresh 下拉刷新这个功能我们都比较常见了,今天介绍的就是这个功能的实现.我将按照这个开 ...

  8. 开源项目PullToRefresh详解(四)——PullToRefreshListView和ViewPager的结合使用

    其实这个不是什么新东西了,在介绍(一)中我们就知道了PullToRefreshListView的用法,这里只要将其放入到ViewPager中就行啦.ViewPager还是和以往一样的定义和使用,在适配 ...

  9. Android 开源项目DiskLruCache 详解

    有兴趣的同学可以读完这篇文章以后 可以看看这个硬盘缓存和volley 或者是其他 图片缓存框架中使用的硬盘缓存有什么异同点. 讲道理的话,其实硬盘缓存这个模块并不难写,难就难在 你要考虑到百分之0.1 ...

随机推荐

  1. JS实现集合和ECMA6集合

    集合类似于数组,但是集合中的元素是唯一的,没有重复值的.就像你学高中数学的概念一样,集合还可以做很多比如,并集,交集,差集的计算.在ECMA6之前,JavaScript没有提供原生的Set类,所以只能 ...

  2. Git(一)Git的简介安装

    一.git历史 同生活中的许多伟大事件一样,Git 诞生于一个极富纷争大举创新的年代.Linux 内核开源项目有着为数众广的参与者.绝大多数的 Linux 内核维护工作都花在了提交补丁和保存归档的繁琐 ...

  3. Angular快速学习笔记(4) -- Observable与RxJS

    介绍RxJS前,先介绍Observable 可观察对象(Observable) 可观察对象支持在应用中的发布者和订阅者之间传递消息. 可观察对象可以发送多个任意类型的值 -- 字面量.消息.事件. 基 ...

  4. 【Java】 大话数据结构(11) 查找算法(2)(二叉排序树/二叉搜索树)

    本文根据<大话数据结构>一书,实现了Java版的二叉排序树/二叉搜索树. 二叉排序树介绍 在上篇博客中,顺序表的插入和删除效率还可以,但查找效率很低:而有序线性表中,可以使用折半.插值.斐 ...

  5. 在Win10下搭建web服务器,使用本机IP不能访问,但是使用localhos或127.0.0.1可以正常访问的解决办法

    最近在在Win10下搭建web服务器,发现通过windows自带的浏览器win10 edge浏览器使用本机IP不能放问,但是使用localhos或127.0.0.1可以正常访问, 后来无意发现,使用w ...

  6. Ubuntu 16.04设置rc.local开机启动命令/脚本的方法

    Ubuntu 16.04设置rc.local开机启动命令/脚本的方法       Ubuntu 16.04设置rc.local开机启动命令/脚本的方法(通过update-rc.d管理Ubuntu开机启 ...

  7. IT常用单词

    recursion 递归enable 使能够two-dimensional 二维failover 故障恢复.转移.切换broker 经济人 代理人Component Gallery 组件库Config ...

  8. 通过jstack与jmap分析一次线上故障

    一.发现问题 下面是线上机器的cpu使用率,可以看到从4月8日开始,随着时间cpu使用率在逐步增高,最终使用率达到100%导致线上服务不可用,后面重启了机器后恢复. 二.排查思路 简单分析下可能出问题 ...

  9. rabbitmq学习(一) —— 安装篇

    安装篇之windows: 略(楼主在windows上安装基本就是按部就班的没遇到什么坑) 安装篇值centos7: 主要记录下centos7下的安装,因为在该系统下安装稍微折腾了下 参考https:/ ...

  10. ADSL

    ADSL属于DSL技术的一种,全称Asymmetric Digital Subscriber Line( 非对称数字用户线路),亦可称作非对称数字用户环路.是一种新的数据传输方式. ADSL技术提供的 ...