Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of TumbleEscape v1.0.35
TumbleEscapeV5.dll
Decompiled 2 weeks agousing System; using System.Collections.Generic; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using BepInEx; using BepInEx.Configuration; 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: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("TumbleEscapeV5")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0")] [assembly: AssemblyProduct("TumbleEscapeV5")] [assembly: AssemblyTitle("TumbleEscapeV5")] [assembly: AssemblyVersion("1.0.0.0")] 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; } } } namespace TumbleEscape { [BepInPlugin("tumbleescape", "Tumble Escape", "1.1.0")] public class TumbleEscape : BaseUnityPlugin { private ConfigEntry<KeyboardShortcut> escapeKey = null; private ConfigEntry<bool> releaseGrabbersAsHost = null; private ConfigEntry<float> pulseInterval = null; private ConfigEntry<bool> enableDebugLogs = null; private PlayerTumble? localTumble; private float nextPulseTime; private bool loggedThisHold; private void Awake() { //IL_0019: Unknown result type (might be due to invalid IL or missing references) escapeKey = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("Controls", "Escape Key", new KeyboardShortcut((KeyCode)122, Array.Empty<KeyCode>()), "Hold this key to request a tumble escape."); releaseGrabbersAsHost = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "Release Grabbers As Host", true, "When host or in singleplayer, ask grabbers holding your tumble body to release."); pulseInterval = ((BaseUnityPlugin)this).Config.Bind<float>("General", "Pulse Interval", 0.08f, "Seconds between escape requests while holding the key."); enableDebugLogs = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "Debug Logs", false, "Enable debug logs."); ((BaseUnityPlugin)this).Logger.LogInfo((object)"Tumble Escape loaded"); } private void Update() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0057: Unknown result type (might be due to invalid IL or missing references) KeyboardShortcut value = escapeKey.Value; if (!((KeyboardShortcut)(ref value)).IsPressed()) { loggedThisHold = false; nextPulseTime = 0f; return; } PlayerTumble val = GetLocalTumble(); if ((Object)(object)val == (Object)null) { return; } value = escapeKey.Value; bool flag = ((KeyboardShortcut)(ref value)).IsDown(); if (flag || !(Time.time < nextPulseTime)) { nextPulseTime = Time.time + Mathf.Clamp(pulseInterval.Value, 0.05f, 0.5f); ApplyEscape(val, flag); if (!loggedThisHold) { LogDebug("Tumble escape active"); loggedThisHold = true; } } } private PlayerTumble? GetLocalTumble() { PlayerAvatar instance = PlayerAvatar.instance; if ((Object)(object)instance == (Object)null) { return null; } if ((Object)(object)localTumble != (Object)null && (Object)(object)localTumble.playerAvatar == (Object)(object)instance) { return localTumble; } localTumble = null; PlayerTumble[] array = Object.FindObjectsOfType<PlayerTumble>(); foreach (PlayerTumble val in array) { if (!((Object)(object)val == (Object)null) && !((Object)(object)val.playerAvatar != (Object)(object)instance)) { localTumble = val; return localTumble; } } return null; } private void ApplyEscape(PlayerTumble tumble, bool firstPulse) { PhysGrabObject component = ((Component)tumble).GetComponent<PhysGrabObject>(); bool flag = (Object)(object)component != (Object)null && component.playerGrabbing != null && component.playerGrabbing.Count > 0; if (releaseGrabbersAsHost.Value && flag && SemiFunc.IsMasterClientOrSingleplayer()) { ReleaseGrabbers(component); } if (firstPulse || flag) { ApplyBreakFreeNudge(tumble); } tumble.TumbleOverrideTime(0f); tumble.TumbleOverride(false); tumble.TumbleRequest(false, true); } private void ReleaseGrabbers(PhysGrabObject tumbleObject) { if (tumbleObject.playerGrabbing == null || tumbleObject.playerGrabbing.Count == 0) { return; } List<PhysGrabber> list = new List<PhysGrabber>(tumbleObject.playerGrabbing); foreach (PhysGrabber item in list) { if (!((Object)(object)item == (Object)null)) { try { item.OverridePullDistanceIncrement(-1.5f); item.OverrideGrabRelease(-1, 0.35f); } catch (Exception ex) { LogDebug("Could not request grab release: " + ex.Message); } } } } private void ApplyBreakFreeNudge(PlayerTumble tumble) { //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_005d: Unknown result type (might be due to invalid IL or missing references) //IL_0063: Unknown result type (might be due to invalid IL or missing references) //IL_0068: Unknown result type (might be due to invalid IL or missing references) //IL_0072: 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_0089: Unknown result type (might be due to invalid IL or missing references) //IL_0093: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Unknown result type (might be due to invalid IL or missing references) //IL_005a: Unknown result type (might be due to invalid IL or missing references) PlayerAvatar instance = PlayerAvatar.instance; if (!((Object)(object)instance == (Object)null)) { Vector3 forward = ((Component)instance).transform.forward; if ((Object)(object)instance.localCamera != (Object)null && (Object)(object)instance.localCamera.GetOverrideTransform() != (Object)null) { forward = instance.localCamera.GetOverrideTransform().forward; } tumble.TumbleForce(forward * 8f + Vector3.up * 2f); tumble.TumbleTorque(((Component)tumble).transform.right * 8f); } } private void LogDebug(string message) { if (enableDebugLogs.Value) { ((BaseUnityPlugin)this).Logger.LogInfo((object)message); } } } }