Decompiled source of FFAArena Lite v1.0.4

BepInEx/plugins/FFAArena_Lite/FFAArena_Lite.dll

Decompiled a day ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using FFAArenaLite.Modules;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: AssemblyCompany("FFAArena_Lite")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0+88eee74c23ce3135eb65f6847908ec4a40aaa461")]
[assembly: AssemblyProduct("FFA Arena Lite")]
[assembly: AssemblyTitle("FFAArena_Lite")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.0.0.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
	internal sealed class RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
namespace FFAArenaLite
{
	[BepInPlugin("com.cheekyentity.ffaarena.lite", "FFA Arena Lite", "1.0.4")]
	[BepInProcess("MageArena.exe")]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	public class Plugin : BaseUnityPlugin
	{
		public const string PluginGuid = "com.cheekyentity.ffaarena.lite";

		public const string PluginName = "FFA Arena Lite";

		public const string PluginVersion = "1.0.4";

		public static string modsync = "all";

		private Harmony _harmony;

		internal static ManualLogSource Log;

		internal static ConfigEntry<int> InitialLives;

		private void Awake()
		{
			//IL_0054: Unknown result type (might be due to invalid IL or missing references)
			//IL_005e: Expected O, but got Unknown
			Log = ((BaseUnityPlugin)this).Logger;
			Log.LogInfo((object)"FFA Arena Lite v1.0.4 loading...");
			InitialLives = ((BaseUnityPlugin)this).Config.Bind<int>("FFA", "InitialLives", 3, "Default lives per player in FFA last-player-standing mode.");
			try
			{
				FFALastStand.DefaultLives = InitialLives.Value;
			}
			catch
			{
			}
			_harmony = new Harmony("com.cheekyentity.ffaarena.lite");
			_harmony.PatchAll();
			Log.LogInfo((object)"Harmony patches applied.");
		}

		private void OnDestroy()
		{
			try
			{
				Harmony harmony = _harmony;
				if (harmony != null)
				{
					harmony.UnpatchSelf();
				}
			}
			catch
			{
			}
			ManualLogSource log = Log;
			if (log != null)
			{
				log.LogInfo((object)"Harmony patches removed. Goodbye.");
			}
		}
	}
}
namespace FFAArenaLite.Patches
{
	[HarmonyPatch]
	public static class EnableMeshRenderersPatch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("EnableMeshRenderers");
			if (type == null)
			{
				return null;
			}
			return AccessTools.Method(type, "enableRenderers", (Type[])null, (Type[])null);
		}

		[HarmonyPrefix]
		private static bool Prefix(object __instance)
		{
			bool flag = FFAMode.IsActive();
			try
			{
				if (!flag)
				{
					try
					{
						flag = MainMenuPatch.IsFFASelected();
					}
					catch
					{
					}
				}
			}
			catch
			{
			}
			if (!flag)
			{
				return true;
			}
			try
			{
				Component val = (Component)((__instance is Component) ? __instance : null);
				if ((Object)(object)val == (Object)null)
				{
					return true;
				}
				int num = 0;
				int num2 = 0;
				MeshRenderer[] componentsInChildren = val.GetComponentsInChildren<MeshRenderer>(true);
				foreach (MeshRenderer val2 in componentsInChildren)
				{
					if (!((Object)(object)val2 == (Object)null))
					{
						if (ShouldSkipObject(((Component)val2).gameObject, ((Renderer)val2).sharedMaterials))
						{
							num2++;
							continue;
						}
						((Renderer)val2).enabled = true;
						num++;
					}
				}
				SkinnedMeshRenderer[] componentsInChildren2 = val.GetComponentsInChildren<SkinnedMeshRenderer>(true);
				foreach (SkinnedMeshRenderer val3 in componentsInChildren2)
				{
					if (!((Object)(object)val3 == (Object)null))
					{
						if (ShouldSkipObject(((Component)val3).gameObject, ((Renderer)val3).sharedMaterials))
						{
							num2++;
							continue;
						}
						((Renderer)val3).enabled = true;
						num++;
					}
				}
				if (num2 > 0)
				{
					ManualLogSource log = Plugin.Log;
					if (log != null)
					{
						log.LogInfo((object)$"EnableMeshRenderersPatch: enabled={num}, skipped(flag/pole/banner)={num2} under '{((Object)val.gameObject).name}'.");
					}
				}
				return false;
			}
			catch (Exception arg)
			{
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogWarning((object)$"EnableMeshRenderersPatch failed, falling back to original: {arg}");
				}
				return true;
			}
		}

		private static bool ShouldSkipObject(GameObject go, Material[] mats)
		{
			try
			{
				if ((Object)(object)go == (Object)null)
				{
					return false;
				}
				Type type = AccessTools.TypeByName("FlagController");
				if (type != null)
				{
					MethodInfo method = typeof(Component).GetMethod("GetComponentInParent", new Type[1] { typeof(Type) });
					if (method != null && (Object)/*isinst with value type is only supported in some contexts*/ != (Object)null)
					{
						return true;
					}
				}
				if (NameMatchesHeuristic(go.transform))
				{
					return true;
				}
				try
				{
					if (mats != null)
					{
						foreach (Material val in mats)
						{
							if (!((Object)(object)val == (Object)null) && StringMatchesHeuristic(((Object)val).name))
							{
								return true;
							}
						}
					}
				}
				catch
				{
				}
			}
			catch
			{
			}
			return false;
		}

		private static bool NameMatchesHeuristic(Transform t)
		{
			int num = 0;
			while ((Object)(object)t != (Object)null && num++ < 5)
			{
				if (StringMatchesHeuristic(((Object)t).name))
				{
					return true;
				}
				t = t.parent;
			}
			return false;
		}

		private static bool StringMatchesHeuristic(string s)
		{
			if (string.IsNullOrEmpty(s))
			{
				return false;
			}
			s = s.ToLowerInvariant();
			if (!s.Contains("flag") && !s.Contains("pole") && !s.Contains("banner"))
			{
				return s.Contains("pennant");
			}
			return true;
		}
	}
	[HarmonyPatch]
	public static class FlagController_OnStartClient_FFAPatch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("FlagController");
			if (!(type != null))
			{
				return null;
			}
			return AccessTools.Method(type, "OnStartClient", (Type[])null, (Type[])null);
		}

		private static bool Prefix(object __instance)
		{
			try
			{
				if (!FFAMode.IsActive() && !MainMenuPatch.IsFFASelected())
				{
					return true;
				}
				Component val = (Component)((__instance is Component) ? __instance : null);
				if (val != null && (Object)(object)val != (Object)null)
				{
					Behaviour val2 = (Behaviour)(object)((val is Behaviour) ? val : null);
					if (val2 != null)
					{
						val2.enabled = false;
					}
					Collider component = val.GetComponent<Collider>();
					if ((Object)(object)component != (Object)null)
					{
						component.enabled = false;
					}
					try
					{
						Type type = ((object)val).GetType();
						FieldInfo fieldInfo = AccessTools.Field(type, "flagvisual");
						FieldInfo fieldInfo2 = AccessTools.Field(type, "FlagAni");
						FieldInfo fieldInfo3 = AccessTools.Field(type, "particles");
						FieldInfo fieldInfo4 = AccessTools.Field(type, "FlagAudio");
						object? obj = fieldInfo?.GetValue(__instance);
						Renderer val3 = (Renderer)((obj is Renderer) ? obj : null);
						if (val3 != null)
						{
							val3.enabled = false;
						}
						object? obj2 = fieldInfo2?.GetValue(__instance);
						Behaviour val4 = (Behaviour)((obj2 is Behaviour) ? obj2 : null);
						if (val4 != null)
						{
							val4.enabled = false;
						}
						if (fieldInfo3?.GetValue(__instance) is ParticleSystem[] array)
						{
							ParticleSystem[] array2 = array;
							foreach (ParticleSystem val5 in array2)
							{
								if (!((Object)(object)val5 == (Object)null))
								{
									val5.Stop(true, (ParticleSystemStopBehavior)0);
									Renderer component2 = ((Component)val5).GetComponent<Renderer>();
									if (Object.op_Implicit((Object)(object)component2))
									{
										component2.enabled = false;
									}
								}
							}
						}
						object? obj3 = fieldInfo4?.GetValue(__instance);
						AudioSource val6 = (AudioSource)((obj3 is AudioSource) ? obj3 : null);
						if (val6 != null)
						{
							val6.Stop();
							((Behaviour)val6).enabled = false;
						}
						Renderer[] componentsInChildren = val.GetComponentsInChildren<Renderer>(true);
						foreach (Renderer val7 in componentsInChildren)
						{
							if ((Object)(object)val7 == (Object)null)
							{
								continue;
							}
							string text = ((Object)val7).name.ToLowerInvariant();
							bool flag = text.Contains("flag") || text.Contains("pole") || text.Contains("banner");
							if (!flag)
							{
								try
								{
									Material[] sharedMaterials = val7.sharedMaterials;
									for (int j = 0; j < sharedMaterials.Length; j++)
									{
										if (flag)
										{
											break;
										}
										Material val8 = sharedMaterials[j];
										if (!((Object)(object)val8 == (Object)null))
										{
											string text2 = ((Object)val8).name.ToLowerInvariant();
											if (text2.Contains("flag") || text2.Contains("pole") || text2.Contains("banner"))
											{
												flag = true;
											}
										}
									}
								}
								catch
								{
								}
							}
							if (flag)
							{
								val7.enabled = false;
							}
						}
					}
					catch
					{
					}
					try
					{
						string text3 = (((Object)(object)val.gameObject != (Object)null) ? ((Object)val.gameObject).name : "<null>");
						ManualLogSource log = Plugin.Log;
						if (log != null)
						{
							log.LogInfo((object)("FFA: Neutralized FlagController in OnStartClient on '" + text3 + "'."));
						}
					}
					catch
					{
					}
				}
				return false;
			}
			catch (Exception arg)
			{
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogWarning((object)$"FFA: FlagController_OnStartClient_FFAPatch failed: {arg}");
				}
				return true;
			}
		}
	}
	[HarmonyPatch]
	public static class FlagController_Awake_FFAPatch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("FlagController");
			if (!(type != null))
			{
				return null;
			}
			return AccessTools.Method(type, "Awake", (Type[])null, (Type[])null);
		}

		private static bool Prefix(object __instance)
		{
			try
			{
				if (!FFAMode.IsActive() && !MainMenuPatch.IsFFASelected())
				{
					return true;
				}
				Component val = (Component)((__instance is Component) ? __instance : null);
				if (val != null && (Object)(object)val != (Object)null)
				{
					Behaviour val2 = (Behaviour)(object)((val is Behaviour) ? val : null);
					if (val2 != null)
					{
						val2.enabled = false;
					}
					Collider component = val.GetComponent<Collider>();
					if ((Object)(object)component != (Object)null)
					{
						component.enabled = false;
					}
					try
					{
						Type type = ((object)val).GetType();
						FieldInfo fieldInfo = AccessTools.Field(type, "flagvisual");
						FieldInfo fieldInfo2 = AccessTools.Field(type, "FlagAni");
						FieldInfo fieldInfo3 = AccessTools.Field(type, "particles");
						FieldInfo fieldInfo4 = AccessTools.Field(type, "FlagAudio");
						object? obj = fieldInfo?.GetValue(__instance);
						Renderer val3 = (Renderer)((obj is Renderer) ? obj : null);
						if (val3 != null)
						{
							val3.enabled = false;
						}
						object? obj2 = fieldInfo2?.GetValue(__instance);
						Behaviour val4 = (Behaviour)((obj2 is Behaviour) ? obj2 : null);
						if (val4 != null)
						{
							val4.enabled = false;
						}
						if (fieldInfo3?.GetValue(__instance) is ParticleSystem[] array)
						{
							ParticleSystem[] array2 = array;
							foreach (ParticleSystem val5 in array2)
							{
								if (!((Object)(object)val5 == (Object)null))
								{
									val5.Stop(true, (ParticleSystemStopBehavior)0);
									Renderer component2 = ((Component)val5).GetComponent<Renderer>();
									if (Object.op_Implicit((Object)(object)component2))
									{
										component2.enabled = false;
									}
								}
							}
						}
						object? obj3 = fieldInfo4?.GetValue(__instance);
						AudioSource val6 = (AudioSource)((obj3 is AudioSource) ? obj3 : null);
						if (val6 != null)
						{
							val6.Stop();
							((Behaviour)val6).enabled = false;
						}
						Renderer[] componentsInChildren = val.GetComponentsInChildren<Renderer>(true);
						foreach (Renderer val7 in componentsInChildren)
						{
							if ((Object)(object)val7 == (Object)null)
							{
								continue;
							}
							string text = ((Object)val7).name.ToLowerInvariant();
							bool flag = text.Contains("flag") || text.Contains("pole") || text.Contains("banner");
							if (!flag)
							{
								try
								{
									Material[] sharedMaterials = val7.sharedMaterials;
									for (int j = 0; j < sharedMaterials.Length; j++)
									{
										if (flag)
										{
											break;
										}
										Material val8 = sharedMaterials[j];
										if (!((Object)(object)val8 == (Object)null))
										{
											string text2 = ((Object)val8).name.ToLowerInvariant();
											if (text2.Contains("flag") || text2.Contains("pole") || text2.Contains("banner"))
											{
												flag = true;
											}
										}
									}
								}
								catch
								{
								}
							}
							if (flag)
							{
								val7.enabled = false;
							}
						}
					}
					catch
					{
					}
					try
					{
						string text3 = (((Object)(object)val.gameObject != (Object)null) ? ((Object)val.gameObject).name : "<null>");
						ManualLogSource log = Plugin.Log;
						if (log != null)
						{
							log.LogInfo((object)("FFA: Neutralized FlagController in Awake on '" + text3 + "'."));
						}
					}
					catch
					{
					}
				}
				return false;
			}
			catch (Exception arg)
			{
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogWarning((object)$"FFA: FlagController_Awake_FFAPatch failed: {arg}");
				}
				return true;
			}
		}
	}
	[HarmonyPatch]
	public static class CastleFlagCapturedNotifier_Start_FFAPatch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("CastleFlagCapturedNotifier");
			if (!(type != null))
			{
				return null;
			}
			return AccessTools.Method(type, "StartFlagsShit", (Type[])null, (Type[])null);
		}

		private static bool Prefix(object __instance)
		{
			try
			{
				if (!FFAMode.IsActive())
				{
					return true;
				}
				Component val = (Component)((__instance is Component) ? __instance : null);
				if (val != null && (Object)(object)val != (Object)null)
				{
					Behaviour val2 = (Behaviour)(object)((val is Behaviour) ? val : null);
					if (val2 != null)
					{
						val2.enabled = false;
					}
					ManualLogSource log = Plugin.Log;
					if (log != null)
					{
						log.LogInfo((object)"FFA: Disabled CastleFlagCapturedNotifier component.");
					}
				}
				return false;
			}
			catch (Exception arg)
			{
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogWarning((object)$"FFA: CastleFlagCapturedNotifier_Start_FFAPatch failed: {arg}");
				}
				return true;
			}
		}
	}
	[HarmonyPatch]
	public static class MagicMissleController_Update_Prefix
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("MagicMissleController");
			if (!(type == null))
			{
				return AccessTools.Method(type, "Update", (Type[])null, (Type[])null);
			}
			return null;
		}

		private static void Prefix(object __instance)
		{
			//IL_011f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0129: Unknown result type (might be due to invalid IL or missing references)
			//IL_01bc: Unknown result type (might be due to invalid IL or missing references)
			//IL_01c2: Unknown result type (might be due to invalid IL or missing references)
			//IL_01cc: Unknown result type (might be due to invalid IL or missing references)
			//IL_01d1: Unknown result type (might be due to invalid IL or missing references)
			//IL_01d6: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e1: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e5: Unknown result type (might be due to invalid IL or missing references)
			//IL_008c: 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_00e5: 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_00e1: 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_00ec: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				if (!FFAMode.IsActive())
				{
					return;
				}
				Type type = __instance.GetType();
				FieldInfo fieldInfo = AccessTools.Field(type, "MissleTarget");
				object? obj = fieldInfo?.GetValue(__instance);
				if ((Object)((obj is GameObject) ? obj : null) != (Object)null)
				{
					return;
				}
				object? obj2 = AccessTools.Field(type, "playerOwner")?.GetValue(__instance);
				GameObject val = (GameObject)((obj2 is GameObject) ? obj2 : null);
				if ((Object)(object)val == (Object)null)
				{
					return;
				}
				object obj3 = AccessTools.Field(type, "playerLayer")?.GetValue(__instance);
				int num2 = ((obj3 is LayerMask val2) ? ((LayerMask)(ref val2)).value : ((obj3 is int num) ? num : (-1)));
				Vector3 val4 = ((AccessTools.Field(type, "forwardVector")?.GetValue(__instance) is Vector3 val3) ? val3 : Vector3.forward);
				bool flag = false;
				try
				{
					FieldInfo fieldInfo2 = AccessTools.Field(type, "shotByAi");
					if (fieldInfo2 != null)
					{
						flag = (bool)fieldInfo2.GetValue(__instance);
					}
				}
				catch
				{
				}
				Collider[] array = Physics.OverlapSphere(((Component)__instance).transform.position, 30f, num2);
				float num3 = float.MaxValue;
				GameObject val5 = null;
				Collider[] array2 = array;
				GetPlayerGameobject val7 = default(GetPlayerGameobject);
				foreach (Collider val6 in array2)
				{
					if ((Object)(object)val6 == (Object)null)
					{
						continue;
					}
					GameObject gameObject = ((Component)val6).gameObject;
					if ((Object)(object)gameObject == (Object)(object)val || (gameObject.TryGetComponent<GetPlayerGameobject>(ref val7) && (Object)(object)val7.player == (Object)(object)val) || (flag && (gameObject.CompareTag("PlayerNpc") || gameObject.CompareTag("Ignorable"))))
					{
						continue;
					}
					Vector3 val8 = ((Component)val6).transform.position - ((Component)__instance).transform.position;
					float magnitude = ((Vector3)(ref val8)).magnitude;
					float num4 = Vector3.Angle(val4, ((Vector3)(ref val8)).normalized);
					if (!(num4 > 90f))
					{
						float num5 = magnitude + num4 * 0.5f;
						if (num5 < num3)
						{
							num3 = num5;
							val5 = gameObject;
						}
					}
				}
				if ((Object)(object)val5 != (Object)null)
				{
					fieldInfo?.SetValue(__instance, val5);
				}
			}
			catch (Exception arg)
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogDebug((object)$"MagicMissile FFA target selection error: {arg}");
				}
			}
		}
	}
	[HarmonyPatch]
	public static class MainMenuPatch
	{
		private static int? selectedFFAMapinfo;

		internal static bool IsFFASelected()
		{
			return selectedFFAMapinfo.HasValue;
		}

		public static bool ShouldHideTeamUI(object mainMenuInstance)
		{
			try
			{
				if (FFAMode.IsActive() || IsFFASelected())
				{
					return true;
				}
				Type type = mainMenuInstance?.GetType();
				GameObject val = null;
				try
				{
					object? obj = AccessTools.Field(type, "InGameLobby")?.GetValue(mainMenuInstance);
					val = (GameObject)((obj is GameObject) ? obj : null);
				}
				catch
				{
				}
				if ((Object)(object)val != (Object)null && MarkerInTransformTree(val.transform))
				{
					return true;
				}
				try
				{
					Transform[] array = Resources.FindObjectsOfTypeAll<Transform>();
					foreach (Transform val2 in array)
					{
						if (!((Object)(object)val2 == (Object)null))
						{
							switch (((Object)val2).name)
							{
							case "FFA_Medium_Button":
							case "FFA_Large_Button":
							case "FreeForAllLabel_Auto":
							case "EditTeamFlag":
								return true;
							}
						}
					}
				}
				catch
				{
				}
			}
			catch
			{
			}
			return false;
			static bool MarkerInTransformTree(Transform root)
			{
				if ((Object)(object)root == (Object)null)
				{
					return false;
				}
				Transform[] componentsInChildren = ((Component)root).GetComponentsInChildren<Transform>(true);
				foreach (Transform val3 in componentsInChildren)
				{
					if (!((Object)(object)val3 == (Object)null))
					{
						string name = ((Object)val3).name;
						if (!string.IsNullOrEmpty(name))
						{
							switch (name)
							{
							case "FFA_Medium_Button":
							case "FFA_Large_Button":
							case "FreeForAllLabel_Auto":
							case "EditTeamFlag":
								return true;
							}
						}
					}
				}
				return false;
			}
		}

		internal static bool IsLocalHostOrServer(object mainMenuInstance)
		{
			try
			{
				Type type = AccessTools.TypeByName("FishNet.Managing.NetworkManager");
				if (type != null)
				{
					object obj = type.GetProperty("Instance", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic)?.GetValue(null, null) ?? Object.FindFirstObjectByType(type);
					if (obj != null)
					{
						PropertyInfo propertyInfo = type.GetProperty("IsServer", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic) ?? type.GetProperty("IsHost", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
						if (propertyInfo != null)
						{
							object value = propertyInfo.GetValue(obj, null);
							bool flag = default(bool);
							int num;
							if (value is bool)
							{
								flag = (bool)value;
								num = 1;
							}
							else
							{
								num = 0;
							}
							if (((uint)num & (flag ? 1u : 0u)) != 0)
							{
								return true;
							}
						}
					}
				}
			}
			catch
			{
			}
			return false;
		}

		internal static Transform FindInactiveTransform(string path)
		{
			if (string.IsNullOrEmpty(path))
			{
				return null;
			}
			try
			{
				string[] array = path.Split('/');
				if (array.Length == 0)
				{
					return null;
				}
				Transform[] array2 = Resources.FindObjectsOfTypeAll<Transform>();
				Transform val = null;
				Transform[] array3 = array2;
				foreach (Transform val2 in array3)
				{
					if ((Object)(object)val2.parent == (Object)null && ((Object)val2).name == array[0])
					{
						val = val2;
						break;
					}
				}
				if ((Object)(object)val == (Object)null)
				{
					return null;
				}
				for (int j = 1; j < array.Length; j++)
				{
					string text = array[j];
					Transform val3 = null;
					for (int k = 0; k < val.childCount; k++)
					{
						Transform child = val.GetChild(k);
						if ((Object)(object)child != (Object)null && ((Object)child).name == text)
						{
							val3 = child;
							break;
						}
					}
					if ((Object)(object)val3 == (Object)null)
					{
						return null;
					}
					val = val3;
				}
				return val;
			}
			catch
			{
				return null;
			}
		}

		internal static Button CloneButtonFromPath(string sourcePath, Transform parent, string newName, string label, Action onClick)
		{
			//IL_0087: 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_00ff: Unknown result type (might be due to invalid IL or missing references)
			//IL_0109: Expected O, but got Unknown
			try
			{
				Transform val = FindInactiveTransform(sourcePath);
				if ((Object)(object)val == (Object)null)
				{
					return null;
				}
				Button component = ((Component)val).GetComponent<Button>();
				if ((Object)(object)component == (Object)null)
				{
					return null;
				}
				GameObject val2 = Object.Instantiate<GameObject>(((Component)component).gameObject, parent);
				((Object)val2).name = newName;
				val2.SetActive(true);
				if ((Object)(object)parent != (Object)null)
				{
					val2.layer = ((Component)parent).gameObject.layer;
				}
				RectTransform component2 = val2.GetComponent<RectTransform>();
				if ((Object)(object)component2 != (Object)null)
				{
					((Transform)component2).localScale = Vector3.one;
					component2.anchoredPosition3D = Vector3.zero;
				}
				CanvasGroup component3 = val2.GetComponent<CanvasGroup>();
				if ((Object)(object)component3 != (Object)null)
				{
					component3.alpha = 1f;
					component3.interactable = true;
					component3.blocksRaycasts = true;
				}
				Button component4 = val2.GetComponent<Button>();
				if ((Object)(object)component4 != (Object)null)
				{
					((UnityEventBase)component4.onClick).RemoveAllListeners();
					if (onClick != null)
					{
						((UnityEvent)component4.onClick).AddListener((UnityAction)delegate
						{
							onClick();
						});
					}
				}
				Text[] componentsInChildren = val2.GetComponentsInChildren<Text>(true);
				for (int i = 0; i < componentsInChildren.Length; i++)
				{
					componentsInChildren[i].text = label;
				}
				return component4;
			}
			catch
			{
				return null;
			}
		}

		[HarmonyPostfix]
		private static void ActuallyStartGameActually_Postfix(object __instance)
		{
			//IL_032b: Unknown result type (might be due to invalid IL or missing references)
			//IL_022d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0232: Unknown result type (might be due to invalid IL or missing references)
			//IL_024f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0254: Unknown result type (might be due to invalid IL or missing references)
			//IL_026c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0271: Unknown result type (might be due to invalid IL or missing references)
			//IL_02d3: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				Type type = __instance.GetType();
				FieldInfo fieldInfo = AccessTools.Field(type, "pm");
				if (fieldInfo == null)
				{
					return;
				}
				object value = fieldInfo.GetValue(__instance);
				if (value == null)
				{
					return;
				}
				FieldInfo fieldInfo2 = AccessTools.Field(value.GetType(), "teamSpawns");
				if (fieldInfo2 == null)
				{
					return;
				}
				object value2 = fieldInfo2.GetValue(value);
				Type elemType = (fieldInfo2.FieldType.IsArray ? fieldInfo2.FieldType.GetElementType() : null);
				if (elemType == null)
				{
					return;
				}
				SpawnService spawnService = new SpawnService();
				FieldInfo fieldInfo3 = AccessTools.Field(type, "mapinfo");
				if (fieldInfo3 != null)
				{
					try
					{
						_ = (int)fieldInfo3.GetValue(__instance);
					}
					catch
					{
					}
				}
				if (selectedFFAMapinfo.HasValue)
				{
					spawnService.CollectFFASpawnsByMapInfo(selectedFFAMapinfo.Value);
					ManualLogSource log = Plugin.Log;
					if (log != null)
					{
						log.LogInfo((object)$"Using FFA custom spawns for mapinfo={selectedFFAMapinfo.Value}.");
					}
				}
				else
				{
					spawnService.CollectNeutralSpawns();
				}
				IReadOnlyList<Transform> sourceSpawns = spawnService.GetSpawns();
				Type wormholeType = AccessTools.TypeByName("RespawnWormhole");
				bool wantWormholes = wormholeType != null && elemType == wormholeType;
				int desiredLen = 4;
				Array array;
				try
				{
					array = BuildWormholesFromTransforms();
				}
				catch
				{
					array = value2 as Array;
				}
				if (array != null)
				{
					if (array.Length < desiredLen)
					{
						Array array2 = Array.CreateInstance(elemType, desiredLen);
						for (int i = 0; i < desiredLen; i++)
						{
							object value3 = ((i < array.Length) ? array.GetValue(i) : ((array.Length > 0) ? array.GetValue(0) : null));
							array2.SetValue(value3, i);
						}
						array = array2;
					}
					fieldInfo2.SetValue(value, array);
				}
				selectedFFAMapinfo = null;
				try
				{
					int num = array?.Length ?? 0;
					if (num <= 0)
					{
						return;
					}
					object? value4 = array.GetValue(0);
					Object val = (Object)((value4 is Object) ? value4 : null);
					Vector3 val2 = Vector3.zero;
					string text = string.Empty;
					Component val3 = (Component)(object)((val is Component) ? val : null);
					if (val3 != null)
					{
						val2 = val3.transform.position;
					}
					else
					{
						GameObject val4 = (GameObject)(object)((val is GameObject) ? val : null);
						if (val4 != null)
						{
							val2 = val4.transform.position;
						}
					}
					try
					{
						Type type2 = ((object)val)?.GetType();
						if (type2 != null && type2.Name == "RespawnWormhole")
						{
							object? obj3 = AccessTools.Field(type2, "spawnpos")?.GetValue(val);
							Transform val5 = (Transform)((obj3 is Transform) ? obj3 : null);
							if ((Object)(object)val5 != (Object)null)
							{
								text = $", spawnpos={val5.position}";
							}
						}
					}
					catch
					{
					}
					ManualLogSource log2 = Plugin.Log;
					if (log2 != null)
					{
						log2.LogDebug((object)string.Format("teamSpawns[0/{0}] type={1} pos={2}{3}", num, (val != (Object)null) ? ((object)val).GetType().Name : "null", val2, text));
					}
				}
				catch
				{
				}
				Array BuildWormholesFromTransforms()
				{
					//IL_0240: Unknown result type (might be due to invalid IL or missing references)
					//IL_021d: Unknown result type (might be due to invalid IL or missing references)
					//IL_0222: Unknown result type (might be due to invalid IL or missing references)
					//IL_0166: Unknown result type (might be due to invalid IL or missing references)
					//IL_013a: Unknown result type (might be due to invalid IL or missing references)
					//IL_0141: Expected O, but got Unknown
					//IL_00c2: Unknown result type (might be due to invalid IL or missing references)
					//IL_00c9: Expected O, but got Unknown
					int num2 = Mathf.Max(desiredLen, sourceSpawns.Count);
					Array array3 = Array.CreateInstance(elemType, num2);
					SpawnService.EnsureRuntimeContainer();
					GameObject val6 = null;
					try
					{
						val6 = GameObject.Find("FFA_Runtime_SpawnContainer");
					}
					catch
					{
					}
					for (int j = 0; j < num2; j++)
					{
						Transform val7 = ((sourceSpawns.Count > 0) ? sourceSpawns[j % sourceSpawns.Count] : null);
						object obj7 = null;
						if ((Object)(object)val7 != (Object)null)
						{
							if (wantWormholes)
							{
								GameObject val8 = null;
								try
								{
									string text2 = $"FFA_Wormhole_{j}";
									if ((Object)(object)val6 != (Object)null)
									{
										Transform val9 = null;
										foreach (Transform item in val6.transform)
										{
											Transform val10 = item;
											if ((Object)(object)val10 != (Object)null && ((Object)val10).name == text2)
											{
												val9 = val10;
												break;
											}
										}
										val8 = (((Object)(object)val9 != (Object)null) ? ((Component)val9).gameObject : null);
									}
									if ((Object)(object)val8 == (Object)null)
									{
										val8 = new GameObject($"FFA_Wormhole_{j}");
										if ((Object)(object)val6 != (Object)null)
										{
											val8.transform.SetParent(val6.transform, false);
										}
									}
									val8.transform.position = val7.position;
									MethodInfo method = typeof(GameObject).GetMethod("AddComponent", new Type[1] { typeof(Type) });
									Component val11 = (Component)(((object)val8.GetComponent(wormholeType)) ?? ((object)/*isinst with value type is only supported in some contexts*/));
									if ((Object)(object)val11 != (Object)null)
									{
										FieldInfo fieldInfo4 = AccessTools.Field(wormholeType, "spawnpos");
										Transform val12 = null;
										try
										{
											object? obj8 = fieldInfo4?.GetValue(val11);
											val12 = (Transform)((obj8 is Transform) ? obj8 : null);
										}
										catch
										{
										}
										if ((Object)(object)val12 == (Object)null)
										{
											GameObject val13 = new GameObject("spawnpos");
											val13.transform.SetParent(val8.transform, false);
											val12 = val13.transform;
										}
										val12.position = val7.position;
										fieldInfo4?.SetValue(val11, val12);
										obj7 = val11;
									}
								}
								catch
								{
								}
							}
							else
							{
								object obj11 = ((val7 != null) ? ((Component)val7).GetComponent(elemType) : null);
								if (obj11 == null)
								{
									obj11 = ((val7 != null) ? ((Component)val7).GetComponentInChildren(elemType, true) : null);
								}
								obj7 = obj11;
								if (obj7 == null && elemType == typeof(Transform))
								{
									obj7 = val7;
								}
							}
						}
						array3.SetValue(obj7, j);
					}
					object obj12 = null;
					for (int k = 0; k < array3.Length; k++)
					{
						if (array3.GetValue(k) != null)
						{
							obj12 = array3.GetValue(k);
							break;
						}
					}
					if (obj12 != null)
					{
						for (int l = 0; l < array3.Length; l++)
						{
							if (array3.GetValue(l) == null)
							{
								array3.SetValue(obj12, l);
							}
						}
					}
					return array3;
				}
			}
			catch (Exception arg)
			{
				ManualLogSource log3 = Plugin.Log;
				if (log3 != null)
				{
					log3.LogWarning((object)$"MainMenuPatch hydration failed: {arg}");
				}
			}
		}

		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("MainMenuManager");
			if (type == null)
			{
				return null;
			}
			return AccessTools.Method(type, "ActuallyStartGameActually", (Type[])null, (Type[])null);
		}

		public static void ApplyFFASelection(object mainMenuInstance, int mapinfoValue)
		{
			try
			{
				Type type = mainMenuInstance.GetType();
				AccessTools.Field(type, "mapinfo")?.SetValue(mainMenuInstance, mapinfoValue);
				selectedFFAMapinfo = mapinfoValue;
				Type type2 = AccessTools.TypeByName("BootstrapManager");
				object obj = AccessTools.Property(type2, "instance")?.GetValue(null, null);
				AccessTools.Method(type2, "ChangeLobbySize", (Type[])null, (Type[])null)?.Invoke(obj, new object[1] { 8 });
				if (AccessTools.Field(type, "checkmarks")?.GetValue(mainMenuInstance) is GameObject[] array && array.Length >= 3)
				{
					array[0].SetActive(mapinfoValue == 1);
					array[1].SetActive(mapinfoValue == 0);
					array[2].SetActive(false);
				}
				try
				{
					int num = 0;
					Transform[] array2 = Resources.FindObjectsOfTypeAll<Transform>();
					foreach (Transform val in array2)
					{
						if ((Object)(object)val != (Object)null && string.Equals(((Object)val).name, "EditTeamFlag", StringComparison.OrdinalIgnoreCase))
						{
							((Component)val).gameObject.SetActive(false);
							num++;
						}
					}
					if (num > 0)
					{
						ManualLogSource log = Plugin.Log;
						if (log != null)
						{
							log.LogInfo((object)$"FFA: hid {num} EditTeamFlag object(s) on selection.");
						}
					}
				}
				catch
				{
				}
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogInfo((object)$"FFA selected. mapinfo={mapinfoValue}. Lobby size set to 8.");
				}
				SpawnService.EnsureRuntimeContainer();
			}
			catch (Exception arg)
			{
				ManualLogSource log3 = Plugin.Log;
				if (log3 != null)
				{
					log3.LogWarning((object)$"ApplyFFASelection failed: {arg}");
				}
			}
		}

		internal static void ClearFFAState()
		{
			try
			{
				selectedFFAMapinfo = null;
				SpawnService.DestroyRuntimeContainer();
				FFALastStand.Reset();
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogInfo((object)"FFA: cleared selection and destroyed runtime container.");
				}
			}
			catch
			{
			}
		}
	}
	[HarmonyPatch]
	public static class MainMenuOpenLobbyPatch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("MainMenuManager");
			if (type == null)
			{
				return null;
			}
			return AccessTools.Method(type, "OpenLobby", (Type[])null, (Type[])null);
		}

		[HarmonyPostfix]
		private static void Postfix(object __instance)
		{
			//IL_0590: Unknown result type (might be due to invalid IL or missing references)
			//IL_059e: Unknown result type (might be due to invalid IL or missing references)
			//IL_05ac: Unknown result type (might be due to invalid IL or missing references)
			//IL_05ba: Unknown result type (might be due to invalid IL or missing references)
			//IL_05c6: Unknown result type (might be due to invalid IL or missing references)
			//IL_05d2: Unknown result type (might be due to invalid IL or missing references)
			//IL_05e0: Unknown result type (might be due to invalid IL or missing references)
			//IL_05ef: Unknown result type (might be due to invalid IL or missing references)
			//IL_05f4: Unknown result type (might be due to invalid IL or missing references)
			//IL_0731: Unknown result type (might be due to invalid IL or missing references)
			//IL_073f: Unknown result type (might be due to invalid IL or missing references)
			//IL_074d: Unknown result type (might be due to invalid IL or missing references)
			//IL_075b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0767: Unknown result type (might be due to invalid IL or missing references)
			//IL_0773: Unknown result type (might be due to invalid IL or missing references)
			//IL_0781: Unknown result type (might be due to invalid IL or missing references)
			//IL_0790: Unknown result type (might be due to invalid IL or missing references)
			//IL_0795: Unknown result type (might be due to invalid IL or missing references)
			//IL_067d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0687: Expected O, but got Unknown
			//IL_081e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0828: Expected O, but got Unknown
			//IL_0afa: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b1a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a3f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a36: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a44: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a52: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a5e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a63: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a79: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a85: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a8a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b6e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b73: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b9a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b9f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e8d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e7d: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogInfo((object)"OpenLobby: Postfix start");
				}
				MainMenuPatch.ClearFFAState();
				try
				{
					int num = 0;
					Transform[] array = Resources.FindObjectsOfTypeAll<Transform>();
					foreach (Transform val in array)
					{
						if ((Object)(object)val == (Object)null)
						{
							continue;
						}
						switch (((Object)val).name)
						{
						case "FFA_Medium_Button":
						case "FFA_Large_Button":
						case "FreeForAllLabel_Auto":
							if (((Component)val).gameObject.activeSelf)
							{
								((Component)val).gameObject.SetActive(false);
								num++;
							}
							break;
						}
					}
					if (num > 0)
					{
						ManualLogSource log2 = Plugin.Log;
						if (log2 != null)
						{
							log2.LogDebug((object)$"FFA: Pre-sanitize — hid {num} FFA UI object(s).");
						}
					}
				}
				catch
				{
				}
				Type type = __instance.GetType();
				if (!MainMenuPatch.IsLocalHostOrServer(__instance))
				{
					ManualLogSource log3 = Plugin.Log;
					if (log3 != null)
					{
						log3.LogDebug((object)"OpenLobby: detected Client (not host) — will hide FFA UI");
					}
					try
					{
						Transform val2 = null;
						try
						{
							object obj2 = AccessTools.Field(type, "Mapchoseholder")?.GetValue(__instance);
							GameObject val3 = (GameObject)((obj2 is GameObject) ? obj2 : null);
							if (val3 != null)
							{
								val2 = val3.transform;
							}
							else
							{
								Transform val4 = (Transform)((obj2 is Transform) ? obj2 : null);
								if (val4 != null)
								{
									val2 = val4;
								}
							}
						}
						catch
						{
						}
						if ((Object)(object)val2 == (Object)null)
						{
							Canvas val5 = Object.FindAnyObjectByType<Canvas>();
							if ((Object)(object)val5 != (Object)null)
							{
								val2 = ((Component)val5).transform;
							}
						}
						int num2 = 0;
						Transform[] array;
						if ((Object)(object)val2 != (Object)null)
						{
							array = ((Component)val2).GetComponentsInChildren<Transform>(true);
							foreach (Transform val6 in array)
							{
								if ((Object)(object)val6 == (Object)null)
								{
									continue;
								}
								switch (((Object)val6).name)
								{
								case "FFA_Medium_Button":
								case "FFA_Large_Button":
								case "FreeForAllLabel_Auto":
									if (((Component)val6).gameObject.activeSelf)
									{
										((Component)val6).gameObject.SetActive(false);
										num2++;
									}
									break;
								}
							}
						}
						array = Resources.FindObjectsOfTypeAll<Transform>();
						foreach (Transform val7 in array)
						{
							if ((Object)(object)val7 == (Object)null)
							{
								continue;
							}
							switch (((Object)val7).name)
							{
							case "FFA_Medium_Button":
							case "FFA_Large_Button":
							case "FreeForAllLabel_Auto":
								if (((Component)val7).gameObject.activeSelf)
								{
									((Component)val7).gameObject.SetActive(false);
									num2++;
								}
								break;
							}
						}
						if (num2 > 0)
						{
							ManualLogSource log4 = Plugin.Log;
							if (log4 != null)
							{
								log4.LogDebug((object)$"FFA: Client view — hid {num2} FFA selection UI objects.");
							}
						}
						return;
					}
					catch
					{
						return;
					}
				}
				ManualLogSource log5 = Plugin.Log;
				if (log5 != null)
				{
					log5.LogInfo((object)"OpenLobby: detected Host — will inject FFA UI if missing");
				}
				Button[] componentsInChildren;
				try
				{
					FieldInfo fieldInfo = AccessTools.Field(type, "Mapchoseholder");
					Transform val8 = null;
					object obj5 = fieldInfo?.GetValue(__instance);
					GameObject val9 = (GameObject)((obj5 is GameObject) ? obj5 : null);
					if (val9 != null)
					{
						val8 = val9.transform;
					}
					else
					{
						Transform val10 = (Transform)((obj5 is Transform) ? obj5 : null);
						if (val10 != null)
						{
							val8 = val10;
						}
					}
					if ((Object)(object)val8 != (Object)null)
					{
						if ((Object)(object)val8.Find("FFA_Medium_Button") == (Object)null && (Object)(object)val8.Find("FFA_Large_Button") == (Object)null)
						{
							ManualLogSource log6 = Plugin.Log;
							if (log6 != null)
							{
								log6.LogDebug((object)"OpenLobby: FFA buttons not found under Mapchoseholder — proceeding to clone");
							}
							Button val11 = null;
							Button val12 = null;
							Transform val13 = val8;
							try
							{
								if ((Object)(object)val13 == (Object)null)
								{
									Canvas val14 = Object.FindAnyObjectByType<Canvas>();
									val13 = (((Object)(object)val14 != (Object)null) ? ((Component)val14).transform : null);
								}
								Transform val15 = null;
								if ((Object)(object)val13 != (Object)null)
								{
									Transform[] array = ((Component)val13).GetComponentsInChildren<Transform>(true);
									foreach (Transform val16 in array)
									{
										if ((Object)(object)val16 != (Object)null && ((Object)val16).name == "Lobby")
										{
											val15 = val16;
											break;
										}
									}
								}
								if ((Object)(object)val15 == (Object)null)
								{
									val15 = val13;
								}
								Transform val17 = null;
								if ((Object)(object)val15 != (Object)null)
								{
									Transform[] array = ((Component)val15).GetComponentsInChildren<Transform>(true);
									foreach (Transform val18 in array)
									{
										if ((Object)(object)val18 != (Object)null && ((Object)val18).name == "mapsizecheck")
										{
											val17 = val18;
											break;
										}
									}
								}
								if ((Object)(object)val17 != (Object)null)
								{
									Transform val19 = null;
									Transform val20 = null;
									Transform[] array = ((Component)val17).GetComponentsInChildren<Transform>(true);
									foreach (Transform val21 in array)
									{
										if ((Object)(object)val21 != (Object)null && ((Object)val21).name == "SmallMap")
										{
											val19 = val21;
										}
										else if ((Object)(object)val21 != (Object)null && ((Object)val21).name == "LargeMap")
										{
											val20 = val21;
										}
									}
									ManualLogSource log7 = Plugin.Log;
									if (log7 != null)
									{
										log7.LogDebug((object)$"OpenLobby: sources found — SmallMap={(Object)(object)val19 != (Object)null} LargeMap={(Object)(object)val20 != (Object)null}");
									}
									Transform val22 = null;
									try
									{
										GameObject val23 = GameObject.Find("ConfirmStart");
										if ((Object)(object)val23 != (Object)null)
										{
											val22 = val23.transform.parent;
										}
									}
									catch
									{
									}
									if ((Object)(object)val22 == (Object)null)
									{
										val22 = (((Object)(object)val17 != (Object)null) ? val17.parent : val8);
									}
									if ((Object)(object)val19 != (Object)null)
									{
										GameObject obj7 = Object.Instantiate<GameObject>(((Component)val19).gameObject);
										((Object)obj7).name = "FFA_Medium_Button";
										obj7.transform.SetParent(val22, false);
										RectTransform component = obj7.GetComponent<RectTransform>();
										RectTransform component2 = ((Component)val19).GetComponent<RectTransform>();
										if ((Object)(object)component != (Object)null && (Object)(object)component2 != (Object)null)
										{
											component.anchorMin = component2.anchorMin;
											component.anchorMax = component2.anchorMax;
											component.pivot = component2.pivot;
											component.sizeDelta = component2.sizeDelta;
											((Transform)component).localScale = Vector3.one;
											((Transform)component).localRotation = Quaternion.identity;
											component.anchoredPosition = component2.anchoredPosition + new Vector2(300f, 0f);
										}
										CanvasGroup component3 = obj7.GetComponent<CanvasGroup>();
										if ((Object)(object)component3 != (Object)null)
										{
											component3.alpha = 1f;
											component3.interactable = true;
											component3.blocksRaycasts = true;
										}
										ContentSizeFitter componentInChildren = obj7.GetComponentInChildren<ContentSizeFitter>(true);
										if ((Object)(object)componentInChildren != (Object)null)
										{
											((Behaviour)componentInChildren).enabled = false;
										}
										SetButtonLabel(obj7, "Medium");
										val11 = obj7.GetComponent<Button>();
										if ((Object)(object)val11 != (Object)null)
										{
											((UnityEventBase)val11.onClick).RemoveAllListeners();
											((UnityEvent)val11.onClick).AddListener((UnityAction)delegate
											{
												MainMenuPatch.ApplyFFASelection(__instance, 1);
											});
											Image component4 = ((Component)val11).GetComponent<Image>();
											if ((Object)(object)component4 != (Object)null)
											{
												((Graphic)component4).raycastTarget = true;
											}
											((Component)val11).transform.SetSiblingIndex(0);
										}
										ManualLogSource log8 = Plugin.Log;
										if (log8 != null)
										{
											log8.LogInfo((object)$"OpenLobby: Created FFA_Medium_Button (btn={(Object)(object)val11 != (Object)null})");
										}
									}
									if ((Object)(object)val20 != (Object)null)
									{
										GameObject obj8 = Object.Instantiate<GameObject>(((Component)val20).gameObject);
										((Object)obj8).name = "FFA_Large_Button";
										obj8.transform.SetParent(val22, false);
										RectTransform component5 = obj8.GetComponent<RectTransform>();
										RectTransform component6 = ((Component)val20).GetComponent<RectTransform>();
										if ((Object)(object)component5 != (Object)null && (Object)(object)component6 != (Object)null)
										{
											component5.anchorMin = component6.anchorMin;
											component5.anchorMax = component6.anchorMax;
											component5.pivot = component6.pivot;
											component5.sizeDelta = component6.sizeDelta;
											((Transform)component5).localScale = Vector3.one;
											((Transform)component5).localRotation = Quaternion.identity;
											component5.anchoredPosition = component6.anchoredPosition + new Vector2(300f, 0f);
										}
										CanvasGroup component7 = obj8.GetComponent<CanvasGroup>();
										if ((Object)(object)component7 != (Object)null)
										{
											component7.alpha = 1f;
											component7.interactable = true;
											component7.blocksRaycasts = true;
										}
										ContentSizeFitter componentInChildren2 = obj8.GetComponentInChildren<ContentSizeFitter>(true);
										if ((Object)(object)componentInChildren2 != (Object)null)
										{
											((Behaviour)componentInChildren2).enabled = false;
										}
										SetButtonLabel(obj8, "Large");
										val12 = obj8.GetComponent<Button>();
										if ((Object)(object)val12 != (Object)null)
										{
											((UnityEventBase)val12.onClick).RemoveAllListeners();
											((UnityEvent)val12.onClick).AddListener((UnityAction)delegate
											{
												MainMenuPatch.ApplyFFASelection(__instance, 0);
											});
											Image component8 = ((Component)val12).GetComponent<Image>();
											if ((Object)(object)component8 != (Object)null)
											{
												((Graphic)component8).raycastTarget = true;
											}
										}
										ManualLogSource log9 = Plugin.Log;
										if (log9 != null)
										{
											log9.LogInfo((object)$"OpenLobby: Created FFA_Large_Button (btn={(Object)(object)val12 != (Object)null})");
										}
									}
								}
							}
							catch
							{
							}
							if ((Object)(object)val11 != (Object)null && (Object)(object)val12 != (Object)null)
							{
								Transform parent = ((Component)val11).transform.parent;
								Transform val24 = null;
								string[] array2 = new string[4] { "Canvas (1)/Main/JoinLobby", "Canvas/Main/JoinLobby", "Canvas (1)/Main/JoinLobbyButton", "Canvas/Main/JoinLobbyButton" };
								for (int i = 0; i < array2.Length; i++)
								{
									val24 = MainMenuPatch.FindInactiveTransform(array2[i]);
									if ((Object)(object)val24 != (Object)null && (Object)(object)val24.parent == (Object)(object)parent)
									{
										break;
									}
									val24 = null;
								}
								int num3 = 0;
								if ((Object)(object)val24 != (Object)null && (Object)(object)val24.parent == (Object)(object)parent)
								{
									num3 = val24.GetSiblingIndex();
								}
								((Component)val11).transform.SetSiblingIndex(Mathf.Min(num3 + 1, parent.childCount - 1));
								((Component)val12).transform.SetSiblingIndex(Mathf.Min(num3 + 2, parent.childCount - 1));
								LayoutRebuilder.ForceRebuildLayoutImmediate((RectTransform)(object)((parent is RectTransform) ? parent : null));
								HorizontalLayoutGroup component9 = ((Component)parent).GetComponent<HorizontalLayoutGroup>();
								VerticalLayoutGroup component10 = ((Component)parent).GetComponent<VerticalLayoutGroup>();
								GridLayoutGroup component11 = ((Component)parent).GetComponent<GridLayoutGroup>();
								if ((Object)(object)component9 != (Object)null || (Object)(object)component10 != (Object)null || (Object)(object)component11 != (Object)null)
								{
									LayoutRebuilder.ForceRebuildLayoutImmediate((RectTransform)(object)((parent is RectTransform) ? parent : null));
								}
								else
								{
									RectTransform component12 = ((Component)val11).GetComponent<RectTransform>();
									RectTransform component13 = ((Component)val12).GetComponent<RectTransform>();
									RectTransform val25 = null;
									componentsInChildren = ((Component)parent).GetComponentsInChildren<Button>(true);
									foreach (Button val26 in componentsInChildren)
									{
										if (!((Object)(object)val26 == (Object)(object)val11) && !((Object)(object)val26 == (Object)(object)val12))
										{
											val25 = ((Component)val26).GetComponent<RectTransform>();
											if ((Object)(object)val25 != (Object)null && (Object)(object)((Component)val26).transform.parent == (Object)(object)parent)
											{
												break;
											}
											val25 = null;
										}
									}
									Vector2 val27 = (((Object)(object)val25 != (Object)null) ? val25.anchoredPosition : Vector2.zero);
									if ((Object)(object)component12 != (Object)null)
									{
										component12.anchoredPosition = val27 + new Vector2(0f, -60f);
									}
									if ((Object)(object)component13 != (Object)null)
									{
										component13.anchoredPosition = val27 + new Vector2(0f, -120f);
									}
								}
								RectTransform component14 = ((Component)val11).GetComponent<RectTransform>();
								RectTransform component15 = ((Component)val12).GetComponent<RectTransform>();
								LayoutElement val28 = ((Component)val11).GetComponent<LayoutElement>() ?? ((Component)val11).gameObject.AddComponent<LayoutElement>();
								LayoutElement obj10 = ((Component)val12).GetComponent<LayoutElement>() ?? ((Component)val12).gameObject.AddComponent<LayoutElement>();
								val28.ignoreLayout = true;
								obj10.ignoreLayout = true;
								if ((Object)(object)component14 != (Object)null)
								{
									component14.anchoredPosition = new Vector2(-760f, 260f);
								}
								if ((Object)(object)component15 != (Object)null)
								{
									component15.anchoredPosition = new Vector2(-560f, 260f);
								}
								ManualLogSource log10 = Plugin.Log;
								if (log10 != null)
								{
									log10.LogInfo((object)"FFA: positioned buttons. Medium=(-760,260) Large=(-560,260)");
								}
								RectTransform component16 = ((Component)val11).GetComponent<RectTransform>();
								RectTransform component17 = ((Component)val12).GetComponent<RectTransform>();
								ManualLogSource log11 = Plugin.Log;
								if (log11 != null)
								{
									object obj11;
									Vector2 anchoredPosition;
									if (!((Object)(object)component16 != (Object)null))
									{
										obj11 = "-";
									}
									else
									{
										anchoredPosition = component16.anchoredPosition;
										obj11 = ((object)(Vector2)(ref anchoredPosition)).ToString();
									}
									object obj12;
									if (!((Object)(object)component17 != (Object)null))
									{
										obj12 = "-";
									}
									else
									{
										anchoredPosition = component17.anchoredPosition;
										obj12 = ((object)(Vector2)(ref anchoredPosition)).ToString();
									}
									log11.LogInfo((object)("Injected FFA Medium/Large buttons into lobby UI. medPos=" + (string?)obj11 + ", largePos=" + (string?)obj12));
								}
								try
								{
									Transform val29 = null;
									Transform[] array3 = Resources.FindObjectsOfTypeAll<Transform>();
									foreach (Transform val30 in array3)
									{
										if ((Object)(object)val30 != (Object)null && ((Object)val30).name == "FreeForAllLabel_Auto")
										{
											val29 = val30;
											break;
										}
									}
									if ((Object)(object)val29 == (Object)null)
									{
										Transform val31 = null;
										Transform val32 = null;
										Transform val33 = null;
										Transform val34 = parent;
										if ((Object)(object)val34 == (Object)null)
										{
											Canvas val35 = Object.FindAnyObjectByType<Canvas>();
											val34 = (((Object)(object)val35 != (Object)null) ? ((Component)val35).transform : null);
										}
										if ((Object)(object)val34 != (Object)null)
										{
											Transform[] array = ((Component)val34).GetComponentsInChildren<Transform>(true);
											foreach (Transform val36 in array)
											{
												if ((Object)(object)val36 != (Object)null && ((Object)val36).name == "Lobby")
												{
													val31 = val36;
													break;
												}
											}
										}
										if ((Object)(object)val31 == (Object)null)
										{
											val31 = val34;
										}
										if ((Object)(object)val31 != (Object)null)
										{
											Transform[] array = ((Component)val31).GetComponentsInChildren<Transform>(true);
											foreach (Transform val37 in array)
											{
												if ((Object)(object)val37 != (Object)null && ((Object)val37).name == "mapsizecheck")
												{
													val32 = val37;
													break;
												}
											}
										}
										if ((Object)(object)val32 != (Object)null)
										{
											Transform[] array = ((Component)val32).GetComponentsInChildren<Transform>(true);
											foreach (Transform val38 in array)
											{
												if ((Object)(object)val38 != (Object)null && ((Object)val38).name == "nothin (2)")
												{
													val33 = val38;
													break;
												}
											}
										}
										if ((Object)(object)val33 != (Object)null)
										{
											GameObject val39 = Object.Instantiate<GameObject>(((Component)val33).gameObject);
											((Object)val39).name = "FreeForAllLabel_Auto";
											val39.transform.SetParent(((Object)(object)val32 != (Object)null) ? val32 : (((Object)(object)val34 != (Object)null) ? val34 : parent), false);
											bool flag = false;
											Text component18 = val39.GetComponent<Text>();
											if ((Object)(object)component18 != (Object)null)
											{
												component18.text = "Free for all";
												flag = true;
											}
											if (!flag)
											{
												Type type2 = AccessTools.TypeByName("TMPro.TextMeshProUGUI");
												if (type2 != null)
												{
													Component component19 = val39.GetComponent(type2);
													if ((Object)(object)component19 != (Object)null)
													{
														AccessTools.Property(type2, "text")?.SetValue(component19, "Free for all", null);
														flag = true;
													}
												}
											}
											if (!flag)
											{
												Type type3 = AccessTools.TypeByName("TMPro.TextMeshPro");
												if (type3 != null)
												{
													Component component20 = val39.GetComponent(type3);
													if ((Object)(object)component20 != (Object)null)
													{
														AccessTools.Property(type3, "text")?.SetValue(component20, "Free for all", null);
														flag = true;
													}
												}
											}
											RectTransform component21 = val39.GetComponent<RectTransform>();
											Vector3 val40 = default(Vector3);
											((Vector3)(ref val40))..ctor(-420f, 160f, 0f);
											if ((Object)(object)component21 != (Object)null)
											{
												component21.anchoredPosition3D = val40;
											}
											else
											{
												val39.transform.position = val40;
											}
											ManualLogSource log12 = Plugin.Log;
											if (log12 != null)
											{
												log12.LogInfo((object)$"FFA: Created FreeForAllLabel_Auto under mapsizecheck. pos=(-420,160,0) textSet={flag}");
											}
										}
										else
										{
											ManualLogSource log13 = Plugin.Log;
											if (log13 != null)
											{
												log13.LogWarning((object)"FFA: Could not find Lobby/mapsizecheck/nothin (2) to duplicate for label.");
											}
										}
									}
								}
								catch (Exception arg)
								{
									ManualLogSource log14 = Plugin.Log;
									if (log14 != null)
									{
										log14.LogWarning((object)$"FFA: FreeForAll label creation failed: {arg}");
									}
								}
							}
							else
							{
								ManualLogSource log15 = Plugin.Log;
								if (log15 != null)
								{
									log15.LogWarning((object)"OpenLobby_Postfix: failed to create FFA buttons from path and template.");
								}
							}
						}
						else
						{
							ManualLogSource log16 = Plugin.Log;
							if (log16 != null)
							{
								log16.LogInfo((object)"OpenLobby: FFA buttons already exist — skipping injection");
							}
						}
					}
					else
					{
						ManualLogSource log17 = Plugin.Log;
						if (log17 != null)
						{
							log17.LogWarning((object)"OpenLobby: Mapchoseholder not found — cannot inject FFA buttons");
						}
					}
				}
				catch (Exception arg2)
				{
					ManualLogSource log18 = Plugin.Log;
					if (log18 != null)
					{
						log18.LogWarning((object)$"OpenLobby: injection failed: {arg2}");
					}
				}
				if (!FFAMode.IsActive() && !MainMenuPatch.IsFFASelected())
				{
					return;
				}
				object? obj13 = AccessTools.Field(type, "lobbyScreen")?.GetValue(__instance);
				GameObject val41 = (GameObject)((obj13 is GameObject) ? obj13 : null);
				Transform val42 = (((Object)(object)val41 != (Object)null) ? val41.transform : null);
				if ((Object)(object)val42 == (Object)null)
				{
					Canvas val43 = Object.FindAnyObjectByType<Canvas>();
					val42 = (((Object)(object)val43 != (Object)null) ? ((Component)val43).transform : null);
				}
				if (!((Object)(object)val42 != (Object)null))
				{
					return;
				}
				int num4 = 0;
				try
				{
					object? obj14 = AccessTools.Field(type, "ctfoverlay")?.GetValue(__instance);
					CanvasGroup val44 = (CanvasGroup)((obj14 is CanvasGroup) ? obj14 : null);
					if ((Object)(object)val44 != (Object)null)
					{
						val44.alpha = 0f;
						val44.interactable = false;
						val44.blocksRaycasts = false;
						((Component)val44).gameObject.SetActive(false);
					}
					try
					{
						Transform[] array = ((Component)val42).GetComponentsInChildren<Transform>(true);
						foreach (Transform val45 in array)
						{
							if ((Object)(object)val45 != (Object)null && string.Equals(((Object)val45).name, "EditTeamFlag", StringComparison.OrdinalIgnoreCase))
							{
								((Component)val45).gameObject.SetActive(false);
								break;
							}
						}
					}
					catch
					{
					}
				}
				catch
				{
				}
				componentsInChildren = ((Component)val42).GetComponentsInChildren<Button>(true);
				foreach (Button val46 in componentsInChildren)
				{
					ButtonClickedEvent onClick = val46.onClick;
					if (onClick == null)
					{
						continue;
					}
					int persistentEventCount = ((UnityEventBase)onClick).GetPersistentEventCount();
					bool flag2 = false;
					for (int k = 0; k < persistentEventCount; k++)
					{
						switch (((UnityEventBase)onClick).GetPersistentMethodName(k))
						{
						case "JoinTeam1":
						case "JoinTeam2":
						case "JoinLowestPlayerCountTeam":
							break;
						default:
							continue;
						}
						flag2 = true;
						break;
					}
					if (!flag2)
					{
						if ((((Object)((Component)val46).gameObject).name ?? string.Empty).Contains("JoinTeam", StringComparison.OrdinalIgnoreCase))
						{
							flag2 = true;
						}
						else
						{
							Text componentInChildren3 = ((Component)val46).GetComponentInChildren<Text>(true);
							if ((Object)(object)componentInChildren3 != (Object)null && componentInChildren3.text != null && componentInChildren3.text.IndexOf("Join Team", StringComparison.OrdinalIgnoreCase) >= 0)
							{
								flag2 = true;
							}
							else
							{
								Type type4 = AccessTools.TypeByName("TMPro.TextMeshProUGUI");
								if (type4 != null)
								{
									Component componentInChildren4 = ((Component)val46).GetComponentInChildren(type4, true);
									if ((Object)(object)componentInChildren4 != (Object)null)
									{
										string text2 = AccessTools.Property(type4, "text")?.GetValue(componentInChildren4, null) as string;
										if (!string.IsNullOrEmpty(text2) && text2.IndexOf("Join Team", StringComparison.OrdinalIgnoreCase) >= 0)
										{
											flag2 = true;
										}
									}
								}
							}
						}
					}
					if (!flag2)
					{
						bool flag3 = false;
						for (int l = 0; l < persistentEventCount; l++)
						{
							if (((UnityEventBase)onClick).GetPersistentMethodName(l) == "EditTeamFlag")
							{
								flag3 = true;
								break;
							}
						}
						if (!flag3)
						{
							if ((((Object)((Component)val46).gameObject).name ?? string.Empty).Equals("EditTeamFlag", StringComparison.OrdinalIgnoreCase))
							{
								flag3 = true;
							}
							else
							{
								Text componentInChildren5 = ((Component)val46).GetComponentInChildren<Text>(true);
								if ((Object)(object)componentInChildren5 != (Object)null && componentInChildren5.text != null && componentInChildren5.text.IndexOf("Edit Team Flag", StringComparison.OrdinalIgnoreCase) >= 0)
								{
									flag3 = true;
								}
								else
								{
									Type type5 = AccessTools.TypeByName("TMPro.TextMeshProUGUI");
									if (type5 != null)
									{
										Component componentInChildren6 = ((Component)val46).GetComponentInChildren(type5, true);
										if ((Object)(object)componentInChildren6 != (Object)null)
										{
											string text3 = AccessTools.Property(type5, "text")?.GetValue(componentInChildren6, null) as string;
											if (!string.IsNullOrEmpty(text3) && text3.IndexOf("Edit Team Flag", StringComparison.OrdinalIgnoreCase) >= 0)
											{
												flag3 = true;
											}
										}
									}
								}
							}
						}
						if (flag3)
						{
							((Component)val46).gameObject.SetActive(false);
							num4++;
							continue;
						}
					}
					if (flag2)
					{
						((Component)val46).gameObject.SetActive(false);
						num4++;
					}
				}
				ManualLogSource log19 = Plugin.Log;
				if (log19 != null)
				{
					log19.LogInfo((object)$"FFA: hid {num4} team selection buttons.");
				}
			}
			catch (Exception arg3)
			{
				ManualLogSource log20 = Plugin.Log;
				if (log20 != null)
				{
					log20.LogWarning((object)$"OpenLobby_Postfix hide team selection failed: {arg3}");
				}
			}
			static void SetButtonLabel(GameObject go, string text)
			{
				Text[] componentsInChildren2 = go.GetComponentsInChildren<Text>(true);
				for (int m = 0; m < componentsInChildren2.Length; m++)
				{
					componentsInChildren2[m].text = text;
				}
			}
		}
	}
	[HarmonyPatch]
	public static class MainMenuStartGamePatch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("MainMenuManager");
			if (type == null)
			{
				return null;
			}
			return AccessTools.Method(type, "StartGame", (Type[])null, (Type[])null);
		}

		[HarmonyPostfix]
		private static void Postfix(object __instance)
		{
			try
			{
				if (!MainMenuPatch.ShouldHideTeamUI(__instance))
				{
					return;
				}
				object? obj = AccessTools.Field(__instance.GetType(), "InGameLobby")?.GetValue(__instance);
				GameObject val = (GameObject)((obj is GameObject) ? obj : null);
				if ((Object)(object)val == (Object)null)
				{
					return;
				}
				int num = 0;
				Button[] componentsInChildren = val.GetComponentsInChildren<Button>(true);
				foreach (Button val2 in componentsInChildren)
				{
					ButtonClickedEvent onClick = val2.onClick;
					if (onClick == null)
					{
						continue;
					}
					int persistentEventCount = ((UnityEventBase)onClick).GetPersistentEventCount();
					bool flag = false;
					for (int j = 0; j < persistentEventCount; j++)
					{
						switch (((UnityEventBase)onClick).GetPersistentMethodName(j))
						{
						case "JoinTeam1":
						case "JoinTeam2":
						case "JoinLowestPlayerCountTeam":
							break;
						default:
							continue;
						}
						flag = true;
						break;
					}
					if (!flag)
					{
						if ((((Object)((Component)val2).gameObject).name ?? string.Empty).Contains("JoinTeam", StringComparison.OrdinalIgnoreCase))
						{
							flag = true;
						}
						else
						{
							Text componentInChildren = ((Component)val2).GetComponentInChildren<Text>(true);
							if ((Object)(object)componentInChildren != (Object)null && componentInChildren.text != null && componentInChildren.text.IndexOf("Join Team", StringComparison.OrdinalIgnoreCase) >= 0)
							{
								flag = true;
							}
							else
							{
								Type type = AccessTools.TypeByName("TMPro.TextMeshProUGUI");
								if (type != null)
								{
									Component componentInChildren2 = ((Component)val2).GetComponentInChildren(type, true);
									if ((Object)(object)componentInChildren2 != (Object)null)
									{
										string text = AccessTools.Property(type, "text")?.GetValue(componentInChildren2, null) as string;
										if (!string.IsNullOrEmpty(text) && text.IndexOf("Join Team", StringComparison.OrdinalIgnoreCase) >= 0)
										{
											flag = true;
										}
									}
								}
							}
						}
					}
					if (flag)
					{
						((Component)val2).gameObject.SetActive(false);
						num++;
					}
				}
				try
				{
					int num2 = 0;
					Transform[] componentsInChildren2 = val.GetComponentsInChildren<Transform>(true);
					foreach (Transform val3 in componentsInChildren2)
					{
						if ((Object)(object)val3 != (Object)null && string.Equals(((Object)val3).name, "EditTeamFlag", StringComparison.OrdinalIgnoreCase) && ((Component)val3).gameObject.activeSelf)
						{
							((Component)val3).gameObject.SetActive(false);
							num2++;
						}
					}
					componentsInChildren2 = Resources.FindObjectsOfTypeAll<Transform>();
					foreach (Transform val4 in componentsInChildren2)
					{
						if ((Object)(object)val4 != (Object)null && string.Equals(((Object)val4).name, "EditTeamFlag", StringComparison.OrdinalIgnoreCase) && ((Component)val4).gameObject.activeSelf)
						{
							((Component)val4).gameObject.SetActive(false);
							num2++;
						}
					}
					if (num2 > 0)
					{
						num += num2;
					}
				}
				catch
				{
				}
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogInfo((object)$"FFA: StartGame Postfix hid {num} team join controls in InGameLobby.");
				}
			}
			catch (Exception arg)
			{
				ManualLogSource log2 = Plugin.Log;
				if (log2 != null)
				{
					log2.LogWarning((object)$"StartGame Postfix failed: {arg}");
				}
			}
		}
	}
	[HarmonyPatch]
	public static class MainMenuStartGameActualPatch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("MainMenuManager");
			if (type == null)
			{
				return null;
			}
			return AccessTools.Method(type, "StartGameActual", (Type[])null, (Type[])null);
		}

		[HarmonyPostfix]
		private static void Postfix(object __instance)
		{
			//IL_08fe: Unknown result type (might be due to invalid IL or missing references)
			//IL_0905: Expected O, but got Unknown
			//IL_0760: Unknown result type (might be due to invalid IL or missing references)
			//IL_0765: Unknown result type (might be due to invalid IL or missing references)
			//IL_0778: Unknown result type (might be due to invalid IL or missing references)
			//IL_0783: Unknown result type (might be due to invalid IL or missing references)
			//IL_094d: Unknown result type (might be due to invalid IL or missing references)
			//IL_095c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0797: Unknown result type (might be due to invalid IL or missing references)
			//IL_07a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_07b9: Unknown result type (might be due to invalid IL or missing references)
			//IL_07c5: Unknown result type (might be due to invalid IL or missing references)
			//IL_07d1: Unknown result type (might be due to invalid IL or missing references)
			//IL_07dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_0985: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a24: Unknown result type (might be due to invalid IL or missing references)
			//IL_09af: Unknown result type (might be due to invalid IL or missing references)
			//IL_09bb: Unknown result type (might be due to invalid IL or missing references)
			//IL_09d1: Unknown result type (might be due to invalid IL or missing references)
			//IL_09dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_09e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_09f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a4b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a57: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a6d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a79: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a85: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a91: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				if (!MainMenuPatch.ShouldHideTeamUI(__instance))
				{
					return;
				}
				Type type = __instance.GetType();
				object? obj = AccessTools.Field(type, "InGameLobby")?.GetValue(__instance);
				GameObject val = (GameObject)((obj is GameObject) ? obj : null);
				if ((Object)(object)val == (Object)null)
				{
					return;
				}
				int num = 0;
				Button[] componentsInChildren = val.GetComponentsInChildren<Button>(true);
				foreach (Button val2 in componentsInChildren)
				{
					ButtonClickedEvent onClick = val2.onClick;
					if (onClick == null)
					{
						continue;
					}
					int persistentEventCount = ((UnityEventBase)onClick).GetPersistentEventCount();
					bool flag = false;
					for (int j = 0; j < persistentEventCount; j++)
					{
						switch (((UnityEventBase)onClick).GetPersistentMethodName(j))
						{
						case "JoinTeam1":
						case "JoinTeam2":
						case "JoinLowestPlayerCountTeam":
							break;
						default:
							continue;
						}
						flag = true;
						break;
					}
					if (!flag)
					{
						if ((((Object)((Component)val2).gameObject).name ?? string.Empty).Contains("JoinTeam", StringComparison.OrdinalIgnoreCase))
						{
							flag = true;
						}
						else
						{
							Text componentInChildren = ((Component)val2).GetComponentInChildren<Text>(true);
							if ((Object)(object)componentInChildren != (Object)null && componentInChildren.text != null && componentInChildren.text.IndexOf("Join Team", StringComparison.OrdinalIgnoreCase) >= 0)
							{
								flag = true;
							}
							else
							{
								Type type2 = AccessTools.TypeByName("TMPro.TextMeshProUGUI");
								if (type2 != null)
								{
									Component componentInChildren2 = ((Component)val2).GetComponentInChildren(type2, true);
									if ((Object)(object)componentInChildren2 != (Object)null)
									{
										string text = AccessTools.Property(type2, "text")?.GetValue(componentInChildren2, null) as string;
										if (!string.IsNullOrEmpty(text) && text.IndexOf("Join Team", StringComparison.OrdinalIgnoreCase) >= 0)
										{
											flag = true;
										}
									}
								}
							}
						}
					}
					if (flag)
					{
						((Component)val2).gameObject.SetActive(false);
						num++;
					}
				}
				try
				{
					int num2 = 0;
					Transform[] componentsInChildren2 = val.GetComponentsInChildren<Transform>(true);
					foreach (Transform val3 in componentsInChildren2)
					{
						if ((Object)(object)val3 != (Object)null && string.Equals(((Object)val3).name, "EditTeamFlag", StringComparison.OrdinalIgnoreCase) && ((Component)val3).gameObject.activeSelf)
						{
							((Component)val3).gameObject.SetActive(false);
							num2++;
						}
					}
					componentsInChildren2 = Resources.FindObjectsOfTypeAll<Transform>();
					foreach (Transform val4 in componentsInChildren2)
					{
						if ((Object)(object)val4 != (Object)null && string.Equals(((Object)val4).name, "EditTeamFlag", StringComparison.OrdinalIgnoreCase) && ((Component)val4).gameObject.activeSelf)
						{
							((Component)val4).gameObject.SetActive(false);
							num2++;
						}
					}
					if (num2 > 0)
					{
						num += num2;
					}
				}
				catch
				{
				}
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogInfo((object)$"FFA: StartGameActual Postfix hid {num} team join controls in InGameLobby.");
				}
				try
				{
					Type type3 = AccessTools.TypeByName("FlagController");
					Type type4 = AccessTools.TypeByName("CastleFlagCapturedNotifier");
					int num3 = 0;
					int num4 = 0;
					if (type3 != null)
					{
						Object[] array = Resources.FindObjectsOfTypeAll(type3);
						if (array != null)
						{
							Object[] array2 = array;
							foreach (Object val5 in array2)
							{
								Component val6 = (Component)(object)((val5 is Component) ? val5 : null);
								if (val6 == null || !((Object)(object)val6 != (Object)null) || !((Object)(object)val6.gameObject != (Object)null))
								{
									continue;
								}
								Behaviour val7 = (Behaviour)(object)((val6 is Behaviour) ? val6 : null);
								if (val7 != null && val7.enabled)
								{
									val7.enabled = false;
								}
								Collider component = val6.GetComponent<Collider>();
								if ((Object)(object)component != (Object)null && component.enabled)
								{
									component.enabled = false;
								}
								try
								{
									Type type5 = ((object)val6).GetType();
									FieldInfo fieldInfo = AccessTools.Field(type5, "flagvisual");
									FieldInfo fieldInfo2 = AccessTools.Field(type5, "FlagAni");
									FieldInfo fieldInfo3 = AccessTools.Field(type5, "particles");
									FieldInfo fieldInfo4 = AccessTools.Field(type5, "FlagAudio");
									object? obj3 = fieldInfo?.GetValue(val5);
									Renderer val8 = (Renderer)((obj3 is Renderer) ? obj3 : null);
									if (val8 != null)
									{
										val8.enabled = false;
									}
									object? obj4 = fieldInfo2?.GetValue(val5);
									Behaviour val9 = (Behaviour)((obj4 is Behaviour) ? obj4 : null);
									if (val9 != null)
									{
										val9.enabled = false;
									}
									if (fieldInfo3?.GetValue(val5) is ParticleSystem[] array3)
									{
										ParticleSystem[] array4 = array3;
										foreach (ParticleSystem val10 in array4)
										{
											if (!((Object)(object)val10 == (Object)null))
											{
												val10.Stop(true, (ParticleSystemStopBehavior)0);
												Renderer component2 = ((Component)val10).GetComponent<Renderer>();
												if (Object.op_Implicit((Object)(object)component2))
												{
													component2.enabled = false;
												}
											}
										}
									}
									object? obj5 = fieldInfo4?.GetValue(val5);
									AudioSource val11 = (AudioSource)((obj5 is AudioSource) ? obj5 : null);
									if (val11 != null)
									{
										val11.Stop();
										((Behaviour)val11).enabled = false;
									}
									Renderer[] componentsInChildren3 = val6.GetComponentsInChildren<Renderer>(true);
									foreach (Renderer val12 in componentsInChildren3)
									{
										if ((Object)(object)val12 == (Object)null)
										{
											continue;
										}
										string text2 = ((((Object)val12).name != null) ? ((Object)val12).name.ToLowerInvariant() : string.Empty);
										bool flag2 = text2.Contains("flag") || text2.Contains("pole") || text2.Contains("banner");
										if (!flag2)
										{
											try
											{
												Material[] sharedMaterials = val12.sharedMaterials;
												for (int l = 0; l < sharedMaterials.Length; l++)
												{
													if (flag2)
													{
														break;
													}
													Material val13 = sharedMaterials[l];
													if (!((Object)(object)val13 == (Object)null))
													{
														string text3 = ((((Object)val13).name != null) ? ((Object)val13).name.ToLowerInvariant() : string.Empty);
														if (text3.Contains("flag") || text3.Contains("pole") || text3.Contains("banner"))
														{
															flag2 = true;
														}
													}
												}
											}
											catch
											{
											}
										}
										if (flag2)
										{
											val12.enabled = false;
										}
									}
								}
								catch
								{
								}
								num3++;
							}
						}
					}
					if (type4 != null)
					{
						Object[] array5 = Resources.FindObjectsOfTypeAll(type4);
						if (array5 != null)
						{
							Object[] array2 = array5;
							foreach (Object obj8 in array2)
							{
								Component val14 = (Component)(object)((obj8 is Component) ? obj8 : null);
								if (val14 != null && (Object)(object)val14 != (Object)null && (Object)(object)val14.gameObject != (Object)null)
								{
									Behaviour val15 = (Behaviour)(object)((val14 is Behaviour) ? val14 : null);
									if (val15 != null && val15.enabled)
									{
										val15.enabled = false;
									}
									num4++;
								}
							}
						}
					}
					ManualLogSource log2 = Plugin.Log;
					if (log2 != null)
					{
						log2.LogInfo((object)$"FFA: Deactivated {num3} FlagController and {num4} CastleFlagCapturedNotifier objects.");
					}
				}
				catch (Exception arg)
				{
					ManualLogSource log3 = Plugin.Log;
					if (log3 != null)
					{
						log3.LogWarning((object)$"FFA: Flag cleanup after StartGameActual failed: {arg}");
					}
				}
				object? obj9 = AccessTools.Field(type, "ctfoverlay")?.GetValue(__instance);
				CanvasGroup val16 = (CanvasGroup)((obj9 is CanvasGroup) ? obj9 : null);
				if ((Object)(object)val16 == (Object)null)
				{
					ManualLogSource log4 = Plugin.Log;
					if (log4 != null)
					{
						log4.LogWarning((object)"FFA: ctfoverlay CanvasGroup not found; cannot apply FFA overlay.");
					}
					return;
				}
				GameObject gameObject = ((Component)val16).gameObject;
				if ((Object)(object)gameObject == (Object)null)
				{
					ManualLogSource log5 = Plugin.Log;
					if (log5 != null)
					{
						log5.LogWarning((object)"FFA: ctfoverlay GameObject missing; cannot apply FFA overlay.");
					}
					return;
				}
				if (!gameObject.activeSelf)
				{
					gameObject.SetActive(true);
				}
				val16.alpha = 0f;
				val16.interactable = false;
				val16.blocksRaycasts = false;
				RawImage componentInChildren3 = gameObject.GetComponentInChildren<RawImage>(true);
				Image val17 = gameObject.GetComponentInChildren<Image>(true);
				if ((Object)(object)componentInChildren3 == (Object)null && (Object)(object)val17 == (Object)null)
				{
					GameObject val18 = new GameObject("FFAOverlayImage", new Type[2]
					{
						typeof(RectTransform),
						typeof(Image)
					});
					val18.transform.SetParent(gameObject.transform, false);
					val18.transform.SetAsLastSibling();
					RectTransform component3 = val18.GetComponent<RectTransform>();
					if ((Object)(object)component3 != (Object)null)
					{
						component3.anchorMin = Vector2.zero;
						component3.anchorMax = Vector2.one;
						component3.pivot = new Vector2(0.5f, 0.5f);
						component3.offsetMin = Vector2.zero;
						component3.offsetMax = Vector2.zero;
						((Transform)component3).localScale = Vector3.one;
					}
					val17 = val18.GetComponent<Image>();
					if ((Object)(object)val17 != (Object)null)
					{
						((Graphic)val17).raycastTarget = false;
					}
					ManualLogSource log6 = Plugin.Log;
					if (log6 != null)
					{
						log6.LogInfo((object)"FFA: Created FFAOverlayImage under ctfoverlay for overlay sprite.");
					}
				}
				Assembly executingAssembly = Assembly.GetExecutingAssembly();
				string[] array6 = null;
				try
				{
					array6 = executingAssembly.GetManifestResourceNames();
				}
				catch
				{
					array6 = Array.Empty<string>();
				}
				string text4 = null;
				string[] array7 = array6;
				foreach (string text5 in array7)
				{
					if (text5.EndsWith(".Resources.ffaoverlay.png", StringComparison.OrdinalIgnoreCase) || text5.EndsWith("ffaoverlay.png", StringComparison.OrdinalIgnoreCase))
					{
						text4 = text5;
						break;
					}
				}
				if (string.IsNullOrEmpty(text4))
				{
					ManualLogSource log7 = Plugin.Log;
					if (log7 != null)
					{
						log7.LogWarning((object)"FFA: ffaoverlay.png resource not found in assembly manifest.");
					}
					return;
				}
				byte[] array8;
				using (Stream stream = executingAssembly.GetManifestResourceStream(text4))
				{
					if (stream == null)
					{
						ManualLogSource log8 = Plugin.Log;
						if (log8 != null)
						{
							log8.LogWarning((object)"FFA: Failed to open ffaoverlay.png resource stream.");
						}
						return;
					}
					using MemoryStream memoryStream = new MemoryStream();
					stream.CopyTo(memoryStream);
					array8 = memoryStream.ToArray();
				}
				Texture2D val19 = new Texture2D(2, 2, (TextureFormat)5, false);
				if (!ImageConversion.LoadImage(val19, array8))
				{
					ManualLogSource log9 = Plugin.Log;
					if (log9 != null)
					{
						log9.LogWarning((object)"FFA: LoadImage failed for ffaoverlay.png.");
					}
					Object.Destroy((Object)(object)val19);
					return;
				}
				Sprite sprite = Sprite.Create(val19, new Rect(0f, 0f, (float)((Texture)val19).width, (float)((Texture)val19).height), new Vector2(0.5f, 0.5f), 100f);
				if ((Object)(object)componentInChildren3 != (Object)null)
				{
					componentInChildren3.texture = (Texture)(object)val19;
					((Graphic)componentInChildren3).color = Color.white;
					((Graphic)componentInChildren3).raycastTarget = false;
					RectTransform component4 = ((Component)componentInChildren3).GetComponent<RectTransform>();
					if ((Object)(object)component4 != (Object)null)
					{
						component4.anchorMin = Vector2.zero;
						component4.anchorMax = Vector2.one;
						component4.pivot = new Vector2(0.5f, 0.5f);
						component4.offsetMin = Vector2.zero;
						component4.offsetMax = Vector2.zero;
						((Transform)component4).localScale = Vector3.one;
					}
				}
				else if ((Object)(object)val17 != (Object)null)
				{
					val17.sprite = sprite;
					val17.preserveAspect = true;
					((Graphic)val17).color = Color.white;
					((Graphic)val17).raycastTarget = false;
					RectTransform component5 = ((Component)val17).GetComponent<RectTransform>();
					if ((Object)(object)component5 != (Object)null)
					{
						component5.anchorMin = Vector2.zero;
						component5.anchorMax = Vector2.one;
						component5.pivot = new Vector2(0.5f, 0.5f);
						component5.offsetMin = Vector2.zero;
						component5.offsetMax = Vector2.zero;
						((Transform)component5).localScale = Vector3.one;
					}
				}
				ManualLogSource log10 = Plugin.Log;
				if (log10 != null)
				{
					log10.LogInfo((object)"FFA: ctfoverlay sprite swapped to ffaoverlay.png and reactivated for fade.");
				}
			}
			catch (Exception arg2)
			{
				ManualLogSource log11 = Plugin.Log;
				if (log11 != null)
				{
					log11.LogWarning((object)$"FFA: StartGameActual Postfix overlay swap failed: {arg2}");
				}
			}
		}
	}
	public static class PlayerMovementPatch
	{
	}
	internal static class LogSampler
	{
		private static readonly Dictionary<string, int> _counts = new Dictionary<string, int>();

		public static bool Every(string key, int n)
		{
			if (n <= 1)
			{
				return true;
			}
			if (!_counts.TryGetValue(key, out var value))
			{
				value = 0;
			}
			value++;
			_counts[key] = value;
			return value % n == 0;
		}
	}
	[HarmonyPatch]
	public static class PlayerRespawnManager_AddToDeadList_Patch
	{
		[HarmonyPatch]
		public static class PlayerRespawnManager_IJustDied_Prefix
		{
			private static MethodBase TargetMethod()
			{
				Type type = AccessTools.TypeByName("PlayerRespawnManager");
				if (type == null)
				{
					return null;
				}
				MethodInfo[] methods = type.GetMethods(AccessTools.all);
				foreach (MethodInfo methodInfo in methods)
				{
					if (methodInfo.Name == "IJustDied" && methodInfo.GetParameters().Length == 1)
					{
						return methodInfo;
					}
				}
				return null;
			}

			private static bool Prefix(object __instance, object pm)
			{
				try
				{
					if (!FFAMode.IsActive())
					{
						return true;
					}
					if (FFALastStand.IsEnded())
					{
						try
						{
							ManualLogSource log = Plugin.Log;
							if (log != null)
							{
								log.LogDebug((object)"FFA: Match ended at IJustDied; allowing base spectate flow.");
							}
						}
						catch
						{
						}
					}
					else
					{
						try
						{
							Component val = (Component)((pm is Component) ? pm : null);
							GameObject val2 = (((Object)(object)val != (Object)null) ? val.gameObject : null);
							if ((Object)(object)val2 != (Object)null && FFALastStand.IsEliminated(val2))
							{
								ManualLogSource log2 = Plugin.Log;
								if (log2 != null)
								{
									log2.LogDebug((object)"FFA: Player eliminated at IJustDied; allowing base spectate flow.");
								}
							}
						}
						catch
						{
						}
					}
				}
				catch (Exception arg)
				{
					ManualLogSource log3 = Plugin.Log;
					if (log3 != null)
					{
						log3.LogWarning((object)$"FFA IJustDied prefix error: {arg}");
					}
				}
				return true;
			}
		}

		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("PlayerRespawnManager");
			if (!(type == null))
			{
				return AccessTools.Method(type, "AddToDeadList", (Type[])null, (Type[])null);
			}
			return null;
		}

		private static void Postfix(object __instance, GameObject DeadGuy, int pteam)
		{
			try
			{
				if (!FFAMode.IsActive() || (Object)(object)DeadGuy == (Object)null)
				{
					return;
				}
				try
				{
					string arg = ((Object)DeadGuy).name;
					try
					{
						Component component = DeadGuy.GetComponent("PlayerMovement");
						if ((Object)(object)component != (Object)null)
						{
							string text = AccessTools.Field(((object)component).GetType(), "playername")?.GetValue(component) as string;
							if (!string.IsNullOrEmpty(text))
							{
								arg = text;
							}
						}
					}
					catch
					{
					}
					int lives = FFALastStand.GetLives(DeadGuy);
					ManualLogSource log = Plugin.Log;
					if (log != null)
					{
						log.LogDebug((object)$"Death[Server]: {arg} team={pteam} livesBefore={lives}");
					}
				}
				catch
				{
				}
				FFALastStand.EnsureInitialized(DeadGuy);
				int num = FFALastStand.DecrementLife(DeadGuy);
				if (num <= 0)
				{
					FFALastStand.MarkEliminated(DeadGuy);
				}
				try
				{
					string text2 = ((Object)DeadGuy).name;
					try
					{
						Component component2 = DeadGuy.GetComponent("PlayerMovement");
						if ((Object)(object)component2 != (Object)null)
						{
							string text3 = AccessTools.Field(((object)component2).GetType(), "playername")?.GetValue(component2) as string;
							if (!string.IsNullOrEmpty(text3))
							{
								text2 = text3;
							}
						}
					}
					catch
					{
					}
					ManualLogSource log2 = Plugin.Log;
					if (log2 != null)
					{
						log2.LogDebug((object)$"Death[Server]: {text2} team={pteam} livesAfter={num} eliminated={num <= 0}");
					}
				}
				catch
				{
				}
				FFALastStand.MaybeEndMatch();
			}
			catch (Exception arg2)
			{
				ManualLogSource log3 = Plugin.Log;
				if (log3 != null)
				{
					log3.LogWarning((object)$"FFA LPS Server Postfix error: {arg2}");
				}
			}
		}
	}
	[HarmonyPatch]
	public static class PlayerRespawnManager_AddToDeadListObs_Patch
	{
		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("PlayerRespawnManager");
			if (!(type == null))
			{
				return AccessTools.Method(type, "AddToDeadListObs", (Type[])null, (Type[])null);
			}
			return null;
		}

		private static void Postfix(object __instance, GameObject DeadGuy, int pteam)
		{
			try
			{
				if (!FFAMode.IsActive())
				{
					return;
				}
				try
				{
					PropertyInfo propertyInfo = AccessTools.Property(__instance.GetType(), "IsServerInitialized");
					if (propertyInfo != null)
					{
						object value = propertyInfo.GetValue(__instance, null);
						bool flag = default(bool);
						int num;
						if (value is bool)
						{
							flag = (bool)value;
							num = 1;
						}
						else
						{
							num = 0;
						}
						if (((uint)num & (flag ? 1u : 0u)) != 0)
						{
							return;
						}
					}
					else
					{
						FieldInfo fieldInfo = AccessTools.Field(__instance.GetType(), "IsServerInitialized");
						if (fieldInfo != null)
						{
							object value2 = fieldInfo.GetValue(__instance);
							bool flag2 = default(bool);
							int num2;
							if (value2 is bool)
							{
								flag2 = (bool)value2;
								num2 = 1;
							}
							else
							{
								num2 = 0;
							}
							if (((uint)num2 & (flag2 ? 1u : 0u)) != 0)
							{
								return;
							}
						}
					}
				}
				catch
				{
				}
				if ((Object)(object)DeadGuy == (Object)null)
				{
					return;
				}
				try
				{
					string arg = ((Object)DeadGuy).name;
					try
					{
						Component component = DeadGuy.GetComponent("PlayerMovement");
						if ((Object)(object)component != (Object)null)
						{
							string text = AccessTools.Field(((object)component).GetType(), "playername")?.GetValue(component) as string;
							if (!string.IsNullOrEmpty(text))
							{
								arg = text;
							}
						}
					}
					catch
					{
					}
					int lives = FFALastStand.GetLives(DeadGuy);
					ManualLogSource log = Plugin.Log;
					if (log != null)
					{
						log.LogDebug((object)$"Death[Obs]: {arg} team={pteam} livesBefore={lives}");
					}
				}
				catch
				{
				}
				FFALastStand.EnsureInitialized(DeadGuy);
				int num3 = FFALastStand.DecrementLife(DeadGuy);
				if (num3 <= 0)
				{
					FFALastStand.MarkEliminated(DeadGuy);
				}
				try
				{
					string text2 = ((Object)DeadGuy).name;
					try
					{
						Component component2 = DeadGuy.GetComponent("PlayerMovement");
						if ((Object)(object)component2 != (Object)null)
						{
							string text3 = AccessTools.Field(((object)component2).GetType(), "playername")?.GetValue(component2) as string;
							if (!string.IsNullOrEmpty(text3))
							{
								text2 = text3;
							}
						}
					}
					catch
					{
					}
					ManualLogSource log2 = Plugin.Log;
					if (log2 != null)
					{
						log2.LogDebug((object)$"Death[Obs]: {text2} team={pteam} livesAfter={num3} eliminated={num3 <= 0}");
					}
				}
				catch
				{
				}
				FFALastStand.MaybeEndMatch();
			}
			catch (Exception arg2)
			{
				ManualLogSource log3 = Plugin.Log;
				if (log3 != null)
				{
					log3.LogWarning((object)$"FFA LPS Client Postfix error: {arg2}");
				}
			}
		}
	}
	[HarmonyPatch]
	public static class PlayerRespawnManager_RespawnRoutine_Prefix
	{
		[CompilerGenerated]
		private sealed class <SkipEnumerator>d__1 : IEnumerator<object>, IEnumerator, IDisposable
		{
			private int <>1__state;

			private object <>2__current;

			object IEnumerator<object>.Current
			{
				[DebuggerHidden]
				get
				{
					return <>2__current;
				}
			}

			object IEnumerator.Current
			{
				[DebuggerHidden]
				get
				{
					return <>2__current;
				}
			}

			[DebuggerHidden]
			public <SkipEnumerator>d__1(int <>1__state)
			{
				this.<>1__state = <>1__state;
			}

			[DebuggerHidden]
			void IDisposable.Dispose()
			{
				<>1__state = -2;
			}

			private bool MoveNext()
			{
				if (<>1__state != 0)
				{
					return false;
				}
				<>1__state = -1;
				return false;
			}

			bool IEnumerator.MoveNext()
			{
				//ILSpy generated this explicit interface implementation from .override directive in MoveNext
				return this.MoveNext();
			}

			[DebuggerHidden]
			void IEnumerator.Reset()
			{
				throw new NotSupportedException();
			}
		}

		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("PlayerRespawnManager");
			if (type == null)
			{
				return null;
			}
			MethodInfo[] methods = type.GetMethods(AccessTools.all);
			foreach (MethodInfo methodInfo in methods)
			{
				if (methodInfo.Name == "RespawnRoutine" && typeof(IEnumerator).IsAssignableFrom(methodInfo.ReturnType))
				{
					return methodInfo;
				}
			}
			return null;
		}

		[IteratorStateMachine(typeof(<SkipEnumerator>d__1))]
		private static IEnumerator SkipEnumerator()
		{
			//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
			return new <SkipEnumerator>d__1(0);
		}

		private static bool Prefix(object __instance, ref IEnumerator __result)
		{
			try
			{
				if (!FFAMode.IsActive())
				{
					return true;
				}
				object? obj = AccessTools.Field(__instance.GetType(), "pmv")?.GetValue(__instance);
				Component val = (Component)((obj is Component) ? obj : null);
				if ((Object)(object)val == (Object)null)
				{
					return true;
				}
				GameObject gameObject = val.gameObject;
				if (FFALastStand.IsEnded() || FFALastStand.IsEliminated(gameObject))
				{
					__result = SkipEnumerator();
					return false;
				}
			}
			catch (Exception arg)
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogWarning((object)$"FFA RespawnRoutine prefix error: {arg}");
				}
			}
			return true;
		}
	}
	[HarmonyPatch]
	public static class PlayerRespawnManager_ColiRespawnRoutine_Prefix
	{
		[CompilerGenerated]
		private sealed class <SkipEnumerator>d__1 : IEnumerator<object>, IEnumerator, IDisposable
		{
			private int <>1__state;

			private object <>2__current;

			object IEnumerator<object>.Current
			{
				[DebuggerHidden]
				get
				{
					return <>2__current;
				}
			}

			object IEnumerator.Current
			{
				[DebuggerHidden]
				get
				{
					return <>2__current;
				}
			}

			[DebuggerHidden]
			public <SkipEnumerator>d__1(int <>1__state)
			{
				this.<>1__state = <>1__state;
			}

			[DebuggerHidden]
			void IDisposable.Dispose()
			{
				<>1__state = -2;
			}

			private bool MoveNext()
			{
				if (<>1__state != 0)
				{
					return false;
				}
				<>1__state = -1;
				return false;
			}

			bool IEnumerator.MoveNext()
			{
				//ILSpy generated this explicit interface implementation from .override directive in MoveNext
				return this.MoveNext();
			}

			[DebuggerHidden]
			void IEnumerator.Reset()
			{
				throw new NotSupportedException();
			}
		}

		private static MethodBase TargetMethod()
		{
			Type type = AccessTools.TypeByName("PlayerRespawnManager");
			if (type == null)
			{
				return null;
			}
			MethodInfo[] methods = type.GetMethods(AccessTools.all);
			foreach (MethodInfo methodInfo in methods)
			{
				if (methodInfo.Name == "ColiRespawnRoutine" && typeof(IEnumerator).IsAssignableFrom(methodInfo.ReturnType))
				{
					return methodInfo;
				}
			}
			return null;
		}

		[IteratorStateMachine(typeof(<SkipEnumerator>d__1))]
		private static IEnumerator SkipEnumerator()
		{
			//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
			return new <SkipEnumerator>d__1(0);
		}

		private static bool Prefix(object __instance, ref IEnumerator __result)
		{
			try
			{
				if (!FFAMode.IsActive())
				{
					return true;
				}
				object? obj = AccessTools.Field(__instance.GetType(), "pmv")?.GetValue(__instance);
				Component val = (Component)((obj is Component) ? obj : null);
				if ((Object)(object)val == (Object)null)
				{
					return true;
				}
				GameObject gameObject = val.gameObject;
				if (FFALastStand.IsEnded() || FFALastStand.IsEliminated(gameObject))
				{
					__result = SkipEnumerator();
					return false;
				}
			}
			catch (Exception arg)
			{
				ManualLogSource log = Plugin.Log;
				if (log != null)
				{
					log.LogWarning((object)$"FFA ColiRespawnRoutine prefix error: {arg}");
				}
			}
			return true;
		}
	}
	[HarmonyPatch]
	public static class PlayerMovement_RespawnPlayer_Prefix
	{
		private static MethodBa