Decompiled source of TrophyTooltip v0.1.2

TrophyTooltip.dll

Decompiled a day ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using System.Text.RegularExpressions;
using BepInEx;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyCompany("TrophyTooltip")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("TrophyTooltip")]
[assembly: AssemblyTitle("TrophyTooltip")]
[assembly: AssemblyVersion("1.0.0.0")]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
	internal sealed class RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
namespace TrofeusInfo
{
	[BepInPlugin("com.vaSto.trofeusinfo", "TrofeusInfo", "0.1.2")]
	public sealed class TrofeusInfoPlugin : BaseUnityPlugin
	{
		internal const string ModGuid = "com.vaSto.trofeusinfo";

		internal const string ModName = "TrofeusInfo";

		internal const string ModVersion = "0.1.2";

		private Harmony _harmony;

		private void Awake()
		{
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_0011: Expected O, but got Unknown
			_harmony = new Harmony("com.vaSto.trofeusinfo");
			TrophyTooltip.Init((BaseUnityPlugin)(object)this, _harmony, ((BaseUnityPlugin)this).Logger);
			((BaseUnityPlugin)this).Logger.LogInfo((object)"[TrofeusInfo] carregado.");
		}

		private void OnDestroy()
		{
			Harmony harmony = _harmony;
			if (harmony != null)
			{
				harmony.UnpatchSelf();
			}
		}
	}
	internal static class TrophyTooltip
	{
		private class TrophyEntry
		{
			public string trophyDisplayName = string.Empty;

			public string creatureDisplayName = string.Empty;

			public string prefabName = string.Empty;

			public float baseHp;

			public bool isBoss;

			public DamageModifiers damageModifiers;

			public DamageType bestDamageType;

			public float bestDamageMultiplier;

			public readonly List<TrophyDropEntry> drops = new List<TrophyDropEntry>();
		}

		private class TrophyDropEntry
		{
			public string displayName = string.Empty;

			public Sprite icon;

			public int amountMin = 1;

			public int amountMax = 1;

			public float chance = 1f;

			public bool levelMultiplier;

			public bool onePerPlayer;
		}

		private sealed class TrophyHoverBridge : MonoBehaviour, IPointerEnterHandler, IEventSystemHandler, IPointerExitHandler
		{
			private TrophyEntry _entry;

			private string _tooltipText = string.Empty;

			private bool _hovering;

			internal void Bind(TrophyEntry entry)
			{
				_entry = entry;
				_tooltipText = BuildTooltipText(entry);
			}

			public void OnPointerEnter(PointerEventData eventData)
			{
				if (_entry != null)
				{
					_hovering = true;
					ShowTooltip(_entry, _tooltipText);
				}
			}

			public void OnPointerExit(PointerEventData eventData)
			{
				_hovering = false;
				HideTooltip();
			}

			private void OnDisable()
			{
				if (_hovering)
				{
					_hovering = false;
					HideTooltip();
				}
			}

			private void Update()
			{
				if (_hovering)
				{
					UpdateTooltipPosition();
				}
			}
		}

		private struct BestDamageInfo
		{
			public DamageType Type;

			public DamageModifier Modifier;

			public float Multiplier;
		}

		private static readonly Dictionary<int, TrophyEntry> TrophyBySpriteId = new Dictionary<int, TrophyEntry>();

		private static readonly List<GameObject> CreaturePrefabs = new List<GameObject>();

		private static int _lastObjectDbItemCount = -1;

		private static ManualLogSource _log;

		private static GameObject _tooltipRoot;

		private static RectTransform _tooltipRect;

		private static Text _tooltipText;

		private static RectTransform _tooltipTextRect;

		private static RectTransform _dropIconsRect;

		private static Image _bestDamageIconImage;

		private static readonly List<GameObject> _dropIconObjects = new List<GameObject>();

		private static float _dropIconsHeight;

		private static float _dropIconsPreferredWidth;

		private static Font _font;

		private static FieldInfo _hudRootField;

		private static FieldInfo _inventoryGuiTrophyListField;

		private static int _lastConfiguredGridContainerId = -1;

		private static bool _localizationResolved;

		private static MethodInfo _localizeMethod;

		private static PropertyInfo _localizationInstanceProperty;

		private static FieldInfo _localizationInstanceField;

		private static bool _damageIconsLoaded;

		private static AssetBundle _damageIconsBundle;

		private static readonly Dictionary<DamageType, Sprite> DamageIconByType = new Dictionary<DamageType, Sprite>();

		private static readonly Dictionary<string, string> EnglishTranslations = new Dictionary<string, string>();

		private static readonly Dictionary<string, string> PortugueseTranslations = new Dictionary<string, string>();

		private static bool _translationsLoaded;

		private const string BoldColor = "#98c2ed";

		private const string HeaderColor = "#FFFFFF";

		private const string ValueColor = "#FFA03D";

		private const string MutedColor = "#9A9A9A";

		internal static void Init(BaseUnityPlugin plugin, Harmony harmony, ManualLogSource log)
		{
			_log = log;
			EnsureTranslationFilesAndLoad();
			harmony.PatchAll(typeof(TrophyTooltip));
			ManualLogSource log2 = _log;
			if (log2 != null)
			{
				log2.LogInfo((object)"[TrofeusInfo][TrophyTooltip] Modulo carregado.");
			}
		}

		private static Transform ResolveHudParent(Hud hud)
		{
			if ((Object)(object)hud == (Object)null)
			{
				return null;
			}
			if (_hudRootField == null)
			{
				_hudRootField = AccessTools.Field(typeof(Hud), "m_rootObject");
			}
			object? obj = _hudRootField?.GetValue(hud);
			GameObject val = (GameObject)((obj is GameObject) ? obj : null);
			if ((Object)(object)val != (Object)null)
			{
				return val.transform;
			}
			return ((Component)hud).transform;
		}

		private static Transform ResolveTooltipParent()
		{
			if ((Object)(object)InventoryGui.instance != (Object)null)
			{
				return ((Component)InventoryGui.instance).transform;
			}
			if ((Object)(object)Hud.instance != (Object)null)
			{
				return ResolveHudParent(Hud.instance);
			}
			return null;
		}

