mirror of
https://github.com/GrahamKracker/UnityExplorer.git
synced 2025-07-05 21:02:24 +08:00
Compare commits
8 Commits
Author | SHA1 | Date | |
---|---|---|---|
cfa4b12039 | |||
c7ccdf387c | |||
bb46d77a02 | |||
c38155ab04 | |||
97dbecaa2a | |||
e77e4cce07 | |||
dcf0bdce48 | |||
2a3df5de9d |
@ -25,8 +25,8 @@
|
|||||||
|
|
||||||
| Mod Loader | IL2CPP | Mono |
|
| Mod Loader | IL2CPP | Mono |
|
||||||
| ----------- | ------ | ---- |
|
| ----------- | ------ | ---- |
|
||||||
| [MelonLoader](https://github.com/HerpDerpinstine/MelonLoader) | ✔️ [link](https://github.com/sinai-dev/Explorer/releases/latest/download/Explorer.MelonLoader.Il2Cpp.zip) | ✔️ [link](https://github.com/sinai-dev/Explorer/releases/latest/download/Explorer.MelonLoader.Mono.zip) |
|
| [MelonLoader](https://github.com/HerpDerpinstine/MelonLoader) | ✔️ [link](https://github.com/sinai-dev/UnityExplorer/releases/latest/download/UnityExplorer.MelonLoader.Il2Cpp.zip) | ✔️ [link](https://github.com/sinai-dev/UnityExplorer/releases/latest/download/UnityExplorer.MelonLoader.Mono.zip) |
|
||||||
| [BepInEx](https://github.com/BepInEx/BepInEx) | ✔️ [link](https://github.com/sinai-dev/Explorer/releases/latest/download/Explorer.BepInEx.Il2Cpp.zip) | ✔️ [link](https://github.com/sinai-dev/Explorer/releases/latest/download/Explorer.BepInEx.Mono.zip) |
|
| [BepInEx](https://github.com/BepInEx/BepInEx) | ✔️ [link](https://github.com/sinai-dev/UnityExplorer/releases/latest/download/UnityExplorer.BepInEx.Il2Cpp.zip) | ✔️ [link](https://github.com/sinai-dev/UnityExplorer/releases/latest/download/UnityExplorer.BepInEx.Mono.zip) |
|
||||||
|
|
||||||
<b>IL2CPP Issues:</b>
|
<b>IL2CPP Issues:</b>
|
||||||
* Some methods may still fail with a `MissingMethodException`, please let me know if you experience this (with full debug log please).
|
* Some methods may still fail with a `MissingMethodException`, please let me know if you experience this (with full debug log please).
|
||||||
|
@ -1,20 +1,22 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
using UnityEngine;
|
||||||
|
using UnityEngine.SceneManagement;
|
||||||
using UnityExplorer.Config;
|
using UnityExplorer.Config;
|
||||||
using UnityExplorer.Input;
|
using UnityExplorer.Input;
|
||||||
|
using UnityExplorer.Inspectors;
|
||||||
using UnityExplorer.UI;
|
using UnityExplorer.UI;
|
||||||
using UnityExplorer.UI.Modules;
|
using UnityExplorer.UI.Modules;
|
||||||
using UnityEngine;
|
#if CPP
|
||||||
using UnityExplorer.Inspectors;
|
using UnityExplorer.Helpers;
|
||||||
using System.IO;
|
#endif
|
||||||
using UnityExplorer.Unstrip;
|
|
||||||
using UnityEngine.SceneManagement;
|
|
||||||
|
|
||||||
namespace UnityExplorer
|
namespace UnityExplorer
|
||||||
{
|
{
|
||||||
public class ExplorerCore
|
public class ExplorerCore
|
||||||
{
|
{
|
||||||
public const string NAME = "UnityExplorer";
|
public const string NAME = "UnityExplorer";
|
||||||
public const string VERSION = "3.0.1";
|
public const string VERSION = "3.0.4";
|
||||||
public const string AUTHOR = "Sinai";
|
public const string AUTHOR = "Sinai";
|
||||||
public const string GUID = "com.sinai.unityexplorer";
|
public const string GUID = "com.sinai.unityexplorer";
|
||||||
public const string EXPLORER_FOLDER = @"Mods\UnityExplorer";
|
public const string EXPLORER_FOLDER = @"Mods\UnityExplorer";
|
||||||
@ -41,6 +43,10 @@ namespace UnityExplorer
|
|||||||
|
|
||||||
Instance = this;
|
Instance = this;
|
||||||
|
|
||||||
|
#if CPP
|
||||||
|
ReflectionHelpers.TryLoadGameModules();
|
||||||
|
#endif
|
||||||
|
|
||||||
if (!Directory.Exists(EXPLORER_FOLDER))
|
if (!Directory.Exists(EXPLORER_FOLDER))
|
||||||
Directory.CreateDirectory(EXPLORER_FOLDER);
|
Directory.CreateDirectory(EXPLORER_FOLDER);
|
||||||
|
|
||||||
|
@ -105,21 +105,19 @@ namespace UnityExplorer.Helpers
|
|||||||
return getType;
|
return getType;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static readonly Dictionary<Type, IntPtr> ClassPointers = new Dictionary<Type, IntPtr>();
|
private static readonly Dictionary<Type, IntPtr> CppClassPointers = new Dictionary<Type, IntPtr>();
|
||||||
|
|
||||||
public static object Il2CppCast(this object obj, Type castTo)
|
public static object Il2CppCast(this object obj, Type castTo)
|
||||||
{
|
{
|
||||||
if (!(obj is Il2CppSystem.Object ilObj))
|
if (!(obj is Il2CppSystem.Object ilObj))
|
||||||
{
|
|
||||||
return obj;
|
return obj;
|
||||||
}
|
|
||||||
|
|
||||||
if (!Il2CppTypeNotNull(castTo, out IntPtr castToPtr))
|
if (!Il2CppTypeNotNull(castTo, out IntPtr castToPtr))
|
||||||
return obj;
|
return obj;
|
||||||
|
|
||||||
IntPtr classPtr = il2cpp_object_get_class(ilObj.Pointer);
|
IntPtr castFromPtr = il2cpp_object_get_class(ilObj.Pointer);
|
||||||
|
|
||||||
if (!il2cpp_class_is_assignable_from(castToPtr, classPtr))
|
if (!il2cpp_class_is_assignable_from(castToPtr, castFromPtr))
|
||||||
return obj;
|
return obj;
|
||||||
|
|
||||||
if (RuntimeSpecificsStore.IsInjected(castToPtr))
|
if (RuntimeSpecificsStore.IsInjected(castToPtr))
|
||||||
@ -128,24 +126,21 @@ namespace UnityExplorer.Helpers
|
|||||||
return Activator.CreateInstance(castTo, ilObj.Pointer);
|
return Activator.CreateInstance(castTo, ilObj.Pointer);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static bool Il2CppTypeNotNull(Type type)
|
public static bool Il2CppTypeNotNull(Type type) => Il2CppTypeNotNull(type, out _);
|
||||||
{
|
|
||||||
return Il2CppTypeNotNull(type, out _);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static bool Il2CppTypeNotNull(Type type, out IntPtr il2cppPtr)
|
public static bool Il2CppTypeNotNull(Type type, out IntPtr il2cppPtr)
|
||||||
{
|
{
|
||||||
if (!ClassPointers.ContainsKey(type))
|
if (!CppClassPointers.ContainsKey(type))
|
||||||
{
|
{
|
||||||
il2cppPtr = (IntPtr)typeof(Il2CppClassPointerStore<>)
|
il2cppPtr = (IntPtr)typeof(Il2CppClassPointerStore<>)
|
||||||
.MakeGenericType(new Type[] { type })
|
.MakeGenericType(new Type[] { type })
|
||||||
.GetField("NativeClassPtr", BF.Public | BF.Static)
|
.GetField("NativeClassPtr", BF.Public | BF.Static)
|
||||||
.GetValue(null);
|
.GetValue(null);
|
||||||
|
|
||||||
ClassPointers.Add(type, il2cppPtr);
|
CppClassPointers.Add(type, il2cppPtr);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
il2cppPtr = ClassPointers[type];
|
il2cppPtr = CppClassPointers[type];
|
||||||
|
|
||||||
return il2cppPtr != IntPtr.Zero;
|
return il2cppPtr != IntPtr.Zero;
|
||||||
}
|
}
|
||||||
@ -181,31 +176,44 @@ namespace UnityExplorer.Helpers
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if CPP
|
||||||
|
internal static void TryLoadGameModules()
|
||||||
|
{
|
||||||
|
LoadModule("Assembly-CSharp");
|
||||||
|
LoadModule("Assembly-CSharp-firstpass");
|
||||||
|
}
|
||||||
|
|
||||||
public static bool LoadModule(string module)
|
public static bool LoadModule(string module)
|
||||||
{
|
{
|
||||||
#if CPP
|
|
||||||
#if ML
|
#if ML
|
||||||
string path = $@"MelonLoader\Managed\{module}.dll";
|
var path = $@"MelonLoader\Managed\{module}.dll";
|
||||||
#else
|
#else
|
||||||
var path = $@"BepInEx\unhollowed\{module}.dll";
|
var path = $@"BepInEx\unhollowed\{module}.dll";
|
||||||
#endif
|
#endif
|
||||||
if (!File.Exists(path))
|
|
||||||
{
|
return LoadModuleInternal(path);
|
||||||
|
}
|
||||||
|
|
||||||
|
internal static bool LoadModuleInternal(string fullPath)
|
||||||
|
{
|
||||||
|
if (!File.Exists(fullPath))
|
||||||
return false;
|
return false;
|
||||||
}
|
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
Assembly.Load(File.ReadAllBytes(path));
|
Assembly.Load(File.ReadAllBytes(fullPath));
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
ExplorerCore.Log(e.GetType() + ", " + e.Message);
|
Console.WriteLine(e.GetType() + ", " + e.Message);
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
#else
|
||||||
|
public static bool LoadModule(string module) => true;
|
||||||
|
#endif
|
||||||
|
|
||||||
public static bool IsEnumerable(Type t)
|
public static bool IsEnumerable(Type t)
|
||||||
{
|
{
|
||||||
|
@ -35,7 +35,6 @@ namespace UnityExplorer.Helpers
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
public static bool IsReadable(this Texture2D tex)
|
public static bool IsReadable(this Texture2D tex)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
@ -68,6 +67,10 @@ namespace UnityExplorer.Helpers
|
|||||||
return _newTex;
|
return _newTex;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if CPP
|
||||||
|
internal delegate void d_Blit2(IntPtr source, IntPtr dest);
|
||||||
|
#endif
|
||||||
|
|
||||||
public static Texture2D ForceReadTexture(Texture2D tex)
|
public static Texture2D ForceReadTexture(Texture2D tex)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
@ -78,7 +81,13 @@ namespace UnityExplorer.Helpers
|
|||||||
var rt = RenderTexture.GetTemporary(tex.width, tex.height, 0, RenderTextureFormat.ARGB32);
|
var rt = RenderTexture.GetTemporary(tex.width, tex.height, 0, RenderTextureFormat.ARGB32);
|
||||||
rt.filterMode = FilterMode.Point;
|
rt.filterMode = FilterMode.Point;
|
||||||
RenderTexture.active = rt;
|
RenderTexture.active = rt;
|
||||||
|
|
||||||
|
#if MONO
|
||||||
Graphics.Blit(tex, rt);
|
Graphics.Blit(tex, rt);
|
||||||
|
#else
|
||||||
|
var iCall = ICallHelper.GetICall<d_Blit2>("UnityEngine.Graphics::Blit2");
|
||||||
|
iCall.Invoke(tex.Pointer, rt.Pointer);
|
||||||
|
#endif
|
||||||
|
|
||||||
var _newTex = new Texture2D(tex.width, tex.height, TextureFormat.ARGB32, false);
|
var _newTex = new Texture2D(tex.width, tex.height, TextureFormat.ARGB32, false);
|
||||||
|
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
|
using UnityEngine.EventSystems;
|
||||||
|
|
||||||
namespace UnityExplorer.Input
|
namespace UnityExplorer.Input
|
||||||
{
|
{
|
||||||
@ -11,5 +12,12 @@ namespace UnityExplorer.Input
|
|||||||
|
|
||||||
bool GetMouseButtonDown(int btn);
|
bool GetMouseButtonDown(int btn);
|
||||||
bool GetMouseButton(int btn);
|
bool GetMouseButton(int btn);
|
||||||
|
|
||||||
|
BaseInputModule UIModule { get; }
|
||||||
|
|
||||||
|
PointerEventData InputPointerEvent { get; }
|
||||||
|
|
||||||
|
void AddUIInputModule();
|
||||||
|
void ActivateModule();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2,34 +2,26 @@
|
|||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
using System.Diagnostics.CodeAnalysis;
|
using System.Diagnostics.CodeAnalysis;
|
||||||
|
using UnityEngine.EventSystems;
|
||||||
#if CPP
|
#if CPP
|
||||||
using UnhollowerBaseLib;
|
using UnhollowerBaseLib;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace UnityExplorer.Input
|
namespace UnityExplorer.Input
|
||||||
{
|
{
|
||||||
|
public enum InputType
|
||||||
|
{
|
||||||
|
InputSystem,
|
||||||
|
Legacy,
|
||||||
|
None
|
||||||
|
}
|
||||||
|
|
||||||
public static class InputManager
|
public static class InputManager
|
||||||
{
|
{
|
||||||
|
public static InputType CurrentType { get; private set; }
|
||||||
|
|
||||||
private static IHandleInput m_inputModule;
|
private static IHandleInput m_inputModule;
|
||||||
|
|
||||||
public static void Init()
|
|
||||||
{
|
|
||||||
if (InputSystem.TKeyboard != null || (ReflectionHelpers.LoadModule("Unity.InputSystem") && InputSystem.TKeyboard != null))
|
|
||||||
{
|
|
||||||
m_inputModule = new InputSystem();
|
|
||||||
}
|
|
||||||
else if (LegacyInput.TInput != null || (ReflectionHelpers.LoadModule("UnityEngine.InputLegacyModule") && LegacyInput.TInput != null))
|
|
||||||
{
|
|
||||||
m_inputModule = new LegacyInput();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (m_inputModule == null)
|
|
||||||
{
|
|
||||||
ExplorerCore.LogWarning("Could not find any Input module!");
|
|
||||||
m_inputModule = new NoInput();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Vector3 MousePosition => m_inputModule.MousePosition;
|
public static Vector3 MousePosition => m_inputModule.MousePosition;
|
||||||
|
|
||||||
public static bool GetKeyDown(KeyCode key) => m_inputModule.GetKeyDown(key);
|
public static bool GetKeyDown(KeyCode key) => m_inputModule.GetKeyDown(key);
|
||||||
@ -37,5 +29,37 @@ namespace UnityExplorer.Input
|
|||||||
|
|
||||||
public static bool GetMouseButtonDown(int btn) => m_inputModule.GetMouseButtonDown(btn);
|
public static bool GetMouseButtonDown(int btn) => m_inputModule.GetMouseButtonDown(btn);
|
||||||
public static bool GetMouseButton(int btn) => m_inputModule.GetMouseButton(btn);
|
public static bool GetMouseButton(int btn) => m_inputModule.GetMouseButton(btn);
|
||||||
|
|
||||||
|
public static BaseInputModule UIInput => m_inputModule.UIModule;
|
||||||
|
public static PointerEventData InputPointerEvent => m_inputModule.InputPointerEvent;
|
||||||
|
|
||||||
|
public static void ActivateUIModule() => m_inputModule.ActivateModule();
|
||||||
|
|
||||||
|
public static void AddUIModule()
|
||||||
|
{
|
||||||
|
m_inputModule.AddUIInputModule();
|
||||||
|
ActivateUIModule();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void Init()
|
||||||
|
{
|
||||||
|
if (InputSystem.TKeyboard != null || (ReflectionHelpers.LoadModule("Unity.InputSystem") && InputSystem.TKeyboard != null))
|
||||||
|
{
|
||||||
|
m_inputModule = new InputSystem();
|
||||||
|
CurrentType = InputType.InputSystem;
|
||||||
|
}
|
||||||
|
else if (LegacyInput.TInput != null || (ReflectionHelpers.LoadModule("UnityEngine.InputLegacyModule") && LegacyInput.TInput != null))
|
||||||
|
{
|
||||||
|
m_inputModule = new LegacyInput();
|
||||||
|
CurrentType = InputType.Legacy;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (m_inputModule == null)
|
||||||
|
{
|
||||||
|
ExplorerCore.LogWarning("Could not find any Input module!");
|
||||||
|
m_inputModule = new NoInput();
|
||||||
|
CurrentType = InputType.None;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -2,6 +2,9 @@
|
|||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
|
using UnityEngine.EventSystems;
|
||||||
|
using UnityExplorer.UI;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace UnityExplorer.Input
|
namespace UnityExplorer.Input
|
||||||
{
|
{
|
||||||
@ -64,24 +67,46 @@ namespace UnityExplorer.Input
|
|||||||
private static PropertyInfo m_positionProp;
|
private static PropertyInfo m_positionProp;
|
||||||
private static MethodInfo m_readVector2InputMethod;
|
private static MethodInfo m_readVector2InputMethod;
|
||||||
|
|
||||||
public Vector2 MousePosition => (Vector2)m_readVector2InputMethod.Invoke(MousePositionInfo, new object[0]);
|
public Vector2 MousePosition
|
||||||
|
|
||||||
public bool GetKeyDown(KeyCode key)
|
|
||||||
{
|
{
|
||||||
var parsedKey = Enum.Parse(TKey, key.ToString());
|
get
|
||||||
var actualKey = m_kbIndexer.GetValue(CurrentKeyboard, new object[] { parsedKey });
|
{
|
||||||
|
try
|
||||||
return (bool)m_btnWasPressedProp.GetValue(actualKey, null);
|
{
|
||||||
|
return (Vector2)m_readVector2InputMethod.Invoke(MousePositionInfo, new object[0]);
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
return Vector2.zero;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public bool GetKey(KeyCode key)
|
internal static Dictionary<KeyCode, object> ActualKeyDict = new Dictionary<KeyCode, object>();
|
||||||
{
|
|
||||||
var parsed = Enum.Parse(TKey, key.ToString());
|
|
||||||
var actualKey = m_kbIndexer.GetValue(CurrentKeyboard, new object[] { parsed });
|
|
||||||
|
|
||||||
return (bool)m_btnIsPressedProp.GetValue(actualKey, null);
|
internal object GetActualKey(KeyCode key)
|
||||||
|
{
|
||||||
|
if (!ActualKeyDict.ContainsKey(key))
|
||||||
|
{
|
||||||
|
var s = key.ToString();
|
||||||
|
if (s.Contains("Control"))
|
||||||
|
s = s.Replace("Control", "Ctrl");
|
||||||
|
else if (s.Contains("Return"))
|
||||||
|
s = "Enter";
|
||||||
|
|
||||||
|
var parsed = Enum.Parse(TKey, s);
|
||||||
|
var actualKey = m_kbIndexer.GetValue(CurrentKeyboard, new object[] { parsed });
|
||||||
|
|
||||||
|
ActualKeyDict.Add(key, actualKey);
|
||||||
|
}
|
||||||
|
|
||||||
|
return ActualKeyDict[key];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public bool GetKeyDown(KeyCode key) => (bool)m_btnWasPressedProp.GetValue(GetActualKey(key), null);
|
||||||
|
|
||||||
|
public bool GetKey(KeyCode key) => (bool)m_btnIsPressedProp.GetValue(GetActualKey(key), null);
|
||||||
|
|
||||||
public bool GetMouseButtonDown(int btn)
|
public bool GetMouseButtonDown(int btn)
|
||||||
{
|
{
|
||||||
switch (btn)
|
switch (btn)
|
||||||
@ -103,5 +128,44 @@ namespace UnityExplorer.Input
|
|||||||
default: throw new NotImplementedException();
|
default: throw new NotImplementedException();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// UI Input
|
||||||
|
|
||||||
|
//public Type TInputSystemUIInputModule
|
||||||
|
// => m_tUIInputModule
|
||||||
|
// ?? (m_tUIInputModule = ReflectionHelpers.GetTypeByName("UnityEngine.InputSystem.UI.InputSystemUIInputModule"));
|
||||||
|
//internal Type m_tUIInputModule;
|
||||||
|
|
||||||
|
public BaseInputModule UIModule => null; // m_newInputModule;
|
||||||
|
//internal BaseInputModule m_newInputModule;
|
||||||
|
|
||||||
|
public PointerEventData InputPointerEvent => null;
|
||||||
|
|
||||||
|
public void AddUIInputModule()
|
||||||
|
{
|
||||||
|
// if (TInputSystemUIInputModule != null)
|
||||||
|
// {
|
||||||
|
//#if CPP
|
||||||
|
// // m_newInputModule = UIManager.CanvasRoot.AddComponent(Il2CppType.From(TInputSystemUIInputModule)).TryCast<BaseInputModule>();
|
||||||
|
//#else
|
||||||
|
// m_newInputModule = (BaseInputModule)UIManager.CanvasRoot.AddComponent(TInputSystemUIInputModule);
|
||||||
|
//#endif
|
||||||
|
// }
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// ExplorerCore.LogWarning("New input system: Could not find type by name 'UnityEngine.InputSystem.UI.InputSystemUIInputModule'");
|
||||||
|
// }
|
||||||
|
}
|
||||||
|
|
||||||
|
public void ActivateModule()
|
||||||
|
{
|
||||||
|
//#if CPP
|
||||||
|
// // m_newInputModule.ActivateModule();
|
||||||
|
//#else
|
||||||
|
// m_newInputModule.ActivateModule();
|
||||||
|
//#endif
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2,6 +2,8 @@
|
|||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
|
using UnityEngine.EventSystems;
|
||||||
|
using UnityExplorer.UI;
|
||||||
|
|
||||||
namespace UnityExplorer.Input
|
namespace UnityExplorer.Input
|
||||||
{
|
{
|
||||||
@ -36,5 +38,27 @@ namespace UnityExplorer.Input
|
|||||||
public bool GetMouseButton(int btn) => (bool)m_getMouseButtonMethod.Invoke(null, new object[] { btn });
|
public bool GetMouseButton(int btn) => (bool)m_getMouseButtonMethod.Invoke(null, new object[] { btn });
|
||||||
|
|
||||||
public bool GetMouseButtonDown(int btn) => (bool)m_getMouseButtonDownMethod.Invoke(null, new object[] { btn });
|
public bool GetMouseButtonDown(int btn) => (bool)m_getMouseButtonDownMethod.Invoke(null, new object[] { btn });
|
||||||
|
|
||||||
|
// UI Input module
|
||||||
|
|
||||||
|
public BaseInputModule UIModule => m_inputModule;
|
||||||
|
internal StandaloneInputModule m_inputModule;
|
||||||
|
|
||||||
|
public PointerEventData InputPointerEvent =>
|
||||||
|
#if CPP
|
||||||
|
m_inputModule.m_InputPointerEvent;
|
||||||
|
#else
|
||||||
|
null;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
public void AddUIInputModule()
|
||||||
|
{
|
||||||
|
m_inputModule = UIManager.CanvasRoot.gameObject.AddComponent<StandaloneInputModule>();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void ActivateModule()
|
||||||
|
{
|
||||||
|
m_inputModule.ActivateModule();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
|
using UnityEngine.EventSystems;
|
||||||
|
|
||||||
namespace UnityExplorer.Input
|
namespace UnityExplorer.Input
|
||||||
{
|
{
|
||||||
@ -13,5 +14,10 @@ namespace UnityExplorer.Input
|
|||||||
|
|
||||||
public bool GetMouseButton(int btn) => false;
|
public bool GetMouseButton(int btn) => false;
|
||||||
public bool GetMouseButtonDown(int btn) => false;
|
public bool GetMouseButtonDown(int btn) => false;
|
||||||
|
|
||||||
|
public BaseInputModule UIModule => null;
|
||||||
|
public PointerEventData InputPointerEvent => null;
|
||||||
|
public void ActivateModule() { }
|
||||||
|
public void AddUIInputModule() { }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -140,7 +140,7 @@ namespace UnityExplorer.Inspectors.GameObjects
|
|||||||
{
|
{
|
||||||
var vertGroupObj = UIFactory.CreateVerticalGroup(parent, new Color(1, 1, 1, 0));
|
var vertGroupObj = UIFactory.CreateVerticalGroup(parent, new Color(1, 1, 1, 0));
|
||||||
var vertGroup = vertGroupObj.GetComponent<VerticalLayoutGroup>();
|
var vertGroup = vertGroupObj.GetComponent<VerticalLayoutGroup>();
|
||||||
vertGroup.childForceExpandHeight = false;
|
vertGroup.childForceExpandHeight = true;
|
||||||
vertGroup.childForceExpandWidth = false;
|
vertGroup.childForceExpandWidth = false;
|
||||||
vertGroup.childControlWidth = true;
|
vertGroup.childControlWidth = true;
|
||||||
vertGroup.spacing = 5;
|
vertGroup.spacing = 5;
|
||||||
|
@ -136,7 +136,7 @@ namespace UnityExplorer.Inspectors.GameObjects
|
|||||||
{
|
{
|
||||||
var vertGroupObj = UIFactory.CreateVerticalGroup(parent, new Color(1, 1, 1, 0));
|
var vertGroupObj = UIFactory.CreateVerticalGroup(parent, new Color(1, 1, 1, 0));
|
||||||
var vertGroup = vertGroupObj.GetComponent<VerticalLayoutGroup>();
|
var vertGroup = vertGroupObj.GetComponent<VerticalLayoutGroup>();
|
||||||
vertGroup.childForceExpandHeight = false;
|
vertGroup.childForceExpandHeight = true;
|
||||||
vertGroup.childForceExpandWidth = false;
|
vertGroup.childForceExpandWidth = false;
|
||||||
vertGroup.childControlWidth = true;
|
vertGroup.childControlWidth = true;
|
||||||
vertGroup.spacing = 5;
|
vertGroup.spacing = 5;
|
||||||
@ -157,6 +157,7 @@ namespace UnityExplorer.Inspectors.GameObjects
|
|||||||
var compScrollObj = UIFactory.CreateScrollView(vertGroupObj, out s_compListContent, out SliderScrollbar scroller, new Color(0.07f, 0.07f, 0.07f));
|
var compScrollObj = UIFactory.CreateScrollView(vertGroupObj, out s_compListContent, out SliderScrollbar scroller, new Color(0.07f, 0.07f, 0.07f));
|
||||||
var contentLayout = compScrollObj.AddComponent<LayoutElement>();
|
var contentLayout = compScrollObj.AddComponent<LayoutElement>();
|
||||||
contentLayout.minHeight = 50;
|
contentLayout.minHeight = 50;
|
||||||
|
contentLayout.flexibleHeight = 5000;
|
||||||
|
|
||||||
s_compListPageHandler = new PageHandler(scroller);
|
s_compListPageHandler = new PageHandler(scroller);
|
||||||
s_compListPageHandler.ConstructUI(vertGroupObj);
|
s_compListPageHandler.ConstructUI(vertGroupObj);
|
||||||
|
@ -164,7 +164,7 @@ namespace UnityExplorer.Inspectors
|
|||||||
m_layerDropdown.value = TargetGO.layer;
|
m_layerDropdown.value = TargetGO.layer;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_lastScene != TargetGO.scene.name)
|
if (string.IsNullOrEmpty(m_lastScene) || m_lastScene != TargetGO.scene.name)
|
||||||
{
|
{
|
||||||
m_lastScene = TargetGO.scene.name;
|
m_lastScene = TargetGO.scene.name;
|
||||||
|
|
||||||
@ -217,10 +217,20 @@ namespace UnityExplorer.Inspectors
|
|||||||
|
|
||||||
s_content = UIFactory.CreateScrollView(parent, out GameObject scrollContent, out _, new Color(0.1f, 0.1f, 0.1f));
|
s_content = UIFactory.CreateScrollView(parent, out GameObject scrollContent, out _, new Color(0.1f, 0.1f, 0.1f));
|
||||||
|
|
||||||
|
var parentLayout = scrollContent.transform.parent.gameObject.AddComponent<VerticalLayoutGroup>();
|
||||||
|
parentLayout.childForceExpandWidth = true;
|
||||||
|
parentLayout.childControlWidth = true;
|
||||||
|
parentLayout.childForceExpandHeight = true;
|
||||||
|
parentLayout.childControlHeight = true;
|
||||||
|
|
||||||
var scrollGroup = scrollContent.GetComponent<VerticalLayoutGroup>();
|
var scrollGroup = scrollContent.GetComponent<VerticalLayoutGroup>();
|
||||||
scrollGroup.childForceExpandHeight = true;
|
scrollGroup.childForceExpandHeight = true;
|
||||||
scrollGroup.childControlHeight = true;
|
scrollGroup.childControlHeight = true;
|
||||||
|
scrollGroup.childForceExpandWidth = true;
|
||||||
|
scrollGroup.childControlWidth = true;
|
||||||
scrollGroup.spacing = 5;
|
scrollGroup.spacing = 5;
|
||||||
|
var contentFitter = scrollContent.GetComponent<ContentSizeFitter>();
|
||||||
|
contentFitter.verticalFit = ContentSizeFitter.FitMode.Unconstrained;
|
||||||
|
|
||||||
ConstructTopArea(scrollContent);
|
ConstructTopArea(scrollContent);
|
||||||
|
|
||||||
@ -230,6 +240,9 @@ namespace UnityExplorer.Inspectors
|
|||||||
|
|
||||||
s_childList.ConstructChildList(midGroupObj);
|
s_childList.ConstructChildList(midGroupObj);
|
||||||
s_compList.ConstructCompList(midGroupObj);
|
s_compList.ConstructCompList(midGroupObj);
|
||||||
|
|
||||||
|
LayoutRebuilder.ForceRebuildLayoutImmediate(s_content.GetComponent<RectTransform>());
|
||||||
|
Canvas.ForceUpdateCanvases();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void ConstructTopArea(GameObject scrollContent)
|
private void ConstructTopArea(GameObject scrollContent)
|
||||||
@ -431,11 +444,10 @@ namespace UnityExplorer.Inspectors
|
|||||||
midGroup.childControlWidth = true;
|
midGroup.childControlWidth = true;
|
||||||
midGroup.childForceExpandHeight = true;
|
midGroup.childForceExpandHeight = true;
|
||||||
midGroup.childControlHeight = true;
|
midGroup.childControlHeight = true;
|
||||||
var midlayout = midGroupObj.AddComponent<LayoutElement>();
|
|
||||||
midlayout.minHeight = 350;
|
var midLayout = midGroupObj.AddComponent<LayoutElement>();
|
||||||
midlayout.flexibleHeight = 10000;
|
midLayout.minHeight = 300;
|
||||||
midlayout.minWidth = 200;
|
midLayout.flexibleHeight = 5000;
|
||||||
midlayout.flexibleWidth = 25000;
|
|
||||||
|
|
||||||
return midGroupObj;
|
return midGroupObj;
|
||||||
}
|
}
|
||||||
|
@ -230,102 +230,35 @@ namespace UnityExplorer.Inspectors
|
|||||||
invisGroup.padding.right = 2;
|
invisGroup.padding.right = 2;
|
||||||
invisGroup.spacing = 10;
|
invisGroup.spacing = 10;
|
||||||
|
|
||||||
// // time scale group
|
|
||||||
|
|
||||||
// var timeGroupObj = UIFactory.CreateHorizontalGroup(invisObj, new Color(1, 1, 1, 0));
|
|
||||||
// var timeGroup = timeGroupObj.GetComponent<HorizontalLayoutGroup>();
|
|
||||||
// timeGroup.childForceExpandWidth = false;
|
|
||||||
// timeGroup.childControlWidth = true;
|
|
||||||
// timeGroup.childForceExpandHeight = false;
|
|
||||||
// timeGroup.childControlHeight = true;
|
|
||||||
// timeGroup.padding.top = 2;
|
|
||||||
// timeGroup.padding.left = 5;
|
|
||||||
// timeGroup.padding.right = 2;
|
|
||||||
// timeGroup.padding.bottom = 2;
|
|
||||||
// timeGroup.spacing = 5;
|
|
||||||
// timeGroup.childAlignment = TextAnchor.MiddleCenter;
|
|
||||||
// var timeGroupLayout = timeGroupObj.AddComponent<LayoutElement>();
|
|
||||||
// timeGroupLayout.minWidth = 100;
|
|
||||||
// timeGroupLayout.flexibleWidth = 300;
|
|
||||||
// timeGroupLayout.minHeight = 25;
|
|
||||||
// timeGroupLayout.flexibleHeight = 0;
|
|
||||||
|
|
||||||
// // time scale title
|
|
||||||
|
|
||||||
// var timeTitleObj = UIFactory.CreateLabel(timeGroupObj, TextAnchor.MiddleLeft);
|
|
||||||
// var timeTitle = timeTitleObj.GetComponent<Text>();
|
|
||||||
// timeTitle.text = "Time Scale:";
|
|
||||||
// timeTitle.color = new Color(21f / 255f, 192f / 255f, 235f / 255f);
|
|
||||||
// var titleLayout = timeTitleObj.AddComponent<LayoutElement>();
|
|
||||||
// titleLayout.minHeight = 25;
|
|
||||||
// titleLayout.minWidth = 80;
|
|
||||||
// titleLayout.flexibleHeight = 0;
|
|
||||||
// timeTitle.horizontalOverflow = HorizontalWrapMode.Overflow;
|
|
||||||
|
|
||||||
// // actual active time label
|
|
||||||
|
|
||||||
// var timeLabelObj = UIFactory.CreateLabel(timeGroupObj, TextAnchor.MiddleLeft);
|
|
||||||
// var timeLabelLayout = timeLabelObj.AddComponent<LayoutElement>();
|
|
||||||
// timeLabelLayout.minWidth = 40;
|
|
||||||
// timeLabelLayout.minHeight = 25;
|
|
||||||
// timeLabelLayout.flexibleHeight = 0;
|
|
||||||
|
|
||||||
// // todo make static and update
|
|
||||||
// var s_timeText = timeLabelObj.GetComponent<Text>();
|
|
||||||
// s_timeText.text = Time.timeScale.ToString("F1");
|
|
||||||
|
|
||||||
// // time scale input
|
|
||||||
|
|
||||||
// var timeInputObj = UIFactory.CreateInputField(timeGroupObj);
|
|
||||||
// var timeInput = timeInputObj.GetComponent<InputField>();
|
|
||||||
// timeInput.characterValidation = InputField.CharacterValidation.Decimal;
|
|
||||||
// var timeInputLayout = timeInputObj.AddComponent<LayoutElement>();
|
|
||||||
// timeInputLayout.minWidth = 90;
|
|
||||||
// timeInputLayout.flexibleWidth = 0;
|
|
||||||
// timeInputLayout.minHeight = 25;
|
|
||||||
// timeInputLayout.flexibleHeight = 0;
|
|
||||||
|
|
||||||
// // time scale apply button
|
|
||||||
|
|
||||||
// var applyBtnObj = UIFactory.CreateButton(timeGroupObj);
|
|
||||||
// var applyBtn = applyBtnObj.GetComponent<Button>();
|
|
||||||
|
|
||||||
// applyBtn.onClick.AddListener(SetTimeScale);
|
|
||||||
|
|
||||||
// var applyText = applyBtnObj.GetComponentInChildren<Text>();
|
|
||||||
// applyText.text = "Apply";
|
|
||||||
// applyText.fontSize = 14;
|
|
||||||
// var applyLayout = applyBtnObj.AddComponent<LayoutElement>();
|
|
||||||
// applyLayout.minWidth = 50;
|
|
||||||
// applyLayout.minHeight = 25;
|
|
||||||
// applyLayout.flexibleHeight = 0;
|
|
||||||
|
|
||||||
// void SetTimeScale()
|
|
||||||
// {
|
|
||||||
// var scale = float.Parse(timeInput.text);
|
|
||||||
// Time.timeScale = scale;
|
|
||||||
// s_timeText.text = Time.timeScale.ToString("F1");
|
|
||||||
// }
|
|
||||||
|
|
||||||
|
|
||||||
// inspect under mouse button
|
// inspect under mouse button
|
||||||
|
AddMouseInspectButton(topRowObj, MouseInspector.MouseInspectMode.UI);
|
||||||
|
AddMouseInspectButton(topRowObj, MouseInspector.MouseInspectMode.World);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void AddMouseInspectButton(GameObject topRowObj, MouseInspector.MouseInspectMode mode)
|
||||||
|
{
|
||||||
var inspectObj = UIFactory.CreateButton(topRowObj);
|
var inspectObj = UIFactory.CreateButton(topRowObj);
|
||||||
var inspectLayout = inspectObj.AddComponent<LayoutElement>();
|
var inspectLayout = inspectObj.AddComponent<LayoutElement>();
|
||||||
inspectLayout.minWidth = 120;
|
inspectLayout.minWidth = 120;
|
||||||
inspectLayout.flexibleWidth = 0;
|
inspectLayout.flexibleWidth = 0;
|
||||||
|
|
||||||
|
var inspectText = inspectObj.GetComponentInChildren<Text>();
|
||||||
|
inspectText.text = "Mouse Inspect";
|
||||||
|
inspectText.fontSize = 13;
|
||||||
|
|
||||||
|
if (mode == MouseInspector.MouseInspectMode.UI)
|
||||||
|
inspectText.text += " (UI)";
|
||||||
|
|
||||||
var inspectBtn = inspectObj.GetComponent<Button>();
|
var inspectBtn = inspectObj.GetComponent<Button>();
|
||||||
var inspectColors = inspectBtn.colors;
|
var inspectColors = inspectBtn.colors;
|
||||||
inspectColors.normalColor = new Color(0.2f, 0.2f, 0.2f);
|
inspectColors.normalColor = new Color(0.2f, 0.2f, 0.2f);
|
||||||
inspectBtn.colors = inspectColors;
|
inspectBtn.colors = inspectColors;
|
||||||
var inspectText = inspectObj.GetComponentInChildren<Text>();
|
|
||||||
inspectText.text = "Mouse Inspect";
|
|
||||||
inspectText.fontSize = 13;
|
|
||||||
|
|
||||||
inspectBtn.onClick.AddListener(OnInspectMouseClicked);
|
inspectBtn.onClick.AddListener(OnInspectMouseClicked);
|
||||||
|
|
||||||
void OnInspectMouseClicked()
|
void OnInspectMouseClicked()
|
||||||
{
|
{
|
||||||
|
MouseInspector.Mode = mode;
|
||||||
MouseInspector.StartInspect();
|
MouseInspector.StartInspect();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3,18 +3,27 @@ using System.Collections.Generic;
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
|
using UnityEngine.EventSystems;
|
||||||
using UnityEngine.UI;
|
using UnityEngine.UI;
|
||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
using UnityExplorer.Input;
|
using UnityExplorer.Input;
|
||||||
using UnityExplorer.UI;
|
using UnityExplorer.UI;
|
||||||
|
using UnityExplorer.Unstrip;
|
||||||
|
|
||||||
namespace UnityExplorer.Inspectors
|
namespace UnityExplorer.Inspectors
|
||||||
{
|
{
|
||||||
public class MouseInspector
|
public class MouseInspector
|
||||||
{
|
{
|
||||||
|
public enum MouseInspectMode
|
||||||
|
{
|
||||||
|
World,
|
||||||
|
UI
|
||||||
|
}
|
||||||
|
|
||||||
public static bool Enabled { get; set; }
|
public static bool Enabled { get; set; }
|
||||||
|
|
||||||
//internal static Text s_objUnderMouseName;
|
public static MouseInspectMode Mode { get; set; }
|
||||||
|
|
||||||
internal static Text s_objNameLabel;
|
internal static Text s_objNameLabel;
|
||||||
internal static Text s_objPathLabel;
|
internal static Text s_objPathLabel;
|
||||||
internal static Text s_mousePosLabel;
|
internal static Text s_mousePosLabel;
|
||||||
@ -29,6 +38,18 @@ namespace UnityExplorer.Inspectors
|
|||||||
Enabled = true;
|
Enabled = true;
|
||||||
MainMenu.Instance.MainPanel.SetActive(false);
|
MainMenu.Instance.MainPanel.SetActive(false);
|
||||||
s_UIContent.SetActive(true);
|
s_UIContent.SetActive(true);
|
||||||
|
|
||||||
|
// recache Graphic Raycasters each time we start
|
||||||
|
var casters = ResourcesUnstrip.FindObjectsOfTypeAll(typeof(GraphicRaycaster));
|
||||||
|
m_gCasters = new GraphicRaycaster[casters.Length];
|
||||||
|
for (int i = 0; i < casters.Length; i++)
|
||||||
|
{
|
||||||
|
#if CPP
|
||||||
|
m_gCasters[i] = casters[i].TryCast<GraphicRaycaster>();
|
||||||
|
#else
|
||||||
|
m_gCasters[i] = casters[i] as GraphicRaycaster;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void StopInspect()
|
public static void StopInspect()
|
||||||
@ -40,49 +61,68 @@ namespace UnityExplorer.Inspectors
|
|||||||
ClearHitData();
|
ClearHitData();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
internal static GraphicRaycaster[] m_gCasters;
|
||||||
|
|
||||||
public static void UpdateInspect()
|
public static void UpdateInspect()
|
||||||
{
|
{
|
||||||
if (InputManager.GetKeyDown(KeyCode.Escape))
|
if (InputManager.GetKeyDown(KeyCode.Escape))
|
||||||
{
|
{
|
||||||
StopInspect();
|
StopInspect();
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
var mousePos = InputManager.MousePosition;
|
var mousePos = InputManager.MousePosition;
|
||||||
|
|
||||||
if (mousePos != s_lastMousePos)
|
if (mousePos != s_lastMousePos)
|
||||||
{
|
UpdatePosition(mousePos);
|
||||||
s_lastMousePos = mousePos;
|
|
||||||
|
|
||||||
var inversePos = UIManager.CanvasRoot.transform.InverseTransformPoint(mousePos);
|
|
||||||
|
|
||||||
s_mousePosLabel.text = $"<color=grey>Mouse Position:</color> {((Vector2)InputManager.MousePosition).ToString()}";
|
|
||||||
|
|
||||||
float yFix = mousePos.y < 120 ? 80 : -80;
|
|
||||||
|
|
||||||
s_UIContent.transform.localPosition = new Vector3(inversePos.x, inversePos.y + yFix, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!UnityHelpers.MainCamera)
|
if (!UnityHelpers.MainCamera)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// actual inspect raycast
|
// actual inspect raycast
|
||||||
var ray = UnityHelpers.MainCamera.ScreenPointToRay(mousePos);
|
|
||||||
|
|
||||||
if (Physics.Raycast(ray, out RaycastHit hit, 1000f))
|
switch (Mode)
|
||||||
{
|
{
|
||||||
var obj = hit.transform.gameObject;
|
case MouseInspectMode.UI:
|
||||||
|
RaycastUI(mousePos); break;
|
||||||
|
case MouseInspectMode.World:
|
||||||
|
RaycastWorld(mousePos); break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (obj != s_lastHit)
|
internal static void OnHitGameObject(GameObject obj)
|
||||||
{
|
{
|
||||||
s_lastHit = obj;
|
if (obj != s_lastHit)
|
||||||
s_objNameLabel.text = $"<b>Click to Inspect:</b> <color=cyan>{obj.name}</color>";
|
{
|
||||||
s_objPathLabel.text = $"Path: {obj.transform.GetTransformPath(true)}";
|
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))
|
if (InputManager.GetMouseButtonDown(0))
|
||||||
|
{
|
||||||
|
StopInspect();
|
||||||
|
InspectorManager.Instance.Inspect(obj);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
internal static void RaycastWorld(Vector2 mousePos)
|
||||||
|
{
|
||||||
|
var ray = UnityHelpers.MainCamera.ScreenPointToRay(mousePos);
|
||||||
|
var casts = Physics.RaycastAll(ray, 1000f);
|
||||||
|
|
||||||
|
if (casts.Length > 0)
|
||||||
|
{
|
||||||
|
foreach (var cast in casts)
|
||||||
{
|
{
|
||||||
StopInspect();
|
if (cast.transform)
|
||||||
InspectorManager.Instance.Inspect(obj);
|
{
|
||||||
|
var obj = cast.transform.gameObject;
|
||||||
|
|
||||||
|
OnHitGameObject(obj);
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -92,6 +132,56 @@ namespace UnityExplorer.Inspectors
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
internal static void RaycastUI(Vector2 mousePos)
|
||||||
|
{
|
||||||
|
var ped = new PointerEventData(null)
|
||||||
|
{
|
||||||
|
position = mousePos
|
||||||
|
};
|
||||||
|
|
||||||
|
#if MONO
|
||||||
|
var list = new List<RaycastResult>();
|
||||||
|
#else
|
||||||
|
var list = new Il2CppSystem.Collections.Generic.List<RaycastResult>();
|
||||||
|
#endif
|
||||||
|
foreach (var gr in m_gCasters)
|
||||||
|
{
|
||||||
|
gr.Raycast(ped, list);
|
||||||
|
|
||||||
|
if (list.Count > 0)
|
||||||
|
{
|
||||||
|
foreach (var hit in list)
|
||||||
|
{
|
||||||
|
if (hit.gameObject)
|
||||||
|
{
|
||||||
|
var obj = hit.gameObject;
|
||||||
|
|
||||||
|
OnHitGameObject(obj);
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (s_lastHit)
|
||||||
|
ClearHitData();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
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 ClearHitData()
|
internal static void ClearHitData()
|
||||||
{
|
{
|
||||||
s_lastHit = null;
|
s_lastHit = null;
|
||||||
@ -99,7 +189,7 @@ namespace UnityExplorer.Inspectors
|
|||||||
s_objPathLabel.text = "";
|
s_objPathLabel.text = "";
|
||||||
}
|
}
|
||||||
|
|
||||||
#region UI Construction
|
#region UI Construction
|
||||||
|
|
||||||
internal static void ConstructUI()
|
internal static void ConstructUI()
|
||||||
{
|
{
|
||||||
@ -112,7 +202,10 @@ namespace UnityExplorer.Inspectors
|
|||||||
baseRect.anchorMin = half;
|
baseRect.anchorMin = half;
|
||||||
baseRect.anchorMax = half;
|
baseRect.anchorMax = half;
|
||||||
baseRect.pivot = half;
|
baseRect.pivot = half;
|
||||||
baseRect.sizeDelta = new Vector2(700, 100);
|
baseRect.sizeDelta = new Vector2(700, 150);
|
||||||
|
|
||||||
|
var group = content.GetComponent<VerticalLayoutGroup>();
|
||||||
|
group.childForceExpandHeight = true;
|
||||||
|
|
||||||
// Title text
|
// Title text
|
||||||
|
|
||||||
@ -131,13 +224,16 @@ namespace UnityExplorer.Inspectors
|
|||||||
|
|
||||||
var pathLabelObj = UIFactory.CreateLabel(content, TextAnchor.MiddleLeft);
|
var pathLabelObj = UIFactory.CreateLabel(content, TextAnchor.MiddleLeft);
|
||||||
s_objPathLabel = pathLabelObj.GetComponent<Text>();
|
s_objPathLabel = pathLabelObj.GetComponent<Text>();
|
||||||
s_objPathLabel.color = Color.grey;
|
|
||||||
s_objPathLabel.fontStyle = FontStyle.Italic;
|
s_objPathLabel.fontStyle = FontStyle.Italic;
|
||||||
s_objPathLabel.horizontalOverflow = HorizontalWrapMode.Overflow;
|
s_objPathLabel.horizontalOverflow = HorizontalWrapMode.Wrap;
|
||||||
|
|
||||||
|
var pathLayout = pathLabelObj.AddComponent<LayoutElement>();
|
||||||
|
pathLayout.minHeight = 75;
|
||||||
|
pathLayout.flexibleHeight = 0;
|
||||||
|
|
||||||
s_UIContent.SetActive(false);
|
s_UIContent.SetActive(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -5,6 +5,7 @@ using System.Text;
|
|||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
using UnityExplorer.UI;
|
using UnityExplorer.UI;
|
||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
|
using UnityEngine;
|
||||||
|
|
||||||
namespace UnityExplorer.Inspectors.Reflection
|
namespace UnityExplorer.Inspectors.Reflection
|
||||||
{
|
{
|
||||||
@ -14,7 +15,7 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
public override Type FallbackType => (MemInfo as FieldInfo).FieldType;
|
public override Type FallbackType => (MemInfo as FieldInfo).FieldType;
|
||||||
|
|
||||||
public CacheField(FieldInfo fieldInfo, object declaringInstance) : base(fieldInfo, declaringInstance)
|
public CacheField(FieldInfo fieldInfo, object declaringInstance, GameObject parent) : base(fieldInfo, declaringInstance, parent)
|
||||||
{
|
{
|
||||||
CreateIValue(null, fieldInfo.FieldType);
|
CreateIValue(null, fieldInfo.FieldType);
|
||||||
}
|
}
|
||||||
|
@ -43,11 +43,12 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
public string RichTextName => m_richTextName ?? GetRichTextName();
|
public string RichTextName => m_richTextName ?? GetRichTextName();
|
||||||
private string m_richTextName;
|
private string m_richTextName;
|
||||||
|
|
||||||
public CacheMember(MemberInfo memberInfo, object declaringInstance)
|
public CacheMember(MemberInfo memberInfo, object declaringInstance, GameObject parentContent)
|
||||||
{
|
{
|
||||||
MemInfo = memberInfo;
|
MemInfo = memberInfo;
|
||||||
DeclaringType = memberInfo.DeclaringType;
|
DeclaringType = memberInfo.DeclaringType;
|
||||||
DeclaringInstance = declaringInstance;
|
DeclaringInstance = declaringInstance;
|
||||||
|
this.m_parentContent = parentContent;
|
||||||
#if CPP
|
#if CPP
|
||||||
if (DeclaringInstance != null)
|
if (DeclaringInstance != null)
|
||||||
DeclaringInstance = DeclaringInstance.Il2CppCast(DeclaringType);
|
DeclaringInstance = DeclaringInstance.Il2CppCast(DeclaringType);
|
||||||
|
@ -26,7 +26,7 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
public string[] m_genericArgInput = new string[0];
|
public string[] m_genericArgInput = new string[0];
|
||||||
|
|
||||||
public CacheMethod(MethodInfo methodInfo, object declaringInstance) : base(methodInfo, declaringInstance)
|
public CacheMethod(MethodInfo methodInfo, object declaringInstance, GameObject parent) : base(methodInfo, declaringInstance, parent)
|
||||||
{
|
{
|
||||||
GenericArgs = methodInfo.GetGenericArguments();
|
GenericArgs = methodInfo.GetGenericArguments();
|
||||||
|
|
||||||
|
@ -5,6 +5,7 @@ using System.Text;
|
|||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
using UnityExplorer.UI;
|
using UnityExplorer.UI;
|
||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
|
using UnityEngine;
|
||||||
|
|
||||||
namespace UnityExplorer.Inspectors.Reflection
|
namespace UnityExplorer.Inspectors.Reflection
|
||||||
{
|
{
|
||||||
@ -14,7 +15,7 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
public override bool IsStatic => (MemInfo as PropertyInfo).GetAccessors(true)[0].IsStatic;
|
public override bool IsStatic => (MemInfo as PropertyInfo).GetAccessors(true)[0].IsStatic;
|
||||||
|
|
||||||
public CacheProperty(PropertyInfo propertyInfo, object declaringInstance) : base(propertyInfo, declaringInstance)
|
public CacheProperty(PropertyInfo propertyInfo, object declaringInstance, GameObject parent) : base(propertyInfo, declaringInstance, parent)
|
||||||
{
|
{
|
||||||
this.m_arguments = propertyInfo.GetIndexParameters();
|
this.m_arguments = propertyInfo.GetIndexParameters();
|
||||||
this.m_argumentInput = new string[m_arguments.Length];
|
this.m_argumentInput = new string[m_arguments.Length];
|
||||||
|
@ -45,19 +45,95 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
public void ConstructInstanceHelpers()
|
public void ConstructInstanceHelpers()
|
||||||
{
|
{
|
||||||
|
if (!typeof(Component).IsAssignableFrom(m_targetType) && !typeof(UnityEngine.Object).IsAssignableFrom(m_targetType))
|
||||||
|
return;
|
||||||
|
|
||||||
|
var rowObj = UIFactory.CreateHorizontalGroup(Content, new Color(0.1f, 0.1f, 0.1f));
|
||||||
|
var rowGroup = rowObj.GetComponent<HorizontalLayoutGroup>();
|
||||||
|
rowGroup.childForceExpandWidth = true;
|
||||||
|
rowGroup.childControlWidth = true;
|
||||||
|
rowGroup.spacing = 5;
|
||||||
|
rowGroup.padding.top = 2;
|
||||||
|
rowGroup.padding.bottom = 2;
|
||||||
|
rowGroup.padding.right = 2;
|
||||||
|
rowGroup.padding.left = 2;
|
||||||
|
var rowLayout = rowObj.AddComponent<LayoutElement>();
|
||||||
|
rowLayout.minHeight = 25;
|
||||||
|
rowLayout.flexibleWidth = 5000;
|
||||||
|
|
||||||
|
if (typeof(Component).IsAssignableFrom(m_targetType))
|
||||||
|
{
|
||||||
|
ConstructCompHelper(rowObj);
|
||||||
|
}
|
||||||
|
|
||||||
|
ConstructUObjHelper(rowObj);
|
||||||
|
|
||||||
// WIP
|
// WIP
|
||||||
|
|
||||||
//if (m_targetType == typeof(Texture2D))
|
//if (m_targetType == typeof(Texture2D))
|
||||||
// ConstructTextureHelper();
|
// ConstructTextureHelper();
|
||||||
|
}
|
||||||
|
|
||||||
// todo other helpers
|
internal void ConstructCompHelper(GameObject rowObj)
|
||||||
|
{
|
||||||
|
var labelObj = UIFactory.CreateLabel(rowObj, TextAnchor.MiddleLeft);
|
||||||
|
var labelLayout = labelObj.AddComponent<LayoutElement>();
|
||||||
|
labelLayout.minWidth = 90;
|
||||||
|
labelLayout.minHeight = 25;
|
||||||
|
labelLayout.flexibleWidth = 0;
|
||||||
|
var labelText = labelObj.GetComponent<Text>();
|
||||||
|
labelText.text = "GameObject:";
|
||||||
|
|
||||||
//if (typeof(Component).IsAssignableFrom(m_targetType))
|
#if MONO
|
||||||
//{
|
var comp = Target as Component;
|
||||||
//}
|
#else
|
||||||
//else if (typeof(UnityEngine.Object).IsAssignableFrom(m_targetType))
|
var comp = (Target as Il2CppSystem.Object).TryCast<Component>();
|
||||||
//{
|
#endif
|
||||||
//}
|
|
||||||
|
var goBtnObj = UIFactory.CreateButton(rowObj, new Color(0.2f, 0.5f, 0.2f));
|
||||||
|
var goBtnLayout = goBtnObj.AddComponent<LayoutElement>();
|
||||||
|
goBtnLayout.minHeight = 25;
|
||||||
|
goBtnLayout.minWidth = 200;
|
||||||
|
goBtnLayout.flexibleWidth = 0;
|
||||||
|
var text = goBtnObj.GetComponentInChildren<Text>();
|
||||||
|
text.text = comp.name;
|
||||||
|
var btn = goBtnObj.GetComponent<Button>();
|
||||||
|
btn.onClick.AddListener(() => { InspectorManager.Instance.Inspect(comp.gameObject); });
|
||||||
|
}
|
||||||
|
|
||||||
|
internal void ConstructUObjHelper(GameObject rowObj)
|
||||||
|
{
|
||||||
|
var labelObj = UIFactory.CreateLabel(rowObj, TextAnchor.MiddleLeft);
|
||||||
|
var labelLayout = labelObj.AddComponent<LayoutElement>();
|
||||||
|
labelLayout.minWidth = 60;
|
||||||
|
labelLayout.minHeight = 25;
|
||||||
|
labelLayout.flexibleWidth = 0;
|
||||||
|
var labelText = labelObj.GetComponent<Text>();
|
||||||
|
labelText.text = "Name:";
|
||||||
|
|
||||||
|
#if MONO
|
||||||
|
var uObj = Target as UnityEngine.Object;
|
||||||
|
#else
|
||||||
|
var uObj = (Target as Il2CppSystem.Object).TryCast<UnityEngine.Object>();
|
||||||
|
#endif
|
||||||
|
|
||||||
|
var inputObj = UIFactory.CreateInputField(rowObj, 14, 3, 1);
|
||||||
|
var inputLayout = inputObj.AddComponent<LayoutElement>();
|
||||||
|
inputLayout.minHeight = 25;
|
||||||
|
inputLayout.flexibleWidth = 2000;
|
||||||
|
var inputField = inputObj.GetComponent<InputField>();
|
||||||
|
inputField.readOnly = true;
|
||||||
|
inputField.text = uObj.name;
|
||||||
|
|
||||||
|
//var goBtnObj = UIFactory.CreateButton(rowObj, new Color(0.2f, 0.5f, 0.2f));
|
||||||
|
//var goBtnLayout = goBtnObj.AddComponent<LayoutElement>();
|
||||||
|
//goBtnLayout.minHeight = 25;
|
||||||
|
//goBtnLayout.minWidth = 200;
|
||||||
|
//goBtnLayout.flexibleWidth = 0;
|
||||||
|
//var text = goBtnObj.GetComponentInChildren<Text>();
|
||||||
|
//text.text = comp.name;
|
||||||
|
//var btn = goBtnObj.GetComponent<Button>();
|
||||||
|
//btn.onClick.AddListener(() => { InspectorManager.Instance.Inspect(comp.gameObject); });
|
||||||
}
|
}
|
||||||
|
|
||||||
//internal bool showingTextureHelper;
|
//internal bool showingTextureHelper;
|
||||||
|
@ -37,14 +37,7 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
if (m_subContentConstructed)
|
if (m_subContentConstructed)
|
||||||
{
|
{
|
||||||
// changing types, destroy subcontent
|
DestroySubContent();
|
||||||
for (int i = 0; i < m_subContentParent.transform.childCount; i++)
|
|
||||||
{
|
|
||||||
var child = m_subContentParent.transform.GetChild(i);
|
|
||||||
GameObject.Destroy(child.gameObject);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_subContentConstructed = false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!s_enumNamesCache.ContainsKey(type))
|
if (!s_enumNamesCache.ContainsKey(type))
|
||||||
@ -96,7 +89,10 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
private void SetValueFromDropdown()
|
private void SetValueFromDropdown()
|
||||||
{
|
{
|
||||||
var type = Value?.GetType() ?? FallbackType;
|
var type = Value?.GetType() ?? FallbackType;
|
||||||
var value = Enum.Parse(type, m_dropdownText.text);
|
var index = m_dropdown.value;
|
||||||
|
|
||||||
|
var value = Enum.Parse(type, s_enumNamesCache[type][index].Value);
|
||||||
|
|
||||||
if (value != null)
|
if (value != null)
|
||||||
{
|
{
|
||||||
Value = value;
|
Value = value;
|
||||||
|
@ -14,8 +14,9 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
{
|
{
|
||||||
public InteractiveString(object value, Type valueType) : base(value, valueType) { }
|
public InteractiveString(object value, Type valueType) : base(value, valueType) { }
|
||||||
|
|
||||||
public override bool HasSubContent => false;
|
public override bool HasSubContent => true;
|
||||||
public override bool SubContentWanted => false;
|
public override bool SubContentWanted => true;
|
||||||
|
|
||||||
public override bool WantInspectBtn => false;
|
public override bool WantInspectBtn => false;
|
||||||
|
|
||||||
public override void OnValueUpdated()
|
public override void OnValueUpdated()
|
||||||
@ -27,10 +28,9 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
{
|
{
|
||||||
base.OnException(member);
|
base.OnException(member);
|
||||||
|
|
||||||
if (m_hiddenObj.gameObject.activeSelf)
|
if (m_subContentConstructed && m_hiddenObj.gameObject.activeSelf)
|
||||||
m_hiddenObj.gameObject.SetActive(false);
|
m_hiddenObj.gameObject.SetActive(false);
|
||||||
|
|
||||||
// m_baseLabel.text = DefaultLabel;
|
|
||||||
m_labelLayout.minWidth = 200;
|
m_labelLayout.minWidth = 200;
|
||||||
m_labelLayout.flexibleWidth = 5000;
|
m_labelLayout.flexibleWidth = 5000;
|
||||||
}
|
}
|
||||||
@ -45,39 +45,62 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!m_hiddenObj.gameObject.activeSelf)
|
|
||||||
m_hiddenObj.gameObject.SetActive(true);
|
|
||||||
|
|
||||||
m_baseLabel.text = m_richValueType;
|
m_baseLabel.text = m_richValueType;
|
||||||
|
|
||||||
if (Value != null)
|
if (m_subContentConstructed)
|
||||||
{
|
{
|
||||||
var toString = Value.ToString();
|
if (!m_hiddenObj.gameObject.activeSelf)
|
||||||
|
m_hiddenObj.gameObject.SetActive(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!string.IsNullOrEmpty((string)Value))
|
||||||
|
{
|
||||||
|
var toString = (string)Value;
|
||||||
if (toString.Length > 15000)
|
if (toString.Length > 15000)
|
||||||
toString = toString.Substring(0, 15000);
|
toString = toString.Substring(0, 15000);
|
||||||
|
|
||||||
m_valueInput.text = toString;
|
m_readonlyInput.text = toString;
|
||||||
m_placeholderText.text = toString;
|
|
||||||
|
if (m_subContentConstructed)
|
||||||
|
{
|
||||||
|
m_valueInput.text = toString;
|
||||||
|
m_placeholderText.text = toString;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
m_valueInput.text = "";
|
string s = Value == null
|
||||||
m_placeholderText.text = "null";
|
? "null"
|
||||||
|
: "empty";
|
||||||
|
|
||||||
|
m_readonlyInput.text = $"<i><color=grey>{s}</color></i>";
|
||||||
|
|
||||||
|
if (m_subContentConstructed)
|
||||||
|
{
|
||||||
|
m_valueInput.text = "";
|
||||||
|
m_placeholderText.text = s;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
m_labelLayout.minWidth = 50;
|
m_labelLayout.minWidth = 50;
|
||||||
m_labelLayout.flexibleWidth = 0;
|
m_labelLayout.flexibleWidth = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
internal void OnApplyClicked()
|
internal void OnApplyClicked()
|
||||||
{
|
{
|
||||||
Value = m_valueInput.text;
|
Value = m_valueInput.text;
|
||||||
Owner.SetValue();
|
Owner.SetValue();
|
||||||
|
RefreshUIForValue();
|
||||||
}
|
}
|
||||||
|
|
||||||
internal InputField m_valueInput;
|
// for the default label
|
||||||
internal LayoutElement m_labelLayout;
|
internal LayoutElement m_labelLayout;
|
||||||
|
|
||||||
|
//internal InputField m_readonlyInput;
|
||||||
|
internal Text m_readonlyInput;
|
||||||
|
|
||||||
|
// for input
|
||||||
|
internal InputField m_valueInput;
|
||||||
internal GameObject m_hiddenObj;
|
internal GameObject m_hiddenObj;
|
||||||
internal Text m_placeholderText;
|
internal Text m_placeholderText;
|
||||||
|
|
||||||
@ -90,12 +113,38 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
m_labelLayout = m_baseLabel.gameObject.GetComponent<LayoutElement>();
|
m_labelLayout = m_baseLabel.gameObject.GetComponent<LayoutElement>();
|
||||||
|
|
||||||
m_hiddenObj = UIFactory.CreateLabel(m_valueContent, TextAnchor.MiddleLeft);
|
var readonlyInputObj = UIFactory.CreateLabel(m_valueContent, TextAnchor.MiddleLeft);
|
||||||
|
m_readonlyInput = readonlyInputObj.GetComponent<Text>();
|
||||||
|
m_readonlyInput.horizontalOverflow = HorizontalWrapMode.Overflow;
|
||||||
|
|
||||||
|
var testFitter = readonlyInputObj.AddComponent<ContentSizeFitter>();
|
||||||
|
testFitter.verticalFit = ContentSizeFitter.FitMode.MinSize;
|
||||||
|
|
||||||
|
var labelLayout = readonlyInputObj.AddComponent<LayoutElement>();
|
||||||
|
labelLayout.minHeight = 25;
|
||||||
|
labelLayout.preferredHeight = 25;
|
||||||
|
labelLayout.flexibleHeight = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void ConstructSubcontent()
|
||||||
|
{
|
||||||
|
base.ConstructSubcontent();
|
||||||
|
|
||||||
|
var groupObj = UIFactory.CreateVerticalGroup(m_subContentParent, new Color(1, 1, 1, 0));
|
||||||
|
var group = groupObj.GetComponent<VerticalLayoutGroup>();
|
||||||
|
group.spacing = 4;
|
||||||
|
group.padding.top = 3;
|
||||||
|
group.padding.left = 3;
|
||||||
|
group.padding.right = 3;
|
||||||
|
group.padding.bottom = 3;
|
||||||
|
|
||||||
|
m_hiddenObj = UIFactory.CreateLabel(groupObj, TextAnchor.MiddleLeft);
|
||||||
m_hiddenObj.SetActive(false);
|
m_hiddenObj.SetActive(false);
|
||||||
var hiddenText = m_hiddenObj.GetComponent<Text>();
|
var hiddenText = m_hiddenObj.GetComponent<Text>();
|
||||||
hiddenText.color = Color.clear;
|
hiddenText.color = Color.clear;
|
||||||
hiddenText.fontSize = 14;
|
hiddenText.fontSize = 14;
|
||||||
hiddenText.raycastTarget = false;
|
hiddenText.raycastTarget = false;
|
||||||
|
hiddenText.supportRichText = false;
|
||||||
var hiddenFitter = m_hiddenObj.AddComponent<ContentSizeFitter>();
|
var hiddenFitter = m_hiddenObj.AddComponent<ContentSizeFitter>();
|
||||||
hiddenFitter.verticalFit = ContentSizeFitter.FitMode.PreferredSize;
|
hiddenFitter.verticalFit = ContentSizeFitter.FitMode.PreferredSize;
|
||||||
var hiddenLayout = m_hiddenObj.AddComponent<LayoutElement>();
|
var hiddenLayout = m_hiddenObj.AddComponent<LayoutElement>();
|
||||||
@ -121,19 +170,23 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
m_placeholderText = m_valueInput.placeholder.GetComponent<Text>();
|
m_placeholderText = m_valueInput.placeholder.GetComponent<Text>();
|
||||||
|
|
||||||
m_valueInput.onValueChanged.AddListener((string val) =>
|
m_placeholderText.supportRichText = false;
|
||||||
|
m_valueInput.textComponent.supportRichText = false;
|
||||||
|
|
||||||
|
m_valueInput.onValueChanged.AddListener((string val) =>
|
||||||
{
|
{
|
||||||
hiddenText.text = val;
|
hiddenText.text = val ?? "";
|
||||||
LayoutRebuilder.ForceRebuildLayoutImmediate(Owner.m_mainRect);
|
LayoutRebuilder.ForceRebuildLayoutImmediate(Owner.m_mainRect);
|
||||||
});
|
});
|
||||||
|
|
||||||
if (Owner.CanWrite)
|
if (Owner.CanWrite)
|
||||||
{
|
{
|
||||||
var applyBtnObj = UIFactory.CreateButton(m_valueContent, new Color(0.2f, 0.2f, 0.2f));
|
var applyBtnObj = UIFactory.CreateButton(groupObj, new Color(0.2f, 0.2f, 0.2f));
|
||||||
var applyLayout = applyBtnObj.AddComponent<LayoutElement>();
|
var applyLayout = applyBtnObj.AddComponent<LayoutElement>();
|
||||||
applyLayout.minWidth = 50;
|
applyLayout.minWidth = 50;
|
||||||
applyLayout.minHeight = 25;
|
applyLayout.minHeight = 25;
|
||||||
applyLayout.flexibleWidth = 0;
|
applyLayout.flexibleWidth = 0;
|
||||||
|
|
||||||
var applyBtn = applyBtnObj.GetComponent<Button>();
|
var applyBtn = applyBtnObj.GetComponent<Button>();
|
||||||
applyBtn.onClick.AddListener(OnApplyClicked);
|
applyBtn.onClick.AddListener(OnApplyClicked);
|
||||||
|
|
||||||
@ -144,6 +197,8 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
{
|
{
|
||||||
m_valueInput.readOnly = true;
|
m_valueInput.readOnly = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
RefreshUIForValue();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -226,14 +226,15 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
|
|
||||||
if (StructInfo != null)
|
if (StructInfo != null)
|
||||||
{
|
{
|
||||||
// changing types, destroy subcontent
|
DestroySubContent();
|
||||||
for (int i = 0; i < m_subContentParent.transform.childCount; i++)
|
//// changing types, destroy subcontent
|
||||||
{
|
//for (int i = 0; i < m_subContentParent.transform.childCount; i++)
|
||||||
var child = m_subContentParent.transform.GetChild(i);
|
//{
|
||||||
GameObject.Destroy(child.gameObject);
|
// var child = m_subContentParent.transform.GetChild(i);
|
||||||
}
|
// GameObject.Destroy(child.gameObject);
|
||||||
|
//}
|
||||||
|
|
||||||
m_UIConstructed = false;
|
//m_UIConstructed = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_lastStructType = type;
|
m_lastStructType = type;
|
||||||
|
@ -78,7 +78,13 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
m_valueContent.SetActive(false);
|
m_valueContent.SetActive(false);
|
||||||
GameObject.Destroy(this.m_valueContent.gameObject);
|
GameObject.Destroy(this.m_valueContent.gameObject);
|
||||||
}
|
}
|
||||||
if (this.m_subContentParent && SubContentWanted)
|
|
||||||
|
DestroySubContent();
|
||||||
|
}
|
||||||
|
|
||||||
|
public virtual void DestroySubContent()
|
||||||
|
{
|
||||||
|
if (this.m_subContentParent && HasSubContent)
|
||||||
{
|
{
|
||||||
for (int i = 0; i < this.m_subContentParent.transform.childCount; i++)
|
for (int i = 0; i < this.m_subContentParent.transform.childCount; i++)
|
||||||
{
|
{
|
||||||
@ -87,6 +93,8 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
GameObject.Destroy(child.gameObject);
|
GameObject.Destroy(child.gameObject);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
m_subContentConstructed = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual void OnValueUpdated()
|
public virtual void OnValueUpdated()
|
||||||
@ -95,18 +103,16 @@ namespace UnityExplorer.Inspectors.Reflection
|
|||||||
ConstructUI(m_mainContentParent, m_subContentParent);
|
ConstructUI(m_mainContentParent, m_subContentParent);
|
||||||
|
|
||||||
if (Owner is CacheMember ownerMember && !string.IsNullOrEmpty(ownerMember.ReflectionException))
|
if (Owner is CacheMember ownerMember && !string.IsNullOrEmpty(ownerMember.ReflectionException))
|
||||||
{
|
|
||||||
OnException(ownerMember);
|
OnException(ownerMember);
|
||||||
}
|
|
||||||
else
|
else
|
||||||
{
|
|
||||||
RefreshUIForValue();
|
RefreshUIForValue();
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual void OnException(CacheMember member)
|
public virtual void OnException(CacheMember member)
|
||||||
{
|
{
|
||||||
m_baseLabel.text = "<color=red>" + member.ReflectionException + "</color>";
|
if (m_UIConstructed)
|
||||||
|
m_baseLabel.text = "<color=red>" + member.ReflectionException + "</color>";
|
||||||
|
|
||||||
Value = null;
|
Value = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -34,7 +34,7 @@ namespace UnityExplorer.Inspectors
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Blacklists
|
// Blacklists
|
||||||
private static readonly HashSet<string> s_typeAndMemberBlacklist = new HashSet<string>
|
private static readonly HashSet<string> bl_typeAndMember = new HashSet<string>
|
||||||
{
|
{
|
||||||
#if CPP
|
#if CPP
|
||||||
// these cause a crash in IL2CPP
|
// these cause a crash in IL2CPP
|
||||||
@ -45,14 +45,14 @@ namespace UnityExplorer.Inspectors
|
|||||||
"Texture2D.SetPixelDataImpl",
|
"Texture2D.SetPixelDataImpl",
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
private static readonly HashSet<string> s_methodStartsWithBlacklist = new HashSet<string>
|
private static readonly HashSet<string> bl_memberNameStartsWith = new HashSet<string>
|
||||||
{
|
{
|
||||||
// these are redundant
|
// these are redundant
|
||||||
"get_",
|
"get_",
|
||||||
"set_",
|
"set_",
|
||||||
};
|
};
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
#region INSTANCE
|
#region INSTANCE
|
||||||
|
|
||||||
@ -132,24 +132,99 @@ namespace UnityExplorer.Inspectors
|
|||||||
RefreshDisplay();
|
RefreshDisplay();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void OnMemberFilterClicked(MemberTypes type, Button button)
|
internal bool IsBlacklisted(string sig) => bl_typeAndMember.Any(it => sig.Contains(it));
|
||||||
|
internal bool IsBlacklisted(MethodInfo method) => bl_memberNameStartsWith.Any(it => method.Name.StartsWith(it));
|
||||||
|
|
||||||
|
internal string GetSig(MemberInfo member) => $"{member.DeclaringType.Name}.{member.Name}";
|
||||||
|
internal string AppendArgsToSig(ParameterInfo[] args)
|
||||||
{
|
{
|
||||||
if (m_lastActiveMemButton)
|
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 = ReflectionHelpers.GetAllBaseTypes(type);
|
||||||
|
|
||||||
|
var flags = BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static;
|
||||||
|
if (this is InstanceInspector)
|
||||||
|
flags |= BindingFlags.Instance;
|
||||||
|
|
||||||
|
foreach (var declaringType in types)
|
||||||
{
|
{
|
||||||
var lastColors = m_lastActiveMemButton.colors;
|
var target = Target;
|
||||||
lastColors.normalColor = new Color(0.2f, 0.2f, 0.2f);
|
#if CPP
|
||||||
m_lastActiveMemButton.colors = lastColors;
|
target = target.Il2CppCast(declaringType);
|
||||||
|
#endif
|
||||||
|
IEnumerable<MemberInfo> infos = declaringType.GetMethods(flags);
|
||||||
|
infos = infos.Concat(declaringType.GetProperties(flags));
|
||||||
|
infos = infos.Concat(declaringType.GetFields(flags));
|
||||||
|
|
||||||
|
foreach (var member in infos)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
//ExplorerCore.Log($"Trying to cache member {sig}...");
|
||||||
|
//ExplorerCore.Log(member.DeclaringType.FullName + "." + member.Name);
|
||||||
|
|
||||||
|
var sig = GetSig(member);
|
||||||
|
|
||||||
|
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, m_scrollContent));
|
||||||
|
else if (pi != null)
|
||||||
|
list.Add(new CacheProperty(pi, target, m_scrollContent));
|
||||||
|
else
|
||||||
|
list.Add(new CacheField(fi, target, m_scrollContent));
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
ExplorerCore.LogWarning($"Exception caching member {member.DeclaringType.FullName}.{member.Name}!");
|
||||||
|
ExplorerCore.Log(e.ToString());
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
m_memberFilter = type;
|
var typeList = types.ToList();
|
||||||
m_lastActiveMemButton = button;
|
|
||||||
|
|
||||||
var colors = m_lastActiveMemButton.colors;
|
var sorted = new List<CacheMember>();
|
||||||
colors.normalColor = new Color(0.2f, 0.6f, 0.2f);
|
sorted.AddRange(list.Where(it => it is CacheMethod)
|
||||||
m_lastActiveMemButton.colors = colors;
|
.OrderBy(it => typeList.IndexOf(it.DeclaringType))
|
||||||
|
.ThenBy(it => it.NameForFiltering));
|
||||||
|
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));
|
||||||
|
|
||||||
FilterMembers(null, true);
|
m_allMembers = sorted.ToArray();
|
||||||
m_sliderScroller.m_slider.value = 1f;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Update()
|
public override void Update()
|
||||||
@ -178,6 +253,26 @@ namespace UnityExplorer.Inspectors
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void OnMemberFilterClicked(MemberTypes type, Button button)
|
||||||
|
{
|
||||||
|
if (m_lastActiveMemButton)
|
||||||
|
{
|
||||||
|
var lastColors = m_lastActiveMemButton.colors;
|
||||||
|
lastColors.normalColor = new Color(0.2f, 0.2f, 0.2f);
|
||||||
|
m_lastActiveMemButton.colors = lastColors;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_memberFilter = type;
|
||||||
|
m_lastActiveMemButton = button;
|
||||||
|
|
||||||
|
var colors = m_lastActiveMemButton.colors;
|
||||||
|
colors.normalColor = new Color(0.2f, 0.6f, 0.2f);
|
||||||
|
m_lastActiveMemButton.colors = colors;
|
||||||
|
|
||||||
|
FilterMembers(null, true);
|
||||||
|
m_sliderScroller.m_slider.value = 1f;
|
||||||
|
}
|
||||||
|
|
||||||
public void FilterMembers(string nameFilter = null, bool force = false)
|
public void FilterMembers(string nameFilter = null, bool force = false)
|
||||||
{
|
{
|
||||||
int lastCount = m_membersFiltered.Count;
|
int lastCount = m_membersFiltered.Count;
|
||||||
@ -200,7 +295,7 @@ namespace UnityExplorer.Inspectors
|
|||||||
}
|
}
|
||||||
|
|
||||||
// name filter
|
// name filter
|
||||||
if (!string.IsNullOrEmpty(nameFilter) && !mem.NameForFiltering.Contains(nameFilter))
|
if (!string.IsNullOrEmpty(nameFilter) && !mem.NameForFiltering.Contains(nameFilter))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
m_membersFiltered.Add(mem);
|
m_membersFiltered.Add(mem);
|
||||||
@ -266,137 +361,6 @@ namespace UnityExplorer.Inspectors
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void CacheMembers(Type type)
|
|
||||||
{
|
|
||||||
var list = new List<CacheMember>();
|
|
||||||
var cachedSigs = new HashSet<string>();
|
|
||||||
|
|
||||||
var types = ReflectionHelpers.GetAllBaseTypes(type);
|
|
||||||
|
|
||||||
foreach (var declaringType in types)
|
|
||||||
{
|
|
||||||
MemberInfo[] infos;
|
|
||||||
try
|
|
||||||
{
|
|
||||||
infos = declaringType.GetMembers(ReflectionHelpers.CommonFlags);
|
|
||||||
}
|
|
||||||
catch
|
|
||||||
{
|
|
||||||
ExplorerCore.Log($"Exception getting members for type: {declaringType.FullName}");
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
var target = Target;
|
|
||||||
#if CPP
|
|
||||||
try
|
|
||||||
{
|
|
||||||
target = target.Il2CppCast(declaringType);
|
|
||||||
}
|
|
||||||
catch //(Exception e)
|
|
||||||
{
|
|
||||||
//ExplorerCore.LogWarning("Excepting casting " + target.GetType().FullName + " to " + declaringType.FullName);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
foreach (var member in infos)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
// make sure member type is Field, Method or Property (4 / 8 / 16)
|
|
||||||
int m = (int)member.MemberType;
|
|
||||||
if (m < 4 || m > 16)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
//ExplorerCore.Log($"Trying to cache member {sig}...");
|
|
||||||
//ExplorerCore.Log(member.DeclaringType.FullName + "." + member.Name);
|
|
||||||
|
|
||||||
var pi = member as PropertyInfo;
|
|
||||||
var mi = member as MethodInfo;
|
|
||||||
|
|
||||||
if (this is StaticInspector)
|
|
||||||
{
|
|
||||||
if (member is FieldInfo fi && !fi.IsStatic) continue;
|
|
||||||
else if (pi != null && !pi.GetAccessors(true)[0].IsStatic) continue;
|
|
||||||
else if (mi != null && !mi.IsStatic) continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
// check blacklisted members
|
|
||||||
var sig = $"{member.DeclaringType.Name}.{member.Name}";
|
|
||||||
|
|
||||||
if (s_typeAndMemberBlacklist.Any(it => sig.Contains(it)))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if (s_methodStartsWithBlacklist.Any(it => member.Name.StartsWith(it)))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if (mi != null)
|
|
||||||
AppendParams(mi.GetParameters());
|
|
||||||
else if (pi != null)
|
|
||||||
AppendParams(pi.GetIndexParameters());
|
|
||||||
|
|
||||||
void AppendParams(ParameterInfo[] _args)
|
|
||||||
{
|
|
||||||
sig += " (";
|
|
||||||
foreach (var param in _args)
|
|
||||||
sig += $"{param.ParameterType.Name} {param.Name}, ";
|
|
||||||
sig += ")";
|
|
||||||
}
|
|
||||||
|
|
||||||
if (cachedSigs.Contains(sig))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
CacheMember cached;
|
|
||||||
if (mi != null && CacheMember.CanProcessArgs(mi.GetParameters()))
|
|
||||||
cached = new CacheMethod(mi, target);
|
|
||||||
else if (pi != null && CacheMember.CanProcessArgs(pi.GetIndexParameters()))
|
|
||||||
cached = new CacheProperty(pi, target);
|
|
||||||
else if (member is FieldInfo fi)
|
|
||||||
cached = new CacheField(fi, target);
|
|
||||||
else
|
|
||||||
continue;
|
|
||||||
|
|
||||||
cached.m_parentContent = m_scrollContent;
|
|
||||||
|
|
||||||
if (cached != null)
|
|
||||||
{
|
|
||||||
cachedSigs.Add(sig);
|
|
||||||
list.Add(cached);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
ExplorerCore.LogWarning($"Exception caching member {sig}!");
|
|
||||||
ExplorerCore.Log(e.ToString());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
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 CacheMethod)
|
|
||||||
.OrderBy(it => typeList.IndexOf(it.DeclaringType))
|
|
||||||
.ThenBy(it => it.NameForFiltering));
|
|
||||||
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));
|
|
||||||
|
|
||||||
m_allMembers = sorted.ToArray();
|
|
||||||
|
|
||||||
// ExplorerCore.Log("Cached " + m_allMembers.Length + " members");
|
|
||||||
}
|
|
||||||
|
|
||||||
#region UI CONSTRUCTION
|
#region UI CONSTRUCTION
|
||||||
|
|
||||||
internal void ConstructUI()
|
internal void ConstructUI()
|
||||||
@ -578,7 +542,7 @@ namespace UnityExplorer.Inspectors
|
|||||||
|
|
||||||
internal void ConstructOptionsArea()
|
internal void ConstructOptionsArea()
|
||||||
{
|
{
|
||||||
var optionsRowObj = UIFactory.CreateHorizontalGroup(Content, new Color(1,1,1,0));
|
var optionsRowObj = UIFactory.CreateHorizontalGroup(Content, new Color(1, 1, 1, 0));
|
||||||
var optionsLayout = optionsRowObj.AddComponent<LayoutElement>();
|
var optionsLayout = optionsRowObj.AddComponent<LayoutElement>();
|
||||||
optionsLayout.minHeight = 25;
|
optionsLayout.minHeight = 25;
|
||||||
var optionsGroup = optionsRowObj.GetComponent<HorizontalLayoutGroup>();
|
var optionsGroup = optionsRowObj.GetComponent<HorizontalLayoutGroup>();
|
||||||
@ -596,7 +560,7 @@ namespace UnityExplorer.Inspectors
|
|||||||
var updateText = updateButtonObj.GetComponentInChildren<Text>();
|
var updateText = updateButtonObj.GetComponentInChildren<Text>();
|
||||||
updateText.text = "Update Values";
|
updateText.text = "Update Values";
|
||||||
var updateBtn = updateButtonObj.GetComponent<Button>();
|
var updateBtn = updateButtonObj.GetComponent<Button>();
|
||||||
updateBtn.onClick.AddListener(() =>
|
updateBtn.onClick.AddListener(() =>
|
||||||
{
|
{
|
||||||
bool orig = m_autoUpdate;
|
bool orig = m_autoUpdate;
|
||||||
m_autoUpdate = true;
|
m_autoUpdate = true;
|
||||||
@ -617,7 +581,7 @@ namespace UnityExplorer.Inspectors
|
|||||||
|
|
||||||
internal void ConstructMemberList()
|
internal void ConstructMemberList()
|
||||||
{
|
{
|
||||||
var scrollobj = UIFactory.CreateScrollView(Content, out m_scrollContent, out m_sliderScroller, new Color(0.08f, 0.08f, 0.08f));
|
var scrollobj = UIFactory.CreateScrollView(Content, out m_scrollContent, out m_sliderScroller, new Color(0.05f, 0.05f, 0.05f));
|
||||||
|
|
||||||
m_scrollContentRect = m_scrollContent.GetComponent<RectTransform>();
|
m_scrollContentRect = m_scrollContent.GetComponent<RectTransform>();
|
||||||
|
|
||||||
|
@ -24,6 +24,12 @@ namespace UnityExplorer.Tests
|
|||||||
|
|
||||||
public class TestClass
|
public class TestClass
|
||||||
{
|
{
|
||||||
|
public string AAALongString = @"1
|
||||||
|
2
|
||||||
|
3
|
||||||
|
4
|
||||||
|
5";
|
||||||
|
|
||||||
public Vector2 AATestVector2 = new Vector2(1, 2);
|
public Vector2 AATestVector2 = new Vector2(1, 2);
|
||||||
public Vector3 AATestVector3 = new Vector3(1, 2, 3);
|
public Vector3 AATestVector3 = new Vector3(1, 2, 3);
|
||||||
public Vector4 AATestVector4 = new Vector4(1, 2, 3, 4);
|
public Vector4 AATestVector4 = new Vector4(1, 2, 3, 4);
|
||||||
|
@ -77,11 +77,6 @@ namespace UnityExplorer.UI
|
|||||||
catch { }
|
catch { }
|
||||||
|
|
||||||
// Setup Harmony Patches
|
// Setup Harmony Patches
|
||||||
TryPatch(typeof(EventSystem),
|
|
||||||
"current",
|
|
||||||
new HarmonyMethod(typeof(ForceUnlockCursor).GetMethod(nameof(Prefix_EventSystem_set_current))),
|
|
||||||
true);
|
|
||||||
|
|
||||||
TryPatch(typeof(Cursor),
|
TryPatch(typeof(Cursor),
|
||||||
"lockState",
|
"lockState",
|
||||||
new HarmonyMethod(typeof(ForceUnlockCursor).GetMethod(nameof(Prefix_set_lockState))),
|
new HarmonyMethod(typeof(ForceUnlockCursor).GetMethod(nameof(Prefix_set_lockState))),
|
||||||
@ -91,10 +86,21 @@ namespace UnityExplorer.UI
|
|||||||
"visible",
|
"visible",
|
||||||
new HarmonyMethod(typeof(ForceUnlockCursor).GetMethod(nameof(Prefix_set_visible))),
|
new HarmonyMethod(typeof(ForceUnlockCursor).GetMethod(nameof(Prefix_set_visible))),
|
||||||
true);
|
true);
|
||||||
|
|
||||||
|
#if BIE
|
||||||
|
#if CPP
|
||||||
|
// temporarily disabling this patch in BepInEx il2cpp as it's causing a crash in some games.
|
||||||
|
return;
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
TryPatch(typeof(EventSystem),
|
||||||
|
"current",
|
||||||
|
new HarmonyMethod(typeof(ForceUnlockCursor).GetMethod(nameof(Prefix_EventSystem_set_current))),
|
||||||
|
true);
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
ExplorerCore.Log($"Exception on CursorControl.Init! {e.GetType()}, {e.Message}");
|
ExplorerCore.Log($"Exception on ForceUnlockCursor.Init! {e.GetType()}, {e.Message}");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -120,10 +126,10 @@ namespace UnityExplorer.UI
|
|||||||
harmony.Patch(prop.GetGetMethod(), postfix: patch);
|
harmony.Patch(prop.GetGetMethod(), postfix: patch);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch // (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
//string suf = setter ? "set_" : "get_";
|
string suf = setter ? "set_" : "get_";
|
||||||
//ExplorerCore.Log($"Unable to patch {type.Name}.{suf}{property}: {e.Message}");
|
ExplorerCore.Log($"Unable to patch {type.Name}.{suf}{property}: {e.Message}");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -158,13 +164,20 @@ namespace UnityExplorer.UI
|
|||||||
|
|
||||||
public static void SetEventSystem()
|
public static void SetEventSystem()
|
||||||
{
|
{
|
||||||
|
if (InputManager.CurrentType == InputType.InputSystem)
|
||||||
|
return;
|
||||||
|
|
||||||
m_settingEventSystem = true;
|
m_settingEventSystem = true;
|
||||||
UIManager.SetEventSystem();
|
EventSystem.current = UIManager.EventSys;
|
||||||
|
InputManager.ActivateUIModule();
|
||||||
m_settingEventSystem = false;
|
m_settingEventSystem = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void ReleaseEventSystem()
|
public static void ReleaseEventSystem()
|
||||||
{
|
{
|
||||||
|
if (InputManager.CurrentType == InputType.InputSystem)
|
||||||
|
return;
|
||||||
|
|
||||||
if (m_lastEventSystem)
|
if (m_lastEventSystem)
|
||||||
{
|
{
|
||||||
m_settingEventSystem = true;
|
m_settingEventSystem = true;
|
||||||
|
@ -260,11 +260,8 @@ namespace UnityExplorer.UI.Modules
|
|||||||
|
|
||||||
if (searchType == null)
|
if (searchType == null)
|
||||||
return;
|
return;
|
||||||
#if MONO
|
|
||||||
var allObjects = ResourcesUnstrip.FindObjectsOfTypeAll(searchType);
|
var allObjects = ResourcesUnstrip.FindObjectsOfTypeAll(searchType);
|
||||||
#else
|
|
||||||
var allObjects = ResourcesUnstrip.FindObjectsOfTypeAll(Il2CppType.From(searchType));
|
|
||||||
#endif
|
|
||||||
var results = new List<object>();
|
var results = new List<object>();
|
||||||
|
|
||||||
// perform filter comparers
|
// perform filter comparers
|
||||||
|
@ -178,13 +178,9 @@ namespace UnityExplorer.UI
|
|||||||
|
|
||||||
Image image = groupObj.AddComponent<Image>();
|
Image image = groupObj.AddComponent<Image>();
|
||||||
if (color != default)
|
if (color != default)
|
||||||
{
|
|
||||||
image.color = color;
|
image.color = color;
|
||||||
}
|
|
||||||
else
|
else
|
||||||
{
|
|
||||||
image.color = new Color(44f / 255f, 44f / 255f, 44f / 255f);
|
image.color = new Color(44f / 255f, 44f / 255f, 44f / 255f);
|
||||||
}
|
|
||||||
|
|
||||||
return groupObj;
|
return groupObj;
|
||||||
}
|
}
|
||||||
@ -657,16 +653,16 @@ namespace UnityExplorer.UI
|
|||||||
contentFitter.horizontalFit = ContentSizeFitter.FitMode.Unconstrained;
|
contentFitter.horizontalFit = ContentSizeFitter.FitMode.Unconstrained;
|
||||||
contentFitter.verticalFit = ContentSizeFitter.FitMode.PreferredSize;
|
contentFitter.verticalFit = ContentSizeFitter.FitMode.PreferredSize;
|
||||||
|
|
||||||
var contentLayout = content.AddComponent<VerticalLayoutGroup>();
|
var contentGroup = content.AddComponent<VerticalLayoutGroup>();
|
||||||
contentLayout.childForceExpandHeight = true;
|
contentGroup.childForceExpandHeight = true;
|
||||||
contentLayout.childControlHeight = true;
|
contentGroup.childControlHeight = true;
|
||||||
contentLayout.childForceExpandWidth = true;
|
contentGroup.childForceExpandWidth = true;
|
||||||
contentLayout.childControlWidth = true;
|
contentGroup.childControlWidth = true;
|
||||||
contentLayout.padding.left = 5;
|
contentGroup.padding.left = 5;
|
||||||
contentLayout.padding.right = 5;
|
contentGroup.padding.right = 5;
|
||||||
contentLayout.padding.top = 5;
|
contentGroup.padding.top = 5;
|
||||||
contentLayout.padding.bottom = 5;
|
contentGroup.padding.bottom = 5;
|
||||||
contentLayout.spacing = 5;
|
contentGroup.spacing = 5;
|
||||||
|
|
||||||
GameObject scrollBarObj = CreateUIObject("DynamicScrollbar", mainObj);
|
GameObject scrollBarObj = CreateUIObject("DynamicScrollbar", mainObj);
|
||||||
|
|
||||||
|
@ -8,6 +8,7 @@ using System.IO;
|
|||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
using UnityExplorer.UI.Shared;
|
using UnityExplorer.UI.Shared;
|
||||||
|
using UnityExplorer.Input;
|
||||||
#if CPP
|
#if CPP
|
||||||
using UnityExplorer.Unstrip;
|
using UnityExplorer.Unstrip;
|
||||||
#endif
|
#endif
|
||||||
@ -18,37 +19,13 @@ namespace UnityExplorer.UI
|
|||||||
{
|
{
|
||||||
public static GameObject CanvasRoot { get; private set; }
|
public static GameObject CanvasRoot { get; private set; }
|
||||||
public static EventSystem EventSys { get; private set; }
|
public static EventSystem EventSys { get; private set; }
|
||||||
public static StandaloneInputModule InputModule { get; private set; }
|
|
||||||
|
|
||||||
//internal static Material UIMaterial { get; private set; }
|
|
||||||
internal static Sprite ResizeCursor { get; private set; }
|
internal static Sprite ResizeCursor { get; private set; }
|
||||||
internal static Font ConsoleFont { get; private set; }
|
internal static Font ConsoleFont { get; private set; }
|
||||||
|
|
||||||
public static void Init()
|
public static void Init()
|
||||||
{
|
{
|
||||||
var bundlePath = ExplorerCore.EXPLORER_FOLDER + @"\explorerui.bundle";
|
LoadBundle();
|
||||||
if (File.Exists(bundlePath))
|
|
||||||
{
|
|
||||||
var bundle = AssetBundle.LoadFromFile(bundlePath);
|
|
||||||
|
|
||||||
// Fix for games which don't ship with 'UI/Default' shader.
|
|
||||||
if (Graphic.defaultGraphicMaterial.shader?.name != "UI/Default")
|
|
||||||
{
|
|
||||||
ExplorerCore.Log("This game does not ship with the 'UI/Default' shader, using manual Default Shader...");
|
|
||||||
Graphic.defaultGraphicMaterial.shader = bundle.LoadAsset<Shader>("DefaultUI");
|
|
||||||
}
|
|
||||||
|
|
||||||
ResizeCursor = bundle.LoadAsset<Sprite>("cursor");
|
|
||||||
|
|
||||||
ConsoleFont = bundle.LoadAsset<Font>("CONSOLA");
|
|
||||||
|
|
||||||
ExplorerCore.Log("Loaded UI bundle");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ExplorerCore.LogWarning("Could not find the ExplorerUI Bundle! It should exist at '" + bundlePath + "'");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Create core UI Canvas and Event System handler
|
// Create core UI Canvas and Event System handler
|
||||||
CreateRootCanvas();
|
CreateRootCanvas();
|
||||||
@ -62,12 +39,6 @@ namespace UnityExplorer.UI
|
|||||||
Canvas.ForceUpdateCanvases();
|
Canvas.ForceUpdateCanvases();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void SetEventSystem()
|
|
||||||
{
|
|
||||||
EventSystem.current = EventSys;
|
|
||||||
InputModule.ActivateModule();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void OnSceneChange()
|
public static void OnSceneChange()
|
||||||
{
|
{
|
||||||
SceneExplorer.Instance?.OnSceneChange();
|
SceneExplorer.Instance?.OnSceneChange();
|
||||||
@ -78,23 +49,20 @@ namespace UnityExplorer.UI
|
|||||||
{
|
{
|
||||||
MainMenu.Instance?.Update();
|
MainMenu.Instance?.Update();
|
||||||
|
|
||||||
if (EventSys && InputModule)
|
if (EventSys)
|
||||||
{
|
{
|
||||||
if (EventSystem.current != EventSys)
|
if (EventSystem.current != EventSys)
|
||||||
{
|
{
|
||||||
ForceUnlockCursor.SetEventSystem();
|
ForceUnlockCursor.SetEventSystem();
|
||||||
//ForceUnlockCursor.Unlock = true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Fix for games which override the InputModule pointer events (eg, VRChat)
|
|
||||||
#if CPP
|
#if CPP
|
||||||
if (InputModule.m_InputPointerEvent != null)
|
// Fix for games which override the InputModule pointer events (eg, VRChat)
|
||||||
|
var evt = InputManager.InputPointerEvent;
|
||||||
|
if (evt != null)
|
||||||
{
|
{
|
||||||
PointerEventData evt = InputModule.m_InputPointerEvent;
|
|
||||||
if (!evt.eligibleForClick && evt.selectedObject)
|
if (!evt.eligibleForClick && evt.selectedObject)
|
||||||
{
|
|
||||||
evt.eligibleForClick = true;
|
evt.eligibleForClick = true;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@ -125,6 +93,33 @@ namespace UnityExplorer.UI
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static void LoadBundle()
|
||||||
|
{
|
||||||
|
var bundlePath = ExplorerCore.EXPLORER_FOLDER + @"\explorerui.bundle";
|
||||||
|
if (File.Exists(bundlePath))
|
||||||
|
{
|
||||||
|
var bundle = AssetBundle.LoadFromFile(bundlePath);
|
||||||
|
|
||||||
|
// Fix for games which don't ship with 'UI/Default' shader.
|
||||||
|
if (Graphic.defaultGraphicMaterial.shader?.name != "UI/Default")
|
||||||
|
{
|
||||||
|
ExplorerCore.Log("This game does not ship with the 'UI/Default' shader, using manual Default Shader...");
|
||||||
|
Graphic.defaultGraphicMaterial.shader = bundle.LoadAsset<Shader>("DefaultUI");
|
||||||
|
}
|
||||||
|
|
||||||
|
ResizeCursor = bundle.LoadAsset<Sprite>("cursor");
|
||||||
|
|
||||||
|
ConsoleFont = bundle.LoadAsset<Font>("CONSOLA");
|
||||||
|
|
||||||
|
ExplorerCore.Log("Loaded UI bundle");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ExplorerCore.LogWarning("Could not find the ExplorerUI Bundle! It should exist at '" + bundlePath + "'");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private static GameObject CreateRootCanvas()
|
private static GameObject CreateRootCanvas()
|
||||||
{
|
{
|
||||||
GameObject rootObj = new GameObject("ExplorerCanvas");
|
GameObject rootObj = new GameObject("ExplorerCanvas");
|
||||||
@ -135,8 +130,7 @@ namespace UnityExplorer.UI
|
|||||||
CanvasRoot.transform.position = new Vector3(0f, 0f, 1f);
|
CanvasRoot.transform.position = new Vector3(0f, 0f, 1f);
|
||||||
|
|
||||||
EventSys = rootObj.AddComponent<EventSystem>();
|
EventSys = rootObj.AddComponent<EventSystem>();
|
||||||
InputModule = rootObj.AddComponent<StandaloneInputModule>();
|
InputManager.AddUIModule();
|
||||||
InputModule.ActivateModule();
|
|
||||||
|
|
||||||
Canvas canvas = rootObj.AddComponent<Canvas>();
|
Canvas canvas = rootObj.AddComponent<Canvas>();
|
||||||
canvas.renderMode = RenderMode.ScreenSpaceCamera;
|
canvas.renderMode = RenderMode.ScreenSpaceCamera;
|
||||||
|
@ -42,10 +42,10 @@ namespace UnityExplorer.UI
|
|||||||
|
|
||||||
public static string ParseFullSyntax(Type type, bool includeNamespace, MemberInfo memberInfo = null)
|
public static string ParseFullSyntax(Type type, bool includeNamespace, MemberInfo memberInfo = null)
|
||||||
{
|
{
|
||||||
string ret = "";
|
|
||||||
|
|
||||||
if (type == null)
|
if (type == null)
|
||||||
return "????????????";
|
throw new ArgumentNullException("type");
|
||||||
|
|
||||||
|
string ret = "";
|
||||||
|
|
||||||
if (type.IsGenericParameter || (type.HasElementType && type.GetElementType().IsGenericParameter))
|
if (type.IsGenericParameter || (type.HasElementType && type.GetElementType().IsGenericParameter))
|
||||||
{
|
{
|
||||||
|
@ -25,13 +25,13 @@
|
|||||||
<Prefer32Bit>false</Prefer32Bit>
|
<Prefer32Bit>false</Prefer32Bit>
|
||||||
<RootNamespace>UnityExplorer</RootNamespace>
|
<RootNamespace>UnityExplorer</RootNamespace>
|
||||||
<!-- Set this to the BepInEx Il2Cpp Game folder, without the ending '\' character. -->
|
<!-- Set this to the BepInEx Il2Cpp Game folder, without the ending '\' character. -->
|
||||||
<BIECppGameFolder>D:\Steam\steamapps\common\Outward</BIECppGameFolder>
|
<BIECppGameFolder>D:\source\Unity Projects\Test\_BUILD</BIECppGameFolder>
|
||||||
<!-- Set this to the BepInEx Mono Game folder, without the ending '\' character. -->
|
<!-- Set this to the BepInEx Mono Game folder, without the ending '\' character. -->
|
||||||
<BIEMonoGameFolder>D:\source\Unity Projects\Test\_BUILD_MONO</BIEMonoGameFolder>
|
<BIEMonoGameFolder>D:\source\Unity Projects\Test\_BUILD_MONO</BIEMonoGameFolder>
|
||||||
<!-- Set this to the BepInEx Mono Managed folder, without the ending '\' character. -->
|
<!-- Set this to the BepInEx Mono Managed folder, without the ending '\' character. -->
|
||||||
<BIEMonoManagedFolder>D:\source\Unity Projects\Test\_BUILD_MONO\Test_Data\Managed</BIEMonoManagedFolder>
|
<BIEMonoManagedFolder>D:\source\Unity Projects\Test\_BUILD_MONO\Test_Data\Managed</BIEMonoManagedFolder>
|
||||||
<!-- Set this to the MelonLoader Il2Cpp Game folder, without the ending '\' character. -->
|
<!-- Set this to the MelonLoader Il2Cpp Game folder, without the ending '\' character. -->
|
||||||
<MLCppGameFolder>D:\Steam\steamapps\common\VRChat</MLCppGameFolder>
|
<MLCppGameFolder>D:\source\Unity Projects\Test\_BUILD</MLCppGameFolder>
|
||||||
<!-- Set this to the MelonLoader Mono Game folder, without the ending '\' character. -->
|
<!-- Set this to the MelonLoader Mono Game folder, without the ending '\' character. -->
|
||||||
<MLMonoGameFolder>D:\source\Unity Projects\Test\_BUILD_MONO</MLMonoGameFolder>
|
<MLMonoGameFolder>D:\source\Unity Projects\Test\_BUILD_MONO</MLMonoGameFolder>
|
||||||
<!-- Set this to the MelonLoader Mono Managed folder, without the ending '\' character. -->
|
<!-- Set this to the MelonLoader Mono Managed folder, without the ending '\' character. -->
|
||||||
|
@ -3,24 +3,27 @@ using Mono.CSharp;
|
|||||||
using UnityExplorer.Helpers;
|
using UnityExplorer.Helpers;
|
||||||
#if CPP
|
#if CPP
|
||||||
using UnhollowerBaseLib;
|
using UnhollowerBaseLib;
|
||||||
|
using UnhollowerRuntimeLib;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace UnityExplorer.Unstrip
|
namespace UnityExplorer.Unstrip
|
||||||
{
|
{
|
||||||
public class ResourcesUnstrip
|
public class ResourcesUnstrip
|
||||||
{
|
{
|
||||||
|
public static UnityEngine.Object[] FindObjectsOfTypeAll(Type type)
|
||||||
|
{
|
||||||
|
#if MONO
|
||||||
|
return UnityEngine.Resources.FindObjectsOfTypeAll(type);
|
||||||
|
#else
|
||||||
|
var iCall = ICallHelper.GetICall<d_FindObjectsOfTypeAll>("UnityEngine.Resources::FindObjectsOfTypeAll");
|
||||||
|
var cppType = Il2CppType.From(type);
|
||||||
|
|
||||||
|
return new Il2CppReferenceArray<UnityEngine.Object>(iCall.Invoke(cppType.Pointer));
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
#if CPP
|
#if CPP
|
||||||
internal delegate IntPtr d_FindObjectsOfTypeAll(IntPtr type);
|
internal delegate IntPtr d_FindObjectsOfTypeAll(IntPtr type);
|
||||||
|
|
||||||
public static UnityEngine.Object[] FindObjectsOfTypeAll(Il2CppSystem.Type type)
|
|
||||||
{
|
|
||||||
var iCall = ICallHelper.GetICall<d_FindObjectsOfTypeAll>("UnityEngine.Resources::FindObjectsOfTypeAll");
|
|
||||||
|
|
||||||
return new Il2CppReferenceArray<UnityEngine.Object>(iCall.Invoke(type.Pointer));
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
public static UnityEngine.Object[] FindObjectsOfTypeAll(Type type) => UnityEngine.Resources.FindObjectsOfTypeAll(type);
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user