Decompiled source of Super Nintendo Valuables v1.0.0

BepInEx/plugins/Omniscye-Empress_SNES_Pack/EmpressSNESPack.dll

Decompiled 7 hours ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using REPOLib.Modules;
using UnityEngine;
using UnityEngine.Networking;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: AssemblyCompany("Empress")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("EmpressSNESPack")]
[assembly: AssemblyTitle("EmpressSNESPack")]
[assembly: AssemblyVersion("1.0.0.0")]
[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 Empress.REPO.SNESPack
{
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInPlugin("com.empress.repo.snespack", "Empress SNES Pack", "1.0.0")]
	public sealed class EmpressSNESPackPlugin : BaseUnityPlugin
	{
		internal const string PluginGuid = "com.empress.repo.snespack";

		internal const string PluginName = "Empress SNES Pack";

		internal const string PluginVersion = "1.0.0";

		private bool _registrationStarted;

		internal static ManualLogSource Log { get; private set; }

		internal static ConfigEntry<float> AudioVolume { get; private set; }

		internal static ConfigEntry<float> AudioMaxDistance { get; private set; }

		private void Awake()
		{
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Expected O, but got Unknown
			//IL_0076: Unknown result type (might be due to invalid IL or missing references)
			//IL_0080: Expected O, but got Unknown
			//IL_00db: Unknown result type (might be due to invalid IL or missing references)
			Log = ((BaseUnityPlugin)this).Logger;
			AudioVolume = ((BaseUnityPlugin)this).Config.Bind<float>("Audio", "Volume", 0.2f, new ConfigDescription("Music volume when a cart is grabbed.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 1f), Array.Empty<object>()));
			AudioMaxDistance = ((BaseUnityPlugin)this).Config.Bind<float>("Audio", "MaxDistance", 12f, new ConfigDescription("3D music falloff distance.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(2f, 45f), Array.Empty<object>()));
			((Component)this).transform.parent = null;
			((Object)((Component)this).gameObject).hideFlags = (HideFlags)61;
			Object.DontDestroyOnLoad((Object)(object)((Component)this).gameObject);
			string pluginDirectory = Path.GetDirectoryName(((BaseUnityPlugin)this).Info.Location) ?? string.Empty;
			SnesAssets.Load(pluginDirectory);
			((MonoBehaviour)this).StartCoroutine(SnesAudioLibrary.Load(pluginDirectory));
			new Harmony("com.empress.repo.snespack").PatchAll();
			((MonoBehaviour)this).StartCoroutine(RegisterWhenReady());
			((BaseUnityPlugin)this).Logger.LogInfo((object)"Empress SNES Pack v1.0.0 loaded.");
		}

		private IEnumerator RegisterWhenReady()
		{
			if (!_registrationStarted)
			{
				_registrationStarted = true;
				while ((Object)(object)RunManager.instance == (Object)null || ValuablePresets.AllValuablePresets.Count == 0)
				{
					yield return null;
				}
				yield return null;
				int num = new SnesValuablePrefabFactory(((BaseUnityPlugin)this).Logger).RegisterAll();
				((BaseUnityPlugin)this).Logger.LogInfo((object)("Registered " + num + " Empress SNES carts with REPOLib."));
			}
		}
	}
	internal static class SnesAssets
	{
		private const string CartBundleFileName = "empresssnescart";

		private const string CartPrefabName = "SNES Cart";

		private const string TextureSpotName = "TextureSpot";

		private const string CatalogFileName = "snes_cart_catalog.txt";

		private const float TargetMaxDimension = 0.5f;

		private static AssetBundle _bundle;

		private static GameObject _bank;

		private static readonly List<GameObject> _visualPrefabs = new List<GameObject>();

		private static readonly Dictionary<string, SnesCatalogEntry> _catalog = new Dictionary<string, SnesCatalogEntry>(StringComparer.Ordinal);

		public static IReadOnlyList<GameObject> VisualPrefabs => _visualPrefabs;

		public static void Load(string pluginDirectory)
		{
			if ((Object)(object)_bundle != (Object)null)
			{
				return;
			}
			string text = ResolveFile(pluginDirectory, "empresssnescart");
			if (string.IsNullOrEmpty(text))
			{
				EmpressSNESPackPlugin.Log.LogError((object)"Empress SNES cart bundle missing.");
				return;
			}
			_bundle = AssetBundle.LoadFromFile(text);
			if ((Object)(object)_bundle == (Object)null)
			{
				EmpressSNESPackPlugin.Log.LogError((object)"Empress SNES cart bundle could not be loaded.");
				return;
			}
			GameObject val = LoadCartPrefab();
			if ((Object)(object)val == (Object)null)
			{
				EmpressSNESPackPlugin.Log.LogError((object)"SNES Cart prefab was not found in the cart bundle.");
				return;
			}
			List<SnesCatalogEntry> list = LoadCatalog(pluginDirectory);
			if (list.Count == 0)
			{
				EmpressSNESPackPlugin.Log.LogError((object)"Empress SNES catalog missing or empty.");
				return;
			}
			string artDirectory = Path.Combine(pluginDirectory, "art");
			EnsureBank();
			_visualPrefabs.Clear();
			_catalog.Clear();
			foreach (SnesCatalogEntry item in list)
			{
				GameObject val2 = BuildVisual(val, item, artDirectory);
				if (!((Object)(object)val2 == (Object)null))
				{
					_visualPrefabs.Add(val2);
					_catalog[((Object)val2).name] = item;
				}
			}
			EmpressSNESPackPlugin.Log.LogInfo((object)("Prepared " + _visualPrefabs.Count + " Empress SNES cart visuals."));
		}

		public static bool TryGetCatalog(GameObject prefab, out SnesCatalogEntry entry)
		{
			return _catalog.TryGetValue(((Object)prefab).name, out entry);
		}

		public static bool TryAttachVisual(Transform root, GameObject visualPrefab)
		{
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0041: Unknown result type (might be due to invalid IL or missing references)
			//IL_0057: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)visualPrefab == (Object)null)
			{
				return false;
			}
			GameObject val = Object.Instantiate<GameObject>(visualPrefab, root, false);
			((Object)val).name = "EmpressSNESVisual";
			val.transform.localPosition = visualPrefab.transform.localPosition;
			val.transform.localRotation = visualPrefab.transform.localRotation;
			val.transform.localScale = visualPrefab.transform.localScale;
			val.SetActive(true);
			Renderer[] componentsInChildren = val.GetComponentsInChildren<Renderer>(true);
			for (int i = 0; i < componentsInChildren.Length; i++)
			{
				componentsInChildren[i].enabled = true;
			}
			StripColliders(val);
			return true;
		}

		private static GameObject LoadCartPrefab()
		{
			GameObject val = _bundle.LoadAsset<GameObject>("SNES Cart");
			if ((Object)(object)val != (Object)null)
			{
				return val;
			}
			GameObject[] array = _bundle.LoadAllAssets<GameObject>();
			foreach (GameObject val2 in array)
			{
				if ((Object)(object)val2 != (Object)null && (Object)(object)val2.GetComponentInChildren<Renderer>(true) != (Object)null)
				{
					return val2;
				}
			}
			return null;
		}

		private static List<SnesCatalogEntry> LoadCatalog(string pluginDirectory)
		{
			List<SnesCatalogEntry> list = new List<SnesCatalogEntry>();
			string text = ResolveFile(pluginDirectory, "snes_cart_catalog.txt");
			if (string.IsNullOrEmpty(text))
			{
				return list;
			}
			string[] array = File.ReadAllLines(text);
			for (int i = 0; i < array.Length; i++)
			{
				string[] array2 = array[i].Split('\t');
				if (array2.Length >= 4 && int.TryParse(array2[0], out var result))
				{
					list.Add(new SnesCatalogEntry(result, array2[1], array2[2], array2[3]));
				}
			}
			return list;
		}

		private static GameObject BuildVisual(GameObject cartPrefab, SnesCatalogEntry entry, string artDirectory)
		{
			//IL_0023: 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_0043: Unknown result type (might be due to invalid IL or missing references)
			GameObject obj = Object.Instantiate<GameObject>(cartPrefab, _bank.transform, false);
			((Object)obj).name = entry.PrefabName;
			obj.transform.localPosition = Vector3.zero;
			obj.transform.localRotation = Quaternion.identity;
			obj.transform.localScale = Vector3.one;
			obj.SetActive(true);
			StripColliders(obj);
			NormalizeVisual(obj.transform);
			ApplyCover(obj.transform, entry, artDirectory);
			return obj;
		}

		private static void NormalizeVisual(Transform visual)
		{
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: 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_005a: 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_0072: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ae: 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_009c: 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_0118: Unknown result type (might be due to invalid IL or missing references)
			//IL_011d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0124: Unknown result type (might be due to invalid IL or missing references)
			//IL_0129: Unknown result type (might be due to invalid IL or missing references)
			//IL_012e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0131: Unknown result type (might be due to invalid IL or missing references)
			//IL_0136: Unknown result type (might be due to invalid IL or missing references)
			//IL_0137: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d9: Unknown result type (might be due to invalid IL or missing references)
			Bounds bounds = default(Bounds);
			((Bounds)(ref bounds))..ctor(visual.position, Vector3.zero);
			bool flag = false;
			Renderer[] componentsInChildren = ((Component)visual).GetComponentsInChildren<Renderer>(true);
			foreach (Renderer val in componentsInChildren)
			{
				if (!flag)
				{
					bounds = val.bounds;
					flag = true;
				}
				else
				{
					((Bounds)(ref bounds)).Encapsulate(val.bounds);
				}
			}
			if (!flag)
			{
				return;
			}
			float num = Mathf.Max(((Bounds)(ref bounds)).size.x, Mathf.Max(((Bounds)(ref bounds)).size.y, ((Bounds)(ref bounds)).size.z));
			if (num > 0.001f)
			{
				visual.localScale = Vector3.one * (0.5f / num);
			}
			((Bounds)(ref bounds))..ctor(visual.position, Vector3.zero);
			flag = false;
			componentsInChildren = ((Component)visual).GetComponentsInChildren<Renderer>(true);
			foreach (Renderer val2 in componentsInChildren)
			{
				if (!flag)
				{
					bounds = val2.bounds;
					flag = true;
				}
				else
				{
					((Bounds)(ref bounds)).Encapsulate(val2.bounds);
				}
			}
			Vector3 val3 = new Vector3(0f, 0.18f, 0f) + _bank.transform.position - ((Bounds)(ref bounds)).center;
			visual.localPosition += val3;
		}

		private static void ApplyCover(Transform visual, SnesCatalogEntry entry, string artDirectory)
		{
			//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a7: Expected O, but got Unknown
			//IL_017c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0181: Unknown result type (might be due to invalid IL or missing references)
			//IL_0197: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a0: Expected O, but got Unknown
			//IL_0112: Unknown result type (might be due to invalid IL or missing references)
			//IL_0117: Unknown result type (might be due to invalid IL or missing references)
			//IL_0130: Unknown result type (might be due to invalid IL or missing references)
			//IL_013e: Expected O, but got Unknown
			Renderer val = null;
			Renderer[] componentsInChildren = ((Component)visual).GetComponentsInChildren<Renderer>(true);
			foreach (Renderer val2 in componentsInChildren)
			{
				if (((Object)((Component)val2).gameObject).name.IndexOf("TextureSpot", StringComparison.OrdinalIgnoreCase) >= 0)
				{
					val = val2;
					break;
				}
			}
			if ((Object)(object)val == (Object)null)
			{
				EmpressSNESPackPlugin.Log.LogWarning((object)("TextureSpot missing on cart for " + entry.DisplayName + "."));
				return;
			}
			string path = Path.Combine(artDirectory, entry.CoverFile);
			if (!File.Exists(path))
			{
				EmpressSNESPackPlugin.Log.LogWarning((object)("Missing box art: " + entry.CoverFile));
				return;
			}
			Texture2D val3 = new Texture2D(2, 2, (TextureFormat)4, true);
			if (!ImageConversion.LoadImage(val3, File.ReadAllBytes(path)))
			{
				EmpressSNESPackPlugin.Log.LogWarning((object)("Could not read box art: " + entry.CoverFile));
				return;
			}
			int num = ((Texture)val3).width - ((Texture)val3).width % 4;
			int num2 = ((Texture)val3).height - ((Texture)val3).height % 4;
			if ((num != ((Texture)val3).width || num2 != ((Texture)val3).height) && num >= 4 && num2 >= 4)
			{
				Texture2D val4 = new Texture2D(num, num2, (TextureFormat)4, true);
				val4.SetPixels(val3.GetPixels(0, ((Texture)val3).height - num2, num, num2));
				val4.Apply(true);
				Object.Destroy((Object)(object)val3);
				val3 = val4;
			}
			((Object)val3).name = entry.PrefabName + "_Cover";
			((Texture)val3).wrapMode = (TextureWrapMode)1;
			if (((Texture)val3).width % 4 == 0 && ((Texture)val3).height % 4 == 0)
			{
				val3.Compress(true);
			}
			Material sharedMaterial = new Material(val.sharedMaterial)
			{
				name = entry.PrefabName + "_CoverMaterial",
				mainTexture = (Texture)(object)val3
			};
			val.sharedMaterial = sharedMaterial;
		}

		private static void StripColliders(GameObject visual)
		{
			PhysGrabObjectCollider[] componentsInChildren = visual.GetComponentsInChildren<PhysGrabObjectCollider>(true);
			for (int i = 0; i < componentsInChildren.Length; i++)
			{
				Object.DestroyImmediate((Object)(object)componentsInChildren[i]);
			}
			PhysGrabObjectBoxCollider[] componentsInChildren2 = visual.GetComponentsInChildren<PhysGrabObjectBoxCollider>(true);
			for (int i = 0; i < componentsInChildren2.Length; i++)
			{
				Object.DestroyImmediate((Object)(object)componentsInChildren2[i]);
			}
			PhysGrabObjectMeshCollider[] componentsInChildren3 = visual.GetComponentsInChildren<PhysGrabObjectMeshCollider>(true);
			for (int i = 0; i < componentsInChildren3.Length; i++)
			{
				Object.DestroyImmediate((Object)(object)componentsInChildren3[i]);
			}
			Collider[] componentsInChildren4 = visual.GetComponentsInChildren<Collider>(true);
			for (int i = 0; i < componentsInChildren4.Length; i++)
			{
				Object.DestroyImmediate((Object)(object)componentsInChildren4[i]);
			}
		}

		private static void EnsureBank()
		{
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_0025: Expected O, but got Unknown
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			if (!((Object)(object)_bank != (Object)null))
			{
				_bank = new GameObject("EmpressSNESVisualBank")
				{
					hideFlags = (HideFlags)61
				};
				_bank.transform.position = new Vector3(0f, -4200f, 0f);
				Object.DontDestroyOnLoad((Object)(object)_bank);
			}
		}

		private static string ResolveFile(string pluginDirectory, string fileName)
		{
			string[] array = new string[2]
			{
				Path.Combine(pluginDirectory, "bundles", fileName),
				Path.Combine(pluginDirectory, fileName)
			};
			foreach (string text in array)
			{
				if (File.Exists(text))
				{
					return text;
				}
			}
			return string.Empty;
		}
	}
	internal static class SnesAudioLibrary
	{
		private static readonly Dictionary<string, AudioClip> Clips = new Dictionary<string, AudioClip>(StringComparer.Ordinal);

		public static IEnumerator Load(string pluginDirectory)
		{
			Clips.Clear();
			List<string> list = FindAudioFiles(pluginDirectory);
			foreach (string file in list)
			{
				UnityWebRequest request = UnityWebRequestMultimedia.GetAudioClip(new Uri(file).AbsoluteUri, (AudioType)14);
				DownloadHandler downloadHandler = request.downloadHandler;
				DownloadHandlerAudioClip val = (DownloadHandlerAudioClip)(object)((downloadHandler is DownloadHandlerAudioClip) ? downloadHandler : null);
				if (val != null)
				{
					val.streamAudio = false;
					val.compressed = false;
				}
				yield return request.SendWebRequest();
				if ((int)request.result != 1)
				{
					EmpressSNESPackPlugin.Log.LogWarning((object)("Could not load SNES cart audio: " + Path.GetFileName(file)));
					request.Dispose();
					continue;
				}
				AudioClip content = DownloadHandlerAudioClip.GetContent(request);
				if ((Object)(object)content != (Object)null && content.samples > 0 && content.length > 0.1f)
				{
					((Object)content).name = Path.GetFileNameWithoutExtension(file);
					Clips[NormalizeName(((Object)content).name)] = content;
				}
				else if ((Object)(object)content != (Object)null)
				{
					EmpressSNESPackPlugin.Log.LogWarning((object)("Skipped empty SNES cart audio: " + Path.GetFileName(file)));
				}
				request.Dispose();
			}
			EmpressSNESPackPlugin.Log.LogInfo((object)("Loaded " + Clips.Count + " Empress SNES cart audio files."));
		}

		public static bool TryGetClip(IEnumerable<string> names, out AudioClip clip)
		{
			foreach (string name in names)
			{
				if (name != null && Clips.TryGetValue(NormalizeName(name), out clip))
				{
					return true;
				}
			}
			if (Clips.Count == 1)
			{
				using Dictionary<string, AudioClip>.ValueCollection.Enumerator enumerator2 = Clips.Values.GetEnumerator();
				if (enumerator2.MoveNext())
				{
					AudioClip current2 = enumerator2.Current;
					clip = current2;
					return true;
				}
			}
			clip = null;
			return false;
		}

		private static List<string> FindAudioFiles(string pluginDirectory)
		{
			HashSet<string> seen = new HashSet<string>(StringComparer.OrdinalIgnoreCase);
			List<string> list = new List<string>();
			AddAudioFiles(pluginDirectory, seen, list);
			AddAudioFiles(Path.Combine(pluginDirectory, "audio"), seen, list);
			list.Sort(StringComparer.OrdinalIgnoreCase);
			return list;
		}

		private static void AddAudioFiles(string directory, HashSet<string> seen, List<string> files)
		{
			if (!Directory.Exists(directory))
			{
				return;
			}
			string[] files2 = Directory.GetFiles(directory, "*.ogg", SearchOption.TopDirectoryOnly);
			for (int i = 0; i < files2.Length; i++)
			{
				string fullPath = Path.GetFullPath(files2[i]);
				if (seen.Add(fullPath))
				{
					files.Add(fullPath);
				}
			}
		}

		private static string NormalizeName(string value)
		{
			StringBuilder stringBuilder = new StringBuilder(value.Length);
			for (int i = 0; i < value.Length; i++)
			{
				char c = char.ToLowerInvariant(value[i]);
				if (char.IsLetterOrDigit(c))
				{
					stringBuilder.Append(c);
				}
			}
			return stringBuilder.ToString();
		}
	}
	internal sealed class SnesCatalogEntry
	{
		public int Index { get; }

		public string SafeName { get; }

		public string DisplayName { get; }

		public string CoverFile { get; }

		public string PrefabName { get; }

		public SnesCatalogEntry(int index, string safeName, string displayName, string coverFile)
		{
			Index = index;
			SafeName = safeName;
			DisplayName = displayName;
			CoverFile = coverFile;
			PrefabName = "EmpressSNESCart_" + index.ToString("D3", CultureInfo.InvariantCulture) + "_" + safeName;
		}
	}
	internal static class SnesRepoAccess
	{
		private static readonly FieldRef<LevelValuables, List<PrefabRef>> TinyRef = AccessTools.FieldRefAccess<LevelValuables, List<PrefabRef>>("tiny");

		private static readonly FieldRef<LevelValuables, List<PrefabRef>> SmallRef = AccessTools.FieldRefAccess<LevelValuables, List<PrefabRef>>("small");

		private static readonly FieldRef<LevelValuables, List<PrefabRef>> MediumRef = AccessTools.FieldRefAccess<LevelValuables, List<PrefabRef>>("medium");

		private static readonly FieldRef<LevelValuables, List<PrefabRef>> BigRef = AccessTools.FieldRefAccess<LevelValuables, List<PrefabRef>>("big");

		private static readonly FieldRef<LevelValuables, List<PrefabRef>> WideRef = AccessTools.FieldRefAccess<LevelValuables, List<PrefabRef>>("wide");

		private static readonly FieldRef<LevelValuables, List<PrefabRef>> TallRef = AccessTools.FieldRefAccess<LevelValuables, List<PrefabRef>>("tall");

		private static readonly FieldRef<LevelValuables, List<PrefabRef>> VeryTallRef = AccessTools.FieldRefAccess<LevelValuables, List<PrefabRef>>("veryTall");

		private static readonly FieldRef<ValuableObject, Value> ValuePresetRef = AccessTools.FieldRefAccess<ValuableObject, Value>("valuePreset");

		private static readonly FieldRef<ValuableObject, Durability> DurabilityPresetRef = AccessTools.FieldRefAccess<ValuableObject, Durability>("durabilityPreset");

		private static readonly FieldRef<ValuableObject, PhysAttribute> PhysAttributePresetRef = AccessTools.FieldRefAccess<ValuableObject, PhysAttribute>("physAttributePreset");

		private static readonly FieldRef<ValuableObject, Type> VolumeTypeRef = AccessTools.FieldRefAccess<ValuableObject, Type>("volumeType");

		private static readonly FieldRef<ValuableObject, int> DollarValueOverrideRef = AccessTools.FieldRefAccess<ValuableObject, int>("dollarValueOverride");

		private static readonly FieldRef<ValuableObject, bool> DebugVolumeRef = AccessTools.FieldRefAccess<ValuableObject, bool>("debugVolume");

		private static readonly FieldRef<ValuableObject, Gradient> ParticleColorsRef = AccessTools.FieldRefAccess<ValuableObject, Gradient>("particleColors");

		private static readonly FieldRef<Value, float> ValueMinRef = AccessTools.FieldRefAccess<Value, float>("valueMin");

		private static readonly FieldRef<Value, float> ValueMaxRef = AccessTools.FieldRefAccess<Value, float>("valueMax");

		private static readonly FieldRef<Durability, float> FragilityRef = AccessTools.FieldRefAccess<Durability, float>("fragility");

		private static readonly FieldRef<Durability, float> DurabilityRef = AccessTools.FieldRefAccess<Durability, float>("durability");

		private static readonly FieldRef<PhysAttribute, float> MassRef = AccessTools.FieldRefAccess<PhysAttribute, float>("mass");

		private static readonly FieldRef<PhysGrabObject, bool> GrabbedRef = AccessTools.FieldRefAccess<PhysGrabObject, bool>("grabbed");

		private static readonly FieldRef<PhysGrabObject, bool> GrabbedLocalRef = AccessTools.FieldRefAccess<PhysGrabObject, bool>("grabbedLocal");

		private static readonly FieldRef<PhysGrabObject, bool> HeldByLocalPlayerRef = AccessTools.FieldRefAccess<PhysGrabObject, bool>("heldByLocalPlayer");

		private static readonly FieldRef<PhysGrabObject, List<PhysGrabber>> PlayerGrabbingRef = AccessTools.FieldRefAccess<PhysGrabObject, List<PhysGrabber>>("playerGrabbing");

		public static List<PrefabRef> GetList(LevelValuables preset, Type type)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0022: Expected I4, but got Unknown
			return (int)type switch
			{
				0 => TinyRef.Invoke(preset), 
				1 => SmallRef.Invoke(preset), 
				2 => MediumRef.Invoke(preset), 
				3 => BigRef.Invoke(preset), 
				4 => WideRef.Invoke(preset), 
				5 => TallRef.Invoke(preset), 
				6 => VeryTallRef.Invoke(preset), 
				_ => SmallRef.Invoke(preset), 
			};
		}

		public static void ConfigureValuable(ValuableObject valuable, SnesValuableDefinition definition)
		{
			//IL_0042: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Expected I4, but got Unknown
			ValuePresetRef.Invoke(valuable) = CreateValuePreset(definition);
			DurabilityPresetRef.Invoke(valuable) = CreateDurabilityPreset(definition);
			PhysAttributePresetRef.Invoke(valuable) = CreatePhysAttributePreset(definition);
			VolumeTypeRef.Invoke(valuable) = (Type)(int)definition.VolumeType;
			DollarValueOverrideRef.Invoke(valuable) = 0;
			DebugVolumeRef.Invoke(valuable) = false;
			ParticleColorsRef.Invoke(valuable) = CreateParticleGradient(definition);
		}

		public static bool IsGrabbedForAudio(PhysGrabObject physGrabObject)
		{
			List<PhysGrabber> list = PlayerGrabbingRef.Invoke(physGrabObject);
			if (!GrabbedRef.Invoke(physGrabObject) && !GrabbedLocalRef.Invoke(physGrabObject) && !HeldByLocalPlayerRef.Invoke(physGrabObject))
			{
				if (list != null)
				{
					return list.Count > 0;
				}
				return false;
			}
			return true;
		}

		private static Value CreateValuePreset(SnesValuableDefinition definition)
		{
			Value val = ScriptableObject.CreateInstance<Value>();
			((Object)val).hideFlags = (HideFlags)61;
			((Object)val).name = "Value - " + definition.DisplayName;
			ValueMinRef.Invoke(val) = definition.ValueMin;
			ValueMaxRef.Invoke(val) = definition.ValueMax;
			return val;
		}

		private static Durability CreateDurabilityPreset(SnesValuableDefinition definition)
		{
			Durability val = ScriptableObject.CreateInstance<Durability>();
			((Object)val).hideFlags = (HideFlags)61;
			((Object)val).name = "Durability - " + definition.DisplayName;
			FragilityRef.Invoke(val) = Mathf.Clamp(definition.Fragility, 4f, 30f);
			DurabilityRef.Invoke(val) = Mathf.Clamp(definition.Durability, 75f, 100f);
			return val;
		}

		private static PhysAttribute CreatePhysAttributePreset(SnesValuableDefinition definition)
		{
			PhysAttribute val = ScriptableObject.CreateInstance<PhysAttribute>();
			((Object)val).hideFlags = (HideFlags)61;
			((Object)val).name = "PhysAttribute - " + definition.DisplayName;
			MassRef.Invoke(val) = definition.Mass;
			return val;
		}

		private static Gradient CreateParticleGradient(SnesValuableDefinition definition)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0006: Expected O, but got Unknown
			//IL_0010: 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)
			//IL_001f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0027: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0037: Unknown result type (might be due to invalid IL or missing references)
			//IL_0041: Unknown result type (might be due to invalid IL or missing references)
			//IL_0046: 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)
			//IL_0058: Unknown result type (might be due to invalid IL or missing references)
			//IL_005d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0074: Unknown result type (might be due to invalid IL or missing references)
			//IL_0079: Unknown result type (might be due to invalid IL or missing references)
			//IL_008a: Unknown result type (might be due to invalid IL or missing references)
			//IL_008f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a0: 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)
			Gradient val = new Gradient();
			val.SetKeys((GradientColorKey[])(object)new GradientColorKey[3]
			{
				new GradientColorKey(definition.Accent, 0f),
				new GradientColorKey(Color.Lerp(definition.Primary, definition.Secondary, 0.5f), 0.55f),
				new GradientColorKey(definition.Secondary, 1f)
			}, (GradientAlphaKey[])(object)new GradientAlphaKey[3]
			{
				new GradientAlphaKey(1f, 0f),
				new GradientAlphaKey(0.7f, 0.72f),
				new GradientAlphaKey(0f, 1f)
			});
			return val;
		}
	}
	internal sealed class SnesValuableAudioOnGrab : MonoBehaviour
	{
		[SerializeField]
		private string[] _audioNames = Array.Empty<string>();

		private AudioSource _audioSource;

		private PhysGrabObject _physGrabObject;

		private bool _wasGrabbed;

		private float _nextAllowedTime;

		private float _stopGraceUntil;

		public void Configure(string[] audioNames)
		{
			_audioNames = audioNames ?? Array.Empty<string>();
		}

		public void TryPlayFromGrab()
		{
			EnsureComponents();
			RequestPlay();
		}

		private void Awake()
		{
			EnsureComponents();
		}

		private void OnEnable()
		{
			EnsureComponents();
			_wasGrabbed = false;
		}

		private void Update()
		{
			EnsureComponents();
			if (!((Object)(object)_physGrabObject == (Object)null) && !((Object)(object)_audioSource == (Object)null))
			{
				bool flag = SnesRepoAccess.IsGrabbedForAudio(_physGrabObject);
				if (flag && !_wasGrabbed)
				{
					RequestPlay();
				}
				_wasGrabbed = flag;
				if (!flag && _audioSource.isPlaying && Time.time >= _stopGraceUntil)
				{
					_audioSource.Stop();
					_nextAllowedTime = Time.time + 0.2f;
				}
			}
		}

		private void EnsureComponents()
		{
			if ((Object)(object)_physGrabObject == (Object)null)
			{
				_physGrabObject = ((Component)this).GetComponent<PhysGrabObject>();
			}
			if ((Object)(object)_audioSource == (Object)null)
			{
				_audioSource = ((Component)this).GetComponent<AudioSource>() ?? ((Component)this).gameObject.AddComponent<AudioSource>();
			}
			_audioSource.playOnAwake = false;
			_audioSource.loop = true;
			((Behaviour)_audioSource).enabled = true;
			_audioSource.mute = false;
			_audioSource.spatialBlend = 1f;
			_audioSource.rolloffMode = (AudioRolloffMode)0;
			_audioSource.minDistance = 0.8f;
			_audioSource.maxDistance = EmpressSNESPackPlugin.AudioMaxDistance.Value;
			_audioSource.dopplerLevel = 0f;
			_audioSource.priority = 48;
			_audioSource.ignoreListenerPause = true;
		}

		private void RequestPlay()
		{
			if (!(Time.time < _nextAllowedTime))
			{
				_nextAllowedTime = Time.time + 0.75f;
				PlayClip();
			}
		}

		private void PlayClip()
		{
			if (!((Object)(object)_audioSource == (Object)null) && !_audioSource.isPlaying && SnesAudioLibrary.TryGetClip(_audioNames, out var clip) && !((Object)(object)clip == (Object)null) && clip.samples > 0)
			{
				_audioSource.pitch = 1f;
				_audioSource.volume = Mathf.Clamp01(EmpressSNESPackPlugin.AudioVolume.Value);
				_audioSource.maxDistance = EmpressSNESPackPlugin.AudioMaxDistance.Value;
				_audioSource.clip = clip;
				_audioSource.Play();
				_stopGraceUntil = Time.time + 0.6f;
			}
		}
	}
	internal static class SnesValuableAudioPatches
	{
		[HarmonyPatch(typeof(PhysGrabObject), "GrabStarted")]
		[HarmonyPostfix]
		private static void PhysGrabObjectGrabStartedPostfix(PhysGrabObject __instance)
		{
			TryPlay(__instance);
		}

		[HarmonyPatch(typeof(PhysGrabObject), "GrabLinkRPC")]
		[HarmonyPostfix]
		private static void PhysGrabObjectGrabLinkRpcPostfix(PhysGrabObject __instance)
		{
			TryPlay(__instance);
		}

		[HarmonyPatch(typeof(PhysGrabObject), "GrabPlayerAddRPC")]
		[HarmonyPostfix]
		private static void PhysGrabObjectGrabPlayerAddRpcPostfix(PhysGrabObject __instance)
		{
			TryPlay(__instance);
		}

		private static void TryPlay(PhysGrabObject physGrabObject)
		{
			((Component)physGrabObject).GetComponent<SnesValuableAudioOnGrab>()?.TryPlayFromGrab();
		}
	}
	internal sealed class SnesValuableDefinition
	{
		public SnesCatalogEntry Entry { get; }

		public GameObject VisualPrefab { get; }

		public string PrefabName { get; }

		public string DisplayName { get; }

		public Type VolumeType { get; }

		public int ValueMin { get; }

		public int ValueMax { get; }

		public float Fragility { get; }

		public float Durability { get; }

		public float Mass { get; }

		public Color Primary { get; }

		public Color Secondary { get; }

		public Color Accent { get; }

		public Vector3 GrabBoundsCenter { get; }

		public Vector3 GrabBoundsSize { get; }

		public string[] AudioNames { get; }

		public SnesValuableDefinition(SnesCatalogEntry entry, GameObject visualPrefab)
		{
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_010f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0114: Unknown result type (might be due to invalid IL or missing references)
			//IL_0134: Unknown result type (might be due to invalid IL or missing references)
			//IL_0139: Unknown result type (might be due to invalid IL or missing references)
			//IL_0159: Unknown result type (might be due to invalid IL or missing references)
			//IL_015e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0173: 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_018d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0192: Unknown result type (might be due to invalid IL or missing references)
			Entry = entry;
			VisualPrefab = visualPrefab;
			PrefabName = entry.PrefabName + "_Valuable";
			DisplayName = entry.DisplayName;
			VolumeType = (Type)1;
			int num = PriceScore(entry);
			ValueMin = Mathf.Clamp(num, 650, 9000);
			ValueMax = Mathf.Clamp(num + 550 + StableInt(entry.PrefabName, "value", 1250), ValueMin + 300, 11000);
			Fragility = 12f + (float)StableInt(entry.PrefabName, "fragility", 5);
			Durability = 91f + (float)StableInt(entry.PrefabName, "durability", 8);
			Mass = 0.72f + (float)StableInt(entry.PrefabName, "mass", 18) * 0.01f;
			Primary = Color.HSVToRGB(StableUnit(entry.PrefabName, "primary"), 0.62f, 0.92f);
			Secondary = Color.HSVToRGB(StableUnit(entry.PrefabName, "secondary"), 0.58f, 0.72f);
			Accent = Color.HSVToRGB(StableUnit(entry.PrefabName, "accent"), 0.88f, 1f);
			GrabBoundsCenter = new Vector3(0f, 0.18f, 0f);
			GrabBoundsSize = new Vector3(0.72f, 0.22f, 0.52f);
			AudioNames = new string[3] { entry.DisplayName, entry.SafeName, entry.PrefabName };
		}

		public static List<SnesValuableDefinition> CreateAll()
		{
			List<SnesValuableDefinition> list = new List<SnesValuableDefinition>();
			foreach (GameObject visualPrefab in SnesAssets.VisualPrefabs)
			{
				if (SnesAssets.TryGetCatalog(visualPrefab, out var entry))
				{
					list.Add(new SnesValuableDefinition(entry, visualPrefab));
				}
			}
			return list;
		}

		private static int PriceScore(SnesCatalogEntry entry)
		{
			string text = entry.DisplayName.ToLowerInvariant();
			int num = 850 + entry.Index * 18 + StableInt(entry.PrefabName, "base", 1800);
			string[] array = new string[15]
			{
				"bucky", "battletoads", "bubble bobble", "bonk", "bionic", "batman", "blaster master", "dragon", "zelda", "mario",
				"metroid", "kirby", "castlevania", "mega man", "contra"
			};
			string[] array2 = new string[7] { "baseball", "basketball", "golf", "barbie", "jeopardy", "wheel of fortune", "football" };
			string[] array3 = array;
			foreach (string value in array3)
			{
				if (text.Contains(value))
				{
					num += 1150;
				}
			}
			array3 = array2;
			foreach (string value2 in array3)
			{
				if (text.Contains(value2))
				{
					num -= 325;
				}
			}
			if (text.Contains("action 52"))
			{
				num += 1800;
			}
			if (text.Contains("part 2") || text.Contains(" iii") || text.Contains(" iv"))
			{
				num += 525;
			}
			return RoundTo(num, 25);
		}

		private static int RoundTo(int value, int step)
		{
			return Mathf.RoundToInt((float)value / (float)step) * step;
		}

		private static int StableInt(string name, string salt, int maxExclusive)
		{
			return (int)(StableHash(name + ":" + salt) % (uint)Math.Max(maxExclusive, 1));
		}

		private static float StableUnit(string name, string salt)
		{
			return (float)(StableHash(name + ":" + salt) & 0xFFFF) / 65535f;
		}

		private static uint StableHash(string text)
		{
			uint num = 2166136261u;
			for (int i = 0; i < text.Length; i++)
			{
				num ^= text[i];
				num *= 16777619;
			}
			return num;
		}
	}
	internal static class SnesValuableGrabBounds
	{
		public static void Add(Transform root, SnesValuableDefinition definition)
		{
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_0025: 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_003d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_004d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0053: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0064: 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_006b: Unknown result type (might be due to invalid IL or missing references)
			//IL_006e: 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_007b: 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_00a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f6: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e1: 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_0105: Unknown result type (might be due to invalid IL or missing references)
			//IL_0106: Unknown result type (might be due to invalid IL or missing references)
			//IL_0110: Unknown result type (might be due to invalid IL or missing references)
			//IL_0115: Unknown result type (might be due to invalid IL or missing references)
			//IL_011a: Unknown result type (might be due to invalid IL or missing references)
			//IL_011b: Unknown result type (might be due to invalid IL or missing references)
			//IL_011c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0126: Unknown result type (might be due to invalid IL or missing references)
			//IL_012b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0130: Unknown result type (might be due to invalid IL or missing references)
			//IL_0131: Unknown result type (might be due to invalid IL or missing references)
			//IL_0138: Unknown result type (might be due to invalid IL or missing references)
			//IL_0143: Unknown result type (might be due to invalid IL or missing references)
			//IL_014f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0155: Expected O, but got Unknown
			//IL_0155: Unknown result type (might be due to invalid IL or missing references)
			RemoveTemplateColliders(root);
			Bounds val = CalculateVisualBounds(root, definition);
			GameObject val2 = new GameObject("EmpressSNESGrabBounds");
			val2.transform.SetParent(root, false);
			val2.transform.localPosition = root.InverseTransformPoint(((Bounds)(ref val)).center);
			val2.transform.localRotation = Quaternion.identity;
			val2.transform.localScale = Vector3.one;
			Vector3 size = ((Bounds)(ref val)).size;
			Vector3 lossyScale = root.lossyScale;
			size.x = ((lossyScale.x == 0f) ? definition.GrabBoundsSize.x : (size.x / Mathf.Abs(lossyScale.x)));
			size.y = ((lossyScale.y == 0f) ? definition.GrabBoundsSize.y : (size.y / Mathf.Abs(lossyScale.y)));
			size.z = ((lossyScale.z == 0f) ? definition.GrabBoundsSize.z : (size.z / Mathf.Abs(lossyScale.z)));
			size += Vector3.one * 0.012f;
			size = Vector3.Max(size, Vector3.one * 0.05f);
			BoxCollider obj = val2.AddComponent<BoxCollider>();
			obj.center = Vector3.zero;
			obj.size = size;
			((Collider)obj).isTrigger = false;
			ConfigureColliderObject(val2);
			val2.AddComponent<PhysGrabObjectCollider>();
			val2.AddComponent<PhysGrabObjectBoxCollider>().drawGizmos = false;
		}

		private static Bounds CalculateVisualBounds(Transform root, SnesValuableDefinition definition)
		{
			//IL_000b: 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_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_005c: Unknown result type (might be due to invalid IL or missing references)
			//IL_004a: Unknown result type (might be due to invalid IL or missing references)
			//IL_004f: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Unknown result type (might be due to invalid IL or missing references)
			Renderer[] componentsInChildren = ((Component)root).GetComponentsInChildren<Renderer>(true);
			Bounds bounds = default(Bounds);
			((Bounds)(ref bounds))..ctor(root.TransformPoint(definition.GrabBoundsCenter), definition.GrabBoundsSize);
			bool flag = false;
			Renderer[] array = componentsInChildren;
			foreach (Renderer val in array)
			{
				if (val.enabled)
				{
					if (flag)
					{
						((Bounds)(ref bounds)).Encapsulate(val.bounds);
						continue;
					}
					bounds = val.bounds;
					flag = true;
				}
			}
			return bounds;
		}

		private static void ConfigureColliderObject(GameObject gameObject)
		{
			gameObject.tag = "Phys Grab Object";
			int num = LayerMask.NameToLayer("PhysGrabObject");
			if (num >= 0)
			{
				gameObject.layer = num;
			}
		}

		private static void RemoveTemplateColliders(Transform root)
		{
			PhysGrabObjectCollider[] componentsInChildren = ((Component)root).GetComponentsInChildren<PhysGrabObjectCollider>(true);
			for (int i = 0; i < componentsInChildren.Length; i++)
			{
				DestroyComponent((Component)(object)componentsInChildren[i]);
			}
			PhysGrabObjectBoxCollider[] componentsInChildren2 = ((Component)root).GetComponentsInChildren<PhysGrabObjectBoxCollider>(true);
			for (int i = 0; i < componentsInChildren2.Length; i++)
			{
				DestroyComponent((Component)(object)componentsInChildren2[i]);
			}
			PhysGrabObjectMeshCollider[] componentsInChildren3 = ((Component)root).GetComponentsInChildren<PhysGrabObjectMeshCollider>(true);
			for (int i = 0; i < componentsInChildren3.Length; i++)
			{
				DestroyComponent((Component)(object)componentsInChildren3[i]);
			}
			Collider[] componentsInChildren4 = ((Component)root).GetComponentsInChildren<Collider>(true);
			for (int i = 0; i < componentsInChildren4.Length; i++)
			{
				DestroyComponent((Component)(object)componentsInChildren4[i]);
			}
		}

		private static void DestroyComponent(Component component)
		{
			if ((Object)(object)component != (Object)null)
			{
				Object.DestroyImmediate((Object)(object)component);
			}
		}
	}
	internal sealed class SnesValuablePrefabFactory
	{
		private static readonly List<string> GenericPreset = new List<string> { "Valuables - Generic" };

		private static readonly Type[] VolumeTypes;

		private readonly ManualLogSource _log;

		private readonly Dictionary<Type, GameObject> _templates = new Dictionary<Type, GameObject>();

		private GameObject _prefabBank;

		public SnesValuablePrefabFactory(ManualLogSource log)
		{
			_log = log;
		}

		public int RegisterAll()
		{
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			ResolveTemplates();
			if (_templates.Count == 0)
			{
				_log.LogError((object)"No vanilla valuable templates were available.");
				return 0;
			}
			int num = 0;
			foreach (SnesValuableDefinition item in SnesValuableDefinition.CreateAll())
			{
				GameObject template = GetTemplate(item.VolumeType);
				if ((Object)(object)template == (Object)null)
				{
					_log.LogWarning((object)("Skipping " + item.DisplayName + ": no valuable template exists."));
				}
				else if (Valuables.RegisterValuable(CreatePrefab(item, template), GenericPreset) == null)
				{
					_log.LogWarning((object)("REPOLib rejected " + item.DisplayName + "."));
				}
				else
				{
					num++;
				}
			}
			return num;
		}

		private void ResolveTemplates()
		{
			//IL_0031: 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_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_0061: Unknown result type (might be due to invalid IL or missing references)
			_templates.Clear();
			foreach (LevelValuables value in ValuablePresets.AllValuablePresets.Values)
			{
				Type[] volumeTypes = VolumeTypes;
				foreach (Type val in volumeTypes)
				{
					if (!_templates.ContainsKey(val))
					{
						GameObject val2 = FindTemplateInList(SnesRepoAccess.GetList(value, val));
						if ((Object)(object)val2 != (Object)null)
						{
							_templates.Add(val, val2);
						}
					}
				}
			}
		}

		private static GameObject FindTemplateInList(List<PrefabRef> prefabRefs)
		{
			if (prefabRefs == null)
			{
				return null;
			}
			foreach (PrefabRef prefabRef in prefabRefs)
			{
				if (prefabRef != null && prefabRef.IsValid())
				{
					GameObject prefab = prefabRef.Prefab;
					if ((Object)(object)prefab != (Object)null && (Object)(object)prefab.GetComponent<ValuableObject>() != (Object)null)
					{
						return prefab;
					}
				}
			}
			return null;
		}

		private GameObject GetTemplate(Type type)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			if (_templates.TryGetValue(type, out var value) && (Object)(object)value != (Object)null)
			{
				return value;
			}
			if (_templates.TryGetValue((Type)1, out value) && (Object)(object)value != (Object)null)
			{
				return value;
			}
			if (_templates.TryGetValue((Type)2, out value) && (Object)(object)value != (Object)null)
			{
				return value;
			}
			foreach (GameObject value2 in _templates.Values)
			{
				if ((Object)(object)value2 != (Object)null)
				{
					return value2;
				}
			}
			return null;
		}

		private GameObject CreatePrefab(SnesValuableDefinition definition, GameObject template)
		{
			GameObject val = EnsurePrefabBank();
			GameObject val2 = Object.Instantiate<GameObject>(template, val.transform, false);
			((Object)val2).name = definition.PrefabName;
			((Object)val2).hideFlags = (HideFlags)61;
			val2.SetActive(true);
			SnesRepoAccess.ConfigureValuable(val2.GetComponent<ValuableObject>(), definition);
			DisableTemplateRenderers(val2);
			SnesAssets.TryAttachVisual(val2.transform, definition.VisualPrefab);
			SnesValuableGrabBounds.Add(val2.transform, definition);
			(val2.GetComponent<SnesValuableAudioOnGrab>() ?? val2.AddComponent<SnesValuableAudioOnGrab>()).Configure(definition.AudioNames);
			return val2;
		}

		private GameObject EnsurePrefabBank()
		{
			//IL_001b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Expected O, but got Unknown
			if ((Object)(object)_prefabBank != (Object)null)
			{
				return _prefabBank;
			}
			_prefabBank = new GameObject("EmpressSNESPack Prefab Bank")
			{
				hideFlags = (HideFlags)61
			};
			_prefabBank.SetActive(false);
			Object.DontDestroyOnLoad((Object)(object)_prefabBank);
			return _prefabBank;
		}

		private static void DisableTemplateRenderers(GameObject prefab)
		{
			Renderer[] componentsInChildren = prefab.GetComponentsInChildren<Renderer>(true);
			for (int i = 0; i < componentsInChildren.Length; i++)
			{
				componentsInChildren[i].enabled = false;
			}
		}

		static SnesValuablePrefabFactory()
		{
			Type[] array = new Type[7];
			RuntimeHelpers.InitializeArray(array, (RuntimeFieldHandle)/*OpCode not supported: LdMemberToken*/);
			VolumeTypes = (Type[])(object)array;
		}
	}
}