Create Multiple Foldouts.

Hi all, I’m trying to create a multiple group of foldout options, I’ve gotten close but some-things are messing up. Either they all open at once, or I get out of range exceptions. Can anyone help me out?

Here is my code. Thanks in advance!

using UnityEngine;
using UnityEditor;
using System.Collections;
using System.Collections.Generic;

public class TrophyEditor : EditorWindow {

    TrophyList trophyDB;
    Vector2 scroll = Vector2.zero;
    List<bool> collapse = new List<bool>();

    [MenuItem("Tools/Trophy Editor")]
    static void Initialize() {
        var window = ScriptableObject.CreateInstance<TrophyEditor>();
        window.title = "Trophy Editor";
        window.ShowUtility();
    }

    void OnEnable() {
        trophyDB = Resources.Load<TrophyList>("Data/TrophyList");
        // If the trophy list is empty, initialize it
        if (trophyDB.trophiesList.Count == 0) {
            trophyDB.trophiesList.Add(new Trophy());
        }
    }

    void OnDestroy() {
        Save();
    }

    void Save() {
        AssetDatabase.Refresh();
        EditorUtility.SetDirty(trophyDB);
        AssetDatabase.SaveAssets();
    }

    void OnGUI() {
        GUILayout.BeginHorizontal(EditorStyles.toolbar);
        if (GUILayout.Button("Save", EditorStyles.toolbarButton)) {
            Save();
            EditorUtility.DisplayDialog("Save Asset", "The list of Trophies has been saved!", "Okay");
        }
        GUILayout.FlexibleSpace();
        GUILayout.EndHorizontal();

        EditorGUILayout.HelpBox("Welcome to the Trophy Editor.

", MessageType.Info);

        EditorGUILayout.BeginHorizontal();
        EditorGUILayout.BeginVertical();
        scroll = EditorGUILayout.BeginScrollView(scroll);

        foreach (Trophy t in trophyDB.trophiesList) {
            for (int i = 0; i < collapse.Count; ++i) {
                collapse _= EditorGUILayout.Foldout(collapse*, "Trophy: " + t.title);*_

if (collapse*) {*
GUILayout.Space(10);
t.trophyIcon = (Texture2D)EditorGUILayout.ObjectField(“Icon”, t.trophyIcon, typeof(Texture2D), false);
t.title = EditorGUILayout.TextField(“Title”, t.title);
t.grade = (TrophyGrade)EditorGUILayout.EnumPopup(“Grade”, t.grade);
t.details = EditorGUILayout.TextArea(t.details, GUILayout.Height(60));
}
}
}

EditorGUILayout.EndScrollView();
EditorGUILayout.EndVertical();
EditorGUILayout.EndHorizontal();

EditorGUILayout.BeginHorizontal();
if (GUILayout.Button(“Add”)) {
trophyDB.trophiesList.Add(new Trophy());
collapse.Add(false);
}
if (GUILayout.Button(“Remove”)) {
trophyDB.trophiesList.RemoveAt(trophyDB.trophiesList.Count);
collapse.RemoveAt(collapse.Count);
}
EditorGUILayout.EndHorizontal();
}

}

At the moment you have a nexted loop which doesn’t make much sense as you want one boolean for each trophy. You should do something like this:

// make sure we have as many booleans as we have trophies.
while (collapse.Count < trophyDB.trophiesList.Count)
    collapse.Add(true); // expand by default

for (int i = 0; i < trophyDB.trophiesList.Count; ++i)
{
    Trophy t = trophyDB.trophiesList*;*

collapse = EditorGUILayout.Foldout(collapse*, "Trophy: " + t.title);*
if (collapse*)*
{
GUILayout.Space(10);
t.trophyIcon = (Texture2D)EditorGUILayout.ObjectField(“Icon”, t.trophyIcon, typeof(Texture2D), false);
t.title = EditorGUILayout.TextField(“Title”, t.title);
t.grade = (TrophyGrade)EditorGUILayout.EnumPopup(“Grade”, t.grade);
t.details = EditorGUILayout.TextArea(t.details, GUILayout.Height(60));
if (GUILayout.Button(“Remove”))
{
trophyDB.trophiesList.RemoveAt(i);
collapse.RemoveAt(i);
EditorGUIUtility.ExitGUI(); // important to stop current GUI execution
}
}
}
I’ve added the remove button to the trophy itself so you can remove arbitrary items.