77
88namespace Toolbox . Editor . Hierarchy
99{
10- //TODO: refactor
10+ //TODO: refactor: replace labels with drawers (similar approach to the Inspector), possibility to define drawers and implement them using a dedicated base class
1111
1212 /// <summary>
1313 /// Base class for all custom, Hierarchy-related labels based on targeted <see cref="GameObject"/>.
@@ -16,16 +16,6 @@ public abstract class HierarchyPropertyLabel
1616 {
1717 protected GameObject target ;
1818
19- /// <summary>
20- /// Does this label draw over the whole item?
21- /// </summary>
22- public virtual bool UsesWholeItemRect { get ; } = false ;
23-
24- /// <summary>
25- /// Should this label draw for headers too?
26- /// </summary>
27- public virtual bool DrawForHeaders { get ; } = false ;
28-
2919 public virtual bool Prepare ( GameObject target , Rect availableRect )
3020 {
3121 return this . target = target ;
@@ -52,7 +42,6 @@ public virtual float GetWidth()
5242
5343 public abstract void OnGui ( Rect rect ) ;
5444
55-
5645 /// <summary>
5746 /// Returns built-in label class associated to provided <see cref="HierarchyItemDataType"/>.
5847 /// </summary>
@@ -77,31 +66,44 @@ public static HierarchyPropertyLabel GetPropertyLabel(HierarchyItemDataType data
7766 return null ;
7867 }
7968
69+ /// <summary>
70+ /// Does this label draw over the whole item?
71+ /// </summary>
72+ public virtual bool UsesWholeItemRect { get ; } = false ;
73+
74+ /// <summary>
75+ /// Should this label draw for headers too?
76+ /// </summary>
77+ public virtual bool DrawForHeaders { get ; } = false ;
78+
8079 #region Classes: Internal
8180
8281 private class HierarchyIconLabel : HierarchyPropertyLabel
8382 {
8483 public override void OnGui ( Rect rect )
8584 {
8685 var content = EditorGuiUtility . GetObjectContent ( target , typeof ( GameObject ) ) ;
87- if ( content . image )
86+ if ( content . image == null )
8887 {
89- GUI . Label ( rect , content . image ) ;
88+ return ;
9089 }
90+
91+ GUI . Label ( rect , content . image ) ;
9192 }
9293 }
9394
9495 private class HierarchyToggleLabel : HierarchyPropertyLabel
9596 {
97+ private readonly GUIContent label = new GUIContent ( string . Empty , "Enable/disable GameObject" ) ;
98+
9699 public override void OnGui ( Rect rect )
97100 {
98- var content = new GUIContent ( string . Empty , "Enable/disable GameObject" ) ;
99101 //NOTE: using EditorGUI.Toggle will cause bug and deselect all hierarchy toggles when you will pick a multi-selected property in the Inspector
100102 var result = GUI . Toggle ( new Rect ( rect . x + EditorGUIUtility . standardVerticalSpacing ,
101103 rect . y ,
102104 rect . width ,
103105 rect . height ) ,
104- target . activeSelf , content ) ;
106+ target . activeSelf , label ) ;
105107
106108 if ( rect . Contains ( Event . current . mousePosition ) )
107109 {
@@ -116,14 +118,16 @@ public override void OnGui(Rect rect)
116118
117119 private class HierarchyTagLabel : HierarchyPropertyLabel
118120 {
121+ private const string untaggedTag = "Untagged" ;
122+
119123 public override float GetWidth ( )
120124 {
121125 return Style . maxWidth ;
122126 }
123127
124128 public override void OnGui ( Rect rect )
125129 {
126- var content = new GUIContent ( target . CompareTag ( "Untagged" ) ? string . Empty : target . tag , target . tag ) ;
130+ var content = new GUIContent ( target . CompareTag ( untaggedTag ) ? string . Empty : target . tag , target . tag ) ;
127131 EditorGUI . LabelField ( rect , content , Style . defaultAlignTextStyle ) ;
128132 }
129133 }
@@ -165,18 +169,19 @@ private class HierarchyScriptLabel : HierarchyPropertyLabel
165169 /// </summary>
166170 private List < Component > cachedComponents ;
167171
168-
169172 private void CacheComponents ( GameObject target )
170173 {
171174 var components = target . GetComponents < Component > ( ) ;
172175 cachedComponents = new List < Component > ( components . Length ) ;
173176 //cache only valid (non-null) components
174177 foreach ( var component in components )
175178 {
176- if ( component )
179+ if ( component == null )
177180 {
178- cachedComponents . Add ( component ) ;
181+ continue ;
179182 }
183+
184+ cachedComponents . Add ( component ) ;
180185 }
181186 }
182187
@@ -212,7 +217,6 @@ private GUIContent GetContent(Component component)
212217 return content ;
213218 }
214219
215-
216220 public override bool Prepare ( GameObject target , Rect availableRect )
217221 {
218222 var isValid = base . Prepare ( target , availableRect ) ;
@@ -302,27 +306,27 @@ private class HierarchyTreeLinesLabel : HierarchyPropertyLabel, IDisposable
302306 private const float columnSize = 14.0f ;
303307
304308 private readonly List < TreeLineLevelRenderer > levelRenderers = new List < TreeLineLevelRenderer > ( ) ;
309+
305310 private int itemRenderCount = 0 ;
306311
307312 public HierarchyTreeLinesLabel ( )
308313 {
309- EditorApplication . update += ResetItemRenderCount ;
314+ EditorApplication . update += ResetItemRenderCount ;
310315 }
311316
312317 public void Dispose ( )
313318 {
314319 EditorApplication . update -= ResetItemRenderCount ;
315320 }
316321
317- public override sealed void OnGui ( Rect rect )
322+ public sealed override void OnGui ( Rect rect )
318323 {
319324 if ( Event . current . type != EventType . Repaint )
320325 {
321326 return ;
322327 }
323328
324329 var levels = ( int ) ( ( rect . x + firstElementXOffset ) / columnSize ) ;
325-
326330 if ( levels <= 0 )
327331 {
328332 return ;
@@ -354,18 +358,18 @@ public override sealed void OnGui(Rect rect)
354358
355359 x -- ;
356360
357- Transform transformBuffer = targetTransform ;
361+ var transformBuffer = targetTransform ;
358362 for ( ; x >= startIndex ; x -- )
359363 {
360364 levelRenderers [ x ] . Initialize ( transformBuffer ) ;
361365 transformBuffer = transformBuffer . parent ;
362366 }
363367 }
364368
365- Color colorCache = GUI . color ;
369+ var colorCache = GUI . color ;
366370 GUI . color = Color . gray ;
367371
368- int i = 0 ;
372+ var i = 0 ;
369373 for ( ; i < ( levels - 1 ) ; i ++ )
370374 {
371375 levelRenderers [ i ] . OnGUI ( rect , target , siblingIndex , false ) ;
@@ -382,9 +386,9 @@ private void ResetItemRenderCount()
382386 itemRenderCount = 0 ;
383387 }
384388
385- public override sealed bool UsesWholeItemRect => true ;
389+ public sealed override bool UsesWholeItemRect => true ;
386390
387- public override sealed bool DrawForHeaders => true ;
391+ public sealed override bool DrawForHeaders => true ;
388392
389393 private bool IsFirstRenderedElement => itemRenderCount == 0 ;
390394
@@ -463,6 +467,8 @@ protected static class Style
463467 internal static readonly GUIContent elementCross ;
464468 internal static readonly GUIContent elementPass ;
465469
470+ internal static readonly Color characterColor ;
471+
466472 static Style ( )
467473 {
468474 elementLast = new GUIContent ( "└" ) ;
@@ -501,6 +507,11 @@ static Style()
501507 {
502508 fontSize = 18 ,
503509 } ;
510+
511+ if ( ! EditorGUIUtility . isProSkin )
512+ {
513+ centreAlignTreeLineStyle . normal . textColor = Color . white ;
514+ }
504515 }
505516 }
506517 }
0 commit comments