Fix strings boxed as Il2CppSystem.Objects

This commit is contained in:
Sinai 2021-04-04 13:44:58 +10:00
parent 113f2fd922
commit 6ca117b070
6 changed files with 42 additions and 11 deletions

View File

@ -154,21 +154,24 @@ namespace UnityExplorer.Core.Runtime.Il2Cpp
/// <returns>The object, as the type (or a normal C# object) if successful or the input value if not.</returns>
public static object Il2CppCast(object obj, Type castTo)
{
if (!(obj is Il2CppSystem.Object ilObj))
if (!(obj is Il2CppSystem.Object cppObj))
return obj;
if (!Il2CppTypeNotNull(castTo, out IntPtr castToPtr))
return obj;
IntPtr castFromPtr = il2cpp_object_get_class(ilObj.Pointer);
IntPtr castFromPtr = il2cpp_object_get_class(cppObj.Pointer);
if (!il2cpp_class_is_assignable_from(castToPtr, castFromPtr))
return null;
if (RuntimeSpecificsStore.IsInjected(castToPtr))
return UnhollowerBaseLib.Runtime.ClassInjectorBase.GetMonoObjectFromIl2CppPointer(ilObj.Pointer);
return UnhollowerBaseLib.Runtime.ClassInjectorBase.GetMonoObjectFromIl2CppPointer(cppObj.Pointer);
return Activator.CreateInstance(castTo, ilObj.Pointer);
if (castTo == typeof(string))
return cppObj.ToString();
return Activator.CreateInstance(castTo, cppObj.Pointer);
}
/// <summary>
@ -319,6 +322,14 @@ namespace UnityExplorer.Core.Runtime.Il2Cpp
return false;
}
public override void BoxStringToType(ref object value, Type castTo)
{
if (castTo == typeof(Il2CppSystem.String))
value = (Il2CppSystem.String)(value as string);
else
value = (Il2CppSystem.Object)(value as string);
}
// ~~~~~~~~~~ not used ~~~~~~~~~~~~
// cached il2cpp unbox methods

View File

@ -27,6 +27,9 @@ namespace UnityExplorer.Core.Runtime.Mono
public override string ProcessTypeNameInString(Type type, string theString, ref string typeName)
=> theString;
// not necessary
public override void BoxStringToType(ref object _string, Type castTo) { }
}
}

View File

@ -25,5 +25,7 @@ namespace UnityExplorer.Core.Runtime
public abstract string ProcessTypeNameInString(Type type, string theString, ref string typeName);
public abstract bool LoadModule(string module);
public abstract void BoxStringToType(ref object _string, Type castTo);
}
}

View File

@ -5,9 +5,14 @@ using System.Text;
namespace UnityExplorer
{
#if CPP
public static class TestClass
{
#if CPP
public static string testStringOne = "Test";
public static Il2CppSystem.Object testStringTwo = "string boxed as cpp object";
public static Il2CppSystem.String testStringThree = "string boxed as cpp string";
public static string nullString = null;
public static Il2CppSystem.Collections.Hashtable testHashset;
static TestClass()
@ -17,6 +22,6 @@ namespace UnityExplorer
testHashset.Add("key2", "itemTwo");
testHashset.Add("key3", "itemThree");
}
}
#endif
}
}

View File

@ -5,6 +5,7 @@ using UnityExplorer.Core.Config;
using UnityExplorer.Core.Input;
using UnityExplorer.Core.Runtime;
using UnityExplorer.UI;
using UnityExplorer.UI.Inspectors;
using UnityExplorer.UI.Main;
namespace UnityExplorer
@ -12,7 +13,7 @@ namespace UnityExplorer
public class ExplorerCore
{
public const string NAME = "UnityExplorer";
public const string VERSION = "3.3.5";
public const string VERSION = "3.3.6";
public const string AUTHOR = "Sinai";
public const string GUID = "com.sinai.unityexplorer";

View File

@ -9,6 +9,7 @@ using UnityExplorer.Core.Unity;
using UnityExplorer.UI;
using UnityExplorer.UI.Utility;
using UnityExplorer.UI.CacheObject;
using UnityExplorer.Core.Runtime;
namespace UnityExplorer.UI.InteractiveValues
{
@ -27,8 +28,8 @@ namespace UnityExplorer.UI.InteractiveValues
// strings boxed as Il2CppSystem.Objects can behave weirdly.
// GetActualType will find they are a string, but if its boxed
// then we need to unbox it like this...
if (!(Value is string))
Value = ((Il2CppSystem.Object)Value).ToString();
if (!(Value is string) && Value is Il2CppSystem.Object cppobj)
Value = cppobj.ToString();
#endif
base.OnValueUpdated();
@ -96,10 +97,18 @@ namespace UnityExplorer.UI.InteractiveValues
m_labelLayout.flexibleWidth = 0;
}
internal void OnApplyClicked()
internal void SetValueFromInput()
{
Value = m_valueInput.text;
if (!typeof(string).IsAssignableFrom(Owner.FallbackType))
ReflectionProvider.Instance.BoxStringToType(ref Value, Owner.FallbackType);
Owner.SetValue();
// revert back to string now
OnValueUpdated();
RefreshUIForValue();
}
@ -170,7 +179,7 @@ namespace UnityExplorer.UI.InteractiveValues
if (Owner.CanWrite)
{
var apply = UIFactory.CreateButton(groupObj, "ApplyButton", "Apply", OnApplyClicked, new Color(0.2f, 0.2f, 0.2f));
var apply = UIFactory.CreateButton(groupObj, "ApplyButton", "Apply", SetValueFromInput, new Color(0.2f, 0.2f, 0.2f));
UIFactory.SetLayoutElement(apply.gameObject, minWidth: 50, minHeight: 25, flexibleWidth: 0);
}
else