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 MyLittleUI v1.2.33
MyLittleUI.dll
Decompiled 6 days 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.Linq; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text; using AzuExtendedPlayerInventory; using BepInEx; using BepInEx.Bootstrap; using BepInEx.Configuration; using ConditionalConfigSync; using ExtraSlotsAPI; using GUIFramework; using HarmonyLib; using JetBrains.Annotations; using Microsoft.CodeAnalysis; using MyLittleUI; using TMPro; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.Events; using UnityEngine.InputSystem; using UnityEngine.TextCore; using UnityEngine.UI; using Valheim.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: AssemblyTitle("My Little UI")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("")] [assembly: AssemblyProduct("My Little UI")] [assembly: AssemblyCopyright("Copyright © 2023")] [assembly: AssemblyTrademark("")] [assembly: ComVisible(false)] [assembly: Guid("345181bf-e9ed-4c88-a4f4-38450f53cc41")] [assembly: AssemblyFileVersion("1.2.33")] [assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.2.33.0")] [module: UnverifiableCode] [HarmonyPatch] public static class Advize_StumpsRegrow_Compat { internal const string GUID = "advize.StumpsRegrow"; private static ConfigEntry<float> stumpGrowthTime; private static bool initialized; private static bool hasGrowthTime; public static MethodBase target; private static double GetTimeSincePlanted(ZNetView nview) { return (ZNet.instance.GetTime() - new DateTime(nview.GetZDO().GetLong(ZDOVars.s_plantTime, 0L))).TotalSeconds; } private static float GetGrowTime() { return (stumpGrowthTime != null) ? Mathf.Max(stumpGrowthTime.Value, 1f) : 1f; } private static void Postfix(object __instance, ref string __result) { if (!global::MyLittleUI.MyLittleUI.modEnabled.Value || __instance == null || !global::MyLittleUI.MyLittleUI.hoverStumpGrowerEnabled.Value || global::MyLittleUI.MyLittleUI.hoverStumpGrower.Value == global::MyLittleUI.MyLittleUI.StationHover.Vanilla || string.IsNullOrWhiteSpace(__result)) { return; } if (!initialized) { initialized = true; hasGrowthTime = Chainloader.PluginInfos.TryGetValue("advize.StumpsRegrow", out var value) && value.Instance.Config.TryGetEntry<float>("General", "StumpGrowthTime", ref stumpGrowthTime); } if (!hasGrowthTime) { return; } object obj = ((__instance is MonoBehaviour) ? __instance : null); ZNetView val = ((obj != null) ? ((Component)obj).GetComponent<ZNetView>() : null); if (!((Object)(object)val == (Object)null) && val.IsValid()) { if (global::MyLittleUI.MyLittleUI.hoverStumpGrower.Value == global::MyLittleUI.MyLittleUI.StationHover.Percentage) { __result += $"\n{GetTimeSincePlanted(val) / (double)GetGrowTime():P0}"; } else if (global::MyLittleUI.MyLittleUI.hoverStumpGrower.Value == global::MyLittleUI.MyLittleUI.StationHover.Bar) { __result = __result + "\n" + global::MyLittleUI.MyLittleUI.FromPercent(GetTimeSincePlanted(val) / (double)GetGrowTime()); } else if (global::MyLittleUI.MyLittleUI.hoverStumpGrower.Value == global::MyLittleUI.MyLittleUI.StationHover.MinutesSeconds) { __result = __result + "\n" + global::MyLittleUI.MyLittleUI.FromSeconds((double)GetGrowTime() - GetTimeSincePlanted(val)); } } } public static bool Prepare(MethodBase original) { if (!Chainloader.PluginInfos.TryGetValue("advize.StumpsRegrow", out var value)) { return false; } if ((object)target == null) { target = AccessTools.Method(((object)value.Instance).GetType().Assembly.GetType("Advize_StumpsRegrow.StumpGrower"), "GetHoverText", (Type[])null, (Type[])null); } if (target == null) { return false; } if (original == null) { global::MyLittleUI.MyLittleUI.LogInfo("Advize_StumpsRegrow.StumpGrower:GetHoverText method is patched to show configurable hover"); } return true; } public static MethodBase TargetMethod() { return target; } } namespace MyLittleUI { internal static class AmmoCountIcon { internal sealed class ElementExtraData { internal readonly GameObject Cell; internal ElementData Element; internal bool Seen; internal TMP_Text m_ammo; internal Image m_icon; internal Image m_bait; internal Image m_mead; internal ItemData m_item; private int styleRevision = -1; private TMP_Text baitAmount; private string previousAmountText; private string baitAmountText; internal ElementExtraData(ElementData element) { Cell = element.m_go; Element = element; Transform obj = Cell.transform.Find("MLUI_AmmoAmount"); m_ammo = ((obj != null) ? ((Component)obj).GetComponent<TMP_Text>() : null); Transform obj2 = Cell.transform.Find("MLUI_AmmoIcon"); m_icon = ((obj2 != null) ? ((Component)obj2).GetComponent<Image>() : null); Transform obj3 = Cell.transform.Find("MLUI_AmmoBait"); m_bait = ((obj3 != null) ? ((Component)obj3).GetComponent<Image>() : null); Transform obj4 = Cell.transform.Find("MLUI_AmmoMead"); m_mead = ((obj4 != null) ? ((Component)obj4).GetComponent<Image>() : null); } internal void Bind(ElementData element) { if (Element != element) { RestoreBaitCount(); Element = element; m_item = null; styleRevision = -1; } } internal void ApplyStyle(AmmoCountTemplates templates) { if (templates.Ready && styleRevision != templates.Revision) { templates.ApplyAmount(m_ammo); templates.ApplyIcon(m_icon, 0); templates.ApplyIcon(m_bait, 1); templates.ApplyIcon(m_mead, 2); styleRevision = templates.Revision; PlaceDecorations(); } } private void PlaceDecorations() { if (Object.op_Implicit((Object)(object)Cell) && Object.op_Implicit((Object)(object)Element.m_icon)) { int siblingIndex = ((Component)Element.m_icon).transform.GetSiblingIndex() + 1; if (Object.op_Implicit((Object)(object)m_ammo)) { m_ammo.transform.SetSiblingIndex(siblingIndex++); } if (Object.op_Implicit((Object)(object)m_icon)) { ((Component)m_icon).transform.SetSiblingIndex(siblingIndex++); } if (Object.op_Implicit((Object)(object)m_bait)) { ((Component)m_bait).transform.SetSiblingIndex(siblingIndex++); } if (Object.op_Implicit((Object)(object)m_mead)) { ((Component)m_mead).transform.SetSiblingIndex(siblingIndex); } } } private T CreateDecoration<T>(T template) where T : Graphic { T val = Object.Instantiate<T>(template, Cell.transform, false); ((Object)(object)val).name = ((Object)(object)template).name; return val; } internal void UpdateState(AmmoCountTemplates templates, Player player) { if (!MyLittleUI.modEnabled.Value || !Object.op_Implicit((Object)(object)Cell) || !Cell.activeInHierarchy || !Object.op_Implicit((Object)(object)player) || ((Character)player).IsDead() || m_item?.m_shared == null) { Hide(); return; } ApplyStyle(templates); Inventory inventory = ((Humanoid)player).GetInventory(); ItemData currentAmmo = GetCurrentAmmo(player); int num = ((currentAmmo != null) ? inventory.CountItems(currentAmmo.m_shared.m_name, -1, true) : 0); bool flag = templates.Ready && MyLittleUI.ammoCountEnabled.Value && num > 0; if (flag) { if (!Object.op_Implicit((Object)(object)m_ammo)) { m_ammo = CreateDecoration<TMP_Text>(templates.Amount); PlaceDecorations(); } m_ammo.SetText(num.ToString()); } SetVisible((Graphic)(object)m_ammo, flag); Sprite val = ((currentAmmo != null) ? currentAmmo.GetIcon() : null); UpdateIcon(ref m_icon, templates.Icon, val, templates.Ready && MyLittleUI.ammoIconEnabled.Value && Object.op_Implicit((Object)(object)val)); ItemData currentBait = GetCurrentBait(player); Sprite val2 = ((currentBait != null) ? currentBait.GetIcon() : null); UpdateIcon(ref m_bait, templates.Bait, val2, templates.Ready && MyLittleUI.baitIconEnabled.Value && Object.op_Implicit((Object)(object)val2)); int num2 = ((currentBait != null) ? inventory.CountItems(currentBait.m_shared.m_name, -1, true) : 0); if (num2 > 0 && MyLittleUI.baitCountEnabled.Value && Object.op_Implicit((Object)(object)Element.m_amount) && !((Component)Element.m_amount).gameObject.activeSelf) { baitAmount = Element.m_amount; previousAmountText = baitAmount.text; baitAmountText = num2.ToString(); baitAmount.SetText(baitAmountText); ((Component)baitAmount).gameObject.SetActive(true); } ItemData currentMead = GetCurrentMead(player); Sprite val3 = ((currentMead != null) ? currentMead.GetIcon() : null); UpdateIcon(ref m_mead, templates.Mead, val3, templates.Ready && MyLittleUI.meadIconEnabled.Value && Object.op_Implicit((Object)(object)val3)); } private void UpdateIcon(ref Image image, Image template, Sprite sprite, bool visible) { if (visible) { if (!Object.op_Implicit((Object)(object)image)) { image = CreateDecoration<Image>(template); PlaceDecorations(); } image.overrideSprite = sprite; } SetVisible((Graphic)(object)image, visible); } private static void SetVisible(Graphic graphic, bool visible) { if (Object.op_Implicit((Object)(object)graphic) && ((Component)graphic).gameObject.activeSelf != visible) { ((Component)graphic).gameObject.SetActive(visible); } } internal void RestoreBaitCount() { if (Object.op_Implicit((Object)(object)baitAmount) && baitAmount.text == baitAmountText) { baitAmount.SetText(previousAmountText); ((Component)baitAmount).gameObject.SetActive(false); if (Element != null && (Object)(object)Element.m_amount == (Object)(object)baitAmount) { Element.m_stackText = -1; } } baitAmount = null; previousAmountText = null; baitAmountText = null; } internal void Hide() { RestoreBaitCount(); SetVisible((Graphic)(object)m_ammo, visible: false); SetVisible((Graphic)(object)m_icon, visible: false); SetVisible((Graphic)(object)m_bait, visible: false); SetVisible((Graphic)(object)m_mead, visible: false); m_item = null; } internal void Dispose() { Hide(); if (Object.op_Implicit((Object)(object)m_ammo)) { Object.Destroy((Object)(object)((Component)m_ammo).gameObject); } if (Object.op_Implicit((Object)(object)m_icon)) { Object.Destroy((Object)(object)((Component)m_icon).gameObject); } if (Object.op_Implicit((Object)(object)m_bait)) { Object.Destroy((Object)(object)((Component)m_bait).gameObject); } if (Object.op_Implicit((Object)(object)m_mead)) { Object.Destroy((Object)(object)((Component)m_mead).gameObject); } m_ammo = null; m_icon = null; m_bait = null; m_mead = null; Element = null; } private ItemData GetCurrentAmmo(Player player) { if (m_item == null || Utility.IsNullOrWhiteSpace(m_item.m_shared.m_ammoType) || IsBaitAmmo() || IsAmmo() || IsMeadAmmo()) { return null; } ItemData ammoItem = ((Humanoid)player).GetAmmoItem(); if (ammoItem == null || ammoItem.m_shared.m_ammoType != m_item.m_shared.m_ammoType || !((Humanoid)player).GetInventory().ContainsItem(ammoItem)) { ammoItem = ((Humanoid)player).GetInventory().GetAmmoItem(m_item.m_shared.m_ammoType, (string)null); } return ammoItem; } private ItemData GetCurrentBait(Player player) { if (m_item == null || Utility.IsNullOrWhiteSpace(m_item.m_shared.m_ammoType) || !IsBaitAmmo() || IsAmmo()) { return null; } ItemData ammoItem = ((Humanoid)player).GetAmmoItem(); if (ammoItem == null || ammoItem.m_shared.m_ammoType != m_item.m_shared.m_ammoType || !((Humanoid)player).GetInventory().ContainsItem(ammoItem)) { ammoItem = ((Humanoid)player).GetInventory().GetAmmoItem(m_item.m_shared.m_ammoType, (string)null); } return ammoItem; } private ItemData GetCurrentMead(Player player) { if (m_item == null || Utility.IsNullOrWhiteSpace(m_item.m_shared.m_ammoType) || IsBaitAmmo() || IsAmmo() || !IsMeadAmmo()) { return null; } return ((Humanoid)player).GetInventory().GetAmmoItem(m_item.m_shared.m_ammoType, (string)null); } private bool IsAmmo() { //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Invalid comparison between Unknown and I4 //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0027: Invalid comparison between Unknown and I4 //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_003a: Invalid comparison between Unknown and I4 return (int)m_item.m_shared.m_itemType == 9 || (int)m_item.m_shared.m_itemType == 23 || (int)m_item.m_shared.m_itemType == 2; } private bool IsBaitAmmo() { return m_item.m_shared.m_ammoType == "$item_fishingbait"; } private bool IsMeadAmmo() { return m_item.m_shared.m_ammoType == "mead"; } } [HarmonyPatch(typeof(HotkeyBar), "OnEnable")] private static class HotkeyBar_OnEnable_PrepareAmmoTemplates { [HarmonyPriority(0)] [HarmonyAfter(new string[] { "Azumatt.AzuExtendedPlayerInventory", "shudnal.ExtraSlots" })] private static void Postfix(HotkeyBar __instance) { GetState(__instance).Refresh(Player.m_localPlayer, refreshDonors: true); } } [HarmonyPatch(typeof(HotkeyBar), "OnDisable")] private static class HotkeyBar_OnDisable_HideAmmoDecorations { private static void Postfix(HotkeyBar __instance) { if (bars.TryGetValue(__instance, out var value) && Object.op_Implicit((Object)(object)value)) { value.Hide(); } } } [HarmonyPatch(typeof(HotkeyBar), "UpdateIcons")] private static class HotkeyBar_UpdateIcons_UpdateAmmoCountAndIcon { [HarmonyPriority(800)] [HarmonyBefore(new string[] { "Azumatt.AzuExtendedPlayerInventory", "shudnal.ExtraSlots" })] private static void Prefix(HotkeyBar __instance) { if (bars.TryGetValue(__instance, out var value) && Object.op_Implicit((Object)(object)value)) { value.RestoreBaitCounts(); } } [HarmonyPriority(0)] [HarmonyAfter(new string[] { "Azumatt.AzuExtendedPlayerInventory", "shudnal.ExtraSlots" })] private static void Postfix(HotkeyBar __instance, Player player) { GetState(__instance).Refresh(player); } } internal const string objectAmmoName = "MLUI_AmmoAmount"; internal const string objectIconName = "MLUI_AmmoIcon"; internal const string objectBaitName = "MLUI_AmmoBait"; internal const string objectMeadName = "MLUI_AmmoMead"; private static readonly Dictionary<HotkeyBar, AmmoCountBarState> bars = new Dictionary<HotkeyBar, AmmoCountBarState>(); private static AmmoCountBarState GetState(HotkeyBar bar) { if (!bars.TryGetValue(bar, out var value) || !Object.op_Implicit((Object)(object)value)) { value = ((Component)bar).GetComponent<AmmoCountBarState>(); if (!Object.op_Implicit((Object)(object)value)) { value = ((Component)bar).gameObject.AddComponent<AmmoCountBarState>(); } value.Initialize(bar); bars[bar] = value; } return value; } internal static void Unregister(HotkeyBar bar, AmmoCountBarState state) { if (bar != null && bars.TryGetValue(bar, out var value) && value == state) { bars.Remove(bar); } } public static void UpdateVisibility() { foreach (AmmoCountBarState value in bars.Values) { if (Object.op_Implicit((Object)(object)value)) { value.UpdateSettings(); } } } internal static void Shutdown() { foreach (AmmoCountBarState item in new List<AmmoCountBarState>(bars.Values)) { if (Object.op_Implicit((Object)(object)item)) { item.Dispose(); Object.Destroy((Object)(object)item); } } bars.Clear(); } } [DisallowMultipleComponent] internal sealed class AmmoCountBarState : MonoBehaviour { private HotkeyBar bar; private readonly AmmoCountTemplates templates = new AmmoCountTemplates(); private readonly Dictionary<GameObject, AmmoCountIcon.ElementExtraData> cells = new Dictionary<GameObject, AmmoCountIcon.ElementExtraData>(); private readonly List<GameObject> removedCells = new List<GameObject>(); internal void Initialize(HotkeyBar owner) { bar = owner; } internal void Refresh(Player player, bool refreshDonors = false) { if (!Object.op_Implicit((Object)(object)bar) || !((Component)this).gameObject.activeInHierarchy) { Hide(); return; } templates.Refresh(bar.m_elementPrefab, refreshDonors); RestoreBaitCounts(); foreach (AmmoCountIcon.ElementExtraData value2 in cells.Values) { value2.Seen = false; } bool flag = Object.op_Implicit((Object)(object)player) && !((Character)player).IsDead(); Inventory val = (flag ? ((Humanoid)player).GetInventory() : null); int num = 0; for (int i = 0; i < bar.m_elements.Count; i++) { ElementData val2 = bar.m_elements[i]; if (val2 == null) { continue; } ItemData val3 = ((val2.m_used && num < bar.m_items.Count) ? bar.m_items[num++] : null); if (Object.op_Implicit((Object)(object)val2.m_go)) { if (!cells.TryGetValue(val2.m_go, out var value)) { value = new AmmoCountIcon.ElementExtraData(val2); cells.Add(val2.m_go, value); } value.Bind(val2); value.Seen = true; value.m_item = ((flag && val3 != null && val.ContainsItem(val3)) ? val3 : null); value.UpdateState(templates, player); } } removedCells.Clear(); foreach (KeyValuePair<GameObject, AmmoCountIcon.ElementExtraData> cell in cells) { if (!Object.op_Implicit((Object)(object)cell.Key) || !cell.Value.Seen) { cell.Value.Dispose(); removedCells.Add(cell.Key); } } foreach (GameObject removedCell in removedCells) { cells.Remove(removedCell); } removedCells.Clear(); } internal void RestoreBaitCounts() { foreach (AmmoCountIcon.ElementExtraData value in cells.Values) { value.RestoreBaitCount(); } } internal void UpdateSettings() { templates.ApplySettings(); foreach (AmmoCountIcon.ElementExtraData value in cells.Values) { value.ApplyStyle(templates); } Refresh(Player.m_localPlayer); } internal void Hide() { foreach (AmmoCountIcon.ElementExtraData value in cells.Values) { value.Hide(); } } internal void Dispose() { foreach (AmmoCountIcon.ElementExtraData value in cells.Values) { value.Dispose(); } cells.Clear(); removedCells.Clear(); templates.Dispose(); AmmoCountIcon.Unregister(bar, this); bar = null; } private void OnDisable() { Hide(); } private void OnDestroy() { Dispose(); } } internal sealed class AmmoCountTemplates { private sealed class RectAppearance { private readonly Vector2 anchorMin; private readonly Vector2 anchorMax; private readonly Vector2 pivot; private readonly Vector2 sizeDelta; private readonly Vector3 anchoredPosition3D; private readonly Vector3 localScale; private readonly Quaternion localRotation; internal RectAppearance(RectTransform source) { //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_0016: 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_0022: 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_002e: Unknown result type (might be due to invalid IL or missing references) //IL_0033: Unknown result type (might be due to invalid IL or missing references) //IL_003a: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_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) anchorMin = source.anchorMin; anchorMax = source.anchorMax; pivot = source.pivot; sizeDelta = source.sizeDelta; anchoredPosition3D = source.anchoredPosition3D; localScale = ((Transform)source).localScale; localRotation = ((Transform)source).localRotation; } internal bool Matches(RectTransform source) { //IL_0002: 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_0015: 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_0028: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) //IL_003b: 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_004e: 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) //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_007a: Unknown result type (might be due to invalid IL or missing references) return anchorMin == source.anchorMin && anchorMax == source.anchorMax && pivot == source.pivot && sizeDelta == source.sizeDelta && anchoredPosition3D == source.anchoredPosition3D && localScale == ((Transform)source).localScale && localRotation == ((Transform)source).localRotation; } internal void Apply(RectTransform target) { //IL_0003: 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_001d: Unknown result type (might be due to invalid IL or missing references) //IL_002a: 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) //IL_0051: Unknown result type (might be due to invalid IL or missing references) target.anchorMin = anchorMin; target.anchorMax = anchorMax; target.pivot = pivot; target.sizeDelta = sizeDelta; target.anchoredPosition3D = anchoredPosition3D; ((Transform)target).localScale = localScale; ((Transform)target).localRotation = localRotation; } } private sealed class TextAppearance { private readonly RectAppearance rect; private readonly int layer; private readonly TMP_FontAsset font; private readonly Material fontSharedMaterial; private readonly TMP_SpriteAsset spriteAsset; private readonly FontStyles fontStyle; private readonly FontWeight fontWeight; private readonly float fontSize; private readonly float fontSizeMin; private readonly float fontSizeMax; private readonly bool enableAutoSizing; private readonly TextAlignmentOptions alignment; private readonly Color color; private readonly bool enableVertexGradient; private readonly VertexGradient colorGradient; private readonly TMP_ColorGradient colorGradientPreset; private readonly float characterSpacing; private readonly float wordSpacing; private readonly float lineSpacing; private readonly float paragraphSpacing; private readonly Vector4 margin; private readonly TextOverflowModes overflowMode; private readonly TextWrappingModes textWrappingMode; private readonly OTL_FeatureTag[] fontFeatures; private readonly bool richText; private readonly bool extraPadding; private readonly bool isRightToLeftText; private readonly bool maskable; internal Color Color => color; internal TextAppearance(TMP_Text source) { //IL_0050: 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_005c: 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) //IL_0098: 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_00a4: 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_00bc: 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) //IL_0104: Unknown result type (might be due to invalid IL or missing references) //IL_0109: Unknown result type (might be due to invalid IL or missing references) //IL_0110: Unknown result type (might be due to invalid IL or missing references) //IL_0115: Unknown result type (might be due to invalid IL or missing references) //IL_011c: Unknown result type (might be due to invalid IL or missing references) //IL_0121: Unknown result type (might be due to invalid IL or missing references) rect = new RectAppearance(source.rectTransform); layer = ((Component)source).gameObject.layer; font = source.font; fontSharedMaterial = source.fontSharedMaterial; spriteAsset = source.spriteAsset; fontStyle = source.fontStyle; fontWeight = source.fontWeight; fontSize = source.fontSize; fontSizeMin = source.fontSizeMin; fontSizeMax = source.fontSizeMax; enableAutoSizing = source.enableAutoSizing; alignment = source.alignment; color = ((Graphic)source).color; enableVertexGradient = source.enableVertexGradient; colorGradient = source.colorGradient; colorGradientPreset = source.colorGradientPreset; characterSpacing = source.characterSpacing; wordSpacing = source.wordSpacing; lineSpacing = source.lineSpacing; paragraphSpacing = source.paragraphSpacing; margin = source.margin; overflowMode = source.overflowMode; textWrappingMode = source.textWrappingMode; fontFeatures = source.fontFeatures?.ToArray() ?? Array.Empty<OTL_FeatureTag>(); richText = source.richText; extraPadding = source.extraPadding; isRightToLeftText = source.isRightToLeftText; maskable = ((MaskableGraphic)source).maskable; } internal bool Matches(TMP_Text source) { //IL_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_0081: 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_00d6: Unknown result type (might be due to invalid IL or missing references) //IL_00dc: Unknown result type (might be due to invalid IL or missing references) //IL_00e7: Unknown result type (might be due to invalid IL or missing references) //IL_00ed: Unknown result type (might be due to invalid IL or missing references) //IL_0113: Unknown result type (might be due to invalid IL or missing references) //IL_0119: Unknown result type (might be due to invalid IL or missing references) //IL_011e: Unknown result type (might be due to invalid IL or missing references) //IL_0133: Unknown result type (might be due to invalid IL or missing references) //IL_0139: Unknown result type (might be due to invalid IL or missing references) //IL_013e: Unknown result type (might be due to invalid IL or missing references) //IL_0153: Unknown result type (might be due to invalid IL or missing references) //IL_0159: Unknown result type (might be due to invalid IL or missing references) //IL_015e: Unknown result type (might be due to invalid IL or missing references) //IL_0173: Unknown result type (might be due to invalid IL or missing references) //IL_0179: Unknown result type (might be due to invalid IL or missing references) //IL_017e: Unknown result type (might be due to invalid IL or missing references) //IL_01e5: Unknown result type (might be due to invalid IL or missing references) //IL_01eb: Unknown result type (might be due to invalid IL or missing references) //IL_01f8: Unknown result type (might be due to invalid IL or missing references) //IL_01fe: Unknown result type (might be due to invalid IL or missing references) //IL_0206: Unknown result type (might be due to invalid IL or missing references) //IL_020c: Unknown result type (might be due to invalid IL or missing references) return rect.Matches(source.rectTransform) && layer == ((Component)source).gameObject.layer && (Object)(object)font == (Object)(object)source.font && (Object)(object)fontSharedMaterial == (Object)(object)source.fontSharedMaterial && (Object)(object)spriteAsset == (Object)(object)source.spriteAsset && fontStyle == source.fontStyle && fontWeight == source.fontWeight && fontSize == source.fontSize && fontSizeMin == source.fontSizeMin && fontSizeMax == source.fontSizeMax && enableAutoSizing == source.enableAutoSizing && alignment == source.alignment && color == ((Graphic)source).color && enableVertexGradient == source.enableVertexGradient && colorGradient.topLeft == source.colorGradient.topLeft && colorGradient.topRight == source.colorGradient.topRight && colorGradient.bottomLeft == source.colorGradient.bottomLeft && colorGradient.bottomRight == source.colorGradient.bottomRight && (Object)(object)colorGradientPreset == (Object)(object)source.colorGradientPreset && characterSpacing == source.characterSpacing && wordSpacing == source.wordSpacing && lineSpacing == source.lineSpacing && paragraphSpacing == source.paragraphSpacing && margin == source.margin && overflowMode == source.overflowMode && textWrappingMode == source.textWrappingMode && MatchesFontFeatures(source.fontFeatures) && richText == source.richText && extraPadding == source.extraPadding && isRightToLeftText == source.isRightToLeftText && maskable == ((MaskableGraphic)source).maskable; } private bool MatchesFontFeatures(List<OTL_FeatureTag> features) { //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Invalid comparison between I4 and Unknown int num = features?.Count ?? 0; if (fontFeatures.Length != num) { return false; } for (int i = 0; i < num; i++) { if ((int)fontFeatures[i] != (int)features[i]) { return false; } } return true; } internal void Apply(TMP_Text target) { //IL_004e: Unknown result type (might be due to invalid IL or missing references) //IL_005b: 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_00a9: Unknown result type (might be due to invalid IL or missing references) //IL_00c3: Unknown result type (might be due to invalid IL or missing references) //IL_0111: Unknown result type (might be due to invalid IL or missing references) //IL_011e: Unknown result type (might be due to invalid IL or missing references) //IL_012b: Unknown result type (might be due to invalid IL or missing references) rect.Apply(target.rectTransform); ((Component)target).gameObject.layer = layer; target.font = font; target.fontSharedMaterial = fontSharedMaterial; target.spriteAsset = spriteAsset; target.fontStyle = fontStyle; target.fontWeight = fontWeight; target.fontSize = fontSize; target.fontSizeMin = fontSizeMin; target.fontSizeMax = fontSizeMax; target.enableAutoSizing = enableAutoSizing; target.alignment = alignment; ((Graphic)target).color = color; target.enableVertexGradient = enableVertexGradient; target.colorGradient = colorGradient; target.colorGradientPreset = colorGradientPreset; target.characterSpacing = characterSpacing; target.wordSpacing = wordSpacing; target.lineSpacing = lineSpacing; target.paragraphSpacing = paragraphSpacing; target.margin = margin; target.overflowMode = overflowMode; target.textWrappingMode = textWrappingMode; target.fontFeatures = new List<OTL_FeatureTag>(fontFeatures); target.richText = richText; target.extraPadding = extraPadding; target.isRightToLeftText = isRightToLeftText; ((MaskableGraphic)target).maskable = maskable; } } private sealed class ImageAppearance { private readonly RectAppearance rect; private readonly int layer; private readonly Material material; private readonly Sprite sprite; private readonly Color color; private readonly Type type; private readonly bool preserveAspect; private readonly bool fillCenter; private readonly FillMethod fillMethod; private readonly int fillOrigin; private readonly float fillAmount; private readonly bool fillClockwise; private readonly float pixelsPerUnitMultiplier; private readonly bool useSpriteMesh; private readonly bool maskable; internal ImageAppearance(Image source) { //IL_0044: Unknown result type (might be due to invalid IL or missing references) //IL_0049: Unknown result type (might be due to invalid IL or missing references) //IL_0050: 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_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) rect = new RectAppearance(((Graphic)source).rectTransform); layer = ((Component)source).gameObject.layer; material = ((Graphic)source).material; sprite = source.sprite; color = ((Graphic)source).color; type = source.type; preserveAspect = source.preserveAspect; fillCenter = source.fillCenter; fillMethod = source.fillMethod; fillOrigin = source.fillOrigin; fillAmount = source.fillAmount; fillClockwise = source.fillClockwise; pixelsPerUnitMultiplier = source.pixelsPerUnitMultiplier; useSpriteMesh = source.useSpriteMesh; maskable = ((MaskableGraphic)source).maskable; } internal bool Matches(Image source) { //IL_005a: Unknown result type (might be due to invalid IL or missing references) //IL_0060: Unknown result type (might be due to invalid IL or missing references) //IL_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_009d: Unknown result type (might be due to invalid IL or missing references) //IL_00a3: Unknown result type (might be due to invalid IL or missing references) return rect.Matches(((Graphic)source).rectTransform) && layer == ((Component)source).gameObject.layer && (Object)(object)material == (Object)(object)((Graphic)source).material && (Object)(object)sprite == (Object)(object)source.sprite && color == ((Graphic)source).color && type == source.type && preserveAspect == source.preserveAspect && fillCenter == source.fillCenter && fillMethod == source.fillMethod && fillOrigin == source.fillOrigin && fillAmount == source.fillAmount && fillClockwise == source.fillClockwise && pixelsPerUnitMultiplier == source.pixelsPerUnitMultiplier && useSpriteMesh == source.useSpriteMesh && maskable == ((MaskableGraphic)source).maskable; } internal void Apply(Image target) { //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_004e: Unknown result type (might be due to invalid IL or missing references) //IL_0075: Unknown result type (might be due to invalid IL or missing references) rect.Apply(((Graphic)target).rectTransform); ((Component)target).gameObject.layer = layer; ((Graphic)target).material = material; target.sprite = sprite; ((Graphic)target).color = color; target.type = type; target.preserveAspect = preserveAspect; target.fillCenter = fillCenter; target.fillMethod = fillMethod; target.fillOrigin = fillOrigin; target.fillAmount = fillAmount; target.fillClockwise = fillClockwise; target.pixelsPerUnitMultiplier = pixelsPerUnitMultiplier; target.useSpriteMesh = useSpriteMesh; ((MaskableGraphic)target).maskable = maskable; } } private GameObject container; private GameObject sourcePrefab; private TMP_Text sourceAmount; private Image sourceIcon; private TextAppearance textAppearance; private ImageAppearance imageAppearance; internal TMP_Text Amount { get; private set; } internal Image Icon { get; private set; } internal Image Bait { get; private set; } internal Image Mead { get; private set; } internal bool Ready { get; private set; } internal int Revision { get; private set; } internal void Refresh(GameObject prefab, bool refreshDonors = false) { //IL_01a4: Unknown result type (might be due to invalid IL or missing references) //IL_01ae: Expected O, but got Unknown if ((Object)(object)sourcePrefab != (Object)(object)prefab || !Object.op_Implicit((Object)(object)sourceAmount) || !Object.op_Implicit((Object)(object)sourceIcon) || refreshDonors) { sourcePrefab = prefab; object obj; if (!Object.op_Implicit((Object)(object)prefab)) { obj = null; } else { Transform obj2 = prefab.transform.Find("amount"); obj = ((obj2 != null) ? ((Component)obj2).GetComponent<TMP_Text>() : null); } sourceAmount = (TMP_Text)obj; object obj3; if (!Object.op_Implicit((Object)(object)prefab)) { obj3 = null; } else { Transform obj4 = prefab.transform.Find("icon"); obj3 = ((obj4 != null) ? ((Component)obj4).GetComponent<Image>() : null); } sourceIcon = (Image)obj3; } Ready = Object.op_Implicit((Object)(object)sourceAmount) && Object.op_Implicit((Object)(object)sourceAmount.font) && Object.op_Implicit((Object)(object)sourceIcon) && Object.op_Implicit((Object)(object)MyLittleUI.instance); if (Ready && (!Object.op_Implicit((Object)(object)container) || !Object.op_Implicit((Object)(object)Amount) || !Object.op_Implicit((Object)(object)Icon) || !Object.op_Implicit((Object)(object)Bait) || !Object.op_Implicit((Object)(object)Mead) || textAppearance == null || !textAppearance.Matches(sourceAmount) || imageAppearance == null || !imageAppearance.Matches(sourceIcon))) { textAppearance = new TextAppearance(sourceAmount); imageAppearance = new ImageAppearance(sourceIcon); if (!Object.op_Implicit((Object)(object)container)) { container = new GameObject("MLUI_AmmoTemplates"); container.SetActive(false); container.transform.SetParent(((Component)MyLittleUI.instance).transform, false); } if (!Object.op_Implicit((Object)(object)Amount)) { Amount = (TMP_Text)(object)CreateTemplate<TextMeshProUGUI>("MLUI_AmmoAmount"); } if (!Object.op_Implicit((Object)(object)Icon)) { Icon = CreateTemplate<Image>("MLUI_AmmoIcon"); } if (!Object.op_Implicit((Object)(object)Bait)) { Bait = CreateTemplate<Image>("MLUI_AmmoBait"); } if (!Object.op_Implicit((Object)(object)Mead)) { Mead = CreateTemplate<Image>("MLUI_AmmoMead"); } Amount.text = string.Empty; ApplySettings(); } } private T CreateTemplate<T>(string name) where T : Graphic { //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Expected O, but got Unknown GameObject val = new GameObject(name, new Type[1] { typeof(RectTransform) }); val.SetActive(false); val.transform.SetParent(container.transform, false); return val.AddComponent<T>(); } internal void ApplySettings() { if (textAppearance != null && imageAppearance != null) { ApplyAmount(Amount); ApplyIcon(Icon, 0); ApplyIcon(Bait, 1); ApplyIcon(Mead, 2); if (Object.op_Implicit((Object)(object)Amount)) { ((Component)Amount).gameObject.SetActive(false); } if (Object.op_Implicit((Object)(object)Icon)) { ((Component)Icon).gameObject.SetActive(false); } if (Object.op_Implicit((Object)(object)Bait)) { ((Component)Bait).gameObject.SetActive(false); } if (Object.op_Implicit((Object)(object)Mead)) { ((Component)Mead).gameObject.SetActive(false); } Revision++; } } internal void ApplyAmount(TMP_Text text) { //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0059: 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_007c: 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_008d: Unknown result type (might be due to invalid IL or missing references) if (Object.op_Implicit((Object)(object)text) && textAppearance != null) { textAppearance.Apply(text); text.rectTransform.anchoredPosition = MyLittleUI.ammoCountPosition.Value; text.fontSize = MyLittleUI.ammoCountFontSize.Value; ((Graphic)text).color = ((MyLittleUI.ammoCountColor.Value == Color.clear) ? textAppearance.Color : MyLittleUI.ammoCountColor.Value); text.horizontalAlignment = MyLittleUI.ammoCountAlignment.Value; ((Graphic)text).raycastTarget = false; } } internal void ApplyIcon(Image image, int kind) { //IL_0047: 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_00be: 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_0084: Unknown result type (might be due to invalid IL or missing references) //IL_009f: Unknown result type (might be due to invalid IL or missing references) if (Object.op_Implicit((Object)(object)image) && imageAppearance != null) { imageAppearance.Apply(image); ((Graphic)image).raycastTarget = false; switch (kind) { case 0: ((Graphic)image).rectTransform.anchoredPosition = MyLittleUI.ammoIconPosition.Value; ((Graphic)image).rectTransform.sizeDelta = MyLittleUI.ammoIconSize.Value; break; case 1: ((Graphic)image).rectTransform.anchorMin = new Vector2(0.5f, 0f); ((Graphic)image).rectTransform.anchorMax = new Vector2(1f, 0.5f); break; default: ((Graphic)image).rectTransform.anchorMin = new Vector2(0.6f, 0.6f); ((Graphic)image).rectTransform.anchorMax = new Vector2(1f, 1f); break; } } } internal void Dispose() { Ready = false; if (Object.op_Implicit((Object)(object)container)) { Object.Destroy((Object)(object)container); } container = null; sourcePrefab = null; sourceAmount = null; sourceIcon = null; Amount = null; Icon = null; Bait = null; Mead = null; textAppearance = null; imageAppearance = null; } } internal class ChestItem { public int m_stack; public int m_value; public string m_name; public float m_weight; public ItemType m_itemType; public ChestItem(ItemData itemData) { //IL_0020: 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) m_name = itemData.m_shared.m_name; m_itemType = itemData.m_shared.m_itemType; } } internal static class ChestHoverText { [HarmonyPatch(typeof(Container), "OnContainerChanged")] private static class Container_OnContainerChanged_HoverCacheReset { private static void Postfix(Container __instance) { if (MyLittleUI.modEnabled.Value) { ResetCache(__instance); } } } [HarmonyPatch(typeof(Container), "GetHoverText")] private static class Container_GetHoverText_Duration { private static readonly StringBuilder result = new StringBuilder(); private static void ReorderItemList(ref List<ChestItem> itemsInChest) { if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Position) { return; } if (MyLittleUI.chestContentSortDir.Value == MyLittleUI.ContentSortDir.Desc) { if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Name) { itemsInChest = itemsInChest.OrderByDescending((ChestItem item) => item.m_name).ToList(); } else if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Weight) { itemsInChest = itemsInChest.OrderByDescending((ChestItem item) => item.m_weight).ToList(); } else if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Amount) { itemsInChest = itemsInChest.OrderByDescending((ChestItem item) => item.m_stack).ToList(); } else if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Value) { itemsInChest = itemsInChest.OrderByDescending((ChestItem item) => item.m_value).ToList(); } } else if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Name) { itemsInChest = itemsInChest.OrderBy((ChestItem item) => item.m_name).ToList(); } else if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Weight) { itemsInChest = itemsInChest.OrderBy((ChestItem item) => item.m_weight).ToList(); } else if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Amount) { itemsInChest = itemsInChest.OrderBy((ChestItem item) => item.m_stack).ToList(); } else if (MyLittleUI.chestContentSortType.Value == MyLittleUI.ContentSortType.Value) { itemsInChest = itemsInChest.OrderBy((ChestItem item) => item.m_value).ToList(); } } private static void AddChestContent(Container container) { //IL_0118: Unknown result type (might be due to invalid IL or missing references) //IL_013d: Unknown result type (might be due to invalid IL or missing references) //IL_01a8: 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_01af: Unknown result type (might be due to invalid IL or missing references) //IL_01b1: Unknown result type (might be due to invalid IL or missing references) //IL_01b3: Unknown result type (might be due to invalid IL or missing references) //IL_01b6: Unknown result type (might be due to invalid IL or missing references) //IL_0214: Expected I4, but got Unknown if (container.GetInventory().NrOfItems() == 0) { return; } result.Append("\n"); List<ChestItem> itemsInChest = new List<ChestItem>(); foreach (ItemData itemData in container.GetInventory().GetAllItemsInGridOrder()) { ChestItem chestItem = itemsInChest.Find((ChestItem item) => item.m_name == itemData.m_shared.m_name); if (chestItem == null) { chestItem = new ChestItem(itemData); itemsInChest.Add(chestItem); } chestItem.m_stack += itemData.m_stack; chestItem.m_value += itemData.GetValue(); chestItem.m_weight += itemData.GetWeight(-1); } ReorderItemList(ref itemsInChest); string itemFormat = "<color=#" + ColorUtility.ToHtmlStringRGBA(MyLittleUI.chestContentItemColor.Value) + ">{0}</color>"; string amountFormat = "<color=#" + ColorUtility.ToHtmlStringRGBA(MyLittleUI.chestContentAmountColor.Value) + ">{0}</color>"; int num = 0; int num2 = 0; int num3 = 0; int num4 = 0; int num5 = 0; for (int num6 = 0; num6 < itemsInChest.Count; num6++) { ChestItem chestItem2 = itemsInChest[num6]; if (num6 < MyLittleUI.chestContentLinesToShow.Value) { AddItemLine(chestItem2.m_name, chestItem2.m_stack); continue; } ItemType itemType = chestItem2.m_itemType; ItemType val = itemType; switch (val - 1) { case 1: num3++; break; case 0: num5++; break; case 2: case 3: case 4: case 13: case 14: case 18: case 19: case 21: num4++; break; case 5: case 6: case 9: case 10: case 11: case 16: case 17: num2++; break; default: num++; break; } } if (num + num2 + num3 + num4 + num5 != 0) { result.Append("\n+"); if (num4 != 0) { AddItemLine("$radial_handitems", num4); } if (num2 != 0) { AddItemLine("$radial_armor_utility", num2); } if (num3 != 0) { AddItemLine("$radial_consumables", num3); } if (num5 != 0) { AddItemLine("$hud_crafting", num5); } if (num != 0) { AddItemLine("$hud_misc", num); } } void AddItemLine(string itemName, int amount) { result.AppendFormat("\n" + MyLittleUI.chestContentEntryFormat.Value, string.Format(itemFormat, itemName), string.Format(amountFormat, amount)); } } private static void Postfix(Container __instance, ref string __result, bool ___m_checkGuardStone, string ___m_name, Inventory ___m_inventory, bool __runOriginal) { //IL_0092: Unknown result type (might be due to invalid IL or missing references) if (!__runOriginal || !MyLittleUI.modEnabled.Value || IsPlanBuildTotem(__instance) || (MyLittleUI.chestHoverName.Value == MyLittleUI.ChestNameHover.Vanilla && MyLittleUI.chestHoverItems.Value == MyLittleUI.ChestItemsHover.Vanilla) || (Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid() || (___m_checkGuardStone && !PrivateArea.CheckAccess(((Component)__instance).transform.position, 0f, false, false))) { return; } string key = ((object)__instance.m_nview.GetZDO()).ToString(); if (hoverTextCache.TryGetValue(key, out var value)) { __result = value; return; } result.Clear(); string text = __instance.m_nview.GetZDO().GetString(ZDOVars.s_text, ""); if (MyLittleUI.chestHoverName.Value == MyLittleUI.ChestNameHover.Vanilla || !MyLittleUI.chestCustomName.Value || Utility.IsNullOrWhiteSpace(text)) { result.Append(___m_name); } else if (MyLittleUI.chestHoverName.Value == MyLittleUI.ChestNameHover.CustomName) { result.Append(text); } else if (MyLittleUI.chestHoverName.Value == MyLittleUI.ChestNameHover.TypeThenCustomName) { result.Append(___m_name); result.Append(" ("); result.Append(text); result.Append(")"); } else if (MyLittleUI.chestHoverName.Value == MyLittleUI.ChestNameHover.CustomNameThenType) { result.Append(text); result.Append(" ("); result.Append(___m_name); result.Append(")"); } if (__instance.CheckAccess(Game.instance.GetPlayerProfile().GetPlayerID())) { result.Append(" "); if (MyLittleUI.chestHoverItems.Value == MyLittleUI.ChestItemsHover.Percentage) { result.Append($"{___m_inventory.SlotsUsedPercentage():F0}%"); } else if (MyLittleUI.chestHoverItems.Value == MyLittleUI.ChestItemsHover.FreeSlots) { result.Append($"{___m_inventory.GetEmptySlots()}"); } else if (MyLittleUI.chestHoverItems.Value == MyLittleUI.ChestItemsHover.ItemsMaxRoom) { result.Append($"{___m_inventory.NrOfItems()}/{___m_inventory.GetWidth() * ___m_inventory.GetHeight()}"); } else if (___m_inventory.NrOfItems() == 0) { result.Append("( $piece_container_empty )"); } result.Append("\n[<color=#ffff00ff><b>$KEY_Use</b></color>] $piece_container_open"); if (MyLittleUI.chestShowHoldToStack.Value) { result.Append(" $msg_stackall_hover"); } if (MyLittleUI.chestShowRename.Value) { if (!ZInput.IsNonClassicFunctionality() || !ZInput.IsGamepadActive()) { result.Append("\n[<color=#ffff00ff><b>$KEY_AltPlace + $KEY_Use</b></color>] $hud_rename"); } else { result.Append("\n[<color=#ffff00ff><b>$KEY_JoyAltKeys + $KEY_Use</b></color>] $hud_rename"); } } if (MyLittleUI.chestContentEnabled.Value) { AddChestContent(__instance); } } __result = Localization.instance.Localize(result.ToString()); hoverTextCache.Add(key, __result); } } [HarmonyPatch(typeof(Container), "Interact")] private class Container_Interact_ChestRename { [HarmonyPriority(0)] private static bool Prefix(Container __instance, Humanoid character, bool hold, bool alt, bool ___m_checkGuardStone, bool __runOriginal) { //IL_007f: Unknown result type (might be due to invalid IL or missing references) if (!__runOriginal) { return false; } if (!MyLittleUI.modEnabled.Value) { return true; } if (IsPlanBuildTotem(__instance)) { return true; } if (!MyLittleUI.chestCustomName.Value) { return true; } if (!alt) { return true; } if (hold) { return true; } if (___m_checkGuardStone && !PrivateArea.CheckAccess(((Component)__instance).transform.position, 0f, true, false)) { ((Character)character).Message((MessageType)2, "$piece_noaccess", 0, (Sprite)null, false); return true; } long playerID = Game.instance.GetPlayerProfile().GetPlayerID(); if (!__instance.CheckAccess(playerID)) { ((Character)character).Message((MessageType)2, "$piece_noaccess", 0, (Sprite)null, false); return true; } textInputForContainer = __instance; TextInput.instance.m_queuedSign = null; TextInput.instance.Show("$hud_rename " + __instance.m_name, __instance.m_nview.GetZDO().GetString(ZDOVars.s_text, ""), 32); return false; } } [HarmonyPatch(typeof(TextInput), "setText")] private class TextInput_setText_ChestRename { private static void Postfix(string text) { if (MyLittleUI.modEnabled.Value && !((Object)(object)textInputForContainer == (Object)null)) { textInputForContainer.m_nview.GetZDO().Set(ZDOVars.s_text, text); textInputForContainer.OnContainerChanged(); textInputForContainer = null; } } } [HarmonyPatch(typeof(TextInput), "Hide")] private class TextInput_Hide_ChestRename { private static void Postfix() { if (MyLittleUI.modEnabled.Value && !((Object)(object)textInputForContainer == (Object)null)) { textInputForContainer = null; } } } private const string PlanBuildTotemPrefab = "piece_plan_totem"; private static Container textInputForContainer; private static readonly Dictionary<string, string> hoverTextCache = new Dictionary<string, string>(); private static bool IsPlanBuildTotem(Container container) { return Object.op_Implicit((Object)(object)container) && Utils.GetPrefabName(((Component)container).gameObject) == "piece_plan_totem"; } internal static void ResetCache(Container container) { if (!((Object)(object)container == (Object)null) && !((Object)(object)container.m_nview == (Object)null) && container.m_nview.IsValid()) { hoverTextCache.Remove(((object)container.m_nview.GetZDO()).ToString()); } } internal static void ResetHoverCache() { hoverTextCache.Clear(); } } internal static class ChatItemLinks { private sealed class ChatItemLinkHover : MonoBehaviour { private TMP_Text output; private UITooltip tooltip; private CanvasGroup chatterPanelCanvasGroup; private bool chatterLabelNeedsMeshUpdate; private int currentLinkId = -1; private void Awake() { output = ((Component)this).GetComponent<TMP_Text>(); } internal void ConfigureForChatter() { chatterPanelCanvasGroup = ((Component)this).GetComponentInParent<CanvasGroup>(); chatterLabelNeedsMeshUpdate = true; } private void LateUpdate() { //IL_00ca: Unknown result type (might be due to invalid IL or missing references) //IL_0117: Unknown result type (might be due to invalid IL or missing references) //IL_011c: 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) //IL_01b8: Unknown result type (might be due to invalid IL or missing references) if (MyLittleUI.modEnabled.Value) { ConfigEntry<bool> chatItemLinksEnabled = MyLittleUI.chatItemLinksEnabled; if (chatItemLinksEnabled != null && chatItemLinksEnabled.Value && Object.op_Implicit((Object)(object)output) && ((Component)output).gameObject.activeInHierarchy) { if (Object.op_Implicit((Object)(object)chatterPanelCanvasGroup) && (!chatterPanelCanvasGroup.blocksRaycasts || chatterPanelCanvasGroup.alpha <= 0f)) { HideTooltip(); return; } if (chatterLabelNeedsMeshUpdate) { output.ForceMeshUpdate(false, false); chatterLabelNeedsMeshUpdate = false; } int num = TMP_TextUtilities.FindIntersectingLink(output, ZInput.pointerPosition, (Camera)null); if (num < 0 || num >= output.textInfo.linkCount) { HideTooltip(); return; } TMP_LinkInfo val = output.textInfo.linkInfo[num]; if (!TryParseTmpLink(((TMP_LinkInfo)(ref val)).GetLinkID(), out var itemLinkId) || !TryGetLinkedItem(itemLinkId, out var item)) { HideTooltip(); } else if ((currentLinkId != itemLinkId || !Object.op_Implicit((Object)(object)tooltip) || !((Object)(object)UITooltip.m_current == (Object)(object)tooltip)) && EnsureTooltip()) { HideTooltip(); tooltip.Set(item.m_shared.m_name, item.GetTooltip(-1), (RectTransform)null, default(Vector2)); tooltip.OnHoverStart(((Component)output).gameObject); currentLinkId = itemLinkId; } return; } } HideTooltip(); } private bool EnsureTooltip() { //IL_00be: Unknown result type (might be due to invalid IL or missing references) //IL_00c4: Expected O, but got Unknown if (Object.op_Implicit((Object)(object)tooltip)) { return true; } if (!Object.op_Implicit((Object)(object)InventoryGui.instance) || !Object.op_Implicit((Object)(object)InventoryGui.instance.m_playerGrid) || !Object.op_Implicit((Object)(object)InventoryGui.instance.m_playerGrid.m_elementPrefab)) { return false; } InventoryElement component = InventoryGui.instance.m_playerGrid.m_elementPrefab.GetComponent<InventoryElement>(); if (!Object.op_Implicit((Object)(object)component) || !Object.op_Implicit((Object)(object)component.m_tooltip) || !Object.op_Implicit((Object)(object)component.m_tooltip.m_tooltipPrefab)) { return false; } GameObject val = new GameObject("MyLittleUI Item Link Tooltip", new Type[1] { typeof(RectTransform) }); val.transform.SetParent(output.transform, false); tooltip = val.AddComponent<UITooltip>(); tooltip.m_tooltipPrefab = component.m_tooltip.m_tooltipPrefab; return true; } private void HideTooltip() { if (Object.op_Implicit((Object)(object)tooltip) && (Object)(object)UITooltip.m_current == (Object)(object)tooltip) { UITooltip.HideTooltip(); } currentLinkId = -1; } private void OnDisable() { HideTooltip(); } private void OnDestroy() { HideTooltip(); } } [HarmonyPatch(typeof(InventoryGrid), "OnLeftDown")] private static class InventoryGrid_OnLeftDown_LinkItem { private static bool Prefix(InventoryGrid __instance, UIInputHandler clickHandler) { //IL_004f: 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_0055: 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_007a: 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) if (MyLittleUI.modEnabled.Value) { ConfigEntry<bool> chatItemLinksEnabled = MyLittleUI.chatItemLinksEnabled; if (chatItemLinksEnabled != null && chatItemLinksEnabled.Value && IsLinkModifierHeld() && !((Object)(object)clickHandler == (Object)null) && __instance.m_inventory != null) { Vector2i buttonPos = __instance.GetButtonPos(((Component)clickHandler).gameObject); if (buttonPos.x < 0 || buttonPos.y < 0) { return true; } ItemData itemAt = __instance.m_inventory.GetItemAt(buttonPos.x, buttonPos.y); if (itemAt == null) { return true; } return !TrySendItemLink(itemAt); } } return true; } } [HarmonyPatch(typeof(Talker), "Awake")] private static class Talker_Awake_RegisterItemLinkRpc { private static void Postfix(Talker __instance) { if (Object.op_Implicit((Object)(object)__instance.m_nview)) { __instance.m_nview.Register<int, UserInfo, string, ZPackage>("MyLittleUI_ItemLink", (Method<int, UserInfo, string, ZPackage>)delegate(long sender, int chatType, UserInfo userInfo, string fallbackText, ZPackage payload) { ReceiveItemLink(__instance, sender, chatType, userInfo, fallbackText, payload); }); } } } [HarmonyPatch(typeof(Chat), "Awake")] private static class Chat_Awake_InitializeItemLinks { private static void Postfix(Chat __instance) { ResetLinks(); chatInspectionWasActive = false; if (Object.op_Implicit((Object)(object)((Terminal)__instance).m_output) && !Object.op_Implicit((Object)(object)((Component)((Terminal)__instance).m_output).GetComponent<ChatItemLinkHover>())) { ((Component)((Terminal)__instance).m_output).gameObject.AddComponent<ChatItemLinkHover>(); } } } [HarmonyPatch(typeof(Chat), "Update")] private static class Chat_Update_InspectItemLinks { [HarmonyPriority(800)] private static void Prefix(Chat __instance) { if (IsChatInspectionHeld()) { __instance.m_hideTimer = 0f; } } [HarmonyPriority(0)] private static void Postfix(Chat __instance) { bool flag = IsChatInspectionHeld(); if (flag) { __instance.m_hideTimer = 0f; if (Object.op_Implicit((Object)(object)((Terminal)__instance).m_chatWindow)) { ((Component)((Terminal)__instance).m_chatWindow).gameObject.SetActive(true); } } else if (chatInspectionWasActive && !__instance.HasFocus()) { __instance.Hide(); if (Object.op_Implicit((Object)(object)((Terminal)__instance).m_chatWindow)) { ((Component)((Terminal)__instance).m_chatWindow).gameObject.SetActive(false); } } chatInspectionWasActive = flag; } } [HarmonyPatch(typeof(GameCamera), "UpdateMouseCapture")] private static class GameCamera_UpdateMouseCapture_InspectItemLinks { [HarmonyPriority(0)] private static void Postfix() { if (IsChatInspectionHeld()) { ZCursor.LockState = (CursorLockMode)0; ZCursor.Show(); } } } [HarmonyPatch(typeof(PlayerController), "TakeInput", new Type[] { typeof(bool) })] private static class PlayerController_TakeInput_InspectItemLinks { private static void Postfix(bool look, ref bool __result) { if (look && IsChatInspectionHeld()) { __result = false; } } } [HarmonyPatch(typeof(Terminal), "AddString", new Type[] { typeof(string) })] private static class Terminal_AddString_RenderItemLink { private static void Prefix(ref string text) { text = RenderChatLink(text); } } [HarmonyPatch(typeof(Chat), "AddInworldText")] private static class Chat_AddInworldText_RenderItemLink { private static void Prefix(ref string text) { if (TryGetMessageLink(text, out var _, out var item)) { text = BuildPlainDisplay(item); } } } private const string RpcName = "MyLittleUI_ItemLink"; private const string LinkIdPrefix = "mlui-item:"; private const string MessageMarkerPrefix = "\ue000MLUI_ITEM_LINK:"; private const string MessageMarkerSuffix = "\ue001"; private const int PayloadVersion = 1; private const int MaxPayloadBytes = 262144; private const int MaxCachedLinks = 300; private static readonly Dictionary<int, ItemData> linkedItems = new Dictionary<int, ItemData>(); private static readonly Queue<int> linkedItemOrder = new Queue<int>(); private static int nextLinkId; private static bool chatInspectionWasActive; internal static bool TrySendItemLink(ItemData item) { //IL_0122: Unknown result type (might be due to invalid IL or missing references) //IL_012c: Expected O, but got Unknown Player localPlayer = Player.m_localPlayer; if (MyLittleUI.modEnabled.Value) { ConfigEntry<bool> chatItemLinksEnabled = MyLittleUI.chatItemLinksEnabled; if (chatItemLinksEnabled != null && chatItemLinksEnabled.Value && Object.op_Implicit((Object)(object)localPlayer) && item != null) { Talker talker = ((Component)localPlayer).GetComponent<Talker>(); if (!Object.op_Implicit((Object)(object)talker) || (Object)(object)talker.m_nview == (Object)null || !talker.m_nview.IsValid()) { return false; } string fallbackText = BuildPlainDisplay(item); ZPackage val = SerializeItem(item); if (val == null || val.Size() > 262144) { MyLittleUI.LogWarning("Item link payload for '" + (item.m_shared?.m_name ?? "unknown item") + "' is too large; sending plain chat text instead."); talker.Say((Type)1, fallbackText); return true; } byte[] payloadData = val.GetArray(); Chat.CheckPermissionsAndSendChatMessageRPCsAsync((SendChatMessageRPCHandler)delegate(long user, bool filterText) { //IL_0056: Unknown result type (might be due to invalid IL or missing references) //IL_005b: Unknown result type (might be due to invalid IL or missing references) //IL_0091: Unknown result type (might be due to invalid IL or missing references) //IL_0096: Unknown result type (might be due to invalid IL or missing references) //IL_0099: Unknown result type (might be due to invalid IL or missing references) //IL_009b: Unknown result type (might be due to invalid IL or missing references) //IL_00a0: Unknown result type (might be due to invalid IL or missing references) //IL_00ac: 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_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00ca: 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_00d1: Unknown result type (might be due to invalid IL or missing references) UserInfo val2 = default(UserInfo); string text = default(string); Chat.GetChatMessageData(fallbackText, filterText, ref val2, ref text); if (user != 0) { SendItemLinkToTarget(talker, user, val2, text, payloadData); } else { HashSet<long> hashSet = new HashSet<long>(); if ((Object)(object)ZNet.instance != (Object)null) { ZDOID val3 = ZNet.instance.LocalPlayerCharacterID; long userID = ((ZDOID)(ref val3)).UserID; if (userID != 0) { hashSet.Add(userID); } foreach (PlayerInfo player in ZNet.instance.GetPlayerList()) { if (player.m_characterID != ZDOID.None) { val3 = player.m_characterID; if (((ZDOID)(ref val3)).UserID != 0) { val3 = player.m_characterID; hashSet.Add(((ZDOID)(ref val3)).UserID); } } } } if (hashSet.Count != 0) { foreach (long item2 in hashSet) { SendItemLinkToTarget(talker, item2, val2, text, payloadData); } return; } talker.m_nview.InvokeRPC(0L, "Say", new object[3] { 1, val2, text }); } }); return true; } } return false; } private static void SendItemLinkToTarget(Talker talker, long target, UserInfo userInfo, string fallbackText, byte[] payloadData) { //IL_0049: Unknown result type (might be due to invalid IL or missing references) //IL_004f: Expected O, but got Unknown if (target == ZNet.GetUID() || ConditionalConfigSync.HasCompatibleConsumer("shudnal.MyLittleUI", target)) { talker.m_nview.InvokeRPC(target, "MyLittleUI_ItemLink", new object[4] { 1, userInfo, fallbackText, (object)new ZPackage(payloadData) }); } else { talker.m_nview.InvokeRPC(target, "Say", new object[3] { 1, userInfo, fallbackText }); } } private static ZPackage SerializeItem(ItemData item) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0008: Expected O, but got Unknown //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Expected O, but got Unknown try { ZPackage val = new ZPackage(); item.Clone().Save(val); ZPackage val2 = new ZPackage(); val2.Write(1); val2.Write(val); return val2; } catch (Exception arg) { MyLittleUI.LogWarning($"Failed to serialize chat item link.{Environment.NewLine}{arg}"); return null; } } private static bool TryDeserializeItem(ZPackage payload, out ItemData item) { //IL_0035: Unknown result type (might be due to invalid IL or missing references) //IL_003b: Expected O, but got Unknown item = null; if (payload == null) { return false; } try { if (payload.ReadInt() != 1) { return false; } ZPackage val = payload.ReadPackage(); ItemData val2 = new ItemData(); int num = ItemData.Load(val, val2, (Item)110); GameObject val3 = (Object.op_Implicit((Object)(object)ObjectDB.instance) ? ObjectDB.instance.GetItemPrefab(num) : null); if (!Object.op_Implicit((Object)(object)val3) && Object.op_Implicit((Object)(object)ZNetScene.instance)) { val3 = ZNetScene.instance.GetPrefab(num); } ItemDrop val4 = (Object.op_Implicit((Object)(object)val3) ? val3.GetComponent<ItemDrop>() : null); if (!Object.op_Implicit((Object)(object)val4)) { return false; } val2.m_dropPrefab = val3; val2.m_shared = val4.m_itemData.m_shared; item = val2; return true; } catch (Exception arg) { MyLittleUI.LogWarning($"Failed to deserialize chat item link.{Environment.NewLine}{arg}"); return false; } } private static void ReceiveItemLink(Talker talker, long sender, int chatType, UserInfo userInfo, string fallbackText, ZPackage payload) { //IL_0033: 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_0037: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Invalid comparison between Unknown and I4 //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_003d: Invalid comparison between Unknown and I4 //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_00fb: Unknown result type (might be due to invalid IL or missing references) //IL_00ee: Unknown result type (might be due to invalid IL or missing references) //IL_0100: Unknown result type (might be due to invalid IL or missing references) //IL_010e: 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) Player localPlayer = Player.m_localPlayer; if (!Object.op_Implicit((Object)(object)localPlayer) || !Object.op_Implicit((Object)(object)talker) || !Object.op_Implicit((Object)(object)Chat.instance)) { return; } Type val = (Type)chatType; float num = (((int)val == 0) ? talker.m_visperDistance : (((int)val == 1) ? talker.m_normalDistance : (((int)val == 2) ? talker.m_shoutDistance : 0f))); if (num <= 0f || Vector3.Distance(((Component)talker).transform.position, ((Component)localPlayer).transform.position) >= num) { return; } string text = fallbackText; if (MyLittleUI.modEnabled.Value) { ConfigEntry<bool> chatItemLinksEnabled = MyLittleUI.chatItemLinksEnabled; if (chatItemLinksEnabled != null && chatItemLinksEnabled.Value && TryDeserializeItem(payload, out var item)) { int linkId = StoreLinkedItem(item); text = BuildMessageMarker(linkId); } } Vector3 val2 = (Object.op_Implicit((Object)(object)talker.m_character) ? talker.m_character.GetHeadPoint() : ((Component)talker).transform.position); Chat.instance.OnNewChatMessage(((Component)talker).gameObject, sender, val2, val, userInfo, text); } private static int StoreLinkedItem(ItemData item) { int num = ++nextLinkId; if (num <= 0) { linkedItems.Clear(); linkedItemOrder.Clear(); nextLinkId = 1; num = 1; } linkedItems[num] = item; linkedItemOrder.Enqueue(num); while (linkedItemOrder.Count > 300) { linkedItems.Remove(linkedItemOrder.Dequeue()); } return num; } private static bool TryGetLinkedItem(int linkId, out ItemData item) { return linkedItems.TryGetValue(linkId, out item); } private static void ResetLinks() { linkedItems.Clear(); linkedItemOrder.Clear(); nextLinkId = 0; } private static string BuildMessageMarker(int linkId) { return "\ue000MLUI_ITEM_LINK:" + linkId + "\ue001"; } private static bool TryGetMessageLink(string text, out int linkId, out ItemData item) { linkId = 0; item = null; if (string.IsNullOrEmpty(text) || !text.StartsWith("\ue000MLUI_ITEM_LINK:", StringComparison.Ordinal) || !text.EndsWith("\ue001", StringComparison.Ordinal)) { return false; } int length = "\ue000MLUI_ITEM_LINK:".Length; int num = text.Length - "\ue000MLUI_ITEM_LINK:".Length - "\ue001".Length; if (num <= 0 || !int.TryParse(text.Substring(length, num), out linkId)) { return false; } return TryGetLinkedItem(linkId, out item); } private static string RenderChatLink(string text) { if (string.IsNullOrEmpty(text)) { return text; } int num = text.IndexOf("\ue000MLUI_ITEM_LINK:", StringComparison.Ordinal); if (num < 0) { return text; } int num2 = num + "\ue000MLUI_ITEM_LINK:".Length; int num3 = text.IndexOf("\ue001", num2, StringComparison.Ordinal); if (num3 < 0) { return text; } int num4 = num3 - num2; if (num4 <= 0 || !int.TryParse(text.Substring(num2, num4), out var result) || !TryGetLinkedItem(result, out var item)) { return text; } int count = num3 + "\ue001".Length - num; return text.Remove(num, count).Insert(num, BuildChatLink(result, item)); } internal static void TryRenderLinkLabel(TMP_Text label) { if (!Object.op_Implicit((Object)(object)label) || !MyLittleUI.modEnabled.Value) { return; } ConfigEntry<bool> chatItemLinksEnabled = MyLittleUI.chatItemLinksEnabled; if (chatItemLinksEnabled == null || !chatItemLinksEnabled.Value) { return; } string text = RenderChatLink(label.text); if (!(text == label.text)) { label.text = text; ChatItemLinkHover chatItemLinkHover = ((Component)label).GetComponent<ChatItemLinkHover>(); if (!Object.op_Implicit((Object)(object)chatItemLinkHover)) { chatItemLinkHover = ((Component)label).gameObject.AddComponent<ChatItemLinkHover>(); } chatItemLinkHover.ConfigureForChatter(); } } private static string BuildChatLink(int linkId, ItemData item) { //IL_0066: Unknown result type (might be due to invalid IL or missing references) //IL_005f: Unknown result type (might be due to invalid IL or missing references) //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0078: 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_007e: Unknown result type (might be due to invalid IL or missing references) //IL_0086: Unknown result type (might be due to invalid IL or missing references) string text = EscapeRichText(Localization.instance.Localize(item.m_shared.m_name)); string text2 = ((item.m_stack > 1) ? $" x{item.m_stack}" : string.Empty); Color val = (Color)(((??)MyLittleUI.chatItemLinkColor?.Value) ?? new Color(1f, 0.75f, 0f, 1f)); Color val2 = MyLittleUI.chatItemLinkBracketsColor?.Value ?? val; string text3 = ColorUtility.ToHtmlStringRGBA(val); string text4 = ColorUtility.ToHtmlStringRGBA(val2); string text5 = "<color=#" + text4 + ">[</color><color=#" + text3 + ">" + text + "</color><color=#" + text4 + ">]</color>"; return string.Format("<link=\"{0}{1}\">{2}</link>{3}", "mlui-item:", linkId, ApplyLinkStyle(text5), text2); } private static string ApplyLinkStyle(string text) { MyLittleUI.ChatItemLinkStyle chatItemLinkStyle = MyLittleUI.chatItemLinkStyle?.Value ?? MyLittleUI.ChatItemLinkStyle.Underline; string text2 = string.Empty; string text3 = string.Empty; if ((chatItemLinkStyle & MyLittleUI.ChatItemLinkStyle.Bold) != MyLittleUI.ChatItemLinkStyle.None) { text2 += "<b>"; text3 = "</b>" + text3; } if ((chatItemLinkStyle & MyLittleUI.ChatItemLinkStyle.Italic) != MyLittleUI.ChatItemLinkStyle.None) { text2 += "<i>"; text3 = "</i>" + text3; } if ((chatItemLinkStyle & MyLittleUI.ChatItemLinkStyle.Underline) != MyLittleUI.ChatItemLinkStyle.None) { text2 += "<u>"; text3 = "</u>" + text3; } return text2 + text + text3; } private static string BuildPlainDisplay(ItemData item) { string text = Localization.instance.Localize(item.m_shared.m_name); string text2 = ((item.m_stack > 1) ? $" x{item.m_stack}" : string.Empty); return "[" + text + "]" + text2; } private static string EscapeRichText(string text) { return (text ?? string.Empty).Replace("<", "‹").Replace(">", "›"); } private static bool IsLinkModifierHeld() { //IL_0016: 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_001e: Unknown result type (might be due to invalid IL or missing references) if (MyLittleUI.chatItemLinkModifier == null) { return false; } KeyboardShortcut value = MyLittleUI.chatItemLinkModifier.Value; return (int)((KeyboardShortcut)(ref value)).MainKey != 0 && ((KeyboardShortcut)(ref value)).IsPressed(); } private static bool IsChatInspectionHeld() { //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_0044: 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_0079: 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_0081: Unknown result type (might be due to invalid IL or missing references) if (MyLittleUI.modEnabled.Value) { ConfigEntry<bool> chatItemLinksEnabled = MyLittleUI.chatItemLinksEnabled; if (chatItemLinksEnabled != null && chatItemLinksEnabled.Value && MyLittleUI.chatItemLinkInspectModifier != null) { KeyboardShortcut value = MyLittleUI.chatItemLinkInspectModifier.Value; if ((int)((KeyboardShortcut)(ref value)).MainKey == 0 || !ZInput.GetKey(((KeyboardShortcut)(ref value)).MainKey, true)) { return false; } foreach (KeyCode modifier in ((KeyboardShortcut)(ref value)).Modifiers) { if (!ZInput.GetKey(modifier, true)) { return false; } } return true; } } return false; } private static bool TryParseTmpLink(string linkId, out int itemLinkId) { itemLinkId = 0; return !string.IsNullOrEmpty(linkId) && linkId.StartsWith("mlui-item:", StringComparison.Ordinal) && int.TryParse(linkId.Substring("mlui-item:".Length), out itemLinkId); } } internal static class RadialMenuHover { [HarmonyPatch] private static class KnownHoverMethods_Localize_AddRadialHint { private static IEnumerable<MethodBase> TargetMethods() { return GetKnownHoverMethods(); } private static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions) { return ReplaceLocalizationCall(instructions); } } [HarmonyPatch(typeof(RadialBase), "SelectStartElement")] private static class RadialBase_SelectStartElement_AdjustInitialMousePosition { private static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions) { foreach (CodeInstruction instruction in instructions) { if (SetMousePositionMethod != null && SetInitialMousePositionMethod != null && CodeInstructionExtensions.Calls(instruction, SetMousePositionMethod)) { CodeInstruction loadRadial = new CodeInstruction(OpCodes.Ldarg_0, (object)null); loadRadial.labels.AddRange(instruction.labels); instruction.labels.Clear(); yield return loadRadial; instruction.opcode = OpCodes.Call; instruction.operand = SetInitialMousePositionMethod; } yield return instruction; } } } [HarmonyPatch(typeof(Hud), "Awake")] private static class Hud_Awake_ApplyHoverTextWidth { [HarmonyPriority(0)] [HarmonyAfter(new string[] { "Azumatt.MinimalUI" })] private static void Postfix(Hud __instance) { ApplyHoverTextWidth(__instance); } } [HarmonyPatch(typeof(OpenRadialConfig), "TryOpenNonDefaultRadials")] private static class OpenRadialConfig_TryOpenNonDefaultRadials_UseSafeItemSearch { [HarmonyPriority(800)] private static bool Prefix(OpenRadialConfig __instance, RadialBase radial, ref bool __result) { if (!MyLittleUI.modEnabled.Value) { return true; } Player localPlayer = Player.m_localPlayer; GameObject val = (Object.op_Implicit((Object)(object)localPlayer) ? ((Humanoid)localPlayer).GetHoverObject() : null); if (!Object.op_Implicit((Object)(object)localPlayer) || !CanOpenContextualRadial(val) || !RadialMenuItemSearch.IsSearchTarget(val)) { return true; } if (!RadialMenuItemSearch.TryGetItems(localPlayer, val, out var items)) { __result = false; return false; } if (items == null || items.Count <= 0) { if (RadialData.SO.OpenNormalRadialWhenHoverMenuFails) { __result = false; } else { if (radial != null) { radial.QueuedClose(); } __result = true; } return false; } __instance.OpenItemMenu(radial, localPlayer, items, val); __result = true; return false; } } [HarmonyPatch(typeof(ItemGroupConfig), "AddElement")] private static class ItemGroupConfig_AddElement_UseSafeHoverCloseCheck { private static void Postfix(List<RadialMenuElement> elements, RadialBase radial) { if ((Object)(object)radial == (Object)null || !radial.IsHoverMenu || !Object.op_Implicit((Object)(object)radial.HoverObject) || !RadialMenuItemSearch.IsSearchTarget(radial.HoverObject) || elements == null || elements.Count == 0) { return; } RadialMenuElement obj = elements[elements.Count - 1]; ItemElement val = (ItemElement)(object)((obj is ItemElement) ? obj : null); if (val != null) { ((RadialMenuElement)val).AdvancedCloseOnInteract = delegate(RadialBase currentRadial, RadialArray<RadialMenuElement> _) { Player localPlayer = Player.m_localPlayer; return !Object.op_Implicit((Object)(object)localPlayer) || !Object.op_Implicit((Object)(object)currentRadial.HoverObject) || !RadialMenuItemSearch.CanUseItems(localPlayer, currentRadial.HoverObject, sendErrorMessage: false); }; } } } [HarmonyPatch(typeof(OpenRadialConfig), "TryOpenNonDefaultRadials")] private static class OpenRadialConfig_TryOpenNonDefaultRadials_SuppressDefaultRadial { [HarmonyPriority(0)] private static void Postfix(RadialBase radial, ref bool __result) { if (__result || !MyLittleUI.modEnabled.Value) { return; } ConfigEntry<bool> hoverRadialMenuSuppressDefault = MyLittleUI.hoverRadialMenuSuppressDefault; if (hoverRadialMenuSuppressDefault == null || !hoverRadialMenuSuppressDefault.Value) { return; } Player localPlayer = Player.m_localPlayer; Hud instance = Hud.instance; if (Object.op_Implicit((Object)(object)localPlayer) && Object.op_Implicit((Object)(object)((Humanoid)localPlayer).GetHoverObject()) && Object.op_Implicit((Object)(object)instance) && Object.op_Implicit((Object)(object)instance.m_hoverName) && ((Behaviour)instance.m_hoverName).isActiveAndEnabled && !string.IsNullOrWhiteSpace(((TMP_Text)instance.m_hoverName).text)) { if (radial != null) { radial.QueuedClose(); } __result = true; } } } private const string UseKey = "$KEY_Use"; private const string RadialKey = "$KEY_OpenRadial"; private const string RadialHint = "[<color=yellow><b>$KEY_OpenRadial</b></color>] $settings_open_radial"; private static readonly HashSet<Type> CanUseErrorTypes = new HashSet<Type>(); private static RectTransform hoverTextTransform; private static float originalHoverTextWidth; private static readonly MethodInfo LocalizeMethod = AccessTools.Method(typeof(Localization), "Localize", new Type[1] { typeof(string) }, (Type[])null); private static readonly MethodInfo LocalizeHoverTextMethod = AccessTools.Method(typeof(RadialMenuHover), "LocalizeHoverText", (Type[])null, (Type[])null); private static readonly MethodInfo SetMousePositionMethod = AccessTools.Method(typeof(ZInput), "SetMousePosition", new Type[1] { typeof(Vector2) }, (Type[])null); private static readonly MethodInfo SetInitialMousePositionMethod = AccessTools.Method(typeof(RadialMenuHover), "SetInitialMousePosition", new Type[2] { typeof(Vector2), typeof(RadialBase) }, (Type[])null); private static bool CanOpenContextualRadial(GameObject hoverObject) { if (!Object.op_Implicit((Object)(object)hoverObject)) { return false; } Catapult val = default(Catapult); ShieldGenerator val2 = default(ShieldGenerator); Chair val3 = default(Chair); Switch val4 = default(Switch); if ((RadialUtilityExtensions.TryGetComponentInParent<Catapult>(hoverObject, ref val) || RadialUtilityExtensions.TryGetComponentInParent<ShieldGenerator>(hoverObject, ref val2) || RadialUtilityExtensions.TryGetComponentInParent<Chair>(hoverObject, ref val3)) && !hoverObject.TryGetComponent<Switch>(ref val4)) { return false; } return hoverObject.GetComponentInParent<Interactable>() != null; } private static bool CanUseHoveredItems(Player player, GameObject hoverObject) { Type type = null; try { type = ((object)(Object.op_Implicit((Object)(object)hoverObject) ? ((IEnumerable<MonoBehaviour>)hoverObject.GetComponentsInParent<MonoBehaviour>()).FirstOrDefault((Func<MonoBehaviour, bool>)((MonoBehaviour component) => component is IHasHoverMenu || component is IHasHoverMenuExtended)) : null))?.GetType(); return RadialMenuItemSearch.CanUseItems(player, hoverObject, sendErrorMessage: false); } catch (Exception arg) { if (type == null || CanUseErrorTypes.Add(type)) { MyLittleUI.LogWarning(string.Format("Failed to evaluate contextual radial availability for '{0}'.{1}{2}", type?.FullName ?? "unknown type", Environment.NewLine, arg)); } } return false; } internal static string AddRadialHint(string hoverText) { if (MyLittleUI.modEnabled.Value) { ConfigEntry<bool> hoverRadialMenuHint = MyLittleUI.hoverRadialMenuHint; if (hoverRadialMenuHint != null && hoverRadialMenuHint.Value && !string.IsNullOrWhiteSpace(hoverText) && hoverText.IndexOf("$KEY_OpenRadial", StringComparison.Ordinal) < 0) { Player localPlayer = Player.m_localPlayer; GameObject hoverObject = (Object.op_Implicit((Object)(object)localPlayer) ? ((Humanoid)localPlayer).GetHoverObject() : null); if (!Object.op_Implicit((Object)(object)localPlayer) || !CanOpenContextualRadial(hoverObject) || !CanUseHoveredItems(localPlayer, hoverObject)) { return hoverText; } int num = hoverText.IndexOf("$KEY_Use", StringComparison.Ordinal); if (num < 0) { return hoverText; } int num2 = hoverText.IndexOf('\n', num); if (num2 < 0) { return hoverText + "\n[<color=yellow><b>$KEY_OpenRadial</b></color>] $settings_open_radial"; } return hoverText.Insert(num2 + 1, "[<color=yellow><b>$KEY_OpenRadial</b></color>] $settings_open_radial\n"); } } return hoverText; } private static string LocalizeHoverText(Localization localization, string hoverText) { return localization.Localize(AddRadialHint(hoverText)); } private static void SetInitialMousePosition(Vector2 selectedPosition, RadialBase radial) { //IL_005c: 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_007a: 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_007d: 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_0074: Unknown result type (might be due to invalid IL or missing references) float num = ((MyLittleUI.modEnabled.Value && MyLittleUI.radialMenuInitialCursorDistance != null) ? Mathf.Clamp(MyLittleUI.radialMenuInitialCursorDistance.Value, 0f, 2f) : 1f); Vector2 val = ((Object.op_Implicit((Object)(object)radial) && Object.op_Implicit((Object)(object)radial.m_elementInfo) && Object.op_Implicit((Object)(object)radial.m_elementInfo.m_title)) ? Vector2.op_Implicit(((TMP_Text)radial.m_elementInfo.m_title).transform.position) : selectedPosition); ZInput.SetMousePosition(Vector2.LerpUnclamped(val, selectedPosition, num)); } private static IEnumerable<MethodInfo> GetArmorStandHoverMethods() { IEnumerable<Type> nestedTypes = typeof(ArmorStand).GetNestedTypes(BindingFlags.Public | BindingFlags.NonPublic); return from method in typeof(ArmorStand).GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic).Concat(nestedTypes.SelectMany((Type type) => type.GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic))) where method.Name.IndexOf("<Awake>", StringComparison.Ordinal) >= 0 && method.ReturnType == typeof(string) && method.GetParameters().Length == 0 select method; } private static IEnumerable<MethodBase> GetKnownHoverMethods() { MethodBase[] source = new MethodBase[8] { AccessTools.Method(typeof(Fireplace), "GetHoverText", (Type[])null, (Type[])null), AccessTools.Method(typeof(CookingStation), "GetHoverText", (Type[])null, (Type[])null), AccessTools.Method(typeof(CookingStation), "OnHoverFuelSwitch", (Type[])null, (Type[])null), AccessTools.Method(typeof(Smelter), "OnHoverAddFuel", (Type[])null, (Type[])null), AccessTools.Method(typeof(Smelter), "OnHoverAddOre", (Type[])null, (Type[])null), AccessTools.Method(typeof(ShieldGenerator), "OnHoverAddFuel", (Type[])null, (Type[])null), AccessTools.Method(typeof(Turret), "GetHoverText", (Type[])null, (Type[])null), AccessTools.Method(typeof(Switch), "GetHoverText", (Type[])null, (Type[])null) }; return source.Where((MethodBase method) => method != null).Concat(GetArmorStandHoverMethods()).Concat(RadialMenuItemReceiver.GetHoverTextMethods()) .Distinct(); } private static IEnumerable<CodeInstruction> ReplaceLocalizationCall(IEnumerable<CodeInstruction> instructions) { foreach (CodeInstruction instruction in instructions) { if (LocalizeMethod != null && LocalizeHoverTextMethod != null && CodeInstructionExtensions.Calls(instruction, LocalizeMethod)) { instruction.opcode = OpCodes.Call; instruction.operand = LocalizeHoverTextMethod; } yield return instruction; } } internal static void ApplyHoverTextWidth(Hud hud = null) { //IL_0054: Unknown result type (might be due to invalid IL or missing references) //IL_0059: Unknown result type (might be due to invalid IL or missing references) if (hud == null) { hud = Hud.instance; } if (Object.op_Implicit((Object)(object)hud) && Object.op_Implicit((Object)(object)hud.m_hoverName) && MyLittleUI.hoverTextWidth != null) { RectTransform rectTransform = ((TMP_Text)hud.m_hoverName).rectTransform; if ((Object)(object)hoverTextTransform != (Object)(object)rectTransform) { hoverTextTransform = rectTransform; Rect rect = rectTransform.rect; originalHoverTextWidth = ((Rect)(ref rect)).width; } rectTransform.SetSizeWithCurrentAnchors((Axis)0, MyLittleUI.modEnabled.Value ? MyLittleUI.hoverTextWidth.Value : originalHoverTextWidth); } } } internal sealed class RadialMenuItemReceiver : MonoBehaviour, IHasHoverMenu { private sealed class ReceiverDefinition { internal Type TargetType { get; } internal Func<bool> Enabled { get; } internal Func<Component, Player, IEnumerable<string>> GetItems { get; } internal Func<Component, Player, bool, bool> CanUseItems { get; } internal MethodBase[] HoverTextMethods { get; } internal bool OverrideTargetHoverMenu { get; } internal ReceiverDefinition(Type targetType, Func<bool> enabled, Func<Component, Player, IEnumerable<string>> getItems, Func<Component, Player, bool, bool> canUseItems, MethodBase[] hoverTextMethods, bool overrideTargetHoverMenu) { TargetType = targetType; Enabled = enabled; GetItems = getItems; CanUseItems = canUseItems; HoverTextMethods = hoverTextMethods; OverrideTargetHoverMenu = overrideTargetHoverMenu; } } [HarmonyPatch] private static class RegisteredReceiver_Initialize_AttachAdapter { private static IEnumerable<MethodBase> TargetMethods() { return GetTargetInitializationMethods(); } [HarmonyPriority(0)] private static void Postfix(object __instance) { Component val = (Component)((__instance is Component) ? __instance : null); if (val != null) { TryAttach(val); } } } private static readonly ReceiverDefinition[] Definitions = new ReceiverDefinition[2] { Create<Fermenter>((Func<bool>)(() => MyLittleUI.radialMenuFermenterItemSelection?.Value ?? false), (Func<Fermenter, Player, IEnumerable<string>>)GetFermenterItems, (Func<Fermenter, Player, bool, bool>)CanUseFermenterItems, new MethodBase[1] { AccessTools.Method(typeof(Fermenter), "GetHoverText", (Type[])null, (Type[])null) }), Create<ShieldGenerator>((Func<bool>)(() => MyLittleUI.radialMenuShieldGeneratorItemSelection?.Value ?? false), (Func<ShieldGenerator, Player, IEnumerable<string>>)GetShieldGeneratorItems, (Func<ShieldGenerator, Player, bool, bool>)CanUseShieldGeneratorItems, overrideTargetHoverMenu: true, new MethodBase[1] { AccessTools.Method(typeof(ShieldGenerator), "OnHoverAddFuel", (Type[])null, (Type[])null) }) }; private static readonly HashSet<Type> ErrorTypes = new HashSet<Type>(); private Component target; private ReceiverDefinition definition; internal bool IsActive { get { int result; if (Object.op_Implicit((Object)(object)target) && definition != null) { ConfigEntry<bool> modEnabled = MyLittleUI.modEnabled; if (modEnabled != null && modEnabled.Value) { result = (definition.Enabled() ? 1 : 0); goto IL_003b; } } result = 0; goto IL_003b; IL_003b: return (byte)result != 0; } } private static ReceiverDefinition Create<T>(Func<bool> enabled, Func<T, Player, IEnumerable<string>> getItems, Func<T, Player, bool, bool> canUseItems, params MethodBase[] hoverTextMethods) where T : Component { return Create(enabled, getItems, canUseItems, overrideTargetHoverMenu: false, hoverTextMethods); } private static ReceiverDefinition Create<T>(Func<bool> enabled, Func<T, Player, IEnumerable<string>> getItems, Func<T, Player, bool, bool> canUseItems, bool overrideTargetHoverMenu, params MethodBase[] hoverTextMethods) where T : Component { return new ReceiverDefinition(typeof(T), enabled, (Component component, Player player) => getItems((T)(object)component, player), (Component component, Player player, bool sendErrorMessage) => canUseItems((T)(object)component, player, sendErrorMessage), hoverTextMethods?.Where((MethodBase method) => method != null).ToArray() ?? Array.Empty<MethodBase>(), overrideTargetHoverMenu); } internal static IEnumerable<MethodBase> GetHoverTextMethods() { return Definitions.SelectMany((ReceiverDefinition receiver) => receiver.HoverTextMethods).Distinct(); } private static IEnumerable<MethodBase> GetTargetInitializationMethods() { return (from receiver in Definitions select GetLifecycleMethod(receiver.TargetType, "Awake") ?? GetLifecycleMethod(receiver.TargetType, "Start") into method where method != null select method).Distinct(); } private static MethodInfo GetLifecycleMethod(Type type, string name) { return type.GetMethod(name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, Type.EmptyTypes, null); } private static void TryAttach(Component targetComponent) { if (!Object.op_Implicit((Object)(object)targetComponent)) { return; } ReceiverDefinition targetDefinition = Definitions.FirstOrDefault((ReceiverDefinition receiver) => receiver.TargetType.IsInstanceOfType(targetComponent)); if (targetDefinition != null) { MonoBehaviour[] components = targetComponent.GetComponents<MonoBehaviour>(); if (!components.Any((MonoBehaviour component) => !(component is RadialMenuItemReceiver) && (component is IHasHoverMenu || component is IHasHoverMenuExtended) && (!targetDefinition.OverrideTargetHoverMenu || (Object)(object)component != (Object)(object)targetComponent))) { RadialMenuItemReceiver radialMenuItemReceiver = components.OfType<RadialMenuItemReceiver>().FirstOrDefault() ?? targetComponent.gameObject.AddComponent<RadialMenuItemReceiver>(); radialMenuItemReceiver.target = targetComponent; radialMenuItemReceiver.definition = targetDefinition; } } } public bool TryGetItems(Player player, out List<string> items) { return TryGetItems(player, sendErrorMessage: true, out items); } internal bool TryGetItems(Player player, bool sendErrorMessage, out List<string> items) { items = new List<string>(); if (!IsActive) { return false; } try { if (!definition.CanUseItems(target, player, sendErrorMessage)) { return true; } items = (definition.GetItems(target, player) ?? Enumerable.Empty<string>()).Where((string item) => !string.IsNullOrWhiteSpace(item)).Distinct().ToList(); return true; } catch (Exception exception) { LogFailure(exception); return false; } } public bool CanUseItems(Player player, bool sendErrorMessage = true) { if (!IsActive) { return false; } try { return definition.CanUseItems(target, player, sendErrorMessage); } catch (Exception exception) { LogFailure(exception); return false; } } private void LogFailure(Exception exception) { Type type = defin