Decompiled source of WeaponRename v0.1.2

plugins/WeaponRename.dll

Decompiled 9 hours ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using System.Security.Permissions;
using BepInEx;
using BepInEx.Configuration;
using HarmonyLib;
using Jotunn;
using Jotunn.Extensions;
using Jotunn.Managers;
using Jotunn.Utils;
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: AssemblyTitle("WeaponRename")]
[assembly: AssemblyDescription("Rename Valheim weapons with a reset-to-default action.")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("yunc")]
[assembly: AssemblyProduct("WeaponRename")]
[assembly: AssemblyCopyright("Copyright © 2026")]
[assembly: AssemblyTrademark("")]
[assembly: ComVisible(false)]
[assembly: Guid("a7f4c2e1-8b3d-4e9a-a1c6-0d5f8e2b7a44")]
[assembly: AssemblyFileVersion("0.1.2")]
[assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("0.1.2.0")]
namespace WeaponRename
{
	internal static class EquippedNameSync
	{
		internal const string ZdoKey = "WeaponRename.Equipped";

		internal static void PublishLocal()
		{
			Player localPlayer = Player.m_localPlayer;
			if ((Object)(object)localPlayer == (Object)null || (Object)(object)((Character)localPlayer).m_nview == (Object)null || !((Character)localPlayer).m_nview.IsValid() || !((Character)localPlayer).m_nview.IsOwner())
			{
				return;
			}
			ZDO zDO = ((Character)localPlayer).m_nview.GetZDO();
			if (zDO != null)
			{
				string displayName = GetDisplayName(localPlayer);
				if (!(zDO.GetString("WeaponRename.Equipped", string.Empty) == displayName))
				{
					zDO.Set("WeaponRename.Equipped", displayName);
				}
			}
		}

		internal static void OnItemChanged(ItemData item)
		{
			Player localPlayer = Player.m_localPlayer;
			if (!((Object)(object)localPlayer == (Object)null) && item != null && (((Humanoid)localPlayer).IsItemEquiped(item) || ((Humanoid)localPlayer).GetCurrentWeapon() == item))
			{
				PublishLocal();
			}
		}

		internal static string ReadDisplayName(Player player)
		{
			if ((Object)(object)player == (Object)null)
			{
				return string.Empty;
			}
			if ((Object)(object)((Character)player).m_nview != (Object)null && ((Character)player).m_nview.IsValid())
			{
				ZDO zDO = ((Character)player).m_nview.GetZDO();
				if (zDO != null)
				{
					string text = zDO.GetString("WeaponRename.Equipped", string.Empty);
					if (!string.IsNullOrEmpty(text))
					{
						return text;
					}
				}
			}
			return GetDisplayName(player);
		}

		private static string GetDisplayName(Player player)
		{
			return RenameData.GetDisplayName(((Humanoid)player).GetCurrentWeapon(), localize: true);
		}
	}
	[BepInPlugin("com.yunc.weaponrename", "WeaponRename", "0.1.2")]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[NetworkCompatibility(/*Could not decode attribute arguments.*/)]
	internal class Plugin : BaseUnityPlugin
	{
		public const string PluginGUID = "com.yunc.weaponrename";

		public const string PluginName = "WeaponRename";

		public const string PluginVersion = "0.1.2";

		private readonly Harmony harmony = new Harmony("com.yunc.weaponrename");

		internal static Plugin Instance { get; private set; }

		private void Awake()
		{
			Instance = this;
			PluginConfig.Bind(((BaseUnityPlugin)this).Config);
			GUIManager.OnCustomGUIAvailable += RenameUI.OnCustomGuiAvailable;
			harmony.PatchAll();
			Logger.LogInfo((object)"WeaponRename 0.1.2 loaded");
		}

		private void Update()
		{
			if (RenameUI.IsOpen && (ZInput.GetButtonDown("Cancel") || Input.GetKeyDown((KeyCode)27)))
			{
				RenameUI.Close();
			}
		}

