SoFunction
Updated on 2025-04-05

Detailed explanation of Android ExpandableListView usage example

introduction

In Android development, list display is a very common form of interaction. As a special list control, ExpandableListView allows us to create lists with grouping functions. Each group can also contain multiple children, and the grouping can expand and shrink, which greatly enhances the flexibility and readability of data display. This article will introduce in detail the usage of ExpandableListView, from basic concepts to specific implementations, and then to advanced applications, to help you fully master this control.

1. ExpandableListView Basic Concept

ExpandableListView inherits from ListView and is an expandable list view provided by Android. It mainly consists of two parts: Group and Child. Each group can contain multiple children, and the user can expand or shrink the list of corresponding children by clicking on the group. This control is suitable for scenarios where data needs to be displayed in categories, such as contact lists grouped by letters, product lists grouped by categories, etc.

2. Add ExpandableListView to the layout file

First, we need to add the ExpandableListView control to the layout file. Here is a simple example:

<!-- activity_main.xml -->
<LinearLayout xmlns:andro
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">
    <ExpandableListView
        android:
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
</LinearLayout>

In this layout we create a vertical linear layout and add an ExpandableListView to it, with both width and height set to match_parent to fill the entire parent layout.

3. Create a data model

In order to show the data of grouping and child items, we need to create the corresponding data model class. Suppose we want to show a fruit classification list, with different fruits under each category, we can create the following data model class:

// 
public class GroupModel {
    private String groupName;
    public GroupModel(String groupName) {
         = groupName;
    }
    public String getGroupName() {
        return groupName;
    }
    public void setGroupName(String groupName) {
         = groupName;
    }
}
// 
public class ChildModel {
    private String childName;
    public ChildModel(String childName) {
         = childName;
    }
    public String getChildName() {
        return childName;
    }
    public void setChildName(String childName) {
         = childName;
    }
}

The GroupModel class is used to represent group information and contains a group name; the ChildModel class is used to represent child information and contains a child name.

4. Create an adapter

ExpandableListView requires an adapter to bind data to the view. We can inherit the BaseExpandableListAdapter class to create a custom adapter. Here is an example:

import ;
import ;
import ;
import ;
import ;
import ;
import ;
public class MyExpandableListAdapter extends BaseExpandableListAdapter {
    private Context context;
    private List<GroupModel> groupList;
    private List<List<ChildModel>> childList;
    public MyExpandableListAdapter(Context context, List<GroupModel> groupList, List<List<ChildModel>> childList) {
         = context;
         = groupList;
         = childList;
    }
    @Override
    public int getGroupCount() {
        return ();
    }
    @Override
    public int getChildrenCount(int groupPosition) {
        return (groupPosition).size();
    }
    @Override
    public Object getGroup(int groupPosition) {
        return (groupPosition);
    }
    @Override
    public Object getChild(int groupPosition, int childPosition) {
        return (groupPosition).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) {
        GroupModel groupModel = (GroupModel) getGroup(groupPosition);
        if (convertView == null) {
            LayoutInflater inflater = (LayoutInflater) (Context.LAYOUT_INFLATER_SERVICE);
            convertView = (.simple_expandable_list_item_1, null);
        }
        TextView groupTextView = (.text1);
        (());
        return convertView;
    }
    @Override
    public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) {
        ChildModel childModel = (ChildModel) getChild(groupPosition, childPosition);
        if (convertView == null) {
            LayoutInflater inflater = (LayoutInflater) (Context.LAYOUT_INFLATER_SERVICE);
            convertView = (.simple_list_item_1, null);
        }
        TextView childTextView = (.text1);
        (());
        return convertView;
    }
    @Override
    public boolean isChildSelectable(int groupPosition, int childPosition) {
        return true;
    }
}

In this adapter, we need to implement a series of methods:

  • getGroupCount(): Returns the number of groups.
  • getChildrenCount(int groupPosition): Returns the number of child items in the specified group.
  • getGroup(int groupPosition): Returns the grouped object at the specified location.
  • getChild(int groupPosition, int childPosition): Returns the child object at the specified position under the specified group.
  • getGroupId(int groupPosition) and getChildId(int groupPosition, int childPosition): Returns the IDs of the group and the child item, respectively.
  • getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent): Creates and returns a grouped view.
  • getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent): Creates and returns the view of the child.
  • isChildSelectable(int groupPosition, int childPosition): Specifies whether the child can be selected.

5. Use ExpandableListView in Activity

In Activity, we need to initialize the data, create an adapter, and set it to the ExpandableListView. Here is the sample code:

