Decompiled source of ShadowChildEnhancements v4.0.0

ShadowChildEnhancements.dll

Decompiled a month ago
using System;
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 HarmonyLib;
using Microsoft.CodeAnalysis;
using Photon.Pun;
using UnityEngine;
using UnityEngine.AI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: IgnoresAccessChecksTo("")]
[assembly: AssemblyCompany("REPOJP")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("zabuMod")]
[assembly: AssemblyTitle("zabuMod")]
[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 REPOJP.ShadowChildEnhancements
{
	[BepInPlugin("REPOJP.ShadowChildEnhancements", "ShadowChildEnhancements", "4.0.0")]
	public sealed class ShadowChildEnhancementsPlugin : BaseUnityPlugin
	{
		public const string PluginGuid = "REPOJP.ShadowChildEnhancements";

		public const string PluginName = "ShadowChildEnhancements";

		public const string PluginVersion = "4.0.0";

		internal static ShadowChildEnhancementsPlugin Instance;

		internal static ManualLogSource LogSource;

		internal static ConfigEntry<float> CfgEyeContactSeconds;

		internal static ConfigEntry<float> CfgKnockbackMultiplier;

		internal static ConfigEntry<int> CfgDamage;

		internal static ConfigEntry<float> CfgLookAwayGraceSeconds;

		internal static ConfigEntry<float> CfgStunSeconds;

		internal static ConfigEntry<bool> CfgApproachEnabled;

		internal static ConfigEntry<bool> CfgApproachOnlyWhenNotWatched;

		internal static ConfigEntry<float> CfgApproachRadius;

		internal static ConfigEntry<float> CfgApproachMoveSpeed;

		internal static ConfigEntry<float> CfgApproachStopDistance;

		internal static ConfigEntry<float> CfgApproachStuckRetargetSeconds;

		internal static ConfigEntry<bool> CfgApproachForceThroughObstacles;

		internal static ConfigEntry<float> CfgApproachForceAssist;

		internal static ConfigEntry<float> CfgApproachTiltAngle;

		internal static ConfigEntry<bool> CfgSolidarityAttack;

		private void Awake()
		{
			//IL_007a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0084: Expected O, but got Unknown
			//IL_00b7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c1: Expected O, but got Unknown
			//IL_00ea: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f4: Expected O, but got Unknown
			//IL_0127: Unknown result type (might be due to invalid IL or missing references)
			//IL_0131: Expected O, but got Unknown
			//IL_0164: Unknown result type (might be due to invalid IL or missing references)
			//IL_016e: Expected O, but got Unknown
			//IL_01e1: Unknown result type (might be due to invalid IL or missing references)
			//IL_01eb: Expected O, but got Unknown
			//IL_021e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0228: Expected O, but got Unknown
			//IL_025b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0265: Expected O, but got Unknown
			//IL_0298: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a2: Expected O, but got Unknown
			//IL_02f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ff: Expected O, but got Unknown
			//IL_0332: Unknown result type (might be due to invalid IL or missing references)
			//IL_033c: Expected O, but got Unknown
			//IL_0366: Unknown result type (might be due to invalid IL or missing references)
			//IL_036c: Expected O, but got Unknown
			try
			{
				Instance = this;
				LogSource = ((BaseUnityPlugin)this).Logger;
				try
				{
					if ((Object)(object)((Component)this).transform.parent != (Object)null)
					{
						((Component)this).transform.SetParent((Transform)null);
					}
					Object.DontDestroyOnLoad((Object)(object)((Component)this).gameObject);
				}
				catch
				{
				}
				CfgEyeContactSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChild", "EyeContactSeconds", 3f, new ConfigDescription("Seconds required before attack.攻撃までに必要な目合わせ秒数", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 20f), Array.Empty<object>()));
				CfgKnockbackMultiplier = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChild", "KnockbackMultiplier", 10f, new ConfigDescription("Pull force multiplier. Default 10 equals vanilla Shadow Child pull strength.引き寄せ力倍率。初期値10でバニラのShadow Child相当", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 50f), Array.Empty<object>()));
				CfgDamage = ((BaseUnityPlugin)this).Config.Bind<int>("ShadowChild", "Damage", 50, new ConfigDescription("Damage amount.ダメージ量", (AcceptableValueBase)(object)new AcceptableValueRange<int>(0, 100), Array.Empty<object>()));
				CfgLookAwayGraceSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChild", "LookAwayGraceSeconds", 0f, new ConfigDescription("Grace seconds after looking away.目を外した直後の猶予秒数", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 20f), Array.Empty<object>()));
				CfgStunSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChild", "StunSeconds", 1f, new ConfigDescription("Seconds to keep the target in tumble stun during the pull.引き寄せ中に対象を倒れ状態へ固定する秒数", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0.1f, 10f), Array.Empty<object>()));
				CfgApproachEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("ShadowChildApproach", "ApproachEnabled", true, "Move toward the first player who enters the detection radius.検知半径に最初に入ったプレイヤーへ移動する");
				CfgApproachOnlyWhenNotWatched = ((BaseUnityPlugin)this).Config.Bind<bool>("ShadowChildApproach", "ApproachOnlyWhenNotWatched", true, "Stop approach movement while any player is looking at the Shadow Child.誰かがShadow Childを見ている間は接近移動を止める");
				CfgApproachRadius = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChildApproach", "ApproachRadius", 50f, new ConfigDescription("Detection radius for selecting approach targets.接近対象を選ぶ検知半径", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 50f), Array.Empty<object>()));
				CfgApproachMoveSpeed = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChildApproach", "ApproachMoveSpeed", 4f, new ConfigDescription("Move speed toward the first-entered player.最初に入ったプレイヤーへ向かう移動速度", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 20f), Array.Empty<object>()));
				CfgApproachStopDistance = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChildApproach", "ApproachStopDistance", 2f, new ConfigDescription("Distance where approach movement stops.接近移動を止める距離", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 10f), Array.Empty<object>()));
				CfgApproachStuckRetargetSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChildApproach", "ApproachStuckRetargetSeconds", 5f, new ConfigDescription("Seconds stuck before abandoning the current approach target and selecting the farthest player in range.現在の接近対象へ詰まった時に対象を破棄して範囲内の最遠プレイヤーへ切り替えるまでの秒数", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 30f), Array.Empty<object>()));
				CfgApproachForceThroughObstacles = ((BaseUnityPlugin)this).Config.Bind<bool>("ShadowChildApproach", "ApproachForceThroughObstacles", true, "Force the Shadow Child forward when it gets stuck on low ceilings, stairs, or small steps.低い天井、階段、小さい段差で詰まった時にShadow Childを移動方向へ強制的に押し進める");
				CfgApproachForceAssist = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChildApproach", "ApproachForceAssist", 18f, new ConfigDescription("Extra physical push strength while approaching.接近移動中の物理押し込み補助の強さ", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 80f), Array.Empty<object>()));
				CfgApproachTiltAngle = ((BaseUnityPlugin)this).Config.Bind<float>("ShadowChildApproach", "ApproachTiltAngle", 34f, new ConfigDescription("Forward lean angle used while forcing movement.強制移動中に前傾させる角度", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 60f), Array.Empty<object>()));
				CfgSolidarityAttack = ((BaseUnityPlugin)this).Config.Bind<bool>("ShadowChild", "SolidarityAttack", true, "Attack all players who entered sight at least once.一瞬でも視界に入ったプレイヤー全員を攻撃対象に含める");
				Harmony val = new Harmony("REPOJP.ShadowChildEnhancements");
				val.PatchAll(typeof(ShadowChildEnhancementsPatches));
				LogSource.LogInfo((object)"ShadowChildEnhancements v4.0.0 loaded");
			}
			catch (Exception ex)
			{
				if (LogSource != null)
				{
					LogSource.LogError((object)("Failure: ShadowChildEnhancements Awake\n" + ex));
				}
			}
		}
	}
	internal static class ShadowChildEnhancementsPatches
	{
		private sealed class RuntimeState
		{
			public float LastOnScreenTime = -99999f;

			public readonly HashSet<int> AccumulatedViewIds = new HashSet<int>();

			public readonly HashSet<int> ActiveVictimViewIds = new HashSet<int>();

			public readonly HashSet<int> NearbyApproachViewIds = new HashSet<int>();

			public int ApproachTargetViewId = -1;

			public float NextDestinationRefreshTime;

			public Vector3 LastApproachDestination = Vector3.zero;

			public GameObject ApproachAgentObject;

			public NavMeshAgent ApproachAgent;

			public Vector3 LastApproachBodyPosition = Vector3.zero;

			public Vector3 LastApproachMoveDirection = Vector3.forward;

			public Vector3 ApproachRetargetReferencePosition = Vector3.zero;

			public float ApproachStuckSeconds;

			public float ApproachRetargetStuckSeconds;

			public float ApproachAssistUntilTime;

			public bool ActiveDamage;
		}

		private sealed class ApproachAgentCleanup : MonoBehaviour
		{
			public GameObject AgentObject;

			private void OnDestroy()
			{
				try
				{
					if ((Object)(object)AgentObject != (Object)null)
					{
						Object.Destroy((Object)(object)AgentObject);
					}
				}
				catch
				{
				}
			}
		}

		private const float FixedLookAwayDecayMultiplier = 0f;

		private const float ExpandedPaddingWidth = 0.35f;

		private const float ExpandedPaddingHeight = 0.35f;

		private const float FastOnScreenPollInterval = 0.02f;

		private const float PullForceBase = 500f;

		private const float TorqueForceBase = 0.2f;

		private const float DamageStateSeconds = 0.5f;

		private const float TargetReachedDistance = 2f;

		private const float ApproachDestinationRefreshInterval = 0.2f;

		private const float ApproachStuckCheckDistance = 0.06f;

		private const float ApproachStuckSecondsThreshold = 0.3f;

		private const float ApproachAssistDuration = 1.1f;

		private const float ApproachMaxFollowTargetDistance = 2.5f;

		private static readonly ConditionalWeakTable<EnemyThinMan, RuntimeState> StateTable = new ConditionalWeakTable<EnemyThinMan, RuntimeState>();

		private static readonly FieldRef<EnemyThinMan, Enemy> F_EnemyThinMan_enemy = AccessTools.FieldRefAccess<EnemyThinMan, Enemy>("enemy");

		private static readonly FieldRef<EnemyThinMan, bool> F_EnemyThinMan_stateImpulse = AccessTools.FieldRefAccess<EnemyThinMan, bool>("stateImpulse");

		private static readonly FieldRef<EnemyThinMan, float> F_EnemyThinMan_stateTimer = AccessTools.FieldRefAccess<EnemyThinMan, float>("stateTimer");

		private static readonly FieldRef<EnemyThinMan, float> F_EnemyThinMan_teleportRoamTimer = AccessTools.FieldRefAccess<EnemyThinMan, float>("teleportRoamTimer");

		private static readonly FieldRef<EnemyThinMan, Vector3> F_EnemyThinMan_teleportPosition = AccessTools.FieldRefAccess<EnemyThinMan, Vector3>("teleportPosition");

		private static readonly FieldRef<EnemyThinMan, bool> F_EnemyThinMan_teleporting = AccessTools.FieldRefAccess<EnemyThinMan, bool>("teleporting");

		private static readonly FieldRef<EnemyThinMan, PlayerAvatar> F_EnemyThinMan_playerTarget = AccessTools.FieldRefAccess<EnemyThinMan, PlayerAvatar>("playerTarget");

		private static readonly MethodInfo M_EnemyThinMan_UpdateState = AccessTools.Method(typeof(EnemyThinMan), "UpdateState", new Type[1] { typeof(State) }, (Type[])null);

		private static readonly MethodInfo M_EnemyThinMan_SetTarget = AccessTools.Method(typeof(EnemyThinMan), "SetTarget", new Type[1] { typeof(PlayerAvatar) }, (Type[])null);

		private static readonly FieldRef<Enemy, EnemyOnScreen> F_Enemy_OnScreen = AccessTools.FieldRefAccess<Enemy, EnemyOnScreen>("OnScreen");

		private static readonly FieldRef<Enemy, EnemyVision> F_Enemy_Vision = AccessTools.FieldRefAccess<Enemy, EnemyVision>("Vision");

		private static readonly FieldInfo FI_EnemyOnScreen_OnScreenTimer = AccessTools.Field(typeof(EnemyOnScreen), "OnScreenTimer");

		private static readonly FieldInfo FI_EnemyOnScreen_OnScreenPlayer = AccessTools.Field(typeof(EnemyOnScreen), "OnScreenPlayer");

		private static readonly FieldInfo FI_EnemyOnScreen_CulledPlayer = AccessTools.Field(typeof(EnemyOnScreen), "CulledPlayer");

		private static readonly FieldRef<PlayerAvatar, bool> F_PlayerAvatar_isDisabled = AccessTools.FieldRefAccess<PlayerAvatar, bool>("isDisabled");

		private static readonly FieldRef<PlayerAvatar, bool> F_PlayerAvatar_deadSet = AccessTools.FieldRefAccess<PlayerAvatar, bool>("deadSet");

		private static readonly FieldRef<PlayerHealth, int> F_PlayerHealth_health = AccessTools.FieldRefAccess<PlayerHealth, int>("health");

		private static readonly FieldRef<PhysGrabObject, PhotonView> F_PhysGrabObject_photonView = AccessTools.FieldRefAccess<PhysGrabObject, PhotonView>("photonView");

		private static readonly MethodInfo M_PlayerHealth_HurtOther5 = AccessTools.Method(typeof(PlayerHealth), "HurtOther", new Type[5]
		{
			typeof(int),
			typeof(Vector3),
			typeof(bool),
			typeof(int),
			typeof(bool)
		}, (Type[])null);

		private static readonly MethodInfo M_PlayerHealth_HurtOther4 = AccessTools.Method(typeof(PlayerHealth), "HurtOther", new Type[4]
		{
			typeof(int),
			typeof(Vector3),
			typeof(bool),
			typeof(int)
		}, (Type[])null);

		private static bool loggedHurtOtherMissing;

		private static bool IsMasterOrSingle()
		{
			try
			{
				return SemiFunc.IsMasterClientOrSingleplayer();
			}
			catch
			{
				if (!GameManager.Multiplayer())
				{
					return true;
				}
				return PhotonNetwork.IsMasterClient;
			}
		}

		private static RuntimeState GetState(EnemyThinMan thinMan)
		{
			return StateTable.GetOrCreateValue(thinMan);
		}

		private static void ClearApproachState(EnemyThinMan thinMan)
		{
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_0045: Unknown result type (might be due to invalid IL or missing references)
			//IL_004b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0050: Unknown result type (might be due to invalid IL or missing references)
			//IL_0056: Unknown result type (might be due to invalid IL or missing references)
			//IL_005b: Unknown result type (might be due to invalid IL or missing references)
			if (!((Object)(object)thinMan == (Object)null))
			{
				RuntimeState state = GetState(thinMan);
				state.ApproachTargetViewId = -1;
				state.NearbyApproachViewIds.Clear();
				state.NextDestinationRefreshTime = 0f;
				state.LastApproachDestination = Vector3.zero;
				state.LastApproachBodyPosition = Vector3.zero;
				state.LastApproachMoveDirection = Vector3.forward;
				state.ApproachRetargetReferencePosition = Vector3.zero;
				state.ApproachStuckSeconds = 0f;
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachAssistUntilTime = 0f;
				StopApproachAgent(state);
			}
		}

		private static Enemy GetEnemy(EnemyThinMan thinMan)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return null;
			}
			try
			{
				return F_EnemyThinMan_enemy.Invoke(thinMan);
			}
			catch
			{
				return null;
			}
		}

		private static PlayerAvatar GetTarget(EnemyThinMan thinMan)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return null;
			}
			try
			{
				return F_EnemyThinMan_playerTarget.Invoke(thinMan);
			}
			catch
			{
				return null;
			}
		}

		private static void SetTarget(EnemyThinMan thinMan, PlayerAvatar target)
		{
			if ((Object)(object)thinMan == (Object)null || M_EnemyThinMan_SetTarget == null)
			{
				return;
			}
			try
			{
				M_EnemyThinMan_SetTarget.Invoke(thinMan, new object[1] { target });
			}
			catch
			{
			}
		}

		private static void UpdateState(EnemyThinMan thinMan, State state)
		{
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || M_EnemyThinMan_UpdateState == null)
			{
				return;
			}
			try
			{
				M_EnemyThinMan_UpdateState.Invoke(thinMan, new object[1] { state });
			}
			catch
			{
			}
		}

		private static void SetStateImpulse(EnemyThinMan thinMan, bool value)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return;
			}
			try
			{
				F_EnemyThinMan_stateImpulse.Invoke(thinMan) = value;
			}
			catch
			{
			}
		}

		private static bool GetStateImpulse(EnemyThinMan thinMan)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return false;
			}
			try
			{
				return F_EnemyThinMan_stateImpulse.Invoke(thinMan);
			}
			catch
			{
				return false;
			}
		}

		private static void SetStateTimer(EnemyThinMan thinMan, float value)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return;
			}
			try
			{
				F_EnemyThinMan_stateTimer.Invoke(thinMan) = value;
			}
			catch
			{
			}
		}

		private static float GetStateTimer(EnemyThinMan thinMan)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return 0f;
			}
			try
			{
				return F_EnemyThinMan_stateTimer.Invoke(thinMan);
			}
			catch
			{
				return 0f;
			}
		}

		private static void SetTeleportRoamTimer(EnemyThinMan thinMan, float value)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return;
			}
			try
			{
				F_EnemyThinMan_teleportRoamTimer.Invoke(thinMan) = Mathf.Max(F_EnemyThinMan_teleportRoamTimer.Invoke(thinMan), value);
			}
			catch
			{
			}
		}

		private static void SetTeleporting(EnemyThinMan thinMan, bool value)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return;
			}
			try
			{
				F_EnemyThinMan_teleporting.Invoke(thinMan) = value;
			}
			catch
			{
			}
		}

		private static Vector3 GetTeleportPosition(EnemyThinMan thinMan)
		{
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_0051: Unknown result type (might be due to invalid IL or missing references)
			//IL_0056: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Unknown result type (might be due to invalid IL or missing references)
			//IL_0022: Unknown result type (might be due to invalid IL or missing references)
			//IL_0027: Unknown result type (might be due to invalid IL or missing references)
			//IL_0059: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null)
			{
				return Vector3.zero;
			}
			try
			{
				return F_EnemyThinMan_teleportPosition.Invoke(thinMan);
			}
			catch
			{
				if ((Object)(object)thinMan.rb != (Object)null)
				{
					return thinMan.rb.position;
				}
				return ((Component)thinMan).transform.position;
			}
		}

		private static void SetTeleportPosition(EnemyThinMan thinMan, Vector3 value)
		{
			//IL_001c: Unknown result type (might be due to invalid IL or missing references)
			//IL_001d: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null)
			{
				return;
			}
			try
			{
				F_EnemyThinMan_teleportPosition.Invoke(thinMan) = value;
			}
			catch
			{
			}
		}

		private static bool HasConfigKey(string section, string key)
		{
			try
			{
				string path = Path.Combine(Paths.ConfigPath, "REPOJP.ShadowChildEnhancements.cfg");
				if (!File.Exists(path))
				{
					return false;
				}
				bool flag = false;
				string[] array = File.ReadAllLines(path);
				for (int i = 0; i < array.Length; i++)
				{
					string text = array[i].Trim();
					if (text.Length == 0 || text.StartsWith("#", StringComparison.Ordinal) || text.StartsWith("//", StringComparison.Ordinal))
					{
						continue;
					}
					if (text.StartsWith("[", StringComparison.Ordinal) && text.EndsWith("]", StringComparison.Ordinal))
					{
						string a = text.Substring(1, text.Length - 2);
						flag = string.Equals(a, section, StringComparison.OrdinalIgnoreCase);
					}
					else
					{
						if (!flag)
						{
							continue;
						}
						int num = text.IndexOf('=');
						if (num > 0)
						{
							string a2 = text.Substring(0, num).Trim();
							if (string.Equals(a2, key, StringComparison.OrdinalIgnoreCase))
							{
								return true;
							}
						}
					}
				}
			}
			catch
			{
			}
			return false;
		}

		private static EnemyOnScreen GetOnScreen(Enemy enemy)
		{
			if ((Object)(object)enemy == (Object)null)
			{
				return null;
			}
			try
			{
				return F_Enemy_OnScreen.Invoke(enemy);
			}
			catch
			{
				return null;
			}
		}

		private static EnemyVision GetVision(Enemy enemy)
		{
			if ((Object)(object)enemy == (Object)null)
			{
				return null;
			}
			try
			{
				return F_Enemy_Vision.Invoke(enemy);
			}
			catch
			{
				return null;
			}
		}

		private static Dictionary<int, bool> GetOnScreenDictionary(EnemyOnScreen onScreen, FieldInfo fieldInfo)
		{
			if ((Object)(object)onScreen == (Object)null || fieldInfo == null)
			{
				return null;
			}
			try
			{
				return fieldInfo.GetValue(onScreen) as Dictionary<int, bool>;
			}
			catch
			{
				return null;
			}
		}

		private static void EnsureOnScreenPlayerKey(EnemyOnScreen onScreen, PlayerAvatar playerAvatar)
		{
			if ((Object)(object)onScreen == (Object)null || (Object)(object)playerAvatar == (Object)null || (Object)(object)playerAvatar.photonView == (Object)null)
			{
				return;
			}
			int viewID = playerAvatar.photonView.ViewID;
			if (viewID <= 0)
			{
				return;
			}
			Dictionary<int, bool> onScreenDictionary = GetOnScreenDictionary(onScreen, FI_EnemyOnScreen_OnScreenPlayer);
			Dictionary<int, bool> onScreenDictionary2 = GetOnScreenDictionary(onScreen, FI_EnemyOnScreen_CulledPlayer);
			try
			{
				if (onScreenDictionary != null && !onScreenDictionary.ContainsKey(viewID))
				{
					onScreenDictionary.Add(viewID, value: false);
				}
			}
			catch
			{
			}
			try
			{
				if (onScreenDictionary2 != null && !onScreenDictionary2.ContainsKey(viewID))
				{
					onScreenDictionary2.Add(viewID, value: false);
				}
			}
			catch
			{
			}
		}

		private static void EnsureOnScreenPlayerKeys(EnemyOnScreen onScreen)
		{
			if ((Object)(object)onScreen == (Object)null || (Object)(object)GameDirector.instance == (Object)null || GameDirector.instance.PlayerList == null)
			{
				return;
			}
			try
			{
				if (!GameManager.Multiplayer())
				{
					return;
				}
			}
			catch
			{
				return;
			}
			foreach (PlayerAvatar player in GameDirector.instance.PlayerList)
			{
				EnsureOnScreenPlayerKey(onScreen, player);
			}
		}

		private static bool SafeGetOnScreen(EnemyOnScreen onScreen, PlayerAvatar playerAvatar)
		{
			if ((Object)(object)onScreen == (Object)null || (Object)(object)playerAvatar == (Object)null)
			{
				return false;
			}
			try
			{
				if (!GameManager.Multiplayer())
				{
					return onScreen.GetOnScreen(playerAvatar);
				}
			}
			catch
			{
				return false;
			}
			EnsureOnScreenPlayerKey(onScreen, playerAvatar);
			if ((Object)(object)playerAvatar.photonView == (Object)null)
			{
				return false;
			}
			Dictionary<int, bool> onScreenDictionary = GetOnScreenDictionary(onScreen, FI_EnemyOnScreen_OnScreenPlayer);
			if (onScreenDictionary == null)
			{
				return false;
			}
			int viewID = playerAvatar.photonView.ViewID;
			if (onScreenDictionary.TryGetValue(viewID, out var value))
			{
				return value;
			}
			return false;
		}

		[HarmonyPatch(typeof(EnemyOnScreen), "GetOnScreen")]
		[HarmonyPrefix]
		private static bool EnemyOnScreen_GetOnScreen_Prefix(EnemyOnScreen __instance, PlayerAvatar _playerAvatar, ref bool __result)
		{
			if ((Object)(object)__instance == (Object)null || (Object)(object)_playerAvatar == (Object)null)
			{
				__result = false;
				return false;
			}
			try
			{
				if (!GameManager.Multiplayer())
				{
					return true;
				}
			}
			catch
			{
				__result = false;
				return false;
			}
			__result = SafeGetOnScreen(__instance, _playerAvatar);
			return false;
		}

		private static void TuneOnScreenComponent(EnemyThinMan thinMan)
		{
			Enemy enemy = GetEnemy(thinMan);
			EnemyOnScreen onScreen = GetOnScreen(enemy);
			if ((Object)(object)onScreen == (Object)null)
			{
				return;
			}
			try
			{
				onScreen.paddingWidth = 0.35f;
				onScreen.paddingHeight = 0.35f;
			}
			catch
			{
			}
			try
			{
				if (FI_EnemyOnScreen_OnScreenTimer != null)
				{
					FI_EnemyOnScreen_OnScreenTimer.SetValue(onScreen, 0.02f);
				}
			}
			catch
			{
			}
		}

		private static bool IsAttackable(PlayerAvatar avatar)
		{
			if ((Object)(object)avatar == (Object)null || (Object)(object)avatar.photonView == (Object)null || (Object)(object)avatar.playerHealth == (Object)null || (Object)(object)avatar.tumble == (Object)null)
			{
				return false;
			}
			bool flag = false;
			bool flag2 = false;
			try
			{
				flag = F_PlayerAvatar_isDisabled.Invoke(avatar);
			}
			catch
			{
				flag = false;
			}
			try
			{
				flag2 = F_PlayerAvatar_deadSet.Invoke(avatar);
			}
			catch
			{
				flag2 = false;
			}
			if (flag || flag2)
			{
				return false;
			}
			int num = 1;
			try
			{
				num = F_PlayerHealth_health.Invoke(avatar.playerHealth);
			}
			catch
			{
				num = 1;
			}
			return num > 0;
		}

		private static List<PlayerAvatar> GetVisiblePlayers(EnemyThinMan thinMan)
		{
			List<PlayerAvatar> list = new List<PlayerAvatar>();
			Enemy enemy = GetEnemy(thinMan);
			EnemyOnScreen onScreen = GetOnScreen(enemy);
			if ((Object)(object)onScreen == (Object)null || (Object)(object)GameDirector.instance == (Object)null || GameDirector.instance.PlayerList == null)
			{
				return list;
			}
			foreach (PlayerAvatar player in GameDirector.instance.PlayerList)
			{
				if (IsAttackable(player))
				{
					bool flag = false;
					try
					{
						flag = SafeGetOnScreen(onScreen, player);
					}
					catch
					{
						flag = false;
					}
					if (flag)
					{
						list.Add(player);
					}
				}
			}
			return list;
		}

		private static bool IsWatchedByAnyPlayer(EnemyThinMan thinMan)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return false;
			}
			return GetVisiblePlayers(thinMan).Count > 0;
		}

		private static bool ShouldPauseApproachForWatchedState(EnemyThinMan thinMan)
		{
			if ((Object)(object)thinMan == (Object)null)
			{
				return false;
			}
			if (!ShadowChildEnhancementsPlugin.CfgApproachOnlyWhenNotWatched.Value)
			{
				return false;
			}
			return IsWatchedByAnyPlayer(thinMan);
		}

		private static bool ContainsPlayer(List<PlayerAvatar> players, PlayerAvatar target)
		{
			if (players == null || (Object)(object)target == (Object)null)
			{
				return false;
			}
			for (int i = 0; i < players.Count; i++)
			{
				if ((Object)(object)players[i] == (Object)(object)target)
				{
					return true;
				}
			}
			return false;
		}

		private static void TrackVisiblePlayers(EnemyThinMan thinMan, List<PlayerAvatar> visiblePlayers)
		{
			if ((Object)(object)thinMan == (Object)null || visiblePlayers == null || visiblePlayers.Count == 0)
			{
				return;
			}
			RuntimeState state = GetState(thinMan);
			for (int i = 0; i < visiblePlayers.Count; i++)
			{
				PlayerAvatar val = visiblePlayers[i];
				if (!((Object)(object)val == (Object)null) && !((Object)(object)val.photonView == (Object)null))
				{
					int viewID = val.photonView.ViewID;
					if (viewID > 0)
					{
						state.AccumulatedViewIds.Add(viewID);
					}
				}
			}
		}

		private static PlayerAvatar ResolvePlayer(int viewId)
		{
			if (viewId <= 0)
			{
				return null;
			}
			try
			{
				PhotonView val = PhotonView.Find(viewId);
				if ((Object)(object)val == (Object)null)
				{
					return null;
				}
				return ((Component)val).GetComponent<PlayerAvatar>();
			}
			catch
			{
				return null;
			}
		}

		private static void AddUniquePlayer(List<PlayerAvatar> players, PlayerAvatar playerAvatar)
		{
			if (!IsAttackable(playerAvatar))
			{
				return;
			}
			for (int i = 0; i < players.Count; i++)
			{
				if ((Object)(object)players[i] == (Object)(object)playerAvatar)
				{
					return;
				}
			}
			players.Add(playerAvatar);
		}

		private static List<PlayerAvatar> CollectVictims(EnemyThinMan thinMan, PlayerAvatar primary)
		{
			List<PlayerAvatar> list = new List<PlayerAvatar>();
			RuntimeState state = GetState(thinMan);
			AddUniquePlayer(list, primary);
			if (!ShadowChildEnhancementsPlugin.CfgSolidarityAttack.Value)
			{
				if (list.Count == 0)
				{
					foreach (int accumulatedViewId in state.AccumulatedViewIds)
					{
						AddUniquePlayer(list, ResolvePlayer(accumulatedViewId));
						if (list.Count > 0)
						{
							break;
						}
					}
				}
				return list;
			}
			foreach (int accumulatedViewId2 in state.AccumulatedViewIds)
			{
				AddUniquePlayer(list, ResolvePlayer(accumulatedViewId2));
			}
			return list;
		}

		private static void SetActiveVictims(EnemyThinMan thinMan, List<PlayerAvatar> victims)
		{
			RuntimeState state = GetState(thinMan);
			state.ActiveVictimViewIds.Clear();
			for (int i = 0; i < victims.Count; i++)
			{
				PlayerAvatar val = victims[i];
				if (!((Object)(object)val == (Object)null) && !((Object)(object)val.photonView == (Object)null))
				{
					int viewID = val.photonView.ViewID;
					if (viewID > 0)
					{
						state.ActiveVictimViewIds.Add(viewID);
					}
				}
			}
			state.ActiveDamage = state.ActiveVictimViewIds.Count > 0;
		}

		private static List<PlayerAvatar> GetActiveVictims(EnemyThinMan thinMan)
		{
			List<PlayerAvatar> list = new List<PlayerAvatar>();
			RuntimeState state = GetState(thinMan);
			foreach (int activeVictimViewId in state.ActiveVictimViewIds)
			{
				AddUniquePlayer(list, ResolvePlayer(activeVictimViewId));
			}
			return list;
		}

		private static void ClearActiveVictims(EnemyThinMan thinMan)
		{
			if (!((Object)(object)thinMan == (Object)null))
			{
				RuntimeState state = GetState(thinMan);
				state.ActiveVictimViewIds.Clear();
				state.ActiveDamage = false;
			}
		}

		private static void InvokeHurtOther(PlayerAvatar playerAvatar, int damage, Vector3 hurtPosition, int enemyIndex)
		{
			//IL_0055: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
			if (damage <= 0 || (Object)(object)playerAvatar == (Object)null || (Object)(object)playerAvatar.playerHealth == (Object)null)
			{
				return;
			}
			try
			{
				if (M_PlayerHealth_HurtOther5 != null)
				{
					M_PlayerHealth_HurtOther5.Invoke(playerAvatar.playerHealth, new object[5] { damage, hurtPosition, false, enemyIndex, false });
				}
				else if (M_PlayerHealth_HurtOther4 != null)
				{
					M_PlayerHealth_HurtOther4.Invoke(playerAvatar.playerHealth, new object[4] { damage, hurtPosition, false, enemyIndex });
				}
				else if (!loggedHurtOtherMissing && ShadowChildEnhancementsPlugin.LogSource != null)
				{
					loggedHurtOtherMissing = true;
					ShadowChildEnhancementsPlugin.LogSource.LogWarning((object)"Failure: PlayerHealth.HurtOther method not found");
				}
			}
			catch (Exception ex)
			{
				if (!loggedHurtOtherMissing && ShadowChildEnhancementsPlugin.LogSource != null)
				{
					loggedHurtOtherMissing = true;
					ShadowChildEnhancementsPlugin.LogSource.LogWarning((object)("Failure: PlayerHealth.HurtOther invoke\n" + ex));
				}
			}
		}

		private static void ReleaseGrabbedObjects(PlayerAvatar playerAvatar, float releaseSeconds)
		{
			if ((Object)(object)playerAvatar == (Object)null || (Object)(object)playerAvatar.tumble == (Object)null || (Object)(object)playerAvatar.tumble.physGrabObject == (Object)null)
			{
				return;
			}
			try
			{
				PhysGrabObject physGrabObject = playerAvatar.tumble.physGrabObject;
				PhotonView val = F_PhysGrabObject_photonView.Invoke(physGrabObject);
				int num = (((Object)(object)val != (Object)null) ? val.ViewID : (-1));
				List<PhysGrabber> list = new List<PhysGrabber>(physGrabObject.playerGrabbing);
				for (int i = 0; i < list.Count; i++)
				{
					PhysGrabber val2 = list[i];
					if (!((Object)(object)val2 == (Object)null))
					{
						val2.OverrideGrabRelease(num, releaseSeconds);
					}
				}
			}
			catch
			{
			}
		}

		private static void ApplyTumbleHold(PlayerAvatar playerAvatar, float stunSeconds)
		{
			if (!((Object)(object)playerAvatar == (Object)null) && !((Object)(object)playerAvatar.tumble == (Object)null))
			{
				try
				{
					playerAvatar.tumble.TumbleRequest(true, false);
				}
				catch
				{
				}
				try
				{
					playerAvatar.tumble.TumbleOverrideTime(stunSeconds);
				}
				catch
				{
				}
				try
				{
					playerAvatar.tumble.OverrideEnemyHurt(stunSeconds);
				}
				catch
				{
				}
				ReleaseGrabbedObjects(playerAvatar, stunSeconds);
			}
		}

		private static Vector3 GetPullOrigin(EnemyThinMan thinMan, Enemy enemy)
		{
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0064: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0083: Unknown result type (might be due to invalid IL or missing references)
			//IL_0088: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0080: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				EnemyVision vision = GetVision(enemy);
				if ((Object)(object)vision != (Object)null && (Object)(object)vision.VisionTransform != (Object)null)
				{
					return vision.VisionTransform.position;
				}
			}
			catch
			{
			}
			if ((Object)(object)thinMan != (Object)null && (Object)(object)thinMan.rb != (Object)null)
			{
				return thinMan.rb.position;
			}
			if ((Object)(object)thinMan != (Object)null)
			{
				return ((Component)thinMan).transform.position;
			}
			return Vector3.zero;
		}

		private static Vector3 GetPlayerCenter(PlayerAvatar playerAvatar)
		{
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0064: Unknown result type (might be due to invalid IL or missing references)
			//IL_0067: Unknown result type (might be due to invalid IL or missing references)
			//IL_0049: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)playerAvatar == (Object)null)
			{
				return Vector3.zero;
			}
			try
			{
				if ((Object)(object)playerAvatar.tumble != (Object)null && (Object)(object)playerAvatar.tumble.physGrabObject != (Object)null)
				{
					return playerAvatar.tumble.physGrabObject.centerPoint;
				}
			}
			catch
			{
			}
			return ((Component)playerAvatar).transform.position;
		}

		private static void ApplyPullForce(EnemyThinMan thinMan, PlayerAvatar playerAvatar)
		{
			//IL_006e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0073: Unknown result type (might be due to invalid IL or missing references)
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007a: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Unknown result type (might be due to invalid IL or missing references)
			//IL_007d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0082: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f7: Unknown result type (might be due to invalid IL or missing references)
			//IL_0101: Unknown result type (might be due to invalid IL or missing references)
			//IL_0114: Unknown result type (might be due to invalid IL or missing references)
			//IL_011d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0127: Unknown result type (might be due to invalid IL or missing references)
			//IL_012e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0133: Unknown result type (might be due to invalid IL or missing references)
			//IL_0137: Unknown result type (might be due to invalid IL or missing references)
			//IL_014a: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || (Object)(object)playerAvatar == (Object)null || (Object)(object)playerAvatar.tumble == (Object)null || (Object)(object)playerAvatar.tumble.physGrabObject == (Object)null)
			{
				return;
			}
			PhysGrabObject physGrabObject = playerAvatar.tumble.physGrabObject;
			if ((Object)(object)physGrabObject.rb == (Object)null)
			{
				return;
			}
			Enemy enemy = GetEnemy(thinMan);
			Vector3 pullOrigin = GetPullOrigin(thinMan, enemy);
			Vector3 playerCenter = GetPlayerCenter(playerAvatar);
			Vector3 val = pullOrigin - playerCenter;
			if (((Vector3)(ref val)).sqrMagnitude <= 0.0001f)
			{
				return;
			}
			Vector3 normalized = ((Vector3)(ref val)).normalized;
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgKnockbackMultiplier.Value, 0f, 50f);
			if (num <= 0f)
			{
				return;
			}
			try
			{
				Rigidbody rb = physGrabObject.rb;
				rb.AddForce(normalized * 500f * num * Time.fixedDeltaTime, (ForceMode)0);
				Vector3 val2 = SemiFunc.PhysFollowDirection(((Component)rb).transform, normalized, rb, 10f) * 0.2f * num;
				rb.AddTorque(val2 / Mathf.Max(rb.mass, 0.01f), (ForceMode)0);
				if (((Vector3)(ref val)).magnitude < 2f)
				{
					SetStateTimer(thinMan, Mathf.Min(GetStateTimer(thinMan), 0.1f));
				}
			}
			catch
			{
			}
		}

		private static Vector3 GetEnemyPosition(EnemyThinMan thinMan)
		{
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_003f: Unknown result type (might be due to invalid IL or missing references)
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0042: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null)
			{
				return Vector3.zero;
			}
			if ((Object)(object)thinMan.rb != (Object)null)
			{
				return thinMan.rb.position;
			}
			return ((Component)thinMan).transform.position;
		}

		private static float GetHorizontalDistanceSqr(Vector3 a, Vector3 b)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0015: Unknown result type (might be due to invalid IL or missing references)
			float num = a.x - b.x;
			float num2 = a.z - b.z;
			return num * num + num2 * num2;
		}

		private static bool HasAnyPlayerWithinApproachRadius(EnemyThinMan thinMan)
		{
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || (Object)(object)GameDirector.instance == (Object)null || GameDirector.instance.PlayerList == null)
			{
				return false;
			}
			if (!ShadowChildEnhancementsPlugin.CfgApproachEnabled.Value)
			{
				return false;
			}
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachRadius.Value, 0f, 50f);
			if (num <= 0f)
			{
				return false;
			}
			float num2 = num * num;
			Vector3 enemyPosition = GetEnemyPosition(thinMan);
			foreach (PlayerAvatar player in GameDirector.instance.PlayerList)
			{
				if (!IsAttackable(player) || !(GetHorizontalDistanceSqr(enemyPosition, GetPlayerCenter(player)) <= num2))
				{
					continue;
				}
				return true;
			}
			return false;
		}

		private static PlayerAvatar UpdateApproachTarget(EnemyThinMan thinMan)
		{
			//IL_00e0: 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_00f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_010f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0113: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ac: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b1: 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_0276: Unknown result type (might be due to invalid IL or missing references)
			//IL_0238: Unknown result type (might be due to invalid IL or missing references)
			//IL_023d: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || (Object)(object)GameDirector.instance == (Object)null || GameDirector.instance.PlayerList == null)
			{
				return null;
			}
			RuntimeState state = GetState(thinMan);
			if (!ShadowChildEnhancementsPlugin.CfgApproachEnabled.Value)
			{
				ClearApproachState(thinMan);
				return null;
			}
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachRadius.Value, 0f, 50f);
			if (num <= 0f)
			{
				ClearApproachState(thinMan);
				return null;
			}
			float num2 = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachStopDistance.Value, 0f, 10f);
			float radiusSqr = num * num;
			float num3 = Mathf.Min(50f, Mathf.Max(num + 5f, num * 1.5f));
			float num4 = num3 * num3;
			Vector3 enemyPosition = GetEnemyPosition(thinMan);
			PlayerAvatar val = ResolvePlayer(state.ApproachTargetViewId);
			UpdateNearbyApproachPlayers(state, enemyPosition, radiusSqr);
			if (IsAttackable(val))
			{
				float horizontalDistanceSqr = GetHorizontalDistanceSqr(enemyPosition, GetPlayerCenter(val));
				if (horizontalDistanceSqr <= num2 * num2)
				{
					PlayerAvatar val2 = SelectFarthestApproachTarget(thinMan, val.photonView.ViewID, allowExcluded: false);
					if ((Object)(object)val2 == (Object)null)
					{
						state.ApproachTargetViewId = -1;
						state.NextDestinationRefreshTime = 0f;
						StopApproachAgent(state);
						return null;
					}
					state.ApproachTargetViewId = val2.photonView.ViewID;
					state.NextDestinationRefreshTime = 0f;
					state.ApproachStuckSeconds = 0f;
					state.ApproachRetargetStuckSeconds = 0f;
					state.ApproachRetargetReferencePosition = Vector3.zero;
					return val2;
				}
				if (horizontalDistanceSqr <= num4)
				{
					return val;
				}
			}
			PlayerAvatar val3 = SelectFarthestApproachTarget(thinMan, -1, allowExcluded: true);
			if ((Object)(object)val3 != (Object)null && (Object)(object)val3.photonView != (Object)null)
			{
				state.ApproachTargetViewId = val3.photonView.ViewID;
				state.NextDestinationRefreshTime = 0f;
				state.ApproachStuckSeconds = 0f;
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachRetargetReferencePosition = Vector3.zero;
				return val3;
			}
			state.ApproachTargetViewId = -1;
			state.NextDestinationRefreshTime = 0f;
			state.ApproachStuckSeconds = 0f;
			state.ApproachRetargetStuckSeconds = 0f;
			state.ApproachRetargetReferencePosition = Vector3.zero;
			StopApproachAgent(state);
			return null;
		}

		private static void UpdateNearbyApproachPlayers(RuntimeState state, Vector3 enemyPosition, float radiusSqr)
		{
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			//IL_0073: Unknown result type (might be due to invalid IL or missing references)
			if (state == null || (Object)(object)GameDirector.instance == (Object)null || GameDirector.instance.PlayerList == null)
			{
				return;
			}
			state.NearbyApproachViewIds.Clear();
			foreach (PlayerAvatar player in GameDirector.instance.PlayerList)
			{
				if (IsAttackable(player) && !((Object)(object)player.photonView == (Object)null) && GetHorizontalDistanceSqr(enemyPosition, GetPlayerCenter(player)) <= radiusSqr)
				{
					int viewID = player.photonView.ViewID;
					if (viewID > 0)
					{
						state.NearbyApproachViewIds.Add(viewID);
					}
				}
			}
		}

		private static float GetTargetDistanceSqr(EnemyThinMan thinMan, PlayerAvatar playerAvatar)
		{
			//IL_0022: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || (Object)(object)playerAvatar == (Object)null)
			{
				return float.MaxValue;
			}
			return GetHorizontalDistanceSqr(GetEnemyPosition(thinMan), GetPlayerCenter(playerAvatar));
		}

		private static PlayerAvatar SelectFarthestApproachTarget(EnemyThinMan thinMan, int excludedViewId, bool allowExcluded)
		{
			//IL_006f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0074: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ea: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || (Object)(object)GameDirector.instance == (Object)null || GameDirector.instance.PlayerList == null)
			{
				return null;
			}
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachRadius.Value, 0f, 50f);
			if (num <= 0f)
			{
				return null;
			}
			float num2 = num * num;
			Vector3 enemyPosition = GetEnemyPosition(thinMan);
			PlayerAvatar result = null;
			float num3 = -1f;
			foreach (PlayerAvatar player in GameDirector.instance.PlayerList)
			{
				if (!IsAttackable(player) || (Object)(object)player.photonView == (Object)null)
				{
					continue;
				}
				int viewID = player.photonView.ViewID;
				if (allowExcluded || excludedViewId <= 0 || viewID != excludedViewId)
				{
					float horizontalDistanceSqr = GetHorizontalDistanceSqr(enemyPosition, GetPlayerCenter(player));
					if (!(horizontalDistanceSqr > num2) && horizontalDistanceSqr > num3)
					{
						num3 = horizontalDistanceSqr;
						result = player;
					}
				}
			}
			return result;
		}

		private static bool TrySampleNavMeshPosition(Vector3 sourcePosition, float sampleDistance, out Vector3 sampledPosition)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0022: Unknown result type (might be due to invalid IL or missing references)
			//IL_0027: Unknown result type (might be due to invalid IL or missing references)
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			NavMeshHit val = default(NavMeshHit);
			if (NavMesh.SamplePosition(sourcePosition, ref val, sampleDistance, -1))
			{
				sampledPosition = ((NavMeshHit)(ref val)).position;
				return true;
			}
			sampledPosition = Vector3.zero;
			return false;
		}

		private static void StopApproachAgent(RuntimeState state)
		{
			if (state == null || (Object)(object)state.ApproachAgent == (Object)null)
			{
				return;
			}
			try
			{
				if (((Behaviour)state.ApproachAgent).enabled && state.ApproachAgent.isOnNavMesh)
				{
					state.ApproachAgent.ResetPath();
					state.ApproachAgent.isStopped = true;
				}
			}
			catch
			{
			}
		}

		private static NavMeshAgent GetOrCreateApproachAgent(EnemyThinMan thinMan)
		{
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Expected O, but got Unknown
			//IL_008d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0158: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null)
			{
				return null;
			}
			RuntimeState state = GetState(thinMan);
			if ((Object)(object)state.ApproachAgent != (Object)null && (Object)(object)state.ApproachAgentObject != (Object)null)
			{
				return state.ApproachAgent;
			}
			if (!TrySampleNavMeshPosition(GetEnemyPosition(thinMan), 8f, out var sampledPosition))
			{
				return null;
			}
			try
			{
				GameObject val = new GameObject("REPOJP_ShadowChildApproachAgent");
				((Object)val).hideFlags = (HideFlags)61;
				val.transform.position = sampledPosition;
				NavMeshAgent val2 = val.AddComponent<NavMeshAgent>();
				val2.updateRotation = false;
				val2.updateUpAxis = true;
				val2.autoBraking = true;
				val2.autoRepath = true;
				val2.radius = 0.45f;
				val2.height = 1.8f;
				val2.baseOffset = 0f;
				val2.speed = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachMoveSpeed.Value, 0f, 20f);
				val2.acceleration = Mathf.Max(val2.speed * 4f, 8f);
				val2.angularSpeed = 720f;
				val2.stoppingDistance = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachStopDistance.Value, 0f, 10f);
				val2.Warp(sampledPosition);
				ApproachAgentCleanup approachAgentCleanup = ((Component)thinMan).gameObject.GetComponent<ApproachAgentCleanup>();
				if ((Object)(object)approachAgentCleanup == (Object)null)
				{
					approachAgentCleanup = ((Component)thinMan).gameObject.AddComponent<ApproachAgentCleanup>();
				}
				approachAgentCleanup.AgentObject = val;
				state.ApproachAgentObject = val;
				state.ApproachAgent = val2;
				return val2;
			}
			catch
			{
				return null;
			}
		}

		private static void ResetApproachAgentPosition(EnemyThinMan thinMan)
		{
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0090: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null)
			{
				return;
			}
			RuntimeState state = GetState(thinMan);
			if ((Object)(object)state.ApproachAgent == (Object)null || !TrySampleNavMeshPosition(GetEnemyPosition(thinMan), 8f, out var sampledPosition))
			{
				return;
			}
			try
			{
				((Behaviour)state.ApproachAgent).enabled = true;
				state.ApproachAgent.Warp(sampledPosition);
				state.ApproachAgent.ResetPath();
				state.ApproachAgent.isStopped = true;
				state.NextDestinationRefreshTime = 0f;
				state.LastApproachDestination = Vector3.zero;
			}
			catch
			{
			}
		}

		private static Vector3 GetApproachMoveDirection(EnemyThinMan thinMan, NavMeshAgent agent, Vector3 targetNavPosition)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			//IL_0009: Unknown result type (might be due to invalid IL or missing references)
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_006a: Unknown result type (might be due to invalid IL or missing references)
			//IL_006e: Unknown result type (might be due to invalid IL or missing references)
			//IL_006f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0070: Unknown result type (might be due to invalid IL or missing references)
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			//IL_009b: Unknown result type (might be due to invalid IL or missing references)
			//IL_009c: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cc: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0032: Unknown result type (might be due to invalid IL or missing references)
			//IL_00db: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			//IL_003f: Unknown result type (might be due to invalid IL or missing references)
			//IL_005c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0061: Unknown result type (might be due to invalid IL or missing references)
			Vector3 enemyPosition = GetEnemyPosition(thinMan);
			Vector3 val = targetNavPosition;
			try
			{
				if ((Object)(object)agent != (Object)null && ((Behaviour)agent).enabled && agent.isOnNavMesh)
				{
					val = agent.steeringTarget;
					if (val == Vector3.zero || Vector3.Distance(val, enemyPosition) < 0.1f)
					{
						val = ((Component)agent).transform.position;
					}
				}
			}
			catch
			{
				val = targetNavPosition;
			}
			Vector3 val2 = val - enemyPosition;
			val2.y = 0f;
			if (((Vector3)(ref val2)).sqrMagnitude <= 0.0001f)
			{
				val2 = targetNavPosition - enemyPosition;
				val2.y = 0f;
			}
			if (((Vector3)(ref val2)).sqrMagnitude <= 0.0001f)
			{
				return Vector3.zero;
			}
			return ((Vector3)(ref val2)).normalized;
		}

		private static bool UpdateApproachStuckState(RuntimeState state, Vector3 currentPosition, float targetDistanceSqr, float stopDistance)
		{
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_0045: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dd: Unknown result type (might be due to invalid IL or missing references)
			if (state == null)
			{
				return false;
			}
			if (state.LastApproachBodyPosition == Vector3.zero)
			{
				state.LastApproachBodyPosition = currentPosition;
				state.ApproachStuckSeconds = 0f;
				return false;
			}
			float horizontalDistanceSqr = GetHorizontalDistanceSqr(currentPosition, state.LastApproachBodyPosition);
			float num = 0.0036f;
			float num2 = Mathf.Max(stopDistance + 0.5f, 0.75f);
			if (targetDistanceSqr > num2 * num2 && horizontalDistanceSqr <= num)
			{
				state.ApproachStuckSeconds += Time.deltaTime;
			}
			else
			{
				state.ApproachStuckSeconds = 0f;
				state.LastApproachBodyPosition = currentPosition;
			}
			if (state.ApproachStuckSeconds >= 0.3f)
			{
				state.ApproachAssistUntilTime = Mathf.Max(state.ApproachAssistUntilTime, Time.time + 1.1f);
				state.LastApproachBodyPosition = currentPosition;
				state.ApproachStuckSeconds = 0f;
				return true;
			}
			return Time.time <= state.ApproachAssistUntilTime;
		}

		private static bool ShouldRetargetApproachTarget(RuntimeState state, Vector3 currentPosition, float targetDistanceSqr, float stopDistance)
		{
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0064: Unknown result type (might be due to invalid IL or missing references)
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0051: Unknown result type (might be due to invalid IL or missing references)
			//IL_008f: 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_0076: Unknown result type (might be due to invalid IL or missing references)
			//IL_0077: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ed: 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_0113: Unknown result type (might be due to invalid IL or missing references)
			//IL_0114: Unknown result type (might be due to invalid IL or missing references)
			if (state == null)
			{
				return false;
			}
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachStuckRetargetSeconds.Value, 0f, 30f);
			if (num <= 0f)
			{
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachRetargetReferencePosition = Vector3.zero;
				return false;
			}
			if (state.ApproachRetargetReferencePosition == Vector3.zero)
			{
				state.ApproachRetargetReferencePosition = currentPosition;
				state.ApproachRetargetStuckSeconds = 0f;
				return false;
			}
			float horizontalDistanceSqr = GetHorizontalDistanceSqr(currentPosition, state.ApproachRetargetReferencePosition);
			float num2 = 0.0036f;
			float num3 = Mathf.Max(stopDistance + 0.5f, 0.75f);
			if (targetDistanceSqr > num3 * num3 && horizontalDistanceSqr <= num2)
			{
				state.ApproachRetargetStuckSeconds += Time.deltaTime;
			}
			else
			{
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachRetargetReferencePosition = currentPosition;
			}
			if (state.ApproachRetargetStuckSeconds >= num)
			{
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachRetargetReferencePosition = currentPosition;
				return true;
			}
			return false;
		}

		private static bool RetargetApproachIfStuck(EnemyThinMan thinMan, RuntimeState state, PlayerAvatar currentTarget, Vector3 currentPosition, float targetDistanceSqr, float stopDistance)
		{
			//IL_0032: Unknown result type (might be due to invalid IL or missing references)
			//IL_0084: Unknown result type (might be due to invalid IL or missing references)
			//IL_0089: Unknown result type (might be due to invalid IL or missing references)
			//IL_008f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00aa: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || state == null || (Object)(object)currentTarget == (Object)null || (Object)(object)currentTarget.photonView == (Object)null)
			{
				return false;
			}
			if (!ShouldRetargetApproachTarget(state, currentPosition, targetDistanceSqr, stopDistance))
			{
				return false;
			}
			int viewID = currentTarget.photonView.ViewID;
			PlayerAvatar val = SelectFarthestApproachTarget(thinMan, viewID, allowExcluded: false);
			state.ApproachStuckSeconds = 0f;
			state.ApproachRetargetStuckSeconds = 0f;
			state.ApproachAssistUntilTime = 0f;
			state.LastApproachBodyPosition = Vector3.zero;
			state.ApproachRetargetReferencePosition = Vector3.zero;
			state.NextDestinationRefreshTime = 0f;
			state.LastApproachDestination = Vector3.zero;
			if ((Object)(object)val != (Object)null && (Object)(object)val.photonView != (Object)null)
			{
				state.ApproachTargetViewId = val.photonView.ViewID;
			}
			else
			{
				state.ApproachTargetViewId = -1;
			}
			StopApproachAgent(state);
			return true;
		}

		private static Vector3 GetClampedFollowTarget(Vector3 currentPosition, Vector3 desiredPosition, Vector3 moveDirection)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Unknown result type (might be due to invalid IL or missing references)
			//IL_003d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Unknown result type (might be due to invalid IL or missing references)
			//IL_004d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0050: Unknown result type (might be due to invalid IL or missing references)
			//IL_005b: Unknown result type (might be due to invalid IL or missing references)
			//IL_005c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0037: Unknown result type (might be due to invalid IL or missing references)
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_0060: Unknown result type (might be due to invalid IL or missing references)
			Vector3 val = desiredPosition - currentPosition;
			Vector3 val2 = default(Vector3);
			((Vector3)(ref val2))..ctor(val.x, 0f, val.z);
			if (((Vector3)(ref val2)).magnitude <= 2.5f)
			{
				return desiredPosition;
			}
			Vector3 result = currentPosition + moveDirection * 2.5f;
			result.y = desiredPosition.y;
			return result;
		}

		private static void ApplyForceMovementAssist(EnemyThinMan thinMan, NavMeshAgent agent, Vector3 targetNavPosition, Vector3 moveDirection, bool forceAssist)
		{
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0123: Unknown result type (might be due to invalid IL or missing references)
			//IL_0124: 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_012e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0144: Unknown result type (might be due to invalid IL or missing references)
			//IL_0152: Unknown result type (might be due to invalid IL or missing references)
			//IL_0157: Unknown result type (might be due to invalid IL or missing references)
			//IL_015c: Unknown result type (might be due to invalid IL or missing references)
			//IL_016a: Unknown result type (might be due to invalid IL or missing references)
			//IL_016f: 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_0187: 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_0223: Unknown result type (might be due to invalid IL or missing references)
			//IL_0225: Unknown result type (might be due to invalid IL or missing references)
			//IL_022a: Unknown result type (might be due to invalid IL or missing references)
			//IL_022e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0233: Unknown result type (might be due to invalid IL or missing references)
			//IL_0235: Unknown result type (might be due to invalid IL or missing references)
			//IL_0237: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e7: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f7: Unknown result type (might be due to invalid IL or missing references)
			//IL_0213: Unknown result type (might be due to invalid IL or missing references)
			//IL_021a: Unknown result type (might be due to invalid IL or missing references)
			//IL_021f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0248: Unknown result type (might be due to invalid IL or missing references)
			//IL_0249: Unknown result type (might be due to invalid IL or missing references)
			//IL_0262: Unknown result type (might be due to invalid IL or missing references)
			//IL_0266: Unknown result type (might be due to invalid IL or missing references)
			//IL_02c6: Unknown result type (might be due to invalid IL or missing references)
			//IL_02cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_02d8: Unknown result type (might be due to invalid IL or missing references)
			//IL_02dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_02e2: Unknown result type (might be due to invalid IL or missing references)
			//IL_02e6: Unknown result type (might be due to invalid IL or missing references)
			//IL_02eb: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f8: Unknown result type (might be due to invalid IL or missing references)
			//IL_02fd: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ff: Unknown result type (might be due to invalid IL or missing references)
			//IL_0304: Unknown result type (might be due to invalid IL or missing references)
			//IL_030c: Unknown result type (might be due to invalid IL or missing references)
			//IL_031f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0299: Unknown result type (might be due to invalid IL or missing references)
			//IL_029a: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a4: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ae: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b2: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b9: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || moveDirection == Vector3.zero)
			{
				return;
			}
			Enemy enemy = GetEnemy(thinMan);
			if ((Object)(object)enemy == (Object)null || (Object)(object)enemy.Rigidbody == (Object)null)
			{
				return;
			}
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachMoveSpeed.Value, 0f, 20f);
			float num2 = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachForceAssist.Value, 0f, 80f);
			float num3 = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachTiltAngle.Value, 0f, 60f);
			if (!ShadowChildEnhancementsPlugin.CfgApproachForceThroughObstacles.Value)
			{
				num2 = 0f;
				num3 = Mathf.Min(num3, 8f);
			}
			try
			{
				enemy.Rigidbody.OverrideFollowPosition(0.25f, Mathf.Max(num, 1f), 80f);
				enemy.Rigidbody.OverrideFollowPositionGravityDisable(0.25f);
				enemy.Rigidbody.OverrideFollowRotation(0.25f, forceAssist ? 8f : 20f);
			}
			catch
			{
			}
			try
			{
				Quaternion val = Quaternion.LookRotation(moveDirection, Vector3.up);
				float num4 = (forceAssist ? num3 : Mathf.Min(num3, 10f));
				Quaternion val2 = val * Quaternion.Euler(num4, 0f, 0f);
				((Component)thinMan).transform.rotation = Quaternion.Slerp(((Component)thinMan).transform.rotation, val2, Time.deltaTime * (forceAssist ? 10f : 5f));
			}
			catch
			{
			}
			if (num2 <= 0f || (Object)(object)thinMan.rb == (Object)null || thinMan.rb.isKinematic)
			{
				return;
			}
			try
			{
				Vector3 val3 = Vector3.zero;
				if ((Object)(object)agent != (Object)null)
				{
					float num5 = Mathf.Clamp(((Component)agent).transform.position.y - thinMan.rb.position.y, -0.4f, 0.6f);
					val3 = Vector3.up * num5;
				}
				Vector3 val4 = moveDirection + val3;
				Vector3 val5 = ((Vector3)(ref val4)).normalized;
				if (val5 == Vector3.zero)
				{
					val5 = moveDirection;
				}
				float num6 = (forceAssist ? num2 : (num2 * 0.35f));
				thinMan.rb.AddForce(val5 * num6, (ForceMode)5);
				if (forceAssist)
				{
					float num7 = Mathf.Clamp(num2 * 0.015f, 0.04f, 0.35f);
					Rigidbody rb = thinMan.rb;
					val4 = moveDirection + Vector3.up * 0.08f;
					rb.AddForce(((Vector3)(ref val4)).normalized * num7, (ForceMode)2);
				}
				val4 = Vector3.up - moveDirection * Mathf.Clamp01(num3 / 60f);
				Vector3 normalized = ((Vector3)(ref val4)).normalized;
				Vector3 val6 = Vector3.Cross(((Component)thinMan.rb).transform.up, normalized);
				thinMan.rb.AddTorque(val6 * Mathf.Max(num2 * 0.5f, 1f), (ForceMode)5);
			}
			catch
			{
			}
		}

		private static void ApplyApproachMovement(EnemyThinMan thinMan, PlayerAvatar targetPlayer)
		{
			//IL_00f8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d9: Unknown result type (might be due to invalid IL or missing references)
			//IL_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_016b: Unknown result type (might be due to invalid IL or missing references)
			//IL_018d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0230: Unknown result type (might be due to invalid IL or missing references)
			//IL_0236: Invalid comparison between Unknown and I4
			//IL_020c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0215: Unknown result type (might be due to invalid IL or missing references)
			//IL_0216: Unknown result type (might be due to invalid IL or missing references)
			//IL_024d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0252: Unknown result type (might be due to invalid IL or missing references)
			//IL_0257: Unknown result type (might be due to invalid IL or missing references)
			//IL_0258: Unknown result type (might be due to invalid IL or missing references)
			//IL_025d: Unknown result type (might be due to invalid IL or missing references)
			//IL_025f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0261: Unknown result type (might be due to invalid IL or missing references)
			//IL_0279: Unknown result type (might be due to invalid IL or missing references)
			//IL_027b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0287: Unknown result type (might be due to invalid IL or missing references)
			//IL_028c: Unknown result type (might be due to invalid IL or missing references)
			//IL_02cd: Unknown result type (might be due to invalid IL or missing references)
			//IL_02dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ee: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f7: Unknown result type (might be due to invalid IL or missing references)
			//IL_02fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_02fe: Unknown result type (might be due to invalid IL or missing references)
			//IL_0303: Unknown result type (might be due to invalid IL or missing references)
			//IL_030e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0325: Unknown result type (might be due to invalid IL or missing references)
			//IL_0326: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_02c2: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)thinMan == (Object)null || !IsAttackable(targetPlayer))
			{
				return;
			}
			if (ShouldPauseApproachForWatchedState(thinMan))
			{
				ClearApproachState(thinMan);
				return;
			}
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachMoveSpeed.Value, 0f, 20f);
			if (num <= 0f)
			{
				return;
			}
			float num2 = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgApproachStopDistance.Value, 0f, 10f);
			float targetDistanceSqr = GetTargetDistanceSqr(thinMan, targetPlayer);
			if (targetDistanceSqr <= num2 * num2)
			{
				RuntimeState state = GetState(thinMan);
				state.ApproachTargetViewId = -1;
				state.NextDestinationRefreshTime = 0f;
				state.ApproachStuckSeconds = 0f;
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachRetargetReferencePosition = Vector3.zero;
				state.ApproachAssistUntilTime = 0f;
				StopApproachAgent(state);
			}
			else
			{
				if (!TrySampleNavMeshPosition(GetPlayerCenter(targetPlayer), 8f, out var sampledPosition))
				{
					return;
				}
				RuntimeState state2 = GetState(thinMan);
				NavMeshAgent orCreateApproachAgent = GetOrCreateApproachAgent(thinMan);
				if ((Object)(object)orCreateApproachAgent == (Object)null)
				{
					return;
				}
				try
				{
					if (!((Behaviour)orCreateApproachAgent).enabled)
					{
						((Behaviour)orCreateApproachAgent).enabled = true;
					}
					if (!orCreateApproachAgent.isOnNavMesh)
					{
						if (!TrySampleNavMeshPosition(GetEnemyPosition(thinMan), 8f, out var sampledPosition2))
						{
							return;
						}
						orCreateApproachAgent.Warp(sampledPosition2);
					}
					orCreateApproachAgent.isStopped = false;
					orCreateApproachAgent.speed = num;
					orCreateApproachAgent.acceleration = Mathf.Max(num * 4f, 8f);
					orCreateApproachAgent.stoppingDistance = num2;
					bool flag = Vector3.Distance(state2.LastApproachDestination, sampledPosition) > 0.75f;
					if (Time.time >= state2.NextDestinationRefreshTime || flag || !orCreateApproachAgent.hasPath)
					{
						orCreateApproachAgent.SetDestination(sampledPosition);
						state2.LastApproachDestination = sampledPosition;
						state2.NextDestinationRefreshTime = Time.time + 0.2f;
					}
					if ((int)orCreateApproachAgent.pathStatus == 2)
					{
						StopApproachAgent(state2);
						return;
					}
					Vector3 enemyPosition = GetEnemyPosition(thinMan);
					Vector3 approachMoveDirection = GetApproachMoveDirection(thinMan, orCreateApproachAgent, sampledPosition);
					if (!(approachMoveDirection == Vector3.zero))
					{
						state2.LastApproachMoveDirection = approachMoveDirection;
						if (Vector3.Distance(((Component)orCreateApproachAgent).transform.position, enemyPosition) > 6f && TrySampleNavMeshPosition(enemyPosition, 8f, out var sampledPosition3))
						{
							orCreateApproachAgent.Warp(sampledPosition3);
							orCreateApproachAgent.SetDestination(sampledPosition);
						}
						bool forceAssist = UpdateApproachStuckState(state2, enemyPosition, targetDistanceSqr, num2);
						if (!RetargetApproachIfStuck(thinMan, state2, targetPlayer, enemyPosition, targetDistanceSqr, num2))
						{
							Vector3 clampedFollowTarget = GetClampedFollowTarget(enemyPosition, ((Component)orCreateApproachAgent).transform.position, approachMoveDirection);
							SetTeleporting(thinMan, value: false);
							SetTeleportPosition(thinMan, clampedFollowTarget);
							SetTeleportRoamTimer(thinMan, 0.5f);
							ApplyForceMovementAssist(thinMan, orCreateApproachAgent, sampledPosition, approachMoveDirection, forceAssist);
						}
					}
				}
				catch
				{
				}
			}
		}

		[HarmonyPatch(typeof(EnemyThinMan), "OnSpawn")]
		[HarmonyPostfix]
		private static void EnemyThinMan_OnSpawn_Postfix(EnemyThinMan __instance)
		{
			//IL_005b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0060: Unknown result type (might be due to invalid IL or missing references)
			//IL_0066: Unknown result type (might be due to invalid IL or missing references)
			//IL_006b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			//IL_0076: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0081: Unknown result type (might be due to invalid IL or missing references)
			if (!((Object)(object)__instance == (Object)null))
			{
				RuntimeState state = GetState(__instance);
				state.LastOnScreenTime = -99999f;
				state.AccumulatedViewIds.Clear();
				state.ActiveVictimViewIds.Clear();
				state.NearbyApproachViewIds.Clear();
				state.ApproachTargetViewId = -1;
				state.NextDestinationRefreshTime = 0f;
				state.LastApproachDestination = Vector3.zero;
				state.LastApproachBodyPosition = Vector3.zero;
				state.LastApproachMoveDirection = Vector3.forward;
				state.ApproachRetargetReferencePosition = Vector3.zero;
				state.ApproachStuckSeconds = 0f;
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachAssistUntilTime = 0f;
				state.ActiveDamage = false;
				ResetApproachAgentPosition(__instance);
				TuneOnScreenComponent(__instance);
			}
		}

		[HarmonyPatch(typeof(EnemyThinMan), "Awake")]
		[HarmonyPostfix]
		private static void EnemyThinMan_Awake_Postfix(EnemyThinMan __instance)
		{
			if ((Object)(object)__instance == (Object)null)
			{
				return;
			}
			TuneOnScreenComponent(__instance);
			if (!IsMasterOrSingle() || HasConfigKey("ShadowChild", "EyeContactSeconds"))
			{
				return;
			}
			try
			{
				if (!((Object)(object)__instance.anim != (Object)null))
				{
					return;
				}
				float tentacleSpeed = __instance.anim.tentacleSpeed;
				if (tentacleSpeed > 0.0001f)
				{
					ShadowChildEnhancementsPlugin.CfgEyeContactSeconds.Value = Mathf.Clamp(1f / tentacleSpeed, 0f, 20f);
					if ((Object)(object)ShadowChildEnhancementsPlugin.Instance != (Object)null)
					{
						((BaseUnityPlugin)ShadowChildEnhancementsPlugin.Instance).Config.Save();
					}
				}
			}
			catch
			{
			}
		}

		[HarmonyPatch(typeof(EnemyThinMan), "StateStand")]
		[HarmonyPrefix]
		private static void EnemyThinMan_StateStand_Prefix(EnemyThinMan __instance)
		{
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_0018: Invalid comparison between Unknown and I4
			if (IsMasterOrSingle() && !((Object)(object)__instance == (Object)null) && (int)__instance.currentState <= 0)
			{
				Enemy enemy = GetEnemy(__instance);
				EnsureOnScreenPlayerKeys(GetOnScreen(enemy));
				if (ShouldPauseApproachForWatchedState(__instance))
				{
					ClearApproachState(__instance);
				}
				else if (HasAnyPlayerWithinApproachRadius(__instance))
				{
					SetTeleportRoamTimer(__instance, 0.5f);
				}
			}
		}

		[HarmonyPatch(typeof(EnemyThinMan), "StateStand")]
		[HarmonyPostfix]
		private static void EnemyThinMan_StateStand_Postfix(EnemyThinMan __instance)
		{
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0041: Invalid comparison between Unknown and I4
			if (!IsMasterOrSingle() || (Object)(object)__instance == (Object)null)
			{
				return;
			}
			List<PlayerAvatar> visiblePlayers = GetVisiblePlayers(__instance);
			if (visiblePlayers.Count > 0)
			{
				TrackVisiblePlayers(__instance, visiblePlayers);
			}
			if ((int)__instance.currentState > 0)
			{
				if (ShadowChildEnhancementsPlugin.CfgApproachOnlyWhenNotWatched.Value && visiblePlayers.Count > 0)
				{
					ClearApproachState(__instance);
				}
				return;
			}
			if (ShadowChildEnhancementsPlugin.CfgApproachOnlyWhenNotWatched.Value && visiblePlayers.Count > 0)
			{
				ClearApproachState(__instance);
				return;
			}
			PlayerAvatar val = UpdateApproachTarget(__instance);
			if ((Object)(object)val != (Object)null)
			{
				ApplyApproachMovement(__instance, val);
			}
		}

		[HarmonyPatch(typeof(EnemyThinMan), "StateOnScreen")]
		[HarmonyPrefix]
		private static bool EnemyThinMan_StateOnScreen_Prefix(EnemyThinMan __instance)
		{
			if (!IsMasterOrSingle() || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			TuneOnScreenComponent(__instance);
			Enemy enemy = GetEnemy(__instance);
			EnsureOnScreenPlayerKeys(GetOnScreen(enemy));
			List<PlayerAvatar> visiblePlayers = GetVisiblePlayers(__instance);
			if (visiblePlayers.Count > 0)
			{
				TrackVisiblePlayers(__instance, visiblePlayers);
				if (ShadowChildEnhancementsPlugin.CfgApproachOnlyWhenNotWatched.Value)
				{
					ClearApproachState(__instance);
				}
				PlayerAvatar target = GetTarget(__instance);
				if ((Object)(object)target == (Object)null || !ContainsPlayer(visiblePlayers, target))
				{
					SetTarget(__instance, visiblePlayers[0]);
				}
			}
			return true;
		}

		[HarmonyPatch(typeof(EnemyThinMan), "StateStunned")]
		[HarmonyPostfix]
		private static void EnemyThinMan_StateStunned_Postfix(EnemyThinMan __instance)
		{
			//IL_0065: Unknown result type (might be due to invalid IL or missing references)
			//IL_006a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0070: Unknown result type (might be due to invalid IL or missing references)
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0080: Unknown result type (might be due to invalid IL or missing references)
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			if (IsMasterOrSingle() && !((Object)(object)__instance == (Object)null))
			{
				RuntimeState state = GetState(__instance);
				state.LastOnScreenTime = -99999f;
				state.AccumulatedViewIds.Clear();
				state.ActiveVictimViewIds.Clear();
				state.NearbyApproachViewIds.Clear();
				state.ApproachTargetViewId = -1;
				state.NextDestinationRefreshTime = 0f;
				state.LastApproachDestination = Vector3.zero;
				state.LastApproachBodyPosition = Vector3.zero;
				state.LastApproachMoveDirection = Vector3.forward;
				state.ApproachRetargetReferencePosition = Vector3.zero;
				state.ApproachStuckSeconds = 0f;
				state.ApproachRetargetStuckSeconds = 0f;
				state.ApproachAssistUntilTime = 0f;
				state.ActiveDamage = false;
				StopApproachAgent(state);
				__instance.tentacleLerp = 0f;
				SetTarget(__instance, null);
			}
		}

		[HarmonyPatch(typeof(EnemyThinMan), "TentacleLogic")]
		[HarmonyPrefix]
		private static bool EnemyThinMan_TentacleLogic_Prefix(EnemyThinMan __instance)
		{
			//IL_00f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fb: Invalid comparison between Unknown and I4
			//IL_0154: Unknown result type (might be due to invalid IL or missing references)
			//IL_015a: Invalid comparison between Unknown and I4
			//IL_016a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0170: Invalid comparison between Unknown and I4
			//IL_018a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0190: Invalid comparison between Unknown and I4
			if (!IsMasterOrSingle())
			{
				return true;
			}
			if ((Object)(object)__instance == (Object)null)
			{
				return false;
			}
			RuntimeState state = GetState(__instance);
			List<PlayerAvatar> visiblePlayers = GetVisiblePlayers(__instance);
			bool flag = visiblePlayers.Count > 0;
			if (flag)
			{
				TrackVisiblePlayers(__instance, visiblePlayers);
				state.LastOnScreenTime = Time.time;
				PlayerAvatar target = GetTarget(__instance);
				if ((Object)(object)target == (Object)null || !ContainsPlayer(visiblePlayers, target))
				{
					SetTarget(__instance, visiblePlayers[0]);
				}
			}
			float num = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgEyeContactSeconds.Value, 0f, 20f);
			float num2 = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgLookAwayGraceSeconds.Value, 0f, 20f);
			float num3 = ((num <= 0.0001f) ? 9999f : (1f / num));
			float deltaTime = Time.deltaTime;
			float num4 = __instance.tentacleLerp;
			if ((int)__instance.currentState == 1)
			{
				if (flag)
				{
					num4 += num3 * deltaTime;
				}
				else
				{
					float num5 = Time.time - state.LastOnScreenTime;
					if (num5 > num2)
					{
						num4 -= num3 * 0.5f * 0f * deltaTime;
					}
				}
			}
			else if ((int)__instance.currentState != 3)
			{
				if ((int)__instance.currentState == 4)
				{
					num4 -= 10f * deltaTime;
				}
				else if ((int)__instance.currentState == 7)
				{
					num4 = 0f;
					state.AccumulatedViewIds.Clear();
					state.ActiveVictimViewIds.Clear();
					state.ActiveDamage = false;
					state.LastOnScreenTime = -99999f;
				}
				else
				{
					float num6 = Time.time - state.LastOnScreenTime;
					if (num6 > num2)
					{
						num4 -= num3 * 0.5f * 0f * deltaTime;
					}
				}
			}
			__instance.tentacleLerp = Mathf.Clamp(num4, 0f, 1f);
			return false;
		}

		[HarmonyPatch(typeof(EnemyThinMan), "StateDamage")]
		[HarmonyPrefix]
		private static bool EnemyThinMan_StateDamage_Prefix(EnemyThinMan __instance)
		{
			//IL_0123: Unknown result type (might be due to invalid IL or missing references)
			if (!IsMasterOrSingle())
			{
				return true;
			}
			if ((Object)(object)__instance == (Object)null)
			{
				return false;
			}
			RuntimeState state = GetState(__instance);
			if (GetStateImpulse(__instance))
			{
				PlayerAvatar target = GetTarget(__instance);
				List<PlayerAvatar> list = CollectVictims(__instance, target);
				if (list.Count == 0)
				{
					state.AccumulatedViewIds.Clear();
					ClearActiveVictims(__instance);
					SetTarget(__instance, null);
					UpdateState(__instance, (State)6);
					return false;
				}
				SetActiveVictims(__instance, list);
				SetStateTimer(__instance, 0.5f);
				SetStateImpulse(__instance, value: false);
				int damage = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgDamage.Value, 0, 100);
				Enemy enemy = GetEnemy(__instance);
				int enemyIndex = -1;
				if ((Object)(object)enemy != (Object)null)
				{
					try
					{
						enemyIndex = SemiFunc.EnemyGetIndex(enemy);
					}
					catch
					{
						enemyIndex = -1;
					}
				}
				for (int i = 0; i < list.Count; i++)
				{
					PlayerAvatar val = list[i];
					if (IsAttackable(val))
					{
						InvokeHurtOther(val, damage, ((Component)val).transform.position, enemyIndex);
					}
				}
			}
			float stunSeconds = Mathf.Clamp(ShadowChildEnhancementsPlugin.CfgStunSeconds.Value, 0.1f, 10f);
			List<PlayerAvatar> activeVictims = GetActiveVictims(__instance);
			for (int j = 0; j < activeVictims.Count; j++)
			{
				ApplyTumbleHold(activeVictims[j], stunSeconds);
			}
			float num = GetStateTimer(__instance) - Time.deltaTime;
			SetStateTimer(__instance, num);
			if (num <= 0f)
			{
				state.AccumulatedViewIds.Clear();
				ClearActiveVictims(__instance);
				SetTarget(__instance, null);
				UpdateState(__instance, (State)6);
			}
			return false;
		}

		[HarmonyPatch(typeof(EnemyThinMan), "StateDamageFixed")]
		[HarmonyPrefix]
		private static bool EnemyThinMan_StateDamageFixed_Prefix(EnemyThinMan __instance)
		{
			//IL_001f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0025: Invalid comparison between Unknown and I4
			if (!IsMasterOrSingle())
			{
				return true;
			}
			if ((Object)(object)__instance == (Object)null || (int)__instance.currentState != 5)
			{
				return false;
			}
			RuntimeState state = GetState(__instance);
			if (!state.ActiveDamage)
			{
				return false;
			}
			List<PlayerAvatar> activeVictims = GetActiveVictims(__instance);
			for (int i = 0; i < activeVictims.Count; i++)
			{
				PlayerAvatar val = activeVictims[i];
				if (IsAttackable(val))
				{
					ApplyPullForce(__instance, val);
				}
			}
			return false;
		}
	}
}