Adding back rest of the menu, ported most of Reflection Inspector for new UI

This commit is contained in:
Sinai
2021-04-25 00:21:12 +10:00
parent 0cf8309a82
commit 6d4cc66079
44 changed files with 5995 additions and 350 deletions

View File

@ -0,0 +1,193 @@
//using System;
//using System.Collections.Generic;
//using System.Linq;
//using System.Text;
//using UnityEngine;
//using UnityEngine.UI;
//using UnityExplorer.Core.Runtime;
//using UnityExplorer.UI.Utility;
//namespace UnityExplorer.UI.Inspectors.GameObjects
//{
// public class ChildList
// {
// internal static ChildList Instance;
// public ChildList()
// {
// Instance = this;
// }
// public static PageHandler s_childListPageHandler;
// private static GameObject s_childListContent;
// private static GameObject[] s_allChildren = new GameObject[0];
// private static readonly List<GameObject> s_childrenShortlist = new List<GameObject>();
// private static int s_lastChildCount;
// private static readonly List<Text> s_childListTexts = new List<Text>();
// private static readonly List<Toggle> s_childListToggles = new List<Toggle>();
// internal void RefreshChildObjectList()
// {
// var go = GameObjectInspector.ActiveInstance.TargetGO;
// s_allChildren = new GameObject[go.transform.childCount];
// for (int i = 0; i < go.transform.childCount; i++)
// {
// var child = go.transform.GetChild(i);
// s_allChildren[i] = child.gameObject;
// }
// var objects = s_allChildren;
// s_childListPageHandler.ListCount = objects.Length;
// int newCount = 0;
// foreach (var itemIndex in s_childListPageHandler)
// {
// newCount++;
// // normalized index starting from 0
// var i = itemIndex - s_childListPageHandler.StartIndex;
// if (itemIndex >= objects.Length)
// {
// if (i > s_lastChildCount || i >= s_childListTexts.Count)
// break;
// GameObject label = s_childListTexts[i].transform.parent.parent.gameObject;
// if (label.activeSelf)
// label.SetActive(false);
// }
// else
// {
// GameObject obj = objects[itemIndex];
// if (!obj)
// continue;
// if (i >= s_childrenShortlist.Count)
// {
// s_childrenShortlist.Add(obj);
// AddChildListButton();
// }
// else
// {
// s_childrenShortlist[i] = obj;
// }
// var text = s_childListTexts[i];
// var name = obj.name;
// if (obj.transform.childCount > 0)
// name = $"<color=grey>[{obj.transform.childCount}]</color> {name}";
// text.text = name;
// text.color = obj.activeSelf ? Color.green : Color.red;
// var tog = s_childListToggles[i];
// tog.isOn = obj.activeSelf;
// var label = text.transform.parent.parent.gameObject;
// if (!label.activeSelf)
// {
// label.SetActive(true);
// }
// }
// }
// s_lastChildCount = newCount;
// }
// internal static void OnChildListObjectClicked(int index)
// {
// if (GameObjectInspector.ActiveInstance == null)
// return;
// if (index >= s_childrenShortlist.Count || !s_childrenShortlist[index])
// return;
// GameObjectInspector.ActiveInstance.ChangeInspectorTarget(s_childrenShortlist[index]);
// GameObjectInspector.ActiveInstance.Update();
// }
// internal static void OnChildListPageTurn()
// {
// if (Instance == null)
// return;
// Instance.RefreshChildObjectList();
// }
// internal static void OnToggleClicked(int index, bool newVal)
// {
// if (GameObjectInspector.ActiveInstance == null)
// return;
// if (index >= s_childrenShortlist.Count || !s_childrenShortlist[index])
// return;
// var obj = s_childrenShortlist[index];
// obj.SetActive(newVal);
// }
// #region UI CONSTRUCTION
// internal void ConstructChildList(GameObject parent)
// {
// var vertGroupObj = UIFactory.CreateVerticalGroup(parent, "ChildListGroup", false, true, true, true, 5, default, new Color(1, 1, 1, 0));
// UIFactory.SetLayoutElement(vertGroupObj, minWidth: 120, flexibleWidth: 25000, minHeight: 200, flexibleHeight: 5000);
// var childTitle = UIFactory.CreateLabel(vertGroupObj, "ChildListTitle", "Children:", TextAnchor.MiddleLeft, Color.grey, true, 14);
// UIFactory.SetLayoutElement(childTitle.gameObject, minHeight: 30);
// var childrenScrollObj = UIFactory.CreateScrollView(vertGroupObj, "ChildListScrollView", out s_childListContent,
// out SliderScrollbar scroller, new Color(0.07f, 0.07f, 0.07f));
// UIFactory.SetLayoutElement(childrenScrollObj, minHeight: 50);
// s_childListPageHandler = new PageHandler(scroller);
// s_childListPageHandler.ConstructUI(vertGroupObj);
// s_childListPageHandler.OnPageChanged += OnChildListPageTurn;
// }
// internal void AddChildListButton()
// {
// int thisIndex = s_childListTexts.Count;
// var btnGroupObj = UIFactory.CreateHorizontalGroup(s_childListContent, "ChildButtonGroup", true, false, true, true,
// 0, default, new Color(0.07f, 0.07f, 0.07f));
// UIFactory.SetLayoutElement(btnGroupObj, flexibleWidth: 320, minHeight: 25, flexibleHeight: 0);
// btnGroupObj.AddComponent<Mask>();
// var toggleObj = UIFactory.CreateToggle(btnGroupObj, "Toggle", out Toggle toggle, out Text toggleText, new Color(0.3f, 0.3f, 0.3f));
// UIFactory.SetLayoutElement(toggleObj, minHeight: 25, minWidth: 25);
// toggleText.text = "";
// toggle.isOn = false;
// s_childListToggles.Add(toggle);
// toggle.onValueChanged.AddListener((bool val) => { OnToggleClicked(thisIndex, val); });
// var mainBtn = UIFactory.CreateButton(btnGroupObj,
// "MainButton",
// "",
// () => { OnChildListObjectClicked(thisIndex); });
// RuntimeProvider.Instance.SetColorBlock(mainBtn, new Color(0.07f, 0.07f, 0.07f),
// new Color(0.2f, 0.2f, 0.2f, 1), new Color(0.05f, 0.05f, 0.05f));
// UIFactory.SetLayoutElement(mainBtn.gameObject, minHeight: 25, flexibleHeight: 0, minWidth: 25, flexibleWidth: 9999);
// Text mainText = mainBtn.GetComponentInChildren<Text>();
// mainText.alignment = TextAnchor.MiddleLeft;
// mainText.horizontalOverflow = HorizontalWrapMode.Overflow;
// mainText.resizeTextForBestFit = true;
// mainText.resizeTextMaxSize = 14;
// mainText.resizeTextMinSize = 10;
// s_childListTexts.Add(mainText);
// }
// #endregion
// }
//}

View File

@ -0,0 +1,192 @@
//using System;
//using System.Collections.Generic;
//using System.Linq;
//using System.Text;
//using UnityEngine;
//using UnityEngine.UI;
//using UnityExplorer.Core;
//using UnityExplorer.Core.Runtime;
//using UnityExplorer.UI.Utility;
//namespace UnityExplorer.UI.Inspectors.GameObjects
//{
// public class ComponentList
// {
// internal static ComponentList Instance;
// public ComponentList()
// {
// Instance = this;
// }
// public static PageHandler s_compListPageHandler;
// private static Component[] s_allComps = new Component[0];
// private static readonly List<Component> s_compShortlist = new List<Component>();
// private static GameObject s_compListContent;
// private static readonly List<Text> s_compListTexts = new List<Text>();
// private static int s_lastCompCount;
// public static readonly List<Toggle> s_compToggles = new List<Toggle>();
// internal void RefreshComponentList()
// {
// var go = GameObjectInspector.ActiveInstance.TargetGO;
// s_allComps = go.GetComponents<Component>().ToArray();
// var components = s_allComps;
// s_compListPageHandler.ListCount = components.Length;
// //int startIndex = m_sceneListPageHandler.StartIndex;
// int newCount = 0;
// foreach (var itemIndex in s_compListPageHandler)
// {
// newCount++;
// // normalized index starting from 0
// var i = itemIndex - s_compListPageHandler.StartIndex;
// if (itemIndex >= components.Length)
// {
// if (i > s_lastCompCount || i >= s_compListTexts.Count)
// break;
// GameObject label = s_compListTexts[i].transform.parent.parent.gameObject;
// if (label.activeSelf)
// label.SetActive(false);
// }
// else
// {
// Component comp = components[itemIndex];
// if (!comp)
// continue;
// if (i >= s_compShortlist.Count)
// {
// s_compShortlist.Add(comp);
// AddCompListButton();
// }
// else
// {
// s_compShortlist[i] = comp;
// }
// var text = s_compListTexts[i];
// text.text = SignatureHighlighter.ParseFullSyntax(ReflectionUtility.GetActualType(comp), true);
// var toggle = s_compToggles[i];
// if (comp.TryCast<Behaviour>() is Behaviour behaviour)
// {
// if (!toggle.gameObject.activeSelf)
// toggle.gameObject.SetActive(true);
// toggle.isOn = behaviour.enabled;
// }
// else
// {
// if (toggle.gameObject.activeSelf)
// toggle.gameObject.SetActive(false);
// }
// var label = text.transform.parent.parent.gameObject;
// if (!label.activeSelf)
// {
// label.SetActive(true);
// }
// }
// }
// s_lastCompCount = newCount;
// }
// internal static void OnCompToggleClicked(int index, bool value)
// {
// var comp = s_compShortlist[index];
// comp.TryCast<Behaviour>().enabled = value;
// }
// internal static void OnCompListObjectClicked(int index)
// {
// if (index >= s_compShortlist.Count || !s_compShortlist[index])
// return;
// InspectorManager.Instance.Inspect(s_compShortlist[index]);
// }
// internal static void OnCompListPageTurn()
// {
// if (Instance == null)
// return;
// Instance.RefreshComponentList();
// }
// #region UI CONSTRUCTION
// internal void ConstructCompList(GameObject parent)
// {
// var vertGroupObj = UIFactory.CreateVerticalGroup(parent, "ComponentList", false, true, true, true, 5, default, new Color(1, 1, 1, 0));
// UIFactory.SetLayoutElement(vertGroupObj, minWidth: 120, flexibleWidth: 25000, minHeight: 200, flexibleHeight: 5000);
// var compTitle = UIFactory.CreateLabel(vertGroupObj, "ComponentsTitle", "Components:", TextAnchor.MiddleLeft, Color.grey);
// UIFactory.SetLayoutElement(compTitle.gameObject, minHeight: 30);
// var compScrollObj = UIFactory.CreateScrollView(vertGroupObj, "ComponentListScrollView", out s_compListContent,
// out SliderScrollbar scroller, new Color(0.07f, 0.07f, 0.07f));
// UIFactory.SetLayoutElement(compScrollObj, minHeight: 50, flexibleHeight: 5000);
// s_compListPageHandler = new PageHandler(scroller);
// s_compListPageHandler.ConstructUI(vertGroupObj);
// s_compListPageHandler.OnPageChanged += OnCompListPageTurn;
// }
// internal void AddCompListButton()
// {
// int thisIndex = s_compListTexts.Count;
// GameObject groupObj = UIFactory.CreateHorizontalGroup(s_compListContent, "CompListButton", true, false, true, true, 0, default,
// new Color(0.07f, 0.07f, 0.07f), TextAnchor.MiddleLeft);
// UIFactory.SetLayoutElement(groupObj, minWidth: 25, flexibleWidth: 999, minHeight: 25, flexibleHeight: 0);
// groupObj.AddComponent<Mask>();
// // Behaviour enabled toggle
// var toggleObj = UIFactory.CreateToggle(groupObj, "EnabledToggle", out Toggle toggle, out Text toggleText, new Color(0.3f, 0.3f, 0.3f));
// UIFactory.SetLayoutElement(toggleObj, minWidth: 25, minHeight: 25);
// toggleText.text = "";
// toggle.isOn = true;
// s_compToggles.Add(toggle);
// toggle.onValueChanged.AddListener((bool val) => { OnCompToggleClicked(thisIndex, val); });
// // Main component button
// var mainBtn = UIFactory.CreateButton(groupObj,
// "MainButton",
// "",
// () => { OnCompListObjectClicked(thisIndex); });
// RuntimeProvider.Instance.SetColorBlock(mainBtn, new Color(0.07f, 0.07f, 0.07f),
// new Color(0.2f, 0.2f, 0.2f, 1), new Color(0.05f, 0.05f, 0.05f));
// UIFactory.SetLayoutElement(mainBtn.gameObject, minHeight: 25, flexibleHeight: 0, minWidth: 25, flexibleWidth: 999);
// // Component button text
// Text mainText = mainBtn.GetComponentInChildren<Text>();
// mainText.alignment = TextAnchor.MiddleLeft;
// mainText.horizontalOverflow = HorizontalWrapMode.Overflow;
// mainText.resizeTextForBestFit = true;
// mainText.resizeTextMaxSize = 14;
// mainText.resizeTextMinSize = 8;
// s_compListTexts.Add(mainText);
// }
// #endregion
// }
//}