		private static void EnsureTooltipCreated()
		{
			//IL_00ce: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d8: Expected O, but got Unknown
			//IL_0108: 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_013c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0156: Unknown result type (might be due to invalid IL or missing references)
			//IL_0181: Unknown result type (might be due to invalid IL or missing references)
			//IL_01cf: 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_01f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_01fc: Expected O, but got Unknown
			//IL_0229: Unknown result type (might be due to invalid IL or missing references)
			//IL_0240: Unknown result type (might be due to invalid IL or missing references)
			//IL_0257: Unknown result type (might be due to invalid IL or missing references)
			//IL_026e: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f2: Unknown result type (might be due to invalid IL or missing references)
			//IL_0312: Unknown result type (might be due to invalid IL or missing references)
			//IL_0319: Expected O, but got Unknown
			//IL_034c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0366: Unknown result type (might be due to invalid IL or missing references)
			//IL_0380: Unknown result type (might be due to invalid IL or missing references)
			//IL_039a: Unknown result type (might be due to invalid IL or missing references)
			//IL_03b4: Unknown result type (might be due to invalid IL or missing references)
			//IL_03c4: Unknown result type (might be due to invalid IL or missing references)
			//IL_03cb: Expected O, but got Unknown
			//IL_03f8: Unknown result type (might be due to invalid IL or missing references)
			//IL_040f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0426: Unknown result type (might be due to invalid IL or missing references)
			//IL_043d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0454: Unknown result type (might be due to invalid IL or missing references)
			Transform val = ResolveTooltipParent();
			if ((Object)(object)val == (Object)null)
			{
				return;
			}
			if ((Object)(object)_tooltipRoot != (Object)null)
			{
				if ((Object)(object)_tooltipRoot.transform.parent != (Object)(object)val)
				{
					_tooltipRoot.transform.SetParent(val, false);
				}
				return;
			}
			if ((Object)(object)_font == (Object)null)
			{
				_font = Resources.GetBuiltinResource<Font>("Arial.ttf");
				if ((Object)(object)_font == (Object)null && (Object)(object)GUI.skin != (Object)null)
				{
					_font = GUI.skin.font;
				}
			}
			if (!((Object)(object)_font == (Object)null))
			{
				_tooltipRoot = new GameObject("Arise_TrophyHpTooltip");
				_tooltipRoot.transform.SetParent(val, false);
				_tooltipRect = _tooltipRoot.AddComponent<RectTransform>();
				_tooltipRect.anchorMin = new Vector2(0f, 0f);
				_tooltipRect.anchorMax = new Vector2(0f, 0f);
				_tooltipRect.pivot = new Vector2(0f, 0f);
				_tooltipRect.sizeDelta = new Vector2(300f, 250f);
				Image val2 = _tooltipRoot.AddComponent<Image>();
				((Graphic)val2).color = new Color(0f, 0f, 0f, 0.9f);
				((Graphic)val2).raycastTarget = false;
				CanvasGroup val3 = _tooltipRoot.AddComponent<CanvasGroup>();
				val3.interactable = false;
				val3.blocksRaycasts = false;
				Outline val4 = _tooltipRoot.AddComponent<Outline>();
				((Shadow)val4).effectColor = new Color(0f, 0f, 0f, 0.9f);
				((Shadow)val4).effectDistance = new Vector2(1f, -1f);
				GameObject val5 = new GameObject("Text");
				val5.transform.SetParent(_tooltipRoot.transform, false);
				RectTransform val6 = val5.AddComponent<RectTransform>();
				val6.anchorMin = new Vector2(0f, 0f);
				val6.anchorMax = new Vector2(1f, 1f);
				val6.offsetMin = new Vector2(10f, 8f);
				val6.offsetMax = new Vector2(-10f, -8f);
				_tooltipTextRect = val6;
				_tooltipText = val5.AddComponent<Text>();
				_tooltipText.font = _font;
				_tooltipText.fontSize = 16;
				_tooltipText.alignment = (TextAnchor)0;
				_tooltipText.horizontalOverflow = (HorizontalWrapMode)0;
				_tooltipText.verticalOverflow = (VerticalWrapMode)1;
				_tooltipText.supportRichText = true;
				((Graphic)_tooltipText).color = new Color(1f, 1f, 1f, 0.98f);
				_tooltipText.text = string.Empty;
				GameObject val7 = new GameObject("DropIcons");
				val7.transform.SetParent(_tooltipRoot.transform, false);
				_dropIconsRect = val7.AddComponent<RectTransform>();
				_dropIconsRect.anchorMin = new Vector2(0f, 0f);
				_dropIconsRect.anchorMax = new Vector2(1f, 0f);
				_dropIconsRect.pivot = new Vector2(0f, 0f);
				_dropIconsRect.anchoredPosition = new Vector2(0f, 8f);
				_dropIconsRect.sizeDelta = new Vector2(0f, 0f);
				GameObject val8 = new GameObject("BestDamageIcon");
				val8.transform.SetParent(_tooltipRoot.transform, false);
				RectTransform val9 = val8.AddComponent<RectTransform>();
				val9.anchorMin = new Vector2(1f, 1f);
				val9.anchorMax = new Vector2(1f, 1f);
				val9.pivot = new Vector2(1f, 1f);
				val9.anchoredPosition = new Vector2(-10f, -10f);
				val9.sizeDelta = new Vector2(22f, 22f);
				_bestDamageIconImage = val8.AddComponent<Image>();
				_bestDamageIconImage.preserveAspect = true;
				((Graphic)_bestDamageIconImage).raycastTarget = false;
				((Behaviour)_bestDamageIconImage).enabled = false;
				_tooltipRoot.SetActive(false);
			}
		}

		private static void DestroyTooltip()
		{
			if ((Object)(object)_tooltipRoot != (Object)null)
			{
				Object.Destroy((Object)(object)_tooltipRoot);
				_tooltipRoot = null;
			}
			_tooltipRect = null;
			_tooltipText = null;
			_tooltipTextRect = null;
			_dropIconsRect = null;
			_bestDamageIconImage = null;
			_dropIconObjects.Clear();
			_dropIconsHeight = 0f;
			_dropIconsPreferredWidth = 0f;
			if ((Object)(object)_damageIconsBundle != (Object)null)
			{
				_damageIconsBundle.Unload(false);
				_damageIconsBundle = null;
			}
			DamageIconByType.Clear();
			_damageIconsLoaded = false;
		}

		private static void HideTooltip()
		{
			if ((Object)(object)_tooltipRoot != (Object)null && _tooltipRoot.activeSelf)
			{
				_tooltipRoot.SetActive(false);
			}
		}

		private static void ShowTooltip(TrophyEntry entry, string text)
		{
			EnsureTooltipCreated();
			if (!((Object)(object)_tooltipRoot == (Object)null) && !((Object)(object)_tooltipRect == (Object)null) && !((Object)(object)_tooltipText == (Object)null))
			{
				_tooltipText.text = text ?? string.Empty;
				RefreshDropIcons(entry);
				RefreshBestDamageIcon(entry);
				ResizeTooltipToContent();
				UpdateTooltipPosition();
				_tooltipRoot.transform.SetAsLastSibling();
				if (!_tooltipRoot.activeSelf)
				{
					_tooltipRoot.SetActive(true);
				}
			}
		}

		private static void ResizeTooltipToContent()
		{
			//IL_0090: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fa: Unknown result type (might be due to invalid IL or missing references)
			if (!((Object)(object)_tooltipRect == (Object)null) && !((Object)(object)_tooltipText == (Object)null) && !((Object)(object)_tooltipTextRect == (Object)null))
			{
				float num = Mathf.Max(280f, (float)Screen.width - 24f);
				float num2 = _tooltipText.preferredWidth + 20f;
				float num3 = _dropIconsPreferredWidth + 20f;
				float num4 = Mathf.Clamp(Mathf.Max(num2, num3), 280f, Mathf.Min(460f, num));
				_tooltipRect.sizeDelta = new Vector2(num4, _tooltipRect.sizeDelta.y);
				Canvas.ForceUpdateCanvases();
				LayoutRebuilder.ForceRebuildLayoutImmediate(_tooltipTextRect);
				float num5 = Mathf.Max(120f, (float)Screen.height - 24f);
				float num6 = Mathf.Clamp(_tooltipText.preferredHeight + 16f + _dropIconsHeight, 120f, num5);
				_tooltipRect.sizeDelta = new Vector2(num4, num6);
			}
		}

		private static void ClearDropIcons()
		{
			for (int i = 0; i < _dropIconObjects.Count; i++)
			{
				GameObject val = _dropIconObjects[i];
				if ((Object)(object)val != (Object)null)
				{
					Object.Destroy((Object)(object)val);
				}
			}
			_dropIconObjects.Clear();
		}

		private static void RefreshDropIcons(TrophyEntry entry)
		{
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_020d: Unknown result type (might be due to invalid IL or missing references)
			//IL_023f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c6: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cd: Expected O, but got Unknown
			//IL_00f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_010c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0123: Unknown result type (might be due to invalid IL or missing references)
			//IL_0143: Unknown result type (might be due to invalid IL or missing references)
			//IL_015a: Unknown result type (might be due to invalid IL or missing references)
			ClearDropIcons();
			_dropIconsHeight = 0f;
			_dropIconsPreferredWidth = 0f;
			if ((Object)(object)_tooltipTextRect != (Object)null)
			{
				_tooltipTextRect.offsetMin = new Vector2(10f, 8f);
			}
			if ((Object)(object)_dropIconsRect == (Object)null || entry == null || entry.drops == null || entry.drops.Count == 0)
			{
				return;
			}
			int num = 0;
			for (int i = 0; i < entry.drops.Count; i++)
			{
				TrophyDropEntry trophyDropEntry = entry.drops[i];
				if (trophyDropEntry != null && !((Object)(object)trophyDropEntry.icon == (Object)null))
				{
					GameObject val = new GameObject("DropIcon_" + i.ToString(CultureInfo.InvariantCulture));
					val.transform.SetParent((Transform)(object)_dropIconsRect, false);
					RectTransform val2 = val.AddComponent<RectTransform>();
					val2.anchorMin = new Vector2(0f, 0f);
					val2.anchorMax = new Vector2(0f, 0f);
					val2.pivot = new Vector2(0f, 0f);
					val2.anchoredPosition = new Vector2(10f + (float)num * 34f, 0f);
					val2.sizeDelta = new Vector2(30f, 30f);
					Image val3 = val.AddComponent<Image>();
					val3.sprite = trophyDropEntry.icon;
					val3.preserveAspect = true;
					((Graphic)val3).raycastTarget = false;
					_dropIconObjects.Add(val);
					num++;
					if (num >= 12)
					{
						break;
					}
				}
			}
			if (num > 0)
			{
				_dropIconsHeight = 38f;
				_dropIconsPreferredWidth = 10f + (float)num * 34f + 10f;
				_dropIconsRect.sizeDelta = new Vector2(0f, _dropIconsHeight);
				if ((Object)(object)_tooltipTextRect != (Object)null)
				{
					_tooltipTextRect.offsetMin = new Vector2(10f, 8f + _dropIconsHeight);
				}
			}
		}

		private static void UpdateTooltipPosition()
		{
			//IL_0027: 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_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_0045: Unknown result type (might be due to invalid IL or missing references)
			if (!((Object)(object)_tooltipRect == (Object)null) && !((Object)(object)_tooltipRoot == (Object)null))
			{
				_tooltipRect.anchoredPosition = ClampTooltipPosition(Input.mousePosition + new Vector3(18f, 18f, 0f));
				_tooltipRoot.transform.SetAsLastSibling();
			}
		}

