Decompiled source of BlueSage QoL Tweaks Beta v0.2.4

BepInEx/plugins/BlueSage_QoL_Tweaks_Beta/BlueSage_QoL_Tweaks_Beta.dll

Decompiled a week ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.IO.Pipes;
using System.Linq;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using System.Security.AccessControl;
using System.Security.Cryptography;
using System.Security.Principal;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using System.Threading.Tasks;
using BepInEx;
using BepInEx.Bootstrap;
using BepInEx.Configuration;
using BepInEx.Logging;
using BlueSage.QoLTweaks.Contracts;
using BlueSage.QoLTweaks.Core;
using BlueSage.QoLTweaks.Data;
using BlueSage.QoLTweaks.Patches;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using PurrNet;
using PurrNet.Modules;
using PurrNet.Packing;
using Steamworks;
using TMPro;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.Events;
using UnityEngine.Networking;
using UnityEngine.Profiling;
using UnityEngine.SceneManagement;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETFramework,Version=v4.6", FrameworkDisplayName = ".NET Framework 4.6")]
[assembly: AssemblyCompany("BlueSage_QoL_Tweaks_Beta")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("0.2.4.0")]
[assembly: AssemblyInformationalVersion("0.2.4+3726c5820cf95325339f9836749fe3c035da0d13")]
[assembly: AssemblyProduct("BlueSage_QoL_Tweaks_Beta")]
[assembly: AssemblyTitle("BlueSage_QoL_Tweaks_Beta")]
[assembly: AssemblyVersion("0.2.4.0")]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Embedded]
	internal sealed class IsReadOnlyAttribute : Attribute
	{
	}
	[CompilerGenerated]
	[Embedded]
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)]
	internal sealed class NullableAttribute : Attribute
	{
		public readonly byte[] NullableFlags;

		public NullableAttribute(byte P_0)
		{
			NullableFlags = new byte[1] { P_0 };
		}

		public NullableAttribute(byte[] P_0)
		{
			NullableFlags = P_0;
		}
	}
	[CompilerGenerated]
	[Embedded]
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)]
	internal sealed class NullableContextAttribute : Attribute
	{
		public readonly byte Flag;

		public NullableContextAttribute(byte P_0)
		{
			Flag = P_0;
		}
	}
	[CompilerGenerated]
	[Embedded]
	[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
	internal sealed class RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
namespace BlueSage.QoLTweaks
{
	public static class BlueSageExtensionRegistry
	{
		private sealed class ChainloaderExtensionCatalog : IBlueSageLoadedExtensionCatalogV1
		{
			public bool TryGetLoaded(string pluginGuid, out BlueSageLoadedExtensionV1 extension)
			{
				extension = default(BlueSageLoadedExtensionV1);
				if (!string.IsNullOrWhiteSpace(pluginGuid) && Chainloader.PluginInfos.TryGetValue(pluginGuid, out var value) && !((Object)(object)((value != null) ? value.Instance : null) == (Object)null))
				{
					BepInPlugin metadata = value.Metadata;
					if (!(((metadata != null) ? metadata.Version : null) == null))
					{
						Assembly assembly = ((object)value.Instance).GetType().Assembly;
						extension = new BlueSageLoadedExtensionV1(assembly, value.Metadata.Version, loaded: true);
						return true;
					}
				}
				return false;
			}
		}

		private sealed class DynamicDiagnosticsProvider : IBlueSageDiagnosticsProviderV1, IBlueSageDiagnosticsControlV2
		{
			private const int PayloadLength = 5;

			private readonly Func<long, long[]> _provider;

			private readonly Func<bool, bool> _overlayVisibilitySetter;

			internal DynamicDiagnosticsProvider(Func<long, long[]> provider, Func<bool, bool> overlayVisibilitySetter = null)
			{
				_provider = provider ?? throw new ArgumentNullException("provider");
				_overlayVisibilitySetter = overlayVisibilitySetter;
			}

			public BlueSageDiagnosticsSnapshotV1 GetSnapshot(long nowUtcTicks)
			{
				long[] array = _provider(nowUtcTicks);
				if (array == null || array.Length != 5 || array[0] < 0 || array[0] > 2 || array[1] < 0 || array[1] > 2 || array[2] < 100 || array[2] > 5000)
				{
					throw new InvalidOperationException("Diagnostics payload failed the public ABI bounds.");
				}
				return new BlueSageDiagnosticsSnapshotV1((BlueSageDiagnosticsOverlayStateV1)array[0], (BlueSageDiagnosticsFreshnessV1)array[1], (int)array[2], array[3], array[4]);
			}

			public bool TrySetOverlayVisible(bool visible)
			{
				if (_overlayVisibilitySetter != null)
				{
					return _overlayVisibilitySetter(visible);
				}
				return false;
			}
		}

		private static readonly object Sync = new object();

		private static readonly BlueSageExtensionRegistryCore Core = new BlueSageExtensionRegistryCore(new ChainloaderExtensionCatalog());

		public static BlueSageExtensionRegistrationTokenV1 RegisterBadgeContributionV1(IBlueSageBadgeContributionV1 provider, string ownerGuid, Version ownerVersion, int abiVersion)
		{
			lock (Sync)
			{
				return Core.RegisterBadgeContribution(provider, ownerGuid, ownerVersion, abiVersion);
			}
		}

		public static bool UnregisterBadgeContributionV1(BlueSageExtensionRegistrationTokenV1 token)
		{
			lock (Sync)
			{
				return Core.UnregisterBadgeContribution(token);
			}
		}

		public static BlueSageExtensionRegistrationTokenV1 RegisterDiagnosticsProviderV1(IBlueSageDiagnosticsProviderV1 provider, string ownerGuid, Version ownerVersion, int abiVersion)
		{
			lock (Sync)
			{
				return Core.RegisterDiagnostics(provider, ownerGuid, ownerVersion, abiVersion);
			}
		}

		public static bool UnregisterDiagnosticsProviderV1(BlueSageExtensionRegistrationTokenV1 token)
		{
			lock (Sync)
			{
				return Core.UnregisterDiagnostics(token);
			}
		}

		public static BlueSageExtensionRegistrationTokenV1 RegisterHostCapabilityProviderV1(IBlueSageHostCapabilityProviderV1 provider, string ownerGuid, Version ownerVersion, int abiVersion)
		{
			lock (Sync)
			{
				return Core.RegisterHostCapability(provider, ownerGuid, ownerVersion, abiVersion);
			}
		}

		public static bool UnregisterHostCapabilityProviderV1(BlueSageExtensionRegistrationTokenV1 token)
		{
			lock (Sync)
			{
				return Core.UnregisterHostCapability(token);
			}
		}

		public static long RegisterDiagnosticsProviderDynamicV1(Func<long, long[]> provider, string ownerGuid, Version ownerVersion, int abiVersion)
		{
			if (provider == null || provider.Target != null || !provider.Method.IsStatic || provider.Method.DeclaringType == null)
			{
				return 0L;
			}
			Assembly assembly = provider.Method.DeclaringType.Assembly;
			lock (Sync)
			{
				return Core.RegisterDiagnostics(new DynamicDiagnosticsProvider(provider), ownerGuid, ownerVersion, abiVersion, assembly).Generation;
			}
		}

		public static bool UnregisterDiagnosticsProviderDynamicV1(long generation)
		{
			lock (Sync)
			{
				return Core.UnregisterDiagnostics(new BlueSageExtensionRegistrationTokenV1(generation));
			}
		}

		public static long RegisterDiagnosticsProviderDynamicV2(Func<long, long[]> provider, Func<bool, bool> overlayVisibilitySetter, string ownerGuid, Version ownerVersion, int abiVersion)
		{
			if (provider == null || overlayVisibilitySetter == null || provider.Target != null || overlayVisibilitySetter.Target != null || !provider.Method.IsStatic || !overlayVisibilitySetter.Method.IsStatic || provider.Method.DeclaringType == null || overlayVisibilitySetter.Method.DeclaringType == null || provider.Method.DeclaringType.Assembly != overlayVisibilitySetter.Method.DeclaringType.Assembly)
			{
				return 0L;
			}
			Assembly assembly = provider.Method.DeclaringType.Assembly;
			lock (Sync)
			{
				return Core.RegisterDiagnostics(new DynamicDiagnosticsProvider(provider, overlayVisibilitySetter), ownerGuid, ownerVersion, abiVersion, assembly).Generation;
			}
		}

		internal static void BeginLobby(long lobbyEpoch, long evidenceGeneration)
		{
			lock (Sync)
			{
				Core.SetEvidenceContext(lobbyEpoch, evidenceGeneration);
			}
		}

		internal static void BeginBadgePresentation(long lobbyEpoch, long evidenceGeneration)
		{
			lock (Sync)
			{
				Core.SetBadgeEvidenceContext(lobbyEpoch, evidenceGeneration);
			}
		}

		internal static bool TryReadBadgeContribution(BlueSageBadgeContributionRequestV1 request, long nowUtcTicks, out BlueSageBadgeContributionResponseV1 response)
		{
			lock (Sync)
			{
				return Core.TryReadBadgeContribution(request, nowUtcTicks, out response);
			}
		}

		internal static bool TryReadDiagnostics(long nowUtcTicks, out BlueSageDiagnosticsSnapshotV1 snapshot)
		{
			lock (Sync)
			{
				return Core.TryReadDiagnostics(nowUtcTicks, out snapshot);
			}
		}

		internal static bool TrySetDiagnosticsOverlayVisible(bool visible)
		{
			lock (Sync)
			{
				return Core.TrySetDiagnosticsOverlayVisible(visible);
			}
		}

		internal static bool TryReadHostCapability(bool isHost, long nonce, long nowUtcTicks, out BlueSageHostCapabilitySnapshotV1 snapshot)
		{
			lock (Sync)
			{
				snapshot = default(BlueSageHostCapabilitySnapshotV1);
				BlueSageHostCapabilityRequestV1 request;
				return Core.TryCreateHostCapabilityRequest(isHost, nonce, nowUtcTicks, out request) && Core.TryReadHostCapability(request, nowUtcTicks, out snapshot);
			}
		}

		internal static bool TryExecuteHostCapability(BlueSageHostCapabilityActionV1 action, bool isHost, long nonce, long nowUtcTicks, out BlueSageHostCapabilityReceiptV1 receipt)
		{
			lock (Sync)
			{
				receipt = default(BlueSageHostCapabilityReceiptV1);
				BlueSageHostCapabilityRequestV1 request;
				return Core.TryCreateHostCapabilityRequest(isHost, nonce, nowUtcTicks, out request) && Core.TryExecuteHostCapability(action, request, nowUtcTicks, out receipt);
			}
		}

		internal static bool HasLiveHostCapabilityProvider()
		{
			lock (Sync)
			{
				return Core.HasLiveHostCapabilityProvider();
			}
		}

		internal static void ClearLobbyState()
		{
			lock (Sync)
			{
				Core.SetEvidenceContext(0L, 0L);
				Core.SetBadgeEvidenceContext(0L, 0L);
			}
		}

		internal static void ClearAll()
		{
			lock (Sync)
			{
				Core.Clear();
			}
		}
	}
	internal static class BlueSageHelpFrame
	{
		internal static HelpFrameLayout Resolve(BlueSageHelpFrameKind kind, Rect window)
		{
			return HelpFramePolicy.Resolve(kind, ((Rect)(ref window)).width, ((Rect)(ref window)).height);
		}

		internal static void BeginFooter(GUIStyle footerStyle, HelpFrameLayout layout)
		{
			GUILayout.BeginVertical(footerStyle, (GUILayoutOption[])(object)new GUILayoutOption[2]
			{
				GUILayout.Height(layout.FooterHeight),
				GUILayout.MaxHeight(layout.FooterHeight)
			});
		}

		internal static void DrawStateAndHelp(GUIStyle textStyle, HelpFrameLayout layout, string stateLine, string helpLine)
		{
			GUILayout.Label(stateLine ?? string.Empty, textStyle, (GUILayoutOption[])(object)new GUILayoutOption[2]
			{
				GUILayout.Height(layout.StateLineHeight),
				GUILayout.MaxHeight(layout.StateLineHeight)
			});
			GUILayout.Label(helpLine ?? string.Empty, textStyle, (GUILayoutOption[])(object)new GUILayoutOption[2]
			{
				GUILayout.Height(layout.HelpLineHeight),
				GUILayout.MaxHeight(layout.HelpLineHeight)
			});
		}

		internal static void EndFooter()
		{
			GUILayout.EndVertical();
		}
	}
	internal sealed class BlueSageUiThemePalette
	{
		public string Key { get; }

		public string DisplayName { get; }

		public Color Window { get; }

		public Color Panel { get; }

		public Color Header { get; }

		public Color HeaderText { get; }

		public Color LabelText { get; }

		public Color SmallText { get; }

		public Color ButtonText { get; }

		public Color ActiveButtonText { get; }

		public Color FieldText { get; }

		public Color PreviewBackground { get; }

		public bool IsMidnightDock => string.Equals(Key, "Midnight Dock", StringComparison.OrdinalIgnoreCase);

		public bool UsesWarmContent
		{
			get
			{
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase) && !string.Equals(Key, "Vanilla Cream OT", StringComparison.OrdinalIgnoreCase))
				{
					return string.Equals(Key, "OG", StringComparison.OrdinalIgnoreCase);
				}
				return true;
			}
		}

		public Color SectionPanel
		{
			get
			{
				//IL_003e: 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_001a: 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)
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					return Color.Lerp(Panel, Window, 0.16f);
				}
				return new Color(0.975f, 0.945f, 0.885f, 1f);
			}
		}

		public Color SectionBorder
		{
			get
			{
				//IL_0068: 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_0044: Unknown result type (might be due to invalid IL or missing references)
				//IL_004e: Unknown result type (might be due to invalid IL or missing references)
				//IL_0027: Unknown result type (might be due to invalid IL or missing references)
				//IL_002d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0037: Unknown result type (might be due to invalid IL or missing references)
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					if (!string.Equals(Key, "Vanilla Cream OT", StringComparison.OrdinalIgnoreCase))
					{
						return Color.Lerp(Header, LabelText, 0.3f);
					}
					return Color.Lerp(Header, FieldText, 0.4f);
				}
				return new Color(0.65f, 0.52f, 0.39f, 1f);
			}
		}

		public Color FieldBackground
		{
			get
			{
				//IL_0041: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				//IL_000e: Unknown result type (might be due to invalid IL or missing references)
				//IL_0027: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return Color.Lerp(SectionPanel, Color.white, UsesWarmContent ? 0.44f : 0.1f);
				}
				return new Color(0.045f, 0.065f, 0.105f, 1f);
			}
		}

		public Color FieldHoverBackground
		{
			get
			{
				//IL_0033: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				//IL_000f: 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)
				if (!IsMidnightDock)
				{
					return Color.Lerp(FieldBackground, Header, 0.1f);
				}
				return new Color(0.075f, 0.115f, 0.165f, 1f);
			}
		}

		public Color FieldFocusedBackground
		{
			get
			{
				//IL_0032: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				//IL_000e: 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)
				if (!IsMidnightDock)
				{
					return Color.Lerp(FieldBackground, Color.white, 0.16f);
				}
				return new Color(0.055f, 0.135f, 0.165f, 1f);
			}
		}

		public Color FieldBorder
		{
			get
			{
				//IL_0023: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return SectionBorder;
				}
				return new Color(0.28f, 0.42f, 0.56f, 1f);
			}
		}

		public Color FieldFocusedBorder
		{
			get
			{
				//IL_0033: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				//IL_000f: 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)
				if (!IsMidnightDock)
				{
					return Color.Lerp(ActiveAccent, DarkStateText, 0.18f);
				}
				return new Color(0.24f, 0.72f, 0.78f, 1f);
			}
		}

		public Color ActiveAccent
		{
			get
			{
				//IL_002e: 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)
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					return Header;
				}
				return new Color(0.91f, 0.49f, 0.39f, 1f);
			}
		}

		public Color EnabledAccent
		{
			get
			{
				//IL_0051: 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_002d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0037: Unknown result type (might be due to invalid IL or missing references)
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					return Color.Lerp(Header, new Color(0.45f, 0.8f, 0.36f, 1f), 0.58f);
				}
				return new Color(0.39f, 0.55f, 0.24f, 1f);
			}
		}

		public string NavigationKeywordHex
		{
			get
			{
				if (!IsMidnightDock)
				{
					return "005A85";
				}
				return "70D6FF";
			}
		}

		public Color DisabledAccent
		{
			get
			{
				//IL_0060: Unknown result type (might be due to invalid IL or missing references)
				//IL_0046: Unknown result type (might be due to invalid IL or missing references)
				//IL_001c: Unknown result type (might be due to invalid IL or missing references)
				//IL_0022: Unknown result type (might be due to invalid IL or missing references)
				//IL_002c: Unknown result type (might be due to invalid IL or missing references)
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					if (!IsMidnightDock)
					{
						return Color.Lerp(ButtonText, Window, 0.58f);
					}
					return new Color(0.26f, 0.31f, 0.39f, 1f);
				}
				return new Color(0.68f, 0.65f, 0.61f, 1f);
			}
		}

		public Color DarkStateText
		{
			get
			{
				//IL_002a: Unknown result type (might be due to invalid IL or missing references)
				//IL_0023: 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 (!IsMidnightDock)
				{
					if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
					{
						return FieldText;
					}
					return Header;
				}
				return Window;
			}
		}

		public Color ActiveStateText
		{
			get
			{
				//IL_0010: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return DarkStateText;
				}
				return ActiveButtonText;
			}
		}

		public Color EnabledButtonText => DarkStateText;

		public Color DisabledButtonText
		{
			get
			{
				//IL_0023: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return DarkStateText;
				}
				return new Color(0.84f, 0.89f, 0.94f, 1f);
			}
		}

		public Color ExperimentalButtonText => DarkStateText;

		public Color NeutralButtonAccent
		{
			get
			{
				//IL_0020: Unknown result type (might be due to invalid IL or missing references)
				//IL_0025: Unknown result type (might be due to invalid IL or missing references)
				//IL_002f: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				//IL_000f: 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)
				if (!IsMidnightDock)
				{
					return Color.Lerp(Panel, ButtonText, 0.3f);
				}
				return Color.Lerp(Panel, Color.white, 0.12f);
			}
		}

		public Color NeutralButtonText
		{
			get
			{
				//IL_0010: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return DarkStateText;
				}
				return ButtonText;
			}
		}

		public Color PreviewText
		{
			get
			{
				//IL_002d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0027: Unknown result type (might be due to invalid IL or missing references)
				if (!string.Equals(Key, "OG", StringComparison.OrdinalIgnoreCase) && !string.Equals(Key, "Vanilla Cream OT", StringComparison.OrdinalIgnoreCase))
				{
					return LabelText;
				}
				return Color.white;
			}
		}

		public Color PopupHeaderText
		{
			get
			{
				//IL_0010: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return DarkStateText;
				}
				return ActiveButtonText;
			}
		}

		public Color PopupBodyText
		{
			get
			{
				//IL_0010: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return DarkStateText;
				}
				return LabelText;
			}
		}

		public Color PopupHintText
		{
			get
			{
				//IL_0010: Unknown result type (might be due to invalid IL or missing references)
				//IL_0016: Unknown result type (might be due to invalid IL or missing references)
				//IL_0020: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				if (!IsMidnightDock)
				{
					return DarkStateText;
				}
				return Color.Lerp(SmallText, LabelText, 0.35f);
			}
		}

		public Color ComfortAccent
		{
			get
			{
				//IL_0036: 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 (!IsMidnightDock)
				{
					return new Color(0.39f, 0.55f, 0.24f, 1f);
				}
				return new Color(0.42f, 0.76f, 0.49f, 1f);
			}
		}

		public Color ChatAccent
		{
			get
			{
				//IL_0036: 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 (!IsMidnightDock)
				{
					return new Color(0.1f, 0.56f, 0.62f, 1f);
				}
				return new Color(0.32f, 0.72f, 0.82f, 1f);
			}
		}

		public Color IdentityAccent
		{
			get
			{
				//IL_0036: 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 (!IsMidnightDock)
				{
					return new Color(0.47f, 0.4f, 0.68f, 1f);
				}
				return new Color(0.55f, 0.63f, 0.91f, 1f);
			}
		}

		public Color PersonalizationAccent
		{
			get
			{
				//IL_0036: 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 (!IsMidnightDock)
				{
					return new Color(0.72f, 0.39f, 0.5f, 1f);
				}
				return new Color(0.82f, 0.55f, 0.73f, 1f);
			}
		}

		public Color ExperimentalAccent => new Color(1f, 0.42f, 0.08f, 1f);

		public Color ExperimentalBorder
		{
			get
			{
				//IL_0020: Unknown result type (might be due to invalid IL or missing references)
				//IL_0009: Unknown result type (might be due to invalid IL or missing references)
				//IL_000f: 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)
				if (!IsMidnightDock)
				{
					return Color.Lerp(ExperimentalAccent, DarkStateText, 0.35f);
				}
				return ExperimentalAccent;
			}
		}

		public Color FooterBackground
		{
			get
			{
				//IL_003e: 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_001a: 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)
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					return Color.Lerp(Header, Window, 0.3f);
				}
				return new Color(0.055f, 0.075f, 0.115f, 1f);
			}
		}

		public Color FooterText
		{
			get
			{
				//IL_002e: 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)
				if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					return HeaderText;
				}
				return new Color(0.84f, 0.93f, 0.98f, 1f);
			}
		}

		public Color FooterBorder
		{
			get
			{
				//IL_002a: Unknown result type (might be due to invalid IL or missing references)
				//IL_0023: 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 (!IsMidnightDock)
				{
					if (!string.Equals(Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
					{
						return DarkStateText;
					}
					return SectionBorder;
				}
				return FieldFocusedBorder;
			}
		}

		public BlueSageUiThemePalette(string key, string displayName, Color window, Color panel, Color header, Color headerText, Color labelText, Color smallText, Color buttonText, Color activeButtonText, Color fieldText, Color previewBackground)
		{
			//IL_0015: Unknown result type (might be due to invalid IL or missing references)
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_001c: Unknown result type (might be due to invalid IL or missing references)
			//IL_001e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			//IL_002e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0034: 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_003c: 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_0044: Unknown result type (might be due to invalid IL or missing references)
			//IL_0046: Unknown result type (might be due to invalid IL or missing references)
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0054: Unknown result type (might be due to invalid IL or missing references)
			//IL_0056: Unknown result type (might be due to invalid IL or missing references)
			//IL_005c: Unknown result type (might be due to invalid IL or missing references)
			//IL_005e: Unknown result type (might be due to invalid IL or missing references)
			Key = key;
			DisplayName = displayName;
			Window = window;
			Panel = panel;
			Header = header;
			HeaderText = headerText;
			LabelText = labelText;
			SmallText = smallText;
			ButtonText = buttonText;
			ActiveButtonText = activeButtonText;
			FieldText = fieldText;
			PreviewBackground = previewBackground;
		}
	}
	internal static class BlueSageUiTheme
	{
		public const string DefaultThemeKey = "BlueSage Harbor";

		private static readonly Dictionary<string, Texture2D> SolidTextures = new Dictionary<string, Texture2D>(StringComparer.Ordinal);

		private static readonly Dictionary<string, Texture2D> PanelTextures = new Dictionary<string, Texture2D>(StringComparer.Ordinal);

		private static readonly BlueSageUiThemePalette[] Palettes = new BlueSageUiThemePalette[4]
		{
			new BlueSageUiThemePalette("BlueSage Harbor", "BlueSage Harbor", new Color(0.93f, 0.875f, 0.79f, 0.995f), new Color(0.985f, 0.95f, 0.88f, 0.995f), new Color(0.055f, 0.075f, 0.115f, 1f), new Color(0.84f, 0.95f, 0.98f, 1f), new Color(0.2f, 0.16f, 0.15f, 1f), new Color(0.35f, 0.29f, 0.27f, 1f), new Color(0.22f, 0.18f, 0.17f, 1f), new Color(1f, 0.96f, 0.88f, 1f), new Color(0.12f, 0.1f, 0.1f, 1f), new Color(0.985f, 0.95f, 0.88f, 0.98f)),
			new BlueSageUiThemePalette("OG", "OG", new Color(0.93f, 0.9f, 0.83f, 0.99f), new Color(0.84f, 0.8f, 0.72f, 0.98f), new Color(0.55f, 0.52f, 0.47f, 1f), new Color(0.12f, 0.09f, 0.1f, 1f), new Color(0.22f, 0.14f, 0.17f, 1f), new Color(0.34f, 0.26f, 0.29f, 1f), new Color(0.24f, 0.17f, 0.2f, 1f), Color.white, new Color(0.14f, 0.11f, 0.12f, 1f), new Color(0.28f, 0.27f, 0.25f, 0.96f)),
			new BlueSageUiThemePalette("Vanilla Cream OT", "Vanilla Cream OT", new Color(0.98f, 0.93f, 0.84f, 0.99f), new Color(0.91f, 0.82f, 0.69f, 0.98f), new Color(0.91f, 0.49f, 0.42f, 1f), new Color(0.23f, 0.14f, 0.16f, 1f), new Color(0.32f, 0.22f, 0.25f, 1f), new Color(0.43f, 0.31f, 0.33f, 1f), new Color(0.31f, 0.22f, 0.25f, 1f), Color.white, new Color(0.15f, 0.11f, 0.12f, 1f), new Color(0.39f, 0.31f, 0.27f, 0.96f)),
			new BlueSageUiThemePalette("Midnight Dock", "Midnight Dock", new Color(0.08f, 0.1f, 0.16f, 0.99f), new Color(0.13f, 0.16f, 0.24f, 0.98f), new Color(0.08f, 0.36f, 0.42f, 1f), new Color(0.88f, 0.98f, 1f, 1f), new Color(0.91f, 0.96f, 1f, 1f), new Color(0.72f, 0.82f, 0.9f, 1f), new Color(0.89f, 0.94f, 1f, 1f), new Color(1f, 0.91f, 0.42f, 1f), new Color(0.96f, 0.98f, 1f, 1f), new Color(0.04f, 0.05f, 0.08f, 0.97f))
		};

		public static int RuntimeTextureGeneration { get; private set; } = 1;

		public static BlueSageUiThemePalette Current => Get(Plugin.UiThemePreset?.Value);

		public static string[] Names => Array.ConvertAll(Palettes, (BlueSageUiThemePalette palette) => palette.DisplayName);

		public static BlueSageUiThemePalette Get(string requested)
		{
			string b = Normalize(requested);
			BlueSageUiThemePalette[] palettes = Palettes;
			foreach (BlueSageUiThemePalette blueSageUiThemePalette in palettes)
			{
				if (string.Equals(blueSageUiThemePalette.Key, b, StringComparison.OrdinalIgnoreCase) || string.Equals(blueSageUiThemePalette.DisplayName, b, StringComparison.OrdinalIgnoreCase))
				{
					return blueSageUiThemePalette;
				}
			}
			return GetDefaultPalette();
		}

		public static string Normalize(string requested)
		{
			string text = (requested ?? string.Empty).Trim();
			if (text.Length == 0)
			{
				return "BlueSage Harbor";
			}
			BlueSageUiThemePalette[] palettes = Palettes;
			foreach (BlueSageUiThemePalette blueSageUiThemePalette in palettes)
			{
				if (string.Equals(blueSageUiThemePalette.Key, text, StringComparison.OrdinalIgnoreCase) || string.Equals(blueSageUiThemePalette.DisplayName, text, StringComparison.OrdinalIgnoreCase))
				{
					return blueSageUiThemePalette.Key;
				}
			}
			return "BlueSage Harbor";
		}

		public static string Next(string requested)
		{
			string b = Normalize(requested);
			for (int i = 0; i < Palettes.Length; i++)
			{
				if (string.Equals(Palettes[i].Key, b, StringComparison.OrdinalIgnoreCase))
				{
					return Palettes[(i + 1) % Palettes.Length].Key;
				}
			}
			return GetDefaultPalette().Key;
		}

		private static BlueSageUiThemePalette GetDefaultPalette()
		{
			BlueSageUiThemePalette[] palettes = Palettes;
			foreach (BlueSageUiThemePalette blueSageUiThemePalette in palettes)
			{
				if (string.Equals(blueSageUiThemePalette.Key, "BlueSage Harbor", StringComparison.OrdinalIgnoreCase))
				{
					return blueSageUiThemePalette;
				}
			}
			return Palettes[0];
		}

		public static GUIStyle CreateTextInputStyle(GUIStyle source, BlueSageUiThemePalette palette, int fontSize, bool wordWrap)
		{
			//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_000d: 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_001b: 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_002a: Expected O, but got Unknown
			//IL_002a: 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_0039: Expected O, but got Unknown
			//IL_0039: 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_0046: Unknown result type (might be due to invalid IL or missing references)
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0056: Unknown result type (might be due to invalid IL or missing references)
			//IL_005d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0063: Unknown result type (might be due to invalid IL or missing references)
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_0073: Unknown result type (might be due to invalid IL or missing references)
			//IL_007a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0080: Unknown result type (might be due to invalid IL or missing references)
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_0090: Unknown result type (might be due to invalid IL or missing references)
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			//IL_009d: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ad: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b4: 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_00c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ca: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ee: 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_00fa: Unknown result type (might be due to invalid IL or missing references)
			//IL_0104: Unknown result type (might be due to invalid IL or missing references)
			//IL_010b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0111: Unknown result type (might be due to invalid IL or missing references)
			//IL_0117: Unknown result type (might be due to invalid IL or missing references)
			//IL_0122: Expected O, but got Unknown
			GUIStyle val = new GUIStyle(source)
			{
				richText = false,
				fontSize = fontSize,
				wordWrap = wordWrap,
				border = new RectOffset(1, 1, 1, 1),
				padding = new RectOffset(8, 8, 5, 5)
			};
			ApplyState(val.normal, palette.FieldBackground, palette.FieldBorder, palette.FieldText);
			ApplyState(val.hover, palette.FieldHoverBackground, palette.FieldBorder, palette.FieldText);
			ApplyState(val.active, palette.FieldFocusedBackground, palette.FieldFocusedBorder, palette.FieldText);
			ApplyState(val.focused, palette.FieldFocusedBackground, palette.FieldFocusedBorder, palette.FieldText);
			ApplyState(val.onNormal, palette.FieldBackground, palette.FieldBorder, palette.FieldText);
			ApplyState(val.onHover, palette.FieldHoverBackground, palette.FieldBorder, palette.FieldText);
			ApplyState(val.onActive, palette.FieldFocusedBackground, palette.FieldFocusedBorder, palette.FieldText);
			ApplyState(val.onFocused, palette.FieldFocusedBackground, palette.FieldFocusedBorder, palette.FieldText);
			return val;
		}

		public static GUIStyle CreateStateButtonStyle(GUIStyle source, Color fill, Color border, Color text, int fontSize)
		{
			//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_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0015: Unknown result type (might be due to invalid IL or missing references)
			//IL_001a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0024: Expected O, but got Unknown
			//IL_0024: 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)
			//IL_0040: 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_0054: Unknown result type (might be due to invalid IL or missing references)
			//IL_0059: Unknown result type (might be due to invalid IL or missing references)
			//IL_005a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0065: 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_0079: Unknown result type (might be due to invalid IL or missing references)
			//IL_007e: Unknown result type (might be due to invalid IL or missing references)
			//IL_007f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0085: Unknown result type (might be due to invalid IL or missing references)
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_0087: Unknown result type (might be due to invalid IL or missing references)
			//IL_008d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0093: Unknown result type (might be due to invalid IL or missing references)
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_0095: 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_00a4: 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_00b0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b2: 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)
			//IL_00be: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bf: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ca: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cf: 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_00db: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ea: Unknown result type (might be due to invalid IL or missing references)
			//IL_00eb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f5: 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)
			//IL_0100: Unknown result type (might be due to invalid IL or missing references)
			//IL_0106: Unknown result type (might be due to invalid IL or missing references)
			//IL_0107: 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_010e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0114: Unknown result type (might be due to invalid IL or missing references)
			//IL_0115: Unknown result type (might be due to invalid IL or missing references)
			//IL_0116: Unknown result type (might be due to invalid IL or missing references)
			//IL_0120: Unknown result type (might be due to invalid IL or missing references)
			//IL_0125: Unknown result type (might be due to invalid IL or missing references)
			//IL_012c: Expected O, but got Unknown
			GUIStyle val = new GUIStyle(source)
			{
				fontSize = fontSize,
				fontStyle = (FontStyle)1,
				border = new RectOffset(1, 1, 1, 1)
			};
			bool flag = RelativeLuminance(text) >= 0.5f;
			Color fill2 = Color.Lerp(fill, flag ? Color.black : Color.white, flag ? 0.08f : 0.11f);
			Color fill3 = Color.Lerp(fill, flag ? Color.black : Color.white, flag ? 0.18f : 0.2f);
			ApplyState(val.normal, fill, border, text);
			ApplyState(val.hover, fill2, Color.Lerp(border, Color.white, 0.16f), text);
			ApplyState(val.active, fill3, border, text);
			ApplyState(val.focused, fill2, Color.Lerp(border, Color.white, 0.16f), text);
			ApplyState(val.onNormal, fill, border, text);
			ApplyState(val.onHover, fill2, Color.Lerp(border, Color.white, 0.16f), text);
			ApplyState(val.onActive, fill3, border, text);
			ApplyState(val.onFocused, fill2, Color.Lerp(border, Color.white, 0.16f), text);
			return val;
		}

		public static GUIStyle CreateNeutralButtonStyle(GUIStyle source, BlueSageUiThemePalette palette, int fontSize)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			return CreateStateButtonStyle(source, palette.NeutralButtonAccent, palette.FieldBorder, palette.NeutralButtonText, fontSize);
		}

		public static GUIStyle CreateSwatchButtonStyle(GUIStyle source, int fontSize)
		{
			//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_000d: 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)
			//IL_0023: Expected O, but got Unknown
			//IL_0023: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0065: 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)
			//IL_006b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0081: 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_0091: Unknown result type (might be due to invalid IL or missing references)
			//IL_0092: Unknown result type (might be due to invalid IL or missing references)
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ad: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00be: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ea: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ef: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ff: Unknown result type (might be due to invalid IL or missing references)
			//IL_0100: Unknown result type (might be due to invalid IL or missing references)
			//IL_0105: Unknown result type (might be due to invalid IL or missing references)
			//IL_0110: Expected O, but got Unknown
			GUIStyle val = new GUIStyle(source)
			{
				fontSize = fontSize,
				fontStyle = (FontStyle)1,
				border = new RectOffset(1, 1, 1, 1)
			};
			Color white = Color.white;
			Color fill = default(Color);
			((Color)(ref fill))..ctor(0.92f, 0.92f, 0.92f, 1f);
			Color fill2 = default(Color);
			((Color)(ref fill2))..ctor(0.82f, 0.82f, 0.82f, 1f);
			ApplyState(val.normal, white, Color.black, Color.white);
			ApplyState(val.hover, fill, Color.black, Color.white);
			ApplyState(val.active, fill2, Color.black, Color.white);
			ApplyState(val.focused, fill, Color.black, Color.white);
			ApplyState(val.onNormal, white, Color.black, Color.white);
			ApplyState(val.onHover, fill, Color.black, Color.white);
			ApplyState(val.onActive, fill2, Color.black, Color.white);
			ApplyState(val.onFocused, fill, Color.black, Color.white);
			return val;
		}

		public static Color BestTextColor(Color background, BlueSageUiThemePalette palette)
		{
			//IL_000b: 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_0010: Unknown result type (might be due to invalid IL or missing references)
			//IL_0011: 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_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_001d: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0025: Unknown result type (might be due to invalid IL or missing references)
			Color val = palette?.DarkStateText ?? Color.black;
			if (!(ContrastRatio(val, background) >= ContrastRatio(Color.white, background)))
			{
				return Color.white;
			}
			return val;
		}

		private static float ContrastRatio(Color first, Color second)
		{
			//IL_0000: 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)
			float val = RelativeLuminance(first);
			float val2 = RelativeLuminance(second);
			float num = Math.Max(val, val2);
			float num2 = Math.Min(val, val2);
			return (num + 0.05f) / (num2 + 0.05f);
		}

		private static float RelativeLuminance(Color color)
		{
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			return 0.2126f * Linearize(color.r) + 0.7152f * Linearize(color.g) + 0.0722f * Linearize(color.b);
		}

		private static float Linearize(float channel)
		{
			if (!(channel <= 0.03928f))
			{
				return (float)Math.Pow((channel + 0.055f) / 1.055f, 2.4000000953674316);
			}
			return channel / 12.92f;
		}

		public static Texture2D GetSolidTexture(Color color)
		{
			//IL_0000: 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_0051: 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_0060: Unknown result type (might be due to invalid IL or missing references)
			//IL_0068: Expected O, but got Unknown
			//IL_006b: Unknown result type (might be due to invalid IL or missing references)
			string text = ColorKey(color);
			if (SolidTextures.TryGetValue(text, out var value))
			{
				if ((Object)(object)value != (Object)null)
				{
					return value;
				}
				SolidTextures.Remove(text);
				RuntimeTextureGeneration++;
			}
			Texture2D val = new Texture2D(1, 1)
			{
				name = "BlueSageUi-Solid-" + text,
				hideFlags = (HideFlags)61,
				wrapMode = (TextureWrapMode)1,
				filterMode = (FilterMode)0
			};
			val.SetPixel(0, 0, color);
			val.Apply();
			SolidTextures[text] = val;
			return val;
		}

		public static Texture2D GetPanelTexture(Color fill, Color border)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			//IL_004b: 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_0061: Unknown result type (might be due to invalid IL or missing references)
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_0070: Unknown result type (might be due to invalid IL or missing references)
			//IL_0078: Expected O, but got Unknown
			//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_009e: Unknown result type (might be due to invalid IL or missing references)
			string text = ColorKey(fill) + "-" + ColorKey(border);
			if (PanelTextures.TryGetValue(text, out var value))
			{
				if ((Object)(object)value != (Object)null)
				{
					return value;
				}
				PanelTextures.Remove(text);
				RuntimeTextureGeneration++;
			}
			Texture2D val = new Texture2D(3, 3)
			{
				name = "BlueSageUi-Panel-" + text,
				hideFlags = (HideFlags)61,
				wrapMode = (TextureWrapMode)1,
				filterMode = (FilterMode)0
			};
			for (int i = 0; i < 3; i++)
			{
				for (int j = 0; j < 3; j++)
				{
					bool flag = j == 0 || i == 0 || j == 2 || i == 2;
					val.SetPixel(j, i, flag ? border : fill);
				}
			}
			val.Apply();
			PanelTextures[text] = val;
			return val;
		}

		public static bool AreRuntimeTexturesAlive()
		{
			foreach (Texture2D value in SolidTextures.Values)
			{
				if ((Object)(object)value == (Object)null)
				{
					return false;
				}
			}
			foreach (Texture2D value2 in PanelTextures.Values)
			{
				if ((Object)(object)value2 == (Object)null)
				{
					return false;
				}
			}
			return true;
		}

		public static void ReleaseRuntimeTextures()
		{
			foreach (Texture2D value in SolidTextures.Values)
			{
				if ((Object)(object)value != (Object)null)
				{
					Object.Destroy((Object)(object)value);
				}
			}
			foreach (Texture2D value2 in PanelTextures.Values)
			{
				if ((Object)(object)value2 != (Object)null)
				{
					Object.Destroy((Object)(object)value2);
				}
			}
			SolidTextures.Clear();
			PanelTextures.Clear();
			RuntimeTextureGeneration++;
		}

		private static string ColorKey(Color color)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//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)
			Color32 val = Color32.op_Implicit(color);
			return val.r.ToString("X2") + val.g.ToString("X2") + val.b.ToString("X2") + val.a.ToString("X2");
		}

		private static void ApplyState(GUIStyleState state, Color fill, Color border, Color text)
		{
			//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_000e: Unknown result type (might be due to invalid IL or missing references)
			state.background = GetPanelTexture(fill, border);
			state.textColor = text;
		}
	}
	internal enum BlueSagePublicWindow
	{
		QolMenu,
		StyleHelper
	}
	internal static class BlueSageWindowCoordinator
	{
		private static bool _qolMenuVisible;

		private static bool _styleHelperVisible;

		internal static void SetVisible(BlueSagePublicWindow window, bool visible)
		{
			if (window == BlueSagePublicWindow.QolMenu)
			{
				_qolMenuVisible = visible;
			}
			else
			{
				_styleHelperVisible = visible;
			}
		}

		internal static WindowFitResult ResolveForOpen(BlueSagePublicWindow window, bool hasOpened, Rect current, float preferredMinWidth, float preferredMinHeight, float screenWidth, float screenHeight)
		{
			SetVisible(window, visible: true);
			return WindowFitPolicy.FitForOpen(hasOpened, ((Rect)(ref current)).x, ((Rect)(ref current)).y, ((Rect)(ref current)).width, ((Rect)(ref current)).height, preferredMinWidth, preferredMinHeight, screenWidth, screenHeight);
		}

		internal static WindowFitResult ResolveForFrame(BlueSagePublicWindow window, Rect current, float preferredMinWidth, float preferredMinHeight, float screenWidth, float screenHeight)
		{
			SetVisible(window, visible: true);
			return WindowFitPolicy.FitToScreen(((Rect)(ref current)).x, ((Rect)(ref current)).y, ((Rect)(ref current)).width, ((Rect)(ref current)).height, preferredMinWidth, preferredMinHeight, screenWidth, screenHeight, expandToMaximum: false);
		}
	}
	internal static class BlueSageWindowHoverScope
	{
		private static int _hoveredWindowId;

		private static int _hoveredPriority;

		private static int _hoveredFrame = -1;

		internal static void RegisterWindow(int windowId, Rect screenRect, int priority)
		{
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			Event current = Event.current;
			if (current != null && ((Rect)(ref screenRect)).Contains(current.mousePosition))
			{
				int frameCount = Time.frameCount;
				if (_hoveredFrame != frameCount || priority >= _hoveredPriority)
				{
					_hoveredWindowId = windowId;
					_hoveredPriority = priority;
					_hoveredFrame = frameCount;
				}
			}
		}

		internal static bool IsWindowHovered(int windowId)
		{
			if (_hoveredFrame == Time.frameCount)
			{
				return _hoveredWindowId == windowId;
			}
			return false;
		}

		internal static void UnregisterWindow(int windowId)
		{
			if (_hoveredFrame == Time.frameCount && _hoveredWindowId == windowId)
			{
				_hoveredWindowId = 0;
				_hoveredPriority = 0;
				_hoveredFrame = -1;
			}
		}
	}
	internal static class ChalkboardModerationController
	{
		internal static string DescribeAuthority()
		{
			if (!SteamIdModerationController.CanLocalIssue(out var isHost, out var _))
			{
				return "local-only";
			}
			if (!isHost)
			{
				return "authenticated Helper-to-Host";
			}
			return "Host-direct";
		}

		internal static int CountCompatibleRecipients()
		{
			return (PlayerIdentityEvidenceController.GetVerifiedRoster() ?? Array.Empty<PlayerIdentityEvidence>()).Count(IsCompatibleRecipient);
		}

		internal static bool IsCompatibleRecipient(PlayerIdentityEvidence evidence)
		{
			//IL_0029: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0039: 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)
			if (evidence == null || evidence.IsLocal || !ulong.TryParse(evidence.SteamId, NumberStyles.None, CultureInfo.InvariantCulture, out var result) || !Plugin.TryGetRescueLobby(out var lobbyId) || lobbyId == CSteamID.Nil)
			{
				return false;
			}
			try
			{
				return CompatibleClientPresencePolicy.IsFresh(SteamMatchmaking.GetLobbyMemberData(lobbyId, new CSteamID(result), "bluesage_qol_client_v1"), DateTimeOffset.UtcNow.ToUnixTimeSeconds());
			}
			catch
			{
				return false;
			}
		}

		internal static string BuildTruth(string action, int boardIndex, string scene, string snapshot, string rollback, string vanillaObserver = "not-observed")
		{
			return ChalkboardCommandPolicy.BuildActionTruth(action, boardIndex, scene, DescribeAuthority(), CountCompatibleRecipients(), snapshot, rollback, vanillaObserver);
		}
	}
	internal static class ChalkboardPersistenceController
	{
		private const string ChalkyGuid = "com.andrewlin.ontogether.chalky";

		private const string Magic = "BSCH1";

		private const int MaxDimension = 512;

		private const int MaxColorIndex = 255;

		private const long MemberDataPollIntervalMilliseconds = 500L;

		private const int ClearCooldownSeconds = 5;

		private static readonly Regex SafeName = new Regex("^[A-Za-z0-9][A-Za-z0-9_-]{0,39}$", RegexOptions.Compiled);

		private static readonly FieldInfo BoardIndexField = AccessTools.Field(typeof(DrawingManager), "_boardIndex");

		private static readonly HashSet<string> SeenClearNonces = new HashSet<string>(StringComparer.Ordinal);

		private static readonly Queue<string> ClearNonceOrder = new Queue<string>();

		private static readonly Dictionary<string, long> LastClearRequestByIssuer = new Dictionary<string, long>(StringComparer.Ordinal);

		private static readonly Dictionary<string, DateTime> LastClearByBoard = new Dictionary<string, DateTime>(StringComparer.Ordinal);

		private static DateTime _lastSharedRestoreUtc = DateTime.MinValue;

		private static long _nextMemberDataPollUnixMilliseconds;

		private static string _memberDataLobbyKey = string.Empty;

		private static string _boardSetSignature = string.Empty;

		private static string _lastListedBoardSetSignature = string.Empty;

		private static long _lastListedBoardSetUnixSeconds;

		private static bool _rollbackUnresolved;

		internal static bool ChalkyInstalled => Chainloader.PluginInfos.ContainsKey("com.andrewlin.ontogether.chalky");

		internal static bool Available
		{
			get
			{
				ConfigEntry<bool> enableChalkboardPersistence = Plugin.EnableChalkboardPersistence;
				if (enableChalkboardPersistence != null && enableChalkboardPersistence.Value)
				{
					return !ChalkyInstalled;
				}
				return false;
			}
		}

		internal static string SaveDirectory => Path.Combine(Paths.ConfigPath, "BlueSageChalkboards");

		internal static string Status()
		{
			if (ChalkyInstalled)
			{
				return "Chalkboard Persistence: Andrew's Chalky is installed, so BlueSage is safely standing down.";
			}
			return "Chalkboard Persistence: " + (Available ? "on." : "off.") + " Catalog=0 River/Stage, 1 Classroom board A (face A), 2 Classroom board B (face B); index 3 is unsupported. Local view/save/delete/map refresh are available to every QoL user. Shared load/clear require Host-direct or authenticated Helper-to-Host authority, a fresh /chalk boards map, and exact current identity. Compatible clients receive full-state replacement; vanilla observer state remains not-observed until live UAT. There is no authoritative drawing-owner identity. rollback=" + ((_rollbackUnresolved || ChalkboardSnapshotTransportController.DestructiveActionsBlocked) ? ChalkboardSnapshotTransportController.RollbackState : "ready") + ".";
		}

		internal static string Save(string name, string boardToken)
		{
			if (!Available)
			{
				return Status();
			}
			if (!TryResolve(name, boardToken, out var normalized, out var board, out var index, out var error))
			{
				return error;
			}
			TrySaveResolved(normalized, board, index, out var message);
			return message;
		}

		private static bool TrySaveResolved(string normalized, QuadPainterGPU board, int index, out string message)
		{
			try
			{
				ValidateGrid(board.PaintColors);
				Directory.CreateDirectory(SaveDirectory);
				string text = Path.Combine(SaveDirectory, normalized + ".bschalk");
				string text2 = text + ".tmp";
				using (FileStream fileStream = new FileStream(text2, FileMode.Create, FileAccess.Write, FileShare.None))
				{
					using BinaryWriter binaryWriter = new BinaryWriter(fileStream);
					binaryWriter.Write("BSCH1");
					binaryWriter.Write(board.PaintColors.Length);
					binaryWriter.Write(board.PaintColors[0].Ints.Count);
					for (int i = 0; i < board.PaintColors.Length; i++)
					{
						for (int j = 0; j < board.PaintColors[i].Ints.Count; j++)
						{
							binaryWriter.Write(board.PaintColors[i].Ints[j]);
						}
					}
					fileStream.Flush(flushToDisk: true);
				}
				if (File.Exists(text))
				{
					string destinationBackupFileName = text + ".bak";
					File.Replace(text2, text, destinationBackupFileName, ignoreMetadataErrors: true);
				}
				else
				{
					File.Move(text2, text);
				}
				message = $"Chalkboard '{normalized}' saved locally from board {index}. " + ChalkboardModerationController.BuildTruth("save", index, DescribeBoardScene(board, index), normalized, "not-needed");
				return true;
			}
			catch (Exception ex)
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogWarning((object)("Chalkboard save failed safely: " + ex.GetType().Name + ": " + ex.Message));
				}
				message = "Chalkboard save failed safely; the existing save was left intact.";
				return false;
			}
		}

		internal static string Load(string name, string boardToken)
		{
			//IL_00f9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ca: Unknown result type (might be due to invalid IL or missing references)
			//IL_0146: Unknown result type (might be due to invalid IL or missing references)
			if (!Available)
			{
				return Status();
			}
			if (!TryNormalizeName(name, out var normalized, out var error))
			{
				return error;
			}
			if (!TryResolveBoard(boardToken, out var board, out var index, out var fingerprint, out var error2))
			{
				return error2;
			}
			DrawingManager i = MonoSingleton<DrawingManager>.I;
			if (!ChalkboardCommandPolicy.TryAuthorizeDestructiveAction(index, (i?.QuadPainterGPUS?.Count).GetValueOrDefault(), _lastListedBoardSetSignature, _lastListedBoardSetUnixSeconds, BuildBoardSetSignature(i), DateTimeOffset.UtcNow.ToUnixTimeSeconds(), _rollbackUnresolved || ChalkboardSnapshotTransportController.DestructiveActionsBlocked, out var error3))
			{
				return error3;
			}
			if (!SteamIdModerationController.CanLocalIssue(out var isHost, out var reason))
			{
				return reason;
			}
			if (isHost)
			{
				string issuerSteamId = (SteamManager.Initialized ? ((ulong)SteamUser.GetSteamID()).ToString() : string.Empty);
				ExecuteLoadAsHost(normalized, index, fingerprint, issuerSteamId, out var message);
				return message;
			}
			if (!Plugin.TryGetRescueLobby(out var lobbyId) || lobbyId == CSteamID.Nil)
			{
				return "The Helper chalkboard restore request could not reach the current host; no board changed.";
			}
			try
			{
				string nonce = Guid.NewGuid().ToString("N").Substring(0, 16);
				string text = ChalkboardModerationPolicy.BuildRestoreMemberData(index, fingerprint, DateTimeOffset.UtcNow.ToUnixTimeSeconds(), nonce, normalized);
				SteamMatchmaking.SetLobbyMemberData(lobbyId, "bluesage_chalk_request_v2", text);
				return $"Helper restore request sent privately for host-local snapshot '{normalized}' and board {index}. " + "The host will revalidate exact Helper identity, current scene/index/fingerprint, freshness, request size/version, nonce/replay, and its own saved snapshot before changing the board; no chat line was sent. " + ChalkboardModerationController.BuildTruth("load-request", index, DescribeBoardScene(board, index), normalized, "pending-host");
			}
			catch (Exception ex)
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogWarning((object)("Helper chalkboard restore request failed safely: " + ex.GetType().Name + ": " + ex.Message));
				}
				return "The Helper chalkboard restore request failed safely; no board changed.";
			}
		}

		private static ChalkboardClearResult ExecuteLoadAsHost(string normalized, int index, string expectedFingerprint, string issuerSteamId, out string message)
		{
			message = "No chalkboard changed.";
			if (!SafeName.IsMatch(normalized ?? string.Empty) || !SteamIdModerationController.TryGetOwnedHostLobby(out var _, out var _) || !SteamIdModerationController.IsAuthorizedCurrentIssuer(issuerSteamId))
			{
				message = "Only the active host or a currently authorized Helper can request a shared chalkboard restore.";
				return ChalkboardClearResult.Rejected;
			}
			if (!TryResolveBoard(index.ToString(CultureInfo.InvariantCulture), out var board, out var index2, out var fingerprint, out var error))
			{
				message = error;
				return ChalkboardClearResult.Rejected;
			}
			if (index2 != index || !string.Equals(fingerprint, expectedFingerprint, StringComparison.Ordinal))
			{
				message = "The board identity changed after selection. No board changed; run /chalk boards again.";
				return ChalkboardClearResult.Rejected;
			}
			if (!((NetworkIdentity)board).isServer)
			{
				message = "The current client is not the authoritative board server. No board changed.";
				return ChalkboardClearResult.Rejected;
			}
			if (_rollbackUnresolved || ChalkboardSnapshotTransportController.DestructiveActionsBlocked)
			{
				message = "A prior chalkboard rollback remains unresolved. No destructive board action is allowed.";
				return ChalkboardClearResult.Rejected;
			}
			if ((DateTime.UtcNow - _lastSharedRestoreUtc).TotalSeconds < 8.0)
			{
				message = "Chalkboard restore is cooling down; wait a few seconds before another shared restore.";
				return ChalkboardClearResult.Rejected;
			}
			string path = Path.Combine(SaveDirectory, normalized + ".bschalk");
			if (!File.Exists(path))
			{
				message = "Host-local chalkboard snapshot '" + normalized + "' was not found. Use /chalk list.";
				return ChalkboardClearResult.Rejected;
			}
			int[][] array = null;
			string text = "preload-b" + index + "-" + DateTime.UtcNow.ToString("yyyyMMddTHHmmssZ", CultureInfo.InvariantCulture);
			try
			{
				int[][] grid = ReadGrid(path, board);
				if (!TrySaveResolved(text, board, index, out var message2))
				{
					message = "Pre-restore recovery snapshot failed, so BlueSage left the board unchanged. " + message2;
					return ChalkboardClearResult.Rejected;
				}
				array = CopyGrid(board.PaintColors);
				ChalkboardDeliveryResult chalkboardDeliveryResult = ApplyGridAndSync(board, grid);
				_lastSharedRestoreUtc = DateTime.UtcNow;
				string text2 = ChalkboardModerationController.BuildTruth("load", index, DescribeBoardScene(board, index), text, "ready");
				if (!chalkboardDeliveryResult.IsComplete)
				{
					message = $"Chalkboard '{normalized}' restored locally to board {index}, but compatible-recipient delivery was partial " + $"(attempted {chalkboardDeliveryResult.Attempted}, sent {chalkboardDeliveryResult.Sent}, skipped {chalkboardDeliveryResult.Skipped}). " + "After the restore cooldown, repeating the exact action is retry-safe. " + text2;
					return ChalkboardClearResult.Partial;
				}
				message = $"Chalkboard '{normalized}' restored to board {index}. Compatible QoL clients replace stale pixels before the native full-board repaint. " + text2;
				return ChalkboardClearResult.Complete;
			}
			catch (Exception ex)
			{
				bool flag = array == null;
				if (array != null)
				{
					try
					{
						ApplyGridAndSync(board, array);
						flag = true;
					}
					catch (Exception ex2)
					{
						RestoreGridValues(board, array);
						_rollbackUnresolved = true;
						ChalkboardSnapshotTransportController.MarkRollbackUnresolved("restore " + ex2.GetType().Name);
						ManualLogSource log = Plugin.Log;
						if (log != null)
						{
							log.LogError((object)("Chalkboard restore rollback repaint failed after restoring grid values: " + ex2.GetType().Name + ": " + ex2.Message));
						}
					}
				}
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogWarning((object)("Chalkboard restore rejected safely: " + ex.GetType().Name + ": " + ex.Message));
				}
				message = "Chalkboard restore failed; rollback=" + (flag ? "restored" : "unresolved-blocking") + ", recovery snapshot='" + text + "', vanillaObserver=not-observed.";
				return ChalkboardClearResult.Rejected;
			}
		}

		internal static string List()
		{
			if (ChalkyInstalled)
			{
				return Status();
			}
			if (!Directory.Exists(SaveDirectory))
			{
				return "Chalkboard saves: none yet.";
			}
			string[] array = (from value in Directory.GetFiles(SaveDirectory, "*.bschalk").Select(Path.GetFileNameWithoutExtension)
				orderby value
				select value).Take(30).ToArray();
			return ((array.Length == 0) ? "Chalkboard saves: none yet." : ("Chalkboard saves: " + string.Join(", ", array) + ".")) + " authority=local-only, snapshot=local-library, rollback=" + (_rollbackUnresolved ? "unresolved" : "ready") + ", vanillaObserver=not-applicable.";
		}

		internal static string Delete(string name)
		{
			if (ChalkyInstalled)
			{
				return Status();
			}
			if (!TryNormalizeName(name, out var normalized, out var error))
			{
				return error;
			}
			string text = Path.Combine(SaveDirectory, normalized + ".bschalk");
			if (!File.Exists(text))
			{
				return "Chalkboard '" + normalized + "' was not found in the local save library.";
			}
			try
			{
				string text2 = text + ".bak";
				File.Copy(text, text2, overwrite: true);
				File.Delete(text);
				return "Deleted local chalkboard save '" + normalized + "' after preserving '" + Path.GetFileName(text2) + "'. " + ChalkboardCommandPolicy.BuildActionTruth("delete", -1, "local-save-library", "local-only", 0, Path.GetFileName(text2), "reversible-from-backup", "not-applicable");
			}
			catch (Exception ex)
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogWarning((object)("Chalkboard local delete failed safely: " + ex.GetType().Name + ": " + ex.Message));
				}
				return "Chalkboard local delete failed safely; the saved snapshot was not intentionally removed.";
			}
		}

		internal static string RefreshMap()
		{
			return "Chalkboard map refreshed locally. " + Boards();
		}

		internal static string View(string boardToken)
		{
			if (!Available)
			{
				return Status();
			}
			if (!TryResolveBoard(boardToken, out var board, out var index, out var fingerprint, out var error))
			{
				return error;
			}
			return "Viewed exact board fingerprint " + fingerprint + ". " + ChalkboardModerationController.BuildTruth("view", index, DescribeBoardScene(board, index), "none", _rollbackUnresolved ? "unresolved" : "ready");
		}

		internal static string Boards()
		{
			//IL_00a4: Unknown result type (might be due to invalid IL or missing references)
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f2: 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)
			//IL_01d9: Unknown result type (might be due to invalid IL or missing references)
			//IL_01de: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f9: 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_0202: Unknown result type (might be due to invalid IL or missing references)
			//IL_020a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0212: Unknown result type (might be due to invalid IL or missing references)
			//IL_0276: 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_02fb: Unknown result type (might be due to invalid IL or missing references)
			//IL_030a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0319: Unknown result type (might be due to invalid IL or missing references)
			if (!Available)
			{
				return Status();
			}
			DrawingManager i = MonoSingleton<DrawingManager>.I;
			if ((Object)(object)i == (Object)null || i.QuadPainterGPUS == null || i.QuadPainterGPUS.Count == 0)
			{
				return "Chalkboards are not ready in this scene.";
			}
			RefreshBoardSetState(i);
			_lastListedBoardSetSignature = _boardSetSignature;
			_lastListedBoardSetUnixSeconds = DateTimeOffset.UtcNow.ToUnixTimeSeconds();
			int num = (int)(BoardIndexField?.GetValue(i) ?? ((object)(-1)));
			PlayerController val = NetworkSingleton<TextChannelManager>.I?.MainPlayerController;
			Vector3 val2 = (((Object)(object)val != (Object)null) ? ((Component)val).transform.position : Vector3.zero);
			bool flag = (Object)(object)val != (Object)null;
			int num2 = -1;
			float num3 = float.MaxValue;
			if (flag)
			{
				int num4 = Math.Min(i.QuadPainterGPUS.Count, 3);
				for (int j = 0; j < num4; j++)
				{
					QuadPainterGPU val3 = i.QuadPainterGPUS[j];
					if (!((Object)(object)val3 == (Object)null))
					{
						float num5 = Vector3.Distance(val2, ((Component)val3).transform.position);
						if (num5 < num3)
						{
							num3 = num5;
							num2 = j;
						}
					}
				}
			}
			List<string> list = new List<string>();
			foreach (ChalkboardCatalogEntry item in ChalkboardCatalogPolicy.Build24259292)
			{
				int index = item.Index;
				if (index >= i.QuadPainterGPUS.Count)
				{
					list.Add(index + " " + item.Label + " unavailable in current scene");
					continue;
				}
				QuadPainterGPU val4 = i.QuadPainterGPUS[index];
				if ((Object)(object)val4 == (Object)null)
				{
					list.Add(index + " " + item.Label + " unavailable");
					continue;
				}
				string text = BuildHierarchyPath(((Component)val4).transform);
				Scene scene = ((Component)val4).gameObject.scene;
				string value = ((Scene)(ref scene)).name ?? string.Empty;
				Vector3 position = ((Component)val4).transform.position;
				string text2 = (string.Equals(ChalkboardModerationPolicy.ClassifyBuild24259292Location(index, position.x, position.y, position.z), item.Label, StringComparison.Ordinal) ? "mapped" : "AMBIGUOUS-MAPPING");
				string text3 = ((index == num) ? " selected" : string.Empty) + ((index == num2) ? " nearest" : string.Empty);
				string text4 = (flag ? (", " + Vector3.Distance(val2, position).ToString("0.0", CultureInfo.InvariantCulture) + "m away") : string.Empty);
				string text5 = ((text.Length > 96) ? ("…" + text.Substring(text.Length - 95)) : text);
				list.Add($"{index} {item.Label} scene={SafeDisplayName(value)} state={text2} at ({position.x:0.0},{position.y:0.0},{position.z:0.0}){text4}" + ((text3.Length > 0) ? (" [" + text3.Trim() + "]") : string.Empty) + " — " + text5);
			}
			string text6 = ((i.QuadPainterGPUS.Count > 3) ? " Extra live surfaces are ignored and cannot become index 3." : string.Empty);
			return "Chalkboards (fresh for " + 30 + "s; exact build 24259292 catalog): " + string.Join("; ", list) + "." + text6 + " Local actions: view/save/delete/refresh. Shared actions: Host-direct or authenticated Helper-to-Host load/clear. compatibleRecipients=" + ChalkboardModerationController.CountCompatibleRecipients() + ", snapshot=required-before-destructive-action, rollback=" + (_rollbackUnresolved ? "unresolved" : "ready") + ", vanillaObserver=not-observed. Clear/load only after rechecking this list.";
		}

		internal static string TryClear(string boardToken)
		{
			//IL_00ec: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ee: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bf: Unknown result type (might be due to invalid IL or missing references)
			//IL_0137: Unknown result type (might be due to invalid IL or missing references)
			if (!Available)
			{
				return Status();
			}
			if (!TryResolveBoard(boardToken, out var board, out var index, out var fingerprint, out var error))
			{
				return error;
			}
			DrawingManager i = MonoSingleton<DrawingManager>.I;
			string currentBoardSetSignature = BuildBoardSetSignature(i);
			if (!ChalkboardCommandPolicy.TryAuthorizeDestructiveAction(index, (i?.QuadPainterGPUS?.Count).GetValueOrDefault(), _lastListedBoardSetSignature, _lastListedBoardSetUnixSeconds, currentBoardSetSignature, DateTimeOffset.UtcNow.ToUnixTimeSeconds(), _rollbackUnresolved || ChalkboardSnapshotTransportController.DestructiveActionsBlocked, out var error2))
			{
				return error2;
			}
			if (!SteamIdModerationController.CanLocalIssue(out var isHost, out var reason))
			{
				return reason;
			}
			if (isHost)
			{
				string issuerSteamId = (SteamManager.Initialized ? ((ulong)SteamUser.GetSteamID()).ToString() : string.Empty);
				ExecuteClearAsHost(index, fingerprint, issuerSteamId, out var message);
				return message;
			}
			if (!Plugin.TryGetRescueLobby(out var lobbyId) || lobbyId == CSteamID.Nil)
			{
				return "The Helper chalkboard clear request could not reach the current host; no board changed.";
			}
			try
			{
				string nonce = Guid.NewGuid().ToString("N").Substring(0, 16);
				string text = ChalkboardModerationPolicy.BuildMemberData(index, fingerprint, DateTimeOffset.UtcNow.ToUnixTimeSeconds(), nonce);
				SteamMatchmaking.SetLobbyMemberData(lobbyId, "bluesage_chalk_request_v2", text);
				return $"Helper clear request sent privately for board {index}. The host will recheck your Helper role, the live board fingerprint, freshness, nonce/replay guard, scene mapping, and exact index before clearing; no chat line was sent. " + ChalkboardModerationController.BuildTruth("clear-request", index, DescribeBoardScene(board, index), "host-pre-action-required", "pending-host");
			}
			catch (Exception ex)
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogWarning((object)("Helper chalkboard clear request failed safely: " + ex.GetType().Name + ": " + ex.Message));
				}
				return "The Helper chalkboard clear request failed safely; no board changed.";
			}
		}

		internal static void PollHostMemberDataRequests()
		{
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_006b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0078: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: 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_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b5: Unknown result type (might be due to invalid IL or missing references)
			long num = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds();
			if (num < _nextMemberDataPollUnixMilliseconds)
			{
				return;
			}
			_nextMemberDataPollUnixMilliseconds = num + 500;
			if (!Available || !SteamIdModerationController.TryGetOwnedHostLobby(out var lobby, out var ownerSteamId))
			{
				return;
			}
			string text = ((ulong)lobby).ToString();
			if (!string.Equals(_memberDataLobbyKey, text, StringComparison.Ordinal))
			{
				_memberDataLobbyKey = text;
				ResetRelayAndCooldownState();
			}
			RefreshBoardSetState(MonoSingleton<DrawingManager>.I);
			int numLobbyMembers = SteamMatchmaking.GetNumLobbyMembers(lobby);
			for (int i = 0; i < numLobbyMembers; i++)
			{
				CSteamID lobbyMemberByIndex = SteamMatchmaking.GetLobbyMemberByIndex(lobby, i);
				string text2 = ((ulong)lobbyMemberByIndex).ToString();
				if (!string.Equals(text2, ownerSteamId, StringComparison.Ordinal) && ChalkboardModerationPolicy.TryParseMemberData(SteamMatchmaking.GetLobbyMemberData(lobby, lobbyMemberByIndex, "bluesage_chalk_request_v2"), out var request))
				{
					ProcessHelperClearRequest(lobby, text2, request);
				}
			}
		}

		internal static void NotifyModerationBoardReview(string targetSteamId)
		{
			if (Available)
			{
				Plugin.AddLocalNotification("Chalkboard moderation follow-up for banned Steam …" + Suffix(targetSteamId) + ": build 24259292 exposes no authoritative drawing-owner identity, so BlueSage did not guess or auto-clear a board. If abusive chalk remains, run /chalk boards, verify the location/index, then /chalk clear <index>. A local recovery snapshot is saved before every clear.");
			}
		}

		internal static bool PrepareForFullSnapshot(QuadPainterGPU board)
		{
			return ChalkboardSnapshotTransportController.PrepareForFullSnapshot(board);
		}

		private static void ProcessHelperClearRequest(CSteamID lobby, string senderSteamId, ChalkboardClearRequest request)
		{
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			long num = DateTimeOffset.UtcNow.ToUnixTimeSeconds();
			if (!ChalkboardModerationPolicy.IsFresh(request.IssuedUnixSeconds, num) || !PlayerIdentityEvidenceController.TryResolveExact(senderSteamId, out var _, out var _) || CountLobbyMembers(lobby, senderSteamId) != 1 || !SteamIdModerationController.IsAuthorizedCurrentIssuer(senderSteamId) || !RememberClearNonce(request.Nonce) || (LastClearRequestByIssuer.TryGetValue(senderSteamId, out var value) && num - value < 2))
			{
				return;
			}
			LastClearRequestByIssuer[senderSteamId] = num;
			ChalkboardClearResult chalkboardClearResult;
			string message;
			if (string.Equals(request.Action, "load", StringComparison.Ordinal))
			{
				chalkboardClearResult = ExecuteLoadAsHost(request.SnapshotName, request.BoardIndex, request.BoardFingerprint, senderSteamId, out message);
			}
			else
			{
				if (!string.Equals(request.Action, "clear", StringComparison.Ordinal))
				{
					return;
				}
				chalkboardClearResult = ExecuteClearAsHost(request.BoardIndex, request.BoardFingerprint, senderSteamId, out message);
			}
			ManualLogSource log = Plugin.Log;
			if (log != null)
			{
				log.LogInfo((object)("Host non-chat chalkboard " + request.Action + " request from Steam …" + Suffix(senderSteamId) + ": " + message));
			}
			Plugin.AddLocalNotification(chalkboardClearResult switch
			{
				ChalkboardClearResult.Partial => "Authorized Helper chalkboard action needs retry: ", 
				ChalkboardClearResult.Complete => "Authorized Helper chalkboard action: ", 
				_ => "Helper chalkboard action rejected: ", 
			} + message);
		}

		private static ChalkboardClearResult ExecuteClearAsHost(int index, string expectedFingerprint, string issuerSteamId, out string message)
		{
			//IL_0083: Unknown result type (might be due to invalid IL or missing references)
			message = "No chalkboard changed.";
			if (!SteamIdModerationController.TryGetOwnedHostLobby(out var lobby, out var _) || !SteamIdModerationController.IsAuthorizedCurrentIssuer(issuerSteamId))
			{
				message = "Only the active host or a currently authorized Helper can request a shared chalkboard clear.";
				return ChalkboardClearResult.Rejected;
			}
			if (!TryResolveBoard(index.ToString(CultureInfo.InvariantCulture), out var board, out var index2, out var fingerprint, out var error))
			{
				message = error;
				return ChalkboardClearResult.Rejected;
			}
			if (index2 != index || !string.Equals(fingerprint, expectedFingerprint, StringComparison.Ordinal))
			{
				message = "The board identity changed after selection. No board changed; run /chalk boards again.";
				return ChalkboardClearResult.Rejected;
			}
			if (!((NetworkIdentity)board).isServer)
			{
				message = "The current client is not the authoritative board server. No board changed.";
				return ChalkboardClearResult.Rejected;
			}
			if (_rollbackUnresolved || ChalkboardSnapshotTransportController.DestructiveActionsBlocked)
			{
				message = "A prior chalkboard rollback remains unresolved. No destructive board action is allowed.";
				return ChalkboardClearResult.Rejected;
			}
			string key = (ulong)lobby + "|" + fingerprint;
			if (LastClearByBoard.TryGetValue(key, out var value) && (DateTime.UtcNow - value).TotalSeconds < 5.0)
			{
				message = "That board clear is cooling down; wait a few seconds, then recheck /chalk boards.";
				return ChalkboardClearResult.Rejected;
			}
			string text = "modclear-b" + index + "-" + DateTime.UtcNow.ToString("yyyyMMddTHHmmssZ", CultureInfo.InvariantCulture);
			if (!TrySaveResolved(text, board, index, out var message2))
			{
				message = "Pre-clear recovery snapshot failed, so BlueSage left the board unchanged. " + message2;
				return ChalkboardClearResult.Rejected;
			}
			int[][] grid = CopyGrid(board.PaintColors);
			try
			{
				int[][] grid2 = CreateBlankGrid(board.PaintColors);
				ChalkboardDeliveryResult chalkboardDeliveryResult = ApplyGridAndSync(board, grid2);
				LastClearByBoard[key] = DateTime.UtcNow;
				string text2 = ChalkboardModerationController.BuildTruth("clear", index, DescribeBoardScene(board, index), text, "ready");
				if (!chalkboardDeliveryResult.IsComplete)
				{
					message = $"Cleared board {index} locally after saving recovery snapshot '{text}', but verified-recipient delivery was partial " + $"(attempted {chalkboardDeliveryResult.Attempted}, sent {chalkboardDeliveryResult.Sent}, skipped {chalkboardDeliveryResult.Skipped}). " + $"After the {5}s cooldown, /chalk clear {index} is retry-safe because the authoritative board is already blank. " + text2;
					return ChalkboardClearResult.Partial;
				}
				message = $"Cleared board {index} after saving recovery snapshot '{text}'. " + $"Verified-recipient delivery completed (attempted {chalkboardDeliveryResult.Attempted}, sent {chalkboardDeliveryResult.Sent}, skipped {chalkboardDeliveryResult.Skipped}). " + "Compatible QoL clients replace stale pixels before the native full-board repaint; validate any vanilla observer separately. " + text2;
				return ChalkboardClearResult.Complete;
			}
			catch (Exception ex)
			{
				bool flag = false;
				try
				{
					ApplyGridAndSync(board, grid);
					flag = true;
				}
				catch (Exception ex2)
				{
					RestoreGridValues(board, grid);
					_rollbackUnresolved = true;
					ChalkboardSnapshotTransportController.MarkRollbackUnresolved("clear " + ex2.GetType().Name);
					ManualLogSource log = Plugin.Log;
					if (log != null)
					{
						log.LogError((object)("Chalkboard clear rollback repaint failed: " + ex2.GetType().Name + ": " + ex2.Message));
					}
				}
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogWarning((object)("Chalkboard clear failed safely: " + ex.GetType().Name + ": " + ex.Message));
				}
				message = "Chalkboard clear failed; rollback=" + (flag ? "restored" : "unresolved-blocking") + ", recovery snapshot='" + text + "', vanillaObserver=not-observed.";
				return ChalkboardClearResult.Rejected;
			}
		}

		private unsafe static ChalkboardDeliveryResult ApplyGridAndSync(QuadPainterGPU board, int[][] grid)
		{
			//IL_00d0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d6: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e6: Unknown result type (might be due to invalid IL or missing references)
			//IL_0102: Unknown result type (might be due to invalid IL or missing references)
			//IL_0107: 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_01b4: Unknown result type (might be due to invalid IL or missing references)
			//IL_01d2: 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_01f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ff: Unknown result type (might be due to invalid IL or missing references)
			//IL_0205: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)board == (Object)null || board.PaintColors == null || grid == null || grid.Length != board.PaintColors.Length)
			{
				throw new InvalidDataException("board grid dimensions changed");
			}
			for (int i = 0; i < grid.Length; i++)
			{
				if (board.PaintColors[i].Ints == null || grid[i] == null || grid[i].Length != board.PaintColors[i].Ints.Count)
				{
					throw new InvalidDataException("board grid dimensions changed");
				}
				for (int j = 0; j < grid[i].Length; j++)
				{
					board.PaintColors[i].Ints[j] = grid[i][j];
				}
			}
			if (!ChalkboardSnapshotTransportController.PrepareForFullSnapshot(board))
			{
				throw new InvalidOperationException("full-board render replacement could not clear the pending-pixel queue and render texture");
			}
			board.GetQuadImage_Original_1(default(PlayerID), board.PaintColors, default(RPCInfo));
			IReadOnlyList<PlayerIdentityEvidence> obj = PlayerIdentityEvidenceController.GetVerifiedRoster() ?? Array.Empty<PlayerIdentityEvidence>();
			PlayerPanelController i2 = NetworkSingleton<PlayerPanelController>.I;
			string b = ((object)((NetworkIdentity)board).localPlayerForced/*cast due to .constrained prefix*/).ToString();
			int num = 0;
			int num2 = 0;
			int num3 = 0;
			foreach (PlayerIdentityEvidence item in obj)
			{
				if (item == null || item.IsLocal || string.Equals(item.NetworkPlayerId, b, StringComparison.Ordinal))
				{
					continue;
				}
				bool flag = ChalkboardModerationController.IsCompatibleRecipient(item);
				if (flag)
				{
					num++;
				}
				int rosterIndex = item.RosterIndex;
				if (i2?.PlayerIDs == null || rosterIndex < 0 || rosterIndex >= i2.PlayerIDs.Count)
				{
					if (flag)
					{
						num3++;
					}
					continue;
				}
				PlayerID val = i2.PlayerIDs[rosterIndex];
				if (!string.Equals(((object)(*(PlayerID*)(&val))/*cast due to .constrained prefix*/).ToString(), item.NetworkPlayerId, StringComparison.Ordinal) || val == ((NetworkIdentity)board).localPlayerForced)
				{
					if (flag)
					{
						num3++;
					}
					continue;
				}
				try
				{
					board.GetQuadImage(val, board.PaintColors, default(RPCInfo));
					if (flag)
					{
						num2++;
					}
				}
				catch (Exception ex)
				{
					if (flag)
					{
						num3++;
					}
					ManualLogSource log = Plugin.Log;
					if (log != null)
					{
						log.LogWarning((object)("Chalkboard verified-recipient snapshot delivery skipped safely for roster " + rosterIndex + ": " + ex.GetType().Name + ": " + ex.Message));
					}
				}
			}
			return new ChalkboardDeliveryResult(num, num2, num3);
		}

		private static int[][] CopyGrid(IntList[] grid)
		{
			ValidateGrid(grid);
			int[][] array = new int[grid.Length][];
			for (int i = 0; i < grid.Length; i++)
			{
				array[i] = grid[i].Ints.ToArray();
			}
			return array;
		}

		private static int[][] CreateBlankGrid(IntList[] grid)
		{
			ValidateGrid(grid);
			int[][] array = new int[grid.Length][];
			for (int i = 0; i < grid.Length; i++)
			{
				array[i] = new int[grid[i].Ints.Count];
			}
			return array;
		}

		private static void RestoreGridValues(QuadPainterGPU board, int[][] grid)
		{
			if (board?.PaintColors == null || grid == null || grid.Length != board.PaintColors.Length)
			{
				return;
			}
			for (int i = 0; i < grid.Length; i++)
			{
				if (grid[i] != null && board.PaintColors[i].Ints != null && grid[i].Length == board.PaintColors[i].Ints.Count)
				{
					for (int j = 0; j < grid[i].Length; j++)
					{
						board.PaintColors[i].Ints[j] = grid[i][j];
					}
				}
			}
		}

		private static bool TryResolveBoard(string boardToken, out QuadPainterGPU board, out int index, out string fingerprint, out string error)
		{
			//IL_00bf: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ec: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fd: Unknown result type (might be due to invalid IL or missing references)
			//IL_0105: Unknown result type (might be due to invalid IL or missing references)
			//IL_013f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0147: 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)
			board = null;
			index = -1;
			fingerprint = string.Empty;
			DrawingManager i = MonoSingleton<DrawingManager>.I;
			RefreshBoardSetState(i);
			int valueOrDefault = (i?.QuadPainterGPUS?.Count).GetValueOrDefault();
			if (!ChalkboardModerationPolicy.TryParseExplicitBoardIndex(boardToken, valueOrDefault, out index, out error))
			{
				return false;
			}
			board = i.QuadPainterGPUS[index];
			if ((Object)(object)board == (Object)null)
			{
				error = "Board " + index + " is unavailable. Run /chalk boards again.";
				return false;
			}
			if (!ChalkboardCatalogPolicy.TryGet(index, out var entry))
			{
				error = "Board " + index + " is outside build 24259292's exact catalog. Index 3 is never accepted.";
				return false;
			}
			Scene scene = ((Component)board).gameObject.scene;
			string sceneName = ((Scene)(ref scene)).name ?? string.Empty;
			string hierarchyPath = BuildHierarchyPath(((Component)board).transform);
			Vector3 position = ((Component)board).transform.position;
			if (!string.Equals(ChalkboardModerationPolicy.ClassifyBuild24259292Location(index, position.x, position.y, position.z), entry.Label, StringComparison.Ordinal))
			{
				error = "Board " + index + " has an ambiguous scene/position mapping. No action is allowed; refresh /chalk boards.";
				return false;
			}
			fingerprint = ChalkboardModerationPolicy.BuildBoardFingerprint(sceneName, hierarchyPath, position.x, position.y, position.z);
			return true;
		}

		private static void RefreshBoardSetState(DrawingManager manager)
		{
			string text = BuildBoardSetSignature(manager);
			if (!string.Equals(_boardSetSignature, text, StringComparison.Ordinal))
			{
				_boardSetSignature = text;
				ResetRelayAndCooldownState();
			}
		}

		private static string BuildBoardSetSignature(DrawingManager manager)
		{
			//IL_0073: Unknown result type (might be due to invalid IL or missing references)
			//IL_0078: Unknown result type (might be due to invalid IL or missing references)
			//IL_0091: Unknown result type (might be due to invalid IL or missing references)
			//IL_0096: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b3: 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_00c1: Unknown result type (might be due to invalid IL or missing references)
			if (manager?.QuadPainterGPUS == null || manager.QuadPainterGPUS.Count == 0)
			{
				return "<no-boards>";
			}
			List<string> list = new List<string>(manager.QuadPainterGPUS.Count);
			for (int i = 0; i < manager.QuadPainterGPUS.Count; i++)
			{
				QuadPainterGPU val = manager.QuadPainterGPUS[i];
				if ((Object)(object)val == (Object)null)
				{
					list.Add(i.ToString(CultureInfo.InvariantCulture) + ":unavailable");
					continue;
				}
				Vector3 position = ((Component)val).transform.position;
				string text = i.ToString(CultureInfo.InvariantCulture);
				Scene scene = ((Component)val).gameObject.scene;
				list.Add(text + ":" + ChalkboardModerationPolicy.BuildBoardFingerprint(((Scene)(ref scene)).name ?? string.Empty, BuildHierarchyPath(((Component)val).transform), position.x, position.y, position.z));
			}
			return string.Join("|", list);
		}

		private static void ResetRelayAndCooldownState()
		{
			SeenClearNonces.Clear();
			ClearNonceOrder.Clear();
			LastClearRequestByIssuer.Clear();
			LastClearByBoard.Clear();
			_lastSharedRestoreUtc = DateTime.MinValue;
			_lastListedBoardSetSignature = string.Empty;
			_lastListedBoardSetUnixSeconds = 0L;
			_rollbackUnresolved = false;
			ChalkboardSnapshotTransportController.ResetForBoardSetChange();
		}

		private static string BuildHierarchyPath(Transform transform)
		{
			Stack<string> stack = new Stack<string>();
			Transform val = transform;
			while ((Object)(object)val != (Object)null)
			{
				stack.Push(SafeDisplayName(((Object)val).name) + "[" + val.GetSiblingIndex() + "]");
				val = val.parent;
			}
			return string.Join("/", stack.ToArray());
		}

		private static string SafeDisplayName(string value)
		{
			string text = (value ?? "Board").Replace("\r", " ").Replace("\n", " ").Replace("|", "/")
				.Trim();
			if (text.Length != 0)
			{
				return text;
			}
			return "Board";
		}

		private static int CountLobbyMembers(CSteamID lobby, string steamId)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			int num = 0;
			int numLobbyMembers = SteamMatchmaking.GetNumLobbyMembers(lobby);
			for (int i = 0; i < numLobbyMembers; i++)
			{
				if (string.Equals(((ulong)SteamMatchmaking.GetLobbyMemberByIndex(lobby, i)).ToString(), steamId, StringComparison.Ordinal))
				{
					num++;
				}
			}
			return num;
		}

		private static bool RememberClearNonce(string nonce)
		{
			if (!SeenClearNonces.Add(nonce))
			{
				return false;
			}
			ClearNonceOrder.Enqueue(nonce);
			while (ClearNonceOrder.Count > 128)
			{
				SeenClearNonces.Remove(ClearNonceOrder.Dequeue());
			}
			return true;
		}

		private static string Suffix(string steamId)
		{
			string text;
			if (steamId == null || steamId.Length <= 6)
			{
				text = steamId;
				if (text == null)
				{
					return "unknown";
				}
			}
			else
			{
				text = steamId.Substring(steamId.Length - 6);
			}
			return text;
		}

		private static int[][] ReadGrid(string path, QuadPainterGPU board)
		{
			using FileStream fileStream = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read);
			using BinaryReader binaryReader = new BinaryReader(fileStream);
			if (binaryReader.ReadString() != "BSCH1")
			{
				throw new InvalidDataException("unsupported save version");
			}
			int num = binaryReader.ReadInt32();
			int num2 = binaryReader.ReadInt32();
			if (num != board.PaintColors.Length || num < 1 || num > 512 || num2 != board.PaintColors[0].Ints.Count || num2 < 1 || num2 > 512)
			{
				throw new InvalidDataException("board dimensions do not match this board");
			}
			int[][] array = new int[num][];
			for (int i = 0; i < num; i++)
			{
				array[i] = new int[num2];
				for (int j = 0; j < num2; j++)
				{
					int num3 = binaryReader.ReadInt32();
					if (num3 < 0 || num3 > 255)
					{
						throw new InvalidDataException("invalid chalk color index");
					}
					array[i][j] = num3;
				}
			}
			if (fileStream.Position != fileStream.Length)
			{
				throw new InvalidDataException("unexpected trailing board data");
			}
			return array;
		}

		private static bool TryNormalizeName(string name, out string normalized, out string error)
		{
			normalized = (name ?? string.Empty).Tr