Decompiled source of FairyDust Hud v1.0.0

Mods\FairyDust.Hud.dll

Decompiled 3 hours ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using FairyDust.Hud;
using FairyDust.Hud.Components.Deck;
using FairyDust.Hud.Configuration;
using FairyDust.Hud.Game.Services;
using FairyDust.Hud.Host;
using FairyDust.Hud.Modules.Status;
using FairyDust.Hud.Modules.Status.Bleed;
using FairyDust.Hud.Modules.Status.Entities;
using FairyDust.Hud.Modules.Status.Frostbite;
using FairyDust.Hud.Modules.Status.Infection;
using FairyDust.Hud.Modules.Status.Services;
using FairyDust.Hud.Modules.Status.Stamina;
using Il2CppInterop.Runtime.InteropTypes;
using Il2CppInterop.Runtime.InteropTypes.Arrays;
using Il2CppTMPro;
using Il2Cppmadeinfairyland.fairyengine;
using Il2Cppmadeinfairyland.fairyengine.actor.player;
using Il2Cppmadeinfairyland.forsakenfrontiers.actor.player;
using Il2Cppmadeinfairyland.forsakenfrontiers.actor.player.datadeck;
using Il2Cppmadeinfairyland.forsakenfrontiers.ui;
using MelonLoader;
using MelonLoader.Preferences;
using UnityEngine;
using UnityEngine.SceneManagement;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: MelonInfo(typeof(Main), "FairyDust.Hud", "1.0.0", "MadeInPG13Land", null)]
[assembly: MelonColor(255, 244, 155, 171)]
[assembly: MelonAuthorColor(255, 155, 126, 189)]
[assembly: MelonGame("made in fairyland", "Forsaken Frontiers")]
[assembly: MelonProcess("Forsaken Frontiers.exe")]
[assembly: MelonPlatformDomain(/*Could not decode attribute arguments.*/)]
[assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = "")]
[assembly: AssemblyCompany("FairyDust.Hud")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("FairyDust.Hud")]
[assembly: AssemblyTitle("FairyDust.Hud")]
[assembly: AssemblyVersion("1.0.0.0")]
namespace FairyDust.Hud
{
	public sealed class Main : MelonMod
	{
		private static Main activeInstance;

		private GameplayHudHost hudHost;

		private bool loggedLateUpdateFailure;

		public override void OnInitializeMelon()
		{
			if (activeInstance != null && activeInstance != this)
			{
				activeInstance.hudHost?.Shutdown();
				activeInstance.hudHost = null;
			}
			activeInstance = this;
			Config.Initialize();
			hudHost = new GameplayHudHost((MelonMod)(object)this);
			hudHost.Register(new StatusBoardModule());
			hudHost.Initialize();
			((MelonBase)this).LoggerInstance.Msg(ConfigConsoleCard.Build());
		}

		public override void OnDeinitializeMelon()
		{
			hudHost?.Shutdown();
			hudHost = null;
			DeckStatusPanel.ReleaseSharedAssets();
			if (activeInstance == this)
			{
				activeInstance = null;
			}
		}

		public override void OnSceneWasLoaded(int buildIndex, string sceneName)
		{
			hudHost?.OnSceneWasLoaded(buildIndex, sceneName);
		}

		public override void OnLateUpdate()
		{
			try
			{
				hudHost?.OnLateUpdate();
			}
			catch (Exception ex)
			{
				if (!loggedLateUpdateFailure)
				{
					loggedLateUpdateFailure = true;
					((MelonBase)this).LoggerInstance.Error("HUD OnLateUpdate failed: " + ex);
				}
			}
		}
	}
	public static class Metadata
	{
		public const string Name = "FairyDust.Hud";

		public const string Version = "1.0.0";

		public const string Author = "MadeInPG13Land";
	}
}
namespace FairyDust.Hud.Modules.Status
{
	internal sealed class StatusBoardModule : IHudModule
	{
		private static readonly TimeSpan TextStyleRefreshInterval = TimeSpan.FromSeconds(1.0);

		private const float NormalBackgroundAlpha = 0.15f;

		private readonly PlayerStatusReadService reads;

		private readonly StatusBoardService board;

		private readonly StatusVisibilityService visibility;

		private readonly List<StatusRowSnapshot> rowBuffer;

		private HudModuleContext context;

		private DeckStatusPanelHandle panel;

		private FFDataDeck lastDeck;

		private DateTime nextTextStyleRefreshUtc = DateTime.MinValue;

		private int lastAppliedVisibleRowCount = -1;

		private Vector2 lastAppliedSlotSize = new Vector2(float.NaN, float.NaN);

		public string SlotObjectName => "Slot_StatusBoard";

		public StatusBoardModule()
		{
			//IL_001d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0022: Unknown result type (might be due to invalid IL or missing references)
			reads = new PlayerStatusReadService();
			StatusFormatterService formatter = new StatusFormatterService(reads);
			board = new StatusBoardService(new IStatusProvider[4]
			{
				new BleedStatusModule().CreateProvider(reads, formatter),
				new InfectionStatusModule().CreateProvider(reads, formatter),
				new FrostbiteStatusModule().CreateProvider(reads, formatter),
				new StaminaStatusModule().CreateProvider(reads, formatter)
			});
			visibility = new StatusVisibilityService(reads);
			rowBuffer = new List<StatusRowSnapshot>(board.Capacity);
		}

		public void OnAttach(HudModuleContext ctx)
		{
			context = ctx;
		}

		public void OnSceneWasLoaded(int buildIndex, string sceneName)
		{
			TeardownPanel();
		}

		public void OnLateUpdate()
		{
			if ((Object)(object)context?.Slot == (Object)null)
			{
				return;
			}
			try
			{
				FFPlayer current = FairyLocalPlayer.Current;
				FFDataDeck dataDeck = reads.GetDataDeck(current);
				if (!visibility.ShouldShowBoard(current, dataDeck, board.Providers))
				{
					SafeSetVisible(visible: false);
					return;
				}
				board.CollectRows(new StatusProviderContext(current, dataDeck), rowBuffer);
				if (rowBuffer.Count == 0)
				{
					SafeSetVisible(visible: false);
					return;
				}
				if (!((Component)context.Slot).gameObject.activeSelf)
				{
					((Component)context.Slot).gameObject.SetActive(true);
				}
				EnsureBuilt(context.Slot, dataDeck);
				panel.SetVisible(visible: true);
				panel.SetBackgroundAlpha(0.15f);
				RefreshDeckFlavor(dataDeck);
				ApplyRows(rowBuffer);
				ApplySlotSize(panel.ApplyVisibleLayout());
			}
			catch
			{
				SafeSetVisible(visible: false);
			}
		}

		private void EnsureBuilt(RectTransform slot, FFDataDeck deck)
		{
			if (!((Object)(object)slot == (Object)null) && (!panel.IsValid || !((Object)(object)panel.Root != (Object)null) || !((Object)(object)panel.Root.transform.parent == (Object)(object)((Component)slot).transform) || !((Object)(object)lastDeck == (Object)(object)deck)))
			{
				TeardownPanel();
				lastDeck = deck;
				panel = DeckStatusPanel.Build(slot, deck, "StatusBoard", board.Capacity);
			}
		}

		private void ApplyRows(IReadOnlyList<StatusRowSnapshot> rows)
		{
			panel.ClearRows();
			for (int i = 0; i < rows.Count; i++)
			{
				StatusRowSnapshot statusRowSnapshot = rows[i];
				panel.SetRow(i, statusRowSnapshot.Label, statusRowSnapshot.Ratio, statusRowSnapshot.ValueText, statusRowSnapshot.Warning);
			}
		}

		private void ApplySlotSize(int visibleRowCount)
		{
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0036: Unknown result type (might be due to invalid IL or missing references)
			//IL_0057: Unknown result type (might be due to invalid IL or missing references)
			//IL_0058: Unknown result type (might be due to invalid IL or missing references)
			//IL_005e: Unknown result type (might be due to invalid IL or missing references)
			//IL_006a: 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_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_0042: Unknown result type (might be due to invalid IL or missing references)
			LayoutElement val = ((Component)context.Slot).GetComponent<LayoutElement>();
			if ((Object)(object)val == (Object)null)
			{
				val = ((Component)context.Slot).gameObject.AddComponent<LayoutElement>();
			}
			Vector2 val2 = DeckStatusPanel.OuterSizeForRows(visibleRowCount);
			if (visibleRowCount != lastAppliedVisibleRowCount || !(val2 == lastAppliedSlotSize))
			{
				lastAppliedVisibleRowCount = visibleRowCount;
				lastAppliedSlotSize = val2;
				val.preferredWidth = val2.x;
				val.preferredHeight = val2.y;
				context.Slot.sizeDelta = val2;
				Transform parent = ((Transform)context.Slot).parent;
				RectTransform val3 = (RectTransform)(object)((parent is RectTransform) ? parent : null);
				if (val3 != null)
				{
					LayoutRebuilder.MarkLayoutForRebuild(val3);
				}
				LayoutRebuilder.MarkLayoutForRebuild(context.Slot);
			}
		}