View File

@ -0,0 +1,467 @@
//using System;
//using System.Collections.Generic;
//using System.Linq;
//using System.Text;
//using UnityEngine;
//using UnityEngine.UI;
//using UnityExplorer.Core.Input;
//using UnityExplorer.Core.Runtime;
//namespace UnityExplorer.UI.Inspectors.GameObjects
//{
// public class GameObjectControls
// {
// internal static GameObjectControls Instance;
// public GameObjectControls()
// {
// Instance = this;
// }
// internal static bool Showing;
// internal static void ToggleVisibility() => SetVisibility(!Showing);
// internal static void SetVisibility(bool show)
// {
// if (show == Showing)
// return;
// Showing = show;
// m_hideShowLabel.text = show ? "Hide" : "Show";
// m_contentObj.SetActive(show);
// }
// internal static GameObject m_contentObj;
// internal static Text m_hideShowLabel;
// private static InputField s_setParentInput;
// private static ControlEditor s_positionControl;
// private static ControlEditor s_localPosControl;
// private static ControlEditor s_rotationControl;
// private static ControlEditor s_scaleControl;
// // Transform Vector editors
// internal struct ControlEditor
// {
// public InputField fullValue;
// public Slider[] sliders;
// public InputField[] inputs;
// public Text[] values;
// }
// internal static bool s_sliderChangedWanted;
// private static Slider s_currentSlider;
// private static ControlType s_currentSliderType;
// private static VectorValue s_currentSliderValueType;
// private static float s_currentSliderValue;
// internal enum ControlType
// {
// position,
// localPosition,
// eulerAngles,
// localScale
// }
// internal enum VectorValue
// {
// x, y, z
// };
// internal void RefreshControls()
// {
// var go = GameObjectInspector.ActiveInstance.TargetGO;
// s_positionControl.fullValue.text = go.transform.position.ToStringPretty();
// s_positionControl.values[0].text = go.transform.position.x.ToString("F3");
// s_positionControl.values[1].text = go.transform.position.y.ToString("F3");
// s_positionControl.values[2].text = go.transform.position.z.ToString("F3");
// s_localPosControl.fullValue.text = go.transform.localPosition.ToStringPretty();
// s_localPosControl.values[0].text = go.transform.localPosition.x.ToString("F3");
// s_localPosControl.values[1].text = go.transform.localPosition.y.ToString("F3");
// s_localPosControl.values[2].text = go.transform.localPosition.z.ToString("F3");
// s_rotationControl.fullValue.text = go.transform.eulerAngles.ToStringPretty();
// s_rotationControl.values[0].text = go.transform.eulerAngles.x.ToString("F3");
// s_rotationControl.values[1].text = go.transform.eulerAngles.y.ToString("F3");
// s_rotationControl.values[2].text = go.transform.eulerAngles.z.ToString("F3");
// s_scaleControl.fullValue.text = go.transform.localScale.ToStringPretty();
// s_scaleControl.values[0].text = go.transform.localScale.x.ToString("F3");
// s_scaleControl.values[1].text = go.transform.localScale.y.ToString("F3");
// s_scaleControl.values[2].text = go.transform.localScale.z.ToString("F3");
// }
// internal static void OnSetParentClicked()
// {
// var go = GameObjectInspector.ActiveInstance.TargetGO;
// if (!go)
// return;
// var input = s_setParentInput.text;
// if (string.IsNullOrEmpty(input))
// {
// go.transform.parent = null;
// }
// else
// {
// if (GameObject.Find(input) is GameObject newParent)
// {
// go.transform.parent = newParent.transform;
// }
// else
// {
// ExplorerCore.Log($"Could not find any GameObject from name or path '{input}'! Note: The target must be enabled.");
// }
// }
// }
// internal static void OnSliderControlChanged(float value, Slider slider, ControlType controlType, VectorValue vectorValue)
// {
// if (value == 0)
// s_sliderChangedWanted = false;
// else
// {
// if (!s_sliderChangedWanted)
// {
// s_sliderChangedWanted = true;
// s_currentSlider = slider;
// s_currentSliderType = controlType;
// s_currentSliderValueType = vectorValue;
// }
// s_currentSliderValue = value;
// }
// }
// internal static void UpdateSliderControl()
// {
// if (!InputManager.GetMouseButton(0))
// {
// s_sliderChangedWanted = false;
// s_currentSlider.value = 0;
// return;
// }
// if (GameObjectInspector.ActiveInstance == null) return;
// var transform = GameObjectInspector.ActiveInstance.TargetGO.transform;
// // get the current vector for the control type
// Vector3 vector = Vector2.zero;
// switch (s_currentSliderType)
// {
// case ControlType.position:
// vector = transform.position; break;
// case ControlType.localPosition:
// vector = transform.localPosition; break;
// case ControlType.eulerAngles:
// vector = transform.eulerAngles; break;
// case ControlType.localScale:
// vector = transform.localScale; break;
// }
// // apply vector value change
// switch (s_currentSliderValueType)
// {
// case VectorValue.x:
// vector.x += s_currentSliderValue; break;
// case VectorValue.y:
// vector.y += s_currentSliderValue; break;
// case VectorValue.z:
// vector.z += s_currentSliderValue; break;
// }
// // set vector to transform member
// switch (s_currentSliderType)
// {
// case ControlType.position:
// transform.position = vector; break;
// case ControlType.localPosition:
// transform.localPosition = vector; break;
// case ControlType.eulerAngles:
// transform.eulerAngles = vector; break;
// case ControlType.localScale:
// transform.localScale = vector; break;
// }
// }
// internal static void OnVectorControlInputApplied(ControlType controlType, VectorValue vectorValue)
// {
// if (!(InspectorManager.Instance.m_activeInspector is GameObjectInspector instance)) return;
// // get relevant input for controltype + value
// InputField[] inputs = null;
// switch (controlType)
// {
// case ControlType.position:
// inputs = s_positionControl.inputs; break;
// case ControlType.localPosition:
// inputs = s_localPosControl.inputs; break;
// case ControlType.eulerAngles:
// inputs = s_rotationControl.inputs; break;
// case ControlType.localScale:
// inputs = s_scaleControl.inputs; break;
// }
// InputField input = inputs[(int)vectorValue];
// float val = float.Parse(input.text);
// // apply transform value
// Vector3 vector = Vector3.zero;
// var transform = instance.TargetGO.transform;
// switch (controlType)
// {
// case ControlType.position:
// vector = transform.position; break;
// case ControlType.localPosition:
// vector = transform.localPosition; break;
// case ControlType.eulerAngles:
// vector = transform.eulerAngles; break;
// case ControlType.localScale:
// vector = transform.localScale; break;
// }
// switch (vectorValue)
// {
// case VectorValue.x:
// vector.x = val; break;
// case VectorValue.y:
// vector.y = val; break;
// case VectorValue.z:
// vector.z = val; break;
// }
// // set back to transform
// switch (controlType)
// {
// case ControlType.position:
// transform.position = vector; break;
// case ControlType.localPosition:
// transform.localPosition = vector; break;
// case ControlType.eulerAngles:
// transform.eulerAngles = vector; break;
// case ControlType.localScale:
// transform.localScale = vector; break;
// }
// }
// //#region UI CONSTRUCTION
// //internal void ConstructControls(GameObject parent)
// //{
// // var mainGroup = UIFactory.CreateVerticalGroup(parent, "ControlsGroup", false, false, true, true, 5, new Vector4(4,4,4,4),
// // new Color(0.07f, 0.07f, 0.07f));
// // // ~~~~~~ Top row ~~~~~~
// // var topRow = UIFactory.CreateHorizontalGroup(mainGroup, "TopRow", false, false, true, true, 5, default, new Color(1, 1, 1, 0));
// // var hideButton = UIFactory.CreateButton(topRow, "ToggleShowButton", "Show", ToggleVisibility, new Color(0.16f, 0.16f, 0.16f));
// // UIFactory.SetLayoutElement(hideButton.gameObject, minWidth: 40, flexibleWidth: 0, minHeight: 25, flexibleHeight: 0);
// // m_hideShowLabel = hideButton.GetComponentInChildren<Text>();
// // var topTitle = UIFactory.CreateLabel(topRow, "ControlsLabel", "Controls", TextAnchor.MiddleLeft);
// // UIFactory.SetLayoutElement(topTitle.gameObject, minWidth: 100, flexibleWidth: 9500, minHeight: 25);
// // //// ~~~~~~~~ Content ~~~~~~~~ //
// // m_contentObj = UIFactory.CreateVerticalGroup(mainGroup, "ContentGroup", true, false, true, true, 5, default, new Color(1, 1, 1, 0));
// // // transform controls
// // ConstructVector3Editor(m_contentObj, "Position", ControlType.position, out s_positionControl);
// // ConstructVector3Editor(m_contentObj, "Local Position", ControlType.localPosition, out s_localPosControl);
// // ConstructVector3Editor(m_contentObj, "Rotation", ControlType.eulerAngles, out s_rotationControl);
// // ConstructVector3Editor(m_contentObj, "Scale", ControlType.localScale, out s_scaleControl);
// // // set parent
// // ConstructSetParent(m_contentObj);
// // // bottom row buttons
// // ConstructBottomButtons(m_contentObj);
// // // set controls content inactive now that content is made (otherwise TMP font size goes way too big?)
// // m_contentObj.SetActive(false);
// //}
// //internal void ConstructSetParent(GameObject contentObj)
// //{
// // var setParentGroupObj = UIFactory.CreateHorizontalGroup(contentObj, "SetParentRow", false, false, true, true, 5, default,
// // new Color(1, 1, 1, 0));
// // UIFactory.SetLayoutElement(setParentGroupObj, minHeight: 25, flexibleHeight: 0);
// // var title = UIFactory.CreateLabel(setParentGroupObj, "SetParentLabel", "Set Parent:", TextAnchor.MiddleLeft, Color.grey);
// // UIFactory.SetLayoutElement(title.gameObject, minWidth: 110, minHeight: 25, flexibleHeight: 0);
// // var inputFieldObj = UIFactory.CreateInputField(setParentGroupObj, "SetParentInputField", "Enter a GameObject name or path...");
// // s_setParentInput = inputFieldObj.GetComponent<InputField>();
// // UIFactory.SetLayoutElement(inputFieldObj, minHeight: 25, preferredWidth: 400, flexibleWidth: 9999);
// // var applyButton = UIFactory.CreateButton(setParentGroupObj, "SetParentButton", "Apply", OnSetParentClicked);
// // UIFactory.SetLayoutElement(applyButton.gameObject, minWidth: 55, flexibleWidth: 0, minHeight: 25, flexibleHeight: 0);
// //}
// //internal void ConstructVector3Editor(GameObject parent, string titleText, ControlType type, out ControlEditor editor)
// //{
// // editor = new ControlEditor();
// // var topBarObj = UIFactory.CreateHorizontalGroup(parent, "Vector3Editor", false, false, true, true, 5, default, new Color(1, 1, 1, 0));
// // UIFactory.SetLayoutElement(topBarObj, minHeight: 25, flexibleHeight: 0);
// // var title = UIFactory.CreateLabel(topBarObj, "Title", titleText, TextAnchor.MiddleLeft, Color.grey);
// // UIFactory.SetLayoutElement(title.gameObject, minWidth: 110, flexibleWidth: 0, minHeight: 25);
// // // expand button
// // var expandButton = UIFactory.CreateButton(topBarObj, "ExpandArrow", "▼");
// // var expandText = expandButton.GetComponentInChildren<Text>();
// // expandText.fontSize = 12;
// // UIFactory.SetLayoutElement(expandButton.gameObject, minWidth: 35, flexibleWidth: 0, minHeight: 25, flexibleHeight: 0);
// // // readonly value input
// // var valueInputObj = UIFactory.CreateInputField(topBarObj, "ValueInput", "...");
// // var valueInput = valueInputObj.GetComponent<InputField>();
// // valueInput.readOnly = true;
// // UIFactory.SetLayoutElement(valueInputObj, minHeight: 25, flexibleHeight: 0, preferredWidth: 400, flexibleWidth: 9999);
// // editor.fullValue = valueInput;
// // editor.sliders = new Slider[3];
// // editor.inputs = new InputField[3];
// // editor.values = new Text[3];
// // var xRow = ConstructEditorRow(parent, editor, type, VectorValue.x);
// // xRow.SetActive(false);
// // var yRow = ConstructEditorRow(parent, editor, type, VectorValue.y);
// // yRow.SetActive(false);
// // var zRow = ConstructEditorRow(parent, editor, type, VectorValue.z);
// // zRow.SetActive(false);
// // // add expand callback now that we have group reference
// // expandButton.onClick.AddListener(ToggleExpand);
// // void ToggleExpand()
// // {
// // if (xRow.activeSelf)
// // {
// // xRow.SetActive(false);
// // yRow.SetActive(false);
// // zRow.SetActive(false);
// // expandText.text = "▼";
// // }
// // else
// // {
// // xRow.SetActive(true);
// // yRow.SetActive(true);
// // zRow.SetActive(true);
// // expandText.text = "▲";
// // }
// // }
// //}
// //internal GameObject ConstructEditorRow(GameObject parent, ControlEditor editor, ControlType type, VectorValue vectorValue)
// //{
// // var rowObject = UIFactory.CreateHorizontalGroup(parent, "EditorRow", false, false, true, true, 5, default, new Color(1, 1, 1, 0));
// // UIFactory.SetLayoutElement(rowObject, minHeight: 25, flexibleHeight: 0, minWidth: 100);
// // // Value labels
// // var valueTitle = UIFactory.CreateLabel(rowObject, "ValueTitle", $"{vectorValue.ToString().ToUpper()}:", TextAnchor.MiddleLeft, Color.cyan);
// // UIFactory.SetLayoutElement(valueTitle.gameObject, minHeight: 25, flexibleHeight: 0, minWidth: 25, flexibleWidth: 0);
// // // actual value label
// // var valueLabel = UIFactory.CreateLabel(rowObject, "ValueLabel", "", TextAnchor.MiddleLeft);
// // editor.values[(int)vectorValue] = valueLabel;
// // UIFactory.SetLayoutElement(valueLabel.gameObject, minWidth: 85, flexibleWidth: 0, minHeight: 25);
// // // input field
// // var inputHolder = UIFactory.CreateVerticalGroup(rowObject, "InputFieldGroup", false, false, true, true, 0, default, new Color(1, 1, 1, 0));
// // var inputObj = UIFactory.CreateInputField(inputHolder, "InputField", "...");
// // var input = inputObj.GetComponent<InputField>();
// // //input.characterValidation = InputField.CharacterValidation.Decimal;
// // UIFactory.SetLayoutElement(inputObj, minHeight: 25, flexibleHeight: 0, minWidth: 90, flexibleWidth: 50);
// // editor.inputs[(int)vectorValue] = input;
// // // apply button
// // var applyBtn = UIFactory.CreateButton(rowObject, "ApplyButton", "Apply", () => { OnVectorControlInputApplied(type, vectorValue); });
// // UIFactory.SetLayoutElement(applyBtn.gameObject, minWidth: 60, minHeight: 25);
// // // Slider
// // var sliderObj = UIFactory.CreateSlider(rowObject, "VectorSlider", out Slider slider);
// // UIFactory.SetLayoutElement(sliderObj, minHeight: 20, flexibleHeight: 0, minWidth: 200, flexibleWidth: 9000);
// // sliderObj.transform.Find("Fill Area").gameObject.SetActive(false);
// // RuntimeProvider.Instance.SetColorBlock(slider, new Color(0.65f, 0.65f, 0.65f));
// // slider.minValue = -2;
// // slider.maxValue = 2;
// // slider.value = 0;
// // slider.onValueChanged.AddListener((float val) => { OnSliderControlChanged(val, slider, type, vectorValue); });
// // editor.sliders[(int)vectorValue] = slider;
// // return rowObject;
// //}
// //internal void ConstructBottomButtons(GameObject contentObj)
// //{
// // var bottomRow = UIFactory.CreateHorizontalGroup(contentObj, "BottomButtons", true, true, false, false, 4, default, new Color(1, 1, 1, 0));
// // var instantiateBtn = UIFactory.CreateButton(bottomRow, "InstantiateBtn", "Instantiate", InstantiateBtn, new Color(0.2f, 0.2f, 0.2f));
// // UIFactory.SetLayoutElement(instantiateBtn.gameObject, minWidth: 150);
// // void InstantiateBtn()
// // {
// // var go = GameObjectInspector.ActiveInstance.TargetGO;
// // if (!go)
// // return;
// // var clone = GameObject.Instantiate(go);
// // InspectorManager.Instance.Inspect(clone);
// // }
// // var dontDestroyBtn = UIFactory.CreateButton(bottomRow, "DontDestroyButton", "Set DontDestroyOnLoad", DontDestroyOnLoadBtn,
// // new Color(0.2f, 0.2f, 0.2f));
// // UIFactory.SetLayoutElement(dontDestroyBtn.gameObject, flexibleWidth: 5000);
// // void DontDestroyOnLoadBtn()
// // {
// // var go = GameObjectInspector.ActiveInstance.TargetGO;
// // if (!go)
// // return;
// // GameObject.DontDestroyOnLoad(go);
// // }
// // var destroyBtn = UIFactory.CreateButton(bottomRow, "DestroyButton", "Destroy", DestroyBtn, new Color(0.2f, 0.2f, 0.2f));
// // UIFactory.SetLayoutElement(destroyBtn.gameObject, minWidth: 150);
// // var destroyText = destroyBtn.GetComponentInChildren<Text>();
// // destroyText.color = Color.red;
// // void DestroyBtn()
// // {
// // var go = GameObjectInspector.ActiveInstance.TargetGO;
// // if (!go)
// // return;
// // GameObject.Destroy(go);
// // }
// //}
// //#endregion
// }
//}