		private static Vector2 ClampTooltipPosition(Vector3 desiredScreenPos)
		{
			//IL_001a: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Unknown result type (might be due to invalid IL or missing references)
			//IL_008e: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00aa: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
			float num = (((Object)(object)_tooltipRect != (Object)null) ? _tooltipRect.sizeDelta.x : 300f);
			float num2 = (((Object)(object)_tooltipRect != (Object)null) ? _tooltipRect.sizeDelta.y : 250f);
			float num3 = Mathf.Max(0f, (float)Screen.width - num - 8f);
			float num4 = Mathf.Max(0f, (float)Screen.height - num2 - 8f);
			float num5 = Mathf.Clamp(desiredScreenPos.x, 8f, num3);
			float num6 = Mathf.Clamp(desiredScreenPos.y, 8f, num4);
			return new Vector2(num5, num6);
		}

		private static void EnsureTrophyCache()
		{
			//IL_017c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0183: Invalid comparison between Unknown and I4
			//IL_0254: Unknown result type (might be due to invalid IL or missing references)
			//IL_02bb: Unknown result type (might be due to invalid IL or missing references)
			//IL_02c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_02c8: Unknown result type (might be due to invalid IL or missing references)
			//IL_02cd: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)ObjectDB.instance == (Object)null || (Object)(object)ZNetScene.instance == (Object)null)
			{
				return;
			}
			int num = ((ObjectDB.instance.m_items != null) ? ObjectDB.instance.m_items.Count : 0);
			if (num == _lastObjectDbItemCount && TrophyBySpriteId.Count > 0)
			{
				return;
			}
			TrophyBySpriteId.Clear();
			_lastObjectDbItemCount = num;
			CreaturePrefabs.Clear();
			List<GameObject> prefabs = ZNetScene.instance.m_prefabs;
			if (prefabs != null)
			{
				for (int i = 0; i < prefabs.Count; i++)
				{
					GameObject val = prefabs[i];
					if (!((Object)(object)val == (Object)null))
					{
						Character component = val.GetComponent<Character>();
						if (!((Object)(object)component == (Object)null))
						{
							CreaturePrefabs.Add(val);
						}
					}
				}
			}
			List<GameObject> items = ObjectDB.instance.m_items;
			if (items == null)
			{
				return;
			}
			for (int j = 0; j < items.Count; j++)
			{
				GameObject val2 = items[j];
				if ((Object)(object)val2 == (Object)null)
				{
					continue;
				}
				ItemDrop component2 = val2.GetComponent<ItemDrop>();
				if ((Object)(object)component2 == (Object)null || component2.m_itemData == null || component2.m_itemData.m_shared == null || (int)component2.m_itemData.m_shared.m_itemType != 13)
				{
					continue;
				}
				Sprite icon = component2.m_itemData.GetIcon();
				if ((Object)(object)icon == (Object)null)
				{
					continue;
				}
				string prefabName = Utils.GetPrefabName(val2);
				GameObject val3 = ResolveCreaturePrefabFromTrophyItem(val2, prefabName);
				if ((Object)(object)val3 == (Object)null)
				{
					continue;
				}
				Character component3 = val3.GetComponent<Character>();
				if (!((Object)(object)component3 == (Object)null))
				{
					string text = component2.m_itemData.m_shared.m_name;
					if (!string.IsNullOrWhiteSpace(text) && text.StartsWith("$"))
					{
						text = LocalizeToken(text);
					}
					string text2 = Utils.GetPrefabName(val3);
					if (string.IsNullOrWhiteSpace(text2))
					{
						text2 = ((Object)val3).name;
					}
					BestDamageInfo bestDamageInfo = ComputeBestDamageInfo(component3.m_damageModifiers);
					TrophyEntry trophyEntry = new TrophyEntry
					{
						trophyDisplayName = (text ?? prefabName),
						creatureDisplayName = FormatEnemyDisplayName(component3.m_name, text2),
						prefabName = text2,
						baseHp = Mathf.Max(1f, component3.m_health),
						isBoss = IsBossPrefabName(text2),
						damageModifiers = ((DamageModifiers)(ref component3.m_damageModifiers)).Clone(),
						bestDamageType = bestDamageInfo.Type,
						bestDamageMultiplier = bestDamageInfo.Multiplier
					};
					trophyEntry.drops.AddRange(BuildDropEntries(val3));
					TrophyBySpriteId[((Object)icon).GetInstanceID()] = trophyEntry;
				}
			}
		}

		private static GameObject ResolveCreaturePrefabFromTrophyItem(GameObject trophyItemPrefab, string trophyItemName)
		{
			if ((Object)(object)trophyItemPrefab == (Object)null)
			{
				return null;
			}
			string value = Utils.GetPrefabName(trophyItemPrefab);
			if (string.IsNullOrWhiteSpace(value))
			{
				value = ((Object)trophyItemPrefab).name;
			}
			string text = NormalizeKey(value);
			for (int i = 0; i < CreaturePrefabs.Count; i++)
			{
				GameObject val = CreaturePrefabs[i];
				if ((Object)(object)val == (Object)null)
				{
					continue;
				}
				CharacterDrop component = val.GetComponent<CharacterDrop>();
				if ((Object)(object)component == (Object)null || component.m_drops == null)
				{
					continue;
				}
				for (int j = 0; j < component.m_drops.Count; j++)
				{
					Drop val2 = component.m_drops[j];
					if (val2 != null && !((Object)(object)val2.m_prefab == (Object)null))
					{
						if ((Object)(object)val2.m_prefab == (Object)(object)trophyItemPrefab)
						{
							return val;
						}
						string value2 = Utils.GetPrefabName(val2.m_prefab);
						if (string.IsNullOrWhiteSpace(value2))
						{
							value2 = ((Object)val2.m_prefab).name;
						}
						if (NormalizeKey(value2) == text)
						{
							return val;
						}
					}
				}
			}
			return ResolveCreaturePrefabFromTrophyName(trophyItemName);
		}

		private static List<TrophyDropEntry> BuildDropEntries(GameObject creaturePrefab)
		{
			List<TrophyDropEntry> list = new List<TrophyDropEntry>();
			if ((Object)(object)creaturePrefab == (Object)null)
			{
				return list;
			}
			CharacterDrop component = creaturePrefab.GetComponent<CharacterDrop>();
			if ((Object)(object)component == (Object)null || component.m_drops == null)
			{
				return list;
			}
			for (int i = 0; i < component.m_drops.Count; i++)
			{
				Drop val = component.m_drops[i];
				if (val != null && !((Object)(object)val.m_prefab == (Object)null))
				{
					ItemDrop component2 = val.m_prefab.GetComponent<ItemDrop>();
					string text = Utils.GetPrefabName(val.m_prefab);
					if (string.IsNullOrWhiteSpace(text))
					{
						text = ((Object)val.m_prefab).name;
					}
					string displayName = text;
					Sprite icon = null;
					if ((Object)(object)component2 != (Object)null && component2.m_itemData != null && component2.m_itemData.m_shared != null)
					{
						string name = component2.m_itemData.m_shared.m_name;
						displayName = ((!string.IsNullOrWhiteSpace(name)) ? LocalizeLabel(name, text) : text);
						icon = component2.m_itemData.GetIcon();
					}
					TrophyDropEntry trophyDropEntry = new TrophyDropEntry
					{
						displayName = displayName,
						icon = icon,
						amountMin = Mathf.Max(1, val.m_amountMin),
						amountMax = Mathf.Max(1, val.m_amountMax),
						chance = Mathf.Max(0f, val.m_chance),
						levelMultiplier = val.m_levelMultiplier,
						onePerPlayer = val.m_onePerPlayer
					};
					if (trophyDropEntry.amountMax < trophyDropEntry.amountMin)
					{
						trophyDropEntry.amountMax = trophyDropEntry.amountMin;
					}
					list.Add(trophyDropEntry);
				}
			}
			return list;
		}

		private static List<GameObject> GetTrophyUiElements(InventoryGui gui)
		{
			if ((Object)(object)gui == (Object)null)
			{
				return null;
			}
			if (_inventoryGuiTrophyListField == null)
			{
				_inventoryGuiTrophyListField = AccessTools.Field(typeof(InventoryGui), "m_trophyList");
			}
			return _inventoryGuiTrophyListField?.GetValue(gui) as List<GameObject>;
		}

