Decompiled source of RecipeRandomizer Il2cpp v1.0.5

RecipeRandomizer.dll

Decompiled a week ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using System.Text;
using HarmonyLib;
using Il2CppFishNet.Connection;
using Il2CppInterop.Runtime.InteropTypes.Arrays;
using Il2CppScheduleOne;
using Il2CppScheduleOne.DevUtilities;
using Il2CppScheduleOne.ItemFramework;
using Il2CppScheduleOne.Persistence.Datas;
using Il2CppScheduleOne.Persistence.ItemLoaders;
using Il2CppScheduleOne.Persistence.Loaders;
using Il2CppScheduleOne.Product;
using Il2CppScheduleOne.Properties;
using Il2CppScheduleOne.UI;
using Il2CppSystem.Collections.Generic;
using MelonLoader;
using MelonLoader.Utils;
using Newtonsoft.Json.Linq;
using RecipeRandomizerNs;
using UnityEngine;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: MelonInfo(typeof(global::RecipeRandomizerNs.RecipeRandomizerNs), "RecipeRandomizer", "1.0.0", "xVilho", null)]
[assembly: MelonColor(255, 180, 55, 255)]
[assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")]
[assembly: AssemblyCompany("RecipeRandomizer")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0+0c6c593d6e4ffcef53498a04e8153dd1891763e3")]
[assembly: AssemblyProduct("RecipeRandomizer")]
[assembly: AssemblyTitle("RecipeRandomizer")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.0.0.0")]
[module: UnverifiableCode]
namespace RecipeRandomizerNs;

public static class SaveHelper
{
	internal static string LatestSaveFolder;

	internal static bool OverrideSeed = true;

	internal static int CustomSeed = 123456789;

	internal static List<string> CustomName1 = new List<string>();

	internal static List<string> CustomName2 = new List<string>();

	private static string ConfigJsonPath => Path.Combine(MelonEnvironment.ModsDirectory, "RecipeRandomizerConfig.json");

	public static void LoadOrCreateConfig()
	{
		//IL_000f: 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_0065: Unknown result type (might be due to invalid IL or missing references)
		//IL_0076: Unknown result type (might be due to invalid IL or missing references)
		//IL_008b: Unknown result type (might be due to invalid IL or missing references)
		//IL_0091: Unknown result type (might be due to invalid IL or missing references)
		//IL_0096: Unknown result type (might be due to invalid IL or missing references)
		//IL_00a6: Unknown result type (might be due to invalid IL or missing references)
		//IL_00b6: Unknown result type (might be due to invalid IL or missing references)
		//IL_00c6: Unknown result type (might be due to invalid IL or missing references)
		//IL_00db: Expected O, but got Unknown
		//IL_00db: 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_00e6: 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_0106: Unknown result type (might be due to invalid IL or missing references)
		//IL_0116: Unknown result type (might be due to invalid IL or missing references)
		//IL_012b: Expected O, but got Unknown
		//IL_012c: Expected O, but got Unknown
		if (!File.Exists(ConfigJsonPath))
		{
			JObject val = new JObject
			{
				["_MaxSeedComment"] = JToken.op_Implicit($"Set seed between -{int.MaxValue} - {int.MaxValue}"),
				["OverrideSeed"] = JToken.op_Implicit(true),
				["CustomSeed"] = JToken.op_Implicit(int.MaxValue)
			};
			JArray val2 = new JArray();
			val2.Add(JToken.op_Implicit("Cosmic"));
			val2.Add(JToken.op_Implicit("Quantum"));
			val2.Add(JToken.op_Implicit("Giga"));
			val2.Add(JToken.op_Implicit("Turbo"));
			val["Name1"] = (JToken)val2;
			JArray val3 = new JArray();
			val3.Add(JToken.op_Implicit("Crunch"));
			val3.Add(JToken.op_Implicit("Goblin"));
			val3.Add(JToken.op_Implicit("Pickle"));
			val3.Add(JToken.op_Implicit("Vortex"));
			val["Name2"] = (JToken)val3;
			JObject val4 = val;
			File.WriteAllText(ConfigJsonPath, ((object)val4).ToString());
			RecipeRandomizerNs.Log("\ud83d\udee0\ufe0f Created default Config.json");
		}
		JObject obj = JObject.Parse(File.ReadAllText(ConfigJsonPath));
		JToken obj2 = obj["OverrideSeed"];
		OverrideSeed = obj2 != null && Extensions.Value<bool>((IEnumerable<JToken>)obj2);
		JToken obj3 = obj["CustomSeed"];
		CustomSeed = ((obj3 != null) ? Extensions.Value<int>((IEnumerable<JToken>)obj3) : 123456789);
		JToken obj4 = obj["Name1"];
		CustomName1 = ((obj4 != null) ? obj4.ToObject<List<string>>() : null) ?? new List<string>();
		JToken obj5 = obj["Name2"];
		CustomName2 = ((obj5 != null) ? obj5.ToObject<List<string>>() : null) ?? new List<string>();
		RecipeRandomizerNs.Logger.Msg($"✅ Loaded Config.json: OverrideSeed={OverrideSeed}, CustomSeed={CustomSeed}, Name1={CustomName1.Count}, Name2={CustomName2.Count}");
	}

	public static int LoadSaveSeed()
	{
		try
		{
			if (OverrideSeed)
			{
				RecipeRandomizerNs.Log($"[SaveHelper] \ud83d\ude80 Using override seed {CustomSeed}");
				return CustomSeed;
			}
			string text = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData).Replace("Local", "LocalLow", StringComparison.OrdinalIgnoreCase), "TVGS", "Schedule I", "Saves");
			if (!Directory.Exists(text))
			{
				RecipeRandomizerNs.LogWarning("❌ Save root folder not found: " + text);
				return 0;
			}
			string[] directories = Directory.GetDirectories(text);
			if (directories.Length == 0)
			{
				RecipeRandomizerNs.LogWarning("❌ No SteamID folders found.");
				return 0;
			}
			DirectoryInfo directoryInfo = new DirectoryInfo(directories[0]);
			DirectoryInfo directoryInfo2 = null;
			DirectoryInfo[] directories2 = directoryInfo.GetDirectories("SaveGame_*");
			foreach (DirectoryInfo directoryInfo3 in directories2)
			{
				if (directoryInfo2 == null || directoryInfo3.LastWriteTimeUtc > directoryInfo2.LastWriteTimeUtc)
				{
					directoryInfo2 = directoryInfo3;
				}
			}
			if (directoryInfo2 == null)
			{
				RecipeRandomizerNs.LogWarning("❌ No SaveGame_* directories inside: " + directoryInfo.FullName);
				return 0;
			}
			LatestSaveFolder = directoryInfo2.FullName;
			RecipeRandomizerNs.Log("\ud83d\udcc2 Found latest save folder: " + Path.GetFileName(LatestSaveFolder));
			string path = Path.Combine(LatestSaveFolder, "Game.json");
			if (!File.Exists(path))
			{
				RecipeRandomizerNs.LogWarning("❌ Game.json not found in save");
				return 0;
			}
			JToken obj = JObject.Parse(File.ReadAllText(path))["Seed"];
			int num = ((obj != null) ? Extensions.Value<int>((IEnumerable<JToken>)obj) : 0);
			RecipeRandomizerNs.Log($"\ud83d\udce6 Loaded seed from Game.json: {num}");
			return num;
		}
		catch (Exception ex)
		{
			RecipeRandomizerNs.LogError("❌ Exception during LoadSaveSeed: " + ex.Message);
			return 0;
		}
	}
}
public class RecipeRandomizerNs : MelonMod
{
	[CompilerGenerated]
	private sealed class <StartupCoroutine>d__12 : IEnumerator<object>, IEnumerator, IDisposable
	{
		private int <>1__state;

		private object <>2__current;

		object IEnumerator<object>.Current
		{
			[DebuggerHidden]
			get
			{
				return <>2__current;
			}
		}

		object IEnumerator.Current
		{
			[DebuggerHidden]
			get
			{
				return <>2__current;
			}
		}

		[DebuggerHidden]
		public <StartupCoroutine>d__12(int <>1__state)
		{
			this.<>1__state = <>1__state;
		}

		[DebuggerHidden]
		void IDisposable.Dispose()
		{
			<>1__state = -2;
		}

		private bool MoveNext()
		{
			switch (<>1__state)
			{
			default:
				return false;
			case 0:
				<>1__state = -1;
				if (Logger == null)
				{
					return false;
				}
				SaveSeed = SaveHelper.LoadSaveSeed();
				Logger.Msg($"Save Seed loaded: {SaveSeed}");
				Log("Waiting for ProductManager...");
				break;
			case 1:
				<>1__state = -1;
				break;
			}
			if ((Object)(object)NetworkSingleton<ProductManager>.Instance == (Object)null)
			{
				<>2__current = null;
				<>1__state = 1;
				return true;
			}
			Log("ProductManager ready.");
			Il2CppArrayBase<Property> obj = Resources.FindObjectsOfTypeAll<Property>();
			List<Property> val = new List<Property>(obj.Length);
			foreach (Property item in obj)
			{
				val.Add(item);
			}
			CachedAllEffects = val;
			Log($"Cached {CachedAllEffects.Count} Property effects.");
			return false;
		}

		bool IEnumerator.MoveNext()
		{
			//ILSpy generated this explicit interface implementation from .override directive in MoveNext
			return this.MoveNext();
		}

		[DebuggerHidden]
		void IEnumerator.Reset()
		{
			throw new NotSupportedException();
		}
	}

	internal static Instance Logger;

	private static readonly bool DebugLog;

	private static readonly bool DebugWarning;

	private static readonly bool DebugLogError;

	public static List<Property> CachedAllEffects;

	public static int SaveSeed;

	private Harmony harmony;

	public static void Log(string msg)
	{
		if (DebugLog && Logger != null)
		{
			Logger.Msg(msg);
		}
	}

	public static void LogWarning(string msg)
	{
		if (DebugWarning && Logger != null)
		{
			Logger.Warning(msg);
		}
	}

	public static void LogError(string msg)
	{
		if (DebugLogError && Logger != null)
		{
			Logger.Error(msg);
		}
	}

	public override void OnInitializeMelon()
	{
		//IL_001b: Unknown result type (might be due to invalid IL or missing references)
		//IL_0025: Expected O, but got Unknown
		Logger = ((MelonBase)this).LoggerInstance;
		Log("Initialized.");
		harmony = new Harmony("recipe.randomizer.patch");
	}

	public override void OnSceneWasLoaded(int buildIndex, string sceneName)
	{
		if (Logger == null)
		{
			return;
		}
		Log($"Scene loaded: {sceneName} ({buildIndex})");
		if (sceneName == "Menu")
		{
			SaveHelper.LoadOrCreateConfig();
		}
		if (sceneName == "Main")
		{
			Log("Main Scene loaded. Applying Harmony patches and starting randomization coroutine...");
			try
			{
				harmony.PatchAll();
				Log("Harmony patches applied.");
			}
			catch (Exception value)
			{
				LogError($"Harmony patching failed: {value}");
			}
			MelonCoroutines.Start(StartupCoroutine());
		}
	}

	[IteratorStateMachine(typeof(<StartupCoroutine>d__12))]
	private static IEnumerator StartupCoroutine()
	{
		//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
		return new <StartupCoroutine>d__12(0);
	}
}
[HarmonyPatch(typeof(PropertyMixCalculator), "MixProperties")]
public static class PropertyMixCalculator_Patch
{
	private static readonly Dictionary<int, List<Property>> _cache = new Dictionary<int, List<Property>>();

	public static void Postfix(List<Property> existingProperties, Property newProperty, ref List<Property> __result)
	{
		if (RecipeRandomizerNs.Logger == null || RecipeRandomizerNs.SaveSeed == 0)
		{
			return;
		}
		existingProperties = existingProperties ?? new List<Property>();
		__result = __result ?? new List<Property>();
		if ((Object)(object)NetworkSingleton<ProductManager>.Instance.GetRecipe(existingProperties, newProperty) != (Object)null)
		{
			return;
		}
		int num = RecipeRandomizerNs.SaveSeed;
		Enumerator<Property> enumerator = existingProperties.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current = enumerator.Current;
			num ^= StableHash(((Object)current).name);
		}
		if ((Object)(object)newProperty != (Object)null)
		{
			num ^= StableHash(((Object)newProperty).name);
		}
		Random random = new Random(num);
		List<Property> val = default(List<Property>);
		if (_cache.TryGetValue(num, ref val))
		{
			List<Property> val2 = new List<Property>();
			enumerator = val.GetEnumerator();
			while (enumerator.MoveNext())
			{
				Property current2 = enumerator.Current;
				val2.Add(current2);
			}
			__result = val2;
			return;
		}
		List<Property> val3 = new List<Property>();
		List<Property> val4 = new List<Property>();
		enumerator = RecipeRandomizerNs.CachedAllEffects.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current3 = enumerator.Current;
			val4.Add(current3);
		}
		enumerator = existingProperties.GetEnumerator();
		while (enumerator.MoveNext())
		{
			_ = enumerator.Current;
			if (val4.Count == 0)
			{
				break;
			}
			int num2 = random.Next(val4.Count);
			val3.Add(val4[num2]);
			val4.RemoveAt(num2);
		}
		if ((Object)(object)newProperty != (Object)null && !val3.Contains(newProperty) && val3.Count < 8)
		{
			val3.Add(newProperty);
		}
		List<Property> val5 = new List<Property>();
		enumerator = val3.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current4 = enumerator.Current;
			val5.Add(current4);
		}
		_cache[num] = val5;
		__result = val3;
	}

	private static int StableHash(string s)
	{
		int num = -2128831035;
		byte[] bytes = Encoding.UTF8.GetBytes(s);
		foreach (byte b in bytes)
		{
			num = (num ^ b) * 16777619;
		}
		return num;
	}

	public static void ClearCache()
	{
		_cache.Clear();
	}
}
[HarmonyPatch(typeof(NewMixScreen), "Awake")]
public static class NewMixScreen_Awake_Patch
{
	public static void Postfix(NewMixScreen __instance)
	{
		if ((Object)(object)__instance == (Object)null || RecipeRandomizerNs.Logger == null)
		{
			RecipeRandomizerNs.LogError("NewMixScreen instance is null in Awake Postfix.");
			return;
		}
		RecipeRandomizerNs.Log("Attempting to add custom names via NewMixScreen.Awake Postfix...");
		try
		{
			FieldInfo fieldInfo = AccessTools.Field(typeof(NewMixScreen), "name1Library");
			FieldInfo fieldInfo2 = AccessTools.Field(typeof(NewMixScreen), "name2Library");
			if (fieldInfo != null && fieldInfo.GetValue(__instance) is List<string> list && SaveHelper.CustomName1.Count > 0)
			{
				if (!list.Contains(SaveHelper.CustomName1[0]))
				{
					list.AddRange(SaveHelper.CustomName1.ToArray());
					RecipeRandomizerNs.Log($"Added {SaveHelper.CustomName1.Count} custom names to name1Library.");
				}
				else
				{
					RecipeRandomizerNs.Log("Custom names already added to name1Library. Skipping.");
				}
			}
			if (fieldInfo2 != null && fieldInfo2.GetValue(__instance) is List<string> list2)
			{
				if (!list2.Contains(SaveHelper.CustomName2[0]))
				{
					list2.AddRange(SaveHelper.CustomName2);
					RecipeRandomizerNs.Log($"Added {SaveHelper.CustomName2.Count} custom names to name2Library.");
				}
				else
				{
					RecipeRandomizerNs.Log("Custom names already added to name2Library. Skipping.");
				}
			}
		}
		catch (Exception ex)
		{
			RecipeRandomizerNs.LogError("Exception patching NewMixScreen.Awake: " + ex.Message);
		}
	}
}
public class CustomProductState
{
	public float RandomPotency;