View File

@ -0,0 +1,349 @@
//using System;
//using System.Collections.Generic;
//using System.Linq;
//using System.Text;
//using UnityEngine;
//using UnityEngine.UI;
//using UnityExplorer.Core.Runtime;
//namespace UnityExplorer.UI.Inspectors.GameObjects
//{
// public class GameObjectInspector : InspectorBase
// {
// public override string TabLabel => $" <color=cyan>[G]</color> {TargetGO?.name}";
// public static GameObjectInspector ActiveInstance { get; private set; }
// public GameObject TargetGO;
// //// sub modules
// //internal static ChildList s_childList;
// //internal static ComponentList s_compList;
// //internal static GameObjectControls s_controls;
// internal static bool m_UIConstructed;
// public GameObjectInspector(GameObject target) : base(target)
// {
// ActiveInstance = this;
// TargetGO = target;
// if (!TargetGO)
// {
// ExplorerCore.LogWarning("Target GameObject is null!");
// return;
// }
// // one UI is used for all gameobject inspectors. no point recreating it.
// if (!m_UIConstructed)
// {
// m_UIConstructed = true;
// //s_childList = new ChildList();
// //s_compList = new ComponentList();
// //s_controls = new GameObjectControls();
// //ConstructUI();
// }
// }
// public override void SetActive()
// {
// base.SetActive();
// ActiveInstance = this;
// }
// public override void SetInactive()
// {
// base.SetInactive();
// ActiveInstance = null;
// }
// internal void ChangeInspectorTarget(GameObject newTarget)
// {
// if (!newTarget)
// return;
// this.Target = this.TargetGO = newTarget;
// }
// // Update
// //public override void Update()
// //{
// // base.Update();
// // if (m_pendingDestroy || !this.IsActive)
// // return;
// // RefreshTopInfo();
// // s_childList.RefreshChildObjectList();
// // s_compList.RefreshComponentList();
// // s_controls.RefreshControls();
// // if (GameObjectControls.s_sliderChangedWanted)
// // GameObjectControls.UpdateSliderControl();
// //}
// private static GameObject s_content;
// public override GameObject Content
// {
// get => s_content;
// set => s_content = value;
// }
// private static string m_lastName;
// public static InputField m_nameInput;
// private static string m_lastPath;
// public static InputField m_pathInput;
// private static RectTransform m_pathInputRect;
// private static GameObject m_pathGroupObj;
// private static Text m_hiddenPathText;
// private static RectTransform m_hiddenPathRect;
// private static Toggle m_enabledToggle;
// private static Text m_enabledText;
// private static bool? m_lastEnabledState;
// private static Dropdown m_layerDropdown;
// private static int m_lastLayer = -1;
// private static Text m_sceneText;
// private static string m_lastScene;
// internal void RefreshTopInfo()
// {
// var target = TargetGO;
// string name = target.name;
// if (m_lastName != name)
// {
// m_lastName = name;
// m_nameInput.text = m_lastName;
// }
// if (target.transform.parent)
// {
// if (!m_pathGroupObj.activeSelf)
// m_pathGroupObj.SetActive(true);
// var path = target.transform.GetTransformPath(true);
// if (m_lastPath != path)
// {
// m_lastPath = path;
// m_pathInput.text = path;
// m_hiddenPathText.text = path;
// LayoutRebuilder.ForceRebuildLayoutImmediate(m_pathInputRect);
// LayoutRebuilder.ForceRebuildLayoutImmediate(m_hiddenPathRect);
// }
// }
// else if (m_pathGroupObj.activeSelf)
// m_pathGroupObj.SetActive(false);
// if (m_lastEnabledState != target.activeSelf)
// {
// m_lastEnabledState = target.activeSelf;
// m_enabledToggle.isOn = target.activeSelf;
// m_enabledText.text = target.activeSelf ? "Enabled" : "Disabled";
// m_enabledText.color = target.activeSelf ? Color.green : Color.red;
// }
// if (m_lastLayer != target.layer)
// {
// m_lastLayer = target.layer;
// m_layerDropdown.value = target.layer;
// }
// if (string.IsNullOrEmpty(m_lastScene) || m_lastScene != target.scene.name)
// {
// m_lastScene = target.scene.name;
// if (!string.IsNullOrEmpty(target.scene.name))
// m_sceneText.text = m_lastScene;
// else
// m_sceneText.text = "None (Asset/Resource)";
// }
// }
// // UI Callbacks
// private static void OnApplyNameClicked()
// {
// if (ActiveInstance == null)
// return;
// ActiveInstance.TargetGO.name = m_nameInput.text;
// }
// private static void OnEnableToggled(bool enabled)
// {
// if (ActiveInstance == null)
// return;
// ActiveInstance.TargetGO.SetActive(enabled);
// }
// private static void OnLayerSelected(int layer)
// {
// if (ActiveInstance == null)
// return;
// ActiveInstance.TargetGO.layer = layer;
// }
// internal static void OnBackButtonClicked()
// {
// if (ActiveInstance == null)
// return;
// ActiveInstance.ChangeInspectorTarget(ActiveInstance.TargetGO.transform.parent.gameObject);
// }
// //#region UI CONSTRUCTION
// //internal void ConstructUI()
// //{
// // var parent = InspectorManager.m_inspectorContent;
// // s_content = UIFactory.CreateScrollView(parent, "GameObjectInspector_Content", out GameObject scrollContent, out _,
// // new Color(0.1f, 0.1f, 0.1f));
// // UIFactory.SetLayoutGroup<VerticalLayoutGroup>(scrollContent.transform.parent.gameObject, true, true, true, true);
// // UIFactory.SetLayoutGroup<VerticalLayoutGroup>(scrollContent, true, true, true, true, 5);
// // var contentFitter = scrollContent.GetComponent<ContentSizeFitter>();
// // contentFitter.verticalFit = ContentSizeFitter.FitMode.Unconstrained;
// // ConstructTopArea(scrollContent);
// // s_controls.ConstructControls(scrollContent);
// // var midGroupObj = ConstructMidGroup(scrollContent);
// // s_childList.ConstructChildList(midGroupObj);
// // s_compList.ConstructCompList(midGroupObj);
// // LayoutRebuilder.ForceRebuildLayoutImmediate(s_content.GetComponent<RectTransform>());
// // Canvas.ForceUpdateCanvases();
// //}
// //private void ConstructTopArea(GameObject scrollContent)
// //{
// // // path row
// // m_pathGroupObj = UIFactory.CreateHorizontalGroup(scrollContent, "TopArea", false, false, true, true, 5, default, new Color(0.1f, 0.1f, 0.1f));
// // var pathRect = m_pathGroupObj.GetComponent<RectTransform>();
// // pathRect.sizeDelta = new Vector2(pathRect.sizeDelta.x, 20);
// // UIFactory.SetLayoutElement(m_pathGroupObj, minHeight: 20, flexibleHeight: 75);
// // // Back button
// // var backButton = UIFactory.CreateButton(m_pathGroupObj, "BackButton", "◄", OnBackButtonClicked, new Color(0.15f, 0.15f, 0.15f));
// // UIFactory.SetLayoutElement(backButton.gameObject, minWidth: 55, flexibleWidth: 0, minHeight: 25, flexibleHeight: 0);
// // m_hiddenPathText = UIFactory.CreateLabel(m_pathGroupObj, "HiddenPathText", "", TextAnchor.MiddleLeft);
// // m_hiddenPathText.color = Color.clear;
// // m_hiddenPathText.fontSize = 14;
// // m_hiddenPathText.raycastTarget = false;
// // var hiddenFitter = m_hiddenPathText.gameObject.AddComponent<ContentSizeFitter>();
// // hiddenFitter.verticalFit = ContentSizeFitter.FitMode.PreferredSize;
// // UIFactory.SetLayoutElement(m_hiddenPathText.gameObject, minHeight: 25, flexibleHeight: 125, minWidth: 250, flexibleWidth: 9000);
// // UIFactory.SetLayoutGroup<HorizontalLayoutGroup>(m_hiddenPathText.gameObject, true, true, true, true);
// // // Path input
// // var pathInputObj = UIFactory.CreateInputField(m_hiddenPathText.gameObject, "PathInputField", "...");
// // UIFactory.SetLayoutElement(pathInputObj, minHeight: 25, flexibleHeight: 75, preferredWidth: 400, flexibleWidth: 9999);
// // var pathInputRect = pathInputObj.GetComponent<RectTransform>();
// // pathInputRect.sizeDelta = new Vector2(pathInputRect.sizeDelta.x, 25);
// // m_pathInput = pathInputObj.GetComponent<InputField>();
// // m_pathInput.text = ActiveInstance.TargetGO.transform.GetTransformPath();
// // m_pathInput.readOnly = true;
// // m_pathInput.lineType = InputField.LineType.MultiLineNewline;
// // m_pathInput.textComponent.color = new Color(0.75f, 0.75f, 0.75f);
// // var textRect = m_pathInput.textComponent.GetComponent<RectTransform>();
// // textRect.offsetMin = new Vector2(3, 3);
// // textRect.offsetMax = new Vector2(3, 3);
// // m_pathInputRect = m_pathInput.GetComponent<RectTransform>();
// // m_hiddenPathRect = m_hiddenPathText.GetComponent<RectTransform>();
// // // name and enabled row
// // var nameRowObj = UIFactory.CreateHorizontalGroup(scrollContent, "NameGroup", false, false, true, true, 5, default, new Color(0.1f, 0.1f, 0.1f));
// // UIFactory.SetLayoutElement(nameRowObj, minHeight: 25, flexibleHeight: 0);
// // var nameRect = nameRowObj.GetComponent<RectTransform>();
// // nameRect.sizeDelta = new Vector2(nameRect.sizeDelta.x, 25);
// // var nameLabel = UIFactory.CreateLabel(nameRowObj, "NameLabel", "Name:", TextAnchor.MiddleCenter, Color.grey, true, 14);
// // UIFactory.SetLayoutElement(nameLabel.gameObject, minHeight: 25, flexibleHeight: 0, minWidth: 55, flexibleWidth: 0);
// // var nameInputObj = UIFactory.CreateInputField(nameRowObj, "NameInput", "...");
// // var nameInputRect = nameInputObj.GetComponent<RectTransform>();
// // nameInputRect.sizeDelta = new Vector2(nameInputRect.sizeDelta.x, 25);
// // m_nameInput = nameInputObj.GetComponent<InputField>();
// // m_nameInput.text = ActiveInstance.TargetGO.name;
// // var applyNameBtn = UIFactory.CreateButton(nameRowObj, "ApplyNameButton", "Apply", OnApplyNameClicked);
// // UIFactory.SetLayoutElement(applyNameBtn.gameObject, minWidth: 65, minHeight: 25, flexibleHeight: 0);
// // var applyNameRect = applyNameBtn.GetComponent<RectTransform>();
// // applyNameRect.sizeDelta = new Vector2(applyNameRect.sizeDelta.x, 25);
// // var activeLabel = UIFactory.CreateLabel(nameRowObj, "ActiveLabel", "Active:", TextAnchor.MiddleCenter, Color.grey, true, 14);
// // UIFactory.SetLayoutElement(activeLabel.gameObject, minWidth: 55, minHeight: 25);
// // var enabledToggleObj = UIFactory.CreateToggle(nameRowObj, "EnabledToggle", out m_enabledToggle, out m_enabledText);
// // UIFactory.SetLayoutElement(enabledToggleObj, minHeight: 25, minWidth: 100, flexibleWidth: 0);
// // m_enabledText.text = "Enabled";
// // m_enabledText.color = Color.green;
// // m_enabledToggle.onValueChanged.AddListener(OnEnableToggled);
// // // layer and scene row
// // var sceneLayerRow = UIFactory.CreateHorizontalGroup(scrollContent, "SceneLayerRow", false, true, true, true, 5, default, new Color(0.1f, 0.1f, 0.1f));
// // // layer
// // var layerLabel = UIFactory.CreateLabel(sceneLayerRow, "LayerLabel", "Layer:", TextAnchor.MiddleCenter, Color.grey, true, 14);
// // UIFactory.SetLayoutElement(layerLabel.gameObject, minWidth: 55, flexibleWidth: 0);
// // var layerDropdownObj = UIFactory.CreateDropdown(sceneLayerRow, out m_layerDropdown, "", 14, OnLayerSelected);
// // m_layerDropdown.options.Clear();
// // for (int i = 0; i < 32; i++)
// // {
// // var layer = RuntimeProvider.Instance.LayerToName(i);
// // m_layerDropdown.options.Add(new Dropdown.OptionData { text = $"{i}: {layer}" });
// // }
// // UIFactory.SetLayoutElement(layerDropdownObj, minWidth: 120, flexibleWidth: 2000, minHeight: 25);
// // // scene
// // var sceneLabel = UIFactory.CreateLabel(sceneLayerRow, "SceneLabel", "Scene:", TextAnchor.MiddleCenter, Color.grey, true, 14);
// // UIFactory.SetLayoutElement(sceneLabel.gameObject, minWidth: 55, flexibleWidth: 0);
// // m_sceneText = UIFactory.CreateLabel(sceneLayerRow, "SceneText", "", TextAnchor.MiddleLeft);
// // UIFactory.SetLayoutElement(m_sceneText.gameObject, minWidth: 120, flexibleWidth: 2000);
// //}
// //private GameObject ConstructMidGroup(GameObject parent)
// //{
// // var midGroupObj = UIFactory.CreateHorizontalGroup(parent, "MidGroup", true, true, true, true, 5, default, new Color(1, 1, 1, 0));
// // UIFactory.SetLayoutElement(midGroupObj, minHeight: 300, flexibleHeight: 3000);
// // return midGroupObj;
// //}
// //#endregion
// }
//}

