Android中两级都实现带CheckBox的 ExpandableListView,实现两级联动选择,代码实现的比较乱,Demo界面更是丑的可以,将就着看吧……
效果:
下面贴上代码,或者直接访问CSDN的地址免积分下载:http://download.csdn.net/download/zw_yuyan/7550811
/**
* @Title: ItemBean.java
* @Package com.example.test
* @Description: 父列表项
* @date 2014-6-25 上午9:45:29
*/
package com.example.test;
import java.util.List;
public class GroupItem {
private String id;
private String name;
private List<ChildrenItem> childrenItems;
public GroupItem() {
}
public GroupItem(String id,String name,List<ChildrenItem> childrenItems) {
this.id = id;
this.name = name;
this.childrenItems = childrenItems;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public List<ChildrenItem> getChildrenItems() {
return childrenItems;
}
public void setChildrenItems(List<ChildrenItem> childrenItems) {
this.childrenItems = childrenItems;
}
}
/**
* @Title: ItemBean.java
* @Package com.example.test
* @Description: 子列表项
* @date 2014-6-25 上午9:45:29
*/
package com.example.test;
public class ChildrenItem {
private String id;
private String name;
public ChildrenItem() {
}
public ChildrenItem(String id,String name) {
this.id = id;
this.name = name;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
主界面:
package com.example.test;
import java.util.ArrayList;
import java.util.List;
import android.app.Activity;
import android.app.AlertDialog;
import android.app.AlertDialog.Builder;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ExpandableListView;
public class MainActivity extends Activity {
private ExpandableListView expandableList;
private Button showBtn;
private ListViewAdapter adapter;
private List<GroupItem> dataList = new ArrayList<GroupItem>();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
expandableList = (ExpandableListView)findViewById(R.id.expandable_list);
showBtn = (Button)findViewById(R.id.showBtn);
showBtn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
showCheckedItems();
}
});
initData();
adapter = new ListViewAdapter(this, dataList);
expandableList.setAdapter(adapter);
}
private void showCheckedItems(){
String checkedItems = "";
List<String> checkedChildren = adapter.getCheckedChildren();
if (checkedChildren!=null && !checkedChildren.isEmpty()) {
for (String child : checkedChildren) {
if (checkedItems.length()>0) {
checkedItems += "\n";
}
checkedItems += child;
}
}
final Builder builder = new AlertDialog.Builder(this);
builder.setTitle("已选中项(无排序):");
builder.setMessage(checkedItems);
builder.setPositiveButton("关闭", null);
builder.setCancelable(true);
builder.create().show();
}
/**
* 初始化Adapter数据
* @Title:
* @Description:
* @return void 返回类型
* @author zhangxiaolei
* @throws
*/
private void initData(){
List<ChildrenItem> list1 = new ArrayList<ChildrenItem>();
list1.add(new ChildrenItem("childrenItem1","childrenItem1"));
list1.add(new ChildrenItem("childrenItem2","childrenItem2"));
list1.add(new ChildrenItem("childrenItem3","childrenItem3"));
GroupItem groupItem1 = new GroupItem("groupItem1","groupItem1",list1);
dataList.add(groupItem1);
List<ChildrenItem> list2 = new ArrayList<ChildrenItem>();
list2.add(new ChildrenItem("childrenItem4","childrenItem4"));
list2.add(new ChildrenItem("childrenItem5","childrenItem5"));
GroupItem groupItem2 = new GroupItem("groupItem2","groupItem2",list2);
dataList.add(groupItem2);
List<ChildrenItem> list3 = new ArrayList<ChildrenItem>();
list3.add(new ChildrenItem("childrenItem6","childrenItem6"));
list3.add(new ChildrenItem("childrenItem7","childrenItem7"));
list3.add(new ChildrenItem("childrenItem8","childrenItem8"));
GroupItem groupItem3 = new GroupItem("groupItem3","groupItem3",list3);
dataList.add(groupItem3);
}
}
ListView所用的自定义Adapter:
package com.example.test;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.BaseExpandableListAdapter;
import android.widget.CheckBox;
import android.widget.CompoundButton;
import android.widget.CompoundButton.OnCheckedChangeListener;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
public class ListViewAdapter extends BaseExpandableListAdapter {
private List<GroupItem> dataList;
private LayoutInflater inflater;
//以选中的子列表项
private List<String> checkedChildren = new ArrayList<String>();
//父列表项的选中状态:value值为1(选中)、2(部分选中)、3(未选中)
private Map<String, Integer> groupCheckedStateMap = new HashMap<String, Integer>();
public ListViewAdapter(Context context, List<GroupItem> dataList) {
this.dataList = dataList;
inflater = LayoutInflater.from(context);
//默认设置所有的父列表项和子列表项都为选中状态
int groupCount = getGroupCount();
for (int groupPosition = 0; groupPosition < groupCount; groupPosition++) {
try {
GroupItem groupItem = dataList.get(groupPosition);
if (groupItem==null || groupItem.getChildrenItems() == null
|| groupItem.getChildrenItems().isEmpty()) {
groupCheckedStateMap.put(groupItem.getId(), 3);
continue;
}
groupCheckedStateMap.put(groupItem.getId(), 1);
List<ChildrenItem> childrenItems = groupItem.getChildrenItems();
for (ChildrenItem childrenItem : childrenItems) {
checkedChildren.add(childrenItem.getId());
}
} catch (Exception e) {
}
}
}
@Override
public Object getChild(int groupPosition, int childPosition) {
final GroupItem groupItem = dataList.get(groupPosition);
if (groupItem==null || groupItem.getChildrenItems()==null
|| groupItem.getChildrenItems().isEmpty()) {
return null;
}
return groupItem.getChildrenItems().get(childPosition);
}
@Override
public long getChildId(int groupPosition, int childPosition) {
return childPosition;
}
@Override
public View getChildView(final int groupPosition, int childPosition,
boolean isLastChild, View convertView, final ViewGroup parent) {
ChildrenItem childrenItem = (ChildrenItem) getChild(groupPosition, childPosition);
ChildViewHolder viewHolder = null;
if (convertView == null) {
viewHolder = new ChildViewHolder();
convertView = inflater.inflate(R.layout.children_item, null);
viewHolder.childrenNameTV = (TextView) convertView.findViewById(R.id.children_name);
viewHolder.childrenCB = (CheckBox) convertView.findViewById(R.id.children_cb);
convertView.setTag(viewHolder);
} else {
viewHolder = (ChildViewHolder) convertView.getTag();
}
viewHolder.childrenNameTV.setText(childrenItem.getName());
final String childrenId = childrenItem.getId();
viewHolder.childrenCB.setOnCheckedChangeListener(new OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
if (isChecked) {
if (!checkedChildren.contains(childrenId)) {
checkedChildren.add(childrenId);
}
}else {
checkedChildren.remove(childrenId);
}
setGroupItemCheckedState(dataList.get(groupPosition));
ListViewAdapter.this.notifyDataSetChanged();
}
});
if (checkedChildren.contains(childrenId)) {
viewHolder.childrenCB.setChecked(true);
}else {
viewHolder.childrenCB.setChecked(false);
}
return convertView;
}
@Override
public int getChildrenCount(int groupPosition) {
final GroupItem groupItem = dataList.get(groupPosition);
if (groupItem== null || groupItem.getChildrenItems()==null
|| groupItem.getChildrenItems().isEmpty()) {
return 0;
}
return groupItem.getChildrenItems().size();
}
@Override
public Object getGroup(int groupPosition) {
if (dataList==null) {
return null;
}
return dataList.get(groupPosition);
}
@Override
public int getGroupCount() {
if (dataList==null) {
return 0;
}
return dataList.size();
}
@Override
public long getGroupId(int groupPosition) {
return groupPosition;
}
@Override
public View getGroupView(int groupPosition, boolean isExpanded,
View convertView, ViewGroup parent) {
try {
GroupItem groupItem = dataList.get(groupPosition);
GroupViewHolder viewHolder = null;
if (convertView == null) {
viewHolder = new GroupViewHolder();
convertView = inflater.inflate(R.layout.group_item, null);
viewHolder.groupNameTV = (TextView) convertView.findViewById(R.id.group_name);
viewHolder.groupCBImg = (ImageView) convertView.findViewById(R.id.group_cb_img);
viewHolder.groupCBLayout = (LinearLayout) convertView.findViewById(R.id.cb_layout);
convertView.setTag(viewHolder);
} else {
viewHolder = (GroupViewHolder) convertView.getTag();
}
viewHolder.groupCBLayout.setOnClickListener(new GroupCBLayoutOnClickListener(groupItem));
viewHolder.groupNameTV.setText(groupItem.getName());
int state = groupCheckedStateMap.get(groupItem.getId());
switch (state) {
case 1:
viewHolder.groupCBImg.setImageResource(R.drawable.ck_checked);
break;
case 2:
viewHolder.groupCBImg.setImageResource(R.drawable.ck_partial_checked);
break;
case 3:
viewHolder.groupCBImg.setImageResource(R.drawable.ck_unchecked);
break;
default:
break;
}
} catch (Exception e) {
e.printStackTrace();
}
return convertView;
}
@Override
public boolean hasStableIds() {
return false;
}
@Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return false;
}
private void setGroupItemCheckedState(GroupItem groupItem){
List<ChildrenItem> childrenItems = groupItem.getChildrenItems();
if (childrenItems==null || childrenItems.isEmpty()) {
groupCheckedStateMap.put(groupItem.getId(), 3);
return;
}
int checkedCount = 0;
for (ChildrenItem childrenItem : childrenItems) {
if (checkedChildren.contains(childrenItem.getId())) {
checkedCount ++;
}
}
int state = 1;
if (checkedCount==0) {
state = 3;
}else if (checkedCount==childrenItems.size()) {
state = 1;
}else {
state = 2;
}
groupCheckedStateMap.put(groupItem.getId(), state);
}
final static class GroupViewHolder {
TextView groupNameTV;
ImageView groupCBImg;
LinearLayout groupCBLayout;
}
final static class ChildViewHolder {
TextView childrenNameTV;
CheckBox childrenCB;
}
public class GroupCBLayoutOnClickListener implements OnClickListener{
private GroupItem groupItem;
public GroupCBLayoutOnClickListener(GroupItem groupItem){
this.groupItem = groupItem;
}
@Override
public void onClick(View v) {
List<ChildrenItem> childrenItems = groupItem.getChildrenItems();
if (childrenItems==null || childrenItems.isEmpty()) {
groupCheckedStateMap.put(groupItem.getId(), 3);
return;
}
int checkedCount = 0;
for (ChildrenItem childrenItem : childrenItems) {
if (checkedChildren.contains(childrenItem.getId())) {
checkedCount ++;
}
}
boolean checked = false;
if (checkedCount==childrenItems.size()) {
checked = false;
groupCheckedStateMap.put(groupItem.getId(), 3);
}else{
checked = true;
groupCheckedStateMap.put(groupItem.getId(), 1);
}
for (ChildrenItem childrenItem : childrenItems) {
String holderKey = childrenItem.getId();
if (checked) {
if (!checkedChildren.contains(holderKey)) {
checkedChildren.add(holderKey);
}
}else {
checkedChildren.remove(holderKey);
}
}
ListViewAdapter.this.notifyDataSetChanged();
}
}
public List<String> getCheckedRecords() {
return checkedChildren;
}
public List<String> getCheckedChildren() {
return checkedChildren;
}
}
主界面布局:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical"
android:gravity="center_horizontal">
<Button android:id="@+id/showBtn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:layout_marginBottom="10dp"
android:text="点击查看选中项"
/>
<ExpandableListView
android:id="@+id/expandable_list"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:indicatorLeft="1sp" >
</ExpandableListView>
</LinearLayout>
父列表项布局:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="60dp"
android:background="#FFF" >
<LinearLayout
android:id="@+id/cb_layout"
android:layout_width="70dp"
android:layout_height="60dp"
android:layout_alignParentRight="true"
android:background="#CCC"
android:gravity="center" >
<ImageView
android:id="@+id/group_cb_img"
android:layout_width="25dp"
android:layout_height="25dp"
android:src="@drawable/ck_checked" />
</LinearLayout>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="60dp"
android:layout_marginLeft="30dp"
android:layout_toLeftOf="@id/zxjc_upload_cb_layout"
android:gravity="center_vertical" >
<TextView
android:id="@+id/group_name"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:gravity="center_vertical"
android:singleLine="true"
android:textColor="#FF0000"
android:textSize="20sp" />
</LinearLayout>
</RelativeLayout>
子列表项布局:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:background="@drawable/li_bg2"
android:gravity="center_vertical"
android:orientation="horizontal"
android:paddingBottom="5dp"
android:paddingLeft="20dp"
android:paddingRight="20dp"
android:paddingTop="5dp" >
<LinearLayout
android:id="@+id/zxjc_upload_cb_layout"
android:layout_width="60dp"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:gravity="center_vertical|right"
android:orientation="horizontal" >
<CheckBox
android:id="@+id/children_cb"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="20dp" />
</LinearLayout>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:layout_toLeftOf="@id/zxjc_upload_cb_layout"
android:orientation="vertical" >
<TextView
android:id="@+id/children_name"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:textSize="20sp" />
</LinearLayout>
</RelativeLayout>