		private void OnDestroy()
		{
			GUIManager.OnCustomGUIAvailable -= RenameUI.OnCustomGuiAvailable;
			harmony.UnpatchSelf();
		}
	}
	internal static class PluginConfig
	{
		internal static ConfigEntry<bool> RenameEnabled;

		internal static ConfigEntry<bool> WeaponsOnly;

		internal static ConfigEntry<int> NameCharacterLimit;

		internal static ConfigEntry<KeyboardShortcut> MenuModifier;

		internal static ConfigEntry<bool> DarwinAwardsShowWeapon;

		internal static void Bind(ConfigFile config)
		{
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			RenameEnabled = ConfigFileExtensions.BindConfig<bool>(config, "Server", "RenameEnabled", true, "When on, players may rename weapons from the inventory action panel.", true, (int?)null, (AcceptableValueBase)null, (Action<ConfigEntryBase>)null, (ConfigurationManagerAttributes)null);
			WeaponsOnly = ConfigFileExtensions.BindConfig<bool>(config, "Server", "WeaponsOnly", true, "When on, only listed combat gear can be renamed: melee (axes, clubs, swords, spears, polearms, knives, fists, shields), bows, crossbows, elemental and blood magic, and ammo (arrows, bolts, missiles, bombs, blob bombs). Pickaxes, tools, armor, and food are excluded. Turn off to allow any item.", true, (int?)null, (AcceptableValueBase)null, (Action<ConfigEntryBase>)null, (ConfigurationManagerAttributes)null);
			AcceptableValueBase val = (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 80);
			NameCharacterLimit = ConfigFileExtensions.BindConfig<int>(config, "Server", "NameCharacterLimit", 40, "Maximum length of a custom weapon name.", true, (int?)null, val, (Action<ConfigEntryBase>)null, (ConfigurationManagerAttributes)null);
			MenuModifier = ConfigFileExtensions.BindConfig<KeyboardShortcut>(config, "UI", "MenuModifier", new KeyboardShortcut((KeyCode)304, Array.Empty<KeyCode>()), "Hold this key and right-click a weapon in inventory to open the rename panel. Not synced so it will not fight other mods on each client.", false, (int?)null, (AcceptableValueBase)null, (Action<ConfigEntryBase>)null, (ConfigurationManagerAttributes)null);
			DarwinAwardsShowWeapon = ConfigFileExtensions.BindConfig<bool>(config, "Compatibility", "DarwinAwardsShowWeapon", true, "When DarwinAwards is installed, replace {weapon} in PvP death lines with the killing weapon's display name (custom if set). Lines without {weapon} are left unchanged.", true, (int?)null, (AcceptableValueBase)null, (Action<ConfigEntryBase>)null, (ConfigurationManagerAttributes)null);
		}

		internal static bool IsModifierHeld()
		{
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			KeyboardShortcut value = MenuModifier.Value;
			if ((int)((KeyboardShortcut)(ref value)).MainKey == 0)
			{
				return true;
			}
			return ((KeyboardShortcut)(ref value)).IsPressed();
		}
	}
	internal static class RenameData
	{
		internal const string CustomNameKey = "WeaponRename.Name";

		internal static bool TryGetCustomName(ItemData item, out string name)
		{
			name = null;
			if (item?.m_customData == null)
			{
				return false;
			}
			if (!item.m_customData.TryGetValue("WeaponRename.Name", out var value))
			{
				return false;
			}
			if (string.IsNullOrEmpty(value))
			{
				return false;
			}
			name = value;
			return true;
		}

		internal static string GetDisplayName(ItemData item, bool localize)
		{
			if (item?.m_shared == null)
			{
				return string.Empty;
			}
			if (TryGetCustomName(item, out var name))
			{
				return name;
			}
			string text = item.m_shared.m_name ?? string.Empty;
			if (!localize || Localization.instance == null)
			{
				return text;
			}
			return Localization.instance.Localize(text);
		}

		internal static string GetVanillaDisplayName(ItemData item)
		{
			if (item?.m_shared == null)
			{
				return string.Empty;
			}
			string text = item.m_shared.m_name ?? string.Empty;
			if (Localization.instance == null)
			{
				return text;
			}
			return Localization.instance.Localize(text);
		}

