Decompiled source of ICantSwim v13.48.0

ICantSwim.dll

Decompiled 3 days ago
using System;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using UnityEngine;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: AssemblyTitle("ICantSwim")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("HP")]
[assembly: AssemblyProduct("ICantSwim")]
[assembly: AssemblyCopyright("Copyright © HP 2026")]
[assembly: AssemblyTrademark("")]
[assembly: ComVisible(false)]
[assembly: Guid("7cbc919b-f1b1-4cdd-a1ba-e50b02f458ae")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: TargetFramework(".NETFramework,Version=v4.8.1", FrameworkDisplayName = "")]
[assembly: AssemblyVersion("1.0.0.0")]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)]
	internal sealed class NullableAttribute : Attribute
	{
		public readonly byte[] NullableFlags;

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

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

		public NullableContextAttribute(byte P_0)
		{
			Flag = P_0;
		}
	}
	[CompilerGenerated]
	[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 ICantSwim
{
	[BepInPlugin("YouDied.ICantSwim", "I Can't Swim", "13.48.0")]
	[BepInProcess("valheim.exe")]
	public class ICantSwimPlugin : BaseUnityPlugin
	{
		public const string PluginGUID = "YouDied.ICantSwim";

		public const string PluginName = "I Can't Swim";

		public const string PluginVersion = "13.48.0";

		internal static ManualLogSource Log;

		public static ConfigEntry<bool> ModEnabled;

		public static ConfigEntry<string> ToggleKey;

		public static ConfigEntry<int> WalkSpeed;

		public static ConfigEntry<int> RunSpeed;

		public static ConfigEntry<bool> EasterEgg;

		private readonly Harmony _harmony = new Harmony("YouDied.ICantSwim");

		private void Awake()
		{
			//IL_0072: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Expected O, but got Unknown
			//IL_00a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ad: Expected O, but got Unknown
			Log = ((BaseUnityPlugin)this).Logger;
			ModEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "Enabled", true, "Enable the mod.");
			ToggleKey = ((BaseUnityPlugin)this).Config.Bind<string>("General", "ToggleKey", "E", "Key to toggle water walking (E, F, G, etc).");
			WalkSpeed = ((BaseUnityPlugin)this).Config.Bind<int>("Movement", "WalkSpeed", 1, new ConfigDescription("Water walk speed multiplier (1 = normal, max 5).", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 5), Array.Empty<object>()));
			RunSpeed = ((BaseUnityPlugin)this).Config.Bind<int>("Movement", "RunSpeed", 1, new ConfigDescription("Water run speed multiplier (1 = normal, max 5).", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 5), Array.Empty<object>()));
			EasterEgg = ((BaseUnityPlugin)this).Config.Bind<bool>("Secret", "RisingAnimation", false, "Enable the rising-from-water transition animation (secret easter egg).");
			if (ModEnabled.Value)
			{
				_harmony.PatchAll(typeof(Patches));
				Log.LogInfo((object)"I Can't Swim 13.48.0 loaded.");
			}
		}

		private void OnDestroy()
		{
			_harmony.UnpatchSelf();
		}
	}
	internal static class S
	{
		public static bool WalkOnWater = false;

		public static bool Active = false;

		public static float WaterSurfaceY = 30f;

		public static float WaterSurfaceSmooth = 0f;

		public static bool WaterSurfaceValid = false;

		public static bool IsJumping = false;

		public static float JumpTimer = 0f;

		public static bool JumpPressed = false;

		public static bool JumpHeld = false;

		public static bool Ready = false;

		public static float ReadyTimer = 0f;

		public static float DeactivateCooldown = 0f;

		public static bool OverWater = false;

		public static float LogTimer = 0f;

		public const float LogInterval = 1f;

		public static bool IsRising = false;

		public static float RiseTimer = 0f;

		public static float RiseFromY = 0f;

		public static float RiseToY = 0f;

		public static void Reset()
		{
			WalkOnWater = false;
			Active = false;
			WaterSurfaceY = 30f;
			WaterSurfaceValid = false;
			IsJumping = false;
			JumpTimer = 0f;
			JumpPressed = false;
			JumpHeld = false;
			Ready = false;
			ReadyTimer = 0f;
			DeactivateCooldown = 0f;
			LogTimer = 0f;
			OverWater = false;
			WaterSurfaceSmooth = 0f;
			IsRising = false;
			RiseTimer = 0f;
			RiseFromY = 0f;
			RiseToY = 0f;
		}
	}
	internal static class F
	{
		internal static readonly FieldInfo waterLevel = AccessTools.Field(typeof(Character), "m_waterLevel");

		internal static readonly FieldInfo? liquidDepth = AccessTools.Field(typeof(Character), "m_cashedInLiquidDepth");

		internal static readonly FieldInfo swimTimer = AccessTools.Field(typeof(Character), "m_swimTimer");

		internal static readonly FieldInfo tolerateWater = AccessTools.Field(typeof(Character), "m_tolerateWater");

		internal static readonly FieldInfo body = AccessTools.Field(typeof(Character), "m_body");

		internal static readonly FieldInfo fallTimer = AccessTools.Field(typeof(Character), "m_fallTimer");

		internal static readonly FieldInfo groundContact = AccessTools.Field(typeof(Character), "m_groundContact");

		internal static readonly FieldInfo groundContactNormal = AccessTools.Field(typeof(Character), "m_groundContactNormal");

		internal static readonly FieldInfo groundContactPoint = AccessTools.Field(typeof(Character), "m_groundContactPoint");

		internal static readonly FieldInfo lastGroundNormal = AccessTools.Field(typeof(Character), "m_lastGroundNormal");

		internal static readonly FieldInfo lastGroundPoint = AccessTools.Field(typeof(Character), "m_lastGroundPoint");

		internal static readonly FieldInfo lastGroundTouch = AccessTools.Field(typeof(Character), "m_lastGroundTouch");

		internal static readonly FieldInfo maxAirAltitude = AccessTools.Field(typeof(Character), "m_maxAirAltitude");

		internal static readonly FieldInfo seWet = AccessTools.Field(typeof(SEMan), "s_statusEffectWet");

		internal static readonly FieldInfo seCold = AccessTools.Field(typeof(SEMan), "s_statusEffectCold");

		internal static readonly FieldInfo seFreezing = AccessTools.Field(typeof(SEMan), "s_statusEffectFreezing");

		internal static readonly FieldInfo semanCharacter = AccessTools.Field(typeof(SEMan), "m_character");

		internal static readonly FieldInfo seCharacter = AccessTools.Field(typeof(StatusEffect), "m_character");

		internal static MethodInfo? jumpMethod;

		internal static MethodInfo? resetGroundContact;

		internal static readonly FieldInfo? animField = AccessTools.Field(typeof(Character), "m_animator");

		internal static readonly FieldInfo? s_onGround = AccessTools.Field(typeof(Character), "s_onGround");

		internal static readonly FieldInfo? s_inWater = AccessTools.Field(typeof(Character), "s_inWater");

		internal static readonly FieldInfo? s_forwardSpeed = AccessTools.Field(typeof(Character), "s_forwardSpeed");

		internal static readonly FieldInfo? s_sidewaySpeed = AccessTools.Field(typeof(Character), "s_sidewaySpeed");

		internal static readonly FieldInfo? s_turnSpeed = AccessTools.Field(typeof(Character), "s_turnSpeed");

		internal static readonly FieldInfo? walkSpeed = AccessTools.Field(typeof(Character), "m_walkSpeed");

		internal static readonly FieldInfo? runSpeed = AccessTools.Field(typeof(Character), "m_runSpeed");

		internal static readonly FieldInfo? run = AccessTools.Field(typeof(Character), "m_run");

		internal static readonly FieldInfo? moveDir = AccessTools.Field(typeof(Character), "m_moveDir");

		internal static Rigidbody? Rb(Character c)
		{
			object? value = body.GetValue(c);
			return (Rigidbody?)((value is Rigidbody) ? value : null);
		}

		internal static void InjectGroundContact(Character c, Rigidbody rb, float waterY)
		{
			//IL_0041: Unknown result type (might be due to invalid IL or missing references)
			//IL_0053: Unknown result type (might be due to invalid IL or missing references)
			//IL_007a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0090: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b8: Unknown result type (might be due to invalid IL or missing references)
			if (resetGroundContact == null)
			{
				resetGroundContact = AccessTools.Method(typeof(Character), "ResetGroundContact", (Type[])null, (Type[])null);
			}
			resetGroundContact?.Invoke(c, null);
			Vector3 val = default(Vector3);
			((Vector3)(ref val))..ctor(rb.position.x, waterY - 0.05f, rb.position.z);
			groundContact.SetValue(c, true);
			groundContactNormal.SetValue(c, Vector3.up);
			groundContactPoint.SetValue(c, val);
			lastGroundNormal.SetValue(c, Vector3.up);
			lastGroundPoint.SetValue(c, val);
			lastGroundTouch.SetValue(c, 0f);
			maxAirAltitude.SetValue(c, -1000f);
			fallTimer.SetValue(c, 0f);
		}
	}
	public static class Patches
	{
		[HarmonyPatch(typeof(Player), "OnSpawned")]
		[HarmonyPostfix]
		public static void OnSpawned_Post(Player __instance)
		{
			if (!((Object)(object)__instance != (Object)(object)Player.m_localPlayer))
			{
				S.Reset();
				ICantSwimPlugin.Log.LogInfo((object)"[ICantSwim] Spawned — state reset.");
			}
		}

		[HarmonyPatch(typeof(Player), "Update")]
		[HarmonyPostfix]
		public static void Player_Update(Player __instance)
		{
			//IL_00c6: Unknown result type (might be due to invalid IL or missing references)
			//IL_0140: Unknown result type (might be due to invalid IL or missing references)
			//IL_0210: 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_031d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0381: Unknown result type (might be due to invalid IL or missing references)
			//IL_0339: Unknown result type (might be due to invalid IL or missing references)
			//IL_034a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0354: 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_02f9: 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)
			if ((Object)(object)__instance != (Object)(object)Player.m_localPlayer)
			{
				return;
			}
			if (!S.Ready)
			{
				S.ReadyTimer += Time.deltaTime;
				if (S.ReadyTimer >= 2f)
				{
					S.Ready = true;
					ICantSwimPlugin.Log.LogInfo((object)"[ICantSwim] Ready.");
				}
				return;
			}
			bool flag = ((Object)(object)Chat.instance != (Object)null && Chat.instance.HasFocus()) || Console.IsVisible() || Minimap.IsOpen() || InventoryGui.IsVisible() || StoreGui.IsVisible() || Menu.IsVisible();
			bool flag2 = false;
			if (!flag && Enum.TryParse<KeyCode>(ICantSwimPlugin.ToggleKey.Value, ignoreCase: true, out KeyCode result))
			{
				flag2 = ZInput.GetKeyDown(result, true);
			}
			if (!flag)
			{
				flag2 |= ZInput.GetKeyDown((KeyCode)330, true);
			}
			if (flag2 && (Object)(object)((Humanoid)__instance).GetHoverObject() == (Object)null && (!((Object)(object)Chat.instance != (Object)null) || !Chat.instance.HasFocus()) && !Console.IsVisible())
			{
				bool flag3 = !S.WalkOnWater;
				if (flag3 && S.WaterSurfaceValid && ((Component)__instance).transform.position.y > S.WaterSurfaceY + 10f)
				{
					MessageHud instance = MessageHud.instance;
					if (instance != null)
					{
						instance.ShowMessage((MessageType)1, "Can't water walk from up here!", 0, (Sprite)null, false);
					}
					return;
				}
				S.WalkOnWater = flag3;
				string text = (S.WalkOnWater ? "Water Walking enabled" : "Water Walking disabled");
				ICantSwimPlugin.Log.LogInfo((object)("[ICantSwim] Toggle -> " + (S.WalkOnWater ? "WALK" : "SWIM")));
				MessageHud instance2 = MessageHud.instance;
				if (instance2 != null)
				{
					instance2.ShowMessage((MessageType)1, text, 0, (Sprite)null, false);
				}
				if (S.WalkOnWater && S.WaterSurfaceValid)
				{
					Rigidbody val = F.Rb((Character)(object)__instance);
					if ((Object)(object)val != (Object)null)
					{
						float y = val.position.y;
						float groundBelow = GetGroundBelow(((Component)__instance).transform.position, S.WaterSurfaceY - 1f);
						bool flag4 = S.WaterSurfaceY > groundBelow + 0.3f;
						bool flag5 = y < S.WaterSurfaceY - 0.2f;
						if (ICantSwimPlugin.EasterEgg.Value && flag4 && flag5)
						{
							S.IsRising = true;
							S.RiseTimer = 0f;
							S.RiseFromY = y;
							S.RiseToY = S.WaterSurfaceY;
							ICantSwimPlugin.Log.LogInfo((object)$"[ICantSwim] Rising armed: from y={y:F2} to wl={S.WaterSurfaceY:F2}");
							if ((Object)(object)ZNetScene.instance != (Object)null)
							{
								GameObject prefab = ZNetScene.instance.GetPrefab("vfx_player_spawn");
								if ((Object)(object)prefab != (Object)null)
								{
									Object.Instantiate<GameObject>(prefab, ((Component)__instance).transform.position, Quaternion.identity);
								}
							}
							val.linearVelocity = Vector3.zero;
						}
						else
						{
							if (val.position.y < S.WaterSurfaceY)
							{
								val.position = new Vector3(val.position.x, S.WaterSurfaceY, val.position.z);
								ICantSwimPlugin.Log.LogInfo((object)$"[ICantSwim] Snapped to surface y={S.WaterSurfaceY:F2}");
							}
							val.linearVelocity = Vector3.zero;
						}
					}
				}
			}
			bool flag6 = Input.GetKeyDown((KeyCode)32) || ZInput.GetButtonDown("jump") || ZInput.GetButtonDown("JoyJump");
			S.JumpHeld = Input.GetKey((KeyCode)32) || ZInput.GetButton("jump") || ZInput.GetButton("JoyJump");
			if (flag6 && S.Active && !S.IsJumping)
			{
				S.JumpPressed = true;
			}
			if (!S.JumpHeld)
			{
				S.JumpPressed = false;
			}
		}

		[HarmonyPatch(typeof(Character), "ApplyGroundForce")]
		[HarmonyPrefix]
		public static bool ApplyGroundForce_Pre(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			return !S.Active;
		}

		[HarmonyPatch(typeof(Character), "ApplySlide")]
		[HarmonyPrefix]
		public static bool ApplySlide_Pre(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			return !S.Active;
		}

		[HarmonyPatch(typeof(Character), "UnderWorldCheck")]
		[HarmonyPrefix]
		public static bool UnderWorldCheck_Pre(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			return !S.Active;
		}

		[HarmonyPatch(typeof(Character), "UpdateGroundContact")]
		[HarmonyPostfix]
		public static void UpdateGroundContact_Post(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val != null && !((Object)(object)val != (Object)(object)Player.m_localPlayer) && S.Active && !S.IsJumping)
			{
				Rigidbody val2 = F.Rb(__instance);
				if (!((Object)(object)val2 == (Object)null))
				{
					F.InjectGroundContact(__instance, val2, S.WaterSurfaceY);
				}
			}
		}

		[HarmonyPatch(typeof(Character), "UpdateMotion")]
		[HarmonyPrefix]
		public static bool UpdateMotion_Pre(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			return !S.Active;
		}

		[HarmonyPatch(typeof(Character), "UpdateWalking")]
		[HarmonyPrefix]
		public static bool UpdateWalking_Pre(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			if (!S.Active)
			{
				return true;
			}
			if (S.IsJumping)
			{
				return false;
			}
			F.liquidDepth?.SetValue(__instance, 0f);
			F.tolerateWater.SetValue(__instance, true);
			return true;
		}

		[HarmonyPatch(typeof(Character), "CustomFixedUpdate")]
		[HarmonyPostfix]
		public static void FixedUpdate_Post(Character __instance)
		{
			//IL_08cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_08e5: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ec: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f1: 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_0306: Unknown result type (might be due to invalid IL or missing references)
			//IL_030b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0332: Unknown result type (might be due to invalid IL or missing references)
			//IL_0926: Unknown result type (might be due to invalid IL or missing references)
			//IL_0209: Unknown result type (might be due to invalid IL or missing references)
			//IL_09bc: Unknown result type (might be due to invalid IL or missing references)
			//IL_09c9: Unknown result type (might be due to invalid IL or missing references)
			//IL_09d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_09df: Unknown result type (might be due to invalid IL or missing references)
			//IL_09e4: Unknown result type (might be due to invalid IL or missing references)
			//IL_04b1: Unknown result type (might be due to invalid IL or missing references)
			//IL_04c1: Unknown result type (might be due to invalid IL or missing references)
			//IL_04cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_04d7: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a1a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a11: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a16: Unknown result type (might be due to invalid IL or missing references)
			//IL_05e1: Unknown result type (might be due to invalid IL or missing references)
			//IL_05d8: Unknown result type (might be due to invalid IL or missing references)
			//IL_05dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a23: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a21: Unknown result type (might be due to invalid IL or missing references)
			//IL_05ea: Unknown result type (might be due to invalid IL or missing references)
			//IL_05e8: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b42: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b65: Unknown result type (might be due to invalid IL or missing references)
			//IL_0733: Unknown result type (might be due to invalid IL or missing references)
			//IL_0604: Unknown result type (might be due to invalid IL or missing references)
			//IL_0610: Unknown result type (might be due to invalid IL or missing references)
			//IL_0617: Unknown result type (might be due to invalid IL or missing references)
			//IL_061c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0620: Unknown result type (might be due to invalid IL or missing references)
			//IL_0625: Unknown result type (might be due to invalid IL or missing references)
			//IL_0627: Unknown result type (might be due to invalid IL or missing references)
			//IL_0629: Unknown result type (might be due to invalid IL or missing references)
			//IL_062e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0633: Unknown result type (might be due to invalid IL or missing references)
			//IL_0637: Unknown result type (might be due to invalid IL or missing references)
			//IL_063c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0649: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b88: 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_077a: Unknown result type (might be due to invalid IL or missing references)
			//IL_07b2: Unknown result type (might be due to invalid IL or missing references)
			//IL_07bf: Unknown result type (might be due to invalid IL or missing references)
			//IL_07c9: Unknown result type (might be due to invalid IL or missing references)
			//IL_0bb8: Unknown result type (might be due to invalid IL or missing references)
			//IL_0bbf: Unknown result type (might be due to invalid IL or missing references)
			//IL_0bc6: Unknown result type (might be due to invalid IL or missing references)
			//IL_0bcb: Unknown result type (might be due to invalid IL or missing references)
			//IL_07fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_07f3: Unknown result type (might be due to invalid IL or missing references)
			//IL_07f8: Unknown result type (might be due to invalid IL or missing references)
			//IL_06ae: Unknown result type (might be due to invalid IL or missing references)
			//IL_06b3: Unknown result type (might be due to invalid IL or missing references)
			//IL_06b7: Unknown result type (might be due to invalid IL or missing references)
			//IL_06be: Unknown result type (might be due to invalid IL or missing references)
			//IL_06e2: Unknown result type (might be due to invalid IL or missing references)
			//IL_06e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_070c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0ddd: Unknown result type (might be due to invalid IL or missing references)
			//IL_0de2: Unknown result type (might be due to invalid IL or missing references)
			//IL_0805: Unknown result type (might be due to invalid IL or missing references)
			//IL_0803: Unknown result type (might be due to invalid IL or missing references)
			//IL_0a9c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0aa3: Unknown result type (might be due to invalid IL or missing references)
			//IL_0ac7: Unknown result type (might be due to invalid IL or missing references)
			//IL_0ace: Unknown result type (might be due to invalid IL or missing references)
			//IL_0af0: Unknown result type (might be due to invalid IL or missing references)
			//IL_0afc: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b03: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b08: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b0c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b11: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b15: 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_0b1c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b21: Unknown result type (might be due to invalid IL or missing references)
			//IL_0b31: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e0c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e03: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e08: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e15: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e2c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e4d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e5c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e6b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e7a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0e13: Unknown result type (might be due to invalid IL or missing references)
			//IL_0876: Unknown result type (might be due to invalid IL or missing references)
			//IL_0885: Unknown result type (might be due to invalid IL or missing references)
			//IL_088f: Unknown result type (might be due to invalid IL or missing references)
			//IL_086f: Unknown result type (might be due to invalid IL or missing references)
			//IL_08a5: Unknown result type (might be due to invalid IL or missing references)
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer || !S.Ready)
			{
				return;
			}
			Rigidbody val2 = F.Rb(__instance);
			if ((Object)(object)val2 == (Object)null)
			{
				return;
			}
			if (S.DeactivateCooldown > 0f)
			{
				S.DeactivateCooldown -= Time.fixedDeltaTime;
			}
			float num2 = ((F.waterLevel.GetValue(__instance) is float num) ? num : S.WaterSurfaceY);
			if (num2 > 20f && num2 < 40f)
			{
				S.WaterSurfaceY = num2;
				S.WaterSurfaceValid = true;
				if (S.WaterSurfaceSmooth < 20f)
				{
					S.WaterSurfaceSmooth = num2;
				}
				S.WaterSurfaceSmooth = Mathf.Lerp(S.WaterSurfaceSmooth, num2, 0.12f);
			}
			if (!S.WalkOnWater || !S.WaterSurfaceValid || S.DeactivateCooldown > 0f)
			{
				if (S.Active)
				{
					Deactivate(__instance, val2, "preference off");
				}
				return;
			}
			if (!S.Active)
			{
				S.Active = true;
				ICantSwimPlugin.Log.LogInfo((object)$"[ICantSwim] Active. wl={S.WaterSurfaceY:F2}");
			}
			if (S.JumpPressed && !S.IsJumping)
			{
				S.JumpPressed = false;
				S.IsJumping = true;
				S.JumpTimer = 0f;
				val2.useGravity = true;
				if (F.jumpMethod == null)
				{
					F.jumpMethod = AccessTools.Method(typeof(Character), "Jump", new Type[1] { typeof(bool) }, (Type[])null);
				}
				F.jumpMethod?.Invoke(__instance, new object[1] { true });
				ICantSwimPlugin.Log.LogInfo((object)$"[ICantSwim] Jump! vel.y={val2.linearVelocity.y:F2}");
				return;
			}
			if (S.IsRising)
			{
				S.RiseTimer += Time.fixedDeltaTime;
				float num3 = Mathf.Clamp01(S.RiseTimer / 2f);
				if (S.RiseTimer < 0.1f)
				{
					ICantSwimPlugin.Log.LogInfo((object)$"[ICantSwim] Rise tick: timer={S.RiseTimer:F3} t={num3:F3} fromY={S.RiseFromY:F2} toY={S.RiseToY:F2}");
				}
				float num4 = 1f - (1f - num3) * (1f - num3);
				float y = Mathf.Lerp(S.RiseFromY, S.RiseToY, num4);
				val2.useGravity = false;
				Vector3 position = val2.position;
				position.y = y;
				val2.position = position;
				Vector3 linearVelocity = val2.linearVelocity;
				linearVelocity.x = 0f;
				linearVelocity.z = 0f;
				linearVelocity.y = 0f;
				val2.linearVelocity = linearVelocity;
				object? obj = F.animField?.GetValue(__instance);
				Animator val3 = (Animator)((obj is Animator) ? obj : null);
				if (val3 != null)
				{
					if (F.s_forwardSpeed?.GetValue(null) is int num5)
					{
						val3.SetFloat(num5, 0f);
					}
					if (F.s_sidewaySpeed?.GetValue(null) is int num6)
					{
						val3.SetFloat(num6, 0f);
					}
					if (F.s_turnSpeed?.GetValue(null) is int num7)
					{
						val3.SetFloat(num7, 0f);
					}
					if (F.s_onGround?.GetValue(null) is int num8)
					{
						val3.SetBool(num8, false);
					}
					if (F.s_inWater?.GetValue(null) is int num9)
					{
						val3.SetBool(num9, false);
					}
				}
				if (num3 >= 1f)
				{
					S.IsRising = false;
					val2.position = new Vector3(val2.position.x, S.RiseToY, val2.position.z);
					val2.linearVelocity = Vector3.zero;
					ICantSwimPlugin.Log.LogInfo((object)$"[ICantSwim] Rise complete. t={num3:F3} timer={S.RiseTimer:F3}");
				}
				return;
			}
			Vector3 val7;
			if (S.IsJumping)
			{
				object? obj2 = F.animField?.GetValue(__instance);
				Animator val4 = (Animator)((obj2 is Animator) ? obj2 : null);
				if (val4 != null)
				{
					if (F.s_onGround?.GetValue(null) is int num10)
					{
						val4.SetBool(num10, false);
					}
					if (F.s_inWater?.GetValue(null) is int num11)
					{
						val4.SetBool(num11, false);
					}
				}
				Vector3 val6 = ((F.moveDir?.GetValue(__instance) is Vector3 val5) ? val5 : Vector3.zero);
				if (((Vector3)(ref val6)).sqrMagnitude > 0.01f)
				{
					val7 = new Vector3(val6.x, 0f, val6.z);
					Vector3 normalized = ((Vector3)(ref val7)).normalized;
					Quaternion val8 = Quaternion.LookRotation(normalized, Vector3.up);
					val2.rotation = Quaternion.RotateTowards(val2.rotation, val8, 300f * Time.fixedDeltaTime);
					object obj3 = F.run?.GetValue(__instance);
					bool flag = default(bool);
					int num12;
					if (obj3 is bool)
					{
						flag = (bool)obj3;
						num12 = 1;
					}
					else
					{
						num12 = 0;
					}
					float num13 = ((((uint)num12 & (flag ? 1u : 0u)) != 0) ? (7.5f * (float)ICantSwimPlugin.RunSpeed.Value) : (4.5f * (float)ICantSwimPlugin.WalkSpeed.Value));
					Vector3 linearVelocity2 = val2.linearVelocity;
					linearVelocity2.x = Mathf.MoveTowards(linearVelocity2.x, val6.x * num13, num13 * 8f * Time.fixedDeltaTime);
					linearVelocity2.z = Mathf.MoveTowards(linearVelocity2.z, val6.z * num13, num13 * 8f * Time.fixedDeltaTime);
					val2.linearVelocity = linearVelocity2;
				}
				S.JumpTimer += Time.fixedDeltaTime;
				val2.useGravity = true;
				float groundBelow = GetGroundBelow(((Component)__instance).transform.position, S.WaterSurfaceY - 1f);
				float num14 = Mathf.Max(S.WaterSurfaceY, groundBelow);
				if (S.JumpTimer >= 0.2f && val2.position.y <= num14 + 0.6f && val2.linearVelocity.y < -0.5f)
				{
					S.IsJumping = false;
					S.JumpTimer = 0f;
					val2.useGravity = false;
					val2.position = new Vector3(val2.position.x, num14, val2.position.z);
					Vector3 val10 = ((F.moveDir?.GetValue(__instance) is Vector3 val9) ? val9 : Vector3.zero);
					object obj3 = F.run?.GetValue(__instance);
					bool flag2 = default(bool);
					int num15;
					if (obj3 is bool)
					{
						flag2 = (bool)obj3;
						num15 = 1;
					}
					else
					{
						num15 = 0;
					}
					float num16 = ((((uint)num15 & (flag2 ? 1u : 0u)) != 0) ? (7.5f * (float)ICantSwimPlugin.RunSpeed.Value) : (4.5f * (float)ICantSwimPlugin.WalkSpeed.Value));
					val2.linearVelocity = (Vector3)((((Vector3)(ref val10)).sqrMagnitude > 0.01f) ? new Vector3(val10.x * num16, 0f, val10.z * num16) : Vector3.zero);
					ICantSwimPlugin.Log.LogInfo((object)$"[ICantSwim] Landed. rb.y={val2.position.y:F2}");
				}
				return;
			}
			float groundBelow2 = GetGroundBelow(((Component)__instance).transform.position, S.WaterSurfaceY - 1f);
			groundBelow2 = Mathf.Min(groundBelow2, val2.position.y + 0.1f);
			float num17 = Mathf.Max(S.WaterSurfaceY, groundBelow2);
			S.OverWater = S.WaterSurfaceY > groundBelow2 + 0.3f;
			if (S.Active && val2.position.y > S.WaterSurfaceY + 10f)
			{
				S.WalkOnWater = false;
				S.Active = false;
				S.IsJumping = false;
				S.JumpPressed = false;
				S.DeactivateCooldown = 0.3f;
				val2.useGravity = true;
				F.groundContact.SetValue(__instance, false);
				ICantSwimPlugin.Log.LogInfo((object)"[ICantSwim] Deactivated: too high above water");
				MessageHud instance = MessageHud.instance;
				if (instance != null)
				{
					instance.ShowMessage((MessageType)1, "Water Walking disabled", 0, (Sprite)null, false);
				}
				return;
			}
			val2.useGravity = false;
			val2.position = new Vector3(val2.position.x, num17, val2.position.z);
			Vector3 linearVelocity3 = val2.linearVelocity;
			linearVelocity3.y = 0f;
			Vector3 val12 = ((F.moveDir?.GetValue(__instance) is Vector3 val11) ? val11 : Vector3.zero);
			if (((Vector3)(ref val12)).sqrMagnitude > 0.01f)
			{
				object obj3 = F.run?.GetValue(__instance);
				bool flag3 = default(bool);
				int num18;
				if (obj3 is bool)
				{
					flag3 = (bool)obj3;
					num18 = 1;
				}
				else
				{
					num18 = 0;
				}
				bool flag4 = (byte)((uint)num18 & (flag3 ? 1u : 0u)) != 0;
				float num19 = (flag4 ? 7.5f : 4.5f) * (float)(flag4 ? ICantSwimPlugin.RunSpeed.Value : ICantSwimPlugin.WalkSpeed.Value);
				linearVelocity3.x = Mathf.MoveTowards(linearVelocity3.x, val12.x * num19, num19 * 40f * Time.fixedDeltaTime);
				linearVelocity3.z = Mathf.MoveTowards(linearVelocity3.z, val12.z * num19, num19 * 40f * Time.fixedDeltaTime);
				val7 = new Vector3(val12.x, 0f, val12.z);
				Vector3 normalized2 = ((Vector3)(ref val7)).normalized;
				val2.rotation = Quaternion.RotateTowards(val2.rotation, Quaternion.LookRotation(normalized2, Vector3.up), 300f * Time.fixedDeltaTime);
			}
			else
			{
				linearVelocity3.x = Mathf.MoveTowards(linearVelocity3.x, 0f, 25f * Time.fixedDeltaTime);
				linearVelocity3.z = Mathf.MoveTowards(linearVelocity3.z, 0f, 25f * Time.fixedDeltaTime);
			}
			val2.linearVelocity = linearVelocity3;
			object? obj4 = F.animField?.GetValue(__instance);
			Animator val13 = (Animator)((obj4 is Animator) ? obj4 : null);
			if (val13 != null)
			{
				Vector2 val14 = new Vector2(linearVelocity3.x, linearVelocity3.z);
				float magnitude = ((Vector2)(ref val14)).magnitude;
				object obj3 = F.run?.GetValue(__instance);
				bool flag5 = default(bool);
				int num20;
				if (obj3 is bool)
				{
					flag5 = (bool)obj3;
					num20 = 1;
				}
				else
				{
					num20 = 0;
				}
				float num21 = ((((uint)num20 & (flag5 ? 1u : 0u)) != 0) ? magnitude : ((magnitude > 0.1f) ? (magnitude * 0.6f) : 0f));
				if (F.s_forwardSpeed?.GetValue(null) is int num22)
				{
					val13.SetFloat(num22, num21);
				}
				if (F.s_sidewaySpeed?.GetValue(null) is int num23)
				{
					val13.SetFloat(num23, 0f);
				}
				if (F.s_turnSpeed?.GetValue(null) is int num24)
				{
					val13.SetFloat(num24, 0f);
				}
				if (F.s_onGround?.GetValue(null) is int num25)
				{
					val13.SetBool(num25, true);
				}
				if (F.s_inWater?.GetValue(null) is int num26)
				{
					val13.SetBool(num26, false);
				}
			}
			F.InjectGroundContact(__instance, val2, S.WaterSurfaceY);
			F.liquidDepth?.SetValue(__instance, 0f);
			F.tolerateWater.SetValue(__instance, true);
			F.swimTimer.SetValue(__instance, 0f);
			S.LogTimer -= Time.fixedDeltaTime;
			if (S.LogTimer <= 0f)
			{
				S.LogTimer = 1f;
				Vector3 linearVelocity4 = val2.linearVelocity;
				Vector3 val16 = ((F.moveDir?.GetValue(__instance) is Vector3 val15) ? val15 : Vector3.zero);
				ICantSwimPlugin.Log.LogInfo((object)($"[ICantSwim] wl={S.WaterSurfaceY:F2} rb.y={val2.position.y:F2} " + $"vel=({linearVelocity4.x:F2},{linearVelocity4.z:F2}) dir=({val16.x:F2},{val16.z:F2})"));
			}
		}

		private static float GetGroundBelow(Vector3 pos, float fallback)
		{
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0055: 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_006e: Unknown result type (might be due to invalid IL or missing references)
			Vector3 val = default(Vector3);
			((Vector3)(ref val))..ctor(pos.x, 700f, pos.z);
			int mask = LayerMask.GetMask(new string[6] { "terrain", "Default", "static_solid", "Default_small", "piece", "piece_nonsolid" });
			RaycastHit val2 = default(RaycastHit);
			if (Physics.Raycast(val, Vector3.down, ref val2, 750f, mask))
			{
				return ((RaycastHit)(ref val2)).point.y;
			}
			return fallback;
		}

		private static void Deactivate(Character c, Rigidbody rb, string reason)
		{
			S.Active = false;
			S.IsJumping = false;
			S.JumpPressed = false;
			S.DeactivateCooldown = 0.8f;
			rb.useGravity = true;
			F.groundContact.SetValue(c, false);
			ICantSwimPlugin.Log.LogInfo((object)("[ICantSwim] Deactivated: " + reason));
		}

		[HarmonyPatch(typeof(Character), "UpdateWater")]
		[HarmonyPrefix]
		public static bool UpdateWater_Pre(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			return !S.Active;
		}

		[HarmonyPatch(typeof(Character), "IsSwimming")]
		[HarmonyPostfix]
		public static void IsSwimming_Post(Character __instance, ref bool __result)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val != null && !((Object)(object)val != (Object)(object)Player.m_localPlayer) && S.Active)
			{
				__result = false;
			}
		}

		[HarmonyPatch(typeof(Character), "IsOnGround")]
		[HarmonyPostfix]
		public static void IsOnGround_Post(Character __instance, ref bool __result)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val != null && !((Object)(object)val != (Object)(object)Player.m_localPlayer) && S.Active && !S.IsJumping)
			{
				__result = true;
			}
		}

		[HarmonyPatch(typeof(Player), "OnSwimming")]
		[HarmonyPrefix]
		public static bool OnSwimming_Pre(Player __instance)
		{
			if ((Object)(object)__instance != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			return !S.Active;
		}

		[HarmonyPatch(typeof(Character), "UpdateSwimming")]
		[HarmonyPrefix]
		public static bool UpdateSwimming_Pre(Character __instance)
		{
			Player val = (Player)(object)((__instance is Player) ? __instance : null);
			if (val == null || (Object)(object)val != (Object)(object)Player.m_localPlayer)
			{
				return true;
			}
			return !S.Active;
		}

		[HarmonyPatch(typeof(SEMan), "AddStatusEffect", new Type[]
		{
			typeof(StatusEffect),
			typeof(bool),
			typeof(int),
			typeof(float)
		})]
		[HarmonyPrefix]
		public static bool AddSE_Object(SEMan __instance, StatusEffect statusEffect)
		{
			if (!S.WalkOnWater || (Object)(object)statusEffect == (Object)null)
			{
				return true;
			}
			object? value = F.seCharacter.GetValue(statusEffect);
			Character val = (Character)((value is Character) ? value : null);
			if (!((Object)(object)val == (Object)null))
			{
				Player val2 = (Player)(object)((val is Player) ? val : null);
				if (val2 != null && !((Object)(object)val2 != (Object)(object)Player.m_localPlayer))
				{
					return !(statusEffect is SE_Wet);
				}
			}
			return true;
		}

		[HarmonyPatch(typeof(SEMan), "AddStatusEffect", new Type[]
		{
			typeof(int),
			typeof(bool),
			typeof(int),
			typeof(float)
		})]
		[HarmonyPrefix]
		public static bool AddSE_Hash(SEMan __instance, int nameHash)
		{
			if (!S.WalkOnWater)
			{
				return true;
			}
			object? value = F.semanCharacter.GetValue(__instance);
			Character val = (Character)((value is Character) ? value : null);
			if (!((Object)(object)val == (Object)null))
			{
				Player val2 = (Player)(object)((val is Player) ? val : null);
				if (val2 != null && !((Object)(object)val2 != (Object)(object)Player.m_localPlayer))
				{
					int num = (int)F.seWet.GetValue(null);
					int num2 = (int)F.seCold.GetValue(null);
					int num3 = (int)F.seFreezing.GetValue(null);
					return nameHash != num && nameHash != num2 && nameHash != num3;
				}
			}
			return true;
		}
	}
}