View File

@ -0,0 +1,327 @@
//using System;
//using System.Collections.Generic;
//using System.Linq;
//using System.Text;
//using UnityEngine;
//using UnityEngine.EventSystems;
//using UnityEngine.UI;
//using UnityExplorer.Core;
//using UnityExplorer.Core.Input;
//using UnityExplorer.Core.Runtime;
//using UnityExplorer.UI;
//using UnityExplorer.UI.Main;
//using UnityExplorer.UI.Inspectors;
//namespace UnityExplorer.UI.Main.Home
//{
// public class InspectUnderMouse
// {
// public enum MouseInspectMode
// {
// World,
// UI
// }
// public static bool Inspecting { get; set; }
// public static MouseInspectMode Mode { get; set; }
// private static GameObject s_lastHit;
// private static Vector3 s_lastMousePos;
// private static readonly List<Graphic> _wasDisabledGraphics = new List<Graphic>();
// private static readonly List<CanvasGroup> _wasDisabledCanvasGroups = new List<CanvasGroup>();
// private static readonly List<GameObject> _objectsAddedCastersTo = new List<GameObject>();
// internal static Camera MainCamera;
// internal static GraphicRaycaster[] graphicRaycasters;
// public static void Init()
// {
// ConstructUI();
// }
// public static void StartInspect(MouseInspectMode mode)
// {
// MainCamera = Camera.main;
// if (!MainCamera)
// return;
// Mode = mode;
// Inspecting = true;
// MainMenu.Instance.MainPanel.SetActive(false);
// s_UIContent.SetActive(true);
// if (mode == MouseInspectMode.UI)
// SetupUIRaycast();
// }
// internal static void ClearHitData()
// {
// s_lastHit = null;
// s_objNameLabel.text = "No hits...";
// s_objPathLabel.text = "";
// }
// public static void StopInspect()
// {
// Inspecting = false;
// MainMenu.Instance.MainPanel.SetActive(true);
// s_UIContent.SetActive(false);
// if (Mode == MouseInspectMode.UI)
// StopUIInspect();
// ClearHitData();
// }
// public static void UpdateInspect()
// {
// if (InputManager.GetKeyDown(KeyCode.Escape))
// {
// StopInspect();
// return;
// }
// var mousePos = InputManager.MousePosition;
// if (mousePos != s_lastMousePos)
// UpdatePosition(mousePos);
// // actual inspect raycast
// switch (Mode)
// {
// case MouseInspectMode.UI:
// RaycastUI(mousePos); break;
// case MouseInspectMode.World:
// RaycastWorld(mousePos); break;
// }
// }
// internal static void UpdatePosition(Vector2 mousePos)
// {
// s_lastMousePos = mousePos;
// var inversePos = UIManager.CanvasRoot.transform.InverseTransformPoint(mousePos);
// s_mousePosLabel.text = $"<color=grey>Mouse Position:</color> {mousePos.ToString()}";
// float yFix = mousePos.y < 120 ? 80 : -80;
// s_UIContent.transform.localPosition = new Vector3(inversePos.x, inversePos.y + yFix, 0);
// }
// internal static void OnHitGameObject(GameObject obj)
// {
// if (obj != s_lastHit)
// {
// s_lastHit = obj;
// s_objNameLabel.text = $"<b>Click to Inspect:</b> <color=cyan>{obj.name}</color>";
// s_objPathLabel.text = $"Path: {obj.transform.GetTransformPath(true)}";
// }
// if (InputManager.GetMouseButtonDown(0))
// {
// StopInspect();
// InspectorManager.Instance.Inspect(obj);
// }
// }
// // Collider raycasting
// internal static void RaycastWorld(Vector2 mousePos)
// {
// var ray = MainCamera.ScreenPointToRay(mousePos);
// Physics.Raycast(ray, out RaycastHit hit, 1000f);
// if (hit.transform)
// {
// var obj = hit.transform.gameObject;
// OnHitGameObject(obj);
// }
// else
// {
// if (s_lastHit)
// ClearHitData();
// }
// }
// // UI Graphic raycasting
// private static void SetupUIRaycast()
// {
// foreach (var obj in RuntimeProvider.Instance.FindObjectsOfTypeAll(typeof(Canvas)))
// {
// var canvas = obj.Cast(typeof(Canvas)) as Canvas;
// if (!canvas || !canvas.enabled || !canvas.gameObject.activeInHierarchy)
// continue;
// if (!canvas.GetComponent<GraphicRaycaster>())
// {
// canvas.gameObject.AddComponent<GraphicRaycaster>();
// //ExplorerCore.Log("Added raycaster to " + canvas.name);
// _objectsAddedCastersTo.Add(canvas.gameObject);
// }
// }
// // recache Graphic Raycasters each time we start
// var casters = RuntimeProvider.Instance.FindObjectsOfTypeAll(typeof(GraphicRaycaster));
// graphicRaycasters = new GraphicRaycaster[casters.Length];
// for (int i = 0; i < casters.Length; i++)
// {
// graphicRaycasters[i] = casters[i].Cast(typeof(GraphicRaycaster)) as GraphicRaycaster;
// }
// // enable raycastTarget on Graphics
// foreach (var obj in RuntimeProvider.Instance.FindObjectsOfTypeAll(typeof(Graphic)))
// {
// var graphic = obj.Cast(typeof(Graphic)) as Graphic;
// if (!graphic || !graphic.enabled || graphic.raycastTarget || !graphic.gameObject.activeInHierarchy)
// continue;
// graphic.raycastTarget = true;
// //ExplorerCore.Log("Enabled raycastTarget on " + graphic.name);
// _wasDisabledGraphics.Add(graphic);
// }
// // enable blocksRaycasts on CanvasGroups
// foreach (var obj in RuntimeProvider.Instance.FindObjectsOfTypeAll(typeof(CanvasGroup)))
// {
// var canvas = obj.Cast(typeof(CanvasGroup)) as CanvasGroup;
// if (!canvas || !canvas.gameObject.activeInHierarchy || canvas.blocksRaycasts)
// continue;
// canvas.blocksRaycasts = true;
// //ExplorerCore.Log("Enabled raycasts on " + canvas.name);
// _wasDisabledCanvasGroups.Add(canvas);
// }
// }
// internal static void RaycastUI(Vector2 mousePos)
// {
// var ped = new PointerEventData(null)
// {
// position = mousePos
// };
// //ExplorerCore.Log("~~~~~~~~~ begin raycast ~~~~~~~~");
// GameObject hitObject = null;
// int highestLayer = int.MinValue;
// int highestOrder = int.MinValue;
// int highestDepth = int.MinValue;
// foreach (var gr in graphicRaycasters)
// {
// var list = new List<RaycastResult>();
// RuntimeProvider.Instance.GraphicRaycast(gr, ped, list);
// //gr.Raycast(ped, list);
// if (list.Count > 0)
// {
// foreach (var hit in list)
// {
// // Manual trying to determine which object is "on top".
// // Not perfect, but not terrible.
// if (!hit.gameObject)
// continue;
// if (hit.gameObject.GetComponent<CanvasGroup>() is CanvasGroup group && group.alpha == 0)
// continue;
// if (hit.gameObject.GetComponent<Graphic>() is Graphic graphic && graphic.color.a == 0f)
// continue;
// if (hit.sortingLayer < highestLayer)
// continue;
// if (hit.sortingLayer > highestLayer)
// {
// highestLayer = hit.sortingLayer;
// highestDepth = int.MinValue;
// }
// if (hit.depth < highestDepth)
// continue;
// if (hit.depth > highestDepth)
// {
// highestDepth = hit.depth;
// highestOrder = int.MinValue;
// }
// if (hit.sortingOrder <= highestOrder)
// continue;
// highestOrder = hit.sortingOrder;
// hitObject = hit.gameObject;
// }
// }
// else
// {
// if (s_lastHit)
// ClearHitData();
// }
// }
// if (hitObject)
// OnHitGameObject(hitObject);
// //ExplorerCore.Log("~~~~~~~~~ end raycast ~~~~~~~~");
// }
// private static void StopUIInspect()
// {
// foreach (var obj in _objectsAddedCastersTo)
// {
// if (obj.GetComponent<GraphicRaycaster>() is GraphicRaycaster raycaster)
// GameObject.Destroy(raycaster);
// }
// foreach (var graphic in _wasDisabledGraphics)
// graphic.raycastTarget = false;
// foreach (var canvas in _wasDisabledCanvasGroups)
// canvas.blocksRaycasts = false;
// _objectsAddedCastersTo.Clear();
// _wasDisabledCanvasGroups.Clear();
// _wasDisabledGraphics.Clear();
// }
// internal static Text s_objNameLabel;
// internal static Text s_objPathLabel;
// internal static Text s_mousePosLabel;
// internal static GameObject s_UIContent;
// internal static void ConstructUI()
// {
// s_UIContent = UIFactory.CreatePanel("InspectUnderMouse_UI", out GameObject content);
// var baseRect = s_UIContent.GetComponent<RectTransform>();
// var half = new Vector2(0.5f, 0.5f);
// baseRect.anchorMin = half;
// baseRect.anchorMax = half;
// baseRect.pivot = half;
// baseRect.sizeDelta = new Vector2(700, 150);
// var group = content.GetComponent<VerticalLayoutGroup>();
// group.childForceExpandHeight = true;
// // Title text
// UIFactory.CreateLabel(content, "InspectLabel", "<b>Mouse Inspector</b> (press <b>ESC</b> to cancel)", TextAnchor.MiddleCenter);
// s_mousePosLabel = UIFactory.CreateLabel(content, "MousePosLabel", "Mouse Position:", TextAnchor.MiddleCenter);
// s_objNameLabel = UIFactory.CreateLabel(content, "HitLabelObj", "No hits...", TextAnchor.MiddleLeft);
// s_objNameLabel.horizontalOverflow = HorizontalWrapMode.Overflow;
// s_objPathLabel = UIFactory.CreateLabel(content, "PathLabel", "", TextAnchor.MiddleLeft);
// s_objPathLabel.fontStyle = FontStyle.Italic;
// s_objPathLabel.horizontalOverflow = HorizontalWrapMode.Wrap;
// UIFactory.SetLayoutElement(s_objPathLabel.gameObject, minHeight: 75);
// s_UIContent.SetActive(false);
// }
// }
//}