		internal static bool SetCustomName(ItemData item, string name)
		{
			if (item == null)
			{
				return false;
			}
			if (item.m_customData == null)
			{
				item.m_customData = new Dictionary<string, string>();
			}
			string text = name?.Trim() ?? string.Empty;
			if (string.IsNullOrEmpty(text))
			{
				return ClearCustomName(item);
			}
			int value = PluginConfig.NameCharacterLimit.Value;
			if (text.Length > value)
			{
				text = text.Substring(0, value);
			}
			item.m_customData["WeaponRename.Name"] = text;
			MarkDirty(item);
			EquippedNameSync.OnItemChanged(item);
			return true;
		}

		internal static bool ClearCustomName(ItemData item)
		{
			if (item?.m_customData == null)
			{
				return false;
			}
			bool num = item.m_customData.Remove("WeaponRename.Name");
			if (num)
			{
				MarkDirty(item);
				EquippedNameSync.OnItemChanged(item);
			}
			return num;
		}

		internal static void MarkDirty(ItemData item)
		{
			if (item == null)
			{
				return;
			}
			Player localPlayer = Player.m_localPlayer;
			if ((Object)(object)localPlayer != (Object)null)
			{
				Inventory inventory = ((Humanoid)localPlayer).GetInventory();
				if (inventory != null && inventory.ContainsItem(item))
				{
					inventory.Changed();
				}
			}
			InventoryGui instance = InventoryGui.instance;
			Container val = (((Object)(object)instance != (Object)null) ? instance.m_currentContainer : null);
			if ((Object)(object)val != (Object)null && val.m_inventory != null && val.m_inventory.ContainsItem(item))
			{
				val.m_inventory.Changed();
			}
		}
	}
	internal static class RenameUI
	{
		private const float PanelWidth = 380f;

		private const float PanelHeight = 200f;

		private static GameObject panel;

		private static InputField nameInput;

		private static ItemData currentItem;

		private static bool inputBlocked;

		internal static bool IsOpen
		{
			get
			{
				if ((Object)(object)panel != (Object)null)
				{
					return panel.activeSelf;
				}
				return false;
			}
		}

		internal static void OnCustomGuiAvailable()
		{
			CreatePanel();
		}

		internal static void Open(ItemData item)
		{
			if (item == null)
			{
				return;
			}
			if (GUIManager.Instance == null || (Object)(object)GUIManager.CustomGUIFront == (Object)null)
			{
				Logger.LogWarning((object)"Rename UI is not ready yet.");
				return;
			}
			if ((Object)(object)panel == (Object)null)
			{
				CreatePanel();
			}
			if (!((Object)(object)panel == (Object)null) && !((Object)(object)nameInput == (Object)null))
			{
				currentItem = item;
				nameInput.characterLimit = PluginConfig.NameCharacterLimit.Value;
				nameInput.text = RenameData.GetDisplayName(item, localize: true);
				panel.SetActive(true);
				panel.transform.SetAsLastSibling();
				nameInput.ActivateInputField();
				((Selectable)nameInput).Select();
				SetInputBlocked(blocked: true);
			}
		}

		internal static void Close()
		{
			if ((Object)(object)panel != (Object)null)
			{
				panel.SetActive(false);
			}
			currentItem = null;
			SetInputBlocked(blocked: false);
		}

