Android StudioでExpandableListView（折りたたみリスト）を使う方法

##はじめに
折りたたむことができるリストのメモになります。

##コード
```string.xml
<resources>
    <string name="app_name">ExpandableListView</string>
</resources>
```

```activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <ExpandableListView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/exListView"></ExpandableListView>

</LinearLayout>
```

```MainActivity.java
package com.websarva.wings.android.expandablelistview;

import android.app.AlertDialog;
import android.content.Context;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseExpandableListAdapter;
import android.widget.ExpandableListAdapter;
import android.widget.ExpandableListView;
import android.widget.SimpleExpandableListAdapter;
import android.widget.TextView;
import android.widget.Toast;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class MainActivity extends AppCompatActivity {

    List<Map<String, String>> parentList;
    List<List<Map<String, String>>> childList;
    List<Map<String, String>> childDataList;
    Map<String, String> childtData;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        parentList = new ArrayList<>();
        childList = new ArrayList<>();

        //親リストに表示する内容を生成
        setParentList("parentKey", "親1");
        setParentList("parentKey", "親2");

        //子リストに表示する内容を生成
        String firstItemName1[] = {"子1", "子2"};
        String secondItemName1[] = {"子1段目", "子2段目"};
        setChildDataList("childKey1", firstItemName1, "childKey2", secondItemName1);

        String firstItemName2[] = {"子A", "子B", "子C"};
        String secondItemName2[] = {"子A段目", "子B段目", "子C段目"};
        setChildDataList("childKey1", firstItemName2, "childKey2", secondItemName2);

        //アダプタ作成
        SimpleExpandableListAdapter adapter =
                new SimpleExpandableListAdapter(
                        this,
                        parentList,
                        android.R.layout.simple_expandable_list_item_1,
                        new String[]{"parentKey"},
                        new int[]{android.R.id.text1},
                        childList,
                        android.R.layout.simple_expandable_list_item_2,
                        new String[]{"childKey1", "childKey2"},
                        new int[]{android.R.id.text1, android.R.id.text2}
                );

        ExpandableListView elv = findViewById(R.id.exListView);
        elv.setAdapter(adapter);

    }

    /**
     * 親リストに表示する内容を生成する処理
     * @param parentKey
     * @param value
     * @return　parentList
     */
    private List<Map<String, String>> setParentList(String parentKey, String value) {
        Map<String, String> parentData = new HashMap<String, String>();
        parentData.put(parentKey, value);
        parentList.add(parentData);
        return parentList;
    }

    /**
     * 子リストに表示する内容を生成する処理
     * @param childKey1
     * @param firstItemName
     * @param childKey2
     * @param secondItemName
     * @return childDataList
     */
    private List<Map<String, String>> setChildData(String childKey1, String firstItemName, String childKey2, String secondItemName) {
        childtData = new HashMap<String, String>();
        childtData.put(childKey1, firstItemName);
        childtData.put(childKey2, secondItemName);
        childDataList.add(childtData);
        return childDataList;
    }

    /**
     * 子リストを表示数分作成する処理
     * @param childKey1
     * @param firstItemName
     * @param childKey2
     * @param secondItemName
     * @return childList
     */
    private List<List<Map<String, String>>> setChildDataList(String childKey1, String firstItemName[], String childKey2, String secondItemName[]) {
        childDataList = new ArrayList<>();
        //作成する項目数の回数繰り返す
        for (int i = 0; i < firstItemName.length; i++) {
            setChildData(childKey1, firstItemName[i], childKey2, secondItemName[i]);
        }
        childList.add(childDataList);
        return childList;
    }

}

```

##実行結果
![新しいビットマップ イメージ.jpeg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587966/e74deb45-e713-4ad4-43d4-679e94416eb0.jpeg)

##解説
SimpleExpandableListAdapterを使用して、ExpandableListViewにリストとして表示したいデータをセットします。
リストとして表示したいデータをSimpleExpandableListAdapterに格納するために、下記の手順で作成します。
###手順
1.親リストに表示する内容を生成する処理
2.子リストに表示する内容を生成する処理
3.子リストの項目の数、繰り返す処理
4.親リストに表示するデータをMapに格納する
5.子リストに表示するデータをMapに格納する
6.親リストと、子リストをSimpleExpandableListAdapterへ格納する

###各データの格納
setParentListメソッドを呼び出した数だけ、親リストを作成する。
引数は、MAPのに格納するキーと値を渡す。

```setParentList.親データの格納
@Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        parentList = new ArrayList<>();

　　　　 ~省略~

        //親リストに表示する内容を生成
        setParentList("parentKey", "親1");
        setParentList("parentKey", "親2");

　　　　 ~省略~
    }

private List<Map<String, String>> setParentList(String parentKey, String value) {
        Map<String, String> parentData = new HashMap<String, String>();
        parentData.put(parentKey, value);
        parentList.add(parentData);
        return parentList;
    }
```

setChildDataListメソッドを呼び出した数だけ、親リストを作成する。
引数は、MAPのに格納するキー（第1、第3引数）と値（第2、第4引数）を渡す。

```setChildDataList.子データの格納
@Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

　　　　 ~省略~
        
        childList = new ArrayList<>();

　　　　 ~省略~

        //子リストに表示する内容を生成
        String firstItemName1[] = {"子1", "子2"};
        String secondItemName1[] = {"子1段目", "子2段目"};
        setChildDataList("childKey1", firstItemName1, "childKey2", secondItemName1);

        String firstItemName2[] = {"子A", "子B", "子C"};
        String secondItemName2[] = {"子A段目", "子B段目", "子C段目"};
        setChildDataList("childKey1", firstItemName2, "childKey2", secondItemName2);

　　　　 ~省略~
     }

private List<Map<String, String>> setChildData(String childKey1, String firstItemName, String childKey2, String secondItemName) {
        childtData = new HashMap<String, String>();
        childtData.put(childKey1, firstItemName);
        childtData.put(childKey2, secondItemName);
        childDataList.add(childtData);
        return childDataList;
    }

    private List<List<Map<String, String>>> setChildDataList(String childKey1, String firstItemName[], String childKey2, String secondItemName[]) {
        childDataList = new ArrayList<>();
        //作成する項目数の回数繰り返す
        for (int i = 0; i < firstItemName.length; i++) {
            setChildData(childKey1, firstItemName[i], childKey2, secondItemName[i]);
        }
        childList.add(childDataList);
        return childList;
    }
```
###アダプタの格納
親、子のデータをアダプタに格納する

```
@Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

　　　　 ~省略~

        //アダプタ作成
        SimpleExpandableListAdapter adapter =
                new SimpleExpandableListAdapter(
                        this, ・・・①
                        parentList, ・・・②
                        android.R.layout.simple_expandable_list_item_1, ・・・③
                        new String[]{"parentKey"}, ・・・④
                        new int[]{android.R.id.text1}, ・・・⑤
                        childList, ・・・②
                        android.R.layout.simple_expandable_list_item_2, ・・・③
                        new String[]{"childKey1", "childKey2"}, ・・・④
                        new int[]{android.R.id.text1, android.R.id.text2} ・・・⑤
                );

        ExpandableListView elv = findViewById(R.id.exListView);
        elv.setAdapter(adapter);

    }
```
①ExpandableListViewが関連付けられるContext
②List
③各行のレイアウトを表すR値
④MAPのキー
⑤レイアウト内での文字を表示するTextViewのID

以上、ExpandableListView（折りたたみリスト）の使用方法になります。