A game about forced loneliness, made by TACStudios
1#if UNITY_EDITOR 2using System; 3using System.Linq; 4using UnityEditor; 5using UnityEditor.IMGUI.Controls; 6 7namespace UnityEngine.InputSystem.Editor 8{ 9 internal class AdvancedDropdownGUI 10 { 11 private static class Styles 12 { 13 public static readonly GUIStyle toolbarSearchField = EditorStyles.toolbarSearchField; 14 public static readonly GUIStyle itemStyle = new GUIStyle("PR Label") 15 .WithAlignment(TextAnchor.MiddleLeft) 16 .WithPadding(new RectOffset()) 17 .WithMargin(new RectOffset()) 18 .WithFixedHeight(17); 19 public static readonly GUIStyle richTextItemStyle = new GUIStyle("PR Label") 20 .WithAlignment(TextAnchor.MiddleLeft) 21 .WithPadding(new RectOffset()) 22 .WithMargin(new RectOffset()) 23 .WithFixedHeight(17) 24 .WithRichText(); 25 public static readonly GUIStyle header = new GUIStyle("In BigTitle") 26 .WithFont(EditorStyles.boldLabel.font) 27 .WithMargin(new RectOffset()) 28 .WithBorder(new RectOffset(0, 0, 3, 3)) 29 .WithPadding(new RectOffset(6, 6, 6, 6)) 30 .WithContentOffset(Vector2.zero); 31 public static readonly GUIStyle headerArrow = new GUIStyle() 32 .WithAlignment(TextAnchor.MiddleCenter) 33 .WithFontSize(20) 34 .WithNormalTextColor(Color.gray); 35 public static readonly GUIStyle checkMark = new GUIStyle("PR Label") 36 .WithAlignment(TextAnchor.MiddleCenter) 37 .WithPadding(new RectOffset()) 38 .WithMargin(new RectOffset()) 39 .WithFixedHeight(17); 40 public static readonly GUIContent arrowRightContent = new GUIContent("▸"); 41 public static readonly GUIContent arrowLeftContent = new GUIContent("◂"); 42 } 43 44 //This should ideally match line height 45 private static readonly Vector2 s_IconSize = new Vector2(13, 13); 46 47 internal Rect m_SearchRect; 48 internal Rect m_HeaderRect; 49 private bool m_FocusSet; 50 51 internal virtual float searchHeight => m_SearchRect.height; 52 53 internal virtual float headerHeight => m_HeaderRect.height; 54 55 internal virtual GUIStyle lineStyle => Styles.itemStyle; 56 internal virtual GUIStyle richTextLineStyle => Styles.richTextItemStyle; 57 internal GUIStyle headerStyle => Styles.header; 58 59 internal virtual Vector2 iconSize => s_IconSize; 60 61 internal AdvancedDropdownState state { get; set; } 62 63 private readonly SearchField m_SearchField = new SearchField(); 64 65 public void Init() 66 { 67 m_FocusSet = false; 68 } 69 70 private const float k_IndentPerLevel = 20f; 71 72 internal virtual void BeginDraw(EditorWindow window) 73 { 74 } 75 76 internal virtual void EndDraw(EditorWindow window) 77 { 78 } 79 80 internal virtual void DrawItem(AdvancedDropdownItem item, string name, Texture2D icon, bool enabled, 81 bool drawArrow, bool selected, bool hasSearch, bool richText = false) 82 { 83 var content = new GUIContent(name, icon); 84 var imgTemp = content.image; 85 //we need to pretend we have an icon to calculate proper width in case 86 if (content.image == null) 87 content.image = Texture2D.whiteTexture; 88 var style = richText ? richTextLineStyle : lineStyle; 89 var rect = GUILayoutUtility.GetRect(content, style, GUILayout.ExpandWidth(true)); 90 content.image = imgTemp; 91 92 if (Event.current.type != EventType.Repaint) 93 return; 94 95 style.Draw(rect, GUIContent.none, false, false, selected, selected); 96 if (!hasSearch) 97 { 98 rect.x += item.indent * k_IndentPerLevel; 99 rect.width -= item.indent * k_IndentPerLevel; 100 } 101 102 var imageTemp = content.image; 103 if (content.image == null) 104 { 105 style.Draw(rect, GUIContent.none, false, false, selected, selected); 106 rect.x += iconSize.x + 1; 107 rect.width -= iconSize.x + 1; 108 } 109 rect.x += EditorGUIUtility.standardVerticalSpacing; 110 rect.width -= EditorGUIUtility.standardVerticalSpacing; 111 EditorGUI.BeginDisabledGroup(!enabled); 112 style.Draw(rect, content, false, false, selected, selected); 113 content.image = imageTemp; 114 if (drawArrow) 115 { 116 var size = style.lineHeight; 117 var arrowRect = new Rect(rect.x + rect.width - size, rect.y, size, size); 118 style.Draw(arrowRect, Styles.arrowRightContent, false, false, false, false); 119 } 120 EditorGUI.EndDisabledGroup(); 121 } 122 123 internal virtual void DrawHeader(AdvancedDropdownItem group, Action backButtonPressed, bool hasParent) 124 { 125 var content = new GUIContent(group.name, group.icon); 126 m_HeaderRect = GUILayoutUtility.GetRect(content, Styles.header, GUILayout.ExpandWidth(true)); 127 128 if (Event.current.type == EventType.Repaint) 129 Styles.header.Draw(m_HeaderRect, content, false, false, false, false); 130 131 // Back button 132 if (hasParent) 133 { 134 var arrowWidth = 13; 135 var arrowRect = new Rect(m_HeaderRect.x, m_HeaderRect.y, arrowWidth, m_HeaderRect.height); 136 if (Event.current.type == EventType.Repaint) 137 Styles.headerArrow.Draw(arrowRect, Styles.arrowLeftContent, false, false, false, false); 138 if (Event.current.type == EventType.MouseDown && m_HeaderRect.Contains(Event.current.mousePosition)) 139 { 140 backButtonPressed(); 141 Event.current.Use(); 142 } 143 } 144 } 145 146 internal virtual void DrawFooter(AdvancedDropdownItem selectedItem) 147 { 148 } 149 150 internal void DrawSearchField(bool isSearchFieldDisabled, string searchString, Action<string> searchChanged) 151 { 152 if (!isSearchFieldDisabled && !m_FocusSet) 153 { 154 m_FocusSet = true; 155 m_SearchField.SetFocus(); 156 } 157 158 using (new EditorGUI.DisabledScope(isSearchFieldDisabled)) 159 { 160 var newSearch = DrawSearchFieldControl(searchString); 161 162 if (newSearch != searchString) 163 { 164 searchChanged(newSearch); 165 } 166 } 167 } 168 169 internal virtual string DrawSearchFieldControl(string searchString) 170 { 171 var paddingX = 8f; 172 var paddingY = 2f; 173 var rect = GUILayoutUtility.GetRect(0, 0, Styles.toolbarSearchField); 174 //rect.x += paddingX; 175 rect.y += paddingY + 1; // Add one for the border 176 rect.height += Styles.toolbarSearchField.fixedHeight + paddingY * 3; 177 rect.width -= paddingX;// * 2; 178 m_SearchRect = rect; 179 searchString = m_SearchField.OnToolbarGUI(m_SearchRect, searchString); 180 return searchString; 181 } 182 183 internal Rect GetAnimRect(Rect position, float anim) 184 { 185 // Calculate rect for animated area 186 var rect = new Rect(position); 187 rect.x = position.x + position.width * anim; 188 rect.y += searchHeight; 189 rect.height -= searchHeight; 190 return rect; 191 } 192 193 internal Vector2 CalculateContentSize(AdvancedDropdownDataSource dataSource) 194 { 195 var maxWidth = 0f; 196 var maxHeight = 0f; 197 var includeArrow = false; 198 var arrowWidth = 0f; 199 200 foreach (var child in dataSource.mainTree.children) 201 { 202 var content = new GUIContent(child.name, child.icon); 203 var a = lineStyle.CalcSize(content); 204 a.x += iconSize.x + 1; 205 206 if (maxWidth < a.x) 207 { 208 maxWidth = a.x + 1; 209 includeArrow |= child.children.Any(); 210 } 211 if (child.IsSeparator()) 212 { 213 maxHeight += GUIHelpers.Styles.lineSeparator.CalcHeight(content, maxWidth) + GUIHelpers.Styles.lineSeparator.margin.vertical; 214 } 215 else 216 { 217 maxHeight += lineStyle.CalcHeight(content, maxWidth); 218 } 219 if (arrowWidth == 0) 220 { 221 lineStyle.CalcMinMaxWidth(Styles.arrowRightContent, out arrowWidth, out arrowWidth); 222 } 223 } 224 if (includeArrow) 225 { 226 maxWidth += arrowWidth; 227 } 228 return new Vector2(maxWidth, maxHeight); 229 } 230 231 internal float GetSelectionHeight(AdvancedDropdownDataSource dataSource, Rect buttonRect) 232 { 233 if (state.GetSelectedIndex(dataSource.mainTree) == -1) 234 return 0; 235 var height = 0f; 236 for (var i = 0; i < dataSource.mainTree.children.Count(); i++) 237 { 238 var child = dataSource.mainTree.children.ElementAt(i); 239 var content = new GUIContent(child.name, child.icon); 240 if (state.GetSelectedIndex(dataSource.mainTree) == i) 241 { 242 var diff = (lineStyle.CalcHeight(content, 0) - buttonRect.height) / 2f; 243 return height + diff; 244 } 245 if (child.IsSeparator()) 246 { 247 height += GUIHelpers.Styles.lineSeparator.CalcHeight(content, 0) + GUIHelpers.Styles.lineSeparator.margin.vertical; 248 } 249 else 250 { 251 height += lineStyle.CalcHeight(content, 0); 252 } 253 } 254 return height; 255 } 256 } 257} 258 259#endif // UNITY_EDITOR