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 PlayerTradingChest v1.0.2
marchiori.playertradingchest.dll
Decompiled 20 hours ago
The result has been truncated due to the large size, download it to view full contents!
using System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.Globalization; using System.IO; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Text; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using HarmonyLib; using Marchiori.PlayerTradingChest.Configuration; using Marchiori.PlayerTradingChest.Rules; using Marchiori.PlayerTradingChest.ValheimData; using Marchiori.Utils.Localization; using Marchiori.Utils.Notificator; using Marchiori.Utils.SignTextManager; using Microsoft.CodeAnalysis; using Splatform; using UnityEngine; using UnityEngine.UI; [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.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")] [assembly: AssemblyCompany("marchiori.playertradingchest")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+ee52b2bfcab53d7e96836822c3d6ec6f3c6f91ae")] [assembly: AssemblyProduct("marchiori.playertradingchest")] [assembly: AssemblyTitle("marchiori.playertradingchest")] [assembly: AssemblyVersion("1.0.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Marchiori.PlayerTradingChest { [BepInPlugin("marchiori.playertradingchest", "Player Trading Chest", "1.0.2")] public sealed class BepinexPlugin : BaseUnityPlugin { public const string Guid = "marchiori.playertradingchest"; internal static ManualLogSource Log { get; private set; } private void Awake() { //IL_001e: Unknown result type (might be due to invalid IL or missing references) Log = ((BaseUnityPlugin)this).Logger; ModConfig.Load(((BaseUnityPlugin)this).Config); new Harmony("marchiori.playertradingchest").PatchAll(); ((BaseUnityPlugin)this).Logger.LogInfo((object)"Player Trading Chest loaded."); } } } namespace Marchiori.PlayerTradingChest.ValheimPatches { [HarmonyPatch(typeof(Container), "GetHoverText")] internal static class Container_GetHoverText_Patch { private static bool Prefix(Container __instance, ref string __result) { if (!ShopLink.IsLinked(((Component)__instance).gameObject)) { return true; } __result = ((Localization.instance != null) ? Localization.instance.Localize("$ptc_22") : "Interact with the sign to perform the transaction"); return false; } } [HarmonyPatch(typeof(Container), "Interact")] internal static class Container_Interact_Patch { private static bool Prefix(Container __instance, Humanoid character, bool hold, ref bool __result) { if (hold || !ShopLink.IsLinked(((Component)__instance).gameObject)) { return true; } Player player = (Player)(object)((character is Player) ? character : null); if (ShopAccess.MayOpen(player, __instance)) { return true; } ShopMessages.Show(player, "$ptc_11"); __result = false; return false; } } [HarmonyPatch(typeof(Container), "SetInUse")] internal static class Container_SetInUse_Patch { private static void Postfix(Container __instance, bool inUse) { ShopState.SetOpen(__instance, inUse); } } [HarmonyPatch(typeof(InventoryGrid), "UpdateGui")] internal static class InventoryGrid_UpdateGui_Patch { private static void Postfix(InventoryGrid __instance) { SlotTint.Apply(__instance); } } [HarmonyPatch(typeof(Inventory), "AddItem", new Type[] { typeof(ItemData) })] internal static class Inventory_AddItem_Patch { private static bool Prefix(Inventory __instance, ItemData item, ref bool __result) { return !ShopInventory.TryRedirect(__instance, item, ref __result); } } [HarmonyPatch(typeof(Inventory), "CanAddItem", new Type[] { typeof(ItemData), typeof(int) })] internal static class Inventory_CanAddItem_Item_Patch { private static bool Prefix(Inventory __instance, ItemData item, int stack, ref bool __result) { if ((Object)(object)ShopLink.FindChest(__instance) == (Object)null) { return true; } __result = ShopInventory.CanAccept(__instance, item, stack); return false; } } [HarmonyPatch(typeof(Inventory), "CanAddItem", new Type[] { typeof(GameObject), typeof(int) })] internal static class Inventory_CanAddItem_Prefab_Patch { private static bool Prefix(Inventory __instance, GameObject prefab, int stack, ref bool __result) { if ((Object)(object)ShopLink.FindChest(__instance) == (Object)null) { return true; } __result = ShopInventory.CanAcceptPrefab(__instance, prefab, stack); return false; } } [HarmonyPatch(typeof(Inventory), "MoveItemToThis", new Type[] { typeof(Inventory), typeof(ItemData), typeof(int), typeof(int), typeof(int) })] internal static class Inventory_MoveItemAmount_Patch { private static int _before; private static int _index = -1; private static bool Prefix(Inventory __instance, ItemData item, int x, int y, ref bool __result) { _index = -1; if ((Object)(object)ShopLink.FindChest(__instance) == (Object)null) { return true; } int width = __instance.GetWidth(); int index = ((width > 0) ? (y * width + x) : (-1)); StackState[] slots = ShopInventory.ReadChest(__instance); if (!ShopRules.MayPlace(slots, index, ShopInventory.FromItem(item), ShopRules.WithdrawOnly(ModConfig.Enable, hasSign: true, slots))) { __result = false; return false; } _index = index; _before = ShopInventory.StackAt(__instance, x, y); return true; } private static void Postfix(Inventory __instance) { if (_index >= 0) { int index = _index; int before = _before; _index = -1; ShopInventory.Touch(__instance, index, before); } } } [HarmonyPatch(typeof(Inventory))] internal static class Inventory_RemoveItem_Patch { [HarmonyPatch("RemoveItem", new Type[] { typeof(ItemData), typeof(int) })] [HarmonyPostfix] private static void ByAmount(Inventory __instance) { ShopInventory.Changed(__instance); } [HarmonyPatch("RemoveItem", new Type[] { typeof(ItemData) })] [HarmonyPostfix] private static void Whole(Inventory __instance) { ShopInventory.Changed(__instance); } [HarmonyPatch("RemoveItem", new Type[] { typeof(int) })] [HarmonyPostfix] private static void ByIndex(Inventory __instance) { ShopInventory.Changed(__instance); } } [HarmonyPatch(typeof(Localization), "SetupLanguage")] internal static class Localization_SetupLanguage_Patch { private static void Postfix(Localization __instance) { Localization.OnLanguageChange = (Action)Delegate.Remove(Localization.OnLanguageChange, new Action(OnLanguageChanged)); Localization.OnLanguageChange = (Action)Delegate.Combine(Localization.OnLanguageChange, new Action(OnLanguageChanged)); Apply(__instance, __instance.GetSelectedLanguage()); } private static void OnLanguageChanged() { if (Localization.instance != null) { Apply(Localization.instance, Localization.instance.GetSelectedLanguage()); } } private static void Apply(Localization localization, string language) { string directoryName = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location); LanguageFiles.Apply(localization, language, directoryName, "ptc"); ShopSign.RefreshAll(); } } [HarmonyPatch(typeof(ObjectDB), "Awake")] internal static class ObjectDB_Awake_Patch { private static void Postfix(ObjectDB __instance) { GemPrefabs.RegisterItems(__instance); } } [HarmonyPatch(typeof(Player), "CheckCanRemovePiece")] internal static class Player_CheckCanRemovePiece_Patch { private static bool Prefix(Player __instance, Piece piece, ref bool __result) { if ((Object)(object)piece == (Object)null || !ShopLink.IsLinked(((Component)piece).gameObject)) { return true; } __result = ShopAccess.MayBreak(__instance, (Component)(object)piece); return false; } } [HarmonyPatch(typeof(Player), "RemovePiece")] internal static class Player_RemovePiece_Patch { private static bool Prefix(Player __instance, ref bool __result) { Piece hoveringPiece = __instance.GetHoveringPiece(); if ((Object)(object)hoveringPiece == (Object)null || !ShopLink.IsLinked(((Component)hoveringPiece).gameObject)) { return true; } if (ShopAccess.MayBreak(__instance, (Component)(object)hoveringPiece)) { return true; } __result = false; return false; } } [HarmonyPatch(typeof(Player), "TryPlacePiece")] internal static class Player_TryPlacePiece_Patch { private static bool Prefix(Player __instance, Piece piece, ref bool __result) { return ShopPlacement.TryHandle(__instance, piece, ref __result); } } [HarmonyPatch(typeof(Sign), "Interact")] internal static class Sign_Interact_Patch { private static bool Prefix(Sign __instance, Humanoid character, bool hold, ref bool __result) { if (!ShopLink.IsLinked(((Component)__instance).gameObject)) { return true; } if (hold) { __result = false; return false; } Player player = (Player)(object)((character is Player) ? character : null); Container chest = ShopLink.ChestOf(((Component)__instance).gameObject); __result = ShopTrade.Try(player, chest); return false; } } [HarmonyPatch(typeof(Sign), "UseItem")] internal static class Sign_UseItem_Patch { private static bool Prefix(Sign __instance, ref bool __result) { if (!ShopLink.IsLinked(((Component)__instance).gameObject)) { return true; } __result = false; return false; } } [HarmonyPatch(typeof(StoreGui), "GetSellableItem")] internal static class StoreGui_GetSellableItem_Patch { private static void Postfix(StoreGui __instance, ref ItemData __result) { if (HaldorStock.BlocksSale(__instance, __result)) { __result = null; } } } [HarmonyPatch(typeof(TeleportWorld), "Teleport")] internal static class TeleportWorld_Teleport_Patch { private static void Prefix(Player player, ref bool __state) { __state = (Object)(object)player != (Object)null && ((Character)player).IsTeleporting(); } private static void Postfix(Player player, bool __state) { if (!((Object)(object)player == (Object)null || __state) && ((Character)player).IsTeleporting()) { GemPortal.Apply(player); } } } [HarmonyPatch(typeof(Trader), "GetAvailableItems")] internal static class Trader_GetAvailableItems_Patch { private static void Postfix(Trader __instance, List<TradeItem> __result) { HaldorStock.Append(__instance, __result); } } [HarmonyPatch(typeof(WearNTear), "Destroy")] internal static class WearNTear_Destroy_Patch { private static void Prefix(WearNTear __instance) { ShopBreak.OnDestroying(__instance); } } [HarmonyPatch(typeof(ZNetScene), "Awake")] internal static class ZNetScene_Awake_Patch { private static void Postfix(ZNetScene __instance) { GemPrefabs.RegisterDrops(__instance); } } [HarmonyPatch(typeof(ZNetView), "Awake")] internal static class ZNetView_Awake_Patch { private static void Postfix(ZNetView __instance) { if ((Object)(object)__instance == (Object)null || !__instance.IsValid()) { return; } ZDO zDO = __instance.GetZDO(); if (zDO != null && zDO.GetLong("ptc_link", 0L) != 0) { if ((Object)(object)((Component)__instance).GetComponent<ShopWatch>() == (Object)null) { ((Component)__instance).gameObject.AddComponent<ShopWatch>(); } ShopLink.Register(((Component)__instance).gameObject); } } } } namespace Marchiori.PlayerTradingChest.ValheimData { internal static class EnglishItems { private static readonly FieldInfo SettingsField = AccessTools.Field(typeof(Localization), "m_localizationSettings"); private static Dictionary<string, string> _words; private static bool _ready; internal static string Name(string prefab) { string token = Token(prefab); string text = Word(token); if (!string.IsNullOrEmpty(text)) { return text; } return prefab ?? ""; } internal static string FromToken(string token) { if (string.IsNullOrEmpty(token)) { return ""; } if (token.StartsWith("$", StringComparison.Ordinal)) { token = token.Substring(1); } string text = Word(token); if (!string.IsNullOrEmpty(text)) { return text; } return token; } private static string Token(string prefab) { if ((Object)(object)ObjectDB.instance == (Object)null || string.IsNullOrEmpty(prefab)) { return ""; } GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(prefab); ItemDrop val = (((Object)(object)itemPrefab != (Object)null) ? itemPrefab.GetComponent<ItemDrop>() : null); if ((Object)(object)val == (Object)null || val.m_itemData == null || val.m_itemData.m_shared == null) { return ""; } string text = val.m_itemData.m_shared.m_name ?? ""; if (text.StartsWith("$", StringComparison.Ordinal)) { return text.Substring(1); } return text; } private static string Word(string token) { if (string.IsNullOrEmpty(token)) { return ""; } if (!_ready) { Dictionary<string, string> dictionary = Load(); if (dictionary == null) { return ""; } _words = dictionary; _ready = true; } if (_words != null && _words.TryGetValue(token, out var value)) { return value; } return ""; } private static Dictionary<string, string> Load() { Localization instance = Localization.instance; if (instance == null || SettingsField == null) { return null; } object? value = SettingsField.GetValue(instance); LocalizationSettings val = (LocalizationSettings)((value is LocalizationSettings) ? value : null); if ((Object)(object)val == (Object)null || val.Localizations == null) { return null; } Dictionary<string, string> dictionary = new Dictionary<string, string>(); for (int i = 0; i < val.Localizations.Count; i++) { TextAsset val2 = val.Localizations[i]; if ((Object)(object)val2 == (Object)null || string.IsNullOrEmpty(val2.text)) { continue; } Dictionary<string, string> dictionary2 = EnglishSheet.Read(val2.text); foreach (KeyValuePair<string, string> item in dictionary2) { if (!dictionary.ContainsKey(item.Key)) { dictionary[item.Key] = item.Value; } } } return dictionary; } } internal static class GemPortal { internal static void Apply(Player player) { if ((Object)(object)player == (Object)null || ((Humanoid)player).GetInventory() == null) { return; } Inventory inventory = ((Humanoid)player).GetInventory(); List<ItemData> list = new List<ItemData>(inventory.GetAllItems()); int[] array = new int[GemCatalog.All.Length]; for (int i = 0; i < list.Count; i++) { ItemData val = list[i]; if (val == null || val.m_equipped || (Object)(object)val.m_dropPrefab == (Object)null) { continue; } string text = ShopRules.Normalize(((Object)val.m_dropPrefab).name); for (int j = 0; j < GemCatalog.All.Length; j++) { if (!(GemCatalog.All[j].PrefabName != text)) { int num = ShopRules.PortalLoss(val.m_stack, GemCatalog.All[j].PortalLoss); if (num > 0) { inventory.RemoveItem(val, num); array[j] += num; } break; } } } for (int k = 0; k < array.Length; k++) { if (array[k] > 0) { ShopMessages.Show(player, "$ptc_19", array[k], -1, null, null, ShopMessages.PrefabName(GemCatalog.All[k].PrefabName)); } } } } internal static class GemPrefabs { private const string RubyName = "Ruby"; private static readonly List<GameObject> Prefabs = new List<GameObject>(); private static GameObject _holder; private static bool _logged; private static bool _warned; internal static void RegisterItems(ObjectDB database) { Ensure(database, ZNetScene.instance); AddToObjectDb(database); if ((Object)(object)ZNetScene.instance != (Object)null) { AddToScene(ZNetScene.instance); } LogOnce(); } internal static void RegisterDrops(ZNetScene scene) { Ensure(ObjectDB.instance, scene); if ((Object)(object)ObjectDB.instance != (Object)null) { AddToObjectDb(ObjectDB.instance); } AddToScene(scene); LogOnce(); } private static void Ensure(ObjectDB database, ZNetScene scene) { if (Prefabs.Count == GemCatalog.All.Length) { return; } GameObject val = FindRuby(database, scene); if ((Object)(object)val == (Object)null) { if (!_warned) { _warned = true; ManualLogSource log = BepinexPlugin.Log; if (log != null) { log.LogWarning((object)"Ruby was not found, so Emerald, Sapphire, and Diamond were not created."); } } return; } GameObject holder = Holder(); bool activeSelf = val.activeSelf; if (activeSelf) { val.SetActive(false); } try { GemDefinition[] all = GemCatalog.All; for (int i = 0; i < all.Length; i++) { if (!((Object)(object)FindPrefab(all[i].PrefabName) != (Object)null)) { Create(val, holder, all[i]); } } } finally { if (activeSelf) { val.SetActive(true); } } } private static void Create(GameObject ruby, GameObject holder, GemDefinition gem) { GameObject val = null; try { val = Object.Instantiate<GameObject>(ruby, holder.transform, false); ((Object)val).name = gem.PrefabName; Prepare(val, gem); val.SetActive(true); Prefabs.Add(val); val = null; } catch (Exception ex) { if ((Object)(object)val != (Object)null) { Object.Destroy((Object)(object)val); } ManualLogSource log = BepinexPlugin.Log; if (log != null) { log.LogWarning((object)("Could not create " + gem.PrefabName + ". " + ex.Message)); } } } private static void Prepare(GameObject clone, GemDefinition gem) { ItemDrop component = clone.GetComponent<ItemDrop>(); if ((Object)(object)component == (Object)null || component.m_itemData == null || component.m_itemData.m_shared == null) { throw new InvalidOperationException(gem.PrefabName + " has no item data."); } component.m_itemData = component.m_itemData.Clone(); SharedData val = CopyShared(component.m_itemData.m_shared); val.m_name = gem.NameToken; val.m_description = ""; val.m_value = gem.Value; val.m_weight = gem.Weight; val.m_maxStackSize = gem.StackSize; val.m_teleportable = true; component.m_itemData.m_shared = val; component.m_itemData.m_dropPrefab = clone; GemVisuals.Apply(val, clone, gem); } private static SharedData CopyShared(SharedData source) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Expected O, but got Unknown SharedData val = new SharedData(); FieldInfo[] sharedDataFields = ValheimMembers.SharedDataFields; foreach (FieldInfo fieldInfo in sharedDataFields) { fieldInfo.SetValue(val, Detach(fieldInfo.GetValue(source))); } return val; } private static object Detach(object value) { if (value == null) { return null; } if (value is Array array) { return array.Clone(); } if (!(value is IList list)) { return value; } try { IList list2 = (IList)Activator.CreateInstance(list.GetType()); for (int i = 0; i < list.Count; i++) { list2.Add(list[i]); } return list2; } catch (Exception) { return value; } } private static void AddToObjectDb(ObjectDB database) { if ((Object)(object)database == (Object)null || database.m_items == null || Prefabs.Count == 0) { return; } for (int i = 0; i < Prefabs.Count; i++) { GameObject val = Prefabs[i]; if ((Object)(object)val != (Object)null && !database.m_items.Contains(val)) { database.m_items.Add(val); } } ValheimMembers.RebuildItems(database); } private static void AddToScene(ZNetScene scene) { if ((Object)(object)scene == (Object)null || scene.m_prefabs == null || Prefabs.Count == 0) { return; } Dictionary<int, GameObject> dictionary = ValheimMembers.NamedPrefabs(scene); for (int i = 0; i < Prefabs.Count; i++) { GameObject val = Prefabs[i]; if (!((Object)(object)val == (Object)null)) { if (!scene.m_prefabs.Contains(val)) { scene.m_prefabs.Add(val); } if (dictionary != null) { dictionary[scene.GetPrefabHash(val)] = val; } } } } private static GameObject FindRuby(ObjectDB database, ZNetScene scene) { if ((Object)(object)database != (Object)null) { GameObject itemPrefab = database.GetItemPrefab("Ruby"); if ((Object)(object)itemPrefab != (Object)null) { return itemPrefab; } if (database.m_items != null) { for (int i = 0; i < database.m_items.Count; i++) { GameObject val = database.m_items[i]; if ((Object)(object)val != (Object)null && ((Object)val).name == "Ruby") { return val; } } } } if ((Object)(object)scene != (Object)null && scene.m_prefabs != null) { for (int j = 0; j < scene.m_prefabs.Count; j++) { GameObject val2 = scene.m_prefabs[j]; if ((Object)(object)val2 != (Object)null && ((Object)val2).name == "Ruby" && (Object)(object)val2.GetComponent<ItemDrop>() != (Object)null) { return val2; } } } return null; } private static GameObject FindPrefab(string name) { for (int i = 0; i < Prefabs.Count; i++) { GameObject val = Prefabs[i]; if ((Object)(object)val != (Object)null && ((Object)val).name == name) { return val; } } return null; } private static GameObject Holder() { //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0027: Expected O, but got Unknown if ((Object)(object)_holder != (Object)null) { return _holder; } _holder = new GameObject("playertradingchest gems"); _holder.SetActive(false); Object.DontDestroyOnLoad((Object)(object)_holder); return _holder; } internal static void ApplyNumbers() { for (int i = 0; i < Prefabs.Count; i++) { GameObject val = Prefabs[i]; if (!((Object)(object)val == (Object)null)) { GemDefinition gemDefinition = GemCatalog.Find(((Object)val).name); ItemDrop component = val.GetComponent<ItemDrop>(); if (gemDefinition != null && !((Object)(object)component == (Object)null) && component.m_itemData != null && component.m_itemData.m_shared != null) { component.m_itemData.m_shared.m_value = gemDefinition.Value; component.m_itemData.m_shared.m_weight = gemDefinition.Weight; component.m_itemData.m_shared.m_maxStackSize = gemDefinition.StackSize; } } } } private static void LogOnce() { if (!_logged && Prefabs.Count == GemCatalog.All.Length) { _logged = true; ManualLogSource log = BepinexPlugin.Log; if (log != null) { log.LogInfo((object)"Registered Emerald, Sapphire, and Diamond."); } } } } internal static class GemVisuals { private static readonly Dictionary<string, Texture2D> Cache = new Dictionary<string, Texture2D>(); private static readonly HashSet<string> ShiftedKeys = new HashSet<string>(); internal static void Apply(SharedData shared, GameObject root, GemDefinition gem) { if (shared == null || (Object)(object)root == (Object)null || gem == null) { return; } try { RecolorIcons(shared, gem); RecolorRenderers(root, gem); } catch (Exception ex) { ManualLogSource log = BepinexPlugin.Log; if (log != null) { log.LogWarning((object)("Could not recolor " + gem.PrefabName + ". It keeps Ruby's look. " + ex.Message)); } } } private static void RecolorIcons(SharedData shared, GemDefinition gem) { Sprite[] icons = shared.m_icons; if (icons == null) { return; } for (int i = 0; i < icons.Length; i++) { Sprite val = RecolorSprite(icons[i], gem); if ((Object)(object)val != (Object)null) { icons[i] = val; } } } private static void RecolorRenderers(GameObject root, GemDefinition gem) { //IL_00ce: Unknown result type (might be due to invalid IL or missing references) //IL_00d4: Unknown result type (might be due to invalid IL or missing references) //IL_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00bd: Unknown result type (might be due to invalid IL or missing references) Renderer[] componentsInChildren = root.GetComponentsInChildren<Renderer>(true); for (int i = 0; i < componentsInChildren.Length; i++) { Material[] materials = componentsInChildren[i].materials; foreach (Material val in materials) { if ((Object)(object)val == (Object)null) { continue; } bool shifted = false; Texture mainTexture = val.mainTexture; if ((Object)(object)mainTexture != (Object)null) { Texture2D val2 = RecolorTexture(mainTexture, gem, out shifted); if ((Object)(object)val2 != (Object)null) { val.mainTexture = (Texture)(object)val2; } } if (val.HasProperty("_Color")) { if (gem.White || shifted) { val.color = new Color(1f, 1f, 1f, val.color.a); } else { val.color = RecolorColor(val.color, gem); } } } } } private static Sprite RecolorSprite(Sprite sprite, GemDefinition gem) { //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_002d: Unknown result type (might be due to invalid IL or missing references) //IL_00ab: Unknown result type (might be due to invalid IL or missing references) //IL_00b2: Expected O, but got Unknown //IL_00d2: Unknown result type (might be due to invalid IL or missing references) //IL_010f: Unknown result type (might be due to invalid IL or missing references) //IL_0114: Unknown result type (might be due to invalid IL or missing references) //IL_0125: Unknown result type (might be due to invalid IL or missing references) //IL_012a: Unknown result type (might be due to invalid IL or missing references) //IL_0146: Unknown result type (might be due to invalid IL or missing references) //IL_0151: Unknown result type (might be due to invalid IL or missing references) //IL_0156: Unknown result type (might be due to invalid IL or missing references) //IL_0161: Unknown result type (might be due to invalid IL or missing references) //IL_016c: Unknown result type (might be due to invalid IL or missing references) //IL_0171: Unknown result type (might be due to invalid IL or missing references) //IL_01ad: 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 ((Object)(object)sprite == (Object)null || (Object)(object)sprite.texture == (Object)null) { return null; } Rect textureRect = sprite.textureRect; int x = (int)((Rect)(ref textureRect)).x; int y = (int)((Rect)(ref textureRect)).y; int num = (int)((Rect)(ref textureRect)).width; int num2 = (int)((Rect)(ref textureRect)).height; if (num <= 0 || num2 <= 0) { return null; } Texture2D val = ReadTexture((Texture)(object)sprite.texture); try { byte[] rgba = Crop(val, x, y, num, num2); GemTint.Recolor(rgba, gem.HueDegrees, gem.Saturation, gem.White); Texture2D val2 = new Texture2D(num, num2, (TextureFormat)4, false); ((Object)val2).name = gem.PrefabName + " icon"; ((Texture)val2).filterMode = ((Texture)sprite.texture).filterMode; ((Texture)val2).wrapMode = (TextureWrapMode)1; val2.SetPixels32(ToPixels(rgba)); val2.Apply(); Vector2 val3 = default(Vector2); ((Vector2)(ref val3))..ctor(0.5f, 0.5f); Rect rect = sprite.rect; if (((Rect)(ref rect)).width > 0f) { rect = sprite.rect; if (((Rect)(ref rect)).height > 0f) { float x2 = sprite.pivot.x; rect = sprite.rect; float num3 = x2 / ((Rect)(ref rect)).width; float y2 = sprite.pivot.y; rect = sprite.rect; ((Vector2)(ref val3))..ctor(num3, y2 / ((Rect)(ref rect)).height); } } float num4 = ((sprite.pixelsPerUnit > 0f) ? sprite.pixelsPerUnit : 100f); return Sprite.Create(val2, new Rect(0f, 0f, (float)num, (float)num2), val3, num4); } finally { Object.DestroyImmediate((Object)(object)val); } } private static Texture2D RecolorTexture(Texture source, GemDefinition gem, out bool shifted) { //IL_008b: Unknown result type (might be due to invalid IL or missing references) //IL_0092: Expected O, but got Unknown //IL_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00c1: Unknown result type (might be due to invalid IL or missing references) string text = gem.PrefabName + ":" + ((Object)source).GetInstanceID(); if (Cache.TryGetValue(text, out var value)) { shifted = ShiftedKeys.Contains(text); return value; } Texture2D val = ReadTexture(source); try { Color32[] pixels = val.GetPixels32(); byte[] rgba = FromPixels(pixels); bool flag = GemTint.Recolor(rgba, gem.HueDegrees, gem.Saturation, gem.White); Texture2D val2 = new Texture2D(((Texture)val).width, ((Texture)val).height, (TextureFormat)4, false); ((Object)val2).name = gem.PrefabName + " " + ((Object)source).name; ((Texture)val2).filterMode = source.filterMode; ((Texture)val2).wrapMode = source.wrapMode; val2.SetPixels32(ToPixels(rgba)); val2.Apply(); Cache[text] = val2; if (flag) { ShiftedKeys.Add(text); } shifted = flag; return val2; } finally { Object.DestroyImmediate((Object)(object)val); } } private static Texture2D ReadTexture(Texture source) { //IL_0039: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Expected O, but got Unknown //IL_0058: Unknown result type (might be due to invalid IL or missing references) RenderTexture temporary = RenderTexture.GetTemporary(source.width, source.height, 0, (RenderTextureFormat)0); RenderTexture active = RenderTexture.active; try { Graphics.Blit(source, temporary); RenderTexture.active = temporary; Texture2D val = new Texture2D(source.width, source.height, (TextureFormat)4, false); val.ReadPixels(new Rect(0f, 0f, (float)source.width, (float)source.height), 0, 0); val.Apply(); return val; } finally { RenderTexture.active = active; RenderTexture.ReleaseTemporary(temporary); } } private static byte[] Crop(Texture2D readable, int x, int y, int width, int height) { //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_0088: 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_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00af: Unknown result type (might be due to invalid IL or missing references) Color32[] pixels = readable.GetPixels32(); byte[] array = new byte[width * height * 4]; int width2 = ((Texture)readable).width; for (int i = 0; i < height; i++) { int num = y + i; if (num < 0 || num >= ((Texture)readable).height) { continue; } for (int j = 0; j < width; j++) { int num2 = x + j; if (num2 >= 0 && num2 < width2) { Color32 val = pixels[num * width2 + num2]; int num3 = (i * width + j) * 4; array[num3] = val.r; array[num3 + 1] = val.g; array[num3 + 2] = val.b; array[num3 + 3] = val.a; } } } return array; } private static byte[] FromPixels(Color32[] pixels) { byte[] array = new byte[pixels.Length * 4]; for (int i = 0; i < pixels.Length; i++) { int num = i * 4; array[num] = pixels[i].r; array[num + 1] = pixels[i].g; array[num + 2] = pixels[i].b; array[num + 3] = pixels[i].a; } return array; } private static Color32[] ToPixels(byte[] rgba) { //IL_0029: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) Color32[] array = (Color32[])(object)new Color32[rgba.Length / 4]; for (int i = 0; i < array.Length; i++) { int num = i * 4; array[i] = new Color32(rgba[num], rgba[num + 1], rgba[num + 2], rgba[num + 3]); } return array; } private static Color RecolorColor(Color color, GemDefinition gem) { //IL_0009: 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_0025: Unknown result type (might be due to invalid IL or missing references) //IL_005c: Unknown result type (might be due to invalid IL or missing references) //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_006c: Unknown result type (might be due to invalid IL or missing references) //IL_0071: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Unknown result type (might be due to invalid IL or missing references) byte[] array = new byte[4] { ToByte(color.r), ToByte(color.g), ToByte(color.b), 255 }; GemTint.Recolor(array, gem.HueDegrees, gem.Saturation, gem.White); return Color32.op_Implicit(new Color32(array[0], array[1], array[2], ToByte(color.a))); } private static byte ToByte(float channel) { if (channel <= 0f) { return 0; } if (channel >= 1f) { return byte.MaxValue; } return (byte)Math.Round(channel * 255f, MidpointRounding.AwayFromZero); } } internal static class HaldorStock { internal static bool IsHaldor(Trader trader) { if ((Object)(object)trader == (Object)null) { return false; } string text = ShopRules.Normalize(((Object)((Component)trader).gameObject).name); return text.IndexOf("Haldor", StringComparison.OrdinalIgnoreCase) >= 0 && text.IndexOf("Hildir", StringComparison.OrdinalIgnoreCase) < 0; } internal static void Append(Trader trader, List<TradeItem> items) { //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Unknown result type (might be due to invalid IL or missing references) //IL_0077: Unknown result type (might be due to invalid IL or missing references) //IL_007e: Unknown result type (might be due to invalid IL or missing references) //IL_008f: Expected O, but got Unknown if (!ModConfig.HaldorSells || !IsHaldor(trader) || items == null || (Object)(object)ObjectDB.instance == (Object)null) { return; } for (int i = 0; i < GemCatalog.All.Length; i++) { GemDefinition gemDefinition = GemCatalog.All[i]; GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(gemDefinition.PrefabName); ItemDrop val = (((Object)(object)itemPrefab != (Object)null) ? itemPrefab.GetComponent<ItemDrop>() : null); if (!((Object)(object)val == (Object)null)) { items.Add(new TradeItem { m_prefab = val, m_stack = 1, m_price = gemDefinition.Value }); } } } internal static bool BlocksSale(StoreGui gui, ItemData item) { if (item == null || (Object)(object)item.m_dropPrefab == (Object)null) { return false; } if (GemCatalog.Find(ShopRules.Normalize(((Object)item.m_dropPrefab).name)) == null) { return false; } Trader trader = (Trader)(((Object)(object)gui != (Object)null && ValheimMembers.TraderField != null) ? /*isinst with value type is only supported in some contexts*/: null); return !ModConfig.HaldorBuys || !IsHaldor(trader); } } internal static class ShopAccess { internal static bool MayOpen(Player player, Container chest) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)player == (Object)null || (Object)(object)chest == (Object)null) { return false; } if (WardCovers(((Component)chest).transform.position, out var allowed)) { return allowed; } Piece component = ((Component)chest).GetComponent<Piece>(); return (Object)(object)component != (Object)null && component.GetCreator() == player.GetPlayerID(); } internal static bool MayBreak(Player player, Component piece) { return (Object)(object)player != (Object)null && (Object)(object)piece != (Object)null && ShopLink.IsLinked(piece.gameObject); } internal static bool WardCovers(Vector3 point, out bool allowed) { //IL_00f4: Unknown result type (might be due to invalid IL or missing references) //IL_009c: Unknown result type (might be due to invalid IL or missing references) allowed = true; bool flag = false; List<PrivateArea> list = ((ValheimMembers.AllAreas != null) ? (ValheimMembers.AllAreas.GetValue(null) as List<PrivateArea>) : null); if (list == null || ValheimMembers.AreaEnabled == null || ValheimMembers.AreaInside == null) { return false; } for (int i = 0; i < list.Count; i++) { PrivateArea val = list[i]; if (!((Object)(object)val == (Object)null) && (bool)ValheimMembers.AreaEnabled.Invoke(val, null) && (bool)ValheimMembers.AreaInside.Invoke(val, new object[2] { point, 0f })) { flag = true; } } if (!flag) { allowed = false; return false; } allowed = PrivateArea.CheckAccess(point, 0f, false, false); return true; } } internal static class ShopBreak { private static readonly HashSet<long> Busy = new HashSet<long>(); internal static void Break(GameObject piece) { if ((Object)(object)piece == (Object)null || !ShopLink.IsLinked(piece)) { return; } if ((Object)(object)piece.GetComponent<Container>() != (Object)null) { DropSign(piece); return; } long item = ShopLink.LinkId(piece); if (!Busy.Add(item)) { return; } try { Remove(piece); } finally { Busy.Remove(item); } } internal static void DropSign(GameObject chestObject) { Container val = (((Object)(object)chestObject != (Object)null) ? chestObject.GetComponent<Container>() : null); if ((Object)(object)val == (Object)null) { val = ShopLink.ChestOf(chestObject); } if ((Object)(object)val == (Object)null || !ShopLink.IsLinked(((Component)val).gameObject)) { return; } long item = ShopLink.LinkId(((Component)val).gameObject); if (!Busy.Add(item)) { return; } try { GameObject val2 = ShopLink.Partner(((Component)val).gameObject); ReleaseChest(((Component)val).gameObject); if ((Object)(object)val2 != (Object)null) { Remove(val2); } } finally { Busy.Remove(item); } } internal static void OnDestroying(WearNTear wear) { if ((Object)(object)wear == (Object)null || !ShopLink.IsLinked(((Component)wear).gameObject)) { return; } long item = ShopLink.LinkId(((Component)wear).gameObject); if (!Busy.Add(item)) { return; } try { if ((Object)(object)((Component)wear).GetComponent<Container>() != (Object)null) { GameObject val = ShopLink.Partner(((Component)wear).gameObject); if ((Object)(object)val != (Object)null) { Remove(val); } } else { ReleaseChest(ShopLink.Partner(((Component)wear).gameObject)); } } finally { Busy.Remove(item); } } private static void ReleaseChest(GameObject chestObject) { if (!((Object)(object)chestObject == (Object)null)) { ShopState.Relax(chestObject); Container component = chestObject.GetComponent<Container>(); if ((Object)(object)component != (Object)null) { ShopLink.Unlink(component); } } } private static void Remove(GameObject gameObject) { if (!((Object)(object)gameObject == (Object)null)) { if ((Object)(object)gameObject.transform.parent != (Object)null) { gameObject.transform.SetParent((Transform)null, true); } ZNetView component = gameObject.GetComponent<ZNetView>(); if ((Object)(object)component != (Object)null && component.IsValid() && !component.IsOwner()) { component.ClaimOwnership(); } WearNTear component2 = gameObject.GetComponent<WearNTear>(); if ((Object)(object)component2 != (Object)null) { component2.Remove(false); } else if ((Object)(object)ZNetScene.instance != (Object)null) { ZNetScene.instance.Destroy(gameObject); } } } } internal static class ShopInventory { internal static StackState[] ReadChest(Inventory inventory) { if (inventory == null) { return new StackState[0]; } int width = inventory.GetWidth(); int height = inventory.GetHeight(); StackState[] array = new StackState[width * height]; for (int i = 0; i < height; i++) { for (int j = 0; j < width; j++) { ItemData itemAt = inventory.GetItemAt(j, i); if (itemAt != null) { array[i * width + j] = FromItem(itemAt); } } } return array; } internal static List<StackState> ReadPlayer(Player player) { List<StackState> list = new List<StackState>(); Inventory val = (((Object)(object)player != (Object)null) ? ((Humanoid)player).GetInventory() : null); if (val == null) { return list; } List<ItemData> allItems = val.GetAllItems(); for (int i = 0; i < allItems.Count; i++) { list.Add(FromItem(allItems[i])); } return list; } internal static StackState FromItem(ItemData item) { StackState stackState = new StackState(); if (item == null) { return stackState; } stackState.Amount = item.m_stack; stackState.Quality = item.m_quality; stackState.Equipped = item.m_equipped; float maxDurability = item.GetMaxDurability(); stackState.Durability = ((maxDurability > 0.001f) ? item.GetDurabilityPercentage() : 1f); stackState.MaxStack = ((item.m_shared == null || item.m_shared.m_maxStackSize <= 0) ? 1 : item.m_shared.m_maxStackSize); if ((Object)(object)item.m_dropPrefab != (Object)null) { stackState.Prefab = ShopRules.Normalize(((Object)item.m_dropPrefab).name); } return stackState; } internal static int PrefabMax(string prefabName) { if ((Object)(object)ObjectDB.instance == (Object)null || string.IsNullOrEmpty(prefabName)) { return 999; } GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(prefabName); ItemDrop val = (((Object)(object)itemPrefab != (Object)null) ? itemPrefab.GetComponent<ItemDrop>() : null); if ((Object)(object)val == (Object)null || val.m_itemData == null || val.m_itemData.m_shared == null) { return 999; } return (val.m_itemData.m_shared.m_maxStackSize > 0) ? val.m_itemData.m_shared.m_maxStackSize : 999; } internal static bool CanAccept(Inventory inventory, ItemData item, int stack) { Container val = ShopLink.FindChest(inventory); if ((Object)(object)val == (Object)null || item == null) { return false; } StackState stackState = FromItem(item); if (stack > 0) { stackState.Amount = stack; } return ShopRules.FindAutoSlot(ReadChest(inventory), stackState, Withdraw(val)) >= 0; } internal static bool CanAcceptPrefab(Inventory inventory, GameObject prefab, int stack) { ItemDrop val = (((Object)(object)prefab != (Object)null) ? prefab.GetComponent<ItemDrop>() : null); if ((Object)(object)val == (Object)null) { return false; } return CanAccept(inventory, val.m_itemData, stack); } internal static bool TryRedirect(Inventory inventory, ItemData item, ref bool result) { Container val = ShopLink.FindChest(inventory); if ((Object)(object)val == (Object)null) { return false; } result = false; if (item == null || item.m_shared == null) { return true; } StackState[] slots = ReadChest(inventory); int num = ShopRules.FindAutoSlot(slots, FromItem(item), Withdraw(val)); if (num < 0) { return true; } int width = inventory.GetWidth(); if (width <= 0) { return true; } int x = num % width; int y = num / width; int num2 = StackAt(inventory, x, y); result = MoveInto(inventory, item, x, y, item.m_stack); if (StackAt(inventory, x, y) > num2) { Touch(inventory, num, num2); } else { Changed(inventory); } return true; } internal static int StackAt(Inventory inventory, int x, int y) { if (inventory == null) { return 0; } return inventory.GetItemAt(x, y)?.m_stack ?? 0; } internal static void Touch(Inventory inventory, int index, int previous) { if (ShopState.RunningTrade || inventory == null) { return; } Container val = ShopLink.FindChest(inventory); if (!((Object)(object)val == (Object)null)) { ShopState.OnInventoryChanged(val); int width = inventory.GetWidth(); if (index >= 0 && width > 0 && StackAt(inventory, index % width, index / width) > previous) { Announce(Player.m_localPlayer, inventory, index); } } } internal static void Changed(Inventory inventory) { Touch(inventory, -1, 0); } internal static bool Execute(Container chest, Player player, TradePlan plan) { if ((Object)(object)chest == (Object)null || (Object)(object)player == (Object)null || plan == null || plan.Result != TradeResult.Done) { return false; } Inventory inventory = chest.GetInventory(); Inventory inventory2 = ((Humanoid)player).GetInventory(); if (inventory == null || inventory2 == null || !Ready(chest, plan)) { return false; } ItemData[] array = inventory2.GetAllItems().ToArray(); for (int i = 0; i < plan.PlayerRemovals.Length; i++) { Removal removal = plan.PlayerRemovals[i]; if (removal.Index < 0 || removal.Index >= array.Length || array[removal.Index] == null) { return false; } } ShopState.RunningTrade = true; try { for (int j = 0; j < plan.PlayerRemovals.Length; j++) { Removal removal2 = plan.PlayerRemovals[j]; inventory2.RemoveItem(array[removal2.Index], removal2.Amount); } if (!Give(chest, plan)) { return false; } int width = inventory.GetWidth(); if (width <= 0) { return false; } for (int k = 0; k < plan.ChestRemovals.Length; k++) { Removal removal3 = plan.ChestRemovals[k]; ItemData itemAt = inventory.GetItemAt(removal3.Index % width, removal3.Index / width); if (itemAt == null) { return false; } inventory.RemoveItem(itemAt, removal3.Amount); } Drop(chest, plan); Save(chest); return true; } finally { ShopState.RunningTrade = false; } } internal static void RepairPrefabs(Container chest) { if ((Object)(object)chest == (Object)null || (Object)(object)ObjectDB.instance == (Object)null) { return; } Inventory inventory = chest.GetInventory(); if (inventory == null) { return; } List<ItemData> allItems = inventory.GetAllItems(); if (allItems == null) { return; } bool flag = false; for (int i = 0; i < allItems.Count; i++) { ItemData val = allItems[i]; if (val != null && !((Object)(object)val.m_dropPrefab != (Object)null) && val.m_shared != null) { GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(val.m_shared); if (!((Object)(object)itemPrefab == (Object)null)) { val.m_dropPrefab = itemPrefab; flag = true; } } } if (flag) { Save(chest); } } private static bool Withdraw(Container chest) { return ShopRules.WithdrawOnly(ModConfig.Enable, hasSign: true, ReadChest(chest.GetInventory())); } private static bool MoveInto(Inventory inventory, ItemData item, int x, int y, int amount) { if (ValheimMembers.InventoryAddAt == null || amount <= 0 || inventory == null) { return false; } int num = Room(inventory, x, y, item); int num2 = ((amount < num) ? amount : num); if (num2 <= 0) { return false; } object obj = ValheimMembers.InventoryAddAt.Invoke(inventory, new object[5] { item, num2, x, y, false }); return obj is bool && (bool)obj && item.m_stack <= 0; } private static int Room(Inventory inventory, int x, int y, ItemData incoming) { ItemData itemAt = inventory.GetItemAt(x, y); int num = ((incoming.m_shared == null || incoming.m_shared.m_maxStackSize <= 0) ? 1 : incoming.m_shared.m_maxStackSize); if (itemAt == null) { return num; } int num2 = ((itemAt.m_shared != null && itemAt.m_shared.m_maxStackSize > 0) ? itemAt.m_shared.m_maxStackSize : num); int num3 = num2 - itemAt.m_stack; return (num3 > 0) ? num3 : 0; } private static void Announce(Player player, Inventory inventory, int index) { if ((Object)(object)player == (Object)null || ShopState.RunningTrade || inventory == null || (index != 0 && index != 1)) { return; } int width = inventory.GetWidth(); if (width <= 0) { return; } ItemData itemAt = inventory.GetItemAt(index % width, index / width); if (itemAt != null) { bool flag = ShopRules.Normalize(((Object)(object)itemAt.m_dropPrefab != (Object)null) ? ((Object)itemAt.m_dropPrefab).name : "") == "Coins"; string item = ShopMessages.ItemName(itemAt); string currency = ShopMessages.CoinName(); if (index == 0 && !flag) { ShopMessages.Show(player, "$ptc_4", itemAt.m_stack, -1, item, null, null); } else if (index == 0) { ShopMessages.Show(player, "$ptc_6", itemAt.m_stack, -1, null, currency, null); } else if (flag) { ShopMessages.Show(player, "$ptc_5", itemAt.m_stack, -1, null, currency, null); } else { ShopMessages.Show(player, "$ptc_7", itemAt.m_stack, -1, item, null, null); } } } internal static void Spill(Container chest) { if ((Object)(object)chest == (Object)null) { return; } Inventory inventory = chest.GetInventory(); if (inventory == null) { return; } StackState[] array = ReadChest(inventory); int width = inventory.GetWidth(); if (width <= 0) { return; } bool flag = false; for (int i = 2; i < array.Length; i++) { if (!ShopRules.MiddleBelongs(array, i)) { ItemData itemAt = inventory.GetItemAt(i % width, i / width); if (itemAt != null) { DropItem(((Component)chest).transform, itemAt.Clone(), 0.15f * (float)(i - 2)); inventory.RemoveItem(itemAt, itemAt.m_stack); flag = true; } } } if (flag) { Save(chest); } } private static void Save(Container chest) { if ((Object)(object)chest != (Object)null && ValheimMembers.ContainerSave != null) { ValheimMembers.ContainerSave.Invoke(chest, null); } } private static bool Ready(Container chest, TradePlan plan) { if (plan.Payouts == null || plan.Payouts.Length == 0) { return false; } if (string.IsNullOrEmpty(plan.DropPrefab)) { return false; } if ((Object)(object)ObjectDB.instance == (Object)null || (Object)(object)ObjectDB.instance.GetItemPrefab(plan.DropPrefab) == (Object)null) { return false; } bool flag = plan.Placements != null && plan.Placements.Length != 0; if (flag && (string.IsNullOrEmpty(plan.ReceivePrefab) || (Object)(object)ObjectDB.instance.GetItemPrefab(plan.ReceivePrefab) == (Object)null)) { return false; } Inventory inventory = chest.GetInventory(); if (inventory == null) { return false; } int width = inventory.GetWidth(); if (width <= 0) { return false; } if (!flag) { return true; } StackState[] array = ReadChest(inventory); for (int i = 0; i < plan.Placements.Length; i++) { Placement placement = plan.Placements[i]; if (placement.Slot < 2 || placement.Slot >= array.Length || placement.Amount <= 0) { return false; } ItemData itemAt = inventory.GetItemAt(placement.Slot % width, placement.Slot / width); if (placement.StackOnExisting) { if (itemAt == null || itemAt.m_shared == null) { return false; } if (itemAt.m_stack + placement.Amount > itemAt.m_shared.m_maxStackSize) { return false; } } else if (itemAt != null || placement.Amount > PrefabMax(plan.ReceivePrefab)) { return false; } } return true; } private static bool Give(Container chest, TradePlan plan) { if (plan.Placements == null || plan.Placements.Length == 0) { return true; } GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(plan.ReceivePrefab); ItemDrop val = (((Object)(object)itemPrefab != (Object)null) ? itemPrefab.GetComponent<ItemDrop>() : null); Inventory inventory = chest.GetInventory(); if ((Object)(object)val == (Object)null || val.m_itemData == null || inventory == null || ValheimMembers.InventoryAddAt == null) { return false; } int width = inventory.GetWidth(); if (width <= 0) { return false; } for (int i = 0; i < plan.Placements.Length; i++) { Placement placement = plan.Placements[i]; int num = placement.Slot % width; int num2 = placement.Slot / width; ItemData itemAt = inventory.GetItemAt(num, num2); ItemData val2 = val.m_itemData.Clone(); val2.m_dropPrefab = itemPrefab; val2.m_stack = placement.Amount; val2.m_quality = plan.ReceiveQuality; val2.m_equipped = false; float maxDurability = val2.GetMaxDurability(); val2.m_durability = ((placement.StackOnExisting && itemAt != null) ? itemAt.m_durability : (maxDurability * placement.Durability)); object obj = ValheimMembers.InventoryAddAt.Invoke(inventory, new object[5] { val2, placement.Amount, num, num2, false }); if (!(obj is bool) || !(bool)obj) { return false; } ItemData itemAt2 = inventory.GetItemAt(num, num2); if (itemAt2 != null && (Object)(object)itemAt2.m_dropPrefab == (Object)null) { itemAt2.m_dropPrefab = itemPrefab; } } return true; } private static void Drop(Container chest, TradePlan plan) { GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(plan.DropPrefab); ItemDrop val = (((Object)(object)itemPrefab != (Object)null) ? itemPrefab.GetComponent<ItemDrop>() : null); if ((Object)(object)val == (Object)null || val.m_itemData == null || (Object)(object)chest == (Object)null) { return; } Sign val2 = ShopLink.SignOf(((Component)chest).gameObject); Transform origin = (((Object)(object)val2 != (Object)null) ? ((Component)val2).transform : ((Component)chest).transform); int num = 0; for (int i = 0; i < plan.Payouts.Length; i++) { Payout payout = plan.Payouts[i]; if (payout.Amount > 0) { Spawn(origin, itemPrefab, val, payout.Amount, plan.DropQuality, payout.Durability, num); num++; } } } private static void Spawn(Transform origin, GameObject prefab, ItemDrop drop, int amount, int quality, float durability, int index) { //IL_0073: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_008d: Unknown result type (might be due to invalid IL or missing references) //IL_0092: Unknown result type (might be due to invalid IL or missing references) //IL_0097: Unknown result type (might be due to invalid IL or missing references) //IL_00a1: 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_00ab: Unknown result type (might be due to invalid IL or missing references) //IL_00ae: Unknown result type (might be due to invalid IL or missing references) //IL_00af: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)origin == (Object)null || (Object)(object)drop == (Object)null || drop.m_itemData == null || amount <= 0) { return; } ItemData val = drop.m_itemData.Clone(); val.m_dropPrefab = prefab; val.m_stack = amount; val.m_quality = quality; val.m_durability = val.GetMaxDurability() * durability; val.m_equipped = false; val.m_worldLevel = (byte)Game.m_worldLevel; Vector3 val2 = origin.position + origin.forward * (1.1f + 0.15f * (float)index) + Vector3.up * 0.25f; ItemDrop val3 = ItemDrop.DropItem(val, amount, val2, Quaternion.identity); if (!((Object)(object)val3 == (Object)null) && val3.m_itemData != null) { val3.m_itemData.m_dropPrefab = prefab; val3.m_itemData.m_stack = amount; val3.m_itemData.m_quality = quality; val3.m_itemData.m_durability = val3.m_itemData.GetMaxDurability() * durability; val3.m_itemData.m_worldLevel = val.m_worldLevel; if (ValheimMembers.ItemDropSave != null) { ValheimMembers.ItemDropSave.Invoke(val3, null); } } } private static void DropItem(Transform origin, ItemData data, float extra) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Unknown result type (might be due to invalid IL or missing references) //IL_0048: Unknown result type (might be due to invalid IL or missing references) //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Unknown result type (might be due to invalid IL or missing references) //IL_0056: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)origin == (Object)null || data == null) { return; } int stack = data.m_stack; Vector3 val = origin.position + origin.forward * (1.1f + extra) + Vector3.up * 0.25f; ItemDrop val2 = ItemDrop.DropItem(data, stack, val, Quaternion.identity); if (!((Object)(object)val2 == (Object)null) && val2.m_itemData != null) { val2.m_itemData.m_stack = stack; val2.m_itemData.m_quality = data.m_quality; val2.m_itemData.m_durability = data.m_durability; if (ValheimMembers.ItemDropSave != null) { ValheimMembers.ItemDropSave.Invoke(val2, null); } } } } internal static class ShopLink { private const float PairDistance = 2.5f; private static readonly Dictionary<long, Container> Chests = new Dictionary<long, Container>(); private static readonly Dictionary<long, Sign> Signs = new Dictionary<long, Sign>(); private static readonly Dictionary<Inventory, Container> ByInventory = new Dictionary<Inventory, Container>(); internal static void Register(GameObject gameObject) { if ((Object)(object)gameObject == (Object)null) { return; } ZDO val = ReadZdo(gameObject); if (val == null) { return; } long num = val.GetLong("ptc_link", 0L); if (num == 0) { return; } Container component = gameObject.GetComponent<Container>(); Sign component2 = gameObject.GetComponent<Sign>(); if ((Object)(object)component != (Object)null) { Chests[num] = component; Inventory inventory = component.GetInventory(); if (inventory != null) { ByInventory[inventory] = component; } } if ((Object)(object)component2 != (Object)null) { Signs[num] = component2; } ShopState.Reinforce(gameObject); ParentIfLoose(num); } internal static Container FindChest(Inventory inventory) { if (inventory == null) { return null; } Container value; return ByInventory.TryGetValue(inventory, out value) ? value : null; } internal static bool IsLinked(GameObject gameObject) { return LinkId(gameObject) != 0; } internal static long LinkId(GameObject gameObject) { ZDO val = ReadZdo(gameObject); return (val == null) ? 0 : val.GetLong("ptc_link", 0L); } internal static bool HasSign(Container chest) { long num = LinkId(((Object)(object)chest != (Object)null) ? ((Component)chest).gameObject : null); if (num == 0) { return false; } Sign value; return Signs.TryGetValue(num, out value) && (Object)(object)value != (Object)null; } internal static Container ChestOf(GameObject gameObject) { Container val = (((Object)(object)gameObject != (Object)null) ? gameObject.GetComponent<Container>() : null); if ((Object)(object)val != (Object)null && IsLinked(gameObject)) { return val; } long num = LinkId(gameObject); if (num != 0L && Chests.TryGetValue(num, out var value) && (Object)(object)value != (Object)null) { return value; } return null; } internal static Sign SignOf(GameObject gameObject) { Sign val = (((Object)(object)gameObject != (Object)null) ? gameObject.GetComponent<Sign>() : null); if ((Object)(object)val != (Object)null && IsLinked(gameObject)) { return val; } long num = LinkId(gameObject); if (num != 0L && Signs.TryGetValue(num, out var value) && (Object)(object)value != (Object)null) { return value; } return null; } internal static GameObject Partner(GameObject gameObject) { long num = LinkId(gameObject); if (num == 0) { return null; } Sign value; if ((Object)(object)gameObject.GetComponent<Container>() != (Object)null) { return (Signs.TryGetValue(num, out value) && (Object)(object)value != (Object)null) ? ((Component)value).gameObject : null; } Container value2; return (Chests.TryGetValue(num, out value2) && (Object)(object)value2 != (Object)null) ? ((Component)value2).gameObject : null; } internal static void Bind(Container chest, Sign sign, int face, long deadline) { ZDO val = ReadZdo(((Component)chest).gameObject); ZDO val2 = ReadZdo(((Component)sign).gameObject); if (val != null && val2 != null) { long num = NewLink(); val.Set("ptc_link", num); val2.Set("ptc_link", num); val2.Set("ptc_face", face); val.Set("ptc_deadline", deadline); val2.Set("ptc_deadline", deadline); val.Set("ptc_committed", false); val2.Set("ptc_committed", false); Register(((Component)chest).gameObject); Register(((Component)sign).gameObject); } } internal static void PairByPosition(GameObject gameObject) { //IL_0038: 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_0110: Unknown result type (might be due to invalid IL or missing references) long num = LinkId(gameObject); if (num == 0L || (Object)(object)Partner(gameObject) != (Object)null) { return; } bool flag = (Object)(object)gameObject.GetComponent<Container>() == (Object)null; Collider[] array = Physics.OverlapSphere(gameObject.transform.position, 2.5f); Component val = null; float num2 = 2.5f; for (int i = 0; i < array.Length; i++) { if ((Object)(object)array[i] == (Object)null) { continue; } Component val2 = (Component)(flag ? ((object)((Component)array[i]).GetComponentInParent<Container>()) : ((object)((Component)array[i]).GetComponentInParent<Sign>())); if ((Object)(object)val2 == (Object)null || (Object)(object)val2.gameObject == (Object)(object)gameObject) { continue; } long num3 = LinkId(val2.gameObject); if ((num3 == 0L || num3 == num) && (!flag || ShopRules.Listed(ShopRules.Normalize(((Object)val2.gameObject).name), ModConfig.AllowedChests()))) { float num4 = Vector3.Distance(val2.transform.position, gameObject.transform.position); if (!(num4 >= num2)) { num2 = num4; val = val2; } } } if (!((Object)(object)val == (Object)null)) { ZDO val3 = ReadZdo(val.gameObject); if (val3 != null) { val3.Set("ptc_link", num); Register(val.gameObject); } } } internal static void ForEachSign(Action<Sign> action) { if (action == null) { return; } List<long> list = new List<long>(Signs.Keys); for (int i = 0; i < list.Count; i++) { if (Signs.TryGetValue(list[i], out var value) && (Object)(object)value != (Object)null) { action(value); } } } internal static void Unlink(Container chest) { if (!((Object)(object)chest == (Object)null)) { long num = LinkId(((Component)chest).gameObject); Sign value = null; if (num != 0) { Signs.TryGetValue(num, out value); } ClearShop(ReadZdo(((Component)chest).gameObject)); if ((Object)(object)value != (Object)null) { ClearShop(ReadZdo(((Component)value).gameObject)); } Inventory inventory = chest.GetInventory(); if (inventory != null) { ByInventory.Remove(inventory); } if (num != 0) { Chests.Remove(num); Signs.Remove(num); } } } private static void ClearShop(ZDO zdo) { if (zdo != null) { zdo.Set("ptc_link", 0L); zdo.Set("ptc_deadline", 0L); zdo.Set("ptc_frozen", false); zdo.Set("ptc_remaining", 0L); zdo.Set("ptc_committed", false); zdo.Set("ptc_inuse", false); } } internal static ZDO ReadZdo(GameObject gameObject) { if ((Object)(object)gameObject == (Object)null) { return null; } ZNetView component = gameObject.GetComponent<ZNetView>(); if ((Object)(object)component == (Object)null || !component.IsValid()) { return null; } return component.GetZDO(); } private static void ParentIfLoose(long link) { if (Chests.TryGetValue(link, out var value) && !((Object)(object)value == (Object)null) && Signs.TryGetValue(link, out var value2) && !((Object)(object)value2 == (Object)null) && !((Object)(object)((Component)value2).transform.parent == (Object)(object)((Component)value).transform)) { Parent(link); } } private static void Parent(long link) { //IL_0095: Unknown result type (might be due to invalid IL or missing references) //IL_0097: Unknown result type (might be due to invalid IL or missing references) //IL_00aa: Unknown result type (might be due to invalid IL or missing references) if (Chests.TryGetValue(link, out var value) && !((Object)(object)value == (Object)null) && Signs.TryGetValue(link, out var value2) && !((Object)(object)value2 == (Object)null)) { ZDO val = ReadZdo(((Component)value2).gameObject); int face = ((val != null) ? val.GetInt("ptc_face", 0) : 0); ShopPose.Place(((Component)value).transform, ((Component)value2).transform, face, out var position, out var rotation); ((Component)value2).transform.SetParent(((Component)value).transform, true); ((Component)value2).transform.SetPositionAndRotation(position, rotation); if (val != null) { val.SetPosition(position); } } } private static long NewLink() { long num; do { num = ((long)Random.Range(1, int.MaxValue) << 32) | (uint)Random.Range(1, int.MaxValue); } while (num == 0L || Chests.ContainsKey(num) || Signs.ContainsKey(num)); return num; } } internal static class ShopLog { internal static void Write(Player player, Container chest, Offer offer, TradeResult result, bool succeeded, bool moveFailed = false) { if (!ModConfig.VerboseLogs) { return; } try { string item = (offer.Valid ? EnglishItems.Name(offer.ItemPrefab) : ""); string text = TradeLog.Line(CharacterName(player), offer.Selling, succeeded, result, offer.ItemAmount, item, offer.CoinAmount, offer.Valid, moveFailed); string text2 = Describe(chest, offer, item); if (BepinexPlugin.Log != null) { BepinexPlugin.Log.LogInfo((object)text); BepinexPlugin.Log.LogInfo((object)text2); } } catch (Exception ex) { if (BepinexPlugin.Log != null) { BepinexPlugin.Log.LogWarning((object)("Could not write the shop trade log. " + ex.Message)); } } } private static string Describe(Container chest, Offer offer, string item) { Inventory val = (((Object)(object)chest != (Object)null) ? chest.GetInventory() : null); TradeLog.LogSlot[] slots = Slots(val); int gridWidth = ((val != null) ? val.GetWidth() : 0); int gridHeight = ((val != null) ? val.GetHeight() : 0); int stockItem = -1; int stockCoins = -1; if (offer.Valid && val != null) { StackState[] slots2 = ShopInventory.ReadChest(val); stockItem = ShopRules.MiddleAmount(slots2, offer.ItemPrefab, offer.ItemQuality, coins: false); stockCoins = ShopRules.MiddleAmount(slots2, "Coins", 0, coins: true); } return TradeLog.Contents(offer.Selling, item, offer.CoinAmount, offer.Valid, slots, stockItem, stockCoins, gridWidth, gridHeight); } private static TradeLog.LogSlot[] Slots(Inventory inventory) { if (inventory == null) { return new TradeLog.LogSlot[0]; } int width = inventory.GetWidth(); int height = inventory.GetHeight(); List<ItemData> list = new List<ItemData>(); List<TradeLog.LogSlot> list2 = new List<TradeLog.LogSlot>(); if (width > 0 && height > 0) { for (int i = 0; i < height; i++) { for (int j = 0; j < width; j++) { ItemData itemAt = inventory.GetItemAt(j, i); if (itemAt != null && itemAt.m_stack > 0) { list.Add(itemAt); list2.Add(Make(itemAt, i * width + j, hidden: false)); } } } } List<ItemData> allItems = inventory.GetAllItems(); if (allItems != null) { for (int k = 0; k < allItems.Count; k++) { ItemData val = allItems[k]; if (val != null && val.m_stack > 0 && !Contains(list, val)) { list2.Add(Make(val, -1, hidden: true)); } } } Sort(list2); return list2.ToArray(); } private static TradeLog.LogSlot Make(ItemData item, int slot, bool hidden) { bool missingPrefab; string name = Label(item, out missingPrefab); string note = NoteFor(item, missingPrefab); if (hidden) { note = AppendNote(note, "not-on-grid"); } return new TradeLog.LogSlot(slot, item.m_stack, name, note); } private static bool Contains(List<ItemData> items, ItemData item) { for (int i = 0; i < items.Count; i++) { if (items[i] == item) { return true; } } return false; } private static string Label(ItemData item, out bool missingPrefab) { string text = (((Object)(object)item.m_dropPrefab != (Object)null) ? ShopRules.Normalize(((Object)item.m_dropPrefab).name) : ""); missingPrefab = text.Length == 0; if (!missingPrefab) { return EnglishItems.Name(text); } string token = ((item.m_shared != null) ? item.m_shared.m_name : ""); string text2 = EnglishItems.FromToken(token); return (text2.Length > 0) ? text2 : "item"; } private static string NoteFor(ItemData item, bool missingPrefab) { string text = ""; if (missingPrefab) { text = AppendNote(text, "no-prefab"); } if (item.m_quality > 1) { text = AppendNote(text, "q" + item.m_quality.ToString(CultureInfo.InvariantCulture)); } float maxDurability = item.GetMaxDurability(); if (maxDurability > 0.001f) { float durabilityPercentage = item.GetDurabilityPercentage(); if (durabilityPercentage + 0.0005f < 0.95f) { text = AppendNote(text, ((int)(durabilityPercentage * 100f + 0.5f)).ToString(CultureInfo.InvariantCulture) + "%"); } } if (item.m_worldLevel != 0) { text = AppendNote(text, "world " + item.m_worldLevel.ToString(CultureInfo.InvariantCulture)); } return text; } private static string AppendNote(string note, string part) { if (note.Length == 0) { return part; } return note + " " + part; } private static void Sort(List<TradeLog.LogSlot> slots) { for (int i = 1; i < slots.Count; i++) { TradeLog.LogSlot logSlot = slots[i]; int num = i; while (num > 0 && Order(slots[num - 1]) > Order(logSlot)) { slots[num] = slots[num - 1]; num--; } slots[num] = logSlot; } } private static int Order(TradeLog.LogSlot slot) { return (slot.Slot < 0) ? int.MaxValue : slot.Slot; } internal static Offer Peek(Container chest) { if ((Object)(object)chest == (Object)null) { return default(Offer); } Inventory inventory = chest.GetInventory(); if (inventory == null) { return default(Offer); } return ShopRules.ReadOffer(ShopInventory.ReadChest(inventory)); } private static string CharacterName(Player player) { if ((Object)(object)player == (Object)null) { return ""; } return player.GetPlayerName(); } } internal static class ShopMessages { internal static void Show(Player player, string token) { Show(player, token, -1, -1, null, null, null); } internal static void Show(Player player, string token, int firstAmount, int secondAmount, string item, string currency, string valuable) { if (!((Object)(object)player == (Object)null) && Localization.instance != null && !string.IsNullOrEmpty(token) && !((Object)(object)player != (Object)(object)Player.m_localPlayer)) { string template = Localization.instance.Localize(token); string text = SignLine.Fill(template, firstAmount, secondAmount, item, currency, valuable); Notice.Show(text); } } internal static string ItemName(ItemData item) { if (item == null || item.m_shared == null || Localization.instance == null) { return ""; } return Localization.instance.Localize(item.m_shared.m_name); } internal static string CoinName() { if (Localization.instance == null) { return "Coins"; } return Localization.instance.Localize("$item_coins"); } internal static string PrefabName(string prefab) { if (Localization.instance == null || (Object)(object)ObjectDB.instance == (Object)null || string.IsNullOrEmpty(prefab)) { return prefab ?? ""; } GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(prefab); ItemDrop val = (((Object)(object)itemPrefab != (Object)null) ? itemPrefab.GetComponent<ItemDrop>() : null); if ((Object)(object)val == (Object)null || val.m_itemData == null) { return prefab; } return ItemName(val.m_itemData); } } internal static class ShopPlacement { internal static bool TryHandle(Player player, Piece piece, ref bool result) { //IL_009a: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)player == (Object)null || (Object)(object)piece == (Object)null) { return true; } if (ShopRules.Normalize(((Object)((Component)piece).gameObject).name) != "sign") { return true; } if (!TryHitChest(player, out var chest, out var hit)) { return true; } string text = Refusal(player, chest); if (text != null) { ManualLogSource log = BepinexPlugin.Log; if (log != null) { log.LogInfo((object)("Shop sign was not attached: " + text)); } result = false; return false; } result = Attach(player, piece, chest, ((RaycastHit)(ref hit)).point); return false; } private static bool TryHitChest(Player player, out Container chest, out RaycastHit hit) { //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_007b: Unknown result type (might be due to invalid IL or missing references) //IL_0073: 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_008b: 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_00b9: Unknown result type (might be due to invalid IL or missing references) //IL_00bb: Unknown result type (might be due to invalid IL or missing references) chest = null; hit = default(RaycastHit); if ((Object)(object)GameCamera.instance == (Object)null || ValheimMembers.PlaceRayMask == null) { return false; } int num = (int)ValheimMembers.PlaceRayMask.GetValue(player); Transform val = (Transform)((ValheimMembers.Eye != null) ? /*isinst with value type is only supported in some contexts*/: null); Vector3 val2 = (((Object)(object)val != (Object)null) ? val.position : ((Component)player).transform.position); if (!Physics.Raycast(((Component)GameCamera.instance).transform.position, ((Component)GameCamera.instance).transform.forward, ref hit, 50f, num)) { return false; } if (Vector3.Distance(val2, ((RaycastHit)(ref hit)).point) >= player.m_maxPlaceDistance || (Object)(object)((RaycastHit)(ref hit)).collider == (Object)null) { return false; } chest = ((Component)((RaycastHit)(ref hit)).collider).GetComponentInParent<Container>(); if ((Object)(object)chest == (Object)null) { return false; } return ShopRules.Listed(((Object)((Component)chest).gameObject).name, ModConfig.AllowedChests()); } private static string Refusal(Player player, Container chest) { if (!ModConfig.Enable) { return "new shops are disabled"; } if (ShopLink.LinkId(((Component)chest).gameObject) != 0) { return "this chest already has a sign"; } Piece component = ((Component)chest).GetComponent<Piece>(); if ((Object)(object)component == (Object)null || component.GetCreator() != player.GetPlayerID()) { return "only the player who built the chest can attach a sign"; } if (ValheimMembers.ContainerLoad != null) { ValheimMembers.ContainerLoad.Invoke(chest, null); } if (!ShopRules.IsEmpty(ShopInventory.ReadChest(chest.GetInventory()))) { return "the chest is not empty"; } ZNetView component2 = ((Component)chest).GetComponent<ZNetView>(); if ((Object)(object)component2 == (Object)null || !component2.IsValid()) { return "the chest is not ready"; } return null; } private static bool Attach(Player player, Piece piece, Container chest, Vector3 point) { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_008e: Unknown result type (might be due to invalid IL or missing references) //IL_0192: Unknown result type (might be due to invalid IL or missing references) //IL_0193: Unknown result type (might be due to invalid IL or missing references) //IL_01a1: Unknown result type (might be due to invalid IL or missing references) int face = ShopPose.FaceFrom(((Component)chest).transform, point); ShopPose.World(((Component)chest).transform, face, out var position, out var rotation); GameObject val = Object.Instantiate<GameObject>(((Component)piece).gameObject, position, rotation); Sign component = val.GetComponent<Sign>(); Piece component2 = val.GetComponent<Piece>(); ZNetView component3 = val.GetComponent<ZNetView>(); if ((Object)(object)component == (Object)null || (Object)(object)component2 == (Object)null || (Object)(object)component3 == (Object)null || !component3.IsValid()) { Discard(val); return false; } component2.SetCreator(player.GetPlayerID(), LocalUser()); WearNTear component4 = val.GetComponent<WearNTear>(); if ((Object)(object)component4 != (Object)null) { component4.OnPlaced(); } long deadline = DateTime.UtcNow.Ticks + TimeSpan.FromSeconds(10.0).Ticks; GameObject gameObject = ((Component)chest).gameObject; ShopLink.Bind(chest, component, face, deadline); if (ShopLink.LinkId(val) == 0) { Discard(val); return false; } if (player.PlacementCostDisabled) { ZDO val2 = ShopLink.ReadZdo(val); if (val2 != null) { val2.Set(ZDOVars.s_cheated, true); } } if ((Object)(object)val.GetComponent<ShopWatch>() == (Object)null) { val.AddComponent<ShopWatch>(); } if ((Object)(object)gameObject.GetComponent<ShopWatch>() == (Object)null) { gameObject.AddComponent<ShopWatch>(); } ShopSign.ShowCount(chest); if (piece.m_placeEffect != null) { piece.m_placeEffect.Create(position, rotation, val.transform, 1f, -1, ((Character)player).GetZDOID()); } ManualLogSource log = BepinexPlugin.Log; if (log != null) { log.LogInfo((object)"Attached a shop sign."); } return true; } private static void Discard(GameObject gameObject) { if (!((Object)(object)gameObject == (Object)null)) { if ((Object)(object)ZNetScene.instance != (Object)null) { ZNetScene.instance.Destroy(gameObject); } else { Object.Destroy((Object)(object)gameObject); } } } private static PlatformUserID LocalUser() { //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_003a: Unknown result type (might be due to invalid IL or missing references) if (PlatformManager.DistributionPlatform == null || PlatformManager.DistributionPlatform.LocalUser == null) { return default(PlatformUserID); } return ((IUser)PlatformManager.DistributionPlatform.LocalUser).PlatformUserID; } } internal static class ShopPose { internal static int FaceFrom(Transform chest, Vector3 point) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0003: Unknown result type (might be due to invalid IL or missing references) //IL_0008: Unknown result type (might be due to invalid IL or missing references) //IL_0009: 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_0039: 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) Vector3 val = chest.InverseTransformPoint(point); if (Mathf.Abs(val.x) > Mathf.Abs(val.z)) { return (val.x >= 0f) ? 2 : 3; } return (!(val.z >= 0f)) ? 1 : 0; } internal static void World(Transform chest, int face, out Vector3 position, out Quaternion rotation) { Place(chest, null, face, out position, out rotation); } internal static void Place(Transform chest, Transform sign, int face, out Vector3 position, out Quaternion rotation) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0009: Unknown result type (might be due to invalid IL or missing references) //IL_000a: Unknown result type (might be due to invalid IL or missing references) //IL_000f: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Unknown result type (might be due to invalid IL or missing references) //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) //IL_003c: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Unknown result type (might be due to invalid IL or missing references) //IL_0047: 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_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0057: Unknown result type (might be due to invalid IL or missing references) //IL_0058: Unknown result type (might be due to invalid IL or missing references) //IL_005d: Unknown result type (might be due to invalid IL or missing references) //IL_0062: Unknown result type (might be due to invalid IL or missing references) //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_00cc: Unknown result type (might be due to invalid IL or missing references) //IL_00cd: Unknown result type (might be due to invalid IL or missing references) //IL_00d3: Unknown result type (might be due to invalid IL or missing references) //IL_00d8: Unknown result type (might be due to invalid IL or missing references) //IL_00dd: Unknown result type (might be due to invalid IL or missing references) //IL_0087: Unknown result type (might be due to invalid IL or missing references) //IL_0093: Unknown result type (might be due to invalid IL or missing references) //IL_0094: Unknown result type (might be due to invalid IL or missing references) //IL_009d: Unknown result type (might be due to invalid IL or missing references) //IL_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00a7: Unknown result type (might be due to invalid IL or missing references) //IL_00aa: Unknown result type (might be due to invalid IL or missing references) //IL_00ae: Unknown result type (might be due to invalid IL or missing references) //IL_00b5: Unknown result type (might be due to invalid IL or missing references) //IL_00ba: Unknown result type (might be due to invalid IL or missing references) //IL_00bf: Unknown result type (might be due to invalid IL or missing references) //IL_00c4: Unknown result type (might be due to invalid IL or missing references) Vector3 val = Outward(face); Vector3 val2 = chest.TransformDirection(val); if (((Vector3)(ref val2)).sqrMagnitude < 0.0001f) { val2 = val; } ((Vector3)(ref val2)).Normalize(); rotation = Quaternion.LookRotation(val2, chest.up); Bounds val3 = ChestBounds(chest); Vector3 val4 = chest.TransformPoint(((Bounds)(ref val3)).center + Vector3.Scale(((Bounds)(ref val3)).extents, val)); if ((Object)(object)sign != (Object)null && TryBounds(sign, sign, skipSigns: false, out var bounds)) { float z = ((Bounds)(ref bounds)).extents.z; Vector3 val5 = val4 + val2 * (z + 0.03f); position = val5 - rotation * ((Bounds)(ref bounds)).center; } else { position = val4 + val2 * 0.05f; } } private static Bounds ChestBounds(Transform chest) { //IL_000f: Unknown result type (might be due to invalid IL or missing references) //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_0075: Unknown result type (might be due to invalid IL or missing references) //IL_0054: 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_006d: Unknown result type (might be due to invalid IL or missing references) //IL_0072: Unknown result type (might be due to invalid IL or missing references) //IL_003d: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Unknown result type (might be due to invalid IL or missing references) if (TryBounds(chest, chest, skipSigns: true, out var bounds)) { return bounds; } BoxCollider val = ((Component)chest).GetComponent<BoxCollider>(); if ((Object)(object)val == (Object)null) { val = ((Component)chest).GetComponentInChildren<BoxCollider>(); } if ((Object)(object)val != (Object)null) { return ColliderBounds(chest, val); } return new Bounds(new Vector3(0f, 0.5f, 0f), new Vector3(1.2f, 1f, 0.8f)); } private static Bounds ColliderBounds(Transform chest, BoxCollider box) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0009: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_001b: 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_00a4: Unknown result type (might be due to invalid IL or missing references) //IL_00a5: Unknown result type (might be due to invalid IL or missing references) //IL_0038: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Unknown result type (might be due to invalid IL or missing references) //IL_00a9: Unknown result type (might be due to invalid IL or missing references) //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0045: Unknown result type (might be due to invalid IL or missing references) //IL_0062: Unknown result type (might be due to invalid IL or missing references) //IL_005a: 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) //IL_0073: Unknown result type (might be due to invalid IL or missing references) //IL_007c: Unknown result type (might be due to invalid IL or missing references) //IL_007e: Unknown result type (might be due to invalid IL or missing references) //IL_0083: Unknown result type (might be due to invalid IL or missing references) Vector3 center = box.center; Vector3 val = box.size * 0.5f; Bounds bounds = default(Bounds); bool any = false; for (int i = 0; i < 8; i++) { Vector3 val2 = center + new Vector3(((i & 1) == 0) ? (0f - val.x) : val.x, ((i & 2) == 0) ? (0f - val.y) : val.y, ((i & 4) == 0) ? (0f - val.z) : val.z); Include(chest.InverseTransformPoint(((Component)box).transform.TransformPoint(val2)), ref bounds, ref any); } return bounds; } private static bool TryBounds(Transform space, Transform root, bool skipSigns, out Bounds bounds) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) //IL_0063: Unknown result type (might be due to invalid IL or missing references) //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_006c: 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_007d: Unknown result type (might be due to invalid IL or missing references) //IL_008e: 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_00a5: Unknown result type (might be due to invalid IL or missing references) //IL_009c: Unknown result type (might be due to invalid IL or missing references) //IL_00bc: 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_00c4: Unknown result type (might be due to invalid IL or missing references) //IL_00c9: Unknown result type (might be due to invalid IL or missing references) //IL_00ce: Unknown result type (might be due to invalid IL or missing references) //IL_00d7: Unknown result type (might be due to invalid IL or missing references) //IL_00d9: Unknown result type (might be due to invalid IL or missing references) //IL_00de: Unknown result type (might be due to invalid IL or missing references) bounds = default(Bounds); bool any = false; Renderer[] componentsInChildren = ((Component)root).GetComponentsInChildren<Renderer>(true); foreach (Renderer val in componentsInChildren) { if ((val is MeshRenderer || val is SkinnedMeshRenderer) && (!skipSigns || !((Object)(object)((Component)val).GetComponentInParent<Sign>() != (Object)null))) { Bounds localBounds = val.localBounds; Vector3 center = ((Bounds)(ref localBounds)).center; Vector3 extents = ((Bounds)(ref localBounds)).extents; for (int j = 0; j < 8; j++) { Vector3 val2 = center + new Vector3(((j & 1) == 0) ? (0f - extents.x) : extents.x, ((j & 2) == 0) ? (0f - extents.y) : extents.y, ((j & 4) == 0) ? (0f - extents.z) : extents.z); Include(space.InverseTransformPoint(((Component)val).transform.TransformPoint(val2)), ref bounds, ref any); } } } return any; } private static void Include(Vector3 point, ref Bounds bounds, ref bool any) { //IL_0022: 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_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) if (!any) { bounds = new Bounds(point, Vector3.zero); any = true; } else { ((Bounds)(ref bounds)).Encapsulate(point); } } private static Vector3 Outward(int face) { //IL_0009: Unknown result type (might be due to invalid IL or missing references) //IL_000e: 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_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Unknown result type (might be due to invalid IL or missing references) //IL_0031: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0029: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) return (Vector3)(face switch { 1 => Vector3.back, 2 => Vector3.right, 3 => Vector3.left, _ => Vector3.forward, }); } } internal static class ShopSign { private static readonly Dictionary<int, int> Shown = new Dictionary<int, int>(); internal static void ShowCount(Container chest) { if ((Object)(object)chest == (Object)null) { return; } Sign val = ShopLink.SignOf(((Component)chest).gameObject); if ((Object)(object)val == (Object)null) { return; } int num = ShopState.SecondsLeft(((Component)chest).gameObject); if (num >= 1) { int instanceID = ((Object)val).GetInstanceID(); if (!Shown.TryGetValue(instanceID, out var value) || value != num) { Shown[instanceID] = num; SignText.Present(val, ShopRules.CountdownText(num)); } } } internal static void Update(Container chest) { if ((Object)(object)chest == (Object)null) { return; } Sign val = ShopLink.SignOf(((Component)chest).gameObject); if ((Object)(object)val == (Object)null) { return; } if (ShopState.Counting(chest)) { ShowCount(chest); return; } Shown.Remove(((Object)val).GetInstanceID()); if (Localization.instance != null) { StackState[] slots = ShopInventory.ReadChest(chest.GetInventory()); bool withdrawOnly = ShopRules.WithdrawOnly(ModConfig.Enable, hasSign: true, slots); Offer offer = ShopRules.ReadOffer(slots); int num = ShopInventory.PrefabMax("Coins"); int itemMax = (offer.Valid ? ShopInventory.PrefabMax(offer.ItemPrefab) : num); bool covers = ShopRules.CoversTrade(slots, offer); bool hasSpace = offer.Valid && ShopRules.CanHoldDelivery(slots, offer, itemMax, num); bool endsEmpty = ShopRules.EndsEmpty(slots); SignKind signKind = ShopRules.ChooseSign(ShopState.Committed(((Component)chest).gameObject), withdrawOnly, offer, covers, hasSpace, endsEmpty); string text = ". . ."; if (signKind == SignKind.OutOfStock) { text = Localization.instance.Localize("$ptc_10"); } else if (signKind == SignKind.OutOfSpace) { text = Localization.instance.Localize("$ptc_20"); } else if (signKind == SignKind.Selling || signKind == SignKind.Buying) { text = SignLine.OfferLine(offer.Selling, offer.ItemAmount, ShopMessages.PrefabName(offer.ItemPrefab), offer.ItemQuality, ShowsQuality(offer.ItemPrefab, offer.ItemQuality), offer.CoinAmount); } SignText.Present(val, text); } } private static bool ShowsQuality(string prefab, int quality) { int num = 1; if ((Object)(object)ObjectDB.instance != (Object)null && !string.IsNullOrEmpty(prefab)) { GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(prefab); ItemDrop val = (((Object)(object)itemPrefab != (Object)null) ? itemPrefab.GetComponent<ItemDrop>() : null); if ((Object)(object)val != (Object)null && val.m_itemData != null && val.m_itemData.m_shared != null) { num = val.m_itemData.m_shared.m_maxQuality; } } return num > 1 || quality > 1; } internal static void RefreshAll() { ShopLink.ForEachSign(delegate(Sign sign) { Container val = ShopLink.ChestOf(((Component)sign).gameObject); if ((Object)(object)val != (Object)null) { Update(val); } }); } } internal static class ShopState { private static readonly HashSet<int> Scaled = new HashSet<int>(); internal static bool RunningTrade; internal static bool Committed(GameObject gameObject) { ZDO val = ShopLink.ReadZdo(gameObject); return val != null && val.GetBool("ptc_committed", false); } internal static bool InUse(Container chest) { if ((Object)(object)chest == (Object)null) { return false; } if (chest.IsInUse()) { return true; } ZDO val = ShopLink.ReadZdo(((Component)chest).gameObject); return val != null && val.GetBool("ptc_inuse", false); } internal static void Reinforce(GameObject gameObject) { WearNTear val = Wear(gameObject); ZDO val2 = ShopLink.ReadZdo(gameObject); if ((Object)(object)val == (Object)null || val2 == null || (Object)(object)gameObject == (Object)null) { return; } if ((Object)(object)gameObject.GetComponent<Sign>() != (Object)null) { val.m_noSupportWear = false; val.m_noRoofWear = false; } int instanceID = ((Object)gameObject).GetInstanceID(); if (!Scaled.Contains(instanceID)) { Scaled.Add(instanceID); val.m_health *= 10f; if (!val2.GetBool("ptc_scaled", false)) { val2.Set(ZDOVars.s_health, val.m_health); val2.Set("ptc_scaled", true); } } } private static WearNTear Wear(GameObject gameObject) { return ((Object)(object)gameObject != (Object)null) ? gameObject.GetComponent<WearNTear>() : null; } internal static void OnInventoryChanged(Container chest) { if (!((Object)(object)chest == (Object)null) && ShopLink.IsLinked(((Component)chest).gameObject)) { StackState[] slots = ShopInventory.ReadChest(chest.GetInventory()); if (ShopRules.ReadOffer(slots).Valid && !Committed(((Component)chest).gameObject)) { Commit(chest); } if (!InUse(chest) && !RunningTrade) { HoldClosed(chest, slots); ShopSign.Update(chest); } } } internal static void SetOpen(Container chest, bool open) { if ((Object)(object)chest == (Object)null || !ShopLink.IsLinked(((Component)chest).gameObject)) { return; } ZNetView component = ((Component)chest).GetComponent<ZNetView>(); if ((Object)(object)component == (Object)null || !component.IsValid() || !component.IsOwner()) { return; } ZDO zDO = component.GetZDO(); if (zDO != null) { zDO.Set("ptc_inuse", open); } if (open) { Stop(chest); return; } ShopInventory.RepairPrefabs(chest); ShopInventory.Spill(chest); StackState[] slots = ShopInventory.ReadChest(chest.GetInventory()); if (ShopRules.EndsEmpty(slots)) { Begin(chest); } else { Stop(chest); if (ShopRules.ReadOffer(slots).Valid && !Committed(((Component)chest).gameObject)) { Commit(chest); } } ShopSign.Update(chest); } internal static void Expire(ZNetView view) { if ((Object)(object)view == (Object)null || !view.IsValid() || !view.IsOwner() || !ShopLink.IsLinked(((Component)view).gameObject)) { return;
marchiori.utils.localization.dll
Decompiled 20 hours agousing System; using System.Collections.Generic; using System.Diagnostics; using System.Globalization; using System.IO; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Text; using HarmonyLib; using Microsoft.CodeAnalysis; [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.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")] [assembly: AssemblyCompany("marchiori.utils.localization")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+ee52b2bfcab53d7e96836822c3d6ec6f3c6f91ae")] [assembly: AssemblyProduct("marchiori.utils.localization")] [assembly: AssemblyTitle("marchiori.utils.localization")] [assembly: AssemblyVersion("1.0.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Marchiori.Utils.Localization { public static class LanguageFiles { private const string EnglishFile = "English.csv"; private static readonly MethodInfo AddWord = AccessTools.Method(typeof(Localization), "AddWord", (Type[])null, (Type[])null); public static void Apply(Localization localization, string language, string modDirectory, string tokenPrefix) { if (localization == null || AddWord == null || string.IsNullOrEmpty(modDirectory) || string.IsNullOrEmpty(tokenPrefix)) { return; } string text = Find(modDirectory, SafeFileName(language) + ".csv"); if (text == null) { text = Find(modDirectory, "English.csv"); } if (text == null) { return; } foreach (KeyValuePair<int, string> item in Read(text)) { AddWord.Invoke(localization, new object[2] { tokenPrefix + "_" + item.Key.ToString(CultureInfo.InvariantCulture), item.Value }); } } public static IEnumerable<KeyValuePair<int, string>> Read(string path) { string[] array = File.ReadAllLines(path, Encoding.UTF8); foreach (string raw in array) { string line = raw.Trim(); if (line.Length != 0 && line[0] != '#') { int split = line.IndexOf('='); if (split > 0 && int.TryParse(line.Substring(0, split).Trim(), NumberStyles.Integer, CultureInfo.InvariantCulture, out var id)) { yield return new KeyValuePair<int, string>(value: Unquote(line.Substring(split + 1).Trim()), key: id); } } } } private static string Unquote(string value) { if (value.Length >= 2 && value[0] == '"' && value[value.Length - 1] == '"') { return value.Substring(1, value.Length - 2).Replace("\"\"", "\""); } return value; } private static string Find(string root, string fileName) { if (!Directory.Exists(root)) { return null; } try { using IEnumerator<string> enumerator = Directory.EnumerateFiles(root, fileName, SearchOption.AllDirectories).GetEnumerator(); if (enumerator.MoveNext()) { return enumerator.Current; } } catch (IOException) { return null; } catch (UnauthorizedAccessException) { return null; } return null; } private static string SafeFileName(string language) { if (string.IsNullOrEmpty(language)) { return "English"; } char[] invalidFileNameChars = Path.GetInvalidFileNameChars(); foreach (char c in invalidFileNameChars) { language = language.Replace(c.ToString(), ""); } return (language.Length == 0) ? "English" : language; } } }
marchiori.utils.notificator.dll
Decompiled 20 hours agousing System; using System.Collections.Generic; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using Microsoft.CodeAnalysis; using TMPro; using UnityEngine; using UnityEngine.UI; [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.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")] [assembly: AssemblyCompany("marchiori.utils.notificator")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+ee52b2bfcab53d7e96836822c3d6ec6f3c6f91ae")] [assembly: AssemblyProduct("marchiori.utils.notificator")] [assembly: AssemblyTitle("marchiori.utils.notificator")] [assembly: AssemblyVersion("1.0.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Marchiori.Utils.Notificator { public static class Notice { private sealed class NoticeView : MonoBehaviour { private CanvasGroup _group; private RectTransform _rect; private TextMeshProUGUI _label; private float _width; private float _age; private float _y; private float _fromY; private float _targetY; private float _slide = 0.2f; private bool _settled; public float Height { get; private set; } public float FontSize { get; private set; } public bool Fresh { get; set; } public bool JustShown => _age <= 0f; private void Awake() { _group = ((Component)this).GetComponent<CanvasGroup>(); _rect = ((Component)this).GetComponent<RectTransform>(); } public void Prepare(TextMeshProUGUI label, float width, float height, float fontSize) { _label = label; _width = width; Height = height; FontSize = fontSize; Fresh = true; ((Component)this).transform.SetAsLastSibling(); } public void Place(float targetY, bool snap) { if (snap) { _y = targetY; _fromY = targetY; _targetY = targetY; _slide = 0.2f; Apply(); } else if (!Mathf.Approximately(_targetY, targetY)) { _fromY = _y; _targetY = targetY; _slide = 0f; } } private void Update() { Settle(); if (Hud.IsUserHidden()) { _group.alpha = 0f; return; } float unscaledDeltaTime = Time.unscaledDeltaTime; if (_slide < 0.2f) { _slide += unscaledDeltaTime; float num = Mathf.Clamp01(_slide / 0.2f); _y = Mathf.Lerp(_fromY, _targetY, num); Apply(); } _age += unscaledDeltaTime; if (_age <= 4f) { _group.alpha = 1f; return; } float num2 = (_age - 4f) / 1f; if (num2 >= 1f) { Object.Destroy((Object)(object)((Component)this).gameObject); } else { _group.alpha = 1f - num2; } } private void Settle() { //IL_003c: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_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_00a9: Unknown result type (might be due to invalid IL or missing references) if (!_settled && !((Object)(object)_label == (Object)null) && !((Object)(object)_rect == (Object)null)) { _settled = true; Rect rect = _rect.rect; float width = ((Rect)(ref rect)).width; if (width < 1f) { width = _width; } float num = Measure(_label, width); if (!(num <= Height + 0.5f)) { Height = num; Vector2 sizeDelta = _rect.sizeDelta; sizeDelta.y = num; _rect.sizeDelta = sizeDelta; Layout(); } } } private void Apply() { //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_0020: Unknown result type (might be due to invalid IL or missing references) Vector2 anchoredPosition = _rect.anchoredPosition; anchoredPosition.y = _y; _rect.anchoredPosition = anchoredPosition; } private void OnDestroy() { if (Lines.Remove(this)) { Layout(); } } } private const float HoldSeconds = 4f; private const float FadeSeconds = 1f; private const float SlideSeconds = 0.2f; private const float GapFactor = 0.35f; private const float FromTop = 2f / 3f; private static readonly List<NoticeView> Lines = new List<NoticeView>(); public static void Show(string text) { if (string.IsNullOrEmpty(text) || Hud.IsUserHidden()) { return; } MessageHud instance = MessageHud.instance; if (!((Object)(object)instance == (Object)null) && !((Object)(object)instance.m_messageCenterText == (Object)null)) { NoticeView noticeView = Create(instance.m_messageCenterText, text); if (!((Object)(object)noticeView == (Object)null)) { Lines.Add(noticeView); Layout(); } } } private static NoticeView Create(TMP_Text source, string text) { //IL_0033: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Expected O, but got Unknown //IL_007a: 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_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00ae: Unknown result type (might be due to invalid IL or missing references) //IL_00ef: Unknown result type (might be due to invalid IL or missing references) //IL_0112: Unknown result type (might be due to invalid IL or missing references) Canvas canvas = ((Graphic)source).canvas; if ((Object)(object)canvas == (Object)null || (Object)(object)source.font == (Object)null) { return null; } GameObject val = new GameObject("MarchioriNotice"); val.layer = ((Component)canvas).gameObject.layer; val.SetActive(false); val.transform.SetParent(((Component)canvas).transform, false); RectTransform val2 = val.AddComponent<RectTransform>(); float num = 0.3333333f; val2.anchorMin = new Vector2(0.5f, num); val2.anchorMax = new Vector2(0.5f, num); val2.pivot = new Vector2(0.5f, 0.5f); val2.anchoredPosition = Vector2.zero; TextMeshProUGUI val3 = val.AddComponent<TextMeshProUGUI>(); ((Graphic)val3).raycastTarget = false; CopyStyle(val3, source); ((TMP_Text)val3).text = text; float num2 = Width(source, canvas); val2.sizeDelta = new Vector2(num2, ((TMP_Text)val3).fontSize); val.SetActive(true); float num3 = Measure(val3, num2); val2.sizeDelta = new Vector2(num2, num3); CanvasGroup val4 = val.AddComponent<CanvasGroup>(); val4.blocksRaycasts = false; val4.interactable = false; val4.alpha = 1f; NoticeView noticeView = val.AddComponent<NoticeView>(); noticeView.Prepare(val3, num2, num3, ((TMP_Text)val3).fontSize); return noticeView; } private static float Measure(TextMeshProUGUI label, float width) { //IL_0021: Unknown result type (might be due to invalid IL or missing references) //IL_0026: 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_00c8: Unknown result type (might be due to invalid IL or missing references) //IL_00cd: Unknown result type (might be due to invalid IL or missing references) //IL_00d1: Unknown result type (might be due to invalid IL or missing references) if (width < 1f) { width = 600f; } Vector2 preferredValues = ((TMP_Text)label).GetPreferredValues(((TMP_Text)label).text, width, 0f); float num = preferredValues.y; ((TMP_Text)label).ForceMeshUpdate(true, true); TMP_TextInfo textInfo = ((TMP_Text)label).textInfo; if (textInfo != null && textInfo.lineCount > 0 && textInfo.lineInfo != null) { float num2 = 0f; int num3 = textInfo.lineCount; if (num3 > textInfo.lineInfo.Length) { num3 = textInfo.lineInfo.Length; } for (int i = 0; i < num3; i++) { num2 += textInfo.lineInfo[i].lineHeight; } if (num2 > num) { num = num2; } Bounds textBounds = ((TMP_Text)label).textBounds; float y = ((Bounds)(ref textBounds)).size.y; if (y > num) { num = y; } float num4 = ((TMP_Text)label).fontSize * 1.2f; if (textInfo.lineCount > 1 && num <= num4) { num = (float)textInfo.lineCount * ((TMP_Text)label).fontSize * 1.25f; } } if (float.IsNaN(num) || num < ((TMP_Text)label).fontSize) { num = ((TMP_Text)label).fontSize; } return num; } private static void Layout() { float num = 0f; for (int i = 0; i < Lines.Count; i++) { NoticeView noticeView = Lines[i]; if ((Object)(object)noticeView == (Object)null) { continue; } if (i > 0) { NoticeView noticeView2 = Lines[i - 1]; if ((Object)(object)noticeView2 != (Object)null) { num -= (noticeView2.Height + noticeView.Height) * 0.5f + noticeView2.FontSize * 0.35f; } } noticeView.Place(num, noticeView.Fresh || noticeView.JustShown); noticeView.Fresh = false; } } private static void CopyStyle(TextMeshProUGUI label, TMP_Text source) { //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) //IL_0044: Unknown result type (might be due to invalid IL or missing references) ((TMP_Text)label).font = source.font; ((TMP_Text)label).fontSharedMaterial = source.fontSharedMaterial; ((Graphic)label).color = ((Graphic)source).color; ((TMP_Text)label).enableVertexGradient = source.enableVertexGradient; ((TMP_Text)label).colorGradient = source.colorGradient; ((TMP_Text)label).fontStyle = source.fontStyle; float num = source.fontSize; if (num <= 0f) { num = source.fontSizeMax; } if (num <= 0f) { num = 48f; } ((TMP_Text)label).enableAutoSizing = false; ((TMP_Text)label).fontSize = num * 0.5f; ((TMP_Text)label).richText = source.richText; ((TMP_Text)label).alignment = (TextAlignmentOptions)514; ((TMP_Text)label).textWrappingMode = (TextWrappingModes)1; ((TMP_Text)label).overflowMode = (TextOverflowModes)0; ((TMP_Text)label).characterSpacing = source.characterSpacing; ((TMP_Text)label).wordSpacing = source.wordSpacing; ((TMP_Text)label).lineSpacing = source.lineSpacing; ((TMP_Text)label).paragraphSpacing = source.paragraphSpacing; } private static float Width(TMP_Text source, Canvas canvas) { //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_0045: Unknown result type (might be due to invalid IL or missing references) //IL_004a: Unknown result type (might be due to invalid IL or missing references) Rect val = source.rectTransform.rect; float width = ((Rect)(ref val)).width; if (width >= 100f) { return width; } float num = ((canvas.scaleFactor > 0.01f) ? canvas.scaleFactor : 1f); val = canvas.pixelRect; return ((Rect)(ref val)).width / num * 0.7f; } } }
marchiori.utils.signtextmanager.dll
Decompiled 20 hours agousing System; using System.Collections.Generic; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Text; using Microsoft.CodeAnalysis; using TMPro; using UnityEngine; [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.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")] [assembly: AssemblyCompany("marchiori.utils.signtextmanager")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+ee52b2bfcab53d7e96836822c3d6ec6f3c6f91ae")] [assembly: AssemblyProduct("marchiori.utils.signtextmanager")] [assembly: AssemblyTitle("marchiori.utils.signtextmanager")] [assembly: AssemblyVersion("1.0.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Marchiori.Utils.SignTextManager { public static class SignText { private static readonly Dictionary<int, float> MaxFonts = new Dictionary<int, float>(); public static void Present(Sign sign, string text) { if (!((Object)(object)sign == (Object)null)) { string text2 = text ?? ""; sign.m_characterLimit = 240; Fit(sign.m_textWidget, text2); sign.SetText(text2); Fit(sign.m_textWidget, text2); } } public static void Fit(TextMeshProUGUI widget, string text) { //IL_0017: 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) //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0054: Unknown result type (might be due to invalid IL or missing references) //IL_0061: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)widget == (Object)null)) { Rect rect = ((TMP_Text)widget).rectTransform.rect; float num = ((Rect)(ref rect)).width; float num2 = ((Rect)(ref rect)).height; if (num < 1f || num2 < 1f) { Vector2 sizeDelta = ((TMP_Text)widget).rectTransform.sizeDelta; num = Mathf.Abs(sizeDelta.x); num2 = Mathf.Abs(sizeDelta.y); } ((TMP_Text)widget).textWrappingMode = (TextWrappingModes)1; ((TMP_Text)widget).overflowMode = (TextOverflowModes)3; ((TMP_Text)widget).enableAutoSizing = false; ((TMP_Text)widget).fontSize = SignTextFit.FontSize(text, num, num2, Maximum(widget)); } } private static float Maximum(TextMeshProUGUI widget) { int instanceID = ((Object)widget).GetInstanceID(); if (MaxFonts.TryGetValue(instanceID, out var value)) { return value; } float num = ((TMP_Text)widget).fontSize; if (num <= 1f) { num = ((TMP_Text)widget).fontSizeMax; } if (num <= 1f) { num = 36f; } MaxFonts[instanceID] = num; return num; } } public static class SignTextFit { public const int Lines = 3; public const int CharacterLimit = 240; public const float GlyphWidthFactor = 0.6f; public const float LineHeightFactor = 1.25f; public static string Visible(string text) { if (string.IsNullOrEmpty(text)) { return ""; } StringBuilder stringBuilder = new StringBuilder(text.Length); for (int i = 0; i < text.Length; i++) { if (text[i] == '<') { int num = text.IndexOf('>', i + 1); if (num > i && IsTag(text, i, num)) { i = num; continue; } } stringBuilder.Append(text[i]); } return stringBuilder.ToString(); } public static float FontSize(string text, float width, float height, float maxSize) { if (maxSize < 1f) { maxSize = 1f; } if (width < 1f || height < 1f) { return maxSize; } string visible = Visible(text); if (Fits(visible, width, height, maxSize)) { return maxSize; } float num = 1f; float num2 = maxSize; for (int i = 0; i < 16; i++) { float num3 = (num + num2) * 0.5f; if (Fits(visible, width, height, num3)) { num = num3; } else { num2 = num3; } } return num; } private static bool IsTag(string text, int start, int end) { if (end <= start + 1 || end - start > 48) { return false; } for (int i = start + 1; i < end; i++) { char c = text[i]; if (c == ' ' || c == '<' || c == '\n' || c == '\r') { return false; } } return true; } private static bool Fits(string visible, float width, float height, float font) { float num = font * 0.6f; float num2 = font * 1.25f; if (num < 0.01f || num2 < 0.01f) { return true; } if (num2 > height + 0.5f) { return false; } int num3 = (int)(width / num); if (num3 < 1) { return false; } if (LongestWord(visible) > num3) { return false; } int num4 = WrapLines(visible, num3); if (num4 > 3) { return false; } return (float)num4 * num2 <= height + 0.5f; } private static int LongestWord(string text) { int num = 0; int num2 = 0; foreach (char c in text) { if (c == ' ' || c == '\n' || c == '\r') { if (num2 > num) { num = num2; } num2 = 0; } else { num2++; } } return (num2 > num) ? num2 : num; } private static int WrapLines(string text, int perLine) { if (string.IsNullOrEmpty(text)) { return 1; } int num = 1; int num2 = 0; int i = 0; while (i < text.Length) { if (text[i] == '\r') { i++; continue; } if (text[i] == '\n') { num++; num2 = 0; i++; continue; } int num3 = i; for (; i < text.Length && text[i] != ' ' && text[i] != '\n' && text[i] != '\r'; i++) { } int num4 = i - num3; if (num2 > 0 && num2 + 1 + num4 > perLine) { num++; num2 = num4; } else { num2 += ((num2 != 0) ? 1 : 0) + num4; } if (i < text.Length && text[i] == ' ') { i++; } } return num; } } }