Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of REPO Alchemy v1.2.1
REPOAlchemy.dll
Decompiled 5 months agousing System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using CustomDiscoverStateLib; using HarmonyLib; using Microsoft.CodeAnalysis; using Photon.Pun; using REPOLib.Modules; using REPOLib.Objects.Sdk; using UnityEngine; using UnityEngine.Events; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")] [assembly: AssemblyCompany("REPOAlchemy")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0")] [assembly: AssemblyProduct("My first plugin")] [assembly: AssemblyTitle("REPOAlchemy")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.0.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)] internal sealed class NullableAttribute : Attribute { public readonly byte[] NullableFlags; public NullableAttribute(byte P_0) { NullableFlags = new byte[1] { P_0 }; } public NullableAttribute(byte[] P_0) { NullableFlags = P_0; } } [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace REPOAlchemy { public class AlchemyItem : MonoBehaviour { [HideInInspector] public bool spawnAsValuable = true; [HideInInspector] public string prefabID; public Color color = Color.white; [HideInInspector] public PhotonView photon; public Sprite icon; [HideInInspector] public bool wasCrafted = false; public float potScale = 1f; [HideInInspector] public bool isOnSource = false; public bool itemPersistent = false; public bool itemPersisting = true; private void Start() { photon = ((Component)this).GetComponent<PhotonView>(); if (wasCrafted && (Object)(object)((Component)this).GetComponent<ItemAttributes>() != (Object)null) { Object.Destroy((Object)(object)((Component)this).GetComponent<ItemAttributes>()); } } [PunRPC] public void SetWasCraftedRPC(bool val) { wasCrafted = val; if (wasCrafted && (Object)(object)((Component)this).GetComponent<ItemAttributes>() != (Object)null) { Object.Destroy((Object)(object)((Component)this).GetComponent<ItemAttributes>()); } } [PunRPC] public void AddGrowerRPC(float scale, float speed) { GrowScale growScale = ((Component)this).GetComponent<GrowScale>(); if ((Object)(object)growScale == (Object)null) { growScale = ((Component)this).gameObject.AddComponent<GrowScale>(); } growScale.targetScale = scale; growScale.speed = speed; } [PunRPC] public void SyncScaleRPC(Vector3 scale) { //IL_0007: Unknown result type (might be due to invalid IL or missing references) ((Component)this).transform.localScale = scale; } } public class Cauldron : MonoBehaviour { public struct Recipe { public Color color; public List<string> ingredients; public string result; public Sprite icon; public bool isIngredient; public Recipe(List<string> Ingredients, string Result, Sprite Icon, Color Col, bool isIngredient) { //IL_0017: 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) ingredients = Ingredients; result = Result; icon = Icon; color = Col; this.isIngredient = isIngredient; } } [CompilerGenerated] private sealed class <Restock>d__72 : IEnumerator<object>, IDisposable, IEnumerator { private int <>1__state; private object <>2__current; public Cauldron <>4__this; private List<ObjectSource>.Enumerator <>s__1; private ObjectSource <source>5__2; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <Restock>d__72(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>s__1 = default(List<ObjectSource>.Enumerator); <source>5__2 = null; <>1__state = -2; } private bool MoveNext() { //IL_0098: Unknown result type (might be due to invalid IL or missing references) //IL_00a2: Expected O, but got Unknown //IL_0137: Unknown result type (might be due to invalid IL or missing references) //IL_0141: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>4__this.restocking = true; <>4__this.restockStacks++; if (SemiFunc.IsMultiplayer() && SemiFunc.IsMasterClient()) { <>4__this.photon.RPC("RestockRPC", (RpcTarget)1, Array.Empty<object>()); } <>4__this.PlayRestock(); <>2__current = (object)new WaitForSeconds(0.35f); <>1__state = 1; return true; case 1: <>1__state = -1; <>s__1 = <>4__this.sources.GetEnumerator(); try { while (<>s__1.MoveNext()) { <source>5__2 = <>s__1.Current; <>4__this.RestockItem(<source>5__2); <source>5__2 = null; } } finally { ((IDisposable)<>s__1).Dispose(); } <>s__1 = default(List<ObjectSource>.Enumerator); <>4__this.CheckIndicators(); <>2__current = (object)new WaitForSeconds(0.525f); <>1__state = 2; return true; case 2: <>1__state = -1; <>4__this.restockStacks--; if (<>4__this.restockStacks == 0) { <>4__this.restocking = false; } 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(); } } public static Cauldron instance; private Rigidbody rb; private PhysGrabObjectGrabArea handle; private Vector3 oldVel = Vector3.zero; private float shakeAmount = 0f; private float shakeDecay = 20f; private float shakeMax = 70f; private Animator animator; private bool restocking = false; private PhotonView photon; private Transform shakeIndicator; private SpriteRenderer spriteRenderer; private List<SpriteRenderer> indicators; private float lidOpenDuration = 0f; private List<string> sourceIDs = new List<string>(); private ItemEquippable equippable; private int inventoryPage = 0; private Dictionary<string, int> inventory = new Dictionary<string, int>(); private List<string> inventoryOrder = new List<string>(); public AudioClip openSound; public AudioClip closeSound; public AudioClip restockSound; public List<AudioClip> shakeSounds; public static List<Recipe> recipes = new List<Recipe>(); public List<ObjectSource> sources = new List<ObjectSource>(); private List<AlchemyItem> itemsInPot = new List<AlchemyItem>(); private Recipe activeRecipe; private bool lidOpen; private float checkCooldown = 0f; private bool oldEquipped = false; private bool oldState = false; private List<Ingredient> funneledIngredients = new List<Ingredient>(); private float finishLightPower = 0f; private float shakeSoundCooldown = 0f; private int restockStacks = 0; private void Start() { //IL_0135: Unknown result type (might be due to invalid IL or missing references) //IL_013f: Expected O, but got Unknown Transform val = ((Component)this).transform.Find("Model/Cauldron/Armature/Root/RackFlap/Racks"); indicators = new List<SpriteRenderer> { ((Component)val.Find("RackLeft/Indicator.000")).GetComponent<SpriteRenderer>(), ((Component)val.Find("Indicator.001")).GetComponent<SpriteRenderer>(), ((Component)val.Find("Indicator.002")).GetComponent<SpriteRenderer>(), ((Component)val.Find("RackRight/Indicator.003")).GetComponent<SpriteRenderer>() }; equippable = ((Component)this).GetComponent<ItemEquippable>(); shakeIndicator = ((Component)this).transform.Find("Model/Cauldron/Armature/Root/ResultScreen/ShakeIcon"); spriteRenderer = ((Component)((Component)this).transform.Find("Model/Cauldron/Armature/Root/ResultScreen/PotionSprite")).GetComponent<SpriteRenderer>(); photon = ((Component)this).GetComponent<PhotonView>(); animator = ((Component)((Component)this).transform.Find("Model/Cauldron")).GetComponent<Animator>(); handle = ((Component)this).GetComponent<PhysGrabObjectGrabArea>(); rb = ((Component)this).GetComponent<Rigidbody>(); CheckIndicators(); if (!SemiFunc.IsMasterClientOrSingleplayer()) { return; } foreach (ObjectSource source in sources) { source.objectUnlocked.AddListener(new UnityAction(OnIngredientGrab)); } List<string> storeableIngredients = Tools.storeableIngredients; for (int i = 0; i < storeableIngredients.Count; i++) { if (StatsManager.instance.dictionaryOfDictionaries["ingredients"].ContainsKey(storeableIngredients[i])) { SetIngredient(storeableIngredients[i], Math.Min(StatsManager.instance.dictionaryOfDictionaries["ingredients"][storeableIngredients[i]], 2)); StatsManager.instance.dictionaryOfDictionaries["ingredients"][storeableIngredients[i]] = inventory[storeableIngredients[i]]; } if (SemiFunc.RunIsShop() || SemiFunc.RunIsArena() || Plugin.unlimitedIngredients.Value) { SetIngredient(storeableIngredients[i], -1); } } TryRestock(); } private void OnIngredientGrab() { for (int i = 0; i < sources.Count; i++) { if ((Object)(object)sources[i].obj == (Object)null && sources[i].prefabID != null && sources[i].prefabID != "") { string id = Tools.TryGetKey(Tools.ingredients, sources[i].prefabID); ReduceIngredient(id); } } TryRestock(); } private List<PhysGrabObject> ObjectsInCart() { //IL_0013: 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) //IL_0023: 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) Transform transform = ((Component)((Component)this).GetComponent<PhysGrabCart>().physGrabInCart).transform; Collider[] array = Physics.OverlapBox(transform.position, transform.localScale / 2f, transform.rotation); List<PhysGrabObject> list = new List<PhysGrabObject>(); Collider[] array2 = array; foreach (Collider val in array2) { if (((Component)val).gameObject.layer == LayerMask.NameToLayer("PhysGrabObject")) { PhysGrabObject componentInParent = ((Component)val).GetComponentInParent<PhysGrabObject>(); if (!Enumerable.Contains(list, componentInParent)) { list.Add(componentInParent); } } } return list; } private Dictionary<string, int> IngredientDictionary(List<string> ingredients) { Dictionary<string, int> dictionary = new Dictionary<string, int>(); foreach (string ingredient in ingredients) { if (dictionary.ContainsKey(ingredient)) { dictionary[ingredient]++; } else { dictionary.Add(ingredient, 1); } } return dictionary; } private bool CheckIngredients(List<string> ingredients1, List<string> ingredients2) { if (ingredients1.Count != ingredients2.Count) { return false; } Dictionary<string, int> dictionary = IngredientDictionary(ingredients1); Dictionary<string, int> dictionary2 = IngredientDictionary(ingredients2); foreach (string key in dictionary.Keys) { if (!dictionary2.ContainsKey(key)) { return false; } if (dictionary[key] != dictionary2[key]) { return false; } } return true; } private void GetRecipe() { //IL_00e8: Unknown result type (might be due to invalid IL or missing references) Recipe recipe = activeRecipe; List<PhysGrabObject> list = ObjectsInCart(); List<string> list2 = new List<string>(); List<AlchemyItem> list3 = new List<AlchemyItem>(itemsInPot); itemsInPot.Clear(); foreach (PhysGrabObject item in list) { Ingredient component = ((Component)item).GetComponent<Ingredient>(); if ((Object)(object)component != (Object)null) { list2.Add(component.ingredientID); } AlchemyItem component2 = ((Component)item).GetComponent<AlchemyItem>(); if ((Object)(object)component2 != (Object)null) { itemsInPot.Add(component2); } } activeRecipe = default(Recipe); foreach (Recipe recipe2 in recipes) { if (CheckIngredients(recipe2.ingredients, list2)) { SetColor(recipe2.color); activeRecipe = recipe2; break; } } UpdateIcon(activeRecipe); if (SemiFunc.IsMultiplayer() && !recipe.Equals(activeRecipe)) { photon.RPC("SyncRecipeRPC", (RpcTarget)1, new object[1] { recipes.IndexOf(activeRecipe) }); } foreach (AlchemyItem item2 in list3) { if (!((Object)(object)item2 == (Object)null) && !itemsInPot.Contains(item2)) { item2.AddGrowerRPC(1f, 3f); if (SemiFunc.IsMultiplayer()) { item2.photon.RPC("AddGrowerRPC", (RpcTarget)1, new object[2] { 1f, 3f }); } } } foreach (AlchemyItem item3 in itemsInPot) { if (!((Object)(object)item3 == (Object)null) && !list3.Contains(item3)) { item3.AddGrowerRPC(item3.potScale, 3f); if (SemiFunc.IsMultiplayer()) { item3.photon.RPC("AddGrowerRPC", (RpcTarget)1, new object[2] { item3.potScale, 3f }); } } } } [PunRPC] private void SyncRecipeRPC(int recipeIndex) { activeRecipe = recipes[recipeIndex]; UpdateIcon(activeRecipe); } private void SetColor(Color color) { //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_0032: 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_006a: Unknown result type (might be due to invalid IL or missing references) ((Component)((Component)this).transform.Find("ShakeParticles")).GetComponent<ParticleSystem>().startColor = color; ((Component)((Component)this).transform.Find("FinishParticles")).GetComponent<ParticleSystem>().startColor = color; ((Component)((Component)this).transform.Find("ShakeLight")).GetComponent<Light>().color = color; ((Component)((Component)this).transform.Find("FinishLight")).GetComponent<Light>().color = color; } private void Open() { if (shakeAmount / shakeMax > 0.6f) { FinishEffect(); } ShakeLoop(0f); animator.SetBool("Opened", true); ((Component)this).GetComponent<AudioSource>().clip = openSound; ((Component)this).GetComponent<AudioSource>().Play(); } private void Close() { animator.SetBool("Opened", false); ((Component)this).GetComponent<AudioSource>().clip = closeSound; ((Component)this).GetComponent<AudioSource>().Play(); } private void PlayRestock() { animator.SetTrigger("Restock"); ((Component)this).GetComponent<AudioSource>().clip = restockSound; ((Component)this).GetComponent<AudioSource>().Play(); } [PunRPC] private void SetOpenRPC(bool state) { if ((Object)(object)animator != (Object)null) { if (state) { Open(); } else { Close(); } } ((Component)((Component)this).transform.Find("Cart Wall Collider Close")).gameObject.SetActive(!state); ((Component)((Component)this).transform.Find("Cart Wall Collider Open")).gameObject.SetActive(state); } [PunRPC] private void RestockRPC() { if ((Object)(object)animator != (Object)null) { PlayRestock(); } } private void FixedUpdate() { //IL_0087: Unknown result type (might be due to invalid IL or missing references) //IL_008c: Unknown result type (might be due to invalid IL or missing references) //IL_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00b8: 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_00c2: Unknown result type (might be due to invalid IL or missing references) if (SemiFunc.IsMasterClientOrSingleplayer()) { if (checkCooldown <= 0f) { checkCooldown = 0.5f; GetRecipe(); } checkCooldown -= Time.fixedDeltaTime; } UpdateLight(); ((Component)shakeIndicator).gameObject.SetActive(activeRecipe.result != null); if (activeRecipe.result != null) { Vector3 localPosition = shakeIndicator.localPosition; localPosition.x = (float)Math.Sin(Time.time * 30f) * 0.0002f; Quaternion localRotation = shakeIndicator.localRotation; shakeIndicator.SetLocalPositionAndRotation(localPosition, localRotation); } if (!SemiFunc.IsMasterClientOrSingleplayer()) { return; } UpdatePage(); UpdateEquipped(); bool flag = handle.listOfAllGrabbers.Any(); bool flag2 = activeRecipe.result == null || !flag; if (flag2 != lidOpen) { lidOpen = flag2; if (flag2) { Open(); } else { Close(); } ((Component)((Component)this).transform.Find("Cart Wall Collider Close")).gameObject.SetActive(!flag2); ((Component)((Component)this).transform.Find("Cart Wall Collider Open")).gameObject.SetActive(flag2); if (SemiFunc.IsMultiplayer()) { photon.RPC("SetOpenRPC", (RpcTarget)1, new object[1] { flag2 }); } } foreach (ObjectSource source in sources) { if ((Object)(object)source.obj != (Object)null) { ((Component)source.obj).GetComponent<Rigidbody>().detectCollisions = lidOpenDuration > 0.7f && !restocking; } } if (flag2) { lidOpenDuration += Time.fixedDeltaTime; UpdateFunnel(); } else { lidOpenDuration = 0f; } UpdateShake(flag2, activeRecipe); } private void UpdateEquipped() { if (equippable.IsEquipped() == oldEquipped || restocking) { return; } if (equippable.IsEquipped()) { foreach (ObjectSource source in sources) { if ((Object)(object)source.obj != (Object)null) { ((Component)source.obj).GetComponent<PhysGrabObject>().DestroyPhysGrabObject(); } } } else { TryRestock(); } oldEquipped = equippable.IsEquipped(); } private void UpdatePage() { ItemToggle component = ((Component)this).GetComponent<ItemToggle>(); if (component.toggleState != oldState) { oldState = component.toggleState; inventoryPage++; CheckPage(); TryRestock(); } oldState = component.toggleState; } private void CheckPage() { inventoryPage %= Math.Max((inventory.Count + sources.Count - 1) / sources.Count, 1); } private void UpdateIcon(Recipe recipe) { //IL_0053: 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) ((Component)spriteRenderer).gameObject.SetActive(recipe.result != null); ((Component)shakeIndicator).GetComponent<SpriteRenderer>().color = (recipe.isIngredient ? new Color(0.65f, 0f, 1f) : new Color(1f, 0.55f, 0f)); if (recipe.result != null) { spriteRenderer.sprite = recipe.icon; } } private void UpdateFunnel() { //IL_0013: 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) //IL_0023: 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_0199: Unknown result type (might be due to invalid IL or missing references) Transform val = ((Component)this).transform.Find("InFunnel"); Collider[] array = Physics.OverlapBox(val.position, val.localScale / 2f, val.rotation); Collider[] array2 = array; foreach (Collider val2 in array2) { if (((Component)val2).gameObject.layer != LayerMask.NameToLayer("PhysGrabObject")) { continue; } Ingredient componentInParent = ((Component)val2).GetComponentInParent<Ingredient>(); if ((Object)(object)componentInParent != (Object)null && componentInParent.canStore && componentInParent.IsRegistered() && (Object)(object)((Component)componentInParent).GetComponent<GrowScale>() == (Object)null && !componentInParent.isOnSource) { GrowScale growScale = ((Component)componentInParent).gameObject.AddComponent<GrowScale>(); growScale.targetScale = 0.1f; growScale.speed = 5f; if (SemiFunc.IsMultiplayer()) { ((Component)componentInParent).GetComponent<PhotonView>().RPC("AddGrowerRPC", (RpcTarget)1, new object[2] { 0.1f, 5f }); } if (!funneledIngredients.Contains(componentInParent)) { funneledIngredients.Add(componentInParent); } } } foreach (Ingredient funneledIngredient in funneledIngredients) { if ((Object)(object)funneledIngredient == (Object)null) { funneledIngredients.Remove(funneledIngredient); break; } if (((Component)funneledIngredient).transform.localScale.x == 0.1f) { funneledIngredient.AddIngredient(); AddIngredient(funneledIngredient.ingredientID); ((Component)funneledIngredient).GetComponent<PhysGrabObject>().DestroyPhysGrabObject(); } } } private void AddIngredient(string id) { if (inventory.ContainsKey(id)) { if (inventory[id] >= 0) { inventory[id]++; } } else { inventoryOrder.Add(id); inventory.Add(id, 1); } TryRestock(); } private void ReduceIngredient(string id) { if (inventory.ContainsKey(id)) { inventory[id]--; } CheckIngredients(); } private void SetIngredient(string id, int value) { if (inventory.ContainsKey(id)) { inventory[id] = value; return; } inventoryOrder.Add(id); inventory.Add(id, value); } private void CheckIngredients() { foreach (string item in inventory.Keys.ToList()) { if (inventory[item] == 0) { inventory.Remove(item); inventoryOrder.Remove(item); } } CheckPage(); } private void ShakeLoop(float t) { ShakeLoopRPC(t); if (SemiFunc.IsMultiplayer()) { photon.RPC("ShakeLoopRPC", (RpcTarget)1, new object[1] { t }); } } [PunRPC] private void ShakeLoopRPC(float t) { AudioSource component = ((Component)((Component)this).transform.Find("ShakeLoop1")).GetComponent<AudioSource>(); AudioSource component2 = ((Component)((Component)this).transform.Find("ShakeLoop2")).GetComponent<AudioSource>(); Light component3 = ((Component)((Component)this).transform.Find("ShakeLight")).GetComponent<Light>(); ParticleSystem component4 = ((Component)((Component)this).transform.Find("ShakeParticles")).GetComponent<ParticleSystem>(); component4.loop = t > 0.6f; if (component4.loop) { component4.Play(); } component.volume = Mathf.Clamp(t * 3f, 0f, 1f); component.pitch = 1f + t * 0.5f; component2.volume = Mathf.Clamp((t - 0.6f) * 5f, 0f, 1f); component2.pitch = 1f + t * 0.5f; component3.intensity = t * 2f; } private void ShakeSound() { ShakeSoundRPC(); if (SemiFunc.IsMultiplayer()) { photon.RPC("ShakeSoundRPC", (RpcTarget)1, Array.Empty<object>()); } } [PunRPC] public void ShakeSoundRPC() { AudioSource component = ((Component)((Component)this).transform.Find("ShakeSound")).GetComponent<AudioSource>(); component.PlayOneShot(shakeSounds[Random.RandomRangeInt(0, shakeSounds.Count)]); } private void FinishEffect() { FinishEffectRPC(); if (SemiFunc.IsMultiplayer()) { photon.RPC("FinishEffectRPC", (RpcTarget)1, Array.Empty<object>()); } } [PunRPC] public void FinishEffectRPC() { ((Component)((Component)this).transform.Find("FinishParticles")).GetComponent<ParticleSystem>().Play(); finishLightPower = 1.5f; } private void UpdateLight() { finishLightPower = Mathf.Clamp(finishLightPower - Time.fixedDeltaTime, 0f, 1f); ((Component)((Component)this).transform.Find("FinishLight")).GetComponent<Light>().intensity = finishLightPower * 2f; } private void UpdateShake(bool lidOpen, Recipe recipe) { //IL_0002: 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_0012: Unknown result type (might be due to invalid IL or missing references) //IL_0017: 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_002c: Unknown result type (might be due to invalid IL or missing references) Vector3 val = oldVel - rb.velocity; float magnitude = ((Vector3)(ref val)).magnitude; oldVel = rb.velocity; shakeAmount -= shakeDecay * Time.fixedDeltaTime; if (!lidOpen) { shakeAmount += magnitude; if (shakeAmount >= shakeMax) { Craft(recipe); } float num = magnitude / Time.fixedDeltaTime; if (num > 50f && shakeSoundCooldown <= 0f) { shakeSoundCooldown = 0.3f; ShakeSound(); } shakeSoundCooldown -= Time.fixedDeltaTime; ShakeLoop(shakeAmount / shakeMax); shakeAmount = Mathf.Clamp(shakeAmount, 0f, shakeMax); } } private void FinishSound() { FinishSoundRPC(); if (SemiFunc.IsMultiplayer()) { photon.RPC("FinishSoundRPC", (RpcTarget)1, Array.Empty<object>()); } } [PunRPC] public void FinishSoundRPC() { ((Component)((Component)this).transform.Find("FinishSound")).GetComponent<AudioSource>().Play(); } private void Craft(Recipe recipe) { //IL_016d: 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_01a3: Unknown result type (might be due to invalid IL or missing references) //IL_01ae: Unknown result type (might be due to invalid IL or missing references) //IL_0082: Unknown result type (might be due to invalid IL or missing references) FinishEffect(); FinishSound(); shakeAmount = 0f; foreach (PhysGrabObject item in ObjectsInCart()) { Ingredient component = ((Component)item).GetComponent<Ingredient>(); if ((Object)(object)component != (Object)null) { component.UseIngredient(); } if ((Object)(object)((Component)item).GetComponent<EnemyRigidbody>() != (Object)null) { ((Component)((Component)item).transform.parent).GetComponentInChildren<EnemyHealth>().Hurt(500, Vector3.up); } else if ((Object)(object)((Component)item).GetComponent<PlayerTumble>() == (Object)null && (Object)(object)((Component)item).GetComponent<PlayerDeathHead>() == (Object)null) { ItemAttributes component2 = ((Component)item).GetComponent<ItemAttributes>(); if ((Object)(object)component2 != (Object)null && component.itemPersisting) { StatsManager.instance.ItemRemove(component2.item.prefab.prefabName); } item.DestroyPhysGrabObject(); } if ((Object)(object)((Component)item).GetComponent<PlayerTumble>() != (Object)null) { ((Component)item).GetComponent<PlayerTumble>().playerAvatar.playerHealth.Hurt(100, false, -1); } } Transform val = ((Component)this).transform.Find("ResultSpawn"); PrefabRef networkPrefabRef = NetworkPrefabs.GetNetworkPrefabRef(recipe.result); GameObject val2 = NetworkPrefabs.SpawnNetworkPrefab(networkPrefabRef, val.position, val.rotation, (byte)0, (object[])null); MonoBehaviour.print((object)("Crafted " + ((Object)val2).name)); AlchemyItem component3 = val2.GetComponent<AlchemyItem>(); val2.transform.localScale = Vector3.one * component3.potScale; if (SemiFunc.IsMultiplayer()) { ((Component)component3).GetComponent<PhotonView>().RPC("SyncScaleRPC", (RpcTarget)1, Array.Empty<object>()); } ItemAttributes component4 = val2.GetComponent<ItemAttributes>(); component3.itemPersisting = (Object)(object)component4 != (Object)null && component3.itemPersistent; if (component3.itemPersisting) { StatsManager.instance.ItemPurchase(component4.item.prefab.prefabName); } if (Object.op_Implicit((Object)(object)val2.GetComponent<ValuableObject>())) { val2.GetComponent<ValuableObject>().valuePreset = Plugin.craftedValue; } } public void TryRestock() { CheckIngredients(); for (int i = 0; i < sources.Count; i++) { int num = i + sources.Count * inventoryPage; if (inventoryOrder.Count > num) { string key = inventoryOrder[num]; sources[i].prefabID = Tools.ingredients[key]; } else { sources[i].prefabID = null; } } CheckIndicators(); if (CanRestock()) { ((MonoBehaviour)this).StartCoroutine(Restock()); } } private bool CanRestock() { foreach (ObjectSource source in sources) { if (source.CanSpawn()) { return true; } } return false; } [IteratorStateMachine(typeof(<Restock>d__72))] private IEnumerator Restock() { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <Restock>d__72(0) { <>4__this = this }; } private void RestockItem(ObjectSource source) { if (source.prefabID == null && (Object)(object)source.obj != (Object)null) { ((Component)source.obj).GetComponent<PhysGrabObject>().DestroyPhysGrabObject(); } AlchemyItem alchemyItem = source.SpawnObject(); if (!((Object)(object)alchemyItem == (Object)null)) { alchemyItem.wasCrafted = true; if (SemiFunc.IsMultiplayer()) { ((Component)alchemyItem).GetComponent<PhotonView>().RPC("SetWasCraftedRPC", (RpcTarget)1, new object[1] { true }); } } } private void CheckIndicators() { for (int i = 0; i < sources.Count; i++) { int num = 0; if (sources[i].prefabID != null && sources[i].prefabID != "") { string key = Tools.TryGetKey(Tools.ingredients, sources[i].prefabID); num = inventory[key] - 1; } SetIndicatorRPC(i, num, Plugin.maxIngredientsTransferred.Value); if (SemiFunc.IsMasterClient()) { photon.RPC("SetIndicatorRPC", (RpcTarget)1, new object[3] { i, num, Plugin.maxIngredientsTransferred.Value }); } } } [PunRPC] public void SetIndicatorRPC(int indicator, int count, int max) { //IL_003c: Unknown result type (might be due to invalid IL or missing references) //IL_0068: 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) SpriteRenderer val = indicators[indicator]; ((Component)val).gameObject.SetActive(count != 0); if (count > 0) { val.color = new Color(1f, 0.55f, 0f, 1f); } else if (count < 0) { val.color = new Color(0.95f, 0.23f, 1f, 1f); } if (count >= max) { val.color = new Color(0.8f, 0f, 0f, 1f); } } } public class GrowScale : MonoBehaviour { public float speed = 1f; public float targetScale = 1f; private void Update() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0031: 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) float x = ((Component)this).transform.localScale.x; x = Mathf.MoveTowards(x, targetScale, Time.deltaTime * speed); ((Component)this).transform.localScale = Vector3.one * x; if (x == targetScale) { Object.Destroy((Object)(object)this); } } } public class Ingredient : AlchemyItem { public string ingredientID; public bool canStore = true; [HideInInspector] public bool wasStored = false; public bool storeOnExtract = true; public float storedScale = 0.75f; public bool ingredientHighlighting; private void Start() { photon = ((Component)this).GetComponent<PhotonView>(); Dictionary<string, int> dictionary = StatsManager.instance.dictionaryOfDictionaries["ingredients"]; if (!dictionary.ContainsKey(ingredientID)) { dictionary.Add(ingredientID, 0); } if ((Object)(object)((Component)this).transform.parent != (Object)null) { ObjectSource component = ((Component)((Component)this).transform.parent).GetComponent<ObjectSource>(); if ((Object)(object)component != (Object)null) { wasStored = true; } } } public void AddIngredient() { if (!wasStored) { StatsManager.instance.dictionaryOfDictionaries["ingredients"][ingredientID]++; wasStored = true; } } public void UseIngredient() { if (wasStored && !SemiFunc.RunIsShop()) { StatsManager.instance.dictionaryOfDictionaries["ingredients"][ingredientID]--; } } public bool IsRegistered() { return Tools.ingredients.ContainsKey(ingredientID); } public static Ingredient ConvertToIngredient(AlchemyItem obj) { //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_0015: 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_0060: Unknown result type (might be due to invalid IL or missing references) bool flag = obj.spawnAsValuable; string text = obj.prefabID; Color val = obj.color; PhotonView val2 = obj.photon; Sprite val3 = obj.icon; float num = obj.potScale; bool flag2 = obj.itemPersistent; GameObject gameObject = ((Component)obj).gameObject; Object.Destroy((Object)(object)obj); Ingredient ingredient = gameObject.AddComponent<Ingredient>(); ingredient.spawnAsValuable = flag; ingredient.prefabID = text; ingredient.color = val; ingredient.photon = val2; ingredient.icon = val3; ingredient.potScale = num; ingredient.itemPersistent = flag2; return ingredient; } } public class ObjectSource : MonoBehaviour { public bool spawnAsValuable = false; public string prefabID; public AlchemyItem obj; private float objectRemovedDuration = 0f; private bool objectRemoved = false; public UnityEvent objectUnlocked = new UnityEvent(); private Vector3 oldScale = Vector3.one; public bool CanSpawn() { if (!SemiFunc.IsMasterClientOrSingleplayer()) { return false; } if ((Object)(object)obj != (Object)null && obj.prefabID == prefabID) { return false; } if ((prefabID == null || prefabID == "") && (Object)(object)obj == (Object)null) { return false; } return true; } public AlchemyItem SpawnObject() { //IL_006a: 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_00ad: Unknown result type (might be due to invalid IL or missing references) //IL_00c2: Unknown result type (might be due to invalid IL or missing references) if (!CanSpawn()) { return null; } if (prefabID == null) { return null; } if ((Object)(object)obj != (Object)null) { ((Component)obj).GetComponent<PhysGrabObject>().DestroyPhysGrabObject(); } PrefabRef networkPrefabRef = NetworkPrefabs.GetNetworkPrefabRef(prefabID); obj = NetworkPrefabs.SpawnNetworkPrefab(networkPrefabRef, ((Component)this).transform.position, ((Component)this).transform.rotation, (byte)0, (object[])null).GetComponent<AlchemyItem>(); ((Component)obj).transform.parent = ((Component)this).transform; ((Component)obj).transform.localScale = Vector3.one * ((Component)obj).GetComponent<Ingredient>().storedScale; ((Component)obj).GetComponent<AlchemyItem>().isOnSource = true; ((Component)obj).GetComponent<ValuableObject>().valuePreset = Plugin.craftedValue; Rigidbody component = ((Component)obj).GetComponent<Rigidbody>(); objectRemoved = false; objectRemovedDuration = 0f; ValuableObject component2 = ((Component)obj).GetComponent<ValuableObject>(); NotValuableObject component3 = ((Component)obj).GetComponent<NotValuableObject>(); return obj; } public void UnlockObject() { if (!((Object)(object)obj == (Object)null)) { objectRemoved = true; ((Component)obj).GetComponent<AlchemyItem>().isOnSource = false; Rigidbody component = ((Component)obj).GetComponent<Rigidbody>(); ((Component)obj).transform.parent = null; obj.AddGrowerRPC(1f, 1f); if (SemiFunc.IsMultiplayer()) { ((Component)obj).GetComponent<PhotonView>().RPC("AddGrowerRPC", (RpcTarget)1, new object[2] { 1f, 1f }); } obj = null; objectUnlocked.Invoke(); } } private void Update() { //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_004b: 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_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00a3: 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_0121: 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_00d2: Unknown result type (might be due to invalid IL or missing references) if (objectRemoved) { objectRemovedDuration += Time.deltaTime; } if ((Object)(object)obj != (Object)null) { if (SemiFunc.IsMasterClient() && oldScale != ((Component)obj).transform.lossyScale) { ((Component)obj).GetComponent<PhotonView>().RPC("SyncScaleRPC", (RpcTarget)1, new object[1] { ((Component)obj).transform.lossyScale }); oldScale = ((Component)obj).transform.lossyScale; } Rigidbody component = ((Component)obj).GetComponent<Rigidbody>(); if (!component.isKinematic) { component.velocity = Vector3.zero; component.angularVelocity = Vector3.zero; } ((Component)obj).GetComponent<PhysGrabObject>().OverrideIndestructible(0.1f); ((Component)obj).transform.rotation = ((Component)this).transform.rotation; ((Component)obj).transform.position = ((Component)this).transform.position; if (((Component)obj).GetComponent<PhysGrabObject>().grabbed) { UnlockObject(); } } } } [HarmonyPatch(typeof(StatsManager), "Start")] internal class StatsManagerPatchStart { private static void Prefix() { StatsManager.instance.dictionaryOfDictionaries.Add("ingredients", new Dictionary<string, int>()); } } [HarmonyPatch(typeof(StatsManager), "RunStartStats")] internal class StatsManagerStartStatsPatch { private static void Postfix() { if (Plugin.startWithCauldron.Value) { StatsManager.instance.ItemPurchase(((Component)Cauldron.instance).GetComponent<ItemAttributes>().item.prefab.prefabName); } } } [HarmonyPatch(typeof(ExtractionPoint), "DestroyTheFirstPhysObjectsInHaulList")] internal class ExtractionPointPatch { private static void Prefix() { if (SemiFunc.IsMasterClientOrSingleplayer()) { Ingredient component = RoundDirector.instance.dollarHaulList[0].GetComponent<Ingredient>(); if ((Object)(object)component != (Object)null && component.storeOnExtract) { component.AddIngredient(); } } } } [HarmonyPatch(typeof(ValuableDirector), "SetupHost")] internal class ValuableDirectorPatch { private static void Postfix() { //IL_00fd: 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_010c: Unknown result type (might be due to invalid IL or missing references) //IL_0111: Unknown result type (might be due to invalid IL or missing references) //IL_01a6: Unknown result type (might be due to invalid IL or missing references) //IL_01b2: Unknown result type (might be due to invalid IL or missing references) if (Plugin.ingredientSpawnsMax.Value <= 0) { return; } List<ValuableVolume> list = Object.FindObjectsOfType<ValuableVolume>(false).ToList(); list = list.FindAll((ValuableVolume x) => (int)x.VolumeType == 0); ListExtension.Shuffle<ValuableVolume>((IList<ValuableVolume>)list); if (list.Count == 0) { return; } if (Tools.spawnableIngredients.Count == 0) { MonoBehaviour.print((object)"No ingredients registered. Install a mod that adds ingredients."); return; } int num = Random.Range(Plugin.ingredientSpawnsMin.Value, Plugin.ingredientSpawnsMax.Value + 1); int num2 = 0; List<string> list2 = new List<string>(Tools.spawnableIngredients); ListExtension.Shuffle<string>((IList<string>)list2); MonoBehaviour.print((object)("Attempting to spawn " + num + " ingredients.")); foreach (ValuableVolume item in list) { bool flag = true; Collider[] array = Physics.OverlapBox(((Component)item).transform.position, Vector3.one * 0.25f, Quaternion.identity); Collider[] array2 = array; foreach (Collider val in array2) { if ((Object)(object)((Component)val).GetComponentInParent<PhysGrabObject>() != (Object)null) { flag = false; break; } } if (flag) { int index = ((num2 >= 3) ? Random.Range(0, Tools.spawnableIngredients.Count) : (num2 % list2.Count)); string text = Tools.ingredients[list2[index]]; PrefabRef networkPrefabRef = NetworkPrefabs.GetNetworkPrefabRef(text); GameObject val2 = NetworkPrefabs.SpawnNetworkPrefab(networkPrefabRef, ((Component)item).transform.position, ((Component)item).transform.rotation, (byte)0, (object[])null); num2++; } if (num2 >= num) { MonoBehaviour.print((object)("Successfully spawned all " + num + " potion ingredients!")); return; } } MonoBehaviour.print((object)("Not enough space for all ingredients. Spawned " + num2 + " ingredients.")); } } [HarmonyPatch(typeof(ValuableObject), "Discover")] internal class IngredientDiscoverPatch { private static void Postfix(ValuableObject __instance) { //IL_001d: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)((Component)__instance).GetComponent<Ingredient>() != (Object)null) { ValuableDiscover.instance.New(((Component)__instance).GetComponent<PhysGrabObject>(), Plugin.ingredientDiscoverState); } } } [HarmonyPatch(typeof(Map), "AddValuable")] internal class IngredientDiscoverMapPatch { private static bool Prefix(ValuableObject _valuable) { //IL_0038: 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) if (Object.op_Implicit((Object)(object)((Component)_valuable).GetComponent<Ingredient>())) { MapCustom val = ((Component)_valuable).gameObject.AddComponent<MapCustom>(); val.sprite = Plugin.mapIcon; val.color = new Color(0.21f, 0f, 1f); return false; } return true; } } [HarmonyPatch(typeof(Valuables), "RegisterInitialValuables")] internal class ValuableRegisterPatch { private static void Postfix() { //IL_01d0: Unknown result type (might be due to invalid IL or missing references) //IL_01d5: Unknown result type (might be due to invalid IL or missing references) List<Tools.QueuedIngredient> list = new List<Tools.QueuedIngredient>(Tools.queuedIngredients); foreach (Tools.QueuedIngredient item in list) { if (item.isItem) { continue; } GameObject val = null; foreach (PrefabRef registeredValuable in Valuables.RegisteredValuables) { if (registeredValuable.prefabName == item.name) { val = registeredValuable.Prefab; break; } } Ingredient ingredient = val.AddComponent<Ingredient>(); ingredient.ingredientID = item.ingredientID; ingredient.canStore = item.canStore; ingredient.storeOnExtract = item.storeOnExtract && ingredient.canStore; ingredient.potScale = item.potScale; ingredient.storedScale = item.storedScale; Tools.RegisterIngredient(ingredient, item.canSpawn); Tools.queuedIngredients.Remove(item); } List<Tools.QueuedRecipe> list2 = new List<Tools.QueuedRecipe>(Tools.queuedRecipes); foreach (Tools.QueuedRecipe item2 in list2) { if (item2.isItem) { continue; } GameObject val2 = null; foreach (PrefabRef registeredValuable2 in Valuables.RegisteredValuables) { if (registeredValuable2.prefabName == item2.name) { val2 = registeredValuable2.Prefab; break; } } AlchemyItem alchemyItem = (((Object)(object)val2.GetComponent<AlchemyItem>() != (Object)null) ? val2.GetComponent<AlchemyItem>() : val2.AddComponent<AlchemyItem>()); alchemyItem.color = item2.color; alchemyItem.icon = item2.icon; alchemyItem.itemPersistent = item2.itemPersist; alchemyItem.potScale = item2.potScale; Tools.RegisterRecipe(item2.ingredients, alchemyItem); Tools.queuedRecipes.Remove(item2); } } } [HarmonyPatch(typeof(Items), "RegisterItems")] internal class ItemRegisterPatch { private static void Postfix() { //IL_01d6: Unknown result type (might be due to invalid IL or missing references) //IL_01db: Unknown result type (might be due to invalid IL or missing references) List<Tools.QueuedIngredient> list = new List<Tools.QueuedIngredient>(Tools.queuedIngredients); foreach (Tools.QueuedIngredient item in list) { if (!item.isItem) { continue; } GameObject val = null; foreach (PrefabRef registeredValuable in Valuables.RegisteredValuables) { if (registeredValuable.prefabName == item.name) { val = registeredValuable.Prefab; break; } } Ingredient ingredient = val.AddComponent<Ingredient>(); ingredient.ingredientID = item.ingredientID; ingredient.canStore = item.canStore; ingredient.storeOnExtract = item.storeOnExtract && ingredient.canStore; ingredient.potScale = item.potScale; ingredient.storedScale = item.storedScale; Tools.RegisterIngredient(ingredient, item.canSpawn); Tools.queuedIngredients.Remove(item); } List<Tools.QueuedRecipe> list2 = new List<Tools.QueuedRecipe>(Tools.queuedRecipes); foreach (Tools.QueuedRecipe item2 in list2) { if (!item2.isItem) { continue; } GameObject val2 = null; foreach (PrefabRef registeredValuable2 in Valuables.RegisteredValuables) { if (registeredValuable2.prefabName == item2.name) { val2 = registeredValuable2.Prefab; break; } } AlchemyItem alchemyItem = (((Object)(object)val2.GetComponent<AlchemyItem>() != (Object)null) ? val2.GetComponent<AlchemyItem>() : val2.AddComponent<AlchemyItem>()); alchemyItem.color = item2.color; alchemyItem.icon = item2.icon; alchemyItem.itemPersistent = item2.itemPersist; alchemyItem.potScale = item2.potScale; Tools.RegisterRecipe(item2.ingredients, alchemyItem); Tools.queuedRecipes.Remove(item2); } } } [BepInPlugin("REPOAlchemy", "REPOAlchemy", "0.0.0")] [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInProcess("REPO.exe")] public class Plugin : BaseUnityPlugin { internal static ManualLogSource Logger; public static ConfigEntry<bool> unlimitedIngredients; public static ConfigEntry<int> ingredientSpawnsMax; public static ConfigEntry<int> ingredientSpawnsMin; public static ConfigEntry<int> maxIngredientsTransferred; public static ConfigEntry<bool> startWithCauldron; public static ConfigEntry<bool> purchaseableCauldron; public static ConfigEntry<int> cauldronMinPrice; public static ConfigEntry<int> cauldronMaxPrice; public static Value craftedValue; public static Sprite mapIcon; public static State ingredientDiscoverState; private Harmony harmony = new Harmony("REPOAlchemy"); private AssetBundle assetBundle; private void Awake() { //IL_004b: 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_0069: 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) Logger = ((BaseUnityPlugin)this).Logger; SetUpConfigs(); assetBundle = AssetBundle.LoadFromFile(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "repoalchemy")); ingredientDiscoverState = CustomDiscoverState.AddNewDiscoverGraphic(new Color(0.41f, 0.2f, 1f, 0.075f), new Color(0.41f, 0.2f, 1f, 0.75f)); mapIcon = assetBundle.LoadAsset<Sprite>("Assets/Mods/REPOAlchemy/Map Icon Small.png"); craftedValue = assetBundle.LoadAsset<Value>("Assets/Mods/REPOAlchemy/Cauldron/Value - Ingredient.asset"); LoadCauldron(); harmony.PatchAll(); Logger.LogInfo((object)"Plugin REPOAlchemy is loaded!"); } private void SetUpConfigs() { unlimitedIngredients = ((BaseUnityPlugin)this).Config.Bind<bool>("Ingredients", "Unlimited Ingredients (CHEAT)", false, "Should the POT provide unlimited ingredients"); ingredientSpawnsMax = ((BaseUnityPlugin)this).Config.Bind<int>("Ingredients", "Ingredients Spawn Max", 4, "The maximum amount of ingredients to spawn per level"); ingredientSpawnsMin = ((BaseUnityPlugin)this).Config.Bind<int>("Ingredients", "Ingredients Spawn Min", 1, "The minimum amount of ingredients to spawn per level"); maxIngredientsTransferred = ((BaseUnityPlugin)this).Config.Bind<int>("Ingredients", "Max Ingredients Transferred", 2, "The maximum number of ingredients that can be transferred between levels"); startWithCauldron = ((BaseUnityPlugin)this).Config.Bind<bool>("Cauldron", "Start With Cauldron", true, "Start each game with a P.O.T."); purchaseableCauldron = ((BaseUnityPlugin)this).Config.Bind<bool>("Cauldron", "Purchaseable Cauldron", true, "Should the P.O.T. be purchaseable\nOnly works if Start With Cauldron is false"); cauldronMinPrice = ((BaseUnityPlugin)this).Config.Bind<int>("Cauldron", "Cauldron Min Price", 3500, "Minimum price the P.O.T. should cost (before multipliers)\nDefault is identical to the Pocket C.A.R.T."); cauldronMaxPrice = ((BaseUnityPlugin)this).Config.Bind<int>("Cauldron", "Cauldron Max Price", 4500, "Maximum price the P.O.T. should cost (before multipliers)\nDefault is identical to the Pocket C.A.R.T."); } private void LoadCauldron() { GameObject val = assetBundle.LoadAsset<GameObject>("Assets/Mods/REPOAlchemy/Cauldron/Cauldron.prefab"); Cauldron cauldron = (Cauldron.instance = val.AddComponent<Cauldron>()); val.GetComponent<ItemAttributes>().item.value.valueMin = cauldronMinPrice.Value; val.GetComponent<ItemAttributes>().item.value.valueMax = cauldronMaxPrice.Value; Transform val2 = val.transform.Find("Model/Cauldron/Armature/Root/RackFlap/Racks"); cauldron.sources.Add(((Component)val2.Find("RackLeft/RackSurfaceLeft/Slot.000")).gameObject.AddComponent<ObjectSource>()); cauldron.sources.Add(((Component)val2.Find("RackSurfaceCenter/Slot.001")).gameObject.AddComponent<ObjectSource>()); cauldron.sources.Add(((Component)val2.Find("RackSurfaceCenter/Slot.002")).gameObject.AddComponent<ObjectSource>()); cauldron.sources.Add(((Component)val2.Find("RackRight/RackSurfaceRight/Slot.003")).gameObject.AddComponent<ObjectSource>()); cauldron.openSound = assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Open1.ogg"); cauldron.closeSound = assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Close1.ogg"); cauldron.restockSound = assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Restock1.ogg"); cauldron.shakeSounds = new List<AudioClip> { assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake1.ogg"), assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake2.ogg"), assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake3.ogg"), assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake4.ogg"), assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake5.ogg"), assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake6.ogg"), assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake7.ogg"), assetBundle.LoadAsset<AudioClip>("Assets/Mods/REPOAlchemy/Cauldron/Shake8.ogg") }; if (purchaseableCauldron.Value || startWithCauldron.Value) { Items.RegisterItem(val.GetComponent<ItemAttributes>()); } val.GetComponent<PhysGrabCart>().thrustEffect = val.transform.Find("ThrustEffect"); Logger.LogInfo((object)"Cauldron Loaded!"); } } public class PluginInfo { public const string PLUGIN_GUID = "REPOAlchemy"; public const string PLUGIN_NAME = "REPOAlchemy"; public const string PLUGIN_VERSION = "0.0.0"; } public class Tools { public struct QueuedIngredient { public string name; public string ingredientID; public bool canSpawn; public bool canStore; public bool storeOnExtract; public float potScale; public float storedScale; public bool isItem; } public struct QueuedRecipe { public string name; public Sprite icon; public Color color; public List<string> ingredients; public bool itemPersist; public float potScale; public bool isItem; } public static List<string> spawnableIngredients = new List<string>(); public static Dictionary<string, string> ingredients = new Dictionary<string, string>(); public static List<string> storeableIngredients = new List<string>(); public static List<QueuedIngredient> queuedIngredients = new List<QueuedIngredient>(); public static List<QueuedRecipe> queuedRecipes = new List<QueuedRecipe>(); public static void RegisterIngredient(Ingredient ingredient, bool canSpawn = true) { NetworkPrefabs.RegisterNetworkPrefab(((Component)ingredient).gameObject); ingredients.Add(ingredient.ingredientID, ((Object)((Component)ingredient).gameObject).name); ingredient.prefabID = ((Object)((Component)ingredient).gameObject).name; if (canSpawn) { spawnableIngredients.Add(ingredient.ingredientID); } if (ingredient.canStore) { storeableIngredients.Add(ingredient.ingredientID); } } public static void RegisterIngredientByValuableName(string valuableName, string ingredientID, bool canSpawn = true, bool canStore = true, bool storeOnExtract = false, float potScale = 1f, float storedScale = 0.75f) { QueuedIngredient item = default(QueuedIngredient); item.name = valuableName; item.ingredientID = ingredientID; item.canSpawn = canSpawn; item.canStore = canStore; item.storeOnExtract = storeOnExtract; item.isItem = false; item.potScale = potScale; item.storedScale = storedScale; queuedIngredients.Add(item); } public static void RegisterIngredientByItemName(string itemName, string ingredientID, bool canSpawn = true, bool canStore = true, bool storeOnExtract = false, float potScale = 1f, float storedScale = 0.75f) { QueuedIngredient item = default(QueuedIngredient); item.name = itemName; item.ingredientID = ingredientID; item.canSpawn = canSpawn; item.canStore = canStore; item.storeOnExtract = storeOnExtract; item.isItem = true; item.potScale = potScale; item.storedScale = storedScale; queuedIngredients.Add(item); } public static void RegisterRecipe(List<string> ingredients, AlchemyItem result) { //IL_0036: Unknown result type (might be due to invalid IL or missing references) string name = ((Object)((Component)result).gameObject).name; if (!NetworkPrefabs.HasNetworkPrefab(name)) { NetworkPrefabs.RegisterNetworkPrefab(((Component)result).gameObject); } Cauldron.recipes.Add(new Cauldron.Recipe(ingredients, name, result.icon, result.color, (Object)(object)((Component)result).GetComponent<Ingredient>() != (Object)null)); } public static void RegisterRecipeByItemName(string itemName, List<string> ingredients, Sprite icon, Color color, bool itemPersist = false, float potScale = 1f) { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Unknown result type (might be due to invalid IL or missing references) QueuedRecipe item = default(QueuedRecipe); item.name = itemName; item.icon = icon; item.color = color; item.ingredients = ingredients; item.itemPersist = itemPersist; item.isItem = true; item.potScale = potScale; queuedRecipes.Add(item); } public static void RegisterRecipeByValuableName(string valuableName, List<string> ingredients, Sprite icon, Color color, bool itemPersist = false, float potScale = 1f) { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Unknown result type (might be due to invalid IL or missing references) QueuedRecipe item = default(QueuedRecipe); item.name = valuableName; item.icon = icon; item.color = color; item.ingredients = ingredients; item.itemPersist = itemPersist; item.isItem = false; item.potScale = potScale; queuedRecipes.Add(item); } public static TKey? TryGetKey<TKey, TValue>(Dictionary<TKey, TValue> dictionary, TValue value) { foreach (KeyValuePair<TKey, TValue> item in dictionary) { if (object.Equals(item.Value, value)) { return item.Key; } } return default(TKey); } } public static class MyPluginInfo { public const string PLUGIN_GUID = "REPOAlchemy"; public const string PLUGIN_NAME = "My first plugin"; public const string PLUGIN_VERSION = "1.0.0"; } } namespace REPOAlchemy.Development { [CreateAssetMenu(menuName = "REPOAlchemy/Existing Item Ingredient", order = 2, fileName = "New Item Ingredient")] public class ExistingItemIngredientContent : Content { public string itemName = "Grenade Explosive"; public string ingredientID; public bool canStore = false; public bool useIngredientSpawning = false; public bool storeOnExtract = false; public float potScale = 1f; public float storedScale = 0.75f; public override string Name => "Ingredient" + itemName; public override void Initialize(Mod mod) { Tools.RegisterIngredientByItemName(itemName, ingredientID, useIngredientSpawning, canStore, storeOnExtract, potScale, storedScale); } } [CreateAssetMenu(menuName = "REPOAlchemy/External Item Recipe", order = 5, fileName = "New Item Recipe")] public class ExistingItemRecipeContent : Content { public string itemName = "Grenade Explosive"; public List<string> ingredients = new List<string>(); public Color recipeColor = Color.magenta; public Sprite recipeIcon; public bool itemPersist = false; public float potScale = 1f; public override string Name => "Recipe" + itemName; public override void Initialize(Mod mod) { //IL_0014: Unknown result type (might be due to invalid IL or missing references) Tools.RegisterRecipeByItemName(itemName, ingredients, recipeIcon, recipeColor, itemPersist, potScale); } } [CreateAssetMenu(menuName = "REPOAlchemy/External Valuable Ingredient", order = 1, fileName = "New Valuable Ingredient")] public class ExistingValuableIngredientContent : Content { public string valuableName = "Diamond"; public string ingredientID; public bool canStore = false; public bool useIngredientSpawning = false; public bool storeOnExtract = false; public float potScale = 1f; public float storedScale = 0.75f; public override string Name => "Ingredient" + valuableName; public override void Initialize(Mod mod) { Tools.RegisterIngredientByValuableName(valuableName, ingredientID, useIngredientSpawning, canStore, storeOnExtract, potScale, storedScale); } } [CreateAssetMenu(menuName = "REPOAlchemy/External Valuable Recipe", order = 4, fileName = "New Valuable Recipe")] public class ExistingValuableRecipeContent : Content { public string valuableName = "Diamond"; public List<string> ingredients = new List<string>(); public Color recipeColor = Color.magenta; public Sprite recipeIcon; public float potScale = 1f; public override string Name => "Recipe" + valuableName; public override void Initialize(Mod mod) { //IL_0014: Unknown result type (might be due to invalid IL or missing references) Tools.RegisterRecipeByValuableName(valuableName, ingredients, recipeIcon, recipeColor, itemPersist: false, potScale); } } [CreateAssetMenu(menuName = "REPOAlchemy/Ingredient", order = 0, fileName = "New Ingredient")] public class IngredientContent : Content { public Ingredient prefab; public bool useIngredientSpawning = true; public override string Name { get { Ingredient ingredient = prefab; return "Ingredient" + ((Object)ingredient).name; } } public override void Initialize(Mod mod) { Tools.RegisterIngredient(prefab, useIngredientSpawning); } } [CreateAssetMenu(menuName = "REPOAlchemy/Recipe", order = 3, fileName = "New Recipe")] public class RecipeContent : Content { public AlchemyItem resultPrefab; public List<string> ingredients = new List<string>(); public override string Name { get { AlchemyItem alchemyItem = resultPrefab; return "Recipe" + ((Object)alchemyItem).name; } } public override void Initialize(Mod mod) { Tools.RegisterRecipe(ingredients, resultPrefab); } } }