	public List<Property> RandomizedEffects = new List<Property>();
}
public static class CustomProductManager
{
	private static readonly Dictionary<string, CustomProductState> registry = new Dictionary<string, CustomProductState>();

	public static void Register(string id, CustomProductState state)
	{
		if (!string.IsNullOrEmpty(id) && state != null)
		{
			registry[id] = state;
		}
	}

	public static bool TryGet(string id, out CustomProductState state)
	{
		return registry.TryGetValue(id, out state);
	}

	public static void Clear()
	{
		registry.Clear();
	}
}
[HarmonyPatch]
public static class ProductManager_CreateWeed_Patch
{
	private static MethodBase TargetMethod()
	{
		return typeof(ProductManager).GetMethod("CreateWeed", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[6]
		{
			typeof(NetworkConnection),
			typeof(string),
			typeof(string),
			typeof(EDrugType),
			typeof(List<string>),
			typeof(WeedAppearanceSettings)
		}, null);
	}

	private static void Postfix(NetworkConnection conn, string name, string id, EDrugType type, List<string> properties, WeedAppearanceSettings appearance)
	{
		RecipeRandomizerNs.Log("CreateWeed called for product ID: " + id);
		if (CustomProductManager.TryGet(id, out var _))
		{
			return;
		}
		if (RecipeRandomizerNs.CachedAllEffects == null || RecipeRandomizerNs.CachedAllEffects.Count == 0)
		{
			RecipeRandomizerNs.LogWarning("No effects cached");
			return;
		}
		Random random = new Random(RecipeRandomizerNs.SaveSeed ^ StableHash(id));
		List<Property> randomizedEffects = new List<Property>();
		List<Property> val = new List<Property>(RecipeRandomizerNs.CachedAllEffects.Count);
		Enumerator<Property> enumerator = RecipeRandomizerNs.CachedAllEffects.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current = enumerator.Current;
			val.Add(current);
		}
		float randomPotency = (float)(random.NextDouble() * 5.0 + 1.0);
		CustomProductManager.Register(id, new CustomProductState
		{
			RandomPotency = randomPotency,
			RandomizedEffects = randomizedEffects
		});
		RecipeRandomizerNs.Log("Registered state for " + id);
	}

	private static int StableHash(string s)
	{
		int num = -2128831035;
		byte[] bytes = Encoding.UTF8.GetBytes(s);
		foreach (byte b in bytes)
		{
			num = (num ^ b) * 16777619;
		}
		return num;
	}
}
[HarmonyPatch]
public static class ProductManager_CreateMeth_Patch
{
	private static MethodBase TargetMethod()
	{
		return typeof(ProductManager).GetMethod("CreateMeth", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[6]
		{
			typeof(NetworkConnection),
			typeof(string),
			typeof(string),
			typeof(EDrugType),
			typeof(List<string>),
			typeof(MethAppearanceSettings)
		}, null);
	}