		private static void CreatePanel()
		{
			//IL_0053: Unknown result type (might be due to invalid IL or missing references)
			//IL_0062: Unknown result type (might be due to invalid IL or missing references)
			//IL_0067: Unknown result type (might be due to invalid IL or missing references)
			//IL_00aa: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00de: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e4: 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_0122: Unknown result type (might be due to invalid IL or missing references)
			//IL_0131: Unknown result type (might be due to invalid IL or missing references)
			//IL_0166: Unknown result type (might be due to invalid IL or missing references)
			//IL_0181: Unknown result type (might be due to invalid IL or missing references)
			//IL_018b: Expected O, but got Unknown
			//IL_019a: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b5: Unknown result type (might be due to invalid IL or missing references)
			//IL_01bf: Expected O, but got Unknown
			//IL_01ce: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f3: Expected O, but got Unknown
			if (GUIManager.Instance != null && !((Object)(object)GUIManager.CustomGUIFront == (Object)null))
			{
				if ((Object)(object)panel != (Object)null)
				{
					Object.Destroy((Object)(object)panel);
					panel = null;
					nameInput = null;
				}
				Transform transform = GUIManager.CustomGUIFront.transform;
				panel = GUIManager.Instance.CreateWoodpanel(transform, new Vector2(0.5f, 0.5f), new Vector2(0.5f, 0.5f), Vector2.zero, 380f, 200f, false);
				panel.SetActive(false);
				GUIManager.Instance.CreateText("Rename weapon", panel.transform, new Vector2(0.5f, 1f), new Vector2(0.5f, 1f), new Vector2(0f, -36f), GUIManager.Instance.AveriaSerifBold, 20, GUIManager.Instance.ValheimOrange, true, Color.black, 340f, 36f, false);
				nameInput = GUIManager.Instance.CreateInputField(panel.transform, new Vector2(0.5f, 0.5f), new Vector2(0.5f, 0.5f), new Vector2(0f, 10f), (ContentType)0, "Weapon name...", 16, 320f, 32f).GetComponent<InputField>();
				((UnityEvent)CreateFooterButton("Rename", new Vector2(-110f, 32f), 100f).onClick).AddListener(new UnityAction(ApplyRename));
				((UnityEvent)CreateFooterButton("Reset", new Vector2(0f, 32f), 100f).onClick).AddListener(new UnityAction(ResetName));
				((UnityEvent)CreateFooterButton("Cancel", new Vector2(110f, 32f), 100f).onClick).AddListener(new UnityAction(Close));
			}
		}

		private static Button CreateFooterButton(string label, Vector2 anchoredPosition, float width)
		{
			//IL_001a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0029: Unknown result type (might be due to invalid IL or missing references)
			//IL_002e: Unknown result type (might be due to invalid IL or missing references)
			return GUIManager.Instance.CreateButton(label, panel.transform, new Vector2(0.5f, 0f), new Vector2(0.5f, 0f), anchoredPosition, width, 32f).GetComponent<Button>();
		}

		private static void ApplyRename()
		{
			if (currentItem == null)
			{
				Close();
				return;
			}
			if (!IsItemStillAvailable(currentItem))
			{
				Message("That weapon is no longer in this inventory.");
				Close();
				return;
			}
			string text = (((Object)(object)nameInput != (Object)null) ? nameInput.text.Trim() : string.Empty);
			if (string.IsNullOrEmpty(text))
			{
				Message("Enter a name, or use Reset to restore the default.");
				return;
			}
			RenameData.SetCustomName(currentItem, text);
			Close();
		}

		private static void ResetName()
		{
			if (currentItem == null)
			{
				Close();
			}
			else if (!IsItemStillAvailable(currentItem))
			{
				Message("That weapon is no longer in this inventory.");
				Close();
			}
			else
			{
				RenameData.ClearCustomName(currentItem);
				Close();
			}
		}

		private static bool IsItemStillAvailable(ItemData item)
		{
			Player localPlayer = Player.m_localPlayer;
			if ((Object)(object)localPlayer != (Object)null)
			{
				Inventory inventory = ((Humanoid)localPlayer).GetInventory();
				if (inventory != null && inventory.ContainsItem(item))
				{
					return true;
				}
			}
			InventoryGui instance = InventoryGui.instance;
			Container val = (((Object)(object)instance != (Object)null) ? instance.m_currentContainer : null);
			if ((Object)(object)val != (Object)null && val.m_inventory != null)
			{
				return val.m_inventory.ContainsItem(item);
			}
			return false;
		}

		private static void Message(string text)
		{
			Player localPlayer = Player.m_localPlayer;
			if ((Object)(object)localPlayer != (Object)null)
			{
				((Character)localPlayer).Message((MessageType)2, text, 0, (Sprite)null);
			}
		}