View File

@ -0,0 +1,122 @@
using System;
using UnityEngine;
using UnityEngine.UI;
using UnityExplorer.UI.Panels;
namespace UnityExplorer.UI.Inspectors
{
public abstract class InspectorBase
{
public object Target;
public bool IsActive { get; private set; }
public abstract string TabLabel { get; }
internal bool m_pendingDestroy;
public InspectorBase(object target)
{
Target = target;
if (Target.IsNullOrDestroyed(false))
{
Destroy();
return;
}
AddInspectorTab(this);
}
public virtual void SetActive()
{
this.IsActive = true;
Content?.SetActive(true);
}
public virtual void SetInactive()
{
this.IsActive = false;
Content?.SetActive(false);
}
public virtual void Update()
{
if (Target.IsNullOrDestroyed(false))
{
Destroy();
return;
}
m_tabText.text = TabLabel;
}
public virtual void Destroy()
{
m_pendingDestroy = true;
GameObject tabGroup = m_tabButton?.transform.parent.gameObject;
if (tabGroup)
GameObject.Destroy(tabGroup);
int thisIndex = -1;
if (InspectorManager.ActiveInspectors.Contains(this))
{
thisIndex = InspectorManager.ActiveInspectors.IndexOf(this);
InspectorManager.ActiveInspectors.Remove(this);
}
if (ReferenceEquals(InspectorManager.m_activeInspector, this))
{
InspectorManager.UnsetInspectorTab();
if (InspectorManager.ActiveInspectors.Count > 0)
{
var prevTab = InspectorManager.ActiveInspectors[thisIndex > 0 ? thisIndex - 1 : 0];
InspectorManager.SetInspectorTab(prevTab);
}
}
}
#region UI
public abstract GameObject Content { get; set; }
public Button m_tabButton;
public Text m_tabText;
public void AddInspectorTab(InspectorBase parent)
{
var tabContent = InspectorPanel.Instance.NavbarHolder;
var tabGroupObj = UIFactory.CreateHorizontalGroup(tabContent, "TabObject", true, true, true, true);
UIFactory.SetLayoutElement(tabGroupObj, minWidth: 185, flexibleWidth: 0);
tabGroupObj.AddComponent<Mask>();
m_tabButton = UIFactory.CreateButton(tabGroupObj,
"TabButton",
"",
() => { InspectorManager.SetInspectorTab(parent); });
UIFactory.SetLayoutElement(m_tabButton.gameObject, minWidth: 165, flexibleWidth: 0);
m_tabText = m_tabButton.GetComponentInChildren<Text>();
m_tabText.horizontalOverflow = HorizontalWrapMode.Overflow;
m_tabText.alignment = TextAnchor.MiddleLeft;
var closeBtn = UIFactory.CreateButton(tabGroupObj,
"CloseButton",
"X",
parent.Destroy,
new Color(0.2f, 0.2f, 0.2f, 1));
UIFactory.SetLayoutElement(closeBtn.gameObject, minWidth: 20, flexibleWidth: 0);
var closeBtnText = closeBtn.GetComponentInChildren<Text>();
closeBtnText.color = new Color(1, 0, 0, 1);
}
public virtual void OnPanelResized() { }
#endregion
}
}

