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 DynamicStoragePiles v0.8.0
DynamicStoragePiles.dll
Decompiled a week agousing System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Bootstrap; using BepInEx.Configuration; using DynamicStoragePiles.Compatibility; using HarmonyLib; using Jotunn; using Jotunn.Configs; using Jotunn.Entities; using Jotunn.Managers; using Jotunn.Utils; using UnityEngine; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: AssemblyTitle("DynamicStoragePiles")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("")] [assembly: AssemblyProduct("DynamicStoragePiles")] [assembly: AssemblyCopyright("Copyright © 2021")] [assembly: AssemblyTrademark("")] [assembly: ComVisible(false)] [assembly: Guid("e3243d22-4307-4008-ba36-9f326008cde5")] [assembly: AssemblyFileVersion("0.8.0")] [assembly: TargetFramework(".NETFramework,Version=v4.6.2", FrameworkDisplayName = ".NET Framework 4.6.2")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("0.8.0.0")] [module: UnverifiableCode] namespace DynamicStoragePiles { public static class ConfigSettings { public enum RecipeSetting { AllStoragePiles, OnlyDynamicStoragePiles, OnlyOriginalStoragePiles } private static ConfigFile config; public static ConfigEntry<bool> azuAutoStoreCompat; public static ConfigEntry<bool> azuAutoStoreItemWhitelist; public static ConfigEntry<bool> restrictDynamicPiles; public static ConfigEntry<RecipeSetting> VanillaRecipeSetting { get; private set; } public static ConfigEntry<RecipeSetting> IngotStacksRecipeSetting { get; private set; } public static ConfigEntry<RecipeSetting> StackedBarsRecipeSetting { get; private set; } public static ConfigEntry<RecipeSetting> MoreStacksRecipeSetting { get; private set; } public static ConfigEntry<RecipeSetting> RefinedStonePiecesSetting { get; private set; } public static void Init(ConfigFile configFile) { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0015: Expected O, but got Unknown //IL_008f: Unknown result type (might be due to invalid IL or missing references) //IL_0099: Expected O, but got Unknown config = configFile; ConfigurationManagerAttributes val = new ConfigurationManagerAttributes { IsAdminOnly = true }; string text = "\nCheats or world modifiers can ignore this setting. Existing pieces in the world are not affected"; string text2 = "\nRequires a restart to take effect"; string text3 = "1 - General"; VanillaRecipeSetting = config.Bind<RecipeSetting>(text3, "Vanilla Stack Recipes", RecipeSetting.AllStoragePiles, "Sets which pieces are placeable." + text); VanillaRecipeSetting.SettingChanged += delegate { DynamicStoragePiles.UpdateAllRecipes(); }; restrictDynamicPiles = config.Bind<bool>(text3, "Restrict Container Item Type", true, new ConfigDescription("Only allows the respective items to be stored in stack piles, so wood piles only accept wood etc.\nSynced with server", (AcceptableValueBase)null, new object[1] { val })); text3 = "2.0 - Compatibility AzuAutoStore"; azuAutoStoreCompat = config.Bind<bool>(text3, "Enable Compatibility", true, "Enables compatibility with AzuAutoStore." + text2); azuAutoStoreItemWhitelist = config.Bind<bool>(text3, "Enable Item Whitelist", true, "Only allows the respective items to be stored in stack piles"); text3 = "2.1 - Compatibility IngotStacks"; IngotStacksRecipeSetting = config.Bind<RecipeSetting>(text3, "IngotStacks Stack Recipes", RecipeSetting.AllStoragePiles, "Sets which pieces are placeable." + text); IngotStacksRecipeSetting.SettingChanged += delegate { DynamicStoragePiles.UpdateAllRecipes(); }; text3 = "2.2 - Compatibility StackedBars"; StackedBarsRecipeSetting = config.Bind<RecipeSetting>(text3, "StackedBars Stack Recipes", RecipeSetting.AllStoragePiles, "Sets which pieces are placeable." + text); StackedBarsRecipeSetting.SettingChanged += delegate { DynamicStoragePiles.UpdateAllRecipes(); }; text3 = "2.3 - Compatibility MoreStacks"; MoreStacksRecipeSetting = config.Bind<RecipeSetting>(text3, "MoreStacks Stack Recipes", RecipeSetting.AllStoragePiles, "Sets which pieces are placeable." + text); MoreStacksRecipeSetting.SettingChanged += delegate { DynamicStoragePiles.UpdateAllRecipes(); }; text3 = "2.4 - Compatibility RefinedStonePieces"; RefinedStonePiecesSetting = config.Bind<RecipeSetting>(text3, "RefinedStonePieces Stack Recipes", RecipeSetting.AllStoragePiles, "Sets which pieces are placeable." + text); RefinedStonePiecesSetting.SettingChanged += delegate { DynamicStoragePiles.UpdateAllRecipes(); }; } public static bool IsEnabled(this ConfigEntry<RecipeSetting> configEntry, bool isOriginal) { if (isOriginal) { return configEntry.Value == RecipeSetting.AllStoragePiles || configEntry.Value == RecipeSetting.OnlyOriginalStoragePiles; } return configEntry.Value == RecipeSetting.AllStoragePiles || configEntry.Value == RecipeSetting.OnlyDynamicStoragePiles; } } public static class InventoryHelper { public static string PrefabName(this ItemData item) { if (Object.op_Implicit((Object)(object)item.m_dropPrefab)) { return ((Object)item.m_dropPrefab).name; } Logger.LogWarning((object)("Item has missing prefab " + item.m_shared.m_name)); return item.m_shared.m_name; } } public static class PieceHelper { public static GameObject PreparePiecePrefab(GameObject prefab, GameObject basePrefab, string nameToken) { Object.Destroy((Object)(object)prefab.GetComponent<Gibber>()); Object.Destroy((Object)(object)prefab.GetComponent<Collider>()); if (Object.op_Implicit((Object)(object)prefab.transform.Find("collider"))) { Object.Destroy((Object)(object)((Component)prefab.transform.Find("collider")).gameObject); } ZNetView component = prefab.GetComponent<ZNetView>(); component.m_persistent = true; if (!Object.op_Implicit((Object)(object)prefab.GetComponent<Piece>())) { ExposedGameObjectExtension.AddComponentCopy<Piece>(prefab, basePrefab.GetComponent<Piece>()); } if (!Object.op_Implicit((Object)(object)prefab.GetComponent<WearNTear>())) { ExposedGameObjectExtension.AddComponentCopy<WearNTear>(prefab, basePrefab.GetComponent<WearNTear>()); } Container val = prefab.AddComponent<Container>(); val.m_name = nameToken; val.m_width = 5; val.m_height = 2; VisualStack visualStack = prefab.AddComponent<VisualStack>(); MeshRenderer[] componentsInChildren = prefab.GetComponentsInChildren<MeshRenderer>(); foreach (MeshRenderer val2 in componentsInChildren) { if (!Object.op_Implicit((Object)(object)((Component)val2).gameObject.GetComponent<Collider>())) { ((Component)val2).gameObject.AddComponent<BoxCollider>(); } visualStack.stackMeshes.Add(((Component)val2).transform); } return prefab; } public static GameObject FindDestroyVFX(GameObject prefab, string vfxName) { WearNTear val = default(WearNTear); if (prefab.TryGetComponent<WearNTear>(ref val)) { EffectData[] effectPrefabs = val.m_destroyedEffect.m_effectPrefabs; foreach (EffectData val2 in effectPrefabs) { if (Object.op_Implicit((Object)(object)val2.m_prefab) && ((Object)val2.m_prefab).name == vfxName) { return val2.m_prefab; } } } return null; } public static AssetBundle GetAssetBundle(string bundleName) { foreach (AssetBundle allLoadedAssetBundle in AssetBundle.GetAllLoadedAssetBundles()) { if (((Object)allLoadedAssetBundle).name == bundleName) { return allLoadedAssetBundle; } } return null; } } [BepInPlugin("com.maxsch.valheim.DynamicStoragePiles", "DynamicStoragePiles", "0.8.0")] [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInDependency(/*Could not decode attribute arguments.*/)] [NetworkCompatibility(/*Could not decode attribute arguments.*/)] internal class DynamicStoragePiles : BaseUnityPlugin { [CompilerGenerated] private sealed class <RenderSprite>d__26 : IEnumerator<object>, IDisposable, IEnumerator { private int <>1__state; private object <>2__current; public CustomPiece piece; public DynamicStoragePiles <>4__this; private VisualStack[] <visualStacks>5__1; private VisualStack[] <>s__2; private int <>s__3; private VisualStack <visualStack>5__4; private VisualStack[] <>s__5; private int <>s__6; private VisualStack <visualStack>5__7; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <RenderSprite>d__26(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <visualStacks>5__1 = null; <>s__2 = null; <visualStack>5__4 = null; <>s__5 = null; <visualStack>5__7 = null; <>1__state = -2; } private bool MoveNext() { //IL_00d0: Unknown result type (might be due to invalid IL or missing references) //IL_00d5: Unknown result type (might be due to invalid IL or missing references) //IL_00de: 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_00e8: Unknown result type (might be due to invalid IL or missing references) //IL_00fc: Unknown result type (might be due to invalid IL or missing references) //IL_0101: 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_0114: Unknown result type (might be due to invalid IL or missing references) //IL_0130: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = null; <>1__state = 1; return true; case 1: <>1__state = -1; <visualStacks>5__1 = ((Component)piece.Piece).GetComponentsInChildren<VisualStack>(); <>s__2 = <visualStacks>5__1; for (<>s__3 = 0; <>s__3 < <>s__2.Length; <>s__3++) { <visualStack>5__4 = <>s__2[<>s__3]; <visualStack>5__4.SetVisualsActive(55f); <visualStack>5__4 = null; } <>s__2 = null; piece.Piece.m_icon = RenderManager.Instance.Render(new RenderRequest(piece.PiecePrefab) { Width = 64, Height = 64, Rotation = RenderManager.IsometricRotation * Quaternion.Euler(0f, -90f, 0f), UseCache = true, TargetPlugin = ((BaseUnityPlugin)<>4__this).Info.Metadata }); <>s__5 = <visualStacks>5__1; for (<>s__6 = 0; <>s__6 < <>s__5.Length; <>s__6++) { <visualStack>5__7 = <>s__5[<>s__6]; <visualStack>5__7.SetVisualsActive(100f); <visualStack>5__7 = null; } <>s__5 = null; 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 const string PluginName = "DynamicStoragePiles"; public const string PluginGuid = "com.maxsch.valheim.DynamicStoragePiles"; public const string PluginVersion = "0.8.0"; public const string PLUGIN_MORESTACKS_GUID = "ujhik.MoreStacks"; public static Harmony harmony; private static AssetBundle assetBundle; private List<CustomPiece> renderSprites = new List<CustomPiece>(); public static Dictionary<string, string> allowedItemsByStack = new Dictionary<string, string>(); public static Dictionary<string, string> allowedItemsByContainer = new Dictionary<string, string>(); private static List<string> vanillaStacks = new List<string> { "wood_stack", "wood_fine_stack", "wood_core_stack", "wood_yggdrasil_stack", "blackwood_stack", "stone_pile", "coal_pile", "blackmarble_pile", "grausten_pile", "skull_pile", "treasure_stack", "bone_stack" }; private static List<string> dynamicStacks = new List<string>(); public static DynamicStoragePiles Instance { get; private set; } private void Awake() { //IL_0118: Unknown result type (might be due to invalid IL or missing references) //IL_0122: Expected O, but got Unknown Instance = this; assetBundle = AssetUtils.LoadAssetBundleFromResources("containerstacks"); AddStackPiece("MS_container_wood_stack", "Wood"); AddStackPiece("MS_container_finewood_stack", "FineWood"); AddStackPiece("MS_container_corewood_stack", "RoundLog"); AddStackPiece("MS_container_yggdrasil_wood_stack", "YggdrasilWood"); AddStackPiece("MS_container_blackwood_stack", "Blackwood"); AddStackPiece("MS_container_stone_pile", "Stone"); AddStackPiece("MS_container_coal_pile", "Coal"); AddStackPiece("MS_container_blackmarble_pile", "BlackMarble"); AddStackPiece("MS_container_grausten_pile", "Grausten"); AddStackPiece("MS_container_skull_pile", "Charredskull"); AddStackPiece("MS_container_bone_stack", "BoneFragments"); AddStackPiece("MS_container_coin_pile", "Coins"); ConfigSettings.Init(((BaseUnityPlugin)this).Config); PrefabManager.OnPrefabsRegistered += OnPrefabsRegistered; PieceManager.OnPiecesRegistered += OnPiecesRegistered; harmony = new Harmony("com.maxsch.valheim.DynamicStoragePiles"); harmony.PatchAll(); } private void Start() { if (Chainloader.PluginInfos.ContainsKey("Azumatt.AzuAutoStore") && ConfigSettings.azuAutoStoreCompat.Value) { AzuAutoStore.Init(); } if (Chainloader.PluginInfos.ContainsKey("Richard.IngotStacks")) { IngotStacks.Init(); } if (Chainloader.PluginInfos.ContainsKey("Azumatt.StackedBars")) { StackedBars.Init(); } if (Chainloader.PluginInfos.ContainsKey("blacks7ar.RefinedStonePieces")) { RefinedStonePieces.Init(); } } public static void UpdateAllRecipes() { if (Object.op_Implicit((Object)(object)ZNetScene.instance)) { UpdateRecipes(vanillaStacks, dynamicStacks, ConfigSettings.VanillaRecipeSetting); UpdateRecipes(IngotStacks.ingotStacks, IngotStacks.dynamicIngotStacks, ConfigSettings.IngotStacksRecipeSetting); UpdateRecipes(StackedBars.stackedBars, StackedBars.dynamicStackedBars, ConfigSettings.StackedBarsRecipeSetting); UpdateRecipes(MoreStacks.staticStacks, MoreStacks.dynamicStacks, ConfigSettings.MoreStacksRecipeSetting); UpdateRecipes(RefinedStonePieces.staticStacks, RefinedStonePieces.dynamicStacks, ConfigSettings.RefinedStonePiecesSetting); if (Object.op_Implicit((Object)(object)Player.m_localPlayer)) { Player.m_localPlayer.UpdateAvailablePiecesList(); } } } private static void UpdateRecipes(List<string> originalStackNames, List<string> dynamicStackNames, ConfigEntry<ConfigSettings.RecipeSetting> config) { foreach (string originalStackName in originalStackNames) { EnablePieceRecipes(originalStackName, config.IsEnabled(isOriginal: true)); } foreach (string dynamicStackName in dynamicStackNames) { EnablePieceRecipes(dynamicStackName, config.IsEnabled(isOriginal: false)); } } public static void EnablePieceRecipes(string prefabName, bool enabled) { GameObject prefab = ZNetScene.instance.GetPrefab(prefabName); Piece val = default(Piece); if (Object.op_Implicit((Object)(object)prefab) && prefab.TryGetComponent<Piece>(ref val)) { val.m_enabled = enabled; } else { Logger.LogWarning((object)("Could not find Piece " + prefabName + " to toggle recipes")); } } private void AddStackPiece(string pieceName, string craftItem) { //IL_0011: Unknown result type (might be due to invalid IL or missing references) //IL_0017: Expected O, but got Unknown CustomPiece val = new CustomPiece(assetBundle, pieceName, true, StackConfig(craftItem, 10)); renderSprites.Add(val); dynamicStacks.Add(pieceName); AddPiece(val, craftItem); } public void AddCompatPiece(GameObject prefab, string craftItem, int amount) { //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Expected O, but got Unknown CustomPiece piece = new CustomPiece(prefab, false, StackConfig(craftItem, amount)); AddPiece(piece, craftItem); } public void AddCompatPiece(GameObject prefab, string craftItem, int amount, bool addGraphics) { //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Expected O, but got Unknown CustomPiece val = new CustomPiece(prefab, true, StackConfig(craftItem, amount)); if (addGraphics) { renderSprites.Add(val); } AddPiece(val, craftItem); } private void AddPiece(CustomPiece piece, string craftItem) { PieceManager.Instance.AddPiece(piece); allowedItemsByStack.Add(((Object)piece.PiecePrefab).name, craftItem); allowedItemsByContainer.Add(piece.PiecePrefab.GetComponent<Container>().m_name, craftItem); } private void OnPrefabsRegistered() { if (Chainloader.PluginInfos.ContainsKey("ujhik.MoreStacks")) { MoreStacks.Init(); } } private void OnPiecesRegistered() { PieceManager.OnPiecesRegistered -= OnPiecesRegistered; foreach (CustomPiece renderSprite in renderSprites) { ((MonoBehaviour)this).StartCoroutine(RenderSprite(renderSprite)); } UpdateAllRecipes(); } [IteratorStateMachine(typeof(<RenderSprite>d__26))] private IEnumerator RenderSprite(CustomPiece piece) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <RenderSprite>d__26(0) { <>4__this = this, piece = piece }; } private PieceConfig StackConfig(string item, int amount) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Expected O, but got Unknown //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Expected O, but got Unknown PieceConfig val = new PieceConfig(); val.PieceTable = PieceTables.Hammer; val.Category = PieceCategories.Misc; val.AddRequirement(new RequirementConfig(item, amount, 0, true)); return val; } public static bool IsStackPiece(string pieceName, out string allowedItem) { return allowedItemsByStack.TryGetValue(pieceName, out allowedItem); } } [HarmonyPatch] internal static class RestrictContainers { private static string _loadingContainer; private static string _targetContainer; private static string _allowedItem; [HarmonyPrefix] [HarmonyPatch(typeof(InventoryGrid), "DropItem")] private static bool DropItemPrefix(InventoryGrid __instance, Inventory fromInventory, ItemData item, Vector2i pos) { //IL_001f: 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) if (!CanAddItem(__instance.m_inventory, item)) { return false; } ItemData itemAt = __instance.m_inventory.GetItemAt(pos.x, pos.y); if (itemAt != null) { return CanAddItem(fromInventory, itemAt); } return true; } private static bool CanAddItem(Inventory inventory, ItemData item) { if (inventory == null || item == null) { return false; } if (inventory.m_name == _loadingContainer) { return true; } if (IsRestrictedContainer(inventory.m_name, out var allowedItem)) { bool flag = item.PrefabName() == allowedItem; if (!flag) { string text = item.m_shared.m_name + " cannot be placed in " + inventory.m_name; Player localPlayer = Player.m_localPlayer; if (localPlayer != null) { ((Character)localPlayer).Message((MessageType)2, text, 0, (Sprite)null); } } return flag; } return true; } public static bool IsRestrictedContainer(string containerName, out string allowedItem) { if (!ConfigSettings.restrictDynamicPiles.Value) { allowedItem = null; return false; } return DynamicStoragePiles.allowedItemsByContainer.TryGetValue(containerName, out allowedItem); } [HarmonyPrefix] [HarmonyPatch(typeof(Inventory), "AddItem", new Type[] { typeof(ItemData) })] [HarmonyPatch(typeof(Inventory), "AddItem", new Type[] { typeof(ItemData), typeof(int), typeof(int), typeof(int) })] [HarmonyPriority(800)] private static bool AddItemPrefix(Inventory __instance, ItemData item, ref bool __result) { if (!CanAddItem(__instance, item)) { __result = false; return __result; } return true; } [HarmonyPrefix] [HarmonyPatch(typeof(Inventory), "MoveItemToThis", new Type[] { typeof(Inventory), typeof(ItemData) })] [HarmonyPatch(typeof(Inventory), "MoveItemToThis", new Type[] { typeof(Inventory), typeof(ItemData), typeof(int), typeof(int), typeof(int) })] [HarmonyPriority(800)] private static bool MoveItemToThisPrefix(Inventory __instance, Inventory fromInventory, ItemData item) { if (__instance == null || fromInventory == null || item == null) { return false; } return CanAddItem(__instance, item); } [HarmonyPrefix] [HarmonyPatch(typeof(Inventory), "MoveAll", new Type[] { typeof(Inventory) })] [HarmonyPriority(800)] private static void MoveAllPrefix(Inventory __instance, Inventory fromInventory) { if (__instance != null && fromInventory != null && IsRestrictedContainer(__instance.m_name, out var allowedItem)) { _targetContainer = __instance.m_name; _allowedItem = allowedItem; } } [HarmonyPrefix] [HarmonyPatch(typeof(Inventory), "MoveAll", new Type[] { typeof(Inventory) })] [HarmonyPriority(800)] private static void MoveAllPostfix() { _targetContainer = null; _allowedItem = null; } [HarmonyPrefix] [HarmonyPatch(typeof(Inventory), "RemoveItem", new Type[] { typeof(ItemData) })] [HarmonyPatch(typeof(Inventory), "RemoveItem", new Type[] { typeof(ItemData), typeof(int) })] [HarmonyPriority(800)] private static bool RemoveItemPrefix(Inventory __instance, ItemData item) { return ShouldRemoveItem(__instance, item); } [HarmonyPrefix] [HarmonyPatch(typeof(Inventory), "RemoveOneItem", new Type[] { typeof(ItemData) })] [HarmonyPriority(800)] private static bool RemoveOneItemPrefix(Inventory __instance, ItemData item) { return ShouldRemoveItem(__instance, item); } private static bool ShouldRemoveItem(Inventory __instance, ItemData item) { if (__instance == null || item == null) { return false; } bool flag = !string.IsNullOrEmpty(_targetContainer); bool flag2 = !string.IsNullOrEmpty(_allowedItem); if (flag && flag2) { return item.PrefabName() != _allowedItem; } return true; } [HarmonyPrefix] [HarmonyPatch(typeof(Inventory), "Load")] private static void LoadPrefix(Inventory __instance) { if (__instance != null) { _loadingContainer = __instance.m_name; } } [HarmonyPostfix] [HarmonyPatch(typeof(Inventory), "Load")] private static void LoadPostfix() { _loadingContainer = null; } } public class VisualStack : MonoBehaviour { public List<Transform> stackMeshes = new List<Transform>(); private Container container; private Inventory inventory; private void Start() { container = ((Component)this).GetComponentInParent<Container>(); if (Object.op_Implicit((Object)(object)container)) { inventory = container.GetInventory(); } if (inventory != null) { Inventory obj = inventory; obj.m_onChanged = (Action)Delegate.Combine(obj.m_onChanged, new Action(UpdateVisuals)); UpdateVisuals(); } } private void UpdateVisuals() { SetVisualsActive(inventory.SlotsUsedPercentage()); } public void SetVisualsActive(float fillPercentage) { float num = Mathf.Ceil(fillPercentage / 100f * (float)stackMeshes.Count); for (int i = 0; i < stackMeshes.Count; i++) { bool active = i == 0 || (float)i < num; ((Component)stackMeshes[i]).gameObject.SetActive(active); } } } } namespace DynamicStoragePiles.Patches { [HarmonyPatch] public class PlacementPatch { [HarmonyPatch(typeof(Player), "SetupPlacementGhost")] [HarmonyPostfix] public static void SetupPlacementGhostPatch(Player __instance) { if (Object.op_Implicit((Object)(object)__instance.m_placementGhost)) { VisualStack[] componentsInChildren = __instance.m_placementGhost.GetComponentsInChildren<VisualStack>(); foreach (VisualStack visualStack in componentsInChildren) { Object.Destroy((Object)(object)visualStack); } } } } } namespace DynamicStoragePiles.Compatibility { public static class AzuAutoStore { private static class AzuAutoStore_After_2_0_0 { [HarmonyPatch("AzuAutoStore.Util.Boxes, AzuAutoStore", "CanItemBeStored")] [HarmonyPostfix] private static void CanItemBeStoredPatch(string container, string prefab, ref bool __result) { if (__result && ConfigSettings.azuAutoStoreItemWhitelist.Value && DynamicStoragePiles.IsStackPiece(container, out var allowedItem) && prefab != allowedItem) { __result = false; } } } private static class AzuAutoStore_Before_2_0_0 { [HarmonyPatch("AzuAutoStore.Util.Functions, AzuAutoStore", "CheckDisallowedItems")] [HarmonyPostfix] private static void CheckDisallowedItemsPatch(Container container, ItemData item, ref bool __result) { if (!__result && ConfigSettings.azuAutoStoreItemWhitelist.Value && Object.op_Implicit((Object)(object)container) && item != null && Object.op_Implicit((Object)(object)item.m_dropPrefab)) { string prefabName = Utils.GetPrefabName(((Object)container).name); if (DynamicStoragePiles.IsStackPiece(prefabName, out var allowedItem) && ((Object)item.m_dropPrefab).name != allowedItem) { __result = true; } } } } public static void Init() { PluginInfo val = Chainloader.PluginInfos["Azumatt.AzuAutoStore"]; if (val.Metadata.Version >= new Version(2, 0, 0)) { DynamicStoragePiles.harmony.PatchAll(typeof(AzuAutoStore_After_2_0_0)); } else { DynamicStoragePiles.harmony.PatchAll(typeof(AzuAutoStore_Before_2_0_0)); } } } public static class IngotStacks { private static AssetBundle assetBundle; public static List<string> ingotStacks = new List<string>(); public static List<string> dynamicIngotStacks = new List<string>(); public static void Init() { assetBundle = PieceHelper.GetAssetBundle("stackedingots"); ConvertToPiece("ingot_copper_stack", "vfx_copper_stack_destroyed", "MS_IngotStacks_Copper", "Copper"); ConvertToPiece("ingot_tin_stack", "vfx_tin_stack_destroyed", "MS_IngotStacks_Tin", "Tin"); ConvertToPiece("ingot_bronze_stack", "vfx_bronze_stack_destroyed", "MS_IngotStacks_Bronze", "Bronze"); ConvertToPiece("ingot_iron_stack", "vfx_iron_stack_destroyed", "MS_IngotStacks_Iron", "Iron"); ConvertToPiece("ingot_silver_stack", "vfx_silver_stack_destroyed", "MS_IngotStacks_Silver", "Silver"); ConvertToPiece("ingot_blackmetal_stack", "vfx_blackmetal_stack_destroyed", "MS_IngotStacks_Blackmetal", "BlackMetal"); ConvertToPiece("ingot_flametal_stack", "vfx_flametal_stack_destroyed", "MS_IngotStacks_FlametalNew", "FlametalNew"); } public static void ConvertToPiece(string baseAssetName, string vfxName, string newPrefabName, string resource) { ingotStacks.Add(baseAssetName); dynamicIngotStacks.Add(newPrefabName); GameObject val = assetBundle.LoadAsset<GameObject>(baseAssetName); GameObject val2 = PieceHelper.FindDestroyVFX(val, vfxName); GameObject prefab = PrefabManager.Instance.CreateClonedPrefab(newPrefabName, val2); prefab = PieceHelper.PreparePiecePrefab(prefab, val, "$" + baseAssetName); ((Object)prefab).name = newPrefabName; DynamicStoragePiles.Instance.AddCompatPiece(prefab, resource, 3); } } public static class MoreStacks { public static List<string> staticStacks = new List<string>(); public static List<string> dynamicStacks = new List<string>(); private static BaseUnityPlugin moreStacksInstance = null; private static Dictionary<string, string> vanillaNameToDynamicStorageNameMap = new Dictionary<string, string> { { "wood_fine_stack", "finewood_stack" }, { "wood_core_stack", "corewood_stack" }, { "wood_yggdrasil_stack", "yggdrasil_wood_stack" }, { "treasure_stack", "coin_pile" } }; public static void Init() { if (!Object.op_Implicit((Object)(object)moreStacksInstance) && Chainloader.PluginInfos.TryGetValue("ujhik.MoreStacks", out var value)) { moreStacksInstance = value.Instance; if (!Object.op_Implicit((Object)(object)moreStacksInstance)) { Logger.LogWarning((object)"Failed to cast mod instance for 'ujhik.MoreStacks'."); return; } } FieldInfo field = ((object)moreStacksInstance).GetType().GetField("stackInfoList", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (field != null) { object value2 = field.GetValue(moreStacksInstance); if (!(value2 is IEnumerable enumerable)) { return; } { foreach (object item in enumerable) { Type type = item.GetType(); PropertyInfo property = type.GetProperty("idStackToDuplicate"); PropertyInfo property2 = type.GetProperty("idStackMaterial"); string stackToCloneId = property?.GetValue(item) as string; string materialPrefabId = property2?.GetValue(item) as string; ConvertToPiece(stackToCloneId, materialPrefabId); } return; } } Logger.LogWarning((object)"ujhik.MoreStacks: Failed to retrieve stackInfoList field via reflection, dynamic piles could not be generated"); } public static void ConvertToPiece(string stackToCloneId, string materialPrefabId) { //IL_00e3: Unknown result type (might be due to invalid IL or missing references) if (vanillaNameToDynamicStorageNameMap.TryGetValue(stackToCloneId, out var value)) { stackToCloneId = value; } string text = (string)((object)moreStacksInstance).GetType().GetMethod("getStackName", BindingFlags.Static | BindingFlags.Public)?.Invoke(moreStacksInstance, new object[1] { materialPrefabId }); string text2 = "MS_container_MoreStacks"; string text3 = text2 + "_" + materialPrefabId + "_pile"; string text4 = "MS_container_" + stackToCloneId; staticStacks.Add(text); dynamicStacks.Add(text3); GameObject prefab = PrefabManager.Instance.GetPrefab(text4); GameObject prefab2 = PrefabManager.Instance.GetPrefab(text); GameObject prefab3 = PrefabManager.Instance.GetPrefab(materialPrefabId); GameObject val = PrefabManager.Instance.CreateClonedPrefab(text3, prefab); Object.DestroyImmediate((Object)(object)val.GetComponent<Container>()); val.transform.localScale = prefab2.transform.localScale; string name = prefab2.GetComponent<Piece>().m_name; val = PieceHelper.PreparePiecePrefab(val, prefab, name); val.GetComponent<Piece>().m_name = name; Material sharedMaterial = ((Renderer)prefab2.GetComponentInChildren<MeshRenderer>()).sharedMaterial; MeshRenderer[] componentsInChildren = val.GetComponentsInChildren<MeshRenderer>(); foreach (MeshRenderer val2 in componentsInChildren) { ((Renderer)val2).sharedMaterial = sharedMaterial; } DynamicStoragePiles.Instance.AddCompatPiece(val, materialPrefabId, GetMaterialCostForPiece(materialPrefabId), addGraphics: true); } public static int GetMaterialCostForPiece(string materialPrefabId) { if (materialPrefabId.Contains("Ore") || materialPrefabId.Contains("Scrap")) { return 3; } return 10; } } public static class RefinedStonePieces { private static AssetBundle assetBundle; public static List<string> staticStacks = new List<string>(); public static List<string> dynamicStacks = new List<string>(); public static void Init() { assetBundle = PieceHelper.GetAssetBundle("refinedstonepieces"); ConvertRefinedStoneStackToPiece("BRP_RefinedStone_Stack", "MS_RefinedStonePieces_RefinedStone_Stack", "BRP_RefinedStone"); } public static void ConvertRefinedStoneStackToPiece(string baseAssetName, string newPrefabName, string resource) { staticStacks.Add(baseAssetName); dynamicStacks.Add(newPrefabName); GameObject val = assetBundle.LoadAsset<GameObject>(baseAssetName); GameObject prefab = PrefabManager.Instance.CreateClonedPrefab(newPrefabName, val); prefab = PieceHelper.PreparePiecePrefab(prefab, val, "$brp_refinedstone_stack"); ((Object)prefab).name = newPrefabName; List<Transform> source = prefab.GetComponent<VisualStack>().stackMeshes.OrderBy((Transform t) => t.position.y).ToList(); IOrderedEnumerable<Transform> first = from t in source.Skip(0).Take(6) orderby t.position.z select t; IOrderedEnumerable<Transform> second = from t in source.Skip(6).Take(6) orderby t.position.x select t; IOrderedEnumerable<Transform> second2 = from t in source.Skip(12).Take(6) orderby t.position.z select t; prefab.GetComponent<VisualStack>().stackMeshes = first.Concat(second).Concat(second2).ToList(); DynamicStoragePiles.Instance.AddCompatPiece(prefab, resource, 10, addGraphics: true); } } public static class StackedBars { private static AssetBundle assetBundle; public static List<string> stackedBars = new List<string>(); public static List<string> dynamicStackedBars = new List<string>(); public static void Init() { assetBundle = PieceHelper.GetAssetBundle("stackedbars"); ConvertToPiece("stack_tinbars", "MS_StackedBars_Tin", "Tin"); ConvertToPiece("stack_copperbars", "MS_StackedBars_Copper", "Copper"); ConvertToPiece("stack_bronzebars", "MS_StackedBars_Bronze", "Bronze"); ConvertToPiece("stack_ironbars", "MS_StackedBars_Iron", "Iron"); ConvertToPiece("stack_silverbars", "MS_StackedBars_Silver", "Silver"); ConvertToPiece("stack_blackmetalbars", "MS_StackedBars_BlackMetal", "BlackMetal"); ConvertToPiece("stack_flametalbars", "MS_StackedBars_FlameMetalNew", "FlametalNew"); } public static void ConvertToPiece(string baseAssetName, string newPrefabName, string resource) { stackedBars.Add(baseAssetName); dynamicStackedBars.Add(newPrefabName); GameObject val = assetBundle.LoadAsset<GameObject>(baseAssetName); GameObject prefab = PrefabManager.Instance.CreateClonedPrefab(newPrefabName, val); prefab = PieceHelper.PreparePiecePrefab(prefab, val, "$piece_" + baseAssetName); ((Object)prefab).name = newPrefabName; DynamicStoragePiles.Instance.AddCompatPiece(prefab, resource, 3); } } }