		private static void SetInputBlocked(bool blocked)
		{
			if (blocked != inputBlocked)
			{
				GUIManager.BlockInput(blocked);
				inputBlocked = blocked;
			}
		}
	}
	internal static class WeaponFilter
	{
		internal static bool CanRename(ItemData item)
		{
			if (item?.m_shared == null)
			{
				return false;
			}
			if (!PluginConfig.RenameEnabled.Value)
			{
				return false;
			}
			if (!PluginConfig.WeaponsOnly.Value)
			{
				return true;
			}
			return IsWeapon(item);
		}

		internal static bool IsWeapon(ItemData item)
		{
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_001c: Invalid comparison between Unknown and I4
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			//IL_002e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Invalid comparison between Unknown and I4
			//IL_0033: Unknown result type (might be due to invalid IL or missing references)
			//IL_0036: Invalid comparison between Unknown and I4
			if (item?.m_shared == null)
			{
				return false;
			}
			if ((int)item.m_shared.m_itemType == 5)
			{
				return true;
			}
			SkillType skillType = item.m_shared.m_skillType;
			if (skillType - 1 <= 10 || (int)skillType == 14)
			{
				return true;
			}
			return IsAmmoOrThrowable(item);
		}

		private static bool IsAmmoOrThrowable(ItemData item)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			//IL_000f: Invalid comparison between Unknown and I4
			//IL_0011: Unknown result type (might be due to invalid IL or missing references)
			//IL_0014: Invalid comparison between Unknown and I4
			//IL_001d: Unknown result type (might be due to invalid IL or missing references)
			//IL_001f: Invalid comparison between Unknown and I4
			ItemType itemType = item.m_shared.m_itemType;
			if ((int)itemType == 9 || (int)itemType == 23)
			{
				return IsListedAmmo(item);
			}
			if ((int)itemType == 2)
			{
				return IsBomb(item);
			}
			return false;
		}

		private static bool IsListedAmmo(ItemData item)
		{
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0054: Invalid comparison between Unknown and I4
			//IL_005c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0063: Invalid comparison between Unknown and I4
			if (IsBomb(item))
			{
				return true;
			}
			string value = item.m_shared.m_ammoType ?? string.Empty;
			if (ContainsIgnoreCase(value, "arrow") || ContainsIgnoreCase(value, "bolt") || ContainsIgnoreCase(value, "missile"))
			{
				return true;
			}
			if ((int)item.m_shared.m_skillType == 8 || (int)item.m_shared.m_skillType == 14)
			{
				return true;
			}
			return NameLooksLikeAmmo(item);
		}

		private static bool IsBomb(ItemData item)
		{
			if (!NameContains(item, "bomb") && !NameContains(item, "ooze"))
			{
				return NameContains(item, "blob");
			}
			return true;
		}

		private static bool NameLooksLikeAmmo(ItemData item)
		{
			if (!NameContains(item, "arrow") && !NameContains(item, "bolt"))
			{
				return NameContains(item, "missile");
			}
			return true;
		}

		private static bool NameContains(ItemData item, string token)
		{
			return ContainsIgnoreCase(item.m_shared.m_name, token);
		}

		private static bool ContainsIgnoreCase(string value, string token)
		{
			if (!string.IsNullOrEmpty(value))
			{
				return value.IndexOf(token, StringComparison.OrdinalIgnoreCase) >= 0;
			}
			return false;
		}
	}
}
namespace WeaponRename.Patches
{
	internal static class DarwinAwardsCompat
	{
		[HarmonyPatch(typeof(Character), "ApplyDamage")]
		private static class SaveHitPatch
		{
			private static void Prefix(HitData hit)
			{
				lastHit = hit;
			}

			private static void Finalizer()
			{
				lastHit = null;
			}
		}

		[HarmonyPatch]
		private static class DeathRpcPatch
		{
			private static IEnumerable<MethodBase> TargetMethods()
			{
				foreach (MethodInfo declaredMethod in AccessTools.GetDeclaredMethods(typeof(ZRoutedRpc)))
				{
					if (declaredMethod.Name == "InvokeRoutedRPC")
					{
						yield return declaredMethod;
					}
				}
			}

