-
Notifications
You must be signed in to change notification settings - Fork 0
/
ComponentTitlebarGUI.cs
117 lines (105 loc) · 3.47 KB
/
ComponentTitlebarGUI.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
using System;
using System.Collections.Generic;
using System.Reflection;
using Unity.Profiling;
using UnityEngine;
using UnityEngine.UIElements;
using Object = UnityEngine.Object;
namespace UnityEditor.Custom
{
public static class ComponentTitlebarGUI
{
public static Action<Rect, Object> OnTitlebarGUI;
#if UNITY_EDITOR
private static ProfilerMarker _profileMarker = new ProfilerMarker($"{nameof(ComponentTitlebarGUI)}.{nameof(OnUpdate)}");
private static ProfilerMarker _profileMarker2 = new ProfilerMarker($"{nameof(ComponentTitlebarGUI)}.OnTitlebarGUI");
private static Type type = typeof(EditorWindow).Assembly.GetType("UnityEditor.InspectorWindow");
private static Type type2 = typeof(EditorWindow).Assembly.GetType("UnityEditor.PropertyEditor");
private static Type type3 = typeof(EditorWindow).Assembly.GetType("UnityEditor.UIElements.EditorElement");
private static FieldInfo field = type2.GetField("m_EditorsElement", BindingFlags.NonPublic | BindingFlags.Instance);
private static FieldInfo field2 = type3.GetField("m_Header", BindingFlags.NonPublic | BindingFlags.Instance);
private static FieldInfo field3 = type3.GetField("m_EditorTarget", BindingFlags.NonPublic | BindingFlags.Instance);
private static VisualElement m_EditorsElement;
private static VisualElement editorsElement => m_EditorsElement ??= GetEditorVisualElement();
private static Dictionary<VisualElement, Action> _callbacks = new();
private static VisualElement GetEditorVisualElement()
{
EditorWindow window = EditorWindow.GetWindow(type);
if (window)
{
return field.GetValue(window) as VisualElement;
}
return null;
}
[InitializeOnLoadMethod]
public static void Init()
{
EditorApplication.update -= OnUpdate;
EditorApplication.update += OnUpdate;
Selection.selectionChanged -= OnSelectionChanged;
Selection.selectionChanged += OnSelectionChanged;
}
private static void OnSelectionChanged() => _callbacks.Clear();
private static void OnUpdate()
{
using (_profileMarker.Auto())
{
VisualElement inspectorRoot = editorsElement;
if (inspectorRoot == null) return;
var foundAll = editorsElement.Children();
foreach (VisualElement element in foundAll)
{
if (element.GetType() != type3) continue;
var localTarget = field3.GetValue(element) as Object;
if (localTarget)
{
IMGUIContainer value2 = field2.GetValue(element) as IMGUIContainer;
Action callback = null;
if (_callbacks.TryGetValue(element, out var found))
{
callback = found;
}
else
{
callback = _callbacks[element] = MyLocalCallback;
}
if (value2 != null)
{
value2.onGUIHandler -= callback;
value2.onGUIHandler += callback;
}
void MyLocalCallback()
{
using (_profileMarker2.Auto())
{
try
{
OnTitlebarGUI?.Invoke(GUILayoutUtility.GetLastRect(), localTarget);
}
catch (Exception e)
{
Debug.LogException(e);
}
}
}
}
}
}
}
//private static GUIContent content = EditorGUIUtility.IconContent("console.erroricon.sml");
// [InitializeOnLoadMethod]
// public static void InitTest()
// {
// ComponentTitlebarGUI.OnTitlebarGUI -= TestGUI;
// ComponentTitlebarGUI.OnTitlebarGUI += TestGUI;
// }
//
// private static void TestGUI(Rect rect, Object target)
// {
// if (target is not MonoBehaviour) return;
//
// GUI.Label(rect, content);
// }
#endif
}
}