		private static void BindTooltipToTrophyElements(InventoryGui gui)
		{
			List<GameObject> trophyUiElements = GetTrophyUiElements(gui);
			if (trophyUiElements == null || trophyUiElements.Count == 0)
			{
				return;
			}
			EnsureTrophyGridLayout(trophyUiElements);
			for (int i = 0; i < trophyUiElements.Count; i++)
			{
				GameObject val = trophyUiElements[i];
				if ((Object)(object)val == (Object)null)
				{
					continue;
				}
				NormalizeTrophyElementText(val);
				Transform val2 = val.transform.Find("icon_bkg/icon");
				if ((Object)(object)val2 == (Object)null)
				{
					continue;
				}
				Image component = ((Component)val2).GetComponent<Image>();
				if (!((Object)(object)component == (Object)null) && !((Object)(object)component.sprite == (Object)null) && TrophyBySpriteId.TryGetValue(((Object)component.sprite).GetInstanceID(), out var value) && value != null)
				{
					TrophyHoverBridge trophyHoverBridge = ((Component)val2).GetComponent<TrophyHoverBridge>();
					if ((Object)(object)trophyHoverBridge == (Object)null)
					{
						trophyHoverBridge = ((Component)val2).gameObject.AddComponent<TrophyHoverBridge>();
					}
					trophyHoverBridge.Bind(value);
					((Graphic)component).raycastTarget = true;
				}
			}
		}

		private static void EnsureTrophyGridLayout(List<GameObject> trophyElements)
		{
			//IL_0103: Unknown result type (might be due to invalid IL or missing references)
			//IL_0108: Unknown result type (might be due to invalid IL or missing references)
			//IL_011a: Unknown result type (might be due to invalid IL or missing references)
			//IL_011f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0170: Unknown result type (might be due to invalid IL or missing references)
			//IL_0175: 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_0142: Unknown result type (might be due to invalid IL or missing references)
			//IL_014d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0152: Unknown result type (might be due to invalid IL or missing references)
			//IL_01d8: 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_0198: Unknown result type (might be due to invalid IL or missing references)
			//IL_025b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0272: Unknown result type (might be due to invalid IL or missing references)
			//IL_0289: Unknown result type (might be due to invalid IL or missing references)
			//IL_0296: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a3: Unknown result type (might be due to invalid IL or missing references)
			if (trophyElements == null || trophyElements.Count == 0)
			{
				return;
			}
			GameObject val = trophyElements[0];
			if ((Object)(object)val == (Object)null || (Object)(object)val.transform == (Object)null || (Object)(object)val.transform.parent == (Object)null)
			{
				return;
			}
			Transform parent = val.transform.parent;
			RectTransform val2 = (RectTransform)(object)((parent is RectTransform) ? parent : null);
			if ((Object)(object)val2 == (Object)null)
			{
				return;
			}
			int instanceID = ((Object)val2).GetInstanceID();
			if (instanceID == _lastConfiguredGridContainerId)
			{
				return;
			}
			GridLayoutGroup val3 = ((Component)val2).GetComponent<GridLayoutGroup>();
			if ((Object)(object)val3 == (Object)null)
			{
				val3 = ((Component)val2).gameObject.AddComponent<GridLayoutGroup>();
			}
			ContentSizeFitter val4 = ((Component)val2).GetComponent<ContentSizeFitter>();
			if ((Object)(object)val4 == (Object)null)
			{
				val4 = ((Component)val2).gameObject.AddComponent<ContentSizeFitter>();
			}
			RectTransform component = val.GetComponent<RectTransform>();
			Vector2 val5 = default(Vector2);
			((Vector2)(ref val5))..ctor(170f, 190f);
			Rect rect;
			if ((Object)(object)component != (Object)null)
			{
				rect = component.rect;
				if (((Rect)(ref rect)).width > 20f)
				{
					rect = component.rect;
					if (((Rect)(ref rect)).height > 20f)
					{
						rect = component.rect;
						float width = ((Rect)(ref rect)).width;
						rect = component.rect;
						((Vector2)(ref val5))..ctor(width, ((Rect)(ref rect)).height);
					}
				}
			}
			float num = 18f;
			float num2 = 16f;
			rect = val2.rect;
			float width2 = ((Rect)(ref rect)).width;
			int constraintCount = 4;
			if (width2 > 10f)
			{
				float num3 = Mathf.Max(1f, val5.x + num);
				constraintCount = Mathf.Max(1, Mathf.FloorToInt((width2 + num) / num3));
			}
			val3.startCorner = (Corner)0;
			val3.startAxis = (Axis)0;
			((LayoutGroup)val3).childAlignment = (TextAnchor)1;
			val3.cellSize = val5;
			val3.spacing = new Vector2(num, num2);
			val3.constraint = (Constraint)1;
			val3.constraintCount = constraintCount;
			val4.horizontalFit = (FitMode)0;
			val4.verticalFit = (FitMode)2;
			for (int i = 0; i < trophyElements.Count; i++)
			{
				GameObject val6 = trophyElements[i];
				if (!((Object)(object)val6 == (Object)null))
				{
					RectTransform component2 = val6.GetComponent<RectTransform>();
					if (!((Object)(object)component2 == (Object)null))
					{
						component2.anchorMin = new Vector2(0f, 1f);
						component2.anchorMax = new Vector2(0f, 1f);
						component2.pivot = new Vector2(0f, 1f);
						component2.anchoredPosition3D = Vector3.zero;
						((Transform)component2).localScale = Vector3.one;
					}
				}
			}
			LayoutRebuilder.ForceRebuildLayoutImmediate(val2);
			_lastConfiguredGridContainerId = instanceID;
		}

		private static void NormalizeTrophyElementText(GameObject element)
		{
			if ((Object)(object)element == (Object)null)
			{
				return;
			}
			Text[] componentsInChildren = element.GetComponentsInChildren<Text>(true);
			if (componentsInChildren == null || componentsInChildren.Length == 0)
			{
				return;
			}
			foreach (Text val in componentsInChildren)
			{
				if ((Object)(object)val == (Object)null)
				{
					continue;
				}
				val.resizeTextForBestFit = true;
				val.resizeTextMinSize = 9;
				val.resizeTextMaxSize = Mathf.Max(12, val.fontSize);
				val.horizontalOverflow = (HorizontalWrapMode)1;
				val.verticalOverflow = (VerticalWrapMode)1;
				if (!string.IsNullOrWhiteSpace(val.text))
				{
					string text = SanitizeTrophyListLabel(val.text);
					if (!string.Equals(text, val.text, StringComparison.Ordinal))
					{
						val.text = text;
					}
				}
			}
		}

		private static string SanitizeTrophyListLabel(string text)
		{
			if (string.IsNullOrWhiteSpace(text))
			{
				return string.Empty;
			}
			string text2 = text.Replace("\r", string.Empty).Trim();
			if (text2.Length == 0)
			{
				return text2;
			}
			string[] array = text2.Split(new char[1] { '\n' }, StringSplitOptions.RemoveEmptyEntries);
			if (array.Length <= 1)
			{
				return StripBracketToken(text2);
			}
			for (int i = 0; i < array.Length; i++)
			{
				string text3 = StripBracketToken(array[i].Trim());
				if (!string.IsNullOrWhiteSpace(text3))
				{
					return text3;
				}
			}
			return StripBracketToken(array[0].Trim());
		}

		private static string StripBracketToken(string text)
		{
			if (string.IsNullOrWhiteSpace(text))
			{
				return string.Empty;
			}
			string text2 = text.Trim();
			if (text2.StartsWith("[", StringComparison.Ordinal) && text2.EndsWith("]", StringComparison.Ordinal))
			{
				return string.Empty;
			}
			return text2;
		}

		private static GameObject ResolveCreaturePrefabFromTrophyName(string trophyItemName)
		{
			if (string.IsNullOrWhiteSpace(trophyItemName))
			{
				return null;
			}
			if (CreaturePrefabs.Count == 0)
			{
				return null;
			}
			HashSet<string> hashSet = CreateSearchKeysFromTrophyName(trophyItemName);
			if (hashSet.Count == 0)
			{
				return null;
			}
			GameObject result = null;
			int num = int.MaxValue;
			for (int i = 0; i < CreaturePrefabs.Count; i++)
			{
				GameObject val = CreaturePrefabs[i];
				if ((Object)(object)val == (Object)null)
				{
					continue;
				}
				string value = Utils.GetPrefabName(val);
				if (string.IsNullOrWhiteSpace(value))
				{
					value = ((Object)val).name;
				}
				string text = NormalizeKey(value);
				if (string.IsNullOrWhiteSpace(text))
				{
					continue;
				}
				if (hashSet.Contains(text))
				{
					return val;
				}
				foreach (string item in hashSet)
				{
					if (!string.IsNullOrWhiteSpace(item) && text.Contains(item))
					{
						int length = text.Length;
						if (length < num)
						{
							num = length;
							result = val;
						}
					}
				}
			}
			return result;
		}

		private static HashSet<string> CreateSearchKeysFromTrophyName(string trophyItemName)
		{
			HashSet<string> hashSet = new HashSet<string>();
			string text = NormalizeKey(trophyItemName);
			if (string.IsNullOrWhiteSpace(text))
			{
				return hashSet;
			}
			hashSet.Add(text);
			switch (text)
			{
			case "elder":
			case "theelder":
				hashSet.Add("gdking");
				break;
			case "moder":
				hashSet.Add("dragon");
				break;
			case "yagluth":
				hashSet.Add("goblinking");
				break;
			case "queen":
			case "thequeen":
				hashSet.Add("seekerqueen");
				break;
			}
			return hashSet;
		}