View File

@ -0,0 +1,143 @@
using System;
using System.Collections.Generic;
using System.Linq;
using UnityExplorer.UI;
using UnityEngine;
using UnityEngine.SceneManagement;
using UnityEngine.UI;
using UnityExplorer.Core.Runtime;
using UnityExplorer.UI.CacheObject;
using UnityExplorer.UI.Inspectors.Reflection;
using UnityExplorer.UI.Panels;
namespace UnityExplorer.UI.Inspectors
{
public static class InspectorManager
{
public static InspectorBase m_activeInspector;
public static readonly List<InspectorBase> ActiveInspectors = new List<InspectorBase>();
public static void Update()
{
try
{
for (int i = 0; i < ActiveInspectors.Count; i++)
ActiveInspectors[i].Update();
}
catch (Exception ex)
{
ExplorerCore.LogWarning(ex);
}
}
public static void Inspect(object obj, CacheObjectBase parentMember = null)
{
var type = ReflectionProvider.Instance.GetActualType(obj);
// only need to set parent member for structs
if (!type.IsValueType)
parentMember = null;
obj = ReflectionProvider.Instance.Cast(obj, type);
if (obj.IsNullOrDestroyed(false))
return;
// check if currently inspecting this object
foreach (InspectorBase tab in ActiveInspectors)
{
if (obj.ReferenceEqual(tab.Target))
{
SetInspectorTab(tab);
return;
}
}
InspectorBase inspector;
if (obj is GameObject go)
{
ExplorerCore.Log("TODO");
return;
// inspector = new GameObjectInspector(go);
}
else
inspector = new InstanceInspector(obj);
if (inspector is ReflectionInspector ri)
ri.ParentMember = parentMember;
ActiveInspectors.Add(inspector);
SetInspectorTab(inspector);
}
public static void InspectType(Type type)
{
if (type == null)
{
ExplorerCore.LogWarning("The provided type was null!");
return;
}
foreach (var tab in ActiveInspectors.Where(x => x is StaticInspector))
{
if (ReferenceEquals(tab.Target as Type, type))
{
SetInspectorTab(tab);
return;
}
}
var inspector = new StaticInspector(type);
ActiveInspectors.Add(inspector);
SetInspectorTab(inspector);
}
public static void SetInspectorTab(InspectorBase inspector)
{
UIManager.SetPanelActive(UIManager.Panels.Inspector, true);
if (m_activeInspector == inspector)
return;
UnsetInspectorTab();
m_activeInspector = inspector;
inspector.SetActive();
OnSetInspectorTab(inspector);
}
public static void UnsetInspectorTab()
{
if (m_activeInspector == null)
return;
m_activeInspector.SetInactive();
OnUnsetInspectorTab();
m_activeInspector = null;
}
public static void OnSetInspectorTab(InspectorBase inspector)
{
Color activeColor = new Color(0, 0.25f, 0, 1);
RuntimeProvider.Instance.SetColorBlock(inspector.m_tabButton, activeColor, activeColor);
}
public static void OnUnsetInspectorTab()
{
RuntimeProvider.Instance.SetColorBlock(m_activeInspector.m_tabButton,
new Color(0.2f, 0.2f, 0.2f, 1), new Color(0.1f, 0.3f, 0.1f, 1));
}
internal static void OnPanelResized()
{
foreach (var instance in ActiveInspectors)
{
instance.OnPanelResized();
}
}
}
}

View File

@ -0,0 +1,76 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using UnityEngine;
using UnityExplorer.UI.Widgets;
namespace UnityExplorer.UI.Inspectors.Reflection
{
public class CacheMemberList : IPoolDataSource
{
public ScrollPool ScrollPool { get; }
public ReflectionInspector Inspector { get; }
public CacheMemberList(ScrollPool scrollPool, ReflectionInspector inspector)
{
this.ScrollPool = scrollPool;
this.Inspector = inspector;
}
public int ItemCount => Inspector.filteredMembers.Count;
public int GetRealIndexOfTempIndex(int index)
{
if (index < 0 || index >= Inspector.filteredToRealIndices.Count)
return -1;
return Inspector.filteredToRealIndices[index];
}
public ICell CreateCell(RectTransform cellTransform) => new CellViewHolder(cellTransform.gameObject);
public void DisableCell(ICell cell, int index)
{
var root = (cell as CellViewHolder).UIRoot;
DisableContent(root);
cell.Disable();
}
public void SetCell(ICell icell, int index)
{
var root = (icell as CellViewHolder).UIRoot;
if (index < 0 || index >= ItemCount)
{
DisableContent(root);
icell.Disable();
return;
}
float start = Time.realtimeSinceStartup;
index = GetRealIndexOfTempIndex(index);
var cache = Inspector.allMembers[index];
cache.Enable();
var content = cache.UIRoot;
if (content.transform.parent.ReferenceEqual(root.transform))
return;
var orig = content.transform.parent;
DisableContent(root);
content.transform.SetParent(root.transform, false);
//ExplorerCore.Log("Set cell " + index + ", took " + (Time.realtimeSinceStartup - start) + " secs");
//ExplorerCore.Log("orig parent was " + (orig?.name ?? " <null>"));
}
private void DisableContent(GameObject cellRoot)
{
if (cellRoot.transform.childCount > 0 && cellRoot.transform.GetChild(0) is Transform existing)
existing.transform.SetParent(Inspector.InactiveHolder.transform, false);
}
}
}

View File