		private void SetVisible(bool visible)
		{
			panel.SetVisible(visible);
			if ((Object)(object)context?.Slot != (Object)null)
			{
				((Component)context.Slot).gameObject.SetActive(visible);
			}
		}

		private void SafeSetVisible(bool visible)
		{
			try
			{
				SetVisible(visible);
			}
			catch
			{
			}
		}

		private void TeardownPanel()
		{
			//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)
			panel.Destroy();
			panel = default(DeckStatusPanelHandle);
			lastDeck = null;
			nextTextStyleRefreshUtc = DateTime.MinValue;
			lastAppliedVisibleRowCount = -1;
			lastAppliedSlotSize = new Vector2(float.NaN, float.NaN);
		}

		private void RefreshDeckFlavor(FFDataDeck deck)
		{
			if (!((Object)(object)deck == (Object)null) && panel.IsValid)
			{
				DateTime utcNow = DateTime.UtcNow;
				bool flag = utcNow >= nextTextStyleRefreshUtc;
				if (flag)
				{
					nextTextStyleRefreshUtc = utcNow + TextStyleRefreshInterval;
				}
				panel.RefreshFlavor(deck, flag);
			}
		}
	}
}
namespace FairyDust.Hud.Modules.Status.Stamina
{
	internal sealed class StaminaStatusModule
	{
		public IStatusProvider CreateProvider(PlayerStatusReadService reads, StatusFormatterService formatter)
		{
			return new StaminaStatusProvider(reads);
		}
	}
	internal sealed class StaminaStatusProvider : IStatusProvider
	{
		private const float LowWarningRatio = 0.25f;

		private readonly PlayerStatusReadService reads;

		public string Id => "stamina";

		public int SortOrder => 30;

		public bool IsEnabled => Config.Values.StaminaModuleEnabled;

		public StaminaStatusProvider(PlayerStatusReadService reads)
		{
			this.reads = reads;
		}

		public bool TryGetRow(StatusProviderContext context, out StatusRowSnapshot row)
		{
			float num = Mathf.Max(reads.MaxStamina(context.Player), 1E-05f);
			float num2 = Mathf.Clamp01(reads.Stamina(context.Player) / num);
			row = new StatusRowSnapshot(StatusRowKind.Stamina, Id, "STAMINA", num2, SortOrder, null, num2 <= 0.25f);
			return true;
		}
	}
}
namespace FairyDust.Hud.Modules.Status.Services
{
	internal sealed class PlayerStatusReadService
	{
		public bool IsUsable(FFPlayer player)
		{
			if ((Object)(object)player == (Object)null)
			{
				return false;
			}
			try
			{
				return (Object)(object)((Component)player).gameObject != (Object)null && ((Component)player).gameObject.activeInHierarchy;
			}
			catch
			{
				return false;
			}
		}

		public FFDataDeck GetDataDeck(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.DataDeck : null;
			}
			catch
			{
				return null;
			}
		}

		public bool IsDataDeckOpen(FFDataDeck deck)
		{
			try
			{
				return (Object)(object)deck != (Object)null && deck.DataDeckOpen;
			}
			catch
			{
				return false;
			}
		}

		public bool IsBleeding(FFPlayer player)
		{
			try
			{
				return (Object)(object)player != (Object)null && player.IsBleeding;
			}
			catch
			{
				return false;
			}
		}

		public bool IsInfected(FFPlayer player)
		{
			try
			{
				return (Object)(object)player != (Object)null && player.Infected;
			}
			catch
			{
				return false;
			}
		}

		public bool IsFrostbiteActive(FFPlayer player)
		{
			try
			{
				return (Object)(object)player != (Object)null && player.FrostbiteActive;
			}
			catch
			{
				return false;
			}
		}