		private static string NormalizeKey(string value)
		{
			if (string.IsNullOrWhiteSpace(value))
			{
				return string.Empty;
			}
			string text = value.Trim().ToLowerInvariant();
			text = text.Replace("(clone)", "");
			text = text.Replace("trophy", "");
			text = text.Replace("boss", "");
			text = text.Replace("_", "");
			text = text.Replace("-", "");
			return text.Replace(" ", "");
		}

		private static string BuildTooltipText(TrophyEntry entry)
		{
			//IL_0210: Unknown result type (might be due to invalid IL or missing references)
			//IL_022c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0263: Unknown result type (might be due to invalid IL or missing references)
			//IL_029a: Unknown result type (might be due to invalid IL or missing references)
			//IL_02d1: Unknown result type (might be due to invalid IL or missing references)
			if (entry == null)
			{
				return string.Empty;
			}
			StringBuilder stringBuilder = new StringBuilder(640);
			string text = LocalizeToken(entry.trophyDisplayName);
			if (string.IsNullOrWhiteSpace(text))
			{
				text = entry.trophyDisplayName;
			}
			stringBuilder.Append(Bold(text));
			if (!string.IsNullOrWhiteSpace(entry.creatureDisplayName))
			{
				stringBuilder.Append("\n<color=#dcdcdc>").Append(entry.creatureDisplayName).Append("</color>");
			}
			if (entry.isBoss)
			{
				stringBuilder.Append("\n\n").Append(Bold(Tr("Base HP", "HP Base")));
				stringBuilder.Append("\n<color=").Append("#FFA03D").Append(">")
					.Append(entry.baseHp.ToString("0.##", CultureInfo.InvariantCulture))
					.Append("</color> <color=")
					.Append("#9A9A9A")
					.Append(">")
					.Append(Tr("(scales with nearby players)", "(escala com jogadores proximos)"))
					.Append("</color>");
			}
			else
			{
				stringBuilder.Append("\n\n").Append(Bold(Tr("HP (by stars)", "HP (por estrelas)")));
				for (int i = 1; i <= 3; i++)
				{
					float num = entry.baseHp * (float)i;
					int num2 = i - 1;
					string value = ((num2 <= 0) ? "0★" : new string('★', num2));
					stringBuilder.Append("\n<color=").Append("#FFFFFF").Append(">")
						.Append(value)
						.Append(":</color> <color=")
						.Append("#FFA03D")
						.Append(">")
						.Append(num.ToString("0.##", CultureInfo.InvariantCulture))
						.Append("</color>");
				}
			}
			AppendBestDamageTypeSection(stringBuilder, entry.damageModifiers);
			AppendModifierBlock(stringBuilder, Tr("Weaknesses", "Fraquezas"), entry.damageModifiers, IsWeakModifier);
			AppendModifierBlock(stringBuilder, Tr("Resistances", "Resistencias"), entry.damageModifiers, IsResistantModifier);
			AppendModifierBlock(stringBuilder, Tr("Immunities and Ignore", "Imunidades e Ignora"), entry.damageModifiers, IsImmuneOrIgnoreModifier);
			AppendModifierBlock(stringBuilder, Tr("Normal damage", "Dano normal"), entry.damageModifiers, IsNormalModifier);
			AppendDropsSection(stringBuilder, entry.drops);
			return stringBuilder.ToString();
		}

		private static void AppendModifierBlock(StringBuilder sb, string title, DamageModifiers mods, Func<DamageModifier, bool> include)
		{
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0041: 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)
			sb.Append("\n\n").Append(Bold(title));
			DamageType[] array = new DamageType[10];
			RuntimeHelpers.InitializeArray(array, (RuntimeFieldHandle)/*OpCode not supported: LdMemberToken*/);
			DamageType[] array2 = (DamageType[])(object)array;
			bool flag = false;
			foreach (DamageType val in array2)
			{
				DamageModifier modifier = ((DamageModifiers)(ref mods)).GetModifier(val);
				if (include(modifier))
				{
					AppendDamageModifierLine(sb, val, modifier);
					flag = true;
				}
			}
			if (!flag)
			{
				sb.Append("\n<color=").Append("#9A9A9A").Append(">")
					.Append(Tr("None", "Nenhuma"))
					.Append("</color>");
			}
		}

		private static void RefreshBestDamageIcon(TrophyEntry entry)
		{
			//IL_0057: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)_bestDamageIconImage == (Object)null)
			{
				return;
			}
			if (entry == null || entry.bestDamageMultiplier <= 1f)
			{
				((Behaviour)_bestDamageIconImage).enabled = false;
				_bestDamageIconImage.sprite = null;
				return;
			}
			EnsureDamageIconsLoaded();
			if (!DamageIconByType.TryGetValue(entry.bestDamageType, out var value) || (Object)(object)value == (Object)null)
			{
				((Behaviour)_bestDamageIconImage).enabled = false;
				_bestDamageIconImage.sprite = null;
			}
			else
			{
				_bestDamageIconImage.sprite = value;
				((Behaviour)_bestDamageIconImage).enabled = true;
			}
		}

		private static void EnsureDamageIconsLoaded()
		{
			if (_damageIconsLoaded)
			{
				return;
			}
			_damageIconsLoaded = true;
			try
			{
				Assembly assembly = typeof(TrophyTooltip).Assembly;
				string[] manifestResourceNames = assembly.GetManifestResourceNames();
				string text = null;
				foreach (string text2 in manifestResourceNames)
				{
					if (text2.IndexOf("iconsbundle", StringComparison.OrdinalIgnoreCase) >= 0)
					{
						text = text2;
						break;
					}
				}
				if (string.IsNullOrWhiteSpace(text))
				{
					ManualLogSource log = _log;
					if (log != null)
					{
						log.LogWarning((object)"[TrofeusInfo][TrophyTooltip] iconsbundle nao encontrado nos recursos.");
					}
					return;
				}
				using (Stream stream = assembly.GetManifestResourceStream(text))
				{
					if (stream == null)
					{
						ManualLogSource log2 = _log;
						if (log2 != null)
						{
							log2.LogWarning((object)"[TrofeusInfo][TrophyTooltip] stream do iconsbundle veio nulo.");
						}
						return;
					}
					byte[] array = new byte[stream.Length];
					int num;
					for (int j = 0; j < array.Length; j += num)
					{
						num = stream.Read(array, j, array.Length - j);
						if (num <= 0)
						{
							break;
						}
					}
					_damageIconsBundle = AssetBundle.LoadFromMemory(array);
				}
				if ((Object)(object)_damageIconsBundle == (Object)null)
				{
					ManualLogSource log3 = _log;
					if (log3 != null)
					{
						log3.LogWarning((object)"[TrofeusInfo][TrophyTooltip] falha ao carregar iconsbundle.");
					}
					return;
				}
				Sprite[] array2 = _damageIconsBundle.LoadAllAssets<Sprite>();
				Dictionary<string, Sprite> dictionary = new Dictionary<string, Sprite>(StringComparer.OrdinalIgnoreCase);
				foreach (Sprite val in array2)
				{
					if (!((Object)(object)val == (Object)null) && !string.IsNullOrWhiteSpace(((Object)val).name))
					{
						dictionary[((Object)val).name.Trim()] = val;
					}
				}
				MapDamageIcon((DamageType)2, "cortante", dictionary);
				MapDamageIcon((DamageType)8, "cortar", dictionary);
				MapDamageIcon((DamageType)1, "esmagador", dictionary);
				MapDamageIcon((DamageType)512, "espirito", dictionary);
				MapDamageIcon((DamageType)32, "fogo", dictionary);
				MapDamageIcon((DamageType)64, "gelo", dictionary);
				MapDamageIcon((DamageType)4, "perfurante", dictionary);
				MapDamageIcon((DamageType)16, "picareta", dictionary);
				MapDamageIcon((DamageType)128, "raio", dictionary);
				MapDamageIcon((DamageType)256, "veneno", dictionary);
			}
			catch (Exception ex)
			{
				ManualLogSource log4 = _log;
				if (log4 != null)
				{
					log4.LogWarning((object)("[TrofeusInfo][TrophyTooltip] erro carregando iconsbundle: " + ex.Message));
				}
			}
		}

		private static void MapDamageIcon(DamageType type, string spriteName, Dictionary<string, Sprite> byName)
		{
			//IL_0033: Unknown result type (might be due to invalid IL or missing references)
			if (byName != null && !string.IsNullOrWhiteSpace(spriteName) && byName.TryGetValue(spriteName, out var value) && !((Object)(object)value == (Object)null))
			{
				DamageIconByType[type] = value;
			}
		}