	private static void Postfix(NetworkConnection conn, string name, string id, EDrugType type, List<string> properties, MethAppearanceSettings appearance)
	{
		RecipeRandomizerNs.Log("\ud83d\udc8a CreateMeth called for product ID: " + id);
		if (CustomProductManager.TryGet(id, out var _))
		{
			return;
		}
		if (RecipeRandomizerNs.CachedAllEffects == null || RecipeRandomizerNs.CachedAllEffects.Count == 0)
		{
			RecipeRandomizerNs.LogWarning("❌ No Property effects cached!");
			return;
		}
		Random random = new Random(RecipeRandomizerNs.SaveSeed ^ StableHash(id));
		List<Property> val = new List<Property>();
		List<Property> val2 = new List<Property>(RecipeRandomizerNs.CachedAllEffects.Count);
		Enumerator<Property> enumerator = RecipeRandomizerNs.CachedAllEffects.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current = enumerator.Current;
			val2.Add(current);
		}
		for (int i = 0; i < properties.Count; i++)
		{
			if (val2.Count <= 0)
			{
				break;
			}
			int num = random.Next(val2.Count);
			val.Add(val2[num]);
			val2.RemoveAt(num);
		}
		float randomPotency = (float)(random.NextDouble() * 5.0 + 1.0);
		CustomProductManager.Register(id, new CustomProductState
		{
			RandomPotency = randomPotency,
			RandomizedEffects = val
		});
		RecipeRandomizerNs.Log("\ud83d\udce6 Registered custom Meth state for " + id);
	}

	private static int StableHash(string s)
	{
		int num = -2128831035;
		byte[] bytes = Encoding.UTF8.GetBytes(s);
		foreach (byte b in bytes)
		{
			num = (num ^ b) * 16777619;
		}
		return num;
	}
}
[HarmonyPatch]
public static class ProductManager_CreateCocaine_Patch
{
	private static MethodBase TargetMethod()
	{
		return typeof(ProductManager).GetMethod("CreateCocaine", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[6]
		{
			typeof(NetworkConnection),
			typeof(string),
			typeof(string),
			typeof(EDrugType),
			typeof(List<string>),
			typeof(CocaineAppearanceSettings)
		}, null);
	}