			private static void Prefix(object[] __args)
			{
				TryRewriteDeathRpc(__args);
			}
		}

		internal const string DeathRpcName = "DarwinAwards IDied";

		internal const string WeaponToken = "{weapon}";

		private static HitData lastHit;

		private static void TryRewriteDeathRpc(object[] args)
		{
			if (args == null || !PluginConfig.DarwinAwardsShowWeapon.Value)
			{
				return;
			}
			for (int i = 0; i < args.Length; i++)
			{
				if (args[i] is string text && text == "DarwinAwards IDied")
				{
					RewriteAfterName(args, i);
					break;
				}
			}
		}

		private static void RewriteAfterName(object[] args, int nameIndex)
		{
			if (nameIndex + 2 < args.Length && args[nameIndex + 2] is string text)
			{
				args[nameIndex + 2] = ApplyWeapon(text);
			}
			else if (nameIndex + 1 < args.Length && args[nameIndex + 1] is object[] array && array.Length >= 2 && array[1] is string text2)
			{
				array[1] = ApplyWeapon(text2);
			}
		}

		internal static string ApplyWeapon(string text)
		{
			if (string.IsNullOrEmpty(text))
			{
				return text;
			}
			Player val = (Player)((lastHit != null) ? /*isinst with value type is only supported in some contexts*/: null);
			if ((Object)(object)val == (Object)null)
			{
				return text;
			}
			string text2 = EquippedNameSync.ReadDisplayName(val);
			if (string.IsNullOrEmpty(text2))
			{
				return text;
			}
			if (!text.Contains("{weapon}"))
			{
				return text;
			}
			return text.Replace("{weapon}", text2);
		}
	}
	internal static class DisplayNamePatches
	{
		[HarmonyPatch(typeof(ItemDrop), "GetHoverName")]
		private static class ItemDropGetHoverNamePatch
		{
			private static void Postfix(ItemDrop __instance, ref string __result)
			{
				ApplyItemName(__instance?.m_itemData, ref __result);
			}
		}

		[HarmonyPatch(typeof(ItemDrop), "GetHoverText")]
		private static class ItemDropGetHoverTextPatch
		{
			private static void Postfix(ItemDrop __instance, ref string __result)
			{
				ReplaceVanillaName(__instance?.m_itemData, ref __result);
			}
		}

		[HarmonyPatch(typeof(ItemStand), "GetHoverText")]
		private static class ItemStandGetHoverTextPatch
		{
			private static void Postfix(ItemStand __instance, ref string __result)
			{
				ReplaceVanillaName(LoadStandItem(__instance), ref __result);
			}
		}

		[HarmonyPatch(typeof(InventoryGrid), "CreateItemTooltip")]
		private static class InventoryGridCreateItemTooltipPatch
		{
			private static bool Prefix(InventoryGrid __instance, ItemData item, UITooltip tooltip)
			{
				//IL_0027: Unknown result type (might be due to invalid IL or missing references)
				//IL_002d: Unknown result type (might be due to invalid IL or missing references)
				if (item == null || (Object)(object)tooltip == (Object)null)
				{
					return true;
				}
				string displayName = RenameData.GetDisplayName(item, localize: false);
				tooltip.Set(displayName, item.GetTooltip(-1), __instance.m_tooltipAnchor, default(Vector2));
				return false;
			}
		}

		[HarmonyPatch(typeof(ItemData), "GetTooltip", new Type[] { typeof(int) })]
		private static class ItemDataGetTooltipPatch
		{
			private static void Postfix(ItemData __instance, ref string __result)
			{
				AppendRenameHint(__instance, ref __result);
			}
		}

		private static void ApplyItemName(ItemData item, ref string result)
		{
			if (RenameData.TryGetCustomName(item, out var name))
			{
				result = name;
			}
		}