		private static void AppendDropsSection(StringBuilder sb, List<TrophyDropEntry> drops)
		{
			sb.Append("\n\n").Append(Bold(Tr("Possible drops", "Drops possiveis")));
			if (drops == null || drops.Count == 0)
			{
				sb.Append("\n<color=").Append("#9A9A9A").Append(">")
					.Append(Tr("None configured", "Nenhum configurado"))
					.Append("</color>");
				return;
			}
			for (int i = 0; i < drops.Count; i++)
			{
				TrophyDropEntry trophyDropEntry = drops[i];
				if (trophyDropEntry != null)
				{
					sb.Append("\n<color=white>").Append(trophyDropEntry.displayName).Append("</color> <color=")
						.Append("#FFA03D")
						.Append(">(")
						.Append(FormatDropDescriptor(trophyDropEntry))
						.Append(")</color>");
				}
			}
		}

		private static string FormatDropDescriptor(TrophyDropEntry drop)
		{
			string text = ((drop.amountMin == drop.amountMax) ? ("x" + drop.amountMin.ToString(CultureInfo.InvariantCulture)) : ("x" + drop.amountMin.ToString(CultureInfo.InvariantCulture) + "-" + drop.amountMax.ToString(CultureInfo.InvariantCulture)));
			string text2 = (Mathf.Clamp01(drop.chance) * 100f).ToString("0.#", CultureInfo.InvariantCulture) + "%";
			if (drop.levelMultiplier)
			{
				text2 += " +lvl";
			}
			if (drop.onePerPlayer)
			{
				text2 += Tr(" /player", " /jogador");
			}
			return text + " | " + text2;
		}

