Files
trail-into-darkness/Packages/com.jovian.inspector/Editor/Tools/Internal/UnityObjectEditor.cs
2026-03-29 19:16:39 +02:00

150 lines
6.0 KiB
C#

using UnityEditor;
using UnityEngine;
#if UNITY_EDITOR
namespace Jovian.InspectorTools.Internal {
public interface IGUILayoutPropertyField {
void GUILayoutPropertyField(SerializedProperty serializedProperty, params GUILayoutOption[] options);
void GUILayoutPropertyField(SerializedProperty serializedProperty, bool includeChildren, params GUILayoutOption[] options);
void GUILayoutPropertyField(SerializedProperty serializedProperty, GUIContent label, bool includeChildren, params GUILayoutOption[] options);
}
[CustomEditor(typeof(Object), true)] [CanEditMultipleObjects]
public class UnityObjectEditor : Editor, IGUILayoutPropertyField {
private FoldoutAttributeHandler foldout;
private ButtonMethodHandler buttonMethod;
private ShowInInspectorAttributeHandler showInInspectorHandler;
private float lastShowInInspectorTime;
private static ButtonMethodHandler[] previewButtonMethods;
private static Vector2 previewScroll;
private Rect previewRect;
private void OnEnable() {
if(target == null) {
return;
}
foldout = new FoldoutAttributeHandler(target, serializedObject, this);
buttonMethod = new ButtonMethodHandler(target);
showInInspectorHandler = new ShowInInspectorAttributeHandler(target, serializedObject);
if (previewButtonMethods == null && target is Component component) {
previewScroll = Vector2.zero;
Component[] objectComponents = component.gameObject.GetComponents<Component>();
previewButtonMethods = new ButtonMethodHandler[objectComponents.Length];
for (int i = 0; i < objectComponents.Length; i++) {
previewButtonMethods[i] = new ButtonMethodHandler(objectComponents[i]);
}
}
EditorApplication.update -= OnUpdate;
EditorApplication.update += OnUpdate;
}
private void OnDisable() {
EditorApplication.update -= OnUpdate;
foldout?.OnDisable();
previewButtonMethods = null;
}
private void OnUpdate() {
if(showInInspectorHandler?.HasValues == true) {
float newShowInInspectorTime = Time.realtimeSinceStartup % 1f;
if(newShowInInspectorTime < lastShowInInspectorTime) {
Repaint();
}
lastShowInInspectorTime = newShowInInspectorTime;
}
}
public override void OnInspectorGUI() {
if (buttonMethod != null && buttonMethod.HasAnyVisibleMethods()) {
buttonMethod?.OnBeforeInspectorGUI();
EditorGUILayout.Space();
}
if(foldout != null) {
foldout.Update();
if(!foldout.OverrideInspector) {
base.OnInspectorGUI();
}
else {
foldout.OnInspectorGUI();
}
}
if(showInInspectorHandler != null) {
showInInspectorHandler.Update();
if(showInInspectorHandler.HasValues) {
showInInspectorHandler.OnInspectorGUI(this);
}
}
if(buttonMethod != null && buttonMethod.HasAnyVisibleMethods()){
EditorGUILayout.Space();
buttonMethod?.OnAfterInspectorGUI();
}
}
private static bool HasAnyVisiblePreviewMethods() {
if (previewButtonMethods == null) {
return false;
}
foreach (ButtonMethodHandler previewButtonMethod in previewButtonMethods) {
if (previewButtonMethod.HasAnyVisibleMethods()) {
return true;
}
}
return false;
}
public override bool HasPreviewGUI() => targets != null && targets.Length == 1 && target != null && HasAnyVisiblePreviewMethods();
public override void OnPreviewGUI(Rect r, GUIStyle background) {
// Only Repaint has the true Rect size - so store it whenever we repaint.
if (Event.current.type == EventType.Repaint) {
previewRect = r;
}
GUILayout.BeginArea(previewRect);
previewScroll = GUILayout.BeginScrollView(previewScroll);
foreach (ButtonMethodHandler previewButtonMethod in previewButtonMethods) {
if (previewButtonMethod.HasAnyVisibleMethods()) {
GUILayout.BeginVertical(EditorStyles.helpBox);
GUILayout.Label(ObjectNames.NicifyVariableName(previewButtonMethod.Target.GetType().Name), EditorStyles.boldLabel);
previewButtonMethod.OnBeforeInspectorGUI();
previewButtonMethod.OnAfterInspectorGUI();
GUILayout.EndVertical();
}
}
GUILayout.EndScrollView();
GUILayout.EndArea();
}
public void GUILayoutPropertyField(SerializedProperty serializedProperty, params GUILayoutOption[] options) {
GUILayoutPropertyField(serializedProperty, true, options);
}
public void GUILayoutPropertyField(SerializedProperty serializedProperty, bool includeChildren, params GUILayoutOption[] options) {
GUILayoutPropertyField(serializedProperty, new GUIContent(ObjectNames.NicifyVariableName(serializedProperty.name), serializedProperty.tooltip), includeChildren, options);
}
public void GUILayoutPropertyField(SerializedProperty serializedProperty, GUIContent label, bool includeChildren, params GUILayoutOption[] options) {
if (serializedProperty.isArray) {
ArrayAttributePropertyHandler.DrawArrayProperty(serializedProperty, label, includeChildren, options);
}
else {
EditorGUILayout.PropertyField(serializedProperty, label, includeChildren, options);
}
}
}
}
#endif