Some mods may be broken due to the recent Alloyed Collective update.
Decompiled source of DynamicSkinsFix v1.0.7
DynamicSkinsFix.dll
Decompiled 3 months agousing System; using System.Collections; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Logging; using HG; using IL.RoR2; using Microsoft.CodeAnalysis; using Mono.Cecil.Cil; using MonoMod.Cil; using On.RoR2; using RoR2; using UnityEngine; using UnityEngine.AddressableAssets; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("DynamicSkinsFix")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+7551784b12888f88f017f2d194d7df4ad9e13916")] [assembly: AssemblyProduct("DynamicSkinsFix")] [assembly: AssemblyTitle("DynamicSkinsFix")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.0.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace DynamicSkinsFix { [BepInPlugin("Miyowi.DynamicSkinsFix", "DynamicSkinsFix", "1.0.7")] public class DynamicSkinsFix : BaseUnityPlugin { [CompilerGenerated] private static class <>O { public static hook_Init <0>__SwapAcridRenderer; public static Manipulator <1>__CallObsolete; public static Manipulator <2>__ObsoleteRet; public static Manipulator <3>__AccessOldArray; } public const string PluginGUID = "Miyowi.DynamicSkinsFix"; public const string PluginAuthor = "Miyowi"; public const string PluginName = "DynamicSkinsFix"; public const string PluginVersion = "1.0.7"; private Random random = new Random(); private static int callCount; private const int callLimit = 50; public void Awake() { //IL_0029: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Expected O, but got Unknown //IL_004a: Unknown result type (might be due to invalid IL or missing references) //IL_004f: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Expected O, but got Unknown //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Expected O, but got Unknown //IL_008c: Unknown result type (might be due to invalid IL or missing references) //IL_0091: Unknown result type (might be due to invalid IL or missing references) //IL_0097: Expected O, but got Unknown Log.Init(((BaseUnityPlugin)this).Logger); DupeRenderer(); AttachAcridComponent(); object obj = <>O.<0>__SwapAcridRenderer; if (obj == null) { hook_Init val = SwapAcridRenderer; <>O.<0>__SwapAcridRenderer = val; obj = (object)val; } SkinCatalog.Init += (hook_Init)obj; object obj2 = <>O.<1>__CallObsolete; if (obj2 == null) { Manipulator val2 = CallObsolete; <>O.<1>__CallObsolete = val2; obj2 = (object)val2; } SkinDef.ApplyAsync += (Manipulator)obj2; object obj3 = <>O.<2>__ObsoleteRet; if (obj3 == null) { Manipulator val3 = ObsoleteRet; <>O.<2>__ObsoleteRet = val3; obj3 = (object)val3; } SkinDef.Apply += (Manipulator)obj3; object obj4 = <>O.<3>__AccessOldArray; if (obj4 == null) { Manipulator val4 = AccessOldArray; <>O.<3>__AccessOldArray = val4; obj4 = (object)val4; } BodyCatalog.GetBodySkins += (Manipulator)obj4; } private static void ObsoleteRet(ILContext il) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Expected O, but got Unknown //IL_006c: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) Func<bool> func = delegate { callCount++; StackTrace stackTrace = new StackTrace(); StackFrame[] frames = stackTrace.GetFrames(); foreach (StackFrame stackFrame in frames) { MethodBase method = stackFrame.GetMethod(); if (callCount > 50) { Log.Warning("Potential infinite loop detected. Aborting to prevent game crash"); return true; } if (method.Name == "DMD<RoR2.SkinDef::ApplyAsync>" || method.Name == "ApplyAsync") { return true; } } return false; }; ILCursor val = new ILCursor(il); if (val.TryGotoNext((MoveType)0, new Func<Instruction, bool>[1] { (Instruction x) => ILPatternMatchingExt.MatchLdarg(x, 0) })) { ILLabel val2 = val.DefineLabel(); val.EmitDelegate<Func<bool>>(func); val.Emit(OpCodes.Brfalse, (object)val2); val.Emit(OpCodes.Ret); val.MarkLabel(val2); } else { Log.Error("ILHook failed. Some dynamic skins will not work, or worse"); } } private static void CallObsolete(ILContext il) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Expected O, but got Unknown //IL_005d: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Unknown result type (might be due to invalid IL or missing references) Action<SkinDef, GameObject> action = delegate(SkinDef self, GameObject modelObject) { self.Apply(modelObject); }; ILCursor val = new ILCursor(il); if (val.TryGotoNext((MoveType)0, new Func<Instruction, bool>[1] { (Instruction x) => ILPatternMatchingExt.MatchRet(x) })) { val.Emit(OpCodes.Ldarg_0); val.Emit(OpCodes.Ldarg_1); val.EmitDelegate<Action<SkinDef, GameObject>>(action); } else { Log.Error("ILHook failed. Some dynamic skins will not work, or worse"); } } private static void AccessOldArray(ILContext il) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Expected O, but got Unknown //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_00b2: Unknown result type (might be due to invalid IL or missing references) //IL_00c6: Unknown result type (might be due to invalid IL or missing references) Func<BodyIndex, SkinDef[]> func = delegate(BodyIndex bodyIndex) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Unknown result type (might be due to invalid IL or missing references) //IL_0027: Expected I4, but got Unknown SkinDef[] bodySkinDefs = SkinCatalog.GetBodySkinDefs(bodyIndex); if (bodySkinDefs.Length == 0) { SkinDef[][] skins = BodyCatalog.skins; SkinDef[] array = Array.Empty<SkinDef>(); return ArrayUtils.GetSafe<SkinDef[]>(skins, (int)bodyIndex, ref array); } return bodySkinDefs; }; ILCursor val = new ILCursor(il); if (val.TryGotoNext((MoveType)0, new Func<Instruction, bool>[1] { (Instruction x) => ILPatternMatchingExt.MatchLdarg(x, 0) })) { ILLabel val2 = val.DefineLabel(); val.Emit(OpCodes.Br, (object)val2); if (val.TryGotoNext((MoveType)2, new Func<Instruction, bool>[1] { (Instruction x) => ILPatternMatchingExt.MatchRet(x) })) { val.MarkLabel(val2); val.Emit(OpCodes.Ldarg_0); val.EmitDelegate<Func<BodyIndex, SkinDef[]>>(func); val.Emit(OpCodes.Ret); } else { Log.Error("ILHook failed. Some dynamic skins will not work, or worse"); } } else { Log.Error("ILHook failed. Some dynamic skins will not work, or worse"); } } private static void AttachAcridComponent() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) GameObject val = Addressables.LoadAssetAsync<GameObject>((object)"RoR2/Base/Croco/CrocoBody.prefab").WaitForCompletion(); val.AddComponent<FixAcridMissingGoo>(); } private static void DupeRenderer() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) GameObject val = Addressables.LoadAssetAsync<GameObject>((object)"RoR2/Base/Croco/CrocoBody.prefab").WaitForCompletion(); if ((Object)(object)val != (Object)null) { GameObject gameObject = ((Component)val.GetComponent<ModelLocator>().modelTransform).gameObject; Transform val2 = gameObject.transform.Find("CrocoSpineMesh"); SkinnedMeshRenderer component = ((Component)val2).GetComponent<SkinnedMeshRenderer>(); Transform val3 = Object.Instantiate<Transform>(gameObject.transform.Find("CrocoSpineMesh")); SkinnedMeshRenderer component2 = ((Component)val3).GetComponent<SkinnedMeshRenderer>(); ((Object)((Component)component2).transform).name = "CrocoSpineMesh"; component2.sharedMesh = component.sharedMesh; val3.parent = gameObject.transform; } else { Log.Error("Could not find CrocoBody Prefab. Acrid fixes not applied."); } } private static IEnumerator SwapAcridRenderer(orig_Init orig) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0246: Unknown result type (might be due to invalid IL or missing references) //IL_01ff: Unknown result type (might be due to invalid IL or missing references) GameObject val = Addressables.LoadAssetAsync<GameObject>((object)"RoR2/Base/Croco/CrocoBody.prefab").WaitForCompletion(); GameObject gameObject = ((Component)val.GetComponent<ModelLocator>().modelTransform).gameObject; ModelSkinController component = gameObject.GetComponent<ModelSkinController>(); Renderer[] componentsInChildren = gameObject.GetComponentsInChildren<Renderer>(true); SkinDef[] skins = component.skins; foreach (SkinDef val2 in skins) { bool flag = false; for (int j = 0; j < val2.meshReplacements.Length; j++) { flag = (Object)(object)componentsInChildren[3] == (Object)(object)val2.meshReplacements[j].renderer; if (flag) { break; } } if (!flag) { for (int k = 0; k < val2.rendererInfos.Length; k++) { flag = (Object)(object)componentsInChildren[3] == (Object)(object)val2.rendererInfos[k].renderer; if (flag) { break; } } for (int l = 0; l < val2.gameObjectActivations.Length; l++) { flag = (Object)(object)((Component)componentsInChildren[3]).gameObject == (Object)(object)val2.gameObjectActivations[l].gameObject; if (flag) { break; } } } if (flag) { for (int m = 0; m < val2.meshReplacements.Length; m++) { val2.meshReplacements[m].renderer = GetCorrectRenderer(val2.meshReplacements[m].renderer, componentsInChildren); } for (int n = 0; n < val2.rendererInfos.Length; n++) { val2.rendererInfos[n].renderer = GetCorrectRenderer(val2.rendererInfos[n].renderer, componentsInChildren); } for (int num = 0; num < val2.gameObjectActivations.Length; num++) { val2.gameObjectActivations[num].gameObject = GetCorrectGameObject(val2.gameObjectActivations[num], componentsInChildren); } } } BodyCatalog.skins[BodyCatalog.FindBodyIndex("CrocoBody")] = component.skins; return orig.Invoke(); } private static Renderer GetCorrectRenderer(Renderer renderer, Renderer[] componentsInChildren) { return componentsInChildren[Array.IndexOf(componentsInChildren, renderer) - 1]; } private static GameObject GetCorrectGameObject(GameObjectActivation gameObjectActivation, Renderer[] componentsInChildren) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)gameObjectActivation.gameObject == (Object)(object)((Component)componentsInChildren[3]).gameObject) { return ((Component)componentsInChildren[2]).gameObject; } if ((Object)(object)gameObjectActivation.gameObject == (Object)(object)((Component)componentsInChildren[2]).gameObject) { return ((Component)componentsInChildren[1]).gameObject; } return ((Component)componentsInChildren[0]).gameObject; } private void FixedUpdate() { callCount = 0; } } public class FixAcridMissingGoo : MonoBehaviour { public void Start() { ModelLocator component = ((Component)this).GetComponent<ModelLocator>(); object obj; if (component == null) { obj = null; } else { ChildLocator component2 = ((Component)component.modelTransform).GetComponent<ChildLocator>(); if (component2 == null) { obj = null; } else { Transform obj2 = component2.FindChild("Head"); if (obj2 == null) { obj = null; } else { Transform obj3 = obj2.Find("Goo"); obj = ((obj3 != null) ? ((Component)obj3).GetComponent<ParticleSystemRenderer>() : null); } } } ParticleSystemRenderer val = (ParticleSystemRenderer)obj; if ((Object)(object)val != (Object)null && (Object)(object)((Renderer)val).sharedMaterial == (Object)null) { ((Component)val).gameObject.SetActive(false); } Object.Destroy((Object)(object)this); } } internal static class Log { private static ManualLogSource _logSource; internal static void Init(ManualLogSource logSource) { _logSource = logSource; } internal static void Debug(object data) { _logSource.LogDebug(data); } internal static void Error(object data) { _logSource.LogError(data); } internal static void Fatal(object data) { _logSource.LogFatal(data); } internal static void Info(object data) { _logSource.LogInfo(data); } internal static void Message(object data) { _logSource.LogMessage(data); } internal static void Warning(object data) { _logSource.LogWarning(data); } } }