import ;
import ;
import ;
import ;
import ;
public class MainActivity extends AppCompatActivity {
    private ExpandableListView expandableListView;
    private MyExpandableListAdapter adapter;
    private List&lt;GroupModel&gt; groupList;
    private List&lt;List&lt;ChildModel&gt;&gt; childList;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        (savedInstanceState);
        setContentView(.activity_main);
        expandableListView = findViewById();
        // Initialize the data        initData();
        // Create an adapter        adapter = new MyExpandableListAdapter(this, groupList, childList);
        // Set up the adapter        (adapter);
    }
    private void initData() {
        groupList = new ArrayList&lt;&gt;();
        childList = new ArrayList&lt;&gt;();
        // Add grouped data        GroupModel group1 = new GroupModel("Tropical Fruit");
        GroupModel group2 = new GroupModel("Temperate fruit");
        (group1);
        (group2);
        // Add child data for each group        List&lt;ChildModel&gt; childList1 = new ArrayList&lt;&gt;();
        (new ChildModel("banana"));
        (new ChildModel("mango"));
        (childList1);
        List&lt;ChildModel&gt; childList2 = new ArrayList&lt;&gt;();
        (new ChildModel("apple"));
        (new ChildModel("pear"));
        (childList2);
    }
}

In the onCreate method, we first get the reference to the ExpandableListView control, then call the initData method to initialize the data, then create an adapter and set it to the ExpandableListView.

6. Handle click events for grouping and child items

We can add grouping and child click event listeners to ExpandableListView to implement the corresponding interactive logic. Here is the sample code:

// Add the following code in the onCreate method(new () {
    @Override
    public boolean onGroupClick(ExpandableListView parent, View v, int groupPosition, long id) {
        // Handle group click events        GroupModel groupModel = (GroupModel) (groupPosition);
        String groupName = ();
        // Custom logic can be added here, such as a pop-up prompt box to display the group name        return false;
    }
});
(new () {
    @Override
    public boolean onChildClick(ExpandableListView parent, View v, int groupPosition, int childPosition, long id) {
        // Handle child click event        ChildModel childModel = (ChildModel) (groupPosition, childPosition);
        String childName = ();
        // You can add custom logic here, such as jumping to the details page        return false;
    }
});

In the group click event listener, we can get the grouped object of the click and process it accordingly; in the child click event listener, we can get the child object of the click and process it accordingly.

7. Advanced Application: Custom View

In addition to using the simple layout provided by the system, we can also customize the views of grouping and child items to achieve richer interface effects. Here is an example of a custom view:
Custom group layout file group_item.xml

<LinearLayout xmlns:andro
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="horizontal"
    android:padding="10dp">
    <ImageView
        android:
        android:layout_width="24dp"
        android:layout_height="24dp"
        android:src="@mipmap/ic_launcher" />
    <TextView
        android:
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginLeft="10dp"
        android:textSize="18sp" />
</LinearLayout>

Customize child layout file child_item.xml

<LinearLayout xmlns:andro
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="horizontal"
    android:padding="10dp">
    <ImageView
        android:
        android:layout_width="24dp"
        android:layout_height="24dp"
        android:src="@mipmap/ic_launcher" />
    <TextView
        android:
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginLeft="10dp"
        android:textSize="16sp" />
</LinearLayout>

Modify the getGroupView and getChildView methods in the adapter

@Override
public View getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) {
    GroupModel groupModel = (GroupModel) getGroup(groupPosition);
    if (convertView == null) {
        LayoutInflater inflater = (LayoutInflater) (Context.LAYOUT_INFLATER_SERVICE);
        convertView = (.group_item, null);
    }
    ImageView groupIcon = (.group_icon);
    TextView groupTextView = (.group_name);
    (());
    return convertView;
}
@Override
public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) {
    ChildModel childModel = (ChildModel) getChild(groupPosition, childPosition);
    if (convertView == null) {
        LayoutInflater inflater = (LayoutInflater) (Context.LAYOUT_INFLATER_SERVICE);
        convertView = (.child_item, null);
    }
    ImageView childIcon = (.child_icon);
    TextView childTextView = (.child_name);
    (());
    return convertView;
}

Through custom views, we can add more controls, such as pictures, buttons, etc. to grouping and child items, thereby achieving more complex interface effects.

8. Summary

ExpandableListView is a very practical list control in Android. It can help us implement list display with grouping functions. Through the introduction of this article, you should have mastered the basic usage of ExpandableListView, including the addition of layout files, the creation of data models, the implementation of adapters, the processing of click events, and the application of custom views. In actual development, you can further expand and optimize it according to specific needs to meet different business scenarios. I hope this article will be helpful to you and wish you better results in Android development!