android开发之ExpandableListView的使用,实现相似QQ好友列表

因为工做须要,今天简单研究了一下ExpandableListView,作了一个相似QQ列表的Demo,和你们分享一下。
效果图以下:
这里写图片描述html

先来看看主布局文件:java

<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:background="#EDEDED" tools:context="com.example.expandablelistview.MainActivity" >

    <ExpandableListView  android:id="@+id/my_listview" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_marginLeft="8dp" android:layout_marginRight="8dp" android:layout_marginTop="10dp" android:divider="@null" android:dividerHeight="8dip" >
    </ExpandableListView>

</RelativeLayout>

这里咱们不使用系统默认的分隔线,两个组之间的距离为8dp.android

对于ExpandableListView,系统为咱们提供了专门的适配器BaseExpandableListAdapter,咱们能够自定义一个适配器继承BaseExpandableListAdapter,实现该类中的一些方法便可。
代码以下:git

public class MyAdapter extends BaseExpandableListAdapter {

    private List<GroupBean> list;
    private Context context;

    public MyAdapter(List<GroupBean> list, Context context) {
        this.list = list;
        this.context = context;
    }

    public MyAdapter() {
    }

    @Override
    public int getGroupCount() {
        return list.size();
    }

    @Override
    public int getChildrenCount(int groupPosition) {
        return list.get(groupPosition).getChildren().size();
    }

    @Override
    public Object getGroup(int groupPosition) {
        return list.get(groupPosition);
    }

    @Override
    public Object getChild(int groupPosition, int childPosition) {
        return list.get(groupPosition).getChildren().get(childPosition);
    }

    @Override
    public long getGroupId(int groupPosition) {
        return groupPosition;
    }

    @Override
    public long getChildId(int groupPosition, int childPosition) {
        return childPosition;
    }

    @Override
    public boolean hasStableIds() {
        return false;
    }

    @Override
    public View getGroupView(int groupPosition, boolean isExpanded,
            View convertView, ViewGroup parent) {
        GroupHolder holder;
        if (convertView == null) {
            holder = new GroupHolder();
            convertView = LayoutInflater.from(context).inflate(
                    R.layout.item_group, null);
            holder.title = (TextView) convertView
                    .findViewById(R.id.group_title);
            holder.iv = (ImageView) convertView.findViewById(R.id.group_ico);
            convertView.setTag(holder);
        } else {
            holder = (GroupHolder) convertView.getTag();
        }
        holder.title.setText(list.get(groupPosition).getGroupName());
        if (isExpanded) {
            holder.iv.setImageResource(R.drawable.rounds_open);
        } else {
            holder.iv.setImageResource(R.drawable.rounds_close);
        }
        return convertView;
    }

    @Override
    public View getChildView(int groupPosition, int childPosition,
            boolean isLastChild, View convertView, ViewGroup parent) {
        ChildHolder holder;
        if (convertView == null) {
            holder = new ChildHolder();
            convertView = LayoutInflater.from(context).inflate(
                    R.layout.item_child, null);
            holder.name = (TextView) convertView.findViewById(R.id.child_name);
            holder.sign = (TextView) convertView.findViewById(R.id.child_sign);
            convertView.setTag(holder);
        } else {
            holder = (ChildHolder) convertView.getTag();
        }
        ChildBean cb = list.get(groupPosition).getChildren().get(childPosition);
        holder.name.setText(cb.getName());
        holder.sign.setText("[签名]"+cb.getSign());
        return convertView;
    }

    @Override
    public boolean isChildSelectable(int groupPosition, int childPosition) {
        return false;
    }

    class GroupHolder {
        TextView title;
        ImageView iv;
    }

    class ChildHolder {
        TextView name, sign;
    }
}

这里的代码有点长,咱们稍微解释一下,先是构造方法中传入两个参数,一个是数据源list,另一个是上下文,list是一个GroupBean集合,GroupBean以下:github

public class GroupBean {

    private String groupName;
    private List<ChildBean> children;

    public String getGroupName() {
        return groupName;
    }

    public void setGroupName(String groupName) {
        this.groupName = groupName;
    }

    public List<ChildBean> getChildren() {
        return children;
    }

    public void setChildren(List<ChildBean> children) {
        this.children = children;
    }

    public GroupBean(String groupName, List<ChildBean> children) {
        this.groupName = groupName;
        this.children = children;
    }

    public GroupBean() {
    }

}

很明显,GroupBean有两个属性,一个是组名字,另一个是该组下子项的一个集合,这个ChildBean就是每一个组下面的每个对象的数据,ChildBean代码以下:markdown

public class ChildBean {

    private String name;
    private String sign;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getSign() {
        return sign;
    }

    public void setSign(String sign) {
        this.sign = sign;
    }

    public ChildBean(String name, String sign) {
        this.name = name;
        this.sign = sign;
    }

    public ChildBean() {
    }

}

说完list,下面就是getGroupCount()和getChildrenCount(),这个有点相似于咱们使用BaseAdapter时的getCount(),不一样的是这里分别要返回每一个组的数量,以及组内成员的数量,那么组的数量固然就是list.size(),组内成员的数量因为每组不一样,因此要先拿到每一个组,再拿到该组里成员的数量,代码就是list.get(groupPosition).getChildren().size();。接下来的两个方法就是getGroup()和getChild(),这个相似于BaseAdapter中的getItem,咱们返回的时候仍是组和组内的子项分开返回,代码很简单,就很少说了。稍微长一点的方法就是getGroupView和getChildView,很少也都没啥逻辑,和咱们在ListView中使用BaseAdapter中的getView方法差很少,不一样的是数据赋值的时候有差异。数据结构