		public float BleedToDeathTime(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.BleedToDeathTime : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float BleedToDeathTimer(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.BleedToDeathTimer : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float InfectionTakeoverDuration(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.InfectionTakeoverDuration : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float InfectionTimer(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.InfectionTimer : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float MaxFrostbite(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.maxFrostbite : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float Frostbite(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.Frostbite : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float FrostbiteSpeed(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? player.frostbiteSpeed : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float MaxStamina(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? ((FairyPlayer)player).MaxStamina : 0f;
			}
			catch
			{
				return 0f;
			}
		}

		public float Stamina(FFPlayer player)
		{
			try
			{
				return ((Object)(object)player != (Object)null) ? ((FairyPlayer)player).Stamina : 0f;
			}
			catch
			{
				return 0f;
			}
		}
	}
	internal sealed class StatusBoardService
	{
		private readonly IStatusProvider[] providers;

		public IReadOnlyList<IStatusProvider> Providers => providers;

		public int Capacity => providers.Length;

		public StatusBoardService(IEnumerable<IStatusProvider> providers)
		{
			this.providers = providers.OrderBy((IStatusProvider provider) => provider.SortOrder).ToArray();
		}

		public void CollectRows(StatusProviderContext context, List<StatusRowSnapshot> rows)
		{
			rows.Clear();
			for (int i = 0; i < providers.Length; i++)
			{
				IStatusProvider statusProvider = providers[i];
				if (statusProvider.IsEnabled && statusProvider.TryGetRow(context, out var row))
				{
					rows.Add(row);
				}
			}
			rows.Sort((StatusRowSnapshot left, StatusRowSnapshot right) => left.SortOrder.CompareTo(right.SortOrder));
		}
	}
	internal sealed class StatusFormatterService
	{
		private readonly PlayerStatusReadService reads;

		public StatusFormatterService(PlayerStatusReadService reads)
		{
			this.reads = reads;
		}

		public string Timer(float seconds)
		{
			int num = Mathf.Max(0, Mathf.CeilToInt(seconds));
			int value = num / 60;
			int value2 = num % 60;
			return $"{value:00}:{value2:00}";
		}

		public string FrostbiteValue(FFPlayer player, float frostbite, float maxFrostbite)
		{
			float num = reads.FrostbiteSpeed(player);
			if (reads.IsFrostbiteActive(player) && num > 0.001f && frostbite < maxFrostbite)
			{
				return Timer((maxFrostbite - frostbite) / num);
			}
			return Mathf.RoundToInt(Mathf.Clamp01(frostbite / Mathf.Max(maxFrostbite, 1E-05f)) * 100f) + "%";
		}
	}
	internal sealed class StatusVisibilityService
	{
		private readonly PlayerStatusReadService reads;

		public StatusVisibilityService(PlayerStatusReadService reads)
		{
			this.reads = reads;
		}

		public bool ShouldShowBoard(FFPlayer player, FFDataDeck deck, IReadOnlyList<IStatusProvider> providers)
		{
			if (!reads.IsUsable(player) || reads.IsDataDeckOpen(deck))
			{
				return false;
			}
			for (int i = 0; i < providers.Count; i++)
			{
				if (providers[i].IsEnabled)
				{
					return true;
				}
			}
			return false;
		}
	}
}
namespace FairyDust.Hud.Modules.Status.Infection
{
	internal sealed class InfectionStatusModule
	{
		public IStatusProvider CreateProvider(PlayerStatusReadService reads, StatusFormatterService formatter)
		{
			return new InfectionStatusProvider(reads, formatter);
		}
	}
	internal sealed class InfectionStatusProvider : IStatusProvider
	{
		private const float LowWarningRatio = 0.25f;

		private readonly PlayerStatusReadService reads;

		private readonly StatusFormatterService formatter;

		public string Id => "infection";

		public int SortOrder => 10;

		public bool IsEnabled => Config.Values.InfectionModuleEnabled;

		public InfectionStatusProvider(PlayerStatusReadService reads, StatusFormatterService formatter)
		{
			this.reads = reads;
			this.formatter = formatter;
		}

		public bool TryGetRow(StatusProviderContext context, out StatusRowSnapshot row)
		{
			row = default(StatusRowSnapshot);
			if (!reads.IsInfected(context.Player))
			{
				return false;
			}
			float num = Mathf.Max(reads.InfectionTakeoverDuration(context.Player), 1E-05f);
			float num2 = Mathf.Max(0f, reads.InfectionTimer(context.Player));
			float num3 = Mathf.Clamp01(num2 / num);
			row = new StatusRowSnapshot(StatusRowKind.Infection, Id, "INFECTION", num3, SortOrder, formatter.Timer(num2), num3 <= 0.25f);
			return true;
		}
	}
}
namespace FairyDust.Hud.Modules.Status.Frostbite
{
	internal sealed class FrostbiteStatusModule
	{
		public IStatusProvider CreateProvider(PlayerStatusReadService reads, StatusFormatterService formatter)
		{
			return new FrostbiteStatusProvider(reads, formatter);
		}
	}
	internal sealed class FrostbiteStatusProvider : IStatusProvider
	{
		private const float HighWarningRatio = 0.75f;

		private readonly PlayerStatusReadService reads;

		private readonly StatusFormatterService formatter;

		public string Id => "frostbite";

		public int SortOrder => 20;

		public bool IsEnabled => Config.Values.FrostbiteModuleEnabled;

		public FrostbiteStatusProvider(PlayerStatusReadService reads, StatusFormatterService formatter)
		{
			this.reads = reads;
			this.formatter = formatter;
		}

		public bool TryGetRow(StatusProviderContext context, out StatusRowSnapshot row)
		{
			row = default(StatusRowSnapshot);
			float num = Mathf.Max(reads.MaxFrostbite(context.Player), 1E-05f);
			float num2 = Mathf.Clamp(reads.Frostbite(context.Player), 0f, num);
			if (!reads.IsFrostbiteActive(context.Player) && !(num2 > 0.01f))
			{
				return false;
			}
			float num3 = Mathf.Clamp01(num2 / num);
			row = new StatusRowSnapshot(StatusRowKind.Frostbite, Id, "FROSTBITE", num3, SortOrder, formatter.FrostbiteValue(context.Player, num2, num), num3 >= 0.75f);
			return true;
		}
	}
}
namespace FairyDust.Hud.Modules.Status.Entities
{
	internal interface IStatusProvider
	{
		string Id { get; }

		int SortOrder { get; }

		bool IsEnabled { get; }

		bool TryGetRow(StatusProviderContext context, out StatusRowSnapshot row);
	}
	internal readonly struct StatusProviderContext
	{
		public FFPlayer Player { get; }

		public FFDataDeck Deck { get; }

		public StatusProviderContext(FFPlayer player, FFDataDeck deck)
		{
			Player = player;
			Deck = deck;
		}
	}
	internal enum StatusRowKind
	{
		Bleed,
		Infection,
		Frostbite,
		Stamina
	}
	internal readonly struct StatusRowSnapshot
	{
		public StatusRowKind Kind { get; }

		public string Id { get; }

		public string Label { get; }

		public float Ratio { get; }

		public int SortOrder { get; }

		public string ValueText { get; }

		public bool Warning { get; }

		public StatusRowSnapshot(StatusRowKind kind, string id, string label, float ratio, int sortOrder, string valueText = null, bool warning = false)
		{
			Kind = kind;
			Id = id;
			Label = label;
			Ratio = Mathf.Clamp01(ratio);
			SortOrder = sortOrder;
			ValueText = valueText;
			Warning = warning;
		}
	}
}
namespace FairyDust.Hud.Modules.Status.Bleed
{
	internal sealed class BleedStatusModule
	{
		public IStatusProvider CreateProvider(PlayerStatusReadService reads, StatusFormatterService formatter)
		{
			return new BleedStatusProvider(reads, formatter);
		}
	}
	internal sealed class BleedStatusProvider : IStatusProvider
	{
		private const float LowWarningRatio = 0.25f;

		private readonly PlayerStatusReadService reads;

		private readonly StatusFormatterService formatter;

		public string Id => "bleed";

		public int SortOrder => 0;

		public bool IsEnabled => Config.Values.BleedOutModuleEnabled;

		public BleedStatusProvider(PlayerStatusReadService reads, StatusFormatterService formatter)
		{
			this.reads = reads;
			this.formatter = formatter;
		}

		public bool TryGetRow(StatusProviderContext context, out StatusRowSnapshot row)
		{
			row = default(StatusRowSnapshot);
			if (!reads.IsBleeding(context.Player))
			{
				return false;
			}
			float num = Mathf.Max(reads.BleedToDeathTime(context.Player), 1E-05f);
			float num2 = Mathf.Max(0f, reads.BleedToDeathTimer(context.Player));
			float num3 = Mathf.Clamp01(num2 / num);
			row = new StatusRowSnapshot(StatusRowKind.Bleed, Id, "BLEED", num3, SortOrder, formatter.Timer(num2), num3 <= 0.25f);
			return true;
		}
	}
}
namespace FairyDust.Hud.Host
{
	internal sealed class GameplayHudHost
	{
		private const string RigObjectName = "FairyDust_HudRig";

		private const string CanvasObjectName = "FairyDust_GameHud";

		private const string DockObjectName = "FairyDust_HudDock";

		private readonly MelonMod hostMod;

		private readonly List<IHudModule> modules = new List<IHudModule>();

		private GameObject hudRig;

		private GameObject canvasRoot;

		private Canvas hudCanvas;

		private CanvasScaler hudCanvasScaler;

		private RectTransform dockRoot;

		private VerticalLayoutGroup dockLayoutGroup;

		private Vector2 lastDockPosition = new Vector2(float.NaN, float.NaN);

		private float lastDockSpacing = float.NaN;

		private bool disposed;

		private DateTime nextConfigReloadCheckUtc = DateTime.MinValue;

		private bool loggedConfigReloadFailure;

		public GameplayHudHost(MelonMod hostMod)
		{
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_001b: Unknown result type (might be due to invalid IL or missing references)
			this.hostMod = hostMod;
		}

		public void Register(IHudModule module)
		{
			modules.Add(module);
		}

		public void Initialize()
		{
			BuildCanvasAndDock();
			for (int i = 0; i < modules.Count; i++)
			{
				IHudModule hudModule = modules[i];
				HudModuleContext context = new HudModuleContext(CreateModuleSlot(dockRoot, hudModule.SlotObjectName), hostMod);
				hudModule.OnAttach(context);
			}
		}

		public void OnSceneWasLoaded(int buildIndex, string sceneName)
		{
			WorldSceneGate.OnSceneWasLoaded(buildIndex, sceneName);
			for (int i = 0; i < modules.Count; i++)
			{
				modules[i].OnSceneWasLoaded(buildIndex, sceneName);
			}
		}

		public void OnLateUpdate()
		{
			if (disposed)
			{
				return;
			}
			ReloadConfigIfDue();
			if (!Config.Values.Enabled)
			{
				SetCanvasActive(on: false);
				return;
			}
			if (!WorldSceneGate.IsActiveGameplayScene)
			{
				SetCanvasActive(on: false);
				return;
			}
			SetCanvasActive(on: true);
			UpdateDockLayout();
			for (int i = 0; i < modules.Count; i++)
			{
				modules[i].OnLateUpdate();
			}
		}

		private void ReloadConfigIfDue()
		{
			DateTime utcNow = DateTime.UtcNow;
			if (utcNow < nextConfigReloadCheckUtc)
			{
				return;
			}
			nextConfigReloadCheckUtc = utcNow + TimeSpan.FromSeconds(1.0);
			try
			{
				if (Config.ReloadIfChanged())
				{
					loggedConfigReloadFailure = false;
				}
			}
			catch (Exception ex)
			{
				if (!loggedConfigReloadFailure)
				{
					loggedConfigReloadFailure = true;
					((MelonBase)hostMod).LoggerInstance.Warning("HUD config reload failed: " + ex);
				}
			}
		}

		private void SetCanvasActive(bool on)
		{
			if ((Object)(object)hudRig != (Object)null)
			{
				hudRig.SetActive(on);
			}
		}

		private void UpdateDockLayout()
		{
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_0045: Unknown result type (might be due to invalid IL or missing references)
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0052: Unknown result type (might be due to invalid IL or missing references)
			//IL_0053: Unknown result type (might be due to invalid IL or missing references)
			if (!((Object)(object)dockRoot == (Object)null))
			{
				Vector2 val = default(Vector2);
				((Vector2)(ref val))..ctor(24f, 24f);
				bool flag = false;
				if (dockRoot.anchoredPosition != val)
				{
					dockRoot.anchoredPosition = val;
					flag = true;
				}
				if (val != lastDockPosition)
				{
					lastDockPosition = val;
					flag = true;
				}
				if ((Object)(object)dockLayoutGroup != (Object)null && !Mathf.Approximately(((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).spacing, 8f))
				{
					((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).spacing = 8f;
					flag = true;
				}
				if (!Mathf.Approximately(lastDockSpacing, 8f))
				{
					lastDockSpacing = 8f;
					flag = true;
				}
				if (flag)
				{
					LayoutRebuilder.MarkLayoutForRebuild(dockRoot);
				}
			}
		}

		private void BuildCanvasAndDock()
		{
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0015: Expected O, but got Unknown
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Expected O, but got Unknown
			//IL_008f: 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_00af: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ba: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f3: Unknown result type (might be due to invalid IL or missing references)
			//IL_011e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0124: Expected O, but got Unknown
			//IL_015f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0179: Unknown result type (might be due to invalid IL or missing references)
			//IL_0193: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ad: Unknown result type (might be due to invalid IL or missing references)
			//IL_022c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0236: Expected O, but got Unknown
			//IL_0249: Unknown result type (might be due to invalid IL or missing references)
			//IL_024e: Unknown result type (might be due to invalid IL or missing references)
			DestroyExistingRig();
			hudRig = new GameObject("FairyDust_HudRig");
			Object.DontDestroyOnLoad((Object)(object)hudRig);
			canvasRoot = new GameObject("FairyDust_GameHud");
			canvasRoot.transform.SetParent(hudRig.transform, false);
			Canvas val = (hudCanvas = canvasRoot.AddComponent<Canvas>());
			val.renderMode = (RenderMode)0;
			val.worldCamera = null;
			val.overrideSorting = true;
			val.sortingOrder = 99;
			val.pixelPerfect = false;
			RectTransform component = canvasRoot.GetComponent<RectTransform>();
			component.anchorMin = Vector2.zero;
			component.anchorMax = Vector2.one;
			component.pivot = new Vector2(0.5f, 0.5f);
			component.offsetMin = Vector2.zero;
			component.offsetMax = Vector2.zero;
			CanvasScaler val2 = (hudCanvasScaler = canvasRoot.AddComponent<CanvasScaler>());
			val2.uiScaleMode = (ScaleMode)1;
			val2.referenceResolution = new Vector2(1920f, 1080f);
			val2.matchWidthOrHeight = 0.5f;
			canvasRoot.AddComponent<GraphicRaycaster>().blockingObjects = (BlockingObjects)0;
			GameObject val3 = new GameObject("FairyDust_HudDock");
			val3.transform.SetParent(canvasRoot.transform, false);
			val3.layer = 31;
			dockRoot = val3.AddComponent<RectTransform>();
			dockRoot.anchorMin = new Vector2(0f, 0f);
			dockRoot.anchorMax = new Vector2(0f, 0f);
			dockRoot.pivot = new Vector2(0f, 0f);
			dockRoot.anchoredPosition = new Vector2(24f, 24f);
			ContentSizeFitter obj = val3.AddComponent<ContentSizeFitter>();
			obj.horizontalFit = (FitMode)2;
			obj.verticalFit = (FitMode)2;
			dockLayoutGroup = val3.AddComponent<VerticalLayoutGroup>();
			((LayoutGroup)dockLayoutGroup).childAlignment = (TextAnchor)6;
			((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).childControlWidth = false;
			((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).childControlHeight = false;
			((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).childForceExpandWidth = false;
			((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).childForceExpandHeight = false;
			((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).spacing = 8f;
			((LayoutGroup)dockLayoutGroup).padding = new RectOffset(0, 0, 0, 0);
			((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).reverseArrangement = false;
			lastDockPosition = dockRoot.anchoredPosition;
			lastDockSpacing = ((HorizontalOrVerticalLayoutGroup)dockLayoutGroup).spacing;
		}

		public void Shutdown()
		{
			disposed = true;
			if ((Object)(object)hudRig != (Object)null)
			{
				hudRig.SetActive(false);
				Object.Destroy((Object)(object)hudRig);
				hudRig = null;
			}
			canvasRoot = null;
			dockRoot = null;
			dockLayoutGroup = null;
		}

		private static RectTransform CreateModuleSlot(RectTransform dock, string objectName)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_001b: 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_0042: 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_0061: Unknown result type (might be due to invalid IL or missing references)
			GameObject val = new GameObject(objectName);
			val.transform.SetParent((Transform)(object)dock, false);
			val.layer = 31;
			RectTransform val2 = val.AddComponent<RectTransform>();
			val2.anchorMin = new Vector2(0f, 0f);
			val2.anchorMax = new Vector2(0f, 0f);
			val2.pivot = new Vector2(0f, 0f);
			val.AddComponent<LayoutElement>();
			CanvasGroup obj = val.AddComponent<CanvasGroup>();
			obj.alpha = 1f;
			obj.interactable = false;
			obj.blocksRaycasts = false;
			return val2;
		}

		private static void DestroyExistingRig()
		{
			GameObject[] array = Il2CppArrayBase<GameObject>.op_Implicit(Object.FindObjectsOfType<GameObject>(true));
			if (array == null)
			{
				return;
			}
			foreach (GameObject val in array)
			{
				if (!((Object)(object)val == (Object)null) && !(((Object)val).name != "FairyDust_HudRig"))
				{
					Object.Destroy((Object)(object)val);
				}
			}
		}
	}
	internal static class HudDockLayout
	{
		public const int CanvasSortingOrder = 99;

		public const int HudRenderLayer = 31;

		public const float HudCameraDepth = 1f;

		public const int MarginLeft = 24;

		public const int MarginBottom = 24;

		public const int ModuleStackSpacing = 8;
	}
	public sealed class HudModuleContext
	{
		public RectTransform Slot { get; }

		public MelonMod HostMod { get; }

		public HudModuleContext(RectTransform slot, MelonMod hostMod)
		{
			Slot = slot;
			HostMod = hostMod;
		}
	}
	public interface IHudModule
	{
		string SlotObjectName { get; }

		void OnAttach(HudModuleContext context);

		void OnSceneWasLoaded(int buildIndex, string sceneName);

		void OnLateUpdate();
	}
	internal static class WorldSceneGate
	{
		public const string ForsakenWorldSceneName = "Forsaken Frontiers";

		private static string activeSceneName = string.Empty;

		public static bool IsForsakenWorldLoaded => string.Equals(activeSceneName, "Forsaken Frontiers", StringComparison.Ordinal);

		public static bool IsActiveGameplayScene
		{
			get
			{
				//IL_0000: 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)
				Scene activeScene = SceneManager.GetActiveScene();
				return string.Equals(((Scene)(ref activeScene)).name, "Forsaken Frontiers", StringComparison.Ordinal);
			}
		}

		public static void OnSceneWasLoaded(int buildIndex, string sceneName)
		{
			activeSceneName = sceneName ?? string.Empty;
		}
	}
}
namespace FairyDust.Hud.Game.Services
{
	internal static class FairyLocalPlayer
	{
		public static FFPlayer Current
		{
			get
			{
				FairyPlayer localPlayer = FairyEngine.LocalPlayer;
				if (localPlayer == null)
				{
					return null;
				}
				return ((Il2CppObjectBase)localPlayer).TryCast<FFPlayer>();
			}
		}
	}
}
namespace FairyDust.Hud.Configuration
{
	public static class Config
	{
		private static MelonPreferences_ReflectiveCategory category;

		private static readonly HashSet<string> LoggedInvalidConfigEntries = new HashSet<string>(StringComparer.OrdinalIgnoreCase);

		private static DateTime lastLoadedWriteTimeUtc = DateTime.MinValue;

		public static string FilePath { get; private set; } = string.Empty;


		public static ModConfiguration Values { get; private set; } = new ModConfiguration();


		public static void Initialize()
		{
			HudEnvironment.EnsureUserDataDirectory();
			FilePath = HudEnvironment.ConfigFilePath;
			bool num = File.Exists(FilePath);
			category = MelonPreferences.CreateCategory<ModConfiguration>("FairyDust.Hud", (string)null);
			category.SetFilePath(FilePath, false, false);
			category.LoadFromFile(false);
			category.DestroyFileWatcher();
			Values = LoadValuesFromFile();
			lastLoadedWriteTimeUtc = GetConfigWriteTimeUtc();
			if (!num)
			{
				Save();
				Values = LoadValuesFromFile();
				lastLoadedWriteTimeUtc = GetConfigWriteTimeUtc();
			}
		}

		public static void Save()
		{
			GetCategory().SaveToFile(false);
			lastLoadedWriteTimeUtc = GetConfigWriteTimeUtc();
		}

		public static bool ReloadIfChanged()
		{
			DateTime configWriteTimeUtc = GetConfigWriteTimeUtc();
			if (configWriteTimeUtc == DateTime.MinValue || configWriteTimeUtc <= lastLoadedWriteTimeUtc)
			{
				return false;
			}
			Values = LoadValuesFromFile();
			lastLoadedWriteTimeUtc = configWriteTimeUtc;
			return true;
		}

		private static ModConfiguration LoadValuesFromFile()
		{
			ModConfiguration modConfiguration = new ModConfiguration();
			ApplyFileOverrides(modConfiguration);
			return modConfiguration;
		}

		private static void ApplyFileOverrides(ModConfiguration values)
		{
			if (File.Exists(FilePath))
			{
				Dictionary<string, string> entries = ReadSection(FilePath, "FairyDust.Hud");
				ApplyBool(entries, "Enabled", delegate(bool value)
				{
					values.Enabled = value;
				});
				ApplyBool(entries, "StaminaModuleEnabled", delegate(bool value)
				{
					values.StaminaModuleEnabled = value;
				});
				ApplyBool(entries, "BleedOutModuleEnabled", delegate(bool value)
				{
					values.BleedOutModuleEnabled = value;
				});
				ApplyBool(entries, "InfectionModuleEnabled", delegate(bool value)
				{
					values.InfectionModuleEnabled = value;
				});
				ApplyBool(entries, "FrostbiteModuleEnabled", delegate(bool value)
				{
					values.FrostbiteModuleEnabled = value;
				});
			}
		}

		private static Dictionary<string, string> ReadSection(string path, string sectionName)
		{
			Dictionary<string, string> dictionary = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
			bool flag = false;
			foreach (string item in File.ReadLines(path))
			{
				string text = item.Trim();
				if (text.Length == 0 || text.StartsWith("#") || text.StartsWith(";"))
				{
					continue;
				}
				if (text.StartsWith("[") && text.EndsWith("]"))
				{
					flag = string.Equals(text.Substring(1, text.Length - 2).Trim(), sectionName, StringComparison.OrdinalIgnoreCase);
				}
				else if (flag)
				{
					int num = text.IndexOf('=');
					if (num > 0)
					{
						string key = text.Substring(0, num).Trim();
						string value = text.Substring(num + 1).Trim();
						dictionary[key] = value;
					}
				}
			}
			return dictionary;
		}

		private static void ApplyBool(Dictionary<string, string> entries, string key, Action<bool> apply)
		{
			if (!entries.TryGetValue(key, out var value))
			{
				return;
			}
			if (bool.TryParse(value, out var result))
			{
				apply(result);
				return;
			}
			string item = key + "=" + value;
			if (LoggedInvalidConfigEntries.Add(item))
			{
				MelonLogger.Warning("[FairyDust.Hud] Ignoring invalid bool config value for " + key + ": " + value);
			}
		}

		private static DateTime GetConfigWriteTimeUtc()
		{
			try
			{
				return File.Exists(FilePath) ? File.GetLastWriteTimeUtc(FilePath) : DateTime.MinValue;
			}
			catch
			{
				return DateTime.MinValue;
			}
		}

		private static MelonPreferences_ReflectiveCategory GetCategory()
		{
			return category ?? throw new InvalidOperationException("Config.Initialize() must be called before saving preferences.");
		}
	}
	internal static class ConfigConsoleCard
	{
		private const int Width = 58;

		private static readonly string Border = "+" + new string('-', 58) + "+";

		public static string Build()
		{
			StringBuilder stringBuilder = new StringBuilder();
			stringBuilder.AppendLine();
			stringBuilder.AppendLine(Border);
			stringBuilder.AppendLine(RowCentered("FairyDust.Hud"));
			stringBuilder.AppendLine(Border);
			stringBuilder.AppendLine(RowKeyValue("Version", "1.0.0"));
			stringBuilder.AppendLine(RowKeyValue("File", DisplayConfigPath()));
			stringBuilder.AppendLine(Border);
			stringBuilder.AppendLine(RowText("Status Modules"));
			stringBuilder.AppendLine(RowText(string.Empty));
			stringBuilder.AppendLine(RowSetting(Config.Values.Enabled, "HUD"));
			stringBuilder.AppendLine(RowSetting(Config.Values.StaminaModuleEnabled, "Stamina"));
			stringBuilder.AppendLine(RowSetting(Config.Values.BleedOutModuleEnabled, "Bleed Out"));
			stringBuilder.AppendLine(RowSetting(Config.Values.InfectionModuleEnabled, "Infection"));
			stringBuilder.AppendLine(RowSetting(Config.Values.FrostbiteModuleEnabled, "Frostbite"));
			stringBuilder.AppendLine(Border);
			stringBuilder.AppendLine(RowText("Auto-reload is active. Changes apply while in game."));
			stringBuilder.Append(Border);
			return stringBuilder.ToString();
		}

		private static string DisplayConfigPath()
		{
			try
			{
				string userDataDirectory = HudEnvironment.UserDataDirectory;
				string filePath = Config.FilePath;
				if (!string.IsNullOrEmpty(userDataDirectory) && !string.IsNullOrEmpty(filePath) && filePath.StartsWith(userDataDirectory, StringComparison.OrdinalIgnoreCase))
				{
					string fileName = Path.GetFileName(filePath);
					if (!string.IsNullOrEmpty(fileName))
					{
						return Path.Combine("UserData", fileName);
					}
				}
			}
			catch
			{
			}
			return Config.FilePath;
		}

		private static string RowSetting(bool enabled, string label)
		{
			return RowText("  " + (enabled ? "[ON]  " : "[OFF] ") + label);
		}

		private static string RowKeyValue(string key, string value)
		{
			return RowText(key.PadRight(9) + (value ?? string.Empty));
		}

		private static string RowCentered(string value)
		{
			if (value == null)
			{
				value = string.Empty;
			}
			if (value.Length >= 58)
			{
				return RowText(value);
			}
			int count = (58 - value.Length) / 2;
			return RowText(new string(' ', count) + value);
		}

		private static string RowText(string value)
		{
			if (value == null)
			{
				value = string.Empty;
			}
			if (value.Length > 0 && !char.IsWhiteSpace(value[0]))
			{
				value = "  " + value;
			}
			if (value.Length > 58)
			{
				value = value.Substring(0, 58);
			}
			return "|" + value.PadRight(58) + "|";
		}
	}
	public static class HudEnvironment
	{
		private static string _modDir;

		private static string _userDataDir;

		public static string BaseDirectory => AppContext.BaseDirectory;

		public static string GameRootDirectory => BaseDirectory;

		public static string ModAssemblyDirectory
		{
			get
			{
				object obj = _modDir;
				if (obj == null)
				{
					obj = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) ?? string.Empty;
					_modDir = (string)obj;
				}
				return (string)obj;
			}
		}

		public static string ModsDirectory => Path.Combine(BaseDirectory, "Mods");

		public static string UserDataDirectory => _userDataDir ?? (_userDataDir = ResolveMelonUserDataDirectory());

		public static string MelonLoaderDirectory => Path.Combine(BaseDirectory, "MelonLoader");

		public static string Il2CppAssembliesDirectory => Path.Combine(MelonLoaderDirectory, "Il2CppAssemblies");

		public static string ConfigFilePath => Path.Combine(UserDataDirectory, "FairyDust.Hud.cfg");

		private static string ResolveMelonUserDataDirectory()
		{
			try
			{
				Type type = typeof(MelonMod).Assembly.GetType("MelonLoader.MelonUtils");
				if (type != null)
				{
					string staticString = GetStaticString(type, "UserDataDirectory");
					if (!string.IsNullOrEmpty(staticString))
					{
						return staticString;
					}
					string staticString2 = GetStaticString(type, "GameDirectory");
					if (!string.IsNullOrEmpty(staticString2))
					{
						return Path.Combine(staticString2, "UserData");
					}
				}
			}
			catch
			{
			}
			return Path.Combine(BaseDirectory, "UserData");
		}

		private static string GetStaticString(Type t, string name)
		{
			return t.GetProperty(name, BindingFlags.Static | BindingFlags.Public)?.GetValue(null) as string;
		}

		public static void EnsureUserDataDirectory()
		{
			Directory.CreateDirectory(UserDataDirectory);
		}
	}
	public sealed class ModConfiguration
	{
		public bool Enabled = true;

		public bool StaminaModuleEnabled = true;

		public bool BleedOutModuleEnabled = true;

		public bool InfectionModuleEnabled = true;

		public bool FrostbiteModuleEnabled = true;
	}
}
namespace FairyDust.Hud.Components.Deck
{
	internal static class DeckStatusPanel
	{
		public const int DefaultRowCapacity = 4;

		public const float StrokePx = 2f;

		public const float PadPx = 7f;

		public const float RowHeightPx = 36f;

		public const float LabelWidthPx = 132f;

		public const float BarWidthPx = 136f;

		public const float BarHeightPx = 13f;

		public const float ValueWidthPx = 68f;

		public const float LabelHeightPx = 21f;

		private static readonly Color PanelBackground = new Color(0f, 0f, 0f, 0.15f);

		internal static readonly Color TrackColor = new Color(0.02f, 0.02f, 0.02f, 0.06f);

		private static readonly Color EmptyValueColor = new Color(1f, 1f, 1f, 0f);

		private static Sprite whiteUnitSprite;

		private static Texture2D whiteUnitTexture;

		public static Vector2 PreferredOuterSize => OuterSizeForRows(4);

		public static Vector2 OuterSizeForRows(int visibleRowCount)
		{
			//IL_0019: Unknown result type (might be due to invalid IL or missing references)
			return new Vector2(354f, 18f + 36f * (float)Mathf.Max(1, visibleRowCount));
		}

		public static DeckStatusPanelHandle Build(RectTransform slot, FFDataDeck deck, string rootName, int rowCapacity)
		{
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0044: Unknown result type (might be due to invalid IL or missing references)
			//IL_0059: Unknown result type (might be due to invalid IL or missing references)
			//IL_006b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0076: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ce: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e4: 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)
			rowCapacity = Mathf.Max(1, rowCapacity);
			List<Image> list = new List<Image>();
			List<TextMeshProUGUI> list2 = new List<TextMeshProUGUI>();
			GameObject val = CreateChild(rootName, (Transform)(object)slot);
			RectTransform obj = val.AddComponent<RectTransform>();
			obj.anchorMin = Vector2.zero;
			obj.anchorMax = Vector2.one;
			obj.offsetMin = Vector2.zero;
			obj.offsetMax = Vector2.zero;
			Image val2 = CreateImage("Background", val.transform, PanelBackground);
			RectTransform rectTransform = ((Graphic)val2).rectTransform;
			rectTransform.anchorMin = Vector2.zero;
			rectTransform.anchorMax = Vector2.one;
			rectTransform.offsetMin = new Vector2(2f, 2f);
			rectTransform.offsetMax = new Vector2(-2f, -2f);
			RectTransform val3 = CreateChild("Content", val.transform).AddComponent<RectTransform>();
			val3.anchorMin = Vector2.zero;
			val3.anchorMax = Vector2.one;
			val3.offsetMin = new Vector2(9f, 9f);
			val3.offsetMax = new Vector2(-9f, -9f);
			DeckStatusRow[] array = new DeckStatusRow[rowCapacity];
			for (int i = 0; i < rowCapacity; i++)
			{
				array[i] = BuildRow(val3, deck, list, list2, i);
			}
			return new DeckStatusPanelHandle(val, array, val2, list.ToArray(), list2.ToArray());
		}

		private static DeckStatusRow BuildRow(RectTransform parent, FFDataDeck deck, List<Image> tintedImages, List<TextMeshProUGUI> tintedTexts, int index)
		{
			//IL_0029: 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_0053: Unknown result type (might be due to invalid IL or missing references)
			//IL_006c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0080: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ab: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f4: Unknown result type (might be due to invalid IL or missing references)
			//IL_013b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0150: Unknown result type (might be due to invalid IL or missing references)
			//IL_0165: Unknown result type (might be due to invalid IL or missing references)
			//IL_017a: Unknown result type (might be due to invalid IL or missing references)
			//IL_018e: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a3: 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_01c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_01cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_01d5: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ea: Unknown result type (might be due to invalid IL or missing references)
			//IL_01fe: Unknown result type (might be due to invalid IL or missing references)
			//IL_0209: Unknown result type (might be due to invalid IL or missing references)
			//IL_021e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0232: Unknown result type (might be due to invalid IL or missing references)
			//IL_0254: Unknown result type (might be due to invalid IL or missing references)
			//IL_0275: Unknown result type (might be due to invalid IL or missing references)
			//IL_028b: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ad: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b9: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ff: Unknown result type (might be due to invalid IL or missing references)
			//IL_0314: Unknown result type (might be due to invalid IL or missing references)
			//IL_0329: Unknown result type (might be due to invalid IL or missing references)
			//IL_033e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0352: Unknown result type (might be due to invalid IL or missing references)
			//IL_0374: Unknown result type (might be due to invalid IL or missing references)
			GameObject val = CreateChild("Row" + index, (Transform)(object)parent);
			RectTransform obj = val.AddComponent<RectTransform>();
			obj.anchorMin = new Vector2(0f, 1f);
			obj.anchorMax = new Vector2(1f, 1f);
			obj.pivot = new Vector2(0f, 1f);
			obj.anchoredPosition = new Vector2(0f, -36f * (float)index);
			obj.sizeDelta = new Vector2(0f, 36f);
			GameObject obj2 = CreateChild("Label", val.transform);
			RectTransform obj3 = obj2.AddComponent<RectTransform>();
			obj3.anchorMin = new Vector2(0f, 0.5f);
			obj3.anchorMax = new Vector2(0f, 0.5f);
			obj3.pivot = new Vector2(0f, 0.5f);
			obj3.anchoredPosition = Vector2.zero;
			obj3.sizeDelta = new Vector2(132f, 21f);
			TextMeshProUGUI val2 = obj2.AddComponent<TextMeshProUGUI>();
			SetupText(val2, deck, 21f, rightAligned: false);
			tintedTexts.Add(val2);
			GameObject val3 = CreateChild("Bar", val.transform);
			RectTransform obj4 = val3.AddComponent<RectTransform>();
			obj4.anchorMin = new Vector2(0f, 0.5f);
			obj4.anchorMax = new Vector2(0f, 0.5f);
			obj4.pivot = new Vector2(0f, 0.5f);
			obj4.anchoredPosition = new Vector2(132f, 0f);
			obj4.sizeDelta = new Vector2(136f, 13f);
			Image val4 = CreateImage("Track", val3.transform, TrackColor);
			RectTransform rectTransform = ((Graphic)val4).rectTransform;
			rectTransform.anchorMin = Vector2.zero;
			rectTransform.anchorMax = Vector2.one;
			rectTransform.offsetMin = Vector2.zero;
			rectTransform.offsetMax = Vector2.zero;
			Image val5 = CreateImage("LowWarning", ((Component)val4).transform, Color.white);
			RectTransform rectTransform2 = ((Graphic)val5).rectTransform;
			rectTransform2.anchorMin = Vector2.zero;
			rectTransform2.anchorMax = Vector2.one;
			rectTransform2.offsetMin = new Vector2(-4f, -3f);
			rectTransform2.offsetMax = new Vector2(4f, 3f);
			((Component)val5).gameObject.SetActive(false);
			Image val6 = CreateImage("Fill", ((Component)val4).transform, Color.white);
			RectTransform rectTransform3 = ((Graphic)val6).rectTransform;
			rectTransform3.anchorMin = new Vector2(0f, 0f);
			rectTransform3.anchorMax = new Vector2(0f, 1f);
			rectTransform3.pivot = new Vector2(0f, 0.5f);
			rectTransform3.anchoredPosition = Vector2.zero;
			rectTransform3.sizeDelta = Vector2.zero;
			if ((Object)(object)deck != (Object)null)
			{
				DeckTint.BindImage(val6, deck, darken: false);
			}
			tintedImages.Add(val6);
			GameObject obj5 = CreateChild("Value", val.transform);
			RectTransform obj6 = obj5.AddComponent<RectTransform>();
			obj6.anchorMin = new Vector2(0f, 0.5f);
			obj6.anchorMax = new Vector2(0f, 0.5f);
			obj6.pivot = new Vector2(1f, 0.5f);
			obj6.anchoredPosition = new Vector2(336f, 0f);
			obj6.sizeDelta = new Vector2(68f, 21f);
			TextMeshProUGUI val7 = obj5.AddComponent<TextMeshProUGUI>();
			SetupText(val7, deck, 21f, rightAligned: true);
			((Graphic)val7).color = EmptyValueColor;
			tintedTexts.Add(val7);
			return new DeckStatusRow(val, val2, val7, val4, val5, val6, rectTransform3);
		}

		private static void SetupText(TextMeshProUGUI text, FFDataDeck deck, float targetHeight, bool rightAligned, bool bindTint = true)
		{
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			((Graphic)text).raycastTarget = false;
			((TMP_Text)text).enableWordWrapping = false;
			((TMP_Text)text).overflowMode = (TextOverflowModes)0;
			((TMP_Text)text).margin = Vector4.zero;
			((Graphic)text).color = Color.white;
			DeckTextStyle.Apply(text, deck, targetHeight);
			((TMP_Text)text).alignment = (TextAlignmentOptions)(rightAligned ? 4100 : 4097);
			if (bindTint && (Object)(object)deck != (Object)null)
			{
				DeckTint.BindText(text, deck, darken: false);
			}
		}

		private static Image CreateImage(string name, Transform parent, Color color)
		{
			//IL_001f: Unknown result type (might be due to invalid IL or missing references)
			Image obj = CreateChild(name, parent).AddComponent<Image>();
			obj.sprite = White();
			obj.type = (Type)0;
			((Graphic)obj).color = color;
			((Graphic)obj).raycastTarget = false;
			return obj;
		}

		private static GameObject CreateChild(string name, Transform parent)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_0014: Expected O, but got Unknown
			GameObject val = new GameObject(name);
			val.transform.SetParent(parent, false);
			return val;
		}

		private static Sprite White()
		{
			//IL_0017: Unknown result type (might be due to invalid IL or missing references)
			//IL_0021: Expected O, but got Unknown
			//IL_0028: 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_0066: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)whiteUnitSprite != (Object)null)
			{
				return whiteUnitSprite;
			}
			whiteUnitTexture = new Texture2D(1, 1, (TextureFormat)4, false);
			whiteUnitTexture.SetPixel(0, 0, Color.white);
			whiteUnitTexture.Apply(false, true);
			whiteUnitSprite = Sprite.Create(whiteUnitTexture, new Rect(0f, 0f, 1f, 1f), new Vector2(0.5f, 0.5f), 100f);
			return whiteUnitSprite;
		}

		public static void ReleaseSharedAssets()
		{
			try
			{
				if ((Object)(object)whiteUnitSprite != (Object)null)
				{
					Object.Destroy((Object)(object)whiteUnitSprite);
					whiteUnitSprite = null;
				}
				if ((Object)(object)whiteUnitTexture != (Object)null)
				{
					Object.Destroy((Object)(object)whiteUnitTexture);
					whiteUnitTexture = null;
				}
			}
			catch
			{
			}
		}
	}
	internal readonly struct DeckStatusPanelHandle
	{
		public GameObject Root { get; }

		public DeckStatusRow[] Rows { get; }

		private Image Background { get; }

		private Image[] TintedImages { get; }

		private TextMeshProUGUI[] TintedTexts { get; }

		public bool IsValid
		{
			get
			{
				if ((Object)(object)Root != (Object)null && Rows != null)
				{
					return Rows.Length != 0;
				}
				return false;
			}
		}

		public DeckStatusPanelHandle(GameObject root, DeckStatusRow[] rows, Image background, Image[] tintedImages, TextMeshProUGUI[] tintedTexts)
		{
			Root = root;
			Rows = rows;
			Background = background;
			TintedImages = tintedImages;
			TintedTexts = tintedTexts;
		}

		public void SetVisible(bool visible)
		{
			try
			{
				if ((Object)(object)Root != (Object)null && Root.activeSelf != visible)
				{
					Root.SetActive(visible);
				}
			}
			catch
			{
			}
		}

		public void SetRow(int index, string label, float ratio, string valueText = null, bool lowWarning = false)
		{
			if (!IsValid || index < 0 || index >= Rows.Length)
			{
				return;
			}
			try
			{
				Rows[index].Set(label, ratio, valueText, lowWarning);
			}
			catch
			{
			}
		}

		public void SetBackgroundAlpha(float alpha)
		{
			//IL_0037: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0050: Unknown result type (might be due to invalid IL or missing references)
			//IL_0055: Unknown result type (might be due to invalid IL or missing references)
			//IL_0063: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				if ((Object)(object)Background != (Object)null)
				{
					bool flag = alpha > 0.001f;
					if (((Behaviour)Background).enabled != flag)
					{
						((Behaviour)Background).enabled = flag;
					}
					Color color = ((Graphic)Background).color;
					color.a = Mathf.Clamp01(alpha);
					if (((Graphic)Background).color != color)
					{
						((Graphic)Background).color = color;
					}
				}
			}
			catch
			{
			}
		}

		public void SetRowVisible(int index, bool visible)
		{
			if (!IsValid || index < 0 || index >= Rows.Length)
			{
				return;
			}
			try
			{
				if (Rows[index].IsVisible != visible)
				{
					Rows[index].SetVisible(visible);
				}
			}
			catch
			{
			}
		}

		public void ClearRows()
		{
			if (!IsValid)
			{
				return;
			}
			for (int i = 0; i < Rows.Length; i++)
			{
				try
				{
					if (Rows[i].IsVisible)
					{
						Rows[i].SetVisible(visible: false);
					}
				}
				catch
				{
				}
			}
		}

		public int ApplyVisibleLayout()
		{
			if (!IsValid)
			{
				return 0;
			}
			int num = 0;
			for (int i = 0; i < Rows.Length; i++)
			{
				bool isVisible;
				try
				{
					isVisible = Rows[i].IsVisible;
				}
				catch
				{
					continue;
				}
				if (isVisible)
				{
					try
					{
						Rows[i].SetVisualIndex(num);
					}
					catch
					{
					}
					num++;
				}
			}
			return Mathf.Max(1, num);
		}

		public bool RefreshFlavor(FFDataDeck deck, bool refreshTextStyle)
		{
			//IL_00a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
			//IL_006d: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b8: Unknown result type (might be due to invalid IL or missing references)
			if (!IsValid || !DeckTextStyle.TryResolveDeckColor(deck, out var color))
			{
				return false;
			}
			if (TintedTexts != null)
			{
				for (int i = 0; i < TintedTexts.Length; i++)
				{
					TextMeshProUGUI val = TintedTexts[i];
					if ((Object)(object)val == (Object)null)
					{
						continue;
					}
					try
					{
						if (refreshTextStyle)
						{
							DeckTextStyle.Apply(val, deck, 21f);
							((TMP_Text)val).alignment = (TextAlignmentOptions)(string.Equals(((Object)((Component)val).gameObject).name, "Value", StringComparison.Ordinal) ? 4100 : 4097);
						}
						((Graphic)val).color = color;
					}
					catch
					{
					}
				}
			}
			if (TintedImages != null)
			{
				for (int j = 0; j < TintedImages.Length; j++)
				{
					Image val2 = TintedImages[j];
					try
					{
						if ((Object)(object)val2 != (Object)null && ((Graphic)val2).color != color)
						{
							((Graphic)val2).color = color;
						}
					}
					catch
					{
					}
				}
			}
			return true;
		}

		public void Destroy()
		{
			try
			{
				if ((Object)(object)Root != (Object)null)
				{
					Object.Destroy((Object)(object)Root);
				}
			}
			catch
			{
			}
		}
	}
	internal readonly struct DeckStatusRow
	{
		private readonly GameObject root;

		private readonly TextMeshProUGUI label;

		private readonly TextMeshProUGUI value;

		private readonly Image track;

		private readonly Image lowWarning;

		private readonly Image fill;

		private readonly RectTransform fillRect;

		private readonly RectTransform rootRect;

		public bool IsVisible
		{
			get
			{
				try
				{
					return (Object)(object)root != (Object)null && root.activeSelf;
				}
				catch
				{
					return false;
				}
			}
		}

		public DeckStatusRow(GameObject root, TextMeshProUGUI label, TextMeshProUGUI value, Image track, Image lowWarning, Image fill, RectTransform fillRect)
		{
			this.root = root;
			rootRect = (((Object)(object)root != (Object)null) ? root.GetComponent<RectTransform>() : null);
			this.label = label;
			this.value = value;
			this.track = track;
			this.lowWarning = lowWarning;
			this.fill = fill;
			this.fillRect = fillRect;
		}

		public void SetVisible(bool visible)
		{
			try
			{
				if ((Object)(object)root != (Object)null && root.activeSelf != visible)
				{
					root.SetActive(visible);
				}
			}
			catch
			{
			}
		}

		public void SetVisualIndex(int index)
		{
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				if ((Object)(object)rootRect != (Object)null)
				{
					rootRect.anchoredPosition = new Vector2(0f, -36f * (float)index);
				}
			}
			catch
			{
			}
		}

		public void Set(string labelText, float ratio, string valueText, bool showLowWarning)
		{
			//IL_0074: Unknown result type (might be due to invalid IL or missing references)
			//IL_0079: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0115: Unknown result type (might be due to invalid IL or missing references)
			//IL_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_01aa: Unknown result type (might be due to invalid IL or missing references)
			//IL_01af: Unknown result type (might be due to invalid IL or missing references)
			//IL_013f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0140: Unknown result type (might be due to invalid IL or missing references)
			//IL_014a: Unknown result type (might be due to invalid IL or missing references)
			//IL_014f: 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_0168: Unknown result type (might be due to invalid IL or missing references)
			//IL_0169: Unknown result type (might be due to invalid IL or missing references)
			//IL_017a: Unknown result type (might be due to invalid IL or missing references)
			//IL_017f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0187: Unknown result type (might be due to invalid IL or missing references)
			//IL_018c: Unknown result type (might be due to invalid IL or missing references)
			//IL_01bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_019b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0284: Unknown result type (might be due to invalid IL or missing references)
			//IL_0277: 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_02ae: Unknown result type (might be due to invalid IL or missing references)
			//IL_028d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0294: Unknown result type (might be due to invalid IL or missing references)
			//IL_029b: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a7: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b0: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_02bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_02cc: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)root != (Object)null && !root.activeSelf)
			{
				root.SetActive(true);
			}
			if ((Object)(object)label != (Object)null)
			{
				string text = labelText ?? string.Empty;
				if (!string.Equals(((TMP_Text)label).text, text, StringComparison.Ordinal))
				{
					((TMP_Text)label).text = text;
				}
			}
			if ((Object)(object)track != (Object)null)
			{
				if (((Graphic)track).color != DeckStatusPanel.TrackColor)
				{
					((Graphic)track).color = DeckStatusPanel.TrackColor;
				}
				if (!((Component)track).gameObject.activeSelf)
				{
					((Component)track).gameObject.SetActive(true);
				}
			}
			if ((Object)(object)lowWarning != (Object)null && ((Component)lowWarning).gameObject.activeSelf)
			{
				((Component)lowWarning).gameObject.SetActive(false);
			}
			if ((Object)(object)fill != (Object)null)
			{
				Color val = (((Object)(object)label != (Object)null) ? ((Graphic)label).color : Color.white);
				if (showLowWarning)
				{
					float num = (Mathf.Sin(Time.unscaledTime * 4.5f) + 1f) * 0.5f;
					Color val2 = Color.Lerp(val, Color.black, 0.65f);
					val2.a = Mathf.Clamp01(val.a * 0.28f);
					Color val3 = Color.Lerp(val, val2, Mathf.Lerp(0.15f, 0.9f, num));
					if (((Graphic)fill).color != val3)
					{
						((Graphic)fill).color = val3;
					}
				}
				else if (((Graphic)fill).color != val)
				{
					((Graphic)fill).color = val;
				}
				if (!((Component)fill).gameObject.activeSelf)
				{
					((Component)fill).gameObject.SetActive(true);
				}
			}
			if ((Object)(object)fillRect != (Object)null)
			{
				float num2 = 136f * Mathf.Clamp01(ratio);
				fillRect.SetSizeWithCurrentAnchors((Axis)0, (num2 < 0.5f) ? 0f : num2);
			}
			if ((Object)(object)value != (Object)null)
			{
				bool num3 = !string.IsNullOrEmpty(valueText);
				string text2 = (num3 ? valueText : string.Empty);
				if (!string.Equals(((TMP_Text)value).text, text2, StringComparison.Ordinal))
				{
					((TMP_Text)value).text = text2;
				}
				Color val4 = (((Object)(object)label != (Object)null) ? ((Graphic)label).color : Color.white);
				Color val5 = (Color)(num3 ? val4 : new Color(val4.r, val4.g, val4.b, 0f));
				if (((Graphic)value).color != val5)
				{
					((Graphic)value).color = val5;
				}
			}
		}
	}
	internal static class DeckTextStyle
	{
		public static void Apply(TextMeshProUGUI label, FFDataDeck deck, float targetHeight)
		{
			//IL_0065: Unknown result type (might be due to invalid IL or missing references)
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d8: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)label == (Object)null)
			{
				return;
			}
			TextMeshProUGUI val = TryGetStyleSource(deck);
			if ((Object)(object)val == (Object)null)
			{
				((TMP_Text)label).fontSize = Mathf.Clamp(targetHeight, 10f, 24f);
				((TMP_Text)label).alignment = (TextAlignmentOptions)257;
				return;
			}
			try
			{
				((TMP_Text)label).font = ((TMP_Text)val).font;
				if ((Object)(object)((TMP_Text)val).fontSharedMaterial != (Object)null)
				{
					((TMP_Text)label).fontSharedMaterial = ((TMP_Text)val).fontSharedMaterial;
				}
				((TMP_Text)label).fontStyle = ((TMP_Text)val).fontStyle;
				((TMP_Text)label).fontWeight = ((TMP_Text)val).fontWeight;
				((TMP_Text)label).characterSpacing = ((TMP_Text)val).characterSpacing;
				((TMP_Text)label).wordSpacing = ((TMP_Text)val).wordSpacing;
			}
			catch
			{
				((TMP_Text)label).fontSize = Mathf.Clamp(targetHeight, 10f, 24f);
				((TMP_Text)label).alignment = (TextAlignmentOptions)257;
				return;
			}
			float num = 40f;
			if ((Object)(object)((TMP_Text)val).rectTransform != (Object)null)
			{
				num = Mathf.Max(1f, ((TMP_Text)val).rectTransform.sizeDelta.y);
			}
			((TMP_Text)label).fontSize = Mathf.Clamp(((TMP_Text)val).fontSize * (targetHeight / num), 10f, 24f);
			((TMP_Text)label).alignment = (TextAlignmentOptions)257;
			((TMP_Text)label).lineSpacing = 0f;
			((TMP_Text)label).paragraphSpacing = 0f;
		}

		public static Color ResolveDeckColor(FFDataDeck deck, Color fallback)
		{
			//IL_001d: Unknown result type (might be due to invalid IL or missing references)
			//IL_001e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0010: Unknown result type (might be due to invalid IL or missing references)
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			//IL_0014: Unknown result type (might be due to invalid IL or missing references)
			//IL_0019: Unknown result type (might be due to invalid IL or missing references)
			TextMeshProUGUI val = TryGetStyleSource(deck);
			if ((Object)(object)val == (Object)null)
			{
				return fallback;
			}
			try
			{
				return ((Graphic)val).color;
			}
			catch
			{
				return fallback;
			}
		}

		public static bool TryResolveDeckColor(FFDataDeck deck, out Color color)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_001c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			color = default(Color);
			TextMeshProUGUI val = TryGetStyleSource(deck);
			if ((Object)(object)val == (Object)null)
			{
				return false;
			}
			try
			{
				color = ((Graphic)val).color;
				return true;
			}
			catch
			{
				return false;
			}
		}

		private static TextMeshProUGUI TryGetStyleSource(FFDataDeck deck)
		{
			if ((Object)(object)deck == (Object)null)
			{
				return null;
			}
			TextMeshProUGUI[] array;
			try
			{
				array = (TextMeshProUGUI[])(object)new TextMeshProUGUI[4] { deck.gameTime, deck.characterName, deck.credits, deck.flavorText };
			}
			catch
			{
				return null;
			}
			foreach (TextMeshProUGUI val in array)
			{
				if (IsUsable(val))
				{
					return val;
				}
			}
			return null;
		}

		private static bool IsUsable(TextMeshProUGUI text)
		{
			if ((Object)(object)text == (Object)null)
			{
				return false;
			}
			try
			{
				_ = ((Component)text).gameObject;
				_ = ((TMP_Text)text).rectTransform;
				_ = ((TMP_Text)text).fontSize;
				return true;
			}
			catch
			{
				return false;
			}
		}
	}
	internal static class DeckTint
	{
		public static FFDataDeckUIColorer BindImage(Image image, FFDataDeck deck, bool darken)
		{
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_0017: Unknown result type (might be due to invalid IL or missing references)
			//IL_001f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_001c: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)image == (Object)null)
			{
				return null;
			}
			Color val = DeckTextStyle.ResolveDeckColor(deck, ((Graphic)image).color);
			((Graphic)image).color = (darken ? Darken(val) : val);
			return null;
		}

		public static FFDataDeckUIColorer BindText(TextMeshProUGUI text, FFDataDeck deck, bool darken)
		{
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_0017: Unknown result type (might be due to invalid IL or missing references)
			//IL_001f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_001c: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)text == (Object)null)
			{
				return null;
			}
			Color val = DeckTextStyle.ResolveDeckColor(deck, ((Graphic)text).color);
			((Graphic)text).color = (darken ? Darken(val) : val);
			return null;
		}

		private static Color Darken(Color color)
		{
			//IL_0000: 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_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			return new Color(color.r * 0.6f, color.g * 0.6f, color.b * 0.6f, color.a);
		}
	}
}