Decompiled source of Cubs Gunsmith v0.1.0

CubsGunsmith.dll

Decompiled a day ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Resources;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using System.Text.Json;
using HarmonyLib;
using Il2CppInterop.Runtime;
using Il2CppInterop.Runtime.InteropTypes;
using Il2CppInterop.Runtime.InteropTypes.Arrays;
using Il2CppSystem;
using Il2CppTMPro;
using MelonLoader;
using MelonLoader.Preferences;
using Microsoft.CodeAnalysis;
using UnityEngine;
using UnityEngine.AddressableAssets;
using UnityEngine.Events;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Controls;
using UnityEngine.ResourceManagement.AsyncOperations;
using UnityEngine.UI;
using WeaponCustomization;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: MelonInfo(typeof(Core), "Cub's Gunsmith", "0.1.0", "GraciousCub5622", null)]
[assembly: MelonGame("Keepsake Games", "Jump Space")]
[assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")]
[assembly: AssemblyCompany("CubsGunsmith")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0+5023b42bc8151c5abddb7dac5875f3cf56d3e8b3")]
[assembly: AssemblyProduct("CubsGunsmith")]
[assembly: AssemblyTitle("CubsGunsmith")]
[assembly: NeutralResourcesLanguage("en-US")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.0.0.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[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 WeaponCustomization
{
	public class Core : MelonMod
	{
		private struct WeaponCosmetics
		{
			public int ScopeIndex;

			public int ColorIndex;

			public bool HasScope;

			public bool HasColor;
		}

		private static class MCol
		{
			public static readonly Color Panel = new Color(0.039f, 0.111f, 0.132f, 0.78f);

			public static readonly Color TitleBar = new Color(0.095f, 0.111f, 0.142f, 0.88f);

			public static readonly Color ColHdr = new Color(0.234f, 0.276f, 0.276f, 0.82f);

			public static readonly Color RowDark = new Color(0.039f, 0.111f, 0.132f, 0.75f);

			public static readonly Color RowLight = new Color(0.056f, 0.156f, 0.189f, 0.8f);

			public static readonly Color RowHover = new Color(0.082f, 0.2f, 0.24f, 0.85f);

			public static readonly Color Sel = new Color(0f, 0.246f, 0.33f, 0.82f);

			public static readonly Color SelBar = new Color(0.78f, 0.922f, 0.922f, 1f);

			public static readonly Color Accent = new Color(0.78f, 0.922f, 0.922f, 1f);

			public static readonly Color HdrText = new Color(0.78f, 0.922f, 0.922f, 1f);

			public static readonly Color Text = new Color(0.78f, 0.922f, 0.922f, 0.9f);

			public static readonly Color Muted = new Color(0.5f, 0.62f, 0.65f, 1f);
		}

		private static Dictionary<string, WeaponCosmetics> weaponCosmetics = new Dictionary<string, WeaponCosmetics>();

		private static MelonPreferences_Category prefCategory;

		private static MelonPreferences_Entry<string> prefData;

		private static MelonPreferences_Entry<string> prefMenuKey;

		private static readonly JsonSerializerOptions jsonOpts = new JsonSerializerOptions
		{
			IncludeFields = true
		};

		private static Type globalType;

		private static Type weaponCosmeticsType;

		private static Type cosmeticsHandlerType;

		private static Type cosmeticDataType;

		private static Type colorSwatchType;

		private static Type guiKeybindBtnType;

		private static Key menuKey = (Key)97;

		private static bool rebinding;

		private static int rebindFrame = -1;

		private static bool keybindInjected;

		private static GameObject injectedKeybindBtn;

		private static TMP_Text keybindKeyLabel;

		private static Texture2D gamePanelTex;

		private static RectOffset gamePanelBorder;

		private static bool assetsLoaded;

		private static List<object> cachedScopes = new List<object>();

		private static List<object> cachedColors = new List<object>();

		private static Component weaponHandler;

		private static int lastWeaponInstanceId = -1;

		private static float lastReapplyTime = -999f;

		private static int reapplyGeneration;

		private static bool menuOpen;

		private static float scopeScrollY;

		private static float colorScrollY;

		private static CursorLockMode savedLock;

		private static bool savedCursorVis;

		private static readonly Dictionary<int, Texture2D> scopePreviews = new Dictionary<int, Texture2D>();

		private static readonly Dictionary<int, Texture2D> colorPreviews = new Dictionary<int, Texture2D>();

		private static bool previewsLoaded;

		private static GUIStyle sPanel;

		private static GUIStyle sTitleLabel;

		private static GUIStyle sHintLabel;

		private static GUIStyle sNoWeapLabel;

		private static GUIStyle sColHdr;

		private static GUIStyle sRowNormal;

		private static GUIStyle sRowSel;

		private static bool stylesInited;

		public override void OnInitializeMelon()
		{
			//IL_0084: Unknown result type (might be due to invalid IL or missing references)
			//IL_0085: Unknown result type (might be due to invalid IL or missing references)
			prefCategory = MelonPreferences.CreateCategory("WeaponCustomization");
			prefData = prefCategory.CreateEntry<string>("CosmeticsData", "{}", (string)null, (string)null, false, false, (ValueValidator)null, (string)null);
			prefMenuKey = prefCategory.CreateEntry<string>("MenuKey", "F4", (string)null, (string)null, false, false, (ValueValidator)null, (string)null);
			try
			{
				Dictionary<string, WeaponCosmetics> dictionary = JsonSerializer.Deserialize<Dictionary<string, WeaponCosmetics>>(prefData.Value, jsonOpts);
				if (dictionary != null)
				{
					weaponCosmetics = dictionary;
				}
			}
			catch
			{
			}
			if (Enum.TryParse<Key>(prefMenuKey.Value, ignoreCase: true, out Key result))
			{
				menuKey = result;
			}
			Assembly[] assemblies = AppDomain.CurrentDomain.GetAssemblies();
			foreach (Assembly assembly in assemblies)
			{
				try
				{
					Type[] types = assembly.GetTypes();
					foreach (Type type in types)
					{
						string name = type.Name;
						string text = type.FullName ?? "";
						if (name == "Global")
						{
							globalType = type;
							continue;
						}
						if (name == "PersistentScriptableLibrary" && text.Contains("Cosmetic"))
						{
							weaponCosmeticsType = type;
							continue;
						}
						switch (name)
						{
						case "CosmeticsHandler":
							cosmeticsHandlerType = type;
							break;
						case "CosmeticData":
							cosmeticDataType = type;
							break;
						case "ColorSwatch":
							colorSwatchType = type;
							break;
						case "GUI_Keybinding_Button":
							guiKeybindBtnType = type;
							break;
						}
					}
				}
				catch
				{
				}
			}
		}

		private static void SaveCosmetics()
		{
			try
			{
				prefData.Value = JsonSerializer.Serialize(weaponCosmetics, jsonOpts);
				MelonPreferences.Save();
			}
			catch
			{
			}
		}

		public override void OnUpdate()
		{
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
			if (!rebinding && Time.frameCount != rebindFrame)
			{
				try
				{
					if (((ButtonControl)Keyboard.current[menuKey]).wasPressedThisFrame)
					{
						ToggleMenu();
					}
				}
				catch
				{
				}
			}
			if (!assetsLoaded && Time.frameCount % 60 == 0)
			{
				TryLoadAssets();
			}
			if (!keybindInjected)
			{
				if (Time.frameCount % 60 == 0)
				{
					TryInjectRow();
				}
			}
			else if ((Object)(object)injectedKeybindBtn == (Object)null || !Object.op_Implicit((Object)(object)injectedKeybindBtn))
			{
				keybindInjected = false;
				keybindKeyLabel = null;
			}
			else if (!rebinding && (Object)(object)keybindKeyLabel != (Object)null)
			{
				keybindKeyLabel.SetText(KeyDisplayName(menuKey), true);
			}
			if (menuOpen)
			{
				Cursor.lockState = (CursorLockMode)0;
				Cursor.visible = true;
			}
			try
			{
				object localPlayer = GetLocalPlayer();
				if (localPlayer == null)
				{
					return;
				}
				object persistentPickupable = GetPersistentPickupable(localPlayer);
				object obj2 = ((persistentPickupable is Component) ? persistentPickupable : null);
				int num = ((obj2 != null) ? ((Object)((Component)obj2).gameObject).GetInstanceID() : (-1));
				if (num != lastWeaponInstanceId)
				{
					lastWeaponInstanceId = num;
					weaponHandler = null;
					reapplyGeneration++;
					if (num != -1)
					{
						MelonCoroutines.Start(ReapplyAfterDelay(localPlayer, num, reapplyGeneration, 0));
					}
				}
				else if (num != -1 && (Object)(object)weaponHandler != (Object)null && !Object.op_Implicit((Object)(object)weaponHandler) && Time.time - lastReapplyTime > 3f)
				{
					weaponHandler = null;
					reapplyGeneration++;
					MelonCoroutines.Start(ReapplyAfterDelay(localPlayer, num, reapplyGeneration, 10));
				}
			}
			catch
			{
			}
		}

		private static IEnumerator ReapplyAfterDelay(object player, int instanceId, int generation, int startDelay)
		{
			for (int i = 0; i < startDelay; i++)
			{
				yield return null;
			}
			bool succeeded = false;
			int postSuccessRetries = 0;
			int[] array = new int[9] { 5, 10, 15, 60, 120, 120, 120, 120, 120 };
			int[] array2 = array;
			foreach (int d in array2)
			{
				for (int j = 0; j < d; j++)
				{
					yield return null;
				}
				if (reapplyGeneration != generation)
				{
					break;
				}
				object persistentPickupable = GetPersistentPickupable(player);
				object obj = ((persistentPickupable is Component) ? persistentPickupable : null);
				if (((obj != null) ? ((Object)((Component)obj).gameObject).GetInstanceID() : (-1)) != instanceId)
				{
					break;
				}
				string moduleKey = GetModuleKey(player);
				if (moduleKey == null || !weaponCosmetics.TryGetValue(moduleKey, out var value))
				{
					if (succeeded)
					{
						break;
					}
					continue;
				}
				weaponHandler = null;
				if (GetAvailableScopes().Count == 0 || (Object)(object)GetWeaponCosmeticsHandler(player) == (Object)null)
				{
					if (succeeded)
					{
						break;
					}
					continue;
				}
				lastReapplyTime = Time.time;
				if (value.HasScope)
				{
					ApplyScopeIndex(player, value.ScopeIndex);
				}
				if (value.HasColor)
				{
					ApplyColorIndex(player, value.ColorIndex);
				}
				if (succeeded)
				{
					int num = postSuccessRetries + 1;
					postSuccessRetries = num;
					if (num >= 5)
					{
						break;
					}
				}
				succeeded = true;
			}
		}

		private static object GetLocalPlayer()
		{
			try
			{
				if (globalType == null)
				{
					return null;
				}
				object obj = AccessTools.Property(globalType, "PlayerHandler")?.GetValue(null);
				if (obj == null)
				{
					return null;
				}
				return AccessTools.Property(obj.GetType(), "localPlayerController")?.GetValue(obj);
			}
			catch
			{
				return null;
			}
		}

		private static object GetPersistentPickupable(object player)
		{
			try
			{
				object obj = AccessTools.Property(player.GetType(), "ItemHandler")?.GetValue(player);
				if (obj == null)
				{
					return null;
				}
				return AccessTools.Property(obj.GetType(), "ItemHeldPersistentPickupable")?.GetValue(obj);
			}
			catch
			{
				return null;
			}
		}

		private static GameObject GetWeaponVisualGO(object player)
		{
			try
			{
				object? obj = AccessTools.Property(player.GetType(), "ItemPreviewController")?.GetValue(player);
				object? obj2 = ((obj is Component) ? obj : null);
				return (obj2 != null) ? ((Component)obj2).gameObject : null;
			}
			catch
			{
				return null;
			}
		}

		private static Component GetWeaponCosmeticsHandler(object player)
		{
			if ((Object)(object)weaponHandler != (Object)null && Object.op_Implicit((Object)(object)weaponHandler))
			{
				return weaponHandler;
			}
			weaponHandler = null;
			if (cosmeticsHandlerType == null)
			{
				return null;
			}
			GameObject weaponVisualGO = GetWeaponVisualGO(player);
			if ((Object)(object)weaponVisualGO == (Object)null)
			{
				return null;
			}
			weaponHandler = weaponVisualGO.GetComponentInChildren(Il2CppType.From(cosmeticsHandlerType), true);
			return weaponHandler;
		}

		private static GameObject GetWeaponRoot(object player)
		{
			Component weaponCosmeticsHandler = GetWeaponCosmeticsHandler(player);
			if ((Object)(object)weaponCosmeticsHandler != (Object)null)
			{
				return weaponCosmeticsHandler.gameObject;
			}
			object persistentPickupable = GetPersistentPickupable(player);
			object obj = ((persistentPickupable is Component) ? persistentPickupable : null);
			return ((obj != null) ? ((Component)obj).gameObject : null) ?? GetWeaponVisualGO(player);
		}

		private static string GetModuleKey(object player)
		{
			try
			{
				object persistentPickupable = GetPersistentPickupable(player);
				if (persistentPickupable == null)
				{
					return null;
				}
				object obj = AccessTools.Property(persistentPickupable.GetType(), "m_PickupableItemBlackboardData")?.GetValue(persistentPickupable);
				object obj2 = AccessTools.Property(obj?.GetType(), "m_GeneratedItem")?.GetValue(obj);
				object obj3 = AccessTools.Property(obj2?.GetType(), "Value")?.GetValue(obj2);
				object obj4 = AccessTools.Property(obj3?.GetType(), "m_Modules")?.GetValue(obj3);
				if (obj4 == null)
				{
					return null;
				}
				int num = (int)(AccessTools.Property(obj4.GetType(), "Length")?.GetValue(obj4) ?? ((object)0));
				if (num == 0)
				{
					return null;
				}
				PropertyInfo property = obj4.GetType().GetProperty("Item");
				List<string> list = new List<string>();
				for (int i = 0; i < num; i++)
				{
					object obj5 = property?.GetValue(obj4, new object[1] { i });
					string text = AccessTools.Property(obj5?.GetType(), "m_ModuleGuid")?.GetValue(obj5)?.ToString();
					if (text != null)
					{
						list.Add(text);
					}
				}
				if (list.Count == 0)
				{
					return null;
				}
				list.Sort();
				return string.Join("|", list);
			}
			catch
			{
				return null;
			}
		}

		private static List<object> IterateIl2CppList(object list)
		{
			List<object> list2 = new List<object>();
			if (list == null)
			{
				return list2;
			}
			int num = (int)(list.GetType().GetProperty("Count")?.GetValue(list) ?? ((object)0));
			PropertyInfo property = list.GetType().GetProperty("Item");
			if (property == null)
			{
				return list2;
			}
			for (int i = 0; i < num; i++)
			{
				list2.Add(property.GetValue(list, new object[1] { i }));
			}
			return list2;
		}

		private static void PopulateCosmeticLists()
		{
			if (weaponCosmeticsType == null)
			{
				return;
			}
			try
			{
				List<object> list = IterateIl2CppList(AccessTools.Property(weaponCosmeticsType, "AllCosmetics")?.GetValue(null));
				cachedScopes.Clear();
				cachedColors.Clear();
				foreach (object item in list)
				{
					string text = AccessTools.Property(item.GetType(), "m_SlotType")?.GetValue(item)?.ToString() ?? "";
					if (text.Contains("Scope"))
					{
						cachedScopes.Add(item);
					}
					else if (text.Contains("Color"))
					{
						cachedColors.Add(item);
					}
				}
				previewsLoaded = false;
			}
			catch
			{
			}
		}

		private static List<object> GetAvailableScopes()
		{
			if (cachedScopes.Count == 0)
			{
				PopulateCosmeticLists();
			}
			return cachedScopes;
		}

		private static List<object> GetAvailableColors()
		{
			if (cachedColors.Count == 0)
			{
				PopulateCosmeticLists();
			}
			return cachedColors;
		}

		private static void ApplyScopeIndex(object player, int index)
		{
			List<object> availableScopes = GetAvailableScopes();
			if (index < availableScopes.Count)
			{
				ApplyScope(player, availableScopes[index], GetModuleKey(player));
			}
		}

		private static void ApplyScope(object player, object cd, string moduleKey)
		{
			try
			{
				Component weaponCosmeticsHandler = GetWeaponCosmeticsHandler(player);
				if ((Object)(object)weaponCosmeticsHandler == (Object)null || cosmeticsHandlerType == null || cosmeticDataType == null)
				{
					return;
				}
				string text = AccessTools.Property(cd.GetType(), "name")?.GetValue(cd)?.ToString();
				string text2 = null;
				object obj = AccessTools.Property(weaponCosmeticsType, "CosmeticsByGuid")?.GetValue(null);
				if (obj != null)
				{
					object obj2 = AccessTools.Method(obj.GetType(), "GetEnumerator", (Type[])null, (Type[])null)?.Invoke(obj, null);
					MethodInfo methodInfo = AccessTools.Method(obj2?.GetType(), "MoveNext", (Type[])null, (Type[])null);
					PropertyInfo propertyInfo = AccessTools.Property(obj2?.GetType(), "Current");
					while (obj2 != null && (bool)methodInfo.Invoke(obj2, null))
					{
						object value = propertyInfo.GetValue(obj2);
						object obj3 = AccessTools.Property(value?.GetType(), "Value")?.GetValue(value);
						if (AccessTools.Property(obj3?.GetType(), "name")?.GetValue(obj3)?.ToString() == text)
						{
							text2 = AccessTools.Property(value?.GetType(), "Key")?.GetValue(value)?.ToString();
							break;
						}
					}
				}
				if (text2 == null)
				{
					return;
				}
				object obj4;
				try
				{
					obj4 = Activator.CreateInstance(typeof(AssetReferenceT<>).MakeGenericType(cosmeticDataType), text2);
				}
				catch
				{
					return;
				}
				FindSlotByTypeWithIndex(weaponCosmeticsHandler, "scope", out var foundSlot, out var foundIndex);
				if (foundIndex < 0)
				{
					return;
				}
				object? obj6 = AccessTools.Property(foundSlot?.GetType(), "m_TargetTransform")?.GetValue(foundSlot);
				Transform val = (Transform)((obj6 is Transform) ? obj6 : null);
				object? obj7 = AccessTools.Property(foundSlot?.GetType(), "m_ScopeSecondaryTransform")?.GetValue(foundSlot);
				Transform val2 = (Transform)((obj7 is Transform) ? obj7 : null);
				Transform[] array = (Transform[])(object)new Transform[2] { val, val2 };
				foreach (Transform val3 in array)
				{
					if (!((Object)(object)val3 == (Object)null))
					{
						for (int num = val3.childCount - 1; num >= 0; num--)
						{
							Object.Destroy((Object)(object)((Component)val3.GetChild(num)).gameObject);
						}
					}
				}
				MethodInfo method = cosmeticsHandlerType.GetMethod("ApplyCosmeticAsync", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
				if (!(method == null))
				{
					method.Invoke(RewrapAs(cosmeticsHandlerType, weaponCosmeticsHandler), new object[4] { foundIndex, obj4, -1, false });
					MelonCoroutines.Start(FixScopeLayer(val, val2, 29));
				}
			}
			catch
			{
			}
		}

		private static IEnumerator FixScopeLayer(Transform socket, Transform socketAlt, int layer)
		{
			for (int i = 0; i < 120; i++)
			{
				if ((Object)(object)socket != (Object)null && socket.childCount > 0)
				{
					break;
				}
				if ((Object)(object)socketAlt != (Object)null && socketAlt.childCount > 0)
				{
					break;
				}
				yield return null;
			}
			SetAll();
			for (int i = 0; i < 30; i++)
			{
				yield return null;
			}
			SetAll();
			for (int i = 0; i < 60; i++)
			{
				yield return null;
				Transform[] array = (Transform[])(object)new Transform[2] { socket, socketAlt };
				foreach (Transform val in array)
				{
					if ((Object)(object)val == (Object)null)
					{
						continue;
					}
					for (int k = 0; k < val.childCount; k++)
					{
						Transform child = val.GetChild(k);
						if (((Component)child).gameObject.layer != layer)
						{
							SetLayerRecursive(child, layer);
						}
					}
				}
			}
			void SetAll()
			{
				Transform[] array2 = (Transform[])(object)new Transform[2] { socket, socketAlt };
				foreach (Transform val2 in array2)
				{
					if (!((Object)(object)val2 == (Object)null))
					{
						for (int m = 0; m < val2.childCount; m++)
						{
							SetLayerRecursive(val2.GetChild(m), layer);
						}
					}
				}
			}
		}

		private static void SetLayerRecursive(Transform t, int layer)
		{
			if (!((Object)(object)t == (Object)null))
			{
				if (!((Object)t).name.Contains("Collision") && !((Object)t).name.Contains("ShotClip"))
				{
					((Component)t).gameObject.layer = layer;
				}
				for (int i = 0; i < t.childCount; i++)
				{
					SetLayerRecursive(t.GetChild(i), layer);
				}
			}
		}

		private static void ApplyColorIndex(object player, int index)
		{
			List<object> availableColors = GetAvailableColors();
			if (index < availableColors.Count)
			{
				ApplyColor(player, availableColors[index]);
			}
		}

		private static void ApplyColor(object player, object cd)
		{
			try
			{
				Component weaponCosmeticsHandler = GetWeaponCosmeticsHandler(player);
				Type type = cd.GetType();
				if ((Object)(object)weaponCosmeticsHandler != (Object)null && cosmeticsHandlerType != null && cosmeticDataType != null)
				{
					object obj = FindSlotByType(weaponCosmeticsHandler, "color") ?? FindSlotByType(weaponCosmeticsHandler, "skin");
					MethodInfo method = cosmeticsHandlerType.GetMethod("ApplyColorSwatchesAsync", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
					if (obj != null && method != null)
					{
						method.Invoke(RewrapAs(cosmeticsHandlerType, weaponCosmeticsHandler), new object[2]
						{
							obj,
							RewrapAs(cosmeticDataType, cd)
						});
						return;
					}
				}
				bool flag = (bool)(AccessTools.Property(type, "IsColorSwap")?.GetValue(cd) ?? ((object)false));
				bool flag2 = (bool)(AccessTools.Property(type, "IsMaterialSwap")?.GetValue(cd) ?? ((object)false));
				List<Renderer> weaponRenderers = GetWeaponRenderers(player);
				if (flag && colorSwatchType != null)
				{
					Texture2D val = LoadSwatchLookup(AccessTools.Property(type, "m_MainColor")?.GetValue(cd));
					Texture2D val2 = LoadSwatchLookup(AccessTools.Property(type, "m_SecondaryColor")?.GetValue(cd));
					Texture2D val3 = LoadSwatchLookup(AccessTools.Property(type, "m_DetailColor")?.GetValue(cd));
					{
						foreach (Renderer item in weaponRenderers)
						{
							Il2CppReferenceArray<Material> materials = item.materials;
							for (int i = 0; i < ((Il2CppArrayBase<Material>)(object)materials).Length; i++)
							{
								if (!((Object)(object)((Il2CppArrayBase<Material>)(object)materials)[i] == (Object)null))
								{
									if ((Object)(object)val != (Object)null)
									{
										((Il2CppArrayBase<Material>)(object)materials)[i].SetTexture("_ColorMainLookup", (Texture)(object)val);
									}
									if ((Object)(object)val2 != (Object)null)
									{
										((Il2CppArrayBase<Material>)(object)materials)[i].SetTexture("_ColorSecondaryLookup", (Texture)(object)val2);
									}
									if ((Object)(object)val3 != (Object)null)
									{
										((Il2CppArrayBase<Material>)(object)materials)[i].SetTexture("_ColorDetailLookup", (Texture)(object)val3);
									}
								}
							}
							item.materials = materials;
						}
						return;
					}
				}
				if (!flag2)
				{
					return;
				}
				AsyncOperationHandle<Material> val4 = Addressables.LoadAssetAsync<Material>(Object.op_Implicit(AccessTools.Property(type, "m_AssetGuid")?.GetValue(cd)?.ToString()));
				val4.WaitForCompletion();
				if (!((Object)(object)val4.Result != (Object)null))
				{
					return;
				}
				foreach (Renderer item2 in weaponRenderers)
				{
					item2.material = val4.Result;
				}
			}
			catch
			{
			}
		}

		private static object FindSlotByType(Component handler, string type)
		{
			FindSlotByTypeWithIndex(handler, type, out var foundSlot, out var _);
			return foundSlot;
		}

		private static void FindSlotByTypeWithIndex(Component handler, string type, out object foundSlot, out int foundIndex)
		{
			foundSlot = null;
			foundIndex = -1;
			try
			{
				object obj = RewrapAs(cosmeticsHandlerType, handler);
				List<object> list = IterateIl2CppList(AccessTools.Property(cosmeticsHandlerType, "m_CosmeticSlots")?.GetValue(obj));
				for (int i = 0; i < list.Count; i++)
				{
					if (SlotMatchesType(list[i], type))
					{
						foundSlot = list[i];
						foundIndex = i;
						break;
					}
				}
			}
			catch
			{
			}
		}

		private static bool SlotMatchesType(object slot, string type)
		{
			type = type.ToLower();
			PropertyInfo[] properties = slot.GetType().GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
			foreach (PropertyInfo propertyInfo in properties)
			{
				try
				{
					if ((propertyInfo.GetValue(slot)?.ToString() ?? "").ToLower() == type)
					{
						return true;
					}
				}
				catch
				{
				}
			}
			FieldInfo[] fields = slot.GetType().GetFields(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
			foreach (FieldInfo fieldInfo in fields)
			{
				try
				{
					if ((fieldInfo.GetValue(slot)?.ToString() ?? "").ToLower() == type)
					{
						return true;
					}
				}
				catch
				{
				}
			}
			return false;
		}

		private static object RewrapAs(Type targetType, object obj)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				IntPtr pointer = ((Il2CppObjectBase)obj).Pointer;
				return targetType.GetConstructor(new Type[1] { typeof(IntPtr) })?.Invoke(new object[1] { pointer }) ?? obj;
			}
			catch
			{
				return obj;
			}
		}

		private static List<Renderer> GetWeaponRenderers(object player)
		{
			GameObject weaponRoot = GetWeaponRoot(player);
			List<Renderer> list = new List<Renderer>();
			if ((Object)(object)weaponRoot == (Object)null)
			{
				return list;
			}
			foreach (Renderer componentsInChild in weaponRoot.GetComponentsInChildren<Renderer>(true))
			{
				if (!((Object)((Component)componentsInChild).gameObject).name.Contains("Materia"))
				{
					list.Add(componentsInChild);
				}
			}
			return list;
		}

		private static Texture2D LoadSwatchLookup(object colorRef)
		{
			//IL_006f: Unknown result type (might be due to invalid IL or missing references)
			if (colorRef == null || colorSwatchType == null)
			{
				return null;
			}
			string text = AccessTools.Property(colorRef.GetType(), "AssetGUID")?.GetValue(colorRef)?.ToString();
			if (string.IsNullOrEmpty(text))
			{
				return null;
			}
			AsyncOperationHandle<ScriptableObject> val = Addressables.LoadAssetAsync<ScriptableObject>(Object.op_Implicit(text));
			val.WaitForCompletion();
			if ((Object)(object)val.Result == (Object)null)
			{
				return null;
			}
			IntPtr pointer = ((Il2CppObjectBase)val.Result).Pointer;
			object obj = colorSwatchType.GetConstructor(new Type[1] { typeof(IntPtr) })?.Invoke(new object[1] { pointer });
			if (obj == null)
			{
				return null;
			}
			object obj2 = AccessTools.Property(colorSwatchType, "Lookup")?.GetValue(obj) ?? AccessTools.Field(colorSwatchType, "Lookup")?.GetValue(obj);
			string text2 = AccessTools.Property(obj2?.GetType(), "AssetGUID")?.GetValue(obj2)?.ToString();
			if (string.IsNullOrEmpty(text2))
			{
				return null;
			}
			AsyncOperationHandle<Texture2D> obj3 = Addressables.LoadAssetAsync<Texture2D>(Object.op_Implicit(text2));
			obj3.WaitForCompletion();
			return obj3.Result;
		}

		private static void ToggleMenu()
		{
			//IL_0061: Unknown result type (might be due to invalid IL or missing references)
			//IL_0014: Unknown result type (might be due to invalid IL or missing references)
			//IL_0019: Unknown result type (might be due to invalid IL or missing references)
			menuOpen = !menuOpen;
			if (menuOpen)
			{
				savedLock = Cursor.lockState;
				savedCursorVis = Cursor.visible;
				Cursor.lockState = (CursorLockMode)0;
				Cursor.visible = true;
				scopeScrollY = 0f;
				colorScrollY = 0f;
				SetGameplayInputEnabled(enabled: false);
				if (!previewsLoaded)
				{
					MelonCoroutines.Start(LoadPreviewsAsync());
				}
			}
			else
			{
				Cursor.lockState = savedLock;
				Cursor.visible = savedCursorVis;
				SetGameplayInputEnabled(enabled: true);
			}
		}

		private unsafe static string KeyDisplayName(Key k)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dc: Expected I4, but got Unknown
			//IL_00dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00df: Unknown result type (might be due to invalid IL or missing references)
			//IL_010d: Expected I4, but got Unknown
			switch (k - 4)
			{
			default:
				switch (k - 84)
				{
				case 0:
					return "Num0";
				case 1:
					return "Num1";
				case 2:
					return "Num2";
				case 3:
					return "Num3";
				case 4:
					return "Num4";
				case 5:
					return "Num5";
				case 6:
					return "Num6";
				case 7:
					return "Num7";
				case 8:
					return "Num8";
				case 9:
					return "Num9";
				}
				break;
			case 46:
				return "0";
			case 37:
				return "1";
			case 38:
				return "2";
			case 39:
				return "3";
			case 40:
				return "4";
			case 41:
				return "5";
			case 42:
				return "6";
			case 43:
				return "7";
			case 44:
				return "8";
			case 45:
				return "9";
			case 47:
				return "L.Shift";
			case 48:
				return "R.Shift";
			case 51:
				return "L.Ctrl";
			case 52:
				return "R.Ctrl";
			case 49:
				return "L.Alt";
			case 50:
				return "R.Alt";
			case 0:
				return "`";
			case 9:
				return "-";
			case 10:
				return "=";
			case 7:
				return "[";
			case 8:
				return "]";
			case 6:
				return "\\";
			case 2:
				return ";";
			case 1:
				return "'";
			case 3:
				return ",";
			case 4:
				return ".";
			case 5:
				return "/";
			case 11:
			case 12:
			case 13:
			case 14:
			case 15:
			case 16:
			case 17:
			case 18:
			case 19:
			case 20:
			case 21:
			case 22:
			case 23:
			case 24:
			case 25:
			case 26:
			case 27:
			case 28:
			case 29:
			case 30:
			case 31:
			case 32:
			case 33:
			case 34:
			case 35:
			case 36:
				break;
			}
			return ((object)(*(Key*)(&k))/*cast due to .constrained prefix*/).ToString();
		}

		private unsafe static Key KeyCodeToKey(KeyCode kc)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Invalid comparison between Unknown and I4
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			//IL_0027: Invalid comparison between Unknown and I4
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Invalid comparison between Unknown and I4
			//IL_0045: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Invalid comparison between Unknown and I4
			//IL_0029: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Invalid comparison between Unknown and I4
			//IL_00f4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f7: Invalid comparison between Unknown and I4
			//IL_004d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0050: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ce: Expected I4, but got Unknown
			//IL_02f8: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Unknown result type (might be due to invalid IL or missing references)
			//IL_0033: Invalid comparison between Unknown and I4
			//IL_0022: Unknown result type (might be due to invalid IL or missing references)
			//IL_0355: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_0102: Unknown result type (might be due to invalid IL or missing references)
			//IL_01dc: Expected I4, but got Unknown
			//IL_02e2: Unknown result type (might be due to invalid IL or missing references)
			//IL_0381: Unknown result type (might be due to invalid IL or missing references)
			//IL_033e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0342: Unknown result type (might be due to invalid IL or missing references)
			//IL_0322: Unknown result type (might be due to invalid IL or missing references)
			//IL_0346: Unknown result type (might be due to invalid IL or missing references)
			//IL_034b: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e3: Unknown result type (might be due to invalid IL or missing references)
			//IL_01eb: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f3: Unknown result type (might be due to invalid IL or missing references)
			//IL_01fb: Unknown result type (might be due to invalid IL or missing references)
			//IL_0203: Unknown result type (might be due to invalid IL or missing references)
			//IL_020b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0213: Unknown result type (might be due to invalid IL or missing references)
			//IL_021b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0223: Unknown result type (might be due to invalid IL or missing references)
			//IL_022b: Unknown result type (might be due to invalid IL or missing references)
			//IL_033a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0327: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ce: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ef: Expected I4, but got Unknown
			//IL_0382: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f0: Unknown result type (might be due to invalid IL or missing references)
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_003b: Invalid comparison between Unknown and I4
			//IL_0233: Unknown result type (might be due to invalid IL or missing references)
			//IL_023b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0243: Unknown result type (might be due to invalid IL or missing references)
			//IL_024b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0253: Unknown result type (might be due to invalid IL or missing references)
			//IL_025b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0263: Unknown result type (might be due to invalid IL or missing references)
			//IL_026b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0273: Unknown result type (might be due to invalid IL or missing references)
			//IL_027b: Unknown result type (might be due to invalid IL or missing references)
			//IL_036e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0373: Unknown result type (might be due to invalid IL or missing references)
			//IL_037d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0378: Unknown result type (might be due to invalid IL or missing references)
			//IL_0350: Unknown result type (might be due to invalid IL or missing references)
			//IL_035a: Unknown result type (might be due to invalid IL or missing references)
			//IL_035f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0364: Unknown result type (might be due to invalid IL or missing references)
			//IL_0369: Unknown result type (might be due to invalid IL or missing references)
			//IL_0283: Unknown result type (might be due to invalid IL or missing references)
			//IL_028b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0293: Unknown result type (might be due to invalid IL or missing references)
			//IL_029b: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ab: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b3: Unknown result type (might be due to invalid IL or missing references)
			//IL_02bb: Unknown result type (might be due to invalid IL or missing references)
			//IL_02c3: Unknown result type (might be due to invalid IL or missing references)
			//IL_02cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_02d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_02db: Unknown result type (might be due to invalid IL or missing references)
			//IL_0305: Unknown result type (might be due to invalid IL or missing references)
			//IL_0300: Unknown result type (might be due to invalid IL or missing references)
			//IL_030f: Unknown result type (might be due to invalid IL or missing references)
			//IL_030a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0319: Unknown result type (might be due to invalid IL or missing references)
			//IL_0314: Unknown result type (might be due to invalid IL or missing references)
			//IL_032c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0336: Unknown result type (might be due to invalid IL or missing references)
			//IL_0331: Unknown result type (might be due to invalid IL or missing references)
			//IL_031d: Unknown result type (might be due to invalid IL or missing references)
			//IL_02e9: Unknown result type (might be due to invalid IL or missing references)
			if ((int)kc >= 97 && (int)kc <= 122)
			{
				if (!Enum.TryParse<Key>(((object)(*(KeyCode*)(&kc))/*cast due to .constrained prefix*/).ToString(), out Key result))
				{
					return (Key)0;
				}
				return result;
			}
			if ((int)kc <= 13)
			{
				if ((int)kc == 8)
				{
					return (Key)65;
				}
				if ((int)kc == 9)
				{
					return (Key)3;
				}
				if ((int)kc == 13)
				{
					return (Key)2;
				}
			}
			else if ((int)kc <= 96)
			{
				switch (kc - 32)
				{
				default:
					switch (kc - 91)
					{
					case 5:
						return (Key)4;
					case 0:
						return (Key)11;
					case 2:
						return (Key)12;
					case 1:
						return (Key)10;
					}
					break;
				case 16:
					return (Key)50;
				case 17:
					return (Key)41;
				case 18:
					return (Key)42;
				case 19:
					return (Key)43;
				case 20:
					return (Key)44;
				case 21:
					return (Key)45;
				case 22:
					return (Key)46;
				case 23:
					return (Key)47;
				case 24:
					return (Key)48;
				case 25:
					return (Key)49;
				case 0:
					return (Key)1;
				case 13:
					return (Key)13;
				case 29:
					return (Key)14;
				case 27:
					return (Key)6;
				case 7:
					return (Key)5;
				case 12:
					return (Key)7;
				case 14:
					return (Key)8;
				case 15:
					return (Key)9;
				case 1:
				case 2:
				case 3:
				case 4:
				case 5:
				case 6:
				case 8:
				case 9:
				case 10:
				case 11:
				case 26:
				case 28:
					break;
				}
			}
			else
			{
				if ((int)kc == 127)
				{
					return (Key)71;
				}
				switch (kc - 256)
				{
				case 0:
					return (Key)84;
				case 1:
					return (Key)85;
				case 2:
					return (Key)86;
				case 3:
					return (Key)87;
				case 4:
					return (Key)88;
				case 5:
					return (Key)89;
				case 6:
					return (Key)90;
				case 7:
					return (Key)91;
				case 8:
					return (Key)92;
				case 9:
					return (Key)93;
				case 26:
					return (Key)94;
				case 27:
					return (Key)95;
				case 28:
					return (Key)96;
				case 29:
					return (Key)97;
				case 30:
					return (Key)98;
				case 31:
					return (Key)99;
				case 32:
					return (Key)100;
				case 33:
					return (Key)101;
				case 34:
					return (Key)102;
				case 35:
					return (Key)103;
				case 36:
					return (Key)104;
				case 37:
					return (Key)105;
				case 48:
					return (Key)51;
				case 47:
					return (Key)52;
				case 50:
					return (Key)55;
				case 49:
					return (Key)56;
				case 52:
					return (Key)53;
				case 51:
					return (Key)54;
				case 21:
					return (Key)70;
				case 22:
					return (Key)68;
				case 23:
					return (Key)69;
				case 24:
					return (Key)67;
				case 25:
					return (Key)66;
				case 17:
					return (Key)63;
				case 18:
					return (Key)64;
				case 20:
					return (Key)61;
				case 19:
					return (Key)62;
				}
			}
			return (Key)0;
		}

		private static void TryInjectRow()
		{
			//IL_0165: Unknown result type (might be due to invalid IL or missing references)
			if (guiKeybindBtnType == null)
			{
				return;
			}
			try
			{
				Type val = Il2CppType.From(guiKeybindBtnType);
				Il2CppReferenceArray<Object> val2 = Resources.FindObjectsOfTypeAll(val);
				if (val2 == null || ((Il2CppArrayBase<Object>)(object)val2).Length == 0)
				{
					return;
				}
				Component val3 = null;
				foreach (Object item in (Il2CppArrayBase<Object>)(object)val2)
				{
					Component val4 = ((Il2CppObjectBase)item).TryCast<Component>();
					if (val4 == null)
					{
						continue;
					}
					GameObject gameObject = val4.gameObject;
					if (((gameObject != null) ? new bool?(gameObject.activeInHierarchy) : ((bool?)null)) == true)
					{
						Transform transform = val4.transform;
						if ((Object)(object)((transform != null) ? transform.parent : null) != (Object)null)
						{
							val3 = val4;
							break;
						}
					}
				}
				if ((Object)(object)val3 == (Object)null)
				{
					return;
				}
				GameObject obj = Object.Instantiate<GameObject>(val3.gameObject, val3.transform.parent, false);
				((Object)obj).name = "WeaponCustomization_MenuKey";
				obj.transform.SetAsLastSibling();
				obj.SetActive(true);
				Component component = obj.GetComponent(val);
				if ((Object)(object)component != (Object)null)
				{
					Object.DestroyImmediate((Object)(object)component);
				}
				Il2CppArrayBase<TMP_Text> componentsInChildren = obj.GetComponentsInChildren<TMP_Text>(true);
				if (componentsInChildren.Length >= 1)
				{
					componentsInChildren[0].SetText("Weapon Menu", true);
				}
				Transform val5 = obj.transform.Find("PF_InputButton");
				if ((Object)(object)val5 != (Object)null)
				{
					keybindKeyLabel = ((Component)val5).GetComponentInChildren<TMP_Text>(true);
					TMP_Text obj2 = keybindKeyLabel;
					if (obj2 != null)
					{
						obj2.SetText(KeyDisplayName(menuKey), true);
					}
				}
				Button componentInChildren = obj.GetComponentInChildren<Button>(true);
				if ((Object)(object)componentInChildren != (Object)null)
				{
					((UnityEventBase)componentInChildren.onClick).RemoveAllListeners();
					((UnityEvent)componentInChildren.onClick).AddListener(DelegateSupport.ConvertDelegate<UnityAction>((Delegate)new Action(StartRebind)));
				}
				injectedKeybindBtn = obj;
				keybindInjected = true;
			}
			catch
			{
			}
		}

		private static void StartRebind()
		{
			rebinding = true;
			TMP_Text obj = keybindKeyLabel;
			if (obj != null)
			{
				obj.SetText("...", true);
			}
		}

		private static Texture2D SpriteToTex(Sprite s)
		{
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_005b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0060: Unknown result type (might be due to invalid IL or missing references)
			//IL_007d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0089: Unknown result type (might be due to invalid IL or missing references)
			//IL_009c: Expected O, but got Unknown
			if ((Object)(object)s == (Object)null)
			{
				return null;
			}
			try
			{
				Rect textureRect = s.textureRect;
				RenderTexture temporary = RenderTexture.GetTemporary(((Texture)s.texture).width, ((Texture)s.texture).height, 0, (RenderTextureFormat)0);
				RenderTexture active = RenderTexture.active;
				RenderTexture.active = temporary;
				Graphics.Blit((Texture)(object)s.texture, temporary);
				Texture2D val = new Texture2D((int)((Rect)(ref textureRect)).width, (int)((Rect)(ref textureRect)).height, (TextureFormat)4, false);
				val.ReadPixels(new Rect(((Rect)(ref textureRect)).x, ((Rect)(ref textureRect)).y, ((Rect)(ref textureRect)).width, ((Rect)(ref textureRect)).height), 0, 0);
				val.Apply();
				RenderTexture.active = active;
				RenderTexture.ReleaseTemporary(temporary);
				return val;
			}
			catch
			{
				return null;
			}
		}

		private static void TryLoadAssets()
		{
			//IL_0083: Unknown result type (might be due to invalid IL or missing references)
			//IL_0088: Unknown result type (might be due to invalid IL or missing references)
			//IL_0089: Unknown result type (might be due to invalid IL or missing references)
			//IL_0090: Unknown result type (might be due to invalid IL or missing references)
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			//IL_009e: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00af: Expected O, but got Unknown
			GameObject val = GameObject.Find("PF_GUI");
			if ((Object)(object)val == (Object)null)
			{
				return;
			}
			Transform val2 = val.transform.Find("FullScreenGUI/PF_VAssist");
			if ((Object)(object)val2 == (Object)null)
			{
				return;
			}
			try
			{
				Transform obj = val2.Find("Shadow");
				Image val3 = ((obj != null) ? ((Component)obj).GetComponent<Image>() : null);
				if ((Object)(object)val3 != (Object)null && (Object)(object)val3.sprite != (Object)null)
				{
					gamePanelTex = SpriteToTex(val3.sprite);
					if ((Object)(object)gamePanelTex != (Object)null)
					{
						Vector4 border = val3.sprite.border;
						gamePanelBorder = new RectOffset((int)border.x, (int)border.z, (int)border.w, (int)border.y);
					}
				}
			}
			catch
			{
			}
			assetsLoaded = true;
			stylesInited = false;
		}

		private static void SetGameplayInputEnabled(bool enabled)
		{
			try
			{
				Mouse current = Mouse.current;
				if (current != null)
				{
					if (enabled)
					{
						InputSystem.EnableDevice((InputDevice)(object)current);
					}
					else
					{
						InputSystem.DisableDevice((InputDevice)(object)current, false);
					}
				}
				Gamepad current2 = Gamepad.current;
				if (current2 != null)
				{
					if (enabled)
					{
						InputSystem.EnableDevice((InputDevice)(object)current2);
					}
					else
					{
						InputSystem.DisableDevice((InputDevice)(object)current2, false);
					}
				}
			}
			catch
			{
			}
		}

		private static IEnumerator LoadPreviewsAsync()
		{
			previewsLoaded = true;
			scopePreviews.Clear();
			colorPreviews.Clear();
			List<object> colors = GetAvailableColors();
			for (int i = 0; i < colors.Count; i++)
			{
				object obj = colors[i];
				Texture2D val = LoadSwatchLookup(AccessTools.Property(obj.GetType(), "m_MainColor")?.GetValue(obj));
				if ((Object)(object)val != (Object)null)
				{
					colorPreviews[i] = val;
				}
				yield return null;
			}
		}

		public unsafe override void OnGUI()
		{
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0014: Invalid comparison between Unknown and I4
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Invalid comparison between Unknown and I4
			//IL_0017: Unknown result type (might be due to invalid IL or missing references)
			//IL_009d: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a4: Invalid comparison between Unknown and I4
			//IL_001f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0026: Invalid comparison between Unknown and I4
			//IL_0103: Unknown result type (might be due to invalid IL or missing references)
			//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_0033: Unknown result type (might be due to invalid IL or missing references)
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			//IL_012a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0140: Unknown result type (might be due to invalid IL or missing references)
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0162: Unknown result type (might be due to invalid IL or missing references)
			//IL_0178: Unknown result type (might be due to invalid IL or missing references)
			//IL_018e: Unknown result type (might be due to invalid IL or missing references)
			//IL_01cd: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_0215: Unknown result type (might be due to invalid IL or missing references)
			//IL_021f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			//IL_0282: Unknown result type (might be due to invalid IL or missing references)
			Event current = Event.current;
			if (rebinding && (int)current.type == 4 && (int)current.keyCode != 0 && (int)current.keyCode != 27)
			{
				Key val = KeyCodeToKey(current.keyCode);
				if ((int)val != 0)
				{
					menuKey = val;
					rebindFrame = Time.frameCount;
					prefMenuKey.Value = ((object)(*(Key*)(&val))/*cast due to .constrained prefix*/).ToString();
					MelonPreferences.Save();
					TMP_Text obj = keybindKeyLabel;
					if (obj != null)
					{
						obj.SetText(KeyDisplayName(val), true);
					}
					rebinding = false;
					current.Use();
				}
			}
			else
			{
				if (!menuOpen)
				{
					return;
				}
				if ((int)current.type == 4 && (int)current.keyCode == 27)
				{
					ToggleMenu();
					current.Use();
					return;
				}
				InitMenuStyles();
				float num = ((float)Screen.width - 640f) / 2f;
				float num2 = ((float)Screen.height - 520f) / 2f;
				Rect val2 = default(Rect);
				((Rect)(ref val2))..ctor(num, num2, 640f, 520f);
				if ((current.isMouse || current.isScrollWheel) && !((Rect)(ref val2)).Contains(current.mousePosition))
				{
					current.Use();
					return;
				}
				GUI.color = new Color(1f, 1f, 1f, 0.82f);
				GUI.Box(new Rect(num, num2, 640f, 520f), GUIContent.none, sPanel ?? GUI.skin.box);
				GUI.color = Color.white;
				DrawRect(num, num2, 640f, 40f, MCol.TitleBar);
				DrawRect(num, num2, 3f, 40f, MCol.Accent);
				DrawRect(num, num2 + 40f, 640f, 1f, new Color(MCol.Accent.r, MCol.Accent.g, MCol.Accent.b, 0.3f));
				GUI.Label(new Rect(num + 14f, num2, 470f, 40f), "WEAPON CUSTOMIZATION", sTitleLabel);
				GUI.Label(new Rect(num + 640f - 165f, num2, 158f, 40f), "[" + KeyDisplayName(menuKey) + "]  ESC TO CLOSE", sHintLabel);
				object localPlayer = GetLocalPlayer();
				string text = ((localPlayer != null) ? GetModuleKey(localPlayer) : null);
				weaponCosmetics.TryGetValue(text ?? "", out var value);
				if (text == null)
				{
					GUI.Label(new Rect(num, num2 + 50f, 640f, 40f), "Hold a weapon to customize it.", sNoWeapLabel);
					return;
				}
				float py = num2 + 48f;
				float scrollH = 434f;
				DrawListPanel(num + 8f, py, 308f, scrollH, 30f, 40f, 44f, "SCOPE", GetAvailableScopes(), scopePreviews, value.HasScope, value.ScopeIndex, localPlayer, text, ref value, isScope: true);
				DrawListPanel(num + 16f + 308f, py, 308f, scrollH, 30f, 40f, 44f, "COLOR", GetAvailableColors(), colorPreviews, value.HasColor, value.ColorIndex, localPlayer, text, ref value, isScope: false);
			}
		}

		private static void InitMenuStyles()
		{
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0018: Expected O, but got Unknown
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0062: Unknown result type (might be due to invalid IL or missing references)
			//IL_006c: Expected O, but got Unknown
			//IL_0098: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ac: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b6: Expected O, but got Unknown
			//IL_00d7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00eb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f5: Expected O, but got Unknown
			//IL_0116: Unknown result type (might be due to invalid IL or missing references)
			//IL_012a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0134: Expected O, but got Unknown
			//IL_0160: Unknown result type (might be due to invalid IL or missing references)
			//IL_0174: Unknown result type (might be due to invalid IL or missing references)
			//IL_017e: Expected O, but got Unknown
			//IL_019f: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b3: Unknown result type (might be due to invalid IL or missing references)
			//IL_01bd: Expected O, but got Unknown
			//IL_01e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			if (stylesInited)
			{
				return;
			}
			stylesInited = true;
			try
			{
				sPanel = new GUIStyle();
				sPanel.normal.background = gamePanelTex ?? MakeTex(1, 1, MCol.Panel);
				sPanel.border = (RectOffset)(((object)gamePanelBorder) ?? ((object)new RectOffset(0, 0, 0, 0)));
				sTitleLabel = new GUIStyle(GUI.skin.label);
				sTitleLabel.fontSize = 12;
				sTitleLabel.fontStyle = (FontStyle)1;
				sTitleLabel.alignment = (TextAnchor)3;
				sTitleLabel.normal.textColor = MCol.HdrText;
				sHintLabel = new GUIStyle(GUI.skin.label);
				sHintLabel.fontSize = 11;
				sHintLabel.alignment = (TextAnchor)5;
				sHintLabel.normal.textColor = MCol.Muted;
				sNoWeapLabel = new GUIStyle(GUI.skin.label);
				sNoWeapLabel.fontSize = 13;
				sNoWeapLabel.alignment = (TextAnchor)4;
				sNoWeapLabel.normal.textColor = MCol.Muted;
				sColHdr = new GUIStyle(GUI.skin.label);
				sColHdr.fontSize = 11;
				sColHdr.fontStyle = (FontStyle)1;
				sColHdr.alignment = (TextAnchor)3;
				sColHdr.normal.textColor = MCol.HdrText;
				sRowNormal = new GUIStyle(GUI.skin.label);
				sRowNormal.fontSize = 13;
				sRowNormal.alignment = (TextAnchor)3;
				sRowNormal.normal.textColor = MCol.Text;
				sRowSel = new GUIStyle(GUI.skin.label);
				sRowSel.fontSize = 13;
				sRowSel.fontStyle = (FontStyle)1;
				sRowSel.alignment = (TextAnchor)3;
				sRowSel.normal.textColor = Color.white;
			}
			catch
			{
				stylesInited = false;
			}
		}

		private static Texture2D MakeTex(int w, int h, Color c)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0010: Unknown result type (might be due to invalid IL or missing references)
			//IL_0017: Expected O, but got Unknown
			Texture2D val = new Texture2D(w, h);
			val.SetPixel(0, 0, c);
			val.Apply();
			return val;
		}

		private static void DrawRect(float x, float y, float w, float h, Color c)
		{
			//IL_0000: 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_001a: Unknown result type (might be due to invalid IL or missing references)
			GUI.color = c;
			GUI.DrawTexture(new Rect(x, y, w, h), (Texture)(object)Texture2D.whiteTexture);
			GUI.color = Color.white;
		}

		private static void DrawListPanel(float px, float py, float colW, float scrollH, float hdrH, float rowH, float prevW, string title, List<object> items, Dictionary<int, Texture2D> previews, bool hasSelection, int selectedIdx, object player, string moduleKey, ref WeaponCosmetics wc, bool isScope)
		{
			//IL_0007: 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_0066: Unknown result type (might be due to invalid IL or missing references)
			//IL_0081: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c6: Invalid comparison between Unknown and I4
			//IL_013a: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f3: Unknown result type (might be due to invalid IL or missing references)
			//IL_0109: Unknown result type (might be due to invalid IL or missing references)
			//IL_0229: Unknown result type (might be due to invalid IL or missing references)
			//IL_022e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0237: Unknown result type (might be due to invalid IL or missing references)
			//IL_0247: Unknown result type (might be due to invalid IL or missing references)
			//IL_024c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0254: Unknown result type (might be due to invalid IL or missing references)
			//IL_0259: Unknown result type (might be due to invalid IL or missing references)
			//IL_0281: Unknown result type (might be due to invalid IL or missing references)
			//IL_026a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0263: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a0: Unknown result type (might be due to invalid IL or missing references)
			//IL_026f: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f6: Unknown result type (might be due to invalid IL or missing references)
			//IL_0349: Unknown result type (might be due to invalid IL or missing references)
			//IL_0375: Unknown result type (might be due to invalid IL or missing references)
			GUI.Box(new Rect(px, py, colW, hdrH + scrollH), GUIContent.none, sPanel ?? GUI.skin.box);
			DrawRect(px, py, colW, hdrH, MCol.ColHdr);
			DrawRect(px, py + hdrH, colW, 1f, new Color(MCol.Accent.r, MCol.Accent.g, MCol.Accent.b, 0.4f));
			GUI.Label(new Rect(px + 10f, py, colW - 20f, hdrH), title, sColHdr);
			ref float reference = ref isScope ? ref scopeScrollY : ref colorScrollY;
			float num = Mathf.Max(0f, (float)items.Count * rowH - scrollH);
			if ((int)Event.current.type == 6)
			{
				Vector2 mousePosition = Event.current.mousePosition;
				if (mousePosition.x >= px && mousePosition.x <= px + colW && mousePosition.y >= py + hdrH && mousePosition.y <= py + hdrH + scrollH)
				{
					reference = Mathf.Clamp(reference + Event.current.delta.y * rowH * 0.5f, 0f, num);
					Event.current.Use();
				}
			}
			GUI.BeginClip(new Rect(px, py + hdrH, colW, scrollH));
			bool flag = previews.Count > 0;
			for (int i = 0; i < items.Count; i++)
			{
				float num2 = (float)i * rowH - reference;
				if (num2 + rowH < 0f || num2 > scrollH)
				{
					continue;
				}
				string text = (AccessTools.Property(items[i].GetType(), "name")?.GetValue(items[i])?.ToString() ?? $"Item {i}").Replace("CosmeticData_Scope_", "").Replace("CosmeticData_Color_", "").Replace("_", " ");
				bool flag2 = hasSelection && selectedIdx == i;
				Rect val = new Rect(0f, num2, colW, rowH - 1f);
				bool flag3 = ((Rect)(ref val)).Contains(Event.current.mousePosition);
				Color c = (flag2 ? MCol.Sel : ((!flag3) ? ((i % 2 == 0) ? MCol.RowDark : MCol.RowLight) : MCol.RowHover));
				DrawRect(0f, num2, colW, rowH - 1f, c);
				if (flag2)
				{
					DrawRect(0f, num2, 3f, rowH - 1f, MCol.SelBar);
				}
				float num3 = (flag2 ? 6f : 3f);
				if (flag && previews.TryGetValue(i, out var value) && (Object)(object)value != (Object)null)
				{
					GUI.DrawTexture(new Rect(num3 + 2f, num2 + 4f, prevW - 4f, rowH - 8f), (Texture)(object)value, (ScaleMode)2);
				}
				float num4 = (flag ? (num3 + prevW + 4f) : (num3 + 8f));
				float num5 = (flag ? (colW - num3 - prevW - 8f) : (colW - num3 - 12f));
				GUI.Label(new Rect(num4, num2, num5, rowH - 1f), text, flag2 ? sRowSel : sRowNormal);
				if (GUI.Button(new Rect(0f, num2, colW, rowH - 1f), GUIContent.none, GUIStyle.none))
				{
					if (isScope)
					{
						wc.ScopeIndex = i;
						wc.HasScope = true;
					}
					else
					{
						wc.ColorIndex = i;
						wc.HasColor = true;
					}
					weaponCosmetics[moduleKey] = wc;
					SaveCosmetics();
					if (isScope)
					{
						ApplyScopeIndex(player, i);
					}
					else
					{
						ApplyColorIndex(player, i);
					}
				}
			}
			GUI.EndClip();
		}
	}
}