		private static void ReplaceVanillaName(ItemData item, ref string result)
		{
			if (item != null && !string.IsNullOrEmpty(result) && RenameData.TryGetCustomName(item, out var name))
			{
				string text = item.m_shared?.m_name;
				if (!string.IsNullOrEmpty(text) && result.Contains(text))
				{
					result = result.Replace(text, name);
				}
				string vanillaDisplayName = RenameData.GetVanillaDisplayName(item);
				if (!string.IsNullOrEmpty(vanillaDisplayName) && vanillaDisplayName != name && result.Contains(vanillaDisplayName))
				{
					result = result.Replace(vanillaDisplayName, name);
				}
			}
		}

		private static void AppendRenameHint(ItemData item, ref string result)
		{
			if (WeaponFilter.CanRename(item) && !string.IsNullOrEmpty(result))
			{
				string text = FormatRenameHint();
				if (!result.Contains(text))
				{
					result = result + "\n\n<color=yellow>" + text + "</color>";
				}
			}
		}

		private unsafe static string FormatRenameHint()
		{
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_001a: 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)
			KeyboardShortcut value = PluginConfig.MenuModifier.Value;
			if ((int)((KeyboardShortcut)(ref value)).MainKey == 0)
			{
				return "Right-click to rename";
			}
			KeyboardShortcut val = value;
			return ((object)(*(KeyboardShortcut*)(&val))/*cast due to .constrained prefix*/).ToString() + " + Right-click to rename";
		}

		private static ItemData LoadStandItem(ItemStand stand)
		{
			if ((Object)(object)stand == (Object)null || !stand.HaveAttachment() || (Object)(object)ObjectDB.instance == (Object)null)
			{
				return null;
			}
			string attachedItem = stand.GetAttachedItem();
			if (string.IsNullOrEmpty(attachedItem))
			{
				return null;
			}
			GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(attachedItem);
			if ((Object)(object)itemPrefab == (Object)null)
			{
				return null;
			}
			ItemDrop component = itemPrefab.GetComponent<ItemDrop>();
			if ((Object)(object)component == (Object)null)
			{
				return null;
			}
			ItemData val = component.m_itemData.Clone();
			if ((Object)(object)stand.m_nview != (Object)null && stand.m_nview.IsValid())
			{
				ItemDrop.LoadFromZDO(val, stand.m_nview.GetZDO());
			}
			return val;
		}
	}
	internal static class EquippedNameSyncPatches
	{
		[HarmonyPatch(typeof(Humanoid), "EquipItem")]
		private static class EquipItemPatch
		{
			private static void Postfix(Humanoid __instance, bool __result)
			{
				if (__result && (Object)(object)__instance == (Object)(object)Player.m_localPlayer)
				{
					EquippedNameSync.PublishLocal();
				}
			}
		}

		[HarmonyPatch(typeof(Humanoid), "UnequipItem")]
		private static class UnequipItemPatch
		{
			private static void Postfix(Humanoid __instance)
			{
				if ((Object)(object)__instance == (Object)(object)Player.m_localPlayer)
				{
					EquippedNameSync.PublishLocal();
				}
			}
		}

		[HarmonyPatch(typeof(Player), "OnSpawned")]
		private static class PlayerOnSpawnedPatch
		{
			private static void Postfix(Player __instance)
			{
				if ((Object)(object)__instance == (Object)(object)Player.m_localPlayer)
				{
					EquippedNameSync.PublishLocal();
				}
			}
		}

		[HarmonyPatch(typeof(Character), "Damage")]
		private static class PublishOnAttackPatch
		{
			private static void Prefix(Character __instance, HitData hit)
			{
				if (__instance is Player && hit != null && (Object)(object)hit.GetAttacker() == (Object)(object)Player.m_localPlayer)
				{
					EquippedNameSync.PublishLocal();
				}
			}
		}
	}
	[HarmonyPatch(typeof(InventoryGui), "OnRightClickItem")]
	internal static class InventoryClickPatch
	{
		private static bool Prefix(InventoryGrid grid, ItemData item)
		{
			if (item == null || (Object)(object)grid == (Object)null)
			{
				return true;
			}
			if (!PluginConfig.IsModifierHeld())
			{
				return true;
			}
			if (!WeaponFilter.CanRename(item))
			{
				return true;
			}
			RenameUI.Open(item);
			return false;
		}
	}
}