using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using BepInEx;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using TooManyHats.Helpers;
using TooManyHats.Patches;
using UnityEngine;
[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("TooManyHats")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyFileVersion("1.1.3.0")]
[assembly: AssemblyInformationalVersion("1.1.3")]
[assembly: AssemblyProduct("TooManyHats")]
[assembly: AssemblyTitle("TooManyHats")]
[assembly: AssemblyVersion("1.1.3.0")]
[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 TooManyHats
{
[BepInPlugin("TeddyBRB.toomanyhats", "Too Many Hats", "2.1.0")]
public class Plugin : BaseUnityPlugin
{
public class HatEntry
{
public string Name;
public GameObject Prefab;
public Texture2D Icon;
public HatEntry(string name, GameObject prefab, Texture2D icon)
{
Name = name;
Prefab = prefab;
Icon = icon;
}
}
public static AssetBundle assetBundle;
public static List<HatEntry> hats;
internal static ManualLogSource Logger;
internal static Harmony _harmony;
public static int BaseHatCount { get; set; }
public static int OverrideHatCount { get; set; }
public void Awake()
{
//IL_01e9: Unknown result type (might be due to invalid IL or missing references)
//IL_01f3: Expected O, but got Unknown
Logger = ((BaseUnityPlugin)this).Logger;
BaseHatCount = 0;
OverrideHatCount = 0;
string directoryName = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);
string text = Path.Combine(directoryName, "toomanyhats");
Logger.LogInfo((object)("[TooManyHats] Loading AssetBundle from: " + text));
if (!File.Exists(text))
{
Logger.LogError((object)("[TooManyHats] AssetBundle file not found: " + text));
return;
}
byte[] array = File.ReadAllBytes(text);
assetBundle = AssetBundle.LoadFromMemory(array);
if ((Object)(object)assetBundle == (Object)null)
{
Logger.LogError((object)"[TooManyHats] Failed to load AssetBundle!");
return;
}
hats = new List<HatEntry>();
AddHatIfValid("mario");
AddHatIfValid("luigi");
AddHatIfValid("luffy");
AddHatIfValid("kitty");
AddHatIfValid("kitdy");
AddHatIfValid("cat");
AddHatIfValid("bucket");
AddHatIfValid("construction");
AddHatIfValid("crown");
AddHatIfValid("cowboy");
AddHatIfValid("pirate");
AddHatIfValid("pilot");
AddHatIfValid("rat");
AddHatIfValid("sleepy");
AddHatIfValid("elephant");
AddHatIfValid("froggy");
AddHatIfValid("kirby");
AddHatIfValid("cinnamon");
AddHatIfValid("bunny");
AddHatIfValid("freeze");
AddHatIfValid("spongebob");
AddHatIfValid("longboy");
AddHatIfValid("pikachu");
AddHatIfValid("link");
Logger.LogInfo((object)$"[TooManyHats] Loaded {hats.Count} valid hats.");
_harmony = new Harmony("TeddyBRB.toomanyhats");
_harmony.PatchAll(typeof(PassportManagerPatch));
_harmony.PatchAll(typeof(CharacterCustomizationPatch));
_harmony.PatchAll(typeof(PlayerCustomizationDummyPatch));
_harmony.PatchAll(typeof(PeakHandlePatch));
_harmony.PatchAll(typeof(PassportButtonPatch));
Logger.LogInfo((object)"[TooManyHats] Patches applied.");
}
private static void AddHatIfValid(string hatName)
{
HatEntry hatEntry = LoadHat(hatName);
if (!((Object)(object)hatEntry.Prefab == (Object)null))
{
hats.Add(hatEntry);
}
}
private static HatEntry LoadHat(string hatName)
{
Logger.LogInfo((object)("[TooManyHats] Loading hat '" + hatName + "'"));
GameObject val = assetBundle.LoadAsset<GameObject>("Assets/" + hatName + ".prefab");
Texture2D val2 = assetBundle.LoadAsset<Texture2D>("Assets/" + hatName + ".png");
if ((Object)(object)val == (Object)null)
{
Logger.LogError((object)("[TooManyHats] Missing prefab for hat '" + hatName + "' (Assets/" + hatName + ".prefab)"));
return null;
}
if ((Object)(object)val2 == (Object)null)
{
Logger.LogWarning((object)("[TooManyHats] Missing icon for hat '" + hatName + "' (Assets/" + hatName + ".png). It will still load."));
}
return new HatEntry(hatName, val, val2);
}
}
public static class MyPluginInfo
{
public const string PLUGIN_GUID = "TooManyHats";
public const string PLUGIN_NAME = "TooManyHats";
public const string PLUGIN_VERSION = "1.1.3";
}
}
namespace TooManyHats.Data
{
public abstract class CustomizationData : ScriptableObject
{
public abstract Texture IconTexture { get; }
public abstract Type Type { get; }
public abstract bool IsValid();
}
public abstract class CustomAccessoryData : CustomizationData
{
public sealed override Type Type => (Type)10;
}
public abstract class CustomEyesData : CustomizationData
{
public sealed override Type Type => (Type)20;
}
public abstract class CustomMouthData : CustomizationData
{
public sealed override Type Type => (Type)30;
}
public abstract class CustomHatData : CustomizationData
{
public sealed override Type Type => (Type)50;
}
[CreateAssetMenu(menuName = "PEAK More Customizations/Accessory", fileName = "New Custom Accessory", order = int.MinValue)]
public class CustomAccessory_V1 : CustomAccessoryData
{
[field: SerializeField]
public Texture Texture { get; internal set; }
public override Texture IconTexture => Texture;
public override bool IsValid()
{
return Object.op_Implicit((Object)(object)Texture);
}
}
[CreateAssetMenu(menuName = "PEAK More Customizations/Eye", fileName = "New Custom Eye", order = int.MinValue)]
public class CustomEyes_V1 : CustomEyesData
{
[field: SerializeField]
public Texture Texture { get; internal set; }
public override Texture IconTexture => Texture;
public override bool IsValid()
{
return Object.op_Implicit((Object)(object)Texture);
}
}
[CreateAssetMenu(menuName = "PEAK More Customizations/Hat", fileName = "New Custom Hat", order = int.MinValue)]
public class CustomHat_V1 : CustomHatData
{
[field: SerializeField]
public Texture Icon { get; internal set; }
[field: SerializeField]
public GameObject Prefab { get; internal set; }
[field: SerializeField]
public Texture MainTexture { get; internal set; }
[field: SerializeField]
public Texture SubTexture { get; internal set; }
[field: SerializeField]
public Vector3 PositionOffset { get; internal set; }
[field: SerializeField]
public Vector3 EulerAngleOffset { get; internal set; }
public Vector3 SwizzledPositionOffset => new Vector3(PositionOffset.x, 0f - PositionOffset.z, PositionOffset.y);
public Vector3 SwizzledRotationOffset => new Vector3(EulerAngleOffset.x, 0f - EulerAngleOffset.z, 0f - EulerAngleOffset.y);
public override Texture IconTexture => Icon;
public override bool IsValid()
{
return Object.op_Implicit((Object)(object)Icon) && Object.op_Implicit((Object)(object)Prefab);
}
}
[CreateAssetMenu(menuName = "PEAK More Customizations/Mouth", fileName = "New Custom Mouth", order = int.MinValue)]
public class CustomMouth_V1 : CustomMouthData
{
[field: SerializeField]
public Texture Texture { get; internal set; }
public override Texture IconTexture => Texture;
public override bool IsValid()
{
return Object.op_Implicit((Object)(object)Texture);
}
}
}
namespace TooManyHats.Patches
{
[HarmonyPatch]
public static class CharacterCustomizationPatch
{
[CompilerGenerated]
private sealed class <SetCharacterHatTranspiler>d__3 : IEnumerable<CodeInstruction>, IEnumerable, IEnumerator<CodeInstruction>, IEnumerator, IDisposable
{
private int <>1__state;
private CodeInstruction <>2__current;
private int <>l__initialThreadId;
private IEnumerable<CodeInstruction> instructions;
public IEnumerable<CodeInstruction> <>3__instructions;
private List<CodeInstruction> <codes>5__1;
private bool <patched>5__2;
private int <i>5__3;
private bool <canMatch>5__4;
private MethodInfo <getOverrideHatCount>5__5;
CodeInstruction IEnumerator<CodeInstruction>.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
object IEnumerator.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
[DebuggerHidden]
public <SetCharacterHatTranspiler>d__3(int <>1__state)
{
this.<>1__state = <>1__state;
<>l__initialThreadId = Environment.CurrentManagedThreadId;
}
[DebuggerHidden]
void IDisposable.Dispose()
{
<codes>5__1 = null;
<getOverrideHatCount>5__5 = null;
<>1__state = -2;
}
private bool MoveNext()
{
//IL_02ff: Unknown result type (might be due to invalid IL or missing references)
//IL_0309: Expected O, but got Unknown
//IL_0320: Unknown result type (might be due to invalid IL or missing references)
//IL_032a: Expected O, but got Unknown
switch (<>1__state)
{
default:
return false;
case 0:
<>1__state = -1;
<codes>5__1 = instructions.ToList();
<patched>5__2 = false;
<i>5__3 = 0;
break;
case 1:
<>1__state = -1;
<>2__current = <codes>5__1[<i>5__3 + 1];
<>1__state = 2;
return true;
case 2:
<>1__state = -1;
<>2__current = <codes>5__1[<i>5__3 + 2];
<>1__state = 3;
return true;
case 3:
<>1__state = -1;
<>2__current = <codes>5__1[<i>5__3 + 3];
<>1__state = 4;
return true;
case 4:
<>1__state = -1;
<>2__current = <codes>5__1[<i>5__3 + 4];
<>1__state = 5;
return true;
case 5:
<>1__state = -1;
<getOverrideHatCount>5__5 = AccessTools.Method(typeof(CharacterCustomizationPatch), "GetOverrideHatCount", (Type[])null, (Type[])null);
<>2__current = new CodeInstruction(OpCodes.Call, (object)<getOverrideHatCount>5__5);
<>1__state = 6;
return true;
case 6:
<>1__state = -1;
<>2__current = new CodeInstruction(OpCodes.Add, (object)null);
<>1__state = 7;
return true;
case 7:
<>1__state = -1;
<i>5__3 += 4;
goto IL_0372;
case 8:
{
<>1__state = -1;
goto IL_0372;
}
IL_0372:
<i>5__3++;
break;
}
if (<i>5__3 < <codes>5__1.Count)
{
<canMatch>5__4 = <i>5__3 <= <codes>5__1.Count - 5;
if (<canMatch>5__4 && <codes>5__1[<i>5__3].opcode == OpCodes.Ldarg_0 && <codes>5__1[<i>5__3 + 1].opcode == OpCodes.Call && <codes>5__1[<i>5__3 + 1].operand != null && <codes>5__1[<i>5__3 + 1].operand.ToString().Contains("get_Instance") && <codes>5__1[<i>5__3 + 2].opcode == OpCodes.Ldfld && <codes>5__1[<i>5__3 + 2].operand != null && <codes>5__1[<i>5__3 + 2].operand.ToString().Contains("hats") && <codes>5__1[<i>5__3 + 3].opcode == OpCodes.Ldlen && <codes>5__1[<i>5__3 + 4].opcode == OpCodes.Conv_I4)
{
<patched>5__2 = true;
<>2__current = <codes>5__1[<i>5__3];
<>1__state = 1;
return true;
}
<>2__current = <codes>5__1[<i>5__3];
<>1__state = 8;
return true;
}
if (!<patched>5__2)
{
Plugin.Logger.LogWarning((object)"[TooManyHats] SetCharacterHat transpiler did not find hats length pattern.");
}
return false;
}
bool IEnumerator.MoveNext()
{
//ILSpy generated this explicit interface implementation from .override directive in MoveNext
return this.MoveNext();
}
[DebuggerHidden]
void IEnumerator.Reset()
{
throw new NotSupportedException();
}
[DebuggerHidden]
IEnumerator<CodeInstruction> IEnumerable<CodeInstruction>.GetEnumerator()
{
<SetCharacterHatTranspiler>d__3 <SetCharacterHatTranspiler>d__;
if (<>1__state == -2 && <>l__initialThreadId == Environment.CurrentManagedThreadId)
{
<>1__state = 0;
<SetCharacterHatTranspiler>d__ = this;
}
else
{
<SetCharacterHatTranspiler>d__ = new <SetCharacterHatTranspiler>d__3(0);
}
<SetCharacterHatTranspiler>d__.instructions = <>3__instructions;
return <SetCharacterHatTranspiler>d__;
}
[DebuggerHidden]
IEnumerator IEnumerable.GetEnumerator()
{
return ((IEnumerable<CodeInstruction>)this).GetEnumerator();
}
}
private static Shader _characterShader;
private static int GetOverrideHatCount()
{
return Plugin.OverrideHatCount;
}
[HarmonyPatch(typeof(CharacterCustomization), "Awake")]
[HarmonyPostfix]
public static void AwakePostfix(CharacterCustomization __instance)
{
if ((Object)(object)__instance == (Object)null)
{
return;
}
if ((Object)(object)_characterShader == (Object)null)
{
_characterShader = Shader.Find("W/Character");
}
Transform val = null;
try
{
val = ((Component)__instance).transform.GetChild(0).GetChild(0).GetChild(0)
.GetChild(2)
.GetChild(0)
.GetChild(0)
.GetChild(1)
.GetChild(1);
}
catch
{
}
if ((Object)(object)val == (Object)null)
{
Plugin.Logger.LogError((object)"[TooManyHats] Could not find hats container!");
return;
}
if ((Object)(object)__instance.refs == (Object)null)
{
Plugin.Logger.LogError((object)"[TooManyHats] CharacterCustomization.refs is null!");
return;
}
List<Renderer> list = new List<Renderer>((IEnumerable<Renderer>)(((object)__instance.refs.playerHats) ?? ((object)new Renderer[0])));
if (Plugin.hats == null || Plugin.hats.Count == 0)
{
Plugin.Logger.LogWarning((object)"[TooManyHats] No hats to instantiate in CharacterCustomizationPatch.");
__instance.refs.playerHats = list.ToArray();
return;
}
foreach (Plugin.HatEntry hat in Plugin.hats)
{
if (hat == null || (Object)(object)hat.Prefab == (Object)null)
{
Plugin.Logger.LogWarning((object)"[TooManyHats] Skipping null hat/prefab.");
continue;
}
GameObject val2 = Object.Instantiate<GameObject>(hat.Prefab, val, false);
Renderer componentInChildren = val2.GetComponentInChildren<Renderer>(true);
if ((Object)(object)componentInChildren == (Object)null)
{
Plugin.Logger.LogError((object)("[TooManyHats] No Renderer on hat '" + hat.Name + "'"));
Object.Destroy((Object)(object)val2);
continue;
}
if ((Object)(object)_characterShader != (Object)null)
{
Material[] materials = componentInChildren.materials;
for (int i = 0; i < materials.Length; i++)
{
if ((Object)(object)materials[i] != (Object)null)
{
materials[i].shader = _characterShader;
}
}
componentInChildren.materials = materials;
}
else
{
Plugin.Logger.LogWarning((object)"[TooManyHats] Shader 'W/Character' not found.");
}
((Component)componentInChildren).gameObject.SetActive(false);
((Object)componentInChildren).name = hat.Name;
list.Add(componentInChildren);
Plugin.Logger.LogDebug((object)("[TooManyHats] Added hat '" + hat.Name + "' to playerHats"));
}
__instance.refs.playerHats = list.ToArray();
Plugin.Logger.LogInfo((object)$"[TooManyHats] CharacterCustomization hats ready. playerHats={__instance.refs.playerHats.Length}");
}
[IteratorStateMachine(typeof(<SetCharacterHatTranspiler>d__3))]
[HarmonyPatch(typeof(CharacterCustomization), "SetCharacterHat")]
[HarmonyTranspiler]
public static IEnumerable<CodeInstruction> SetCharacterHatTranspiler(IEnumerable<CodeInstruction> instructions)
{
//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
return new <SetCharacterHatTranspiler>d__3(-2)
{
<>3__instructions = instructions
};
}
}
public class PassportButtonPatch
{
[HarmonyPatch(typeof(PassportButton), "SetButton")]
[HarmonyPostfix]
private static void SetButton(ref int ___currentIndex, CustomizationOption option)
{
//IL_000f: Unknown result type (might be due to invalid IL or missing references)
//IL_0016: Invalid comparison between Unknown and I4
if (!((Object)(object)option == (Object)null) && (int)option.type == 50 && ___currentIndex >= Plugin.BaseHatCount)
{
___currentIndex += Plugin.OverrideHatCount;
}
}
}
public class PassportManagerPatch
{
[CompilerGenerated]
private sealed class <CameraInTranspiler>d__5 : IEnumerable<CodeInstruction>, IEnumerable, IEnumerator<CodeInstruction>, IEnumerator, IDisposable
{
private int <>1__state;
private CodeInstruction <>2__current;
private int <>l__initialThreadId;
private IEnumerable<CodeInstruction> instructions;
public IEnumerable<CodeInstruction> <>3__instructions;
private IEnumerator<CodeInstruction> <>s__1;
private CodeInstruction <instruction>5__2;
CodeInstruction IEnumerator<CodeInstruction>.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
object IEnumerator.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
[DebuggerHidden]
public <CameraInTranspiler>d__5(int <>1__state)
{
this.<>1__state = <>1__state;
<>l__initialThreadId = Environment.CurrentManagedThreadId;
}
[DebuggerHidden]
void IDisposable.Dispose()
{
int num = <>1__state;
if (num == -3 || num == 1)
{
try
{
}
finally
{
<>m__Finally1();
}
}
<>s__1 = null;
<instruction>5__2 = null;
<>1__state = -2;
}
private bool MoveNext()
{
try
{
switch (<>1__state)
{
default:
return false;
case 0:
<>1__state = -1;
<>s__1 = instructions.GetEnumerator();
<>1__state = -3;
break;
case 1:
<>1__state = -3;
<instruction>5__2 = null;
break;
}
if (<>s__1.MoveNext())
{
<instruction>5__2 = <>s__1.Current;
if (<instruction>5__2.opcode == OpCodes.Ldc_R4 && <instruction>5__2.operand != null && <instruction>5__2.operand.Equals(1f))
{
<instruction>5__2.operand = 3f;
}
<>2__current = <instruction>5__2;
<>1__state = 1;
return true;
}
<>m__Finally1();
<>s__1 = null;
return false;
}
catch
{
//try-fault
((IDisposable)this).Dispose();
throw;
}
}
bool IEnumerator.MoveNext()
{
//ILSpy generated this explicit interface implementation from .override directive in MoveNext
return this.MoveNext();
}
private void <>m__Finally1()
{
<>1__state = -1;
if (<>s__1 != null)
{
<>s__1.Dispose();
}
}
[DebuggerHidden]
void IEnumerator.Reset()
{
throw new NotSupportedException();
}
[DebuggerHidden]
IEnumerator<CodeInstruction> IEnumerable<CodeInstruction>.GetEnumerator()
{
<CameraInTranspiler>d__5 <CameraInTranspiler>d__;
if (<>1__state == -2 && <>l__initialThreadId == Environment.CurrentManagedThreadId)
{
<>1__state = 0;
<CameraInTranspiler>d__ = this;
}
else
{
<CameraInTranspiler>d__ = new <CameraInTranspiler>d__5(0);
}
<CameraInTranspiler>d__.instructions = <>3__instructions;
return <CameraInTranspiler>d__;
}
[DebuggerHidden]
IEnumerator IEnumerable.GetEnumerator()
{
return ((IEnumerable<CodeInstruction>)this).GetEnumerator();
}
}
[CompilerGenerated]
private sealed class <CameraOutTranspiler>d__6 : IEnumerable<CodeInstruction>, IEnumerable, IEnumerator<CodeInstruction>, IEnumerator, IDisposable
{
private int <>1__state;
private CodeInstruction <>2__current;
private int <>l__initialThreadId;
private IEnumerable<CodeInstruction> instructions;
public IEnumerable<CodeInstruction> <>3__instructions;
private IEnumerator<CodeInstruction> <>s__1;
private CodeInstruction <instruction>5__2;
CodeInstruction IEnumerator<CodeInstruction>.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
object IEnumerator.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
[DebuggerHidden]
public <CameraOutTranspiler>d__6(int <>1__state)
{
this.<>1__state = <>1__state;
<>l__initialThreadId = Environment.CurrentManagedThreadId;
}
[DebuggerHidden]
void IDisposable.Dispose()
{
int num = <>1__state;
if (num == -3 || num == 1)
{
try
{
}
finally
{
<>m__Finally1();
}
}
<>s__1 = null;
<instruction>5__2 = null;
<>1__state = -2;
}
private bool MoveNext()
{
try
{
switch (<>1__state)
{
default:
return false;
case 0:
<>1__state = -1;
<>s__1 = instructions.GetEnumerator();
<>1__state = -3;
break;
case 1:
<>1__state = -3;
<instruction>5__2 = null;
break;
}
if (<>s__1.MoveNext())
{
<instruction>5__2 = <>s__1.Current;
if (<instruction>5__2.opcode == OpCodes.Ldc_R4 && <instruction>5__2.operand != null && <instruction>5__2.operand.Equals(1f))
{
<instruction>5__2.operand = 3f;
}
<>2__current = <instruction>5__2;
<>1__state = 1;
return true;
}
<>m__Finally1();
<>s__1 = null;
return false;
}
catch
{
//try-fault
((IDisposable)this).Dispose();
throw;
}
}
bool IEnumerator.MoveNext()
{
//ILSpy generated this explicit interface implementation from .override directive in MoveNext
return this.MoveNext();
}
private void <>m__Finally1()
{
<>1__state = -1;
if (<>s__1 != null)
{
<>s__1.Dispose();
}
}
[DebuggerHidden]
void IEnumerator.Reset()
{
throw new NotSupportedException();
}
[DebuggerHidden]
IEnumerator<CodeInstruction> IEnumerable<CodeInstruction>.GetEnumerator()
{
<CameraOutTranspiler>d__6 <CameraOutTranspiler>d__;
if (<>1__state == -2 && <>l__initialThreadId == Environment.CurrentManagedThreadId)
{
<>1__state = 0;
<CameraOutTranspiler>d__ = this;
}
else
{
<CameraOutTranspiler>d__ = new <CameraOutTranspiler>d__6(0);
}
<CameraOutTranspiler>d__.instructions = <>3__instructions;
return <CameraOutTranspiler>d__;
}
[DebuggerHidden]
IEnumerator IEnumerable.GetEnumerator()
{
return ((IEnumerable<CodeInstruction>)this).GetEnumerator();
}
}
[CompilerGenerated]
private sealed class <SetActiveButtonTranspiler>d__4 : IEnumerable<CodeInstruction>, IEnumerable, IEnumerator<CodeInstruction>, IEnumerator, IDisposable
{
private int <>1__state;
private CodeInstruction <>2__current;
private int <>l__initialThreadId;
private IEnumerable<CodeInstruction> instructions;
public IEnumerable<CodeInstruction> <>3__instructions;
private List<CodeInstruction> <codes>5__1;
private bool <patched>5__2;
private int <i>5__3;
private bool <canMatch>5__4;
private MethodInfo <getBaseHatCount>5__5;
private Label <skipLabel>5__6;
private MethodInfo <getOverrideHatCount>5__7;
private CodeInstruction <nop>5__8;
CodeInstruction IEnumerator<CodeInstruction>.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
object IEnumerator.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
[DebuggerHidden]
public <SetActiveButtonTranspiler>d__4(int <>1__state)
{
this.<>1__state = <>1__state;
<>l__initialThreadId = Environment.CurrentManagedThreadId;
}
[DebuggerHidden]
void IDisposable.Dispose()
{
<codes>5__1 = null;
<getBaseHatCount>5__5 = null;
<getOverrideHatCount>5__7 = null;
<nop>5__8 = null;
<>1__state = -2;
}
private bool MoveNext()
{
//IL_0276: Unknown result type (might be due to invalid IL or missing references)
//IL_0280: Expected O, but got Unknown
//IL_02b8: Unknown result type (might be due to invalid IL or missing references)
//IL_02c2: Expected O, but got Unknown
//IL_02ef: Unknown result type (might be due to invalid IL or missing references)
//IL_02f9: Expected O, but got Unknown
//IL_0331: Unknown result type (might be due to invalid IL or missing references)
//IL_033b: Expected O, but got Unknown
//IL_0352: Unknown result type (might be due to invalid IL or missing references)
//IL_035c: Expected O, but got Unknown
//IL_0373: Unknown result type (might be due to invalid IL or missing references)
//IL_037d: Expected O, but got Unknown
switch (<>1__state)
{
default:
return false;
case 0:
<>1__state = -1;
<codes>5__1 = instructions.ToList();
<patched>5__2 = false;
<i>5__3 = 0;
break;
case 1:
<>1__state = -1;
<>2__current = <codes>5__1[<i>5__3 + 1];
<>1__state = 2;
return true;
case 2:
<>1__state = -1;
<>2__current = <codes>5__1[<i>5__3 + 2];
<>1__state = 3;
return true;
case 3:
<>1__state = -1;
<>2__current = new CodeInstruction(OpCodes.Dup, (object)null);
<>1__state = 4;
return true;
case 4:
<>1__state = -1;
<getBaseHatCount>5__5 = AccessTools.Method(typeof(PassportManagerPatch), "GetBaseHatCount", (Type[])null, (Type[])null);
<>2__current = new CodeInstruction(OpCodes.Call, (object)<getBaseHatCount>5__5);
<>1__state = 5;
return true;
case 5:
<>1__state = -1;
<skipLabel>5__6 = default(Label);
<>2__current = new CodeInstruction(OpCodes.Ble_S, (object)<skipLabel>5__6);
<>1__state = 6;
return true;
case 6:
<>1__state = -1;
<getOverrideHatCount>5__7 = AccessTools.Method(typeof(PassportManagerPatch), "GetOverrideHatCount", (Type[])null, (Type[])null);
<>2__current = new CodeInstruction(OpCodes.Call, (object)<getOverrideHatCount>5__7);
<>1__state = 7;
return true;
case 7:
<>1__state = -1;
<>2__current = new CodeInstruction(OpCodes.Sub, (object)null);
<>1__state = 8;
return true;
case 8:
<>1__state = -1;
<nop>5__8 = new CodeInstruction(OpCodes.Nop, (object)null);
<nop>5__8.labels.Add(<skipLabel>5__6);
<>2__current = <nop>5__8;
<>1__state = 9;
return true;
case 9:
<>1__state = -1;
<>2__current = <codes>5__1[<i>5__3 + 3];
<>1__state = 10;
return true;
case 10:
<>1__state = -1;
<i>5__3 += 3;
goto IL_0414;
case 11:
{
<>1__state = -1;
goto IL_0414;
}
IL_0414:
<i>5__3++;
break;
}
if (<i>5__3 < <codes>5__1.Count)
{
<canMatch>5__4 = <i>5__3 <= <codes>5__1.Count - 4;
if (<canMatch>5__4 && <codes>5__1[<i>5__3].opcode == OpCodes.Ldloc_0 && <codes>5__1[<i>5__3 + 1].opcode == OpCodes.Ldfld && <codes>5__1[<i>5__3 + 1].operand != null && <codes>5__1[<i>5__3 + 1].operand.ToString().Contains("customizationData") && <codes>5__1[<i>5__3 + 2].opcode == OpCodes.Ldfld && <codes>5__1[<i>5__3 + 2].operand != null && <codes>5__1[<i>5__3 + 2].operand.ToString().Contains("currentHat") && IsStloc(<codes>5__1[<i>5__3 + 3]))
{
<patched>5__2 = true;
<>2__current = <codes>5__1[<i>5__3];
<>1__state = 1;
return true;
}
<>2__current = <codes>5__1[<i>5__3];
<>1__state = 11;
return true;
}
if (!<patched>5__2)
{
Plugin.Logger.LogWarning((object)"[TooManyHats] SetActiveButton transpiler did not find currentHat pattern.");
}
return false;
}
bool IEnumerator.MoveNext()
{
//ILSpy generated this explicit interface implementation from .override directive in MoveNext
return this.MoveNext();
}
[DebuggerHidden]
void IEnumerator.Reset()
{
throw new NotSupportedException();
}
[DebuggerHidden]
IEnumerator<CodeInstruction> IEnumerable<CodeInstruction>.GetEnumerator()
{
<SetActiveButtonTranspiler>d__4 <SetActiveButtonTranspiler>d__;
if (<>1__state == -2 && <>l__initialThreadId == Environment.CurrentManagedThreadId)
{
<>1__state = 0;
<SetActiveButtonTranspiler>d__ = this;
}
else
{
<SetActiveButtonTranspiler>d__ = new <SetActiveButtonTranspiler>d__4(0);
}
<SetActiveButtonTranspiler>d__.instructions = <>3__instructions;
return <SetActiveButtonTranspiler>d__;
}
[DebuggerHidden]
IEnumerator IEnumerable.GetEnumerator()
{
return ((IEnumerable<CodeInstruction>)this).GetEnumerator();
}
}
private static int GetBaseHatCount()
{
return Plugin.BaseHatCount;
}
private static int GetOverrideHatCount()
{
return Plugin.OverrideHatCount;
}
private static bool IsStloc(CodeInstruction code)
{
return code.opcode == OpCodes.Stloc || code.opcode == OpCodes.Stloc_S || code.opcode == OpCodes.Stloc_0 || code.opcode == OpCodes.Stloc_1 || code.opcode == OpCodes.Stloc_2 || code.opcode == OpCodes.Stloc_3;
}
[HarmonyPatch(typeof(PassportManager), "Awake")]
[HarmonyPostfix]
public static void AwakePostfix(PassportManager __instance)
{
//IL_011c: Unknown result type (might be due to invalid IL or missing references)
//IL_0142: Unknown result type (might be due to invalid IL or missing references)
Customization component = ((Component)__instance).GetComponent<Customization>();
if ((Object)(object)component == (Object)null)
{
Plugin.Logger.LogError((object)"[TooManyHats] Missing Customization component!");
return;
}
List<CustomizationOption> list = new List<CustomizationOption>((IEnumerable<CustomizationOption>)(((object)component.hats) ?? ((object)new CustomizationOption[0])));
Plugin.BaseHatCount = list.Count;
Plugin.OverrideHatCount = 0;
if (component.fits != null)
{
CustomizationOption[] fits = component.fits;
foreach (CustomizationOption val in fits)
{
if ((Object)(object)val != (Object)null && val.overrideHat)
{
Plugin.OverrideHatCount++;
}
}
}
if (Plugin.hats == null || Plugin.hats.Count == 0)
{
Plugin.Logger.LogWarning((object)"[TooManyHats] No hats found to inject.");
component.hats = list.ToArray();
return;
}
foreach (Plugin.HatEntry hat in Plugin.hats)
{
if (hat != null)
{
CustomizationOption val2 = ScriptableObject.CreateInstance<CustomizationOption>();
val2.requiredAchievement = (ACHIEVEMENTTYPE)0;
((Object)val2).name = hat.Name;
val2.texture = (Texture)(object)hat.Icon;
val2.type = (Type)50;
list.Add(val2);
Plugin.Logger.LogDebug((object)("[TooManyHats] Added hat option '" + hat.Name + "'"));
}
}
component.hats = list.ToArray();
Plugin.Logger.LogInfo((object)($"[TooManyHats] Awake complete. BaseHatCount={Plugin.BaseHatCount}, " + $"OverrideHatCount={Plugin.OverrideHatCount}, TotalHats={component.hats.Length}"));
}
[IteratorStateMachine(typeof(<SetActiveButtonTranspiler>d__4))]
[HarmonyPatch(typeof(PassportManager), "SetActiveButton")]
[HarmonyTranspiler]
public static IEnumerable<CodeInstruction> SetActiveButtonTranspiler(IEnumerable<CodeInstruction> instructions)
{
//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
return new <SetActiveButtonTranspiler>d__4(-2)
{
<>3__instructions = instructions
};
}
[IteratorStateMachine(typeof(<CameraInTranspiler>d__5))]
[HarmonyPatch(typeof(PassportManager), "CameraIn")]
[HarmonyTranspiler]
public static IEnumerable<CodeInstruction> CameraInTranspiler(IEnumerable<CodeInstruction> instructions)
{
//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
return new <CameraInTranspiler>d__5(-2)
{
<>3__instructions = instructions
};
}
[IteratorStateMachine(typeof(<CameraOutTranspiler>d__6))]
[HarmonyPatch(typeof(PassportManager), "CameraOut")]
[HarmonyTranspiler]
public static IEnumerable<CodeInstruction> CameraOutTranspiler(IEnumerable<CodeInstruction> instructions)
{
//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
return new <CameraOutTranspiler>d__6(-2)
{
<>3__instructions = instructions
};
}
}
public class PeakHandlePatch
{
[HarmonyPatch(typeof(PeakHandler), "SetCosmetics")]
[HarmonyPrefix]
private static void SetCosmetics(PeakHandler __instance, List<Character> characters)
{
if (!CustomizationRefsHelper.SyncCustomHats(__instance.firstCutsceneScout))
{
Plugin.Logger.LogError((object)"Something went wrong in PeakHandlePatch [firstCutsceneScout]...");
}
for (int i = 0; i < __instance.cutsceneScoutRefs.Count(); i++)
{
if (!CustomizationRefsHelper.SyncCustomHats(__instance.cutsceneScoutRefs[i]))
{
Plugin.Logger.LogError((object)string.Format("Something went wrong in {0} [cutsceneScoutRefs-{1}]...", "PeakHandlePatch", i));
}
}
}
}
public class PlayerCustomizationDummyPatch
{
[HarmonyPatch(typeof(PlayerCustomizationDummy), "SetPlayerHat")]
[HarmonyPrefix]
private static void SetPlayerHat(PlayerCustomizationDummy __instance, int index)
{
if (!CustomizationRefsHelper.SyncCustomHats(__instance.refs))
{
Plugin.Logger.LogError((object)"Something went wrong in SetPlayerHat patch...");
}
}
}
}
namespace TooManyHats.Helpers
{
public class CustomizationRefsHelper
{
public const string REF_TO_HATS_PATH = "Armature/Hip/Mid/AimJoint/Torso/Head/Hat";
public static bool SyncCustomHats(CustomizationRefs dstRefs, CustomizationRefs srcRefs = null)
{
if ((Object)(object)srcRefs == (Object)null)
{
Character localCharacter = Character.localCharacter;
CharacterCustomization val = default(CharacterCustomization);
if (!Object.op_Implicit((Object)(object)localCharacter) || !((Component)localCharacter).TryGetComponent<CharacterCustomization>(ref val))
{
Plugin.Logger.LogError((object)"Cannot get [LocalCharacter] or its' [CustomizationRefs] ...");
return false;
}
srcRefs = val.refs;
}
Renderer[] playerHats = srcRefs.playerHats;
Renderer[] playerHats2 = dstRefs.playerHats;
if (playerHats.Length == playerHats2.Length)
{
return true;
}
Renderer val2 = playerHats2.FirstOrDefault();
if (!Object.op_Implicit((Object)(object)val2))
{
Plugin.Logger.LogError((object)"Cannot find renders in dstPlayerHats...");
return false;
}
int layer = ((Component)val2).gameObject.layer;
Transform val3 = ((Component)srcRefs).transform.Find("Armature/Hip/Mid/AimJoint/Torso/Head/Hat");
Transform val4 = ((Component)dstRefs).transform.Find("Armature/Hip/Mid/AimJoint/Torso/Head/Hat");
List<Renderer> list = new List<Renderer>(playerHats2);
for (int i = playerHats2.Length; i < playerHats.Length; i++)
{
Transform val5 = ((Component)playerHats[i]).transform;
while ((Object)(object)val5.parent != (Object)(object)val3)
{
val5 = val5.parent;
}
GameObject val6 = Object.Instantiate<GameObject>(((Component)val5).gameObject, val4, false);
((Object)val6).name = ((Object)val5).name;
Renderer componentInChildren = val6.GetComponentInChildren<Renderer>(true);
((Component)componentInChildren).gameObject.layer = layer;
list.Add(componentInChildren);
}
dstRefs.playerHats = list.ToArray();
return true;
}
}
}