		private static bool IsWeakModifier(DamageModifier mod)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Invalid comparison between Unknown and I4
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Invalid comparison between Unknown and I4
			//IL_0009: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Invalid comparison between Unknown and I4
			return (int)mod == 8 || (int)mod == 2 || (int)mod == 6;
		}

		private static bool IsResistantModifier(DamageModifier mod)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Invalid comparison between Unknown and I4
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Invalid comparison between Unknown and I4
			//IL_0009: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Invalid comparison between Unknown and I4
			return (int)mod == 7 || (int)mod == 1 || (int)mod == 5;
		}

		private static bool IsImmuneOrIgnoreModifier(DamageModifier mod)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Invalid comparison between Unknown and I4
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Invalid comparison between Unknown and I4
			return (int)mod == 3 || (int)mod == 4;
		}

		private static bool IsNormalModifier(DamageModifier mod)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Invalid comparison between Unknown and I4
			return (int)mod == 0;
		}

		private static BestDamageInfo ComputeBestDamageInfo(DamageModifiers mods)
		{
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0032: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0057: 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_005d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0062: Unknown result type (might be due to invalid IL or missing references)
			//IL_0064: Unknown result type (might be due to invalid IL or missing references)
			//IL_0080: Unknown result type (might be due to invalid IL or missing references)
			//IL_0082: Unknown result type (might be due to invalid IL or missing references)
			//IL_0089: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			DamageType[] array = new DamageType[10];
			RuntimeHelpers.InitializeArray(array, (RuntimeFieldHandle)/*OpCode not supported: LdMemberToken*/);
			DamageType[] array2 = (DamageType[])(object)array;
			BestDamageInfo bestDamageInfo = default(BestDamageInfo);
			bestDamageInfo.Type = array2[0];
			bestDamageInfo.Modifier = ((DamageModifiers)(ref mods)).GetModifier(array2[0]);
			bestDamageInfo.Multiplier = GetModifierMultiplier(((DamageModifiers)(ref mods)).GetModifier(array2[0]));
			BestDamageInfo result = bestDamageInfo;
			for (int i = 1; i < array2.Length; i++)
			{
				DamageType val = array2[i];
				DamageModifier modifier = ((DamageModifiers)(ref mods)).GetModifier(val);
				float modifierMultiplier = GetModifierMultiplier(modifier);
				if (modifierMultiplier > result.Multiplier)
				{
					result.Type = val;
					result.Modifier = modifier;
					result.Multiplier = modifierMultiplier;
				}
			}
			return result;
		}

		private static void AppendBestDamageTypeSection(StringBuilder sb, DamageModifiers mods)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0088: Unknown result type (might be due to invalid IL or missing references)
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			BestDamageInfo bestDamageInfo = ComputeBestDamageInfo(mods);
			sb.Append("\n\n").Append(Bold(Tr("Best damage against this enemy", "Melhor dano contra este inimigo")));
			if (bestDamageInfo.Multiplier <= 1f)
			{
				sb.Append("\n<color=").Append("#9A9A9A").Append(">")
					.Append(Tr("No specific bonus", "Sem bonus especifico"))
					.Append("</color>");
				return;
			}
			string damageTypeLabel = GetDamageTypeLabel(bestDamageInfo.Type);
			string damageModifierLabel = GetDamageModifierLabel(bestDamageInfo.Modifier);
			string value = StripRichText(damageTypeLabel);
			string value2 = StripRichText(damageModifierLabel);
			sb.Append("\n<color=white>").Append(Tr("Type:", "Tipo:")).Append("</color> <size=18><color=#FFA03D><b>")
				.Append(value)
				.Append("</b></color></size>");
			sb.Append("\n<color=white>").Append(Tr("Bonus:", "Bonus:")).Append("</color> <size=18><color=#FFA03D><b>")
				.Append(value2)
				.Append(" (x")
				.Append(bestDamageInfo.Multiplier.ToString("0.##", CultureInfo.InvariantCulture))
				.Append(")</b></color></size>");
		}

		private static void AppendDamageModifierLine(StringBuilder sb, DamageType damageType, DamageModifier modifier)
		{
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			sb.Append("\n<color=white>").Append(GetDamageTypeLabel(damageType)).Append(":</color> <color=")
				.Append("#FFA03D")
				.Append(">")
				.Append(GetDamageModifierLabel(modifier))
				.Append("</color>");
		}

		private static string Bold(string text)
		{
			if (string.IsNullOrEmpty(text))
			{
				return string.Empty;
			}
			return "<color=#98c2ed><b>" + text + "</b></color>";
		}

		private static string Orange(string text)
		{
			if (string.IsNullOrEmpty(text))
			{
				return string.Empty;
			}
			return "<color=#FFA03D>" + text + "</color>";
		}

		private static string OrangeBold(string text)
		{
			if (string.IsNullOrEmpty(text))
			{
				return string.Empty;
			}
			return "<color=#FFA03D><b>" + text + "</b></color>";
		}

		private static string LocalizeLabel(string token, string fallback)
		{
			string text = LocalizeToken(token);
			if (string.IsNullOrWhiteSpace(text))
			{
				return fallback;
			}
			string text2 = text.Trim();
			if (text2.StartsWith("[", StringComparison.Ordinal) && text2.EndsWith("]", StringComparison.Ordinal))
			{
				return fallback;
			}
			if (text2.StartsWith("$", StringComparison.Ordinal))
			{
				return fallback;
			}
			return text2;
		}

		private static string GetDamageModifierLabel(DamageModifier modifier)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			//IL_0004: Unknown result type (might be due to invalid IL or missing references)
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_002f: Expected I4, but got Unknown
			return (int)modifier switch
			{
				7 => LocalizeLabel("$inventory_slightlyresistant", Tr("Slightly resistant", "Levemente resistente")), 
				1 => LocalizeLabel("$inventory_resistant", Tr("Resistant", "Resistente")), 
				5 => LocalizeLabel("$inventory_veryresistant", Tr("Very resistant", "Muito resistente")), 
				8 => LocalizeLabel("$inventory_slightlyweak", Tr("Slightly weak", "Levemente fraco")), 
				2 => LocalizeLabel("$inventory_weak", Tr("Weak", "Fraco")), 
				6 => LocalizeLabel("$inventory_veryweak", Tr("Very weak", "Muito fraco")), 
				3 => LocalizeLabel("$inventory_immune", Tr("Immune", "Imune")), 
				4 => LocalizeLabel("$inventory_ignore", Tr("Ignore", "Ignora")), 
				_ => LocalizeLabel("$inventory_normal", Tr("Normal", "Normal")), 
			};
		}

		private static string GetDamageTypeLabel(DamageType type)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			//IL_0004: Unknown result type (might be due to invalid IL or missing references)
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Invalid comparison between Unknown and I4
			//IL_004b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0051: Invalid comparison between Unknown and I4
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Invalid comparison between Unknown and I4
			//IL_006d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0073: Invalid comparison between Unknown and I4
			//IL_0053: Unknown result type (might be due to invalid IL or missing references)
			//IL_0056: Invalid comparison between Unknown and I4
			//IL_0034: Unknown result type (might be due to invalid IL or missing references)
			//IL_0037: Invalid comparison between Unknown and I4
			//IL_000e: 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_0026: Expected I4, but got Unknown
			//IL_007a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0080: Invalid comparison between Unknown and I4
			//IL_005d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0063: Invalid comparison between Unknown and I4
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0041: Invalid comparison between Unknown and I4
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Invalid comparison between Unknown and I4
			DamageType val = type;
			DamageType val2 = val;
			string text;
			if ((int)val2 <= 32)
			{
				if ((int)val2 <= 8)
				{
					switch (val2 - 1)
					{
					case 0:
						goto IL_008a;
					case 1:
						goto IL_00a9;
					case 3:
						goto IL_00c8;
					case 2:
						goto IL_01b4;
					}
					if ((int)val2 != 8)
					{
						goto IL_01b4;
					}
					text = LocalizeLabel("$inventory_chop", Tr("Chop", "Cortar madeira"));
				}
				else if ((int)val2 != 16)
				{
					if ((int)val2 != 32)
					{
						goto IL_01b4;
					}
					text = LocalizeLabel("$inventory_fire", Tr("Fire", "Fogo"));
				}
				else
				{
					text = LocalizeLabel("$inventory_pickaxe", Tr("Pickaxe", "Picareta"));
				}
			}
			else if ((int)val2 <= 128)
			{
				if ((int)val2 != 64)
				{
					if ((int)val2 != 128)
					{
						goto IL_01b4;
					}
					text = LocalizeLabel("$inventory_lightning", Tr("Lightning", "Raio"));
				}
				else
				{
					text = LocalizeLabel("$inventory_frost", Tr("Frost", "Gelo"));
				}
			}
			else if ((int)val2 != 256)
			{
				if ((int)val2 != 512)
				{
					goto IL_01b4;
				}
				text = LocalizeLabel("$inventory_spirit", Tr("Spirit", "Espirito"));
			}
			else
			{
				text = LocalizeLabel("$inventory_poison", Tr("Poison", "Veneno"));
			}
			goto IL_01c4;
			IL_00a9:
			text = LocalizeLabel("$inventory_slash", Tr("Slash", "Cortante"));
			goto IL_01c4;
			IL_008a:
			text = LocalizeLabel("$inventory_blunt", Tr("Blunt", "Contundente"));
			goto IL_01c4;
			IL_01c4:
			return StripLeadingSymbols(text);
			IL_01b4:
			text = ((object)(DamageType)(ref type)).ToString();
			goto IL_01c4;
			IL_00c8:
			text = LocalizeLabel("$inventory_pierce", Tr("Pierce", "Perfurante"));
			goto IL_01c4;
		}

		private static string StripLeadingSymbols(string text)
		{
			if (string.IsNullOrWhiteSpace(text))
			{
				return string.Empty;
			}
			string text2 = text.Trim();
			int i;
			for (i = 0; i < text2.Length; i++)
			{
				char c = text2[i];
				if (char.IsLetterOrDigit(c))
				{
					break;
				}
			}
			return (i > 0 && i < text2.Length) ? text2.Substring(i).TrimStart(Array.Empty<char>()) : text2;
		}

		private static string StripRichText(string text)
		{
			if (string.IsNullOrEmpty(text))
			{
				return string.Empty;
			}
			StringBuilder stringBuilder = new StringBuilder(text.Length);
			bool flag = false;
			foreach (char c in text)
			{
				switch (c)
				{
				case '<':
					flag = true;
					continue;
				case '>':
					flag = false;
					continue;
				}
				if (!flag)
				{
					stringBuilder.Append(c);
				}
			}
			return stringBuilder.ToString().Trim();
		}

		private static float GetModifierMultiplier(DamageModifier modifier)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			//IL_0004: Unknown result type (might be due to invalid IL or missing references)
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_002f: Expected I4, but got Unknown
			switch ((int)modifier)
			{
			case 7:
				return 0.75f;
			case 1:
				return 0.5f;
			case 5:
				return 0.25f;
			case 8:
				return 1.25f;
			case 2:
				return 1.5f;
			case 6:
				return 2f;
			case 3:
			case 4:
				return 0f;
			default:
				return 1f;
			}
		}

		private static Color GetModifierColor(DamageModifier modifier)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			//IL_0004: Unknown result type (might be due to invalid IL or missing references)
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Expected I4, but got Unknown
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0064: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Unknown result type (might be due to invalid IL or missing references)
			//IL_006f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0067: Unknown result type (might be due to invalid IL or missing references)
			//IL_006c: Unknown result type (might be due to invalid IL or missing references)
			switch (modifier - 1)
			{
			case 1:
			case 5:
			case 7:
				return new Color(1f, 1f, 0f, 1f);
			case 0:
			case 2:
			case 3:
			case 4:
			case 6:
				return new Color(0.6f, 0.6f, 0.6f, 1f);
			default:
				return Color.white;
			}
		}

		private static string LocalizeToken(string token)
		{
			if (string.IsNullOrWhiteSpace(token))
			{
				return string.Empty;
			}
			if (!token.StartsWith("$", StringComparison.Ordinal))
			{
				return token;
			}
			ResolveLocalization();
			if (_localizeMethod == null)
			{
				return token;
			}
			object obj = ((_localizationInstanceProperty != null) ? _localizationInstanceProperty.GetValue(null, null) : _localizationInstanceField?.GetValue(null));
			if (obj == null)
			{
				return token;
			}
			try
			{
				object obj2 = _localizeMethod.Invoke(obj, new object[1] { token });
				string text = obj2 as string;
				if (string.IsNullOrWhiteSpace(text))
				{
					return token;
				}
				return text;
			}
			catch
			{
				return token;
			}
		}

		private static string Tr(string en, string ptBr)
		{
			EnsureTranslationFilesAndLoad();
			bool flag = IsPortuguese();
			Dictionary<string, string> dictionary = (flag ? PortugueseTranslations : EnglishTranslations);
			if (dictionary.TryGetValue(en, out var value) && !string.IsNullOrWhiteSpace(value))
			{
				return value;
			}
			if (dictionary.TryGetValue(ptBr, out value) && !string.IsNullOrWhiteSpace(value))
			{
				return value;
			}
			return flag ? ptBr : en;
		}

		private static bool IsPortuguese()
		{
			ResolveLocalization();
			object obj = ((_localizationInstanceProperty != null) ? _localizationInstanceProperty.GetValue(null, null) : _localizationInstanceField?.GetValue(null));
			if (obj == null)
			{
				return true;
			}
			try
			{
				MethodInfo method = obj.GetType().GetMethod("GetSelectedLanguage", BindingFlags.Instance | BindingFlags.Public);
				if (method != null)
				{
					string text = method.Invoke(obj, null) as string;
					if (!string.IsNullOrWhiteSpace(text))
					{
						string text2 = text.Trim().ToLowerInvariant();
						if (text2.Contains("portugu"))
						{
							return true;
						}
						if (text2.Contains("brazil"))
						{
							return true;
						}
						if (text2.Contains("english"))
						{
							return false;
						}
					}
				}
			}
			catch
			{
			}
			return true;
		}

		private static void EnsureTranslationFilesAndLoad()
		{
			if (_translationsLoaded)
			{
				return;
			}
			_translationsLoaded = true;
			try
			{
				Dictionary<string, string> defaultPortugueseTranslations = GetDefaultPortugueseTranslations();
				Dictionary<string, string> defaultEnglishTranslations = GetDefaultEnglishTranslations();
				string path = Path.Combine(Paths.PluginPath, "TrophyTooltip", "Traslations");
				string text = Path.Combine(path, "English");
				string text2 = Path.Combine(path, "Portuguese_Brazilian");
				Directory.CreateDirectory(text);
				Directory.CreateDirectory(text2);
				string text3 = Path.Combine(text, "English.json");
				string text4 = Path.Combine(text2, "Portuguese_Brazilian.json");
				if (!File.Exists(text3))
				{
					File.WriteAllText(text3, SerializeFlatJson(defaultEnglishTranslations), Encoding.UTF8);
				}
				if (!File.Exists(text4))
				{
					File.WriteAllText(text4, SerializeFlatJson(defaultPortugueseTranslations), Encoding.UTF8);
				}
				EnglishTranslations.Clear();
				PortugueseTranslations.Clear();
				LoadTranslationsFromFile(text3, defaultEnglishTranslations, EnglishTranslations);
				LoadTranslationsFromFile(text4, defaultPortugueseTranslations, PortugueseTranslations);
			}
			catch (Exception ex)
			{
				ManualLogSource log = _log;
				if (log != null)
				{
					log.LogWarning((object)("[TrofeusInfo][TrophyTooltip] Falha ao carregar traducoes: " + ex.Message));
				}
			}
		}

		private static void LoadTranslationsFromFile(string filePath, Dictionary<string, string> defaults, Dictionary<string, string> target)
		{
			foreach (KeyValuePair<string, string> @default in defaults)
			{
				target[@default.Key] = @default.Value;
			}
			if (!File.Exists(filePath))
			{
				return;
			}
			string json = File.ReadAllText(filePath, Encoding.UTF8);
			Dictionary<string, string> dictionary = ParseFlatJson(json);
			foreach (KeyValuePair<string, string> item in dictionary)
			{
				if (!string.IsNullOrWhiteSpace(item.Key))
				{
					target[item.Key] = item.Value ?? string.Empty;
				}
			}
		}

		private static Dictionary<string, string> ParseFlatJson(string json)
		{
			Dictionary<string, string> dictionary = new Dictionary<string, string>();
			if (string.IsNullOrWhiteSpace(json))
			{
				return dictionary;
			}
			MatchCollection matchCollection = Regex.Matches(json, "\"((?:\\\\.|[^\"])*)\"\\s*:\\s*\"((?:\\\\.|[^\"])*)\"");
			for (int i = 0; i < matchCollection.Count; i++)
			{
				string value = matchCollection[i].Groups[1].Value;
				string value2 = matchCollection[i].Groups[2].Value;
				string text = JsonUnescape(value);
				string value3 = JsonUnescape(value2);
				if (!string.IsNullOrWhiteSpace(text))
				{
					dictionary[text] = value3;
				}
			}
			return dictionary;
		}

		private static string SerializeFlatJson(Dictionary<string, string> map)
		{
			StringBuilder stringBuilder = new StringBuilder(2048);
			stringBuilder.Append("{\n");
			bool flag = true;
			foreach (KeyValuePair<string, string> item in map)
			{
				if (!flag)
				{
					stringBuilder.Append(",\n");
				}
				flag = false;
				stringBuilder.Append("  \"").Append(JsonEscape(item.Key)).Append("\": \"")
					.Append(JsonEscape(item.Value ?? string.Empty))
					.Append("\"");
			}
			stringBuilder.Append("\n}\n");
			return stringBuilder.ToString();
		}

		private static string JsonEscape(string s)
		{
			if (string.IsNullOrEmpty(s))
			{
				return string.Empty;
			}
			return s.Replace("\\", "\\\\").Replace("\"", "\\\"").Replace("\r", "\\r")
				.Replace("\n", "\\n")
				.Replace("\t", "\\t");
		}

		private static string JsonUnescape(string s)
		{
			if (string.IsNullOrEmpty(s))
			{
				return string.Empty;
			}
			return s.Replace("\\n", "\n").Replace("\\r", "\r").Replace("\\t", "\t")
				.Replace("\\\"", "\"")
				.Replace("\\\\", "\\");
		}

		private static Dictionary<string, string> GetDefaultPortugueseTranslations()
		{
			return new Dictionary<string, string>
			{
				{ "Base HP", "HP Base" },
				{ "(scales with nearby players)", "(escala com jogadores proximos)" },
				{ "HP (by stars)", "HP (por estrelas)" },
				{ "Weaknesses", "Fraquezas" },
				{ "Resistances", "Resistencias" },
				{ "Immunities and Ignore", "Imunidades e Ignora" },
				{ "Normal damage", "Dano normal" },
				{ "None", "Nenhuma" },
				{ "Possible drops", "Drops possiveis" },
				{ "None configured", "Nenhum configurado" },
				{ " /player", " /jogador" },
				{ "Best damage against this enemy", "Melhor dano contra este inimigo" },
				{ "No specific bonus", "Sem bonus especifico" },
				{ "Type:", "Tipo:" },
				{ "Bonus:", "Bonus:" },
				{ "Slightly resistant", "Levemente resistente" },
				{ "Resistant", "Resistente" },
				{ "Very resistant", "Muito resistente" },
				{ "Slightly weak", "Levemente fraco" },
				{ "Weak", "Fraco" },
				{ "Very weak", "Muito fraco" },
				{ "Immune", "Imune" },
				{ "Ignore", "Ignora" },
				{ "Normal", "Normal" },
				{ "Blunt", "Contundente" },
				{ "Slash", "Cortante" },
				{ "Pierce", "Perfurante" },
				{ "Chop", "Cortar madeira" },
				{ "Pickaxe", "Picareta" },
				{ "Fire", "Fogo" },
				{ "Frost", "Gelo" },
				{ "Lightning", "Raio" },
				{ "Poison", "Veneno" },
				{ "Spirit", "Espirito" },
				{ "Unknown", "Desconhecido" }
			};
		}

		private static Dictionary<string, string> GetDefaultEnglishTranslations()
		{
			return new Dictionary<string, string>
			{
				{ "Base HP", "Base HP" },
				{ "(scales with nearby players)", "(scales with nearby players)" },
				{ "HP (by stars)", "HP (by stars)" },
				{ "Weaknesses", "Weaknesses" },
				{ "Resistances", "Resistances" },
				{ "Immunities and Ignore", "Immunities and Ignore" },
				{ "Normal damage", "Normal damage" },
				{ "None", "None" },
				{ "Possible drops", "Possible drops" },
				{ "None configured", "None configured" },
				{ " /player", " /player" },
				{ "Best damage against this enemy", "Best damage against this enemy" },
				{ "No specific bonus", "No specific bonus" },
				{ "Type:", "Type:" },
				{ "Bonus:", "Bonus:" },
				{ "Slightly resistant", "Slightly resistant" },
				{ "Resistant", "Resistant" },
				{ "Very resistant", "Very resistant" },
				{ "Slightly weak", "Slightly weak" },
				{ "Weak", "Weak" },
				{ "Very weak", "Very weak" },
				{ "Immune", "Immune" },
				{ "Ignore", "Ignore" },
				{ "Normal", "Normal" },
				{ "Blunt", "Blunt" },
				{ "Slash", "Slash" },
				{ "Pierce", "Pierce" },
				{ "Chop", "Chop" },
				{ "Pickaxe", "Pickaxe" },
				{ "Fire", "Fire" },
				{ "Frost", "Frost" },
				{ "Lightning", "Lightning" },
				{ "Poison", "Poison" },
				{ "Spirit", "Spirit" },
				{ "Unknown", "Unknown" }
			};
		}

		private static void ResolveLocalization()
		{
			if (_localizationResolved)
			{
				return;
			}
			_localizationResolved = true;
			Assembly[] assemblies = AppDomain.CurrentDomain.GetAssemblies();
			Type type = null;
			for (int i = 0; i < assemblies.Length; i++)
			{
				type = assemblies[i].GetType("Localization", throwOnError: false);
				if (type != null)
				{
					break;
				}
			}
			if (!(type == null))
			{
				_localizationInstanceProperty = type.GetProperty("instance", BindingFlags.Static | BindingFlags.Public);
				if (_localizationInstanceProperty == null)
				{
					_localizationInstanceField = type.GetField("instance", BindingFlags.Static | BindingFlags.Public);
				}
				_localizeMethod = type.GetMethod("Localize", BindingFlags.Instance | BindingFlags.Public, null, new Type[1] { typeof(string) }, null);
			}
		}

		private static string FormatEnemyDisplayName(string rawName, string fallbackPrefab)
		{
			string result = (string.IsNullOrWhiteSpace(fallbackPrefab) ? Tr("Unknown", "Desconhecido") : fallbackPrefab);
			if (string.IsNullOrWhiteSpace(rawName))
			{
				return result;
			}
			string text = LocalizeToken(rawName);
			if (!string.IsNullOrWhiteSpace(text) && !text.StartsWith("$", StringComparison.Ordinal))
			{
				return text.Trim();
			}
			return result;
		}

		private static bool IsBossPrefabName(string prefabName)
		{
			string text = NormalizeKey(prefabName);
			if (string.IsNullOrWhiteSpace(text))
			{
				return false;
			}
			return text.Contains("eikthyr") || text.Contains("gdking") || text.Contains("bonemass") || text.Contains("dragon") || text.Contains("goblinking") || text.Contains("seekerqueen") || text.Contains("fader");
		}

		[HarmonyPatch(typeof(InventoryGui), "UpdateTrophyList")]
		[HarmonyPostfix]
		private static void InventoryGuiUpdateTrophyList_Postfix(InventoryGui __instance)
		{
			EnsureTrophyCache();
			BindTooltipToTrophyElements(__instance);
		}

		[HarmonyPatch(typeof(InventoryGui), "OnCloseTrophies")]
		[HarmonyPostfix]
		private static void InventoryGuiOnCloseTrophies_Postfix()
		{
			HideTooltip();
		}

		[HarmonyPatch(typeof(InventoryGui), "OnDestroy")]
		[HarmonyPostfix]
		private static void InventoryGuiOnDestroy_Postfix()
		{
			HideTooltip();
		}

		[HarmonyPatch(typeof(Hud), "OnDestroy")]
		[HarmonyPostfix]
		private static void HudOnDestroy_Postfix()
		{
			DestroyTooltip();
		}
	}
}