mirror of
https://github.com/sinai-dev/UnityExplorer.git
synced 2025-06-16 06:08:16 +08:00
1.3.2 cleanup
- cleanup - fixed a mistake with FieldInfos on reflection window, causing all values to be null. - improved displaying of generic objects (now shows object Type after the name)
This commit is contained in:
parent
411593590d
commit
0c3067973e
@ -22,7 +22,24 @@ namespace Explorer
|
|||||||
|
|
||||||
public override void UpdateValue(object obj)
|
public override void UpdateValue(object obj)
|
||||||
{
|
{
|
||||||
m_value = fieldInfo.GetValue(fieldInfo.IsStatic ? null : obj);
|
try
|
||||||
|
{
|
||||||
|
if (obj is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var declaringType = this.fieldInfo.DeclaringType;
|
||||||
|
|
||||||
|
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
||||||
|
m_value = this.fieldInfo.GetValue(fieldInfo.IsStatic ? null : cast);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
m_value = this.fieldInfo.GetValue(fieldInfo.IsStatic ? null : obj);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
MelonLogger.Log($"Error updating FieldInfoHolder | {e.GetType()}: {e.Message}\r\n{e.StackTrace}");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Draw(ReflectionWindow window)
|
public override void Draw(ReflectionWindow window)
|
||||||
@ -31,10 +48,12 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
|
|
||||||
public override void SetValue(object obj)
|
public override void SetValue(object obj)
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (fieldInfo.FieldType.IsEnum)
|
if (fieldInfo.FieldType.IsEnum)
|
||||||
{
|
{
|
||||||
if (System.Enum.Parse(fieldInfo.FieldType, m_value.ToString()) is object enumValue && enumValue != null)
|
if (Enum.Parse(fieldInfo.FieldType, m_value.ToString()) is object enumValue && enumValue != null)
|
||||||
{
|
{
|
||||||
m_value = enumValue;
|
m_value = enumValue;
|
||||||
}
|
}
|
||||||
@ -74,9 +93,28 @@ namespace Explorer
|
|||||||
MelonLogger.LogWarning("Cannot parse " + m_value.ToString() + " to an integer! type: " + fieldInfo.FieldType);
|
MelonLogger.LogWarning("Cannot parse " + m_value.ToString() + " to an integer! type: " + fieldInfo.FieldType);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
MelonLogger.Log("Unsupported primitive field type: " + fieldInfo.FieldType.FullName);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (obj is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var declaringType = this.fieldInfo.DeclaringType;
|
||||||
|
|
||||||
|
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
||||||
|
fieldInfo.SetValue(fieldInfo.IsStatic ? null : cast, m_value);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
fieldInfo.SetValue(fieldInfo.IsStatic ? null : obj, m_value);
|
fieldInfo.SetValue(fieldInfo.IsStatic ? null : obj, m_value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
MelonLogger.Log($"Error setting FieldInfoHolder | {e.GetType()}: {e.Message}\r\n{e.StackTrace}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -33,6 +33,7 @@ namespace Explorer
|
|||||||
if (obj is Il2CppSystem.Object ilObject)
|
if (obj is Il2CppSystem.Object ilObject)
|
||||||
{
|
{
|
||||||
var declaringType = this.propInfo.DeclaringType;
|
var declaringType = this.propInfo.DeclaringType;
|
||||||
|
|
||||||
if (declaringType == typeof(Il2CppObjectBase))
|
if (declaringType == typeof(Il2CppObjectBase))
|
||||||
{
|
{
|
||||||
m_value = ilObject.Pointer;
|
m_value = ilObject.Pointer;
|
||||||
@ -40,7 +41,7 @@ namespace Explorer
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
||||||
m_value = this.propInfo.GetValue(cast, null);
|
m_value = this.propInfo.GetValue(this.propInfo.GetAccessors()[0].IsStatic ? null : cast, null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -70,7 +71,7 @@ namespace Explorer
|
|||||||
{
|
{
|
||||||
if (propInfo.PropertyType.IsEnum)
|
if (propInfo.PropertyType.IsEnum)
|
||||||
{
|
{
|
||||||
if (System.Enum.Parse(propInfo.PropertyType, m_value.ToString()) is object enumValue && enumValue != null)
|
if (Enum.Parse(propInfo.PropertyType, m_value.ToString()) is object enumValue && enumValue != null)
|
||||||
{
|
{
|
||||||
m_value = enumValue;
|
m_value = enumValue;
|
||||||
}
|
}
|
||||||
|
@ -31,54 +31,6 @@ namespace Explorer
|
|||||||
Field
|
Field
|
||||||
}
|
}
|
||||||
|
|
||||||
public Type GetActualType(object m_object)
|
|
||||||
{
|
|
||||||
if (m_object is Il2CppSystem.Object ilObject)
|
|
||||||
{
|
|
||||||
var iltype = ilObject.GetIl2CppType();
|
|
||||||
return Type.GetType(iltype.AssemblyQualifiedName);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return m_object.GetType();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public Type[] GetAllBaseTypes(object m_object)
|
|
||||||
{
|
|
||||||
var list = new List<Type>();
|
|
||||||
|
|
||||||
if (m_object is Il2CppSystem.Object ilObject)
|
|
||||||
{
|
|
||||||
var ilType = ilObject.GetIl2CppType();
|
|
||||||
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilTypeToManaged)
|
|
||||||
{
|
|
||||||
list.Add(ilTypeToManaged);
|
|
||||||
|
|
||||||
while (ilType.BaseType != null)
|
|
||||||
{
|
|
||||||
ilType = ilType.BaseType;
|
|
||||||
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilBaseTypeToManaged)
|
|
||||||
{
|
|
||||||
list.Add(ilBaseTypeToManaged);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var type = m_object.GetType();
|
|
||||||
list.Add(type);
|
|
||||||
while (type.BaseType != null)
|
|
||||||
{
|
|
||||||
type = type.BaseType;
|
|
||||||
list.Add(type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return list.ToArray();
|
|
||||||
}
|
|
||||||
|
|
||||||
public override void Init()
|
public override void Init()
|
||||||
{
|
{
|
||||||
m_object = Target;
|
m_object = Target;
|
||||||
@ -101,7 +53,7 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
catch { }
|
catch { }
|
||||||
|
|
||||||
UpdateValues();
|
UpdateValues(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Update()
|
public override void Update()
|
||||||
@ -112,9 +64,9 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void UpdateValues()
|
private void UpdateValues(bool forceAll = false)
|
||||||
{
|
{
|
||||||
if (m_filter == MemberFilter.Both || m_filter == MemberFilter.Field)
|
if (forceAll || m_filter == MemberFilter.Both || m_filter == MemberFilter.Field)
|
||||||
{
|
{
|
||||||
foreach (var holder in this.m_FieldInfos)
|
foreach (var holder in this.m_FieldInfos)
|
||||||
{
|
{
|
||||||
@ -125,7 +77,7 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_filter == MemberFilter.Both || m_filter == MemberFilter.Property)
|
if (forceAll || m_filter == MemberFilter.Both || m_filter == MemberFilter.Property)
|
||||||
{
|
{
|
||||||
foreach (var holder in this.m_PropertyInfos)
|
foreach (var holder in this.m_PropertyInfos)
|
||||||
{
|
{
|
||||||
@ -278,6 +230,56 @@ namespace Explorer
|
|||||||
GUI.color = Color.white;
|
GUI.color = Color.white;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ============ HELPERS ===============
|
||||||
|
|
||||||
|
public Type GetActualType(object m_object)
|
||||||
|
{
|
||||||
|
if (m_object is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var iltype = ilObject.GetIl2CppType();
|
||||||
|
return Type.GetType(iltype.AssemblyQualifiedName);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return m_object.GetType();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public Type[] GetAllBaseTypes(object m_object)
|
||||||
|
{
|
||||||
|
var list = new List<Type>();
|
||||||
|
|
||||||
|
if (m_object is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var ilType = ilObject.GetIl2CppType();
|
||||||
|
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilTypeToManaged)
|
||||||
|
{
|
||||||
|
list.Add(ilTypeToManaged);
|
||||||
|
|
||||||
|
while (ilType.BaseType != null)
|
||||||
|
{
|
||||||
|
ilType = ilType.BaseType;
|
||||||
|
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilBaseTypeToManaged)
|
||||||
|
{
|
||||||
|
list.Add(ilBaseTypeToManaged);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
var type = m_object.GetType();
|
||||||
|
list.Add(type);
|
||||||
|
while (type.BaseType != null)
|
||||||
|
{
|
||||||
|
type = type.BaseType;
|
||||||
|
list.Add(type);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return list.ToArray();
|
||||||
|
}
|
||||||
|
|
||||||
public static bool IsList(Type t)
|
public static bool IsList(Type t)
|
||||||
{
|
{
|
||||||
return t.IsGenericType
|
return t.IsGenericType
|
||||||
|
@ -20,7 +20,7 @@ namespace Explorer
|
|||||||
|
|
||||||
private string m_searchInput = "";
|
private string m_searchInput = "";
|
||||||
private string m_typeInput = "";
|
private string m_typeInput = "";
|
||||||
private int m_limit = 100;
|
private int m_limit = 20;
|
||||||
private int m_pageOffset = 0;
|
private int m_pageOffset = 0;
|
||||||
private List<object> m_searchResults = new List<object>();
|
private List<object> m_searchResults = new List<object>();
|
||||||
private Vector2 resultsScroll = Vector2.zero;
|
private Vector2 resultsScroll = Vector2.zero;
|
||||||
@ -85,11 +85,11 @@ namespace Explorer
|
|||||||
|
|
||||||
int count = m_searchResults.Count;
|
int count = m_searchResults.Count;
|
||||||
|
|
||||||
if (count > CppExplorer.ArrayLimit)
|
if (count > this.m_limit)
|
||||||
{
|
{
|
||||||
// prev/next page buttons
|
// prev/next page buttons
|
||||||
GUILayout.BeginHorizontal(null);
|
GUILayout.BeginHorizontal(null);
|
||||||
int maxOffset = (int)Mathf.Ceil(count / CppExplorer.ArrayLimit);
|
int maxOffset = (int)Mathf.Ceil(count / this.m_limit);
|
||||||
if (GUILayout.Button("< Prev", null))
|
if (GUILayout.Button("< Prev", null))
|
||||||
{
|
{
|
||||||
if (m_pageOffset > 0) m_pageOffset--;
|
if (m_pageOffset > 0) m_pageOffset--;
|
||||||
@ -110,7 +110,7 @@ namespace Explorer
|
|||||||
|
|
||||||
if (m_searchResults.Count > 0)
|
if (m_searchResults.Count > 0)
|
||||||
{
|
{
|
||||||
int offset = m_pageOffset * CppExplorer.ArrayLimit;
|
int offset = m_pageOffset * this.m_limit;
|
||||||
int preiterated = 0;
|
int preiterated = 0;
|
||||||
|
|
||||||
if (offset >= count) m_pageOffset = 0;
|
if (offset >= count) m_pageOffset = 0;
|
||||||
@ -123,7 +123,7 @@ namespace Explorer
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (i - offset > CppExplorer.ArrayLimit - 1)
|
if (i - offset > this.m_limit - 1)
|
||||||
{
|
{
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -257,14 +257,14 @@ namespace Explorer
|
|||||||
|
|
||||||
private List<object> FindAllObjectsOfType(string _search, string _type)
|
private List<object> FindAllObjectsOfType(string _search, string _type)
|
||||||
{
|
{
|
||||||
Il2CppSystem.Type type = null;
|
Il2CppSystem.Type searchType = null;
|
||||||
|
|
||||||
if (TypeMode == TypeFilter.Custom)
|
if (TypeMode == TypeFilter.Custom)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
var findType = CppExplorer.GetType(_type);
|
var findType = CppExplorer.GetType(_type);
|
||||||
type = Il2CppSystem.Type.GetType(findType.AssemblyQualifiedName);
|
searchType = Il2CppSystem.Type.GetType(findType.AssemblyQualifiedName);
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
@ -273,26 +273,26 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
else if (TypeMode == TypeFilter.Object)
|
else if (TypeMode == TypeFilter.Object)
|
||||||
{
|
{
|
||||||
type = CppExplorer.ObjectType;
|
searchType = CppExplorer.ObjectType;
|
||||||
}
|
}
|
||||||
else if (TypeMode == TypeFilter.GameObject)
|
else if (TypeMode == TypeFilter.GameObject)
|
||||||
{
|
{
|
||||||
type = CppExplorer.GameObjectType;
|
searchType = CppExplorer.GameObjectType;
|
||||||
}
|
}
|
||||||
else if (TypeMode == TypeFilter.Component)
|
else if (TypeMode == TypeFilter.Component)
|
||||||
{
|
{
|
||||||
type = CppExplorer.ComponentType;
|
searchType = CppExplorer.ComponentType;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!CppExplorer.ObjectType.IsAssignableFrom(type))
|
if (!CppExplorer.ObjectType.IsAssignableFrom(searchType))
|
||||||
{
|
{
|
||||||
MelonLogger.LogError("Your Class Type must inherit from UnityEngine.Object! Leave blank to default to UnityEngine.Object");
|
MelonLogger.LogError("Your Custom Class Type must inherit from UnityEngine.Object!");
|
||||||
return new List<object>();
|
return new List<object>();
|
||||||
}
|
}
|
||||||
|
|
||||||
var matches = new List<object>();
|
var matches = new List<object>();
|
||||||
|
|
||||||
var allObjectsOfType = Resources.FindObjectsOfTypeAll(type);
|
var allObjectsOfType = Resources.FindObjectsOfTypeAll(searchType);
|
||||||
|
|
||||||
foreach (var obj in allObjectsOfType)
|
foreach (var obj in allObjectsOfType)
|
||||||
{
|
{
|
||||||
@ -301,6 +301,13 @@ namespace Explorer
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (searchType == CppExplorer.ComponentType && CppExplorer.TransformType.IsAssignableFrom(obj.GetIl2CppType()))
|
||||||
|
{
|
||||||
|
// Transforms shouldn't really be counted as Components, skip them.
|
||||||
|
// They're more akin to GameObjects.
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
if (SceneMode != SceneFilter.Any && !FilterScene(obj, this.SceneMode))
|
if (SceneMode != SceneFilter.Any && !FilterScene(obj, this.SceneMode))
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
|
@ -236,21 +236,8 @@ namespace Explorer
|
|||||||
{
|
{
|
||||||
DrawPrimitive(ref value, rect, setTarget, setAction);
|
DrawPrimitive(ref value, rect, setTarget, setAction);
|
||||||
}
|
}
|
||||||
//else if (valueType == typeof(GameObject) || typeof(Component).IsAssignableFrom(valueType))
|
else if (ilType != null && ilType == CppExplorer.GameObjectType || CppExplorer.TransformType.IsAssignableFrom(ilType))
|
||||||
else if (ilType != null && ilType == CppExplorer.GameObjectType || CppExplorer.ComponentType.IsAssignableFrom(ilType))
|
|
||||||
{
|
{
|
||||||
//GameObject go;
|
|
||||||
//if (value.GetType() == typeof(Transform))
|
|
||||||
//{
|
|
||||||
// go = (value as Transform).gameObject;
|
|
||||||
//}
|
|
||||||
//else
|
|
||||||
//{
|
|
||||||
// go = (value as GameObject);
|
|
||||||
//}
|
|
||||||
|
|
||||||
//var go = (value as GameObject) ?? (value as Component).gameObject;
|
|
||||||
|
|
||||||
GameObject go;
|
GameObject go;
|
||||||
var ilObj = value as Il2CppSystem.Object;
|
var ilObj = value as Il2CppSystem.Object;
|
||||||
if (ilType == CppExplorer.GameObjectType)
|
if (ilType == CppExplorer.GameObjectType)
|
||||||
@ -259,7 +246,7 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
go = ilObj.TryCast<Component>().gameObject;
|
go = ilObj.TryCast<Transform>().gameObject;
|
||||||
}
|
}
|
||||||
|
|
||||||
GameobjButton(go, null, false, rect.width - 250);
|
GameobjButton(go, null, false, rect.width - 250);
|
||||||
@ -438,6 +425,20 @@ namespace Explorer
|
|||||||
label = col.ToString();
|
label = col.ToString();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
string typeLabel;
|
||||||
|
if (ilType != null)
|
||||||
|
{
|
||||||
|
typeLabel = ilType.FullName;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
typeLabel = value.GetType().FullName;
|
||||||
|
}
|
||||||
|
if (!label.Contains(typeLabel))
|
||||||
|
{
|
||||||
|
label += $" ({typeLabel})";
|
||||||
|
}
|
||||||
|
|
||||||
GUI.skin.button.alignment = TextAnchor.MiddleLeft;
|
GUI.skin.button.alignment = TextAnchor.MiddleLeft;
|
||||||
if (GUILayout.Button("<color=yellow>" + label + "</color>", new GUILayoutOption[] { GUILayout.MaxWidth(rect.width - 230) }))
|
if (GUILayout.Button("<color=yellow>" + label + "</color>", new GUILayoutOption[] { GUILayout.MaxWidth(rect.width - 230) }))
|
||||||
{
|
{
|
||||||
@ -447,25 +448,6 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//public static void DrawMember(ref object value, string valueType, string memberName, Rect rect, object setTarget = null, Action<object> setAction = null, float labelWidth = 180, bool autoSet = false)
|
|
||||||
//{
|
|
||||||
// GUILayout.Label("<color=cyan>" + memberName + ":</color>", new GUILayoutOption[] { GUILayout.Width(labelWidth) });
|
|
||||||
|
|
||||||
// DrawValue(ref value, rect, valueType, memberName, setTarget, setAction, autoSet);
|
|
||||||
//}
|
|
||||||
|
|
||||||
//public static void DrawValue(ref object value, Rect rect, string nullValueType = null, string memberName = null, object setTarget = null, Action<object> setAction = null, bool autoSet = false)
|
|
||||||
//{
|
|
||||||
// if (value == null)
|
|
||||||
// {
|
|
||||||
// GUILayout.Label("<i>null (" + nullValueType + ")</i>", null);
|
|
||||||
// }
|
|
||||||
// else
|
|
||||||
// {
|
|
||||||
|
|
||||||
// }
|
|
||||||
//}
|
|
||||||
|
|
||||||
// Helper for drawing primitive values (with Apply button)
|
// Helper for drawing primitive values (with Apply button)
|
||||||
|
|
||||||
public static void DrawPrimitive(ref object value, Rect m_rect, object setTarget = null, Action<object> setAction = null, bool autoSet = false)
|
public static void DrawPrimitive(ref object value, Rect m_rect, object setTarget = null, Action<object> setAction = null, bool autoSet = false)
|
||||||
|
@ -22,7 +22,24 @@ namespace Explorer
|
|||||||
|
|
||||||
public override void UpdateValue(object obj)
|
public override void UpdateValue(object obj)
|
||||||
{
|
{
|
||||||
m_value = fieldInfo.GetValue(fieldInfo.IsStatic ? null : obj);
|
try
|
||||||
|
{
|
||||||
|
if (obj is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var declaringType = this.fieldInfo.DeclaringType;
|
||||||
|
|
||||||
|
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
||||||
|
m_value = this.fieldInfo.GetValue(fieldInfo.IsStatic ? null : cast);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
m_value = this.fieldInfo.GetValue(fieldInfo.IsStatic ? null : obj);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
MelonLogger.Log($"Error updating FieldInfoHolder | {e.GetType()}: {e.Message}\r\n{e.StackTrace}");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Draw(ReflectionWindow window)
|
public override void Draw(ReflectionWindow window)
|
||||||
@ -31,10 +48,12 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
|
|
||||||
public override void SetValue(object obj)
|
public override void SetValue(object obj)
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (fieldInfo.FieldType.IsEnum)
|
if (fieldInfo.FieldType.IsEnum)
|
||||||
{
|
{
|
||||||
if (System.Enum.Parse(fieldInfo.FieldType, m_value.ToString()) is object enumValue && enumValue != null)
|
if (Enum.Parse(fieldInfo.FieldType, m_value.ToString()) is object enumValue && enumValue != null)
|
||||||
{
|
{
|
||||||
m_value = enumValue;
|
m_value = enumValue;
|
||||||
}
|
}
|
||||||
@ -74,9 +93,28 @@ namespace Explorer
|
|||||||
MelonLogger.LogWarning("Cannot parse " + m_value.ToString() + " to an integer! type: " + fieldInfo.FieldType);
|
MelonLogger.LogWarning("Cannot parse " + m_value.ToString() + " to an integer! type: " + fieldInfo.FieldType);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
MelonLogger.Log("Unsupported primitive field type: " + fieldInfo.FieldType.FullName);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (obj is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var declaringType = this.fieldInfo.DeclaringType;
|
||||||
|
|
||||||
|
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
||||||
|
fieldInfo.SetValue(fieldInfo.IsStatic ? null : cast, m_value);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
fieldInfo.SetValue(fieldInfo.IsStatic ? null : obj, m_value);
|
fieldInfo.SetValue(fieldInfo.IsStatic ? null : obj, m_value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
MelonLogger.Log($"Error setting FieldInfoHolder | {e.GetType()}: {e.Message}\r\n{e.StackTrace}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -33,6 +33,7 @@ namespace Explorer
|
|||||||
if (obj is Il2CppSystem.Object ilObject)
|
if (obj is Il2CppSystem.Object ilObject)
|
||||||
{
|
{
|
||||||
var declaringType = this.propInfo.DeclaringType;
|
var declaringType = this.propInfo.DeclaringType;
|
||||||
|
|
||||||
if (declaringType == typeof(Il2CppObjectBase))
|
if (declaringType == typeof(Il2CppObjectBase))
|
||||||
{
|
{
|
||||||
m_value = ilObject.Pointer;
|
m_value = ilObject.Pointer;
|
||||||
@ -40,7 +41,7 @@ namespace Explorer
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
var cast = CppExplorer.Il2CppCast(obj, declaringType);
|
||||||
m_value = this.propInfo.GetValue(cast, null);
|
m_value = this.propInfo.GetValue(this.propInfo.GetAccessors()[0].IsStatic ? null : cast, null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -70,7 +71,7 @@ namespace Explorer
|
|||||||
{
|
{
|
||||||
if (propInfo.PropertyType.IsEnum)
|
if (propInfo.PropertyType.IsEnum)
|
||||||
{
|
{
|
||||||
if (System.Enum.Parse(propInfo.PropertyType, m_value.ToString()) is object enumValue && enumValue != null)
|
if (Enum.Parse(propInfo.PropertyType, m_value.ToString()) is object enumValue && enumValue != null)
|
||||||
{
|
{
|
||||||
m_value = enumValue;
|
m_value = enumValue;
|
||||||
}
|
}
|
||||||
|
@ -31,54 +31,6 @@ namespace Explorer
|
|||||||
Field
|
Field
|
||||||
}
|
}
|
||||||
|
|
||||||
public Type GetActualType(object m_object)
|
|
||||||
{
|
|
||||||
if (m_object is Il2CppSystem.Object ilObject)
|
|
||||||
{
|
|
||||||
var iltype = ilObject.GetIl2CppType();
|
|
||||||
return Type.GetType(iltype.AssemblyQualifiedName);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return m_object.GetType();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public Type[] GetAllBaseTypes(object m_object)
|
|
||||||
{
|
|
||||||
var list = new List<Type>();
|
|
||||||
|
|
||||||
if (m_object is Il2CppSystem.Object ilObject)
|
|
||||||
{
|
|
||||||
var ilType = ilObject.GetIl2CppType();
|
|
||||||
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilTypeToManaged)
|
|
||||||
{
|
|
||||||
list.Add(ilTypeToManaged);
|
|
||||||
|
|
||||||
while (ilType.BaseType != null)
|
|
||||||
{
|
|
||||||
ilType = ilType.BaseType;
|
|
||||||
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilBaseTypeToManaged)
|
|
||||||
{
|
|
||||||
list.Add(ilBaseTypeToManaged);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var type = m_object.GetType();
|
|
||||||
list.Add(type);
|
|
||||||
while (type.BaseType != null)
|
|
||||||
{
|
|
||||||
type = type.BaseType;
|
|
||||||
list.Add(type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return list.ToArray();
|
|
||||||
}
|
|
||||||
|
|
||||||
public override void Init()
|
public override void Init()
|
||||||
{
|
{
|
||||||
m_object = Target;
|
m_object = Target;
|
||||||
@ -101,7 +53,7 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
catch { }
|
catch { }
|
||||||
|
|
||||||
UpdateValues();
|
UpdateValues(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Update()
|
public override void Update()
|
||||||
@ -112,9 +64,9 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void UpdateValues()
|
private void UpdateValues(bool forceAll = false)
|
||||||
{
|
{
|
||||||
if (m_filter == MemberFilter.Both || m_filter == MemberFilter.Field)
|
if (forceAll || m_filter == MemberFilter.Both || m_filter == MemberFilter.Field)
|
||||||
{
|
{
|
||||||
foreach (var holder in this.m_FieldInfos)
|
foreach (var holder in this.m_FieldInfos)
|
||||||
{
|
{
|
||||||
@ -125,7 +77,7 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_filter == MemberFilter.Both || m_filter == MemberFilter.Property)
|
if (forceAll || m_filter == MemberFilter.Both || m_filter == MemberFilter.Property)
|
||||||
{
|
{
|
||||||
foreach (var holder in this.m_PropertyInfos)
|
foreach (var holder in this.m_PropertyInfos)
|
||||||
{
|
{
|
||||||
@ -278,6 +230,56 @@ namespace Explorer
|
|||||||
GUI.color = Color.white;
|
GUI.color = Color.white;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ============ HELPERS ===============
|
||||||
|
|
||||||
|
public Type GetActualType(object m_object)
|
||||||
|
{
|
||||||
|
if (m_object is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var iltype = ilObject.GetIl2CppType();
|
||||||
|
return Type.GetType(iltype.AssemblyQualifiedName);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return m_object.GetType();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public Type[] GetAllBaseTypes(object m_object)
|
||||||
|
{
|
||||||
|
var list = new List<Type>();
|
||||||
|
|
||||||
|
if (m_object is Il2CppSystem.Object ilObject)
|
||||||
|
{
|
||||||
|
var ilType = ilObject.GetIl2CppType();
|
||||||
|
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilTypeToManaged)
|
||||||
|
{
|
||||||
|
list.Add(ilTypeToManaged);
|
||||||
|
|
||||||
|
while (ilType.BaseType != null)
|
||||||
|
{
|
||||||
|
ilType = ilType.BaseType;
|
||||||
|
if (Type.GetType(ilType.AssemblyQualifiedName) is Type ilBaseTypeToManaged)
|
||||||
|
{
|
||||||
|
list.Add(ilBaseTypeToManaged);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
var type = m_object.GetType();
|
||||||
|
list.Add(type);
|
||||||
|
while (type.BaseType != null)
|
||||||
|
{
|
||||||
|
type = type.BaseType;
|
||||||
|
list.Add(type);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return list.ToArray();
|
||||||
|
}
|
||||||
|
|
||||||
public static bool IsList(Type t)
|
public static bool IsList(Type t)
|
||||||
{
|
{
|
||||||
return t.IsGenericType
|
return t.IsGenericType
|
||||||
|
@ -20,7 +20,7 @@ namespace Explorer
|
|||||||
|
|
||||||
private string m_searchInput = "";
|
private string m_searchInput = "";
|
||||||
private string m_typeInput = "";
|
private string m_typeInput = "";
|
||||||
private int m_limit = 100;
|
private int m_limit = 20;
|
||||||
private int m_pageOffset = 0;
|
private int m_pageOffset = 0;
|
||||||
private List<object> m_searchResults = new List<object>();
|
private List<object> m_searchResults = new List<object>();
|
||||||
private Vector2 resultsScroll = Vector2.zero;
|
private Vector2 resultsScroll = Vector2.zero;
|
||||||
@ -85,11 +85,11 @@ namespace Explorer
|
|||||||
|
|
||||||
int count = m_searchResults.Count;
|
int count = m_searchResults.Count;
|
||||||
|
|
||||||
if (count > CppExplorer.ArrayLimit)
|
if (count > this.m_limit)
|
||||||
{
|
{
|
||||||
// prev/next page buttons
|
// prev/next page buttons
|
||||||
GUILayout.BeginHorizontal(null);
|
GUILayout.BeginHorizontal(null);
|
||||||
int maxOffset = (int)Mathf.Ceil(count / CppExplorer.ArrayLimit);
|
int maxOffset = (int)Mathf.Ceil(count / this.m_limit);
|
||||||
if (GUILayout.Button("< Prev", null))
|
if (GUILayout.Button("< Prev", null))
|
||||||
{
|
{
|
||||||
if (m_pageOffset > 0) m_pageOffset--;
|
if (m_pageOffset > 0) m_pageOffset--;
|
||||||
@ -110,7 +110,7 @@ namespace Explorer
|
|||||||
|
|
||||||
if (m_searchResults.Count > 0)
|
if (m_searchResults.Count > 0)
|
||||||
{
|
{
|
||||||
int offset = m_pageOffset * CppExplorer.ArrayLimit;
|
int offset = m_pageOffset * this.m_limit;
|
||||||
int preiterated = 0;
|
int preiterated = 0;
|
||||||
|
|
||||||
if (offset >= count) m_pageOffset = 0;
|
if (offset >= count) m_pageOffset = 0;
|
||||||
@ -123,7 +123,7 @@ namespace Explorer
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (i - offset > CppExplorer.ArrayLimit - 1)
|
if (i - offset > this.m_limit - 1)
|
||||||
{
|
{
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -257,14 +257,14 @@ namespace Explorer
|
|||||||
|
|
||||||
private List<object> FindAllObjectsOfType(string _search, string _type)
|
private List<object> FindAllObjectsOfType(string _search, string _type)
|
||||||
{
|
{
|
||||||
Il2CppSystem.Type type = null;
|
Il2CppSystem.Type searchType = null;
|
||||||
|
|
||||||
if (TypeMode == TypeFilter.Custom)
|
if (TypeMode == TypeFilter.Custom)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
var findType = CppExplorer.GetType(_type);
|
var findType = CppExplorer.GetType(_type);
|
||||||
type = Il2CppSystem.Type.GetType(findType.AssemblyQualifiedName);
|
searchType = Il2CppSystem.Type.GetType(findType.AssemblyQualifiedName);
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
@ -273,26 +273,26 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
else if (TypeMode == TypeFilter.Object)
|
else if (TypeMode == TypeFilter.Object)
|
||||||
{
|
{
|
||||||
type = CppExplorer.ObjectType;
|
searchType = CppExplorer.ObjectType;
|
||||||
}
|
}
|
||||||
else if (TypeMode == TypeFilter.GameObject)
|
else if (TypeMode == TypeFilter.GameObject)
|
||||||
{
|
{
|
||||||
type = CppExplorer.GameObjectType;
|
searchType = CppExplorer.GameObjectType;
|
||||||
}
|
}
|
||||||
else if (TypeMode == TypeFilter.Component)
|
else if (TypeMode == TypeFilter.Component)
|
||||||
{
|
{
|
||||||
type = CppExplorer.ComponentType;
|
searchType = CppExplorer.ComponentType;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!CppExplorer.ObjectType.IsAssignableFrom(type))
|
if (!CppExplorer.ObjectType.IsAssignableFrom(searchType))
|
||||||
{
|
{
|
||||||
MelonLogger.LogError("Your Class Type must inherit from UnityEngine.Object! Leave blank to default to UnityEngine.Object");
|
MelonLogger.LogError("Your Custom Class Type must inherit from UnityEngine.Object!");
|
||||||
return new List<object>();
|
return new List<object>();
|
||||||
}
|
}
|
||||||
|
|
||||||
var matches = new List<object>();
|
var matches = new List<object>();
|
||||||
|
|
||||||
var allObjectsOfType = Resources.FindObjectsOfTypeAll(type);
|
var allObjectsOfType = Resources.FindObjectsOfTypeAll(searchType);
|
||||||
|
|
||||||
foreach (var obj in allObjectsOfType)
|
foreach (var obj in allObjectsOfType)
|
||||||
{
|
{
|
||||||
@ -301,6 +301,13 @@ namespace Explorer
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (searchType == CppExplorer.ComponentType && CppExplorer.TransformType.IsAssignableFrom(obj.GetIl2CppType()))
|
||||||
|
{
|
||||||
|
// Transforms shouldn't really be counted as Components, skip them.
|
||||||
|
// They're more akin to GameObjects.
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
if (SceneMode != SceneFilter.Any && !FilterScene(obj, this.SceneMode))
|
if (SceneMode != SceneFilter.Any && !FilterScene(obj, this.SceneMode))
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
|
@ -236,8 +236,7 @@ namespace Explorer
|
|||||||
{
|
{
|
||||||
DrawPrimitive(ref value, rect, setTarget, setAction);
|
DrawPrimitive(ref value, rect, setTarget, setAction);
|
||||||
}
|
}
|
||||||
//else if (valueType == typeof(GameObject) || typeof(Component).IsAssignableFrom(valueType))
|
else if (ilType != null && ilType == CppExplorer.GameObjectType || CppExplorer.TransformType.IsAssignableFrom(ilType))
|
||||||
else if (ilType != null && ilType == CppExplorer.GameObjectType || CppExplorer.ComponentType.IsAssignableFrom(ilType))
|
|
||||||
{
|
{
|
||||||
GameObject go;
|
GameObject go;
|
||||||
var ilObj = value as Il2CppSystem.Object;
|
var ilObj = value as Il2CppSystem.Object;
|
||||||
@ -247,7 +246,7 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
go = ilObj.TryCast<Component>().gameObject;
|
go = ilObj.TryCast<Transform>().gameObject;
|
||||||
}
|
}
|
||||||
|
|
||||||
GameobjButton(go, null, false, rect.width - 250);
|
GameobjButton(go, null, false, rect.width - 250);
|
||||||
@ -426,6 +425,20 @@ namespace Explorer
|
|||||||
label = col.ToString();
|
label = col.ToString();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
string typeLabel;
|
||||||
|
if (ilType != null)
|
||||||
|
{
|
||||||
|
typeLabel = ilType.FullName;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
typeLabel = value.GetType().FullName;
|
||||||
|
}
|
||||||
|
if (!label.Contains(typeLabel))
|
||||||
|
{
|
||||||
|
label += $" ({typeLabel})";
|
||||||
|
}
|
||||||
|
|
||||||
GUI.skin.button.alignment = TextAnchor.MiddleLeft;
|
GUI.skin.button.alignment = TextAnchor.MiddleLeft;
|
||||||
if (GUILayout.Button("<color=yellow>" + label + "</color>", new GUILayoutOption[] { GUILayout.MaxWidth(rect.width - 230) }))
|
if (GUILayout.Button("<color=yellow>" + label + "</color>", new GUILayoutOption[] { GUILayout.MaxWidth(rect.width - 230) }))
|
||||||
{
|
{
|
||||||
@ -435,25 +448,6 @@ namespace Explorer
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//public static void DrawMember(ref object value, string valueType, string memberName, Rect rect, object setTarget = null, Action<object> setAction = null, float labelWidth = 180, bool autoSet = false)
|
|
||||||
//{
|
|
||||||
// GUILayout.Label("<color=cyan>" + memberName + ":</color>", new GUILayoutOption[] { GUILayout.Width(labelWidth) });
|
|
||||||
|
|
||||||
// DrawValue(ref value, rect, valueType, memberName, setTarget, setAction, autoSet);
|
|
||||||
//}
|
|
||||||
|
|
||||||
//public static void DrawValue(ref object value, Rect rect, string nullValueType = null, string memberName = null, object setTarget = null, Action<object> setAction = null, bool autoSet = false)
|
|
||||||
//{
|
|
||||||
// if (value == null)
|
|
||||||
// {
|
|
||||||
// GUILayout.Label("<i>null (" + nullValueType + ")</i>", null);
|
|
||||||
// }
|
|
||||||
// else
|
|
||||||
// {
|
|
||||||
|
|
||||||
// }
|
|
||||||
//}
|
|
||||||
|
|
||||||
// Helper for drawing primitive values (with Apply button)
|
// Helper for drawing primitive values (with Apply button)
|
||||||
|
|
||||||
public static void DrawPrimitive(ref object value, Rect m_rect, object setTarget = null, Action<object> setAction = null, bool autoSet = false)
|
public static void DrawPrimitive(ref object value, Rect m_rect, object setTarget = null, Action<object> setAction = null, bool autoSet = false)
|
||||||
|
Loading…
x
Reference in New Issue
Block a user