我我的以为,使用ExpandableListView关键在于把数据结构搞清楚,Group和Child搞清楚了,其余的都很简单。ide

这里我把Group的布局和Child的布局贴出来给你们看看:布局

item_group.xmlpost

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="48dp" android:background="@drawable/item_background_select" >

    <TextView  android:id="@+id/group_title" android:layout_width="wrap_content" android:layout_height="48dp" android:layout_marginLeft="36dp" android:gravity="center" android:text="好友分组" android:textSize="18sp" />

    <ImageView  android:id="@+id/group_ico" android:layout_width="24dip" android:layout_height="24dip" android:layout_alignParentRight="true" android:layout_marginBottom="12dp" android:layout_marginLeft="24dp" android:layout_marginRight="24dp" android:layout_marginTop="12dp" android:scaleType="centerInside" android:src="@drawable/rounds_close" />

    <TextView  android:id="@+id/split_lines" android:layout_width="1dip" android:layout_height="48dp" android:layout_toLeftOf="@id/group_ico" android:background="#E6E6E6" />

</RelativeLayout>

item_child.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="36dp" android:orientation="vertical" >

    <TextView  android:id="@+id/child_name" android:layout_width="match_parent" android:layout_height="wrap_content" android:paddingLeft="10dip" android:text="姓名" android:textSize="18sp" />

    <TextView  android:id="@+id/child_sign" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_below="@id/child_name" android:paddingLeft="10dip" android:paddingRight="10dip" android:text="签名" android:textSize="12sp" />

    <View  android:layout_width="match_parent" android:layout_height="1dp" android:background="#B2DFEE" />

</RelativeLayout>

这里还涉及到一个圆角方框,代码是这样的:
item_background_select.xml

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

    <corners android:radius="8dip" />

    <solid android:color="#FFFFFFFF" />

</shape>

好了,全部的准备工做都已经完成,下面看看怎么使用

public class MainActivity extends Activity {

    private ExpandableListView mListView;
    private MyAdapter adapter;
    private List<GroupBean> list;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        //初始化数据
        initData();
        mListView = (ExpandableListView) this.findViewById(R.id.my_listview);
        adapter = new MyAdapter(list, this);
        mListView.setAdapter(adapter);
        mListView.setGroupIndicator(null);
// mListView.expandGroup(0);
    }

    private void initData() {
        list = new ArrayList<GroupBean>();
        {
            List<ChildBean> list1 = new ArrayList<ChildBean>();
            ChildBean cb1 = new ChildBean("妈妈", "123");
            ChildBean cb2 = new ChildBean("爸爸", "456");
            ChildBean cb3 = new ChildBean("爷爷", "789");
            ChildBean cb4 = new ChildBean("妹妹", "000");
            list1.add(cb1);
            list1.add(cb2);
            list1.add(cb3);
            list1.add(cb4);
            GroupBean gb1 = new GroupBean("家", list1);
            list.add(gb1);
        }
        {
            List<ChildBean> list1 = new ArrayList<ChildBean>();
            ChildBean cb1 = new ChildBean("张三", "123");
            ChildBean cb2 = new ChildBean("李四", "456");
            ChildBean cb3 = new ChildBean("王五", "789");
            ChildBean cb4 = new ChildBean("赵六", "000");
            ChildBean cb5 = new ChildBean("风起", "1111");
            ChildBean cb6 = new ChildBean("马坝", "222");
            ChildBean cb7 = new ChildBean("迁就", "3333333");
            list1.add(cb1);
            list1.add(cb2);
            list1.add(cb3);
            list1.add(cb4);
            list1.add(cb5);
            list1.add(cb6);
            list1.add(cb7);
            GroupBean gb1 = new GroupBean("个人朋友", list1);
            list.add(gb1);
        }
        {
            List<ChildBean> list1 = new ArrayList<ChildBean>();
            ChildBean cb1 = new ChildBean("Tom", "123");
            ChildBean cb2 = new ChildBean("Jerry", "456");
            ChildBean cb4 = new ChildBean("Bush", "000");
            list1.add(cb1);
            list1.add(cb2);
            list1.add(cb4);
            GroupBean gb1 = new GroupBean("国际友人", list1);
            list.add(gb1);
        }
        {
            List<ChildBean> list1 = new ArrayList<ChildBean>();
            ChildBean cb1 = new ChildBean("赵工", "123");
            ChildBean cb2 = new ChildBean("马工", "456");
            ChildBean cb3 = new ChildBean("王工", "789");
            ChildBean cb4 = new ChildBean("李工", "000");
            ChildBean cb5 = new ChildBean("为工", "000");
            list1.add(cb1);
            list1.add(cb2);
            list1.add(cb3);
            list1.add(cb4);
            list1.add(cb5);
            GroupBean gb1 = new GroupBean("同事", list1);
            list.add(gb1);
        }
    }
}

这里有两行代码我稍微说一下mListView.setGroupIndicator(null);表示不使用系统提供的展开和收起的图标,mListView.expandGroup(0);表示默认打开第一项。

好了,就说这些,有问题欢迎留言讨论。

本文源码下载地址https://github.com/lenve/expandablelistviewtest1

转载于:https://www.cnblogs.com/qitian1/p/6461739.html