@ -0,0 +1,256 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using UnityEngine;
using UnityEngine.UI;
using UnityExplorer.Core;
using UnityExplorer.Core.Config;
using UnityExplorer.Core.Runtime;
namespace UnityExplorer.UI.Inspectors.Reflection
{
public enum MemberScopes
{
All,
Instance,
Static
}
public class InstanceInspector : ReflectionInspector
{
public override string TabLabel => $" <color=cyan>[R]</color> {base.TabLabel}";
internal MemberScopes m_scopeFilter;
internal Button m_lastActiveScopeButton;
public InstanceInspector(object target) : base(target) { }
internal void OnScopeFilterClicked(MemberScopes type, Button button)
{
if (m_lastActiveScopeButton)
RuntimeProvider.Instance.SetColorBlock(m_lastActiveScopeButton, new Color(0.2f, 0.2f, 0.2f));
m_scopeFilter = type;
m_lastActiveScopeButton = button;
RuntimeProvider.Instance.SetColorBlock(m_lastActiveScopeButton, new Color(0.2f, 0.6f, 0.2f));
FilterMembers(null, true);
ScrollPool.EnableTempCache();
ScrollPool.RefreshAndJumpToTop();
//RefreshDisplay();
//m_sliderScroller.m_slider.value = 1f;
}
public void ConstructInstanceScopeFilters(GameObject parent)
{
var memberFilterRowObj = UIFactory.CreateHorizontalGroup(parent, "InstanceFilterRow", false, false, true, true, 5, default,
new Color(1, 1, 1, 0));
UIFactory.SetLayoutElement(memberFilterRowObj, minHeight: 25, flexibleHeight: 0, flexibleWidth: 5000);
var memLabel = UIFactory.CreateLabel(memberFilterRowObj, "MemberLabel", "Filter scope:", TextAnchor.MiddleLeft);
UIFactory.SetLayoutElement(memLabel.gameObject, minWidth: 100, minHeight: 25, flexibleWidth: 0);
AddFilterButton(memberFilterRowObj, MemberScopes.All, true);
AddFilterButton(memberFilterRowObj, MemberScopes.Instance);
AddFilterButton(memberFilterRowObj, MemberScopes.Static);
}
private void AddFilterButton(GameObject parent, MemberScopes type, bool setEnabled = false)
{
var btn = UIFactory.CreateButton(parent,
"ScopeFilterButton_" + type,
type.ToString(),
null,
new Color(0.2f, 0.2f, 0.2f));
UIFactory.SetLayoutElement(btn.gameObject, minHeight: 25, minWidth: 70);
btn.onClick.AddListener(() => { OnScopeFilterClicked(type, btn); });
RuntimeProvider.Instance.SetColorBlock(btn, highlighted: new Color(0.3f, 0.7f, 0.3f));
if (setEnabled)
{
RuntimeProvider.Instance.SetColorBlock(btn, new Color(0.2f, 0.6f, 0.2f));
m_scopeFilter = type;
m_lastActiveScopeButton = btn;
}
}
public void ConstructUnityInstanceHelpers()
{
if (!typeof(UnityEngine.Object).IsAssignableFrom(m_targetType))
return;
var rowObj = UIFactory.CreateHorizontalGroup(Content, "InstanceHelperRow", true, true, true, true, 5, new Vector4(2, 2, 2, 2),
new Color(0.1f, 0.1f, 0.1f));
UIFactory.SetLayoutElement(rowObj, minHeight: 25, flexibleWidth: 5000);
if (typeof(Component).IsAssignableFrom(m_targetType))
ConstructCompHelper(rowObj);
ConstructUnityObjHelper(rowObj);
if (m_targetType == typeof(Texture2D))
ConstructTextureHelper();
}
internal void ConstructCompHelper(GameObject rowObj)
{
//var gameObjectLabel = UIFactory.CreateLabel(rowObj, "GameObjectLabel", "GameObject:", TextAnchor.MiddleLeft);
//UIFactory.SetLayoutElement(gameObjectLabel.gameObject, minWidth: 90, minHeight: 25, flexibleWidth: 0);
var comp = Target.TryCast(typeof(Component)) as Component;
var btn = UIFactory.CreateButton(rowObj,
"GameObjectButton",
"View GameObject",
() => { InspectorManager.Inspect(comp.gameObject); },
new Color(0.2f, 0.5f, 0.2f));
UIFactory.SetLayoutElement(btn.gameObject, minHeight: 25, minWidth: 120, flexibleWidth: 0);
}
internal void ConstructUnityObjHelper(GameObject rowObj)
{
var label = UIFactory.CreateLabel(rowObj, "NameLabel", "Name:", TextAnchor.MiddleLeft);
UIFactory.SetLayoutElement(label.gameObject, minWidth: 60, minHeight: 25, flexibleWidth: 0);
var uObj = Target.TryCast(typeof(UnityEngine.Object)) as UnityEngine.Object;
var inputObj = UIFactory.CreateInputField(rowObj, "NameInput", "...", out InputField inputField, 14, 3, 1);
UIFactory.SetLayoutElement(inputObj, minHeight: 25, flexibleWidth: 2000);
inputField.readOnly = true;
inputField.text = uObj.name;
}
internal bool showingTextureHelper;
internal bool constructedTextureViewer;
internal GameObject m_textureViewerObj;
internal void ConstructTextureHelper()
{
var rowObj = UIFactory.CreateHorizontalGroup(Content, "TextureHelper", true, false, true, true, 5, new Vector4(3, 3, 3, 3),
new Color(0.1f, 0.1f, 0.1f));
UIFactory.SetLayoutElement(rowObj, minHeight: 25, flexibleHeight: 0);
var showBtn = UIFactory.CreateButton(rowObj, "ShowButton", "Show", null, new Color(0.2f, 0.6f, 0.2f));
UIFactory.SetLayoutElement(showBtn.gameObject, minWidth: 50, flexibleWidth: 0);
UIFactory.CreateLabel(rowObj, "TextureViewerLabel", "Texture Viewer", TextAnchor.MiddleLeft);
var textureViewerObj = UIFactory.CreateScrollView(Content, "TextureViewerContent", out GameObject scrollContent, out _,
new Color(0.1f, 0.1f, 0.1f));
UIFactory.SetLayoutGroup<VerticalLayoutGroup>(textureViewerObj, false, false, true, true);
UIFactory.SetLayoutElement(textureViewerObj, minHeight: 100, flexibleHeight: 9999, flexibleWidth: 9999);
textureViewerObj.SetActive(false);
m_textureViewerObj = textureViewerObj;
var showText = showBtn.GetComponentInChildren<Text>();
showBtn.onClick.AddListener(() =>
{
showingTextureHelper = !showingTextureHelper;
if (showingTextureHelper)
{
if (!constructedTextureViewer)
ConstructTextureViewerArea(scrollContent);
showText.text = "Hide";
ToggleTextureViewer(true);
}
else
{
showText.text = "Show";
ToggleTextureViewer(false);
}
});
}
internal void ConstructTextureViewerArea(GameObject parent)
{
constructedTextureViewer = true;
var tex = Target.TryCast(typeof(Texture2D)) as Texture2D;
if (!tex)
{
ExplorerCore.LogWarning("Could not cast the target instance to Texture2D! Maybe its null or destroyed?");
return;
}
// Save helper
var saveRowObj = UIFactory.CreateHorizontalGroup(parent, "SaveRow", true, true, true, true, 2, new Vector4(2, 2, 2, 2),
new Color(0.1f, 0.1f, 0.1f));
var saveBtn = UIFactory.CreateButton(saveRowObj, "SaveButton", "Save .PNG", null, new Color(0.2f, 0.2f, 0.2f));
UIFactory.SetLayoutElement(saveBtn.gameObject, minHeight: 25, minWidth: 100, flexibleWidth: 0);
var inputObj = UIFactory.CreateInputField(saveRowObj, "SaveInput", "...", out InputField inputField);
UIFactory.SetLayoutElement(inputObj, minHeight: 25, minWidth: 100, flexibleWidth: 9999);
var name = tex.name;
if (string.IsNullOrEmpty(name))
name = "untitled";
inputField.text = Path.Combine(ConfigManager.Default_Output_Path.Value, $"{name}.png");
saveBtn.onClick.AddListener(() =>
{
if (tex && !string.IsNullOrEmpty(inputField.text))
{
var path = inputField.text;
if (!path.EndsWith(".png", StringComparison.InvariantCultureIgnoreCase))
{
ExplorerCore.LogWarning("Desired save path must end with '.png'!");
return;
}
var dir = Path.GetDirectoryName(path);
if (!Directory.Exists(dir))
Directory.CreateDirectory(dir);
if (File.Exists(path))
File.Delete(path);
if (!TextureUtilProvider.IsReadable(tex))
tex = TextureUtilProvider.ForceReadTexture(tex);
byte[] data = TextureUtilProvider.Instance.EncodeToPNG(tex);
File.WriteAllBytes(path, data);
}
});
// Actual texture viewer
var imageObj = UIFactory.CreateUIObject("TextureViewerImage", parent);
var image = imageObj.AddComponent<Image>();
var sprite = TextureUtilProvider.Instance.CreateSprite(tex);
image.sprite = sprite;
var fitter = imageObj.AddComponent<ContentSizeFitter>();
fitter.verticalFit = ContentSizeFitter.FitMode.PreferredSize;
var imageLayout = imageObj.AddComponent<LayoutElement>();
imageLayout.preferredHeight = sprite.rect.height;
imageLayout.preferredWidth = sprite.rect.width;
}
internal void ToggleTextureViewer(bool enabled)
{
m_textureViewerObj.SetActive(enabled);
m_filterAreaObj.SetActive(!enabled);
//m_memberListObj.SetActive(!enabled);
m_updateRowObj.SetActive(!enabled);
}
}
}

View File

