AR Design
UBC EML collab with UBC SALA - visualizing IoT data in AR
AudioEventPropertyDrawer.cs
Go to the documentation of this file.
1 // Copyright (c) Microsoft Corporation. All rights reserved.
2 // Licensed under the MIT License. See LICENSE in the project root for license information.
3 using System.Collections;
4 using System.Collections.Generic;
5 using UnityEngine;
6 using UnityEditor;
7 
8 namespace HoloToolkit.Unity
9 {
14  [CustomPropertyDrawer(typeof(AudioEventAttribute))]
15  public class AudioEventPropertyDrawer : PropertyDrawer
16  {
20  private static GUIContent[] AudioEventNames;
21 
25  private static readonly string NoEventName = "-- None --";
26 
30  private static bool ShowBankNames;
31 
35  private class EventNameComparer : IComparer<GUIContent>
36  {
37  public int Compare(GUIContent x, GUIContent y)
38  {
39  return x.text.ToLower().CompareTo( y.text.ToLower() );
40  }
41  }
42 
43  public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
44  {
45  // Right click menu handler to enable / disable bank names in the list
46  // Having bank names does not affect the data stored in the property
47  if (Event.current.type == EventType.ContextClick)
48  {
49  GenericMenu menu = new GenericMenu();
50  menu.AddItem(new GUIContent("Show Banks", "Show bank names in the dropdown"), ShowBankNames, () => ShowBankNames = !ShowBankNames);
51  menu.ShowAsContext();
52  Event.current.Use();
53  }
54 
55  GetAllEventNames();
56 
57  var currentId = OptionToId(property.stringValue);
58  EditorGUI.BeginProperty(position, new GUIContent(property.name), property);
59  var newId = EditorGUI.Popup(position, label, currentId, AudioEventNames);
60 
61  // Do the necessary modification to property value
62  if (newId != currentId)
63  {
64  if (AudioEventNames[newId].text == NoEventName)
65  {
66  property.stringValue = string.Empty;
67  }
68  else
69  {
70  if (ShowBankNames)
71  {
72  // Remove the bank name before storing the string
73  int skip = AudioEventNames[newId].text.IndexOf('/') + 1;
74  property.stringValue = AudioEventNames[newId].text.Substring(skip);
75  }
76  else
77  {
78  property.stringValue = AudioEventNames[newId].text;
79  }
80  }
81  }
82 
83  EditorGUI.EndProperty();
84  }
85 
89  private static void GetAllEventNames()
90  {
91  List<GUIContent> eventNames = new List<GUIContent>(200);
92 
93  var assets = AssetDatabase.FindAssets("t:AudioEventBank");
94 
95  var audioBanks = Resources.FindObjectsOfTypeAll<AudioEventBank>();
96 
97  // Check all the banks are loaded and load them if they are not
98  if (audioBanks.Length != assets.Length)
99  {
100  List<AudioEventBank> tmpBanks = new List<AudioEventBank>(assets.Length);
101  for(int i=0; i<assets.Length; i++)
102  {
103  tmpBanks.Add(AssetDatabase.LoadAssetAtPath<AudioEventBank>(AssetDatabase.GUIDToAssetPath(assets[i])));
104  }
105  audioBanks = tmpBanks.ToArray();
106  }
107 
108  for (int bankIndex = 0; bankIndex < audioBanks.Length; bankIndex++)
109  {
110  var bank = audioBanks[bankIndex];
111  for (int eventIndex = 0; eventIndex < bank.Events.Length; eventIndex++)
112  {
113  if (ShowBankNames)
114  {
115  // Prepend the bank name to the string, "/" causes a sub-menu to appear
116  // Pro-Tip, place a "/" in your event name to further sub-divide the list of events
117  eventNames.Add(new GUIContent(bank.name + "/" + bank.Events[eventIndex].Name));
118  }
119  else
120  {
121  eventNames.Add(new GUIContent(bank.Events[eventIndex].Name));
122  }
123  }
124  }
125 
126  eventNames.Sort(new EventNameComparer());
127 
128  // Make sure the NoEventName is first in the list
129  eventNames.Insert(0, new GUIContent(NoEventName));
130 
131  AudioEventNames = eventNames.ToArray();
132  }
133 
139  private static int OptionToId(string option)
140  {
141  int optionIndex = 0;
142 
143  if (AudioEventNames != null)
144  {
145  for(int i=0; i<AudioEventNames.Length; i++)
146  {
147  if (ShowBankNames)
148  {
149  if (AudioEventNames[i].text.EndsWith(option))
150  {
151  optionIndex = i;
152  break;
153  }
154  }
155  else
156  {
157  if (AudioEventNames[i].text == option)
158  {
159  optionIndex = i;
160  break;
161  }
162  }
163  }
164  }
165 
166  return optionIndex;
167  }
168  }
169 }
override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
Instance of an AudioBank that contains AudioEvents
By applying the [AudioEvent] attribute to a string field, this PropertyDrawer is used instead of a st...