ExpandListView 使用简介

1,354 阅读1分钟

效果图

只能实现两层折叠。 image.png

属性简单介绍

divider 	 :父布局之间的分割线样式
childDivider     :子布局之间分割样式
dividerHeight    :用于设置分割线的高度
childIndicator	 :用于设置子布局前显示的图标,不设置的话默认是没有图标的
groupIndicator   :设置父布局前显示的图标

indicatorLeft/indicatorStart :默认图标距左侧距离
indicatorRight/indicatorEnd  :默认图标距右侧距离

使用详解

  1. 主界面
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <ExpandableListView
        android:id="@+id/elvExpandList"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:groupIndicator="@null"/>
</androidx.constraintlayout.widget.ConstraintLayout>
  1. activity
class ExpandActivity: AppCompatActivity(R.layout.activity_expand) {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        initData()

    }

    lateinit var adapter: ExpandAdapter
    private fun initData() {
        val list = ArrayList<Contact>()
        var contact: Contact
        for (i in 0..8){
            contact = Contact("朋友$i",
                arrayListOf(
                    Person("张三","123658956987"),
                    Person("李四","123658956987"),
                    Person("王五","123658956987")
                ))
            list.add(contact)
        }
        adapter = ExpandAdapter(this,list)
        elvExpandList.setAdapter(adapter)
        //默认展开第几个
        elvExpandList.expandGroup(3)
        //子布局点击
        elvExpandList.setOnChildClickListener { parent, v, groupPosition, childPosition, id ->
            Toast.makeText(this, "${list[groupPosition].list[childPosition].name}", Toast.LENGTH_SHORT).show()
            true
        }
    }
}
  1. bean
data class Contact(
    var title: String?,
    var list: List<Person>
)

data class Person(var name: String?, var phone: String?)
  1. adpter
class ExpandAdapter(val context: Context, private val list: List<Contact>) :
    BaseExpandableListAdapter() {

    var layoutInflater: LayoutInflater = LayoutInflater.from(context)

    override fun getGroupCount(): Int = list.size

    override fun getChildrenCount(groupPosition: Int): Int = list[groupPosition].list.size

    override fun getGroup(groupPosition: Int): Any {
        return list[groupPosition]
    }

    override fun getChild(groupPosition: Int, childPosition: Int): Any {
        return list[groupPosition].list[childPosition]
    }

    override fun getGroupId(groupPosition: Int): Long {
        return groupPosition.toLong()
    }

    override fun getChildId(groupPosition: Int, childPosition: Int): Long {
        return childPosition.toLong()
    }

    override fun hasStableIds(): Boolean = false

    override fun getGroupView(
        groupPosition: Int,
        isExpanded: Boolean,
        convertView: View?,
        parent: ViewGroup?
    ): View {
        var convertView = convertView
        val holder: GroupViewHolder
        if (convertView == null) {
            convertView = layoutInflater.inflate(R.layout.item_expand_group, parent, false)
            holder = GroupViewHolder(convertView)
            convertView.tag = holder
        } else {
            holder = convertView.tag as GroupViewHolder
        }
        val groupData = list[groupPosition]
        holder.tvTitle.text = groupData.title
        holder.ivArrow.setImageResource(if (isExpanded) R.drawable.arrow_down else R.drawable.arrow_right)
        return convertView!!
    }

    override fun getChildView(
        groupPosition: Int,
        childPosition: Int,
        isLastChild: Boolean,
        convertView: View?,
        parent: ViewGroup?
    ): View {
        var convertView = convertView
        val holder: ChildViewHolder
        if (convertView == null) {
            convertView = layoutInflater.inflate(R.layout.item_expand_child, parent, false)
            holder = ChildViewHolder(convertView!!)
            convertView.tag = holder
        } else {
            holder = convertView.tag as ChildViewHolder
        }
        val childData = list[groupPosition].list[childPosition]
        holder.tvName.text = childData.name
        holder.tvMoblie.text = childData.phone
        return convertView
    }

    //子项是否可选中,如果要设置子项的点击事件,需要返回true
    override fun isChildSelectable(groupPosition: Int, childPosition: Int): Boolean = true

/*    internal class TestViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
        var tvTitle: TextView = itemView.findViewById(R.id.tvItemExpandGroupTitle)

    }*/

    class GroupViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
        var tvTitle: TextView = itemView.findViewById<TextView>(R.id.tvItemExpandGroupTitle)
        var ivArrow: ImageView = itemView.findViewById<ImageView>(R.id.ivExpandGroupArrow)
    }

    class ChildViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
        var tvName = itemView.findViewById<TextView>(R.id.tvItemExpandChildName)
        var tvMoblie = itemView.findViewById<TextView>(R.id.tvItemExpandChildPhone)
    }
}
  1. 外层 Item 布局
<?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="50dp"
    android:paddingHorizontal="15dp">

    <TextView
        android:id="@+id/tvItemExpandGroupTitle"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="分组"
        android:layout_centerVertical="true"/>

    <ImageView
        android:id="@+id/ivExpandGroupArrow"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:src="@drawable/arrow_right"
        android:layout_centerVertical="true"
        android:layout_alignParentRight="true"/>
</RelativeLayout>
  1. 内层 item 布局
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal"
    android:layout_width="match_parent"
    android:layout_height="40dp"
    android:background="@color/colorAccent">

    <TextView
        android:id="@+id/tvItemExpandChildName"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="@string/app_name"
        android:layout_gravity="center_vertical"
        android:layout_marginStart="50dp"
        android:textColor="@color/white"/>

    <TextView
        android:id="@+id/tvItemExpandChildPhone"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="@string/app_name"
        android:layout_gravity="center_vertical"
        android:layout_marginStart="20dp"
        android:textColor="@color/white"/>
</LinearLayout>

参考

ExpandableListView

ExpandableListView使用方法详解

ExpanableListView