@ -0,0 +1,484 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using UnityEngine;
using UnityEngine.UI;
using UnityExplorer.Core;
using UnityExplorer.Core.Config;
using UnityExplorer.Core.Runtime;
using UnityExplorer.UI.CacheObject;
using UnityExplorer.UI.Panels;
using UnityExplorer.UI.Utility;
using UnityExplorer.UI.Widgets;
namespace UnityExplorer.UI.Inspectors.Reflection
{
public class ReflectionInspector : InspectorBase
{
#region STATIC
public static ReflectionInspector ActiveInstance { get; private set; }
//static ReflectionInspector()
//{
// PanelDragger.OnFinishResize += (RectTransform _) => OnContainerResized();
// SceneExplorer.OnToggleShow += OnContainerResized;
//}
//private static void OnContainerResized(bool _ = false)
//{
// if (ActiveInstance == null)
// return;
// ActiveInstance.m_widthUpdateWanted = true;
//}
// Blacklists
private static readonly HashSet<string> bl_typeAndMember = new HashSet<string>
{
#if CPP
// these cause a crash in IL2CPP
"Type.DeclaringMethod",
"Rigidbody2D.Cast",
"Collider2D.Cast",
"Collider2D.Raycast",
"Texture2D.SetPixelDataImpl",
"Camera.CalculateProjectionMatrixFromPhysicalProperties",
#endif
};
private static readonly HashSet<string> bl_methodNameStartsWith = new HashSet<string>
{
// these are redundant, just adds noise, properties are supported directly
"get_",
"set_",
};
#endregion
#region INSTANCE
public override string TabLabel => m_targetTypeShortName;
public CacheObjectBase ParentMember { get; internal set; }
public ScrollPool ScrollPool { get; private set; }
public CacheMemberList CacheMemberList { get; private set; }
public GameObject InactiveHolder => m_inactiveHolder;
private GameObject m_inactiveHolder;
internal readonly Type m_targetType;
internal readonly string m_targetTypeShortName;
// all cached members of the target
internal CacheMember[] allMembers;
// filtered members based on current filters
internal readonly List<CacheMember> filteredMembers = new List<CacheMember>();
// actual shortlist of displayed members
internal readonly List<CacheMember> displayedMembers = new List<CacheMember>();
// index: Index in filter list, Value: Actual real index in allMembers list.
internal readonly List<int> filteredToRealIndices = new List<int>();
internal bool autoUpdate;
public override void OnPanelResized()
{
foreach (var member in displayedMembers)
{
member.memberLabelElement.minWidth = 0.4f * InspectorPanel.CurrentPanelWidth;
}
}
public ReflectionInspector(object target) : base(target)
{
if (this is StaticInspector)
m_targetType = target as Type;
else
m_targetType = ReflectionUtility.GetActualType(target);
m_targetTypeShortName = SignatureHighlighter.ParseFullSyntax(m_targetType, false);
ConstructUI();
CacheMembers(m_targetType);
FilterMembers();
}
public override void SetActive()
{
base.SetActive();
ActiveInstance = this;
}
public override void SetInactive()
{
base.SetInactive();
ActiveInstance = null;
}
public override void Destroy()
{
base.Destroy();
if (this.Content)
GameObject.Destroy(this.Content);
}
internal bool IsBlacklisted(string sig) => bl_typeAndMember.Any(it => sig.Contains(it));
internal bool IsBlacklisted(MethodInfo method) => bl_methodNameStartsWith.Any(it => method.Name.StartsWith(it));
internal string GetSig(MemberInfo member) => $"{member.DeclaringType.Name}.{member.Name}";
internal string AppendArgsToSig(ParameterInfo[] args)
{
string ret = " (";
foreach (var param in args)
ret += $"{param.ParameterType.Name} {param.Name}, ";
ret += ")";
return ret;
}
public void CacheMembers(Type type)
{
var list = new List<CacheMember>();
var cachedSigs = new HashSet<string>();
var types = ReflectionUtility.GetAllBaseTypes(type);
var flags = BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static;
if (this is InstanceInspector)
flags |= BindingFlags.Instance;
foreach (var declaringType in types)
{
var target = Target;
target = target.TryCast(declaringType);
IEnumerable<MemberInfo> infos = declaringType.GetMethods(flags);
infos = infos.Concat(declaringType.GetProperties(flags));
infos = infos.Concat(declaringType.GetFields(flags));
foreach (var member in infos)
{
try
{
var sig = GetSig(member);
//ExplorerCore.Log($"Trying to cache member {sig}...");
//ExplorerCore.Log(member.DeclaringType.FullName + "." + member.Name);
var mi = member as MethodInfo;
var pi = member as PropertyInfo;
var fi = member as FieldInfo;
if (IsBlacklisted(sig) || (mi != null && IsBlacklisted(mi)))
continue;
var args = mi?.GetParameters() ?? pi?.GetIndexParameters();
if (args != null)
{
if (!CacheMember.CanProcessArgs(args))
continue;
sig += AppendArgsToSig(args);
}
if (cachedSigs.Contains(sig))
continue;
cachedSigs.Add(sig);
if (mi != null)
list.Add(new CacheMethod(mi, target, InactiveHolder));
else if (pi != null)
list.Add(new CacheProperty(pi, target, InactiveHolder));
else
list.Add(new CacheField(fi, target, InactiveHolder));
var cached = list[list.Count - 1];
cached.ParentInspector = this;
}
catch (Exception e)
{
ExplorerCore.LogWarning($"Exception caching member {member.DeclaringType.FullName}.{member.Name}!");
ExplorerCore.Log(e.ToString());
}
}
}
var typeList = types.ToList();
var sorted = new List<CacheMember>();
sorted.AddRange(list.Where(it => it is CacheProperty)
.OrderBy(it => typeList.IndexOf(it.DeclaringType))
.ThenBy(it => it.NameForFiltering));
sorted.AddRange(list.Where(it => it is CacheField)
.OrderBy(it => typeList.IndexOf(it.DeclaringType))
.ThenBy(it => it.NameForFiltering));
sorted.AddRange(list.Where(it => it is CacheMethod)
.OrderBy(it => typeList.IndexOf(it.DeclaringType))
.ThenBy(it => it.NameForFiltering));
allMembers = sorted.ToArray();
}
public override void Update()
{
base.Update();
if (autoUpdate)
{
foreach (var member in displayedMembers)
{
if (member == null) break;
member.UpdateValue();
}
}
//if (m_widthUpdateWanted)
//{
// if (!m_widthUpdateWaiting)
// m_widthUpdateWaiting = true;
// else
// {
// UpdateWidths();
// m_widthUpdateWaiting = false;
// m_widthUpdateWanted = false;
// }
//}
}
internal void OnMemberFilterClicked(MemberTypes type, Button button)
{
if (m_lastActiveMemButton)
RuntimeProvider.Instance.SetColorBlock(m_lastActiveMemButton, new Color(0.2f, 0.2f, 0.2f));
m_memberFilter = type;
m_lastActiveMemButton = button;
RuntimeProvider.Instance.SetColorBlock(m_lastActiveMemButton, new Color(0.2f, 0.6f, 0.2f));
FilterMembers(null, true);
ScrollPool.EnableTempCache();
ScrollPool.Rebuild();
}
public void FilterMembers(string nameFilter = null, bool force = false)
{
int lastCount = filteredMembers.Count;
filteredMembers.Clear();
nameFilter = nameFilter?.ToLower() ?? m_nameFilterText.text.ToLower();
filteredToRealIndices.Clear();
for (int i = 0; i < allMembers.Length; i++)
{
var mem = allMembers[i];
// membertype filter
if (m_memberFilter != MemberTypes.All && mem.MemInfo.MemberType != m_memberFilter)
continue;
if (this is InstanceInspector ii && ii.m_scopeFilter != MemberScopes.All)
{
if (mem.IsStatic && ii.m_scopeFilter != MemberScopes.Static)
continue;
else if (!mem.IsStatic && ii.m_scopeFilter != MemberScopes.Instance)
continue;
}
// name filter
if (!string.IsNullOrEmpty(nameFilter) && !mem.NameForFiltering.Contains(nameFilter))
continue;
filteredMembers.Add(mem);
filteredToRealIndices.Add(i);
}
//if (force || lastCount != filteredMembers.Count)
//{
// ScrollPool.EnableTempCache();
// ScrollPool.Rebuild();
//}
}
#endregion
#region UI
private GameObject m_content;
public override GameObject Content
{
get => m_content;
set => m_content = value;
}
internal Text m_nameFilterText;
internal MemberTypes m_memberFilter;
internal Button m_lastActiveMemButton;
internal GameObject m_filterAreaObj;
internal GameObject m_updateRowObj;
internal void ConstructUI()
{
var parent = InspectorPanel.Instance.ContentHolder;
this.Content = UIFactory.CreateVerticalGroup(parent, "ReflectionInspector", true, false, true, true, 5, new Vector4(4, 4, 4, 4),
new Color(0.15f, 0.15f, 0.15f));
this.m_inactiveHolder = new GameObject("InactiveContentHolder");
m_inactiveHolder.transform.SetParent(parent.transform, false);
m_inactiveHolder.SetActive(false);
ConstructTopArea();
ConstructMemberList();
}
internal void ConstructTopArea()
{
var nameRowObj = UIFactory.CreateHorizontalGroup(Content, "NameRowObj", true, true, true, true, 2, default, new Color(1, 1, 1, 0));
UIFactory.SetLayoutElement(nameRowObj, minHeight: 25, flexibleHeight: 0, minWidth: 200, flexibleWidth: 5000);
var typeLabelText = UIFactory.CreateLabel(nameRowObj, "TypeLabel", "Type:", TextAnchor.MiddleLeft);
typeLabelText.horizontalOverflow = HorizontalWrapMode.Overflow;
UIFactory.SetLayoutElement(typeLabelText.gameObject, minWidth: 40, flexibleWidth: 0, minHeight: 25);
var typeDisplay = UIFactory.CreateLabel(nameRowObj, "TypeDisplayText", SignatureHighlighter.ParseFullSyntax(m_targetType, true),
TextAnchor.MiddleLeft);
UIFactory.SetLayoutElement(typeDisplay.gameObject, minHeight: 25, flexibleWidth: 5000);
// instance helper tools
if (this is InstanceInspector instanceInspector)
{
instanceInspector.ConstructUnityInstanceHelpers();
}
ConstructFilterArea();
ConstructUpdateRow();
}
internal void ConstructFilterArea()
{
// Filters
m_filterAreaObj = UIFactory.CreateVerticalGroup(Content, "FilterGroup", true, true, true, true, 4, new Vector4(4, 4, 4, 4),
new Color(0.1f, 0.1f, 0.1f));
UIFactory.SetLayoutElement(m_filterAreaObj, minHeight: 60);
// name filter
var nameFilterRowObj = UIFactory.CreateHorizontalGroup(m_filterAreaObj, "NameFilterRow", false, false, true, true, 5, default,
new Color(1, 1, 1, 0));
UIFactory.SetLayoutElement(nameFilterRowObj, minHeight: 25, flexibleHeight: 0, flexibleWidth: 5000);
var nameLabel = UIFactory.CreateLabel(nameFilterRowObj, "NameLabel", "Filter names:", TextAnchor.MiddleLeft, Color.grey);
UIFactory.SetLayoutElement(nameLabel.gameObject, minWidth: 100, minHeight: 25, flexibleWidth: 0);
var nameInputObj = UIFactory.CreateInputField(nameFilterRowObj, "NameInput", "...", out InputField nameInput, 14, (int)TextAnchor.MiddleLeft,
(int)HorizontalWrapMode.Overflow);
UIFactory.SetLayoutElement(nameInputObj, flexibleWidth: 5000, minWidth: 100, minHeight: 25);
nameInput.onValueChanged.AddListener((string val) =>
{
FilterMembers(val, true);
ScrollPool.EnableTempCache();
ScrollPool.Rebuild();
});
m_nameFilterText = nameInput.textComponent;
// membertype filter
var memberFilterRowObj = UIFactory.CreateHorizontalGroup(m_filterAreaObj, "MemberFilter", false, false, true, true, 5, default,
new Color(1, 1, 1, 0));
UIFactory.SetLayoutElement(memberFilterRowObj, minHeight: 25, flexibleHeight: 0, flexibleWidth: 5000);
var memLabel = UIFactory.CreateLabel(memberFilterRowObj, "MemberFilterLabel", "Filter members:", TextAnchor.MiddleLeft, Color.grey);
UIFactory.SetLayoutElement(memLabel.gameObject, minWidth: 100, minHeight: 25, flexibleWidth: 0);
AddFilterButton(memberFilterRowObj, MemberTypes.All, true);
AddFilterButton(memberFilterRowObj, MemberTypes.Method);
AddFilterButton(memberFilterRowObj, MemberTypes.Property);
AddFilterButton(memberFilterRowObj, MemberTypes.Field);
// Instance filters
if (this is InstanceInspector instanceInspector)
{
instanceInspector.ConstructInstanceScopeFilters(m_filterAreaObj);
}
}
private void AddFilterButton(GameObject parent, MemberTypes type, bool setEnabled = false)
{
var btn = UIFactory.CreateButton(parent,
"FilterButton_" + type,
type.ToString(),
null,
new Color(0.2f, 0.2f, 0.2f));
UIFactory.SetLayoutElement(btn.gameObject, minHeight: 25, minWidth: 70);
btn.onClick.AddListener(() => { OnMemberFilterClicked(type, btn); });
RuntimeProvider.Instance.SetColorBlock(btn, highlighted: new Color(0.3f, 0.7f, 0.3f));
if (setEnabled)
{
RuntimeProvider.Instance.SetColorBlock(btn, new Color(0.2f, 0.6f, 0.2f));
m_memberFilter = type;
m_lastActiveMemButton = btn;
}
}
internal void ConstructUpdateRow()
{
m_updateRowObj = UIFactory.CreateHorizontalGroup(Content, "UpdateRow", false, true, true, true, 10, default, new Color(1, 1, 1, 0));
UIFactory.SetLayoutElement(m_updateRowObj, minHeight: 25);
// update button
var updateBtn = UIFactory.CreateButton(m_updateRowObj, "UpdateButton", "Update Values", null, new Color(0.2f, 0.2f, 0.2f));
UIFactory.SetLayoutElement(updateBtn.gameObject, minWidth: 110, flexibleWidth: 0);
updateBtn.onClick.AddListener(() =>
{
bool orig = autoUpdate;
autoUpdate = true;
Update();
if (!orig)
autoUpdate = orig;
});
// auto update
var autoUpdateObj = UIFactory.CreateToggle(m_updateRowObj, "UpdateToggle", out Toggle autoUpdateToggle, out Text autoUpdateText);
var autoUpdateLayout = autoUpdateObj.AddComponent<LayoutElement>();
autoUpdateLayout.minWidth = 150;
autoUpdateLayout.minHeight = 25;
autoUpdateText.text = "Auto-update?";
autoUpdateToggle.isOn = false;
autoUpdateToggle.onValueChanged.AddListener((bool val) => { autoUpdate = val; });
}
internal void ConstructMemberList()
{
ScrollPool = UIFactory.CreateScrollPool(Content, "MemberList", out GameObject scrollRoot, out GameObject scrollContent,
new Color(0.05f, 0.05f, 0.05f));
UIFactory.SetLayoutElement(scrollRoot, flexibleHeight: 9999);
UIFactory.SetLayoutElement(scrollContent, flexibleHeight: 9999);
CacheMemberList = new CacheMemberList(ScrollPool, this);
ScrollPool.Initialize(CacheMemberList, CellViewHolder.CreatePrototypeCell(scrollRoot));
// ScrollPool.Viewport.GetComponent<Mask>().enabled = false;
}
}
#endregion
}

View File

@ -0,0 +1,14 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace UnityExplorer.UI.Inspectors.Reflection
{
public class StaticInspector : ReflectionInspector
{
public override string TabLabel => $" <color=cyan>[S]</color> {base.TabLabel}";
public StaticInspector(Type type) : base(type) { }
}
}