	private static void Postfix(NetworkConnection conn, string name, string id, EDrugType type, List<string> properties, CocaineAppearanceSettings appearance)
	{
		RecipeRandomizerNs.Log("❄\ufe0f CreateCocaine called for product ID: " + id);
		if (CustomProductManager.TryGet(id, out var _))
		{
			return;
		}
		if (RecipeRandomizerNs.CachedAllEffects == null || RecipeRandomizerNs.CachedAllEffects.Count == 0)
		{
			RecipeRandomizerNs.LogWarning("❌ No Property effects cached!");
			return;
		}
		Random random = new Random(RecipeRandomizerNs.SaveSeed ^ StableHash(id));
		List<Property> val = new List<Property>();
		List<Property> val2 = new List<Property>(RecipeRandomizerNs.CachedAllEffects.Count);
		Enumerator<Property> enumerator = RecipeRandomizerNs.CachedAllEffects.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current = enumerator.Current;
			val2.Add(current);
		}
		for (int i = 0; i < properties.Count; i++)
		{
			if (val2.Count <= 0)
			{
				break;
			}
			int num = random.Next(val2.Count);
			val.Add(val2[num]);
			val2.RemoveAt(num);
		}
		float randomPotency = (float)(random.NextDouble() * 5.0 + 1.0);
		CustomProductManager.Register(id, new CustomProductState
		{
			RandomPotency = randomPotency,
			RandomizedEffects = val
		});
		RecipeRandomizerNs.Log("\ud83d\udce6 Registered custom Cocaine state for " + id);
	}

	private static int StableHash(string s)
	{
		int num = -2128831035;
		byte[] bytes = Encoding.UTF8.GetBytes(s);
		foreach (byte b in bytes)
		{
			num = (num ^ b) * 16777619;
		}
		return num;
	}
}
[HarmonyPatch(typeof(ProductItemInstance), "GetItemData")]
public static class ProductItemInstance_GetItemData_Patch
{
	[HarmonyPatch(typeof(WeedLoader), "LoadItem")]
	public static class WeedLoader_LoadItem_Patch
	{
		public static void Postfix(ref ItemInstance __result)
		{
			ItemInstance obj = __result;
			WeedInstance val = (WeedInstance)(object)((obj is WeedInstance) ? obj : null);
			if (val == null || string.IsNullOrEmpty(((ItemInstance)val).ID))
			{
				return;
			}
			Random random = new Random(RecipeRandomizerNs.SaveSeed ^ ((ItemInstance)val).ID.GetHashCode());
			List<Property> val2 = new List<Property>();
			List<Property> val3 = new List<Property>(RecipeRandomizerNs.CachedAllEffects.Count);
			Enumerator<Property> enumerator = RecipeRandomizerNs.CachedAllEffects.GetEnumerator();
			while (enumerator.MoveNext())
			{
				Property current = enumerator.Current;
				val3.Add(current);
			}
			for (int i = 0; i < 3; i++)
			{
				if (val3.Count <= 0)
				{
					break;
				}
				int num = random.Next(val3.Count);
				val2.Add(val3[num]);
				val3.RemoveAt(num);
			}
			float randomPotency = (float)(random.NextDouble() * 5.0 + 1.0);
			CustomProductManager.Register(((ItemInstance)val).ID, new CustomProductState
			{
				RandomPotency = randomPotency,
				RandomizedEffects = val2
			});
			RecipeRandomizerNs.Log("\ud83d\udce6 Registered custom data for Weed " + ((ItemInstance)val).ID);
		}
	}

	public static void Postfix(ProductItemInstance __instance, ref ItemData __result)
	{
		ItemData obj = __result;
		ProductItemData val = (ProductItemData)(object)((obj is ProductItemData) ? obj : null);
		if (val != null && CustomProductManager.TryGet(((ItemInstance)__instance).ID, out var state))
		{
			((ItemData)val).ID = RecipeUtils.AppendCustomSuffix(((ItemData)val).ID, state);
			RecipeRandomizerNs.Log("Appended custom suffix to ProductItemData ID: " + ((ItemData)val).ID);
		}
	}

	private static string AppendCustomSuffix(string originalID, CustomProductState state)
	{
		List<string> list = new List<string>();
		Enumerator<Property> enumerator = state.RandomizedEffects.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current = enumerator.Current;
			list.Add(((Object)current).name);
		}
		string value = string.Join("-", list);
		return $"{originalID}|RP:{state.RandomPotency:0.00}|FX:{value}";
	}
}
public static class RecipeUtils
{
	public static string AppendCustomSuffix(string originalID, CustomProductState state)
	{
		List<string> list = new List<string>();
		Enumerator<Property> enumerator = state.RandomizedEffects.GetEnumerator();
		while (enumerator.MoveNext())
		{
			Property current = enumerator.Current;
			list.Add(((Object)current).name);
		}
		string value = string.Join("-", list);
		return $"{originalID}|RP:{state.RandomPotency:0.00}|FX:{value}";
	}
}
[HarmonyPatch(typeof(WeedProductLoader), "Load")]
public static class WeedProductLoader_Load_Patch
{
	public static void Postfix()
	{
		//IL_0060: Unknown result type (might be due to invalid IL or missing references)
		//IL_0065: Unknown result type (might be due to invalid IL or missing references)
		//IL_0070: Unknown result type (might be due to invalid IL or missing references)
		//IL_0075: Unknown result type (might be due to invalid IL or missing references)
		//IL_0080: 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)
		//IL_0090: Unknown result type (might be due to invalid IL or missing references)
		//IL_0095: Unknown result type (might be due to invalid IL or missing references)
		//IL_009a: Unknown result type (might be due to invalid IL or missing references)
		//IL_00a1: Expected O, but got Unknown
		RecipeRandomizerNs.Log("Postfix: WeedProductLoader.Load invoked");
		ProductManager instance = NetworkSingleton<ProductManager>.Instance;
		List<ProductDefinition> val = ((instance != null) ? instance.createdProducts : null);
		if (val == null)
		{
			RecipeRandomizerNs.LogError("createdProducts is null!");
			return;
		}
		Enumerator<ProductDefinition> enumerator = val.GetEnumerator();
		while (enumerator.MoveNext())
		{
			ProductDefinition current = enumerator.Current;
			WeedDefinition val2 = (WeedDefinition)(object)((current is WeedDefinition) ? current : null);
			if (val2 != null && !CustomProductManager.TryGet(((ItemDefinition)val2).ID, out var _))
			{
				WeedAppearanceSettings val3 = new WeedAppearanceSettings(Color32.op_Implicit(val2.MainMat.color), Color32.op_Implicit(val2.SecondaryMat.color), Color32.op_Implicit(val2.LeafMat.color), Color32.op_Implicit(val2.StemMat.color));
				List<string> val4 = new List<string>();
				Enumerator<Property> enumerator2 = ((PropertyItemDefinition)val2).Properties.GetEnumerator();
				while (enumerator2.MoveNext())
				{
					Property current2 = enumerator2.Current;
					val4.Add(current2.ID);
				}
				WeedDefinition val5 = Object.Instantiate<WeedDefinition>(NetworkSingleton<ProductManager>.Instance.DefaultWeed);
				((Object)val5).name = ((ItemDefinition)val2).Name;
				((ItemDefinition)val5).Name = ((ItemDefinition)val2).Name;
				((ItemDefinition)val5).Description = string.Empty;
				((ItemDefinition)val5).ID = ((ItemDefinition)val2).ID;
				List<EDrugType> val6 = new List<EDrugType>();
				val6.Add((EDrugType)0);
				val5.Initialize(Singleton<PropertyUtility>.Instance.GetProperties(val4), val6, val3);
				NetworkSingleton<ProductManager>.Instance.createdProducts.Add((ProductDefinition)(object)val5);
				NetworkSingleton<ProductManager>.Instance.ProductPrices.Add((ProductDefinition)(object)val5, ((ProductDefinition)val5).MarketValue);
				NetworkSingleton<ProductManager>.Instance.ProductNames.Add(((ItemDefinition)val5).Name);
				Singleton<Registry>.Instance.AddToRegistry((ItemDefinition)(object)val5);
				((ItemDefinition)val5).Icon = Singleton<ProductIconManager>.Instance.GenerateIcons(((ItemDefinition)val5).ID);
				RecipeRandomizerNs.Log(" Rehydrated weed via loader: " + ((ItemDefinition)val2).ID);
			}
		}
	}
}