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 Multigrasp v1.0.1
Multigrasp.dll
Decompiled 10 hours agousing System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using HarmonyLib; using Microsoft.CodeAnalysis; using TMPro; using UnityEngine; using UnityEngine.UI; [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("Multigrasp")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+beb441afe3bfba81768632e6b8c827ea6dc0490f")] [assembly: AssemblyProduct("Multigrasp")] [assembly: AssemblyTitle("Multigrasp")] [assembly: AssemblyVersion("1.0.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Multigrasp { internal sealed class BeamRenderer { private static readonly Color VanillaOrangeStart = new Color(1f, 0.1856f, 0f, 0.95f); private static readonly Color VanillaOrangeEnd = new Color(1f, 0.1856f, 0f, 0.65f); private readonly string _name; private GameObject _beamObject; private LineRenderer _beam; private Material _ownedMaterial; private float _textureOffset; internal BeamRenderer(string name) { _name = name; } internal void Tick(PhysGrabber primary, Transform fallbackCamera, Vector3 end) { //IL_000f: Unknown result type (might be due to invalid IL or missing references) //IL_001a: Expected O, but got Unknown //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_0029: 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_002c: Unknown result type (might be due to invalid IL or missing references) Ensure(primary); if (!((Object)_beam == (Object)null)) { Vector3 beamStart = GetBeamStart(primary, fallbackCamera); Draw(beamStart, end); } } private void Draw(Vector3 start, Vector3 end) { //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_0009: Unknown result type (might be due to invalid IL or missing references) //IL_000a: Unknown result type (might be due to invalid IL or missing references) //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_0015: 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_0035: 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_00f4: Expected O, but got Unknown //IL_008b: Unknown result type (might be due to invalid IL or missing references) //IL_008c: Unknown result type (might be due to invalid IL or missing references) //IL_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_0096: Unknown result type (might be due to invalid IL or missing references) //IL_0097: Unknown result type (might be due to invalid IL or missing references) //IL_009a: Unknown result type (might be due to invalid IL or missing references) //IL_009f: Unknown result type (might be due to invalid IL or missing references) //IL_00a8: Unknown result type (might be due to invalid IL or missing references) //IL_00aa: Unknown result type (might be due to invalid IL or missing references) //IL_00ae: Unknown result type (might be due to invalid IL or missing references) //IL_011f: Unknown result type (might be due to invalid IL or missing references) float num = Vector3.Distance(start, end); Vector3 val = Vector3.Lerp(start, end, 0.5f) + Vector3.down * Mathf.Min(0.45f, num * 0.06f); _beamObject.SetActive(true); ((Renderer)_beam).enabled = true; _beam.positionCount = 16; for (int i = 0; i < _beam.positionCount; i++) { float num2 = ((_beam.positionCount <= 1) ? 1f : ((float)i / (float)(_beam.positionCount - 1))); Vector3 val2 = Vector3.Lerp(start, val, num2); Vector3 val3 = Vector3.Lerp(val, end, num2); _beam.SetPosition(i, Vector3.Lerp(val2, val3, num2)); } Material val4 = _ownedMaterial ?? ((Renderer)_beam).material; if ((Object)val4 != (Object)null) { _textureOffset -= Time.deltaTime * 2.5f; val4.mainTextureOffset = new Vector2(_textureOffset, 0f); } } internal void Destroy() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown //IL_002f: Unknown result type (might be due to invalid IL or missing references) //IL_003a: Expected O, but got Unknown //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0027: Expected O, but got Unknown //IL_0045: Unknown result type (might be due to invalid IL or missing references) //IL_004f: Expected O, but got Unknown if ((Object)_beamObject != (Object)null) { Object.Destroy((Object)_beamObject); } if ((Object)_ownedMaterial != (Object)null) { Object.Destroy((Object)_ownedMaterial); } _beamObject = null; _beam = null; _ownedMaterial = null; } private void Ensure(PhysGrabber primary) { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Expected O, but got Unknown //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_004b: Expected O, but got Unknown //IL_0051: Unknown result type (might be due to invalid IL or missing references) //IL_005b: Expected O, but got Unknown if (!((Object)_beamObject != (Object)null) || !((Object)_beam != (Object)null)) { Destroy(); _beamObject = new GameObject(_name); Object.DontDestroyOnLoad((Object)_beamObject); _beamObject.SetActive(true); _beam = _beamObject.AddComponent<LineRenderer>(); _beam.useWorldSpace = true; _beam.positionCount = 16; _beam.numCapVertices = 4; _beam.numCornerVertices = 4; ApplyVanillaLikeStyle(primary); ((Renderer)_beam).enabled = false; } } private void ApplyVanillaLikeStyle(PhysGrabber primary) { //IL_0009: Unknown result type (might be due to invalid IL or missing references) //IL_0014: Expected O, but got Unknown //IL_00bb: Unknown result type (might be due to invalid IL or missing references) //IL_00c6: Expected O, but got Unknown //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_002d: Expected O, but got Unknown //IL_0039: Unknown result type (might be due to invalid IL or missing references) //IL_0043: Expected O, but got Unknown //IL_00e9: Unknown result type (might be due to invalid IL or missing references) //IL_00f4: Expected O, but got Unknown //IL_00fe: Unknown result type (might be due to invalid IL or missing references) //IL_0108: Expected O, but got Unknown //IL_0191: Unknown result type (might be due to invalid IL or missing references) //IL_01a2: Unknown result type (might be due to invalid IL or missing references) //IL_01b3: Unknown result type (might be due to invalid IL or missing references) //IL_01be: Expected O, but got Unknown //IL_01e7: 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) LineRenderer sourceLine = GetSourceLine(primary); if ((Object)sourceLine != (Object)null) { if ((Object)((Renderer)sourceLine).sharedMaterial != (Object)null) { SetOwnedMaterial(new Material(((Renderer)sourceLine).sharedMaterial)); } if (sourceLine.startWidth > 0.001f && sourceLine.startWidth < 0.25f) { _beam.startWidth = sourceLine.startWidth; _beam.endWidth = ((sourceLine.endWidth > 0.001f && sourceLine.endWidth < 0.25f) ? sourceLine.endWidth : (sourceLine.startWidth * 0.55f)); } } if ((Object)_ownedMaterial == (Object)null) { Shader val = Shader.Find("Sprites/Default") ?? Shader.Find("Legacy Shaders/Particles/Additive"); if ((Object)val != (Object)null) { SetOwnedMaterial(new Material(val)); } } if (_beam.startWidth <= 0.001f || _beam.startWidth > 0.25f) { _beam.startWidth = 0.035f; } if (_beam.endWidth <= 0.001f || _beam.endWidth > 0.25f) { _beam.endWidth = 0.018f; } _beam.startColor = VanillaOrangeStart; _beam.endColor = VanillaOrangeEnd; if ((Object)_ownedMaterial != (Object)null) { if (_ownedMaterial.HasProperty("_Color")) { _ownedMaterial.SetColor("_Color", VanillaOrangeStart); } if (_ownedMaterial.HasProperty("_EmissionColor")) { _ownedMaterial.SetColor("_EmissionColor", VanillaOrangeStart); } _beam.textureMode = (LineTextureMode)1; } } private void SetOwnedMaterial(Material material) { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_002a: Expected O, but got Unknown //IL_002a: Expected O, but got Unknown //IL_0051: Unknown result type (might be due to invalid IL or missing references) //IL_005c: Expected O, but got Unknown //IL_0038: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Expected O, but got Unknown if ((Object)_ownedMaterial != (Object)null && (Object)_ownedMaterial != (Object)material) { Object.Destroy((Object)_ownedMaterial); } _ownedMaterial = material; if ((Object)_beam != (Object)null) { ((Renderer)_beam).sharedMaterial = _ownedMaterial; } } private static LineRenderer GetSourceLine(PhysGrabber primary) { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Expected O, but got Unknown if ((Object)(primary?.physGrabBeam) == (Object)null) { return null; } return primary.physGrabBeam.GetComponent<LineRenderer>() ?? primary.physGrabBeam.GetComponentInChildren<LineRenderer>(); } private static Vector3 GetBeamStart(PhysGrabber primary, Transform fallbackCamera) { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Expected O, but got Unknown //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_00e2: 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_004e: Expected O, but got Unknown //IL_007d: Unknown result type (might be due to invalid IL or missing references) //IL_0088: Expected O, but got Unknown //IL_0090: Unknown result type (might be due to invalid IL or missing references) //IL_0095: Unknown result type (might be due to invalid IL or missing references) //IL_00a4: Unknown result type (might be due to invalid IL or missing references) //IL_00af: Expected O, but got Unknown //IL_00c5: Unknown result type (might be due to invalid IL or missing references) //IL_00d0: Expected O, but got Unknown //IL_00bc: Unknown result type (might be due to invalid IL or missing references) //IL_00c1: Unknown result type (might be due to invalid IL or missing references) //IL_00da: 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_00df: Unknown result type (might be due to invalid IL or missing references) Transform val = primary?.physGrabBeamComponent?.PhysGrabPointOrigin; if ((Object)val != (Object)null) { return val.position; } PhysGrabBeam val2 = (((Object)(primary?.physGrabBeam) != (Object)null) ? primary.physGrabBeam.GetComponent<PhysGrabBeam>() : null); val = val2?.PhysGrabPointOrigin ?? val2?.PhysGrabPointOriginLocal; if ((Object)val != (Object)null) { return val.position; } if ((Object)(primary?.physGrabPoint) != (Object)null) { return primary.physGrabPoint.position; } return ((Object)fallbackCamera != (Object)null) ? fallbackCamera.position : Vector3.zero; } } internal static class HudNotifier { private const float VisibleSeconds = 2f; private static readonly Vector2 HiddenPosition = new Vector2(24f, -36f); private static readonly Vector2 VisiblePosition = new Vector2(24f, 80f); private static GameObject _canvasObject; private static TextMeshProUGUI _text; private static float _hideAt; private static float _showStartedAt; internal static void Show(string message, Color color) { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Expected O, but got Unknown //IL_004d: 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) try { EnsureOverlay(); if ((Object)_text == (Object)null) { MultigraspPlugin.LogWarning("HUD unavailable for message: " + message); return; } _canvasObject.SetActive(true); ((TMP_Text)_text).text = message; ((Graphic)_text).color = color; ((Behaviour)_text).enabled = true; ((TMP_Text)_text).rectTransform.anchoredPosition = HiddenPosition; _showStartedAt = Time.unscaledTime; _hideAt = Time.unscaledTime + 2f; } catch (Exception ex) { MultigraspPlugin.LogError("HUD message failed", ex); } } internal static void Tick() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Expected O, but got Unknown //IL_005e: Unknown result type (might be due to invalid IL or missing references) //IL_0063: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Unknown result type (might be due to invalid IL or missing references) if (!((Object)_text == (Object)null) && ((Behaviour)_text).enabled) { float num = Mathf.Clamp01((Time.unscaledTime - _showStartedAt) / 0.28f); num = 1f - Mathf.Pow(1f - num, 3f); ((TMP_Text)_text).rectTransform.anchoredPosition = Vector2.LerpUnclamped(HiddenPosition, VisiblePosition, num); if (Time.unscaledTime >= _hideAt) { ((Behaviour)_text).enabled = false; } } } internal static void DestroyOwnedObjects() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Expected O, but got Unknown //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Expected O, but got Unknown if ((Object)_canvasObject != (Object)null) { Object.Destroy((Object)_canvasObject); } _canvasObject = null; _text = null; } private static void EnsureOverlay() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Expected O, but got Unknown //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_0023: Expected O, but got Unknown //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Expected O, but got Unknown //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Expected O, but got Unknown //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_0083: Expected O, but got Unknown //IL_00c1: 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_00e2: Expected O, but got Unknown //IL_015a: Unknown result type (might be due to invalid IL or missing references) //IL_0167: Unknown result type (might be due to invalid IL or missing references) //IL_0174: Unknown result type (might be due to invalid IL or missing references) //IL_0181: Unknown result type (might be due to invalid IL or missing references) //IL_0198: 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_0057: Expected O, but got Unknown if (!((Object)_canvasObject != (Object)null) || !((Object)_text != (Object)null)) { if ((Object)_canvasObject != (Object)null) { Object.Destroy((Object)_canvasObject); } _canvasObject = null; _text = null; _canvasObject = new GameObject("Multigrasp HUD"); Object.DontDestroyOnLoad((Object)_canvasObject); Canvas val = _canvasObject.AddComponent<Canvas>(); val.renderMode = (RenderMode)0; val.sortingOrder = 32760; CanvasScaler val2 = _canvasObject.AddComponent<CanvasScaler>(); val2.uiScaleMode = (ScaleMode)1; val2.referenceResolution = new Vector2(1920f, 1080f); _canvasObject.AddComponent<GraphicRaycaster>(); GameObject val3 = new GameObject("Multigrasp HUD Text"); val3.transform.SetParent(_canvasObject.transform, false); _text = val3.AddComponent<TextMeshProUGUI>(); ((TMP_Text)_text).fontSize = 28f; ((TMP_Text)_text).alignment = (TextAlignmentOptions)513; ((Graphic)_text).raycastTarget = false; ((TMP_Text)_text).text = string.Empty; ((Behaviour)_text).enabled = false; RectTransform rectTransform = ((TMP_Text)_text).rectTransform; rectTransform.anchorMin = Vector2.zero; rectTransform.anchorMax = Vector2.zero; rectTransform.pivot = Vector2.zero; rectTransform.anchoredPosition = HiddenPosition; rectTransform.sizeDelta = new Vector2(700f, 80f); } } } internal sealed class MultigraspManager : MonoBehaviour { internal sealed class PendingAnchorData { internal readonly PhysGrabObject PhysGrabObject; internal readonly Rigidbody Body; internal readonly Transform TargetTransform; internal readonly Vector3 LocalGrabPosition; internal readonly Vector3 PlayerLocalBodyPosition; internal readonly Quaternion PlayerLocalBodyRotation; internal bool IsValid => (Object)PhysGrabObject != (Object)null && (Object)Body != (Object)null && (Object)TargetTransform != (Object)null && ((Behaviour)PhysGrabObject).enabled && !PhysGrabObject.dead && !Body.isKinematic && ((Component)Body).gameObject.activeInHierarchy; internal PendingAnchorData(PhysGrabObject physGrabObject, Rigidbody body, Transform targetTransform, Vector3 localGrabPosition, Vector3 playerLocalBodyPosition, Quaternion playerLocalBodyRotation) { //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_002e: 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) PhysGrabObject = physGrabObject; Body = body; TargetTransform = targetTransform; LocalGrabPosition = localGrabPosition; PlayerLocalBodyPosition = playerLocalBodyPosition; PlayerLocalBodyRotation = playerLocalBodyRotation; } } private sealed class Anchor { private const float MaxVelocityChange = 10f; private const float MaxAngularVelocityChange = 30f; private const float AnchoredMaxAngularVelocity = 50f; internal readonly PhysGrabObject PhysGrabObject; internal readonly Transform TargetTransform; private readonly Rigidbody _body; private readonly Vector3 _localGrabPosition; private readonly Vector3 _localBodyGrabPosition; private Vector3 _playerLocalBodyPosition; private Quaternion _playerLocalBodyRotation; private Vector3 _worldBodyPosition; private Quaternion _worldBodyRotation; private bool _followPlayer; private readonly float _originalMaxAngularVelocity; private readonly bool _changedMaxAngularVelocity; private readonly bool _originalDetectCollisions; private bool _changedDetectCollisions; private readonly BeamRenderer _beam; private bool _loggedGrabPause; internal bool IsValid => (Object)PhysGrabObject != (Object)null && (Object)_body != (Object)null && (Object)TargetTransform != (Object)null && ((Behaviour)PhysGrabObject).enabled && !PhysGrabObject.dead && !_body.isKinematic && ((Component)_body).gameObject.activeInHierarchy; internal string TargetName => ((Object)TargetTransform != (Object)null) ? ((Object)TargetTransform).name : "<missing>"; internal Anchor(PhysGrabObject physGrabObject, Rigidbody body, Transform targetTransform, Vector3 localGrabPosition, Vector3 playerLocalBodyPosition, Quaternion playerLocalBodyRotation, bool followPlayer, bool passthrough, string beamName) { //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_002d: Unknown result type (might be due to invalid IL or missing references) //IL_002f: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_0047: 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_0050: 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_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) PhysGrabObject = physGrabObject; _body = body; TargetTransform = targetTransform; _localGrabPosition = localGrabPosition; _localBodyGrabPosition = ((Component)body).transform.InverseTransformPoint(targetTransform.TransformPoint(localGrabPosition)); _playerLocalBodyPosition = playerLocalBodyPosition; _playerLocalBodyRotation = playerLocalBodyRotation; _worldBodyPosition = body.position; _worldBodyRotation = body.rotation; _followPlayer = followPlayer; _originalMaxAngularVelocity = body.maxAngularVelocity; _originalDetectCollisions = body.detectCollisions; if (IsFinite(_originalMaxAngularVelocity) && body.maxAngularVelocity < 50f) { body.maxAngularVelocity = 50f; _changedMaxAngularVelocity = true; } _beam = new BeamRenderer(beamName); MaintainHeldByLocalPlayer(); SetPassthroughMode(passthrough); } internal bool Matches(PhysGrabObject physGrabObject, Transform targetTransform) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_0033: Expected O, but got Unknown //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Expected O, but got Unknown //IL_0025: Expected O, but got Unknown //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_004b: Expected O, but got Unknown //IL_004b: Expected O, but got Unknown return ((Object)physGrabObject != (Object)null && (Object)PhysGrabObject == (Object)physGrabObject) || ((Object)targetTransform != (Object)null && (Object)TargetTransform == (Object)targetTransform); } internal bool SetFollowPlayer(bool followPlayer, Transform player) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_006d: 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_007e: 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_0032: 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_003c: 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_0053: Unknown result type (might be due to invalid IL or missing references) //IL_0058: 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) if ((Object)player == (Object)null || !IsValid) { return false; } if (followPlayer) { _playerLocalBodyPosition = player.InverseTransformPoint(_body.position); _playerLocalBodyRotation = Quaternion.Inverse(player.rotation) * _body.rotation; } else { _worldBodyPosition = _body.position; _worldBodyRotation = _body.rotation; } _followPlayer = followPlayer; return true; } internal bool TickBeam(PhysGrabber primary, Transform fallbackCamera, Transform player) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_0035: Unknown result type (might be due to invalid IL or missing references) if ((Object)player == (Object)null || !IsValid) { return false; } MaintainHeldByLocalPlayer(); _beam.Tick(primary, fallbackCamera, GetBeamEnd(player)); return true; } internal bool SetPassthroughMode(bool passthrough) { if (!IsValid) { return false; } if (passthrough) { if (_body.detectCollisions) { _body.detectCollisions = false; } _changedDetectCollisions = true; return true; } if (_changedDetectCollisions) { _body.detectCollisions = _originalDetectCollisions; _changedDetectCollisions = false; } return true; } private Vector3 GetBeamEnd(Transform player) { //IL_0014: Unknown result type (might be due to invalid IL or missing references) //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_002d: Unknown result type (might be due to invalid IL or missing references) //IL_00a7: 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_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0058: 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_004a: Unknown result type (might be due to invalid IL or missing references) //IL_0062: 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_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0092: Unknown result type (might be due to invalid IL or missing references) //IL_0093: Unknown result type (might be due to invalid IL or missing references) //IL_0095: Unknown result type (might be due to invalid IL or missing references) //IL_009a: Unknown result type (might be due to invalid IL or missing references) //IL_009f: Unknown result type (might be due to invalid IL or missing references) //IL_00a4: Unknown result type (might be due to invalid IL or missing references) //IL_0085: Unknown result type (might be due to invalid IL or missing references) //IL_008a: 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) if (IsGrabbedByBlockingPlayer(blockLocalActiveGrabber: false)) { return TargetTransform.TransformPoint(_localGrabPosition); } Vector3 val = (_followPlayer ? player.TransformPoint(_playerLocalBodyPosition) : _worldBodyPosition); Quaternion val2 = (_followPlayer ? (player.rotation * _playerLocalBodyRotation) : _worldBodyRotation); if (!IsFinite(val) || !IsFinite(val2)) { return TargetTransform.TransformPoint(_localGrabPosition); } return val + val2 * _localBodyGrabPosition; } internal bool ApplyForce(Transform player) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown if ((Object)player == (Object)null || !IsValid) { MultigraspPlugin.LogVerbose("Removing local anchor: invalid state target=" + TargetName); return false; } if (IsGrabbedByBlockingPlayer(blockLocalActiveGrabber: true)) { if (!_loggedGrabPause) { MultigraspPlugin.LogVerbose("Paused local anchor force while grabbed target=" + TargetName); _loggedGrabPause = true; } return true; } if (_loggedGrabPause) { MultigraspPlugin.LogVerbose("Resumed local anchor force target=" + TargetName); _loggedGrabPause = false; } MaintainHeldByLocalPlayer(); ApplyVelocityCorrection(player); return true; } private void ApplyVelocityCorrection(Transform player) { //IL_0039: 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_0030: 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_0044: 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_0058: 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_006a: 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_007c: Unknown result type (might be due to invalid IL or missing references) //IL_007e: Unknown result type (might be due to invalid IL or missing references) //IL_00d2: Unknown result type (might be due to invalid IL or missing references) //IL_00d8: Unknown result type (might be due to invalid IL or missing references) //IL_00dd: Unknown result type (might be due to invalid IL or missing references) //IL_00ca: Unknown result type (might be due to invalid IL or missing references) //IL_008c: Unknown result type (might be due to invalid IL or missing references) //IL_0093: Unknown result type (might be due to invalid IL or missing references) //IL_0098: Unknown result type (might be due to invalid IL or missing references) //IL_00e2: Unknown result type (might be due to invalid IL or missing references) //IL_00e3: Unknown result type (might be due to invalid IL or missing references) //IL_00b5: Unknown result type (might be due to invalid IL or missing references) //IL_00f3: Unknown result type (might be due to invalid IL or missing references) //IL_00fa: Unknown result type (might be due to invalid IL or missing references) //IL_00ff: Unknown result type (might be due to invalid IL or missing references) //IL_0104: Unknown result type (might be due to invalid IL or missing references) //IL_0109: Unknown result type (might be due to invalid IL or missing references) //IL_013b: Unknown result type (might be due to invalid IL or missing references) //IL_0164: Unknown result type (might be due to invalid IL or missing references) //IL_0170: Unknown result type (might be due to invalid IL or missing references) //IL_0175: Unknown result type (might be due to invalid IL or missing references) //IL_0177: Unknown result type (might be due to invalid IL or missing references) //IL_017f: Unknown result type (might be due to invalid IL or missing references) //IL_0184: Unknown result type (might be due to invalid IL or missing references) //IL_0189: Unknown result type (might be due to invalid IL or missing references) //IL_018b: Unknown result type (might be due to invalid IL or missing references) //IL_0199: Unknown result type (might be due to invalid IL or missing references) //IL_01a0: Unknown result type (might be due to invalid IL or missing references) //IL_01a5: Unknown result type (might be due to invalid IL or missing references) //IL_01c2: Unknown result type (might be due to invalid IL or missing references) float fixedDeltaTime = Time.fixedDeltaTime; if (!IsFinite(fixedDeltaTime) || fixedDeltaTime <= 0f) { return; } Vector3 val = (_followPlayer ? player.TransformPoint(_playerLocalBodyPosition) : _worldBodyPosition); if (IsFinite(val)) { Vector3 val2 = (val - _body.position) / fixedDeltaTime; Vector3 val3 = val2 - _body.velocity; if (IsFinite(val3)) { val3 = Vector3.ClampMagnitude(val3, 10f); if (((Vector3)(ref val3)).sqrMagnitude > 0.0001f) { _body.AddForce(val3, (ForceMode)2); } } } Quaternion val4 = (_followPlayer ? (player.rotation * _playerLocalBodyRotation) : _worldBodyRotation); if (!IsFinite(val4)) { return; } Quaternion val5 = val4 * Quaternion.Inverse(_body.rotation); float num = default(float); Vector3 val6 = default(Vector3); ((Quaternion)(ref val5)).ToAngleAxis(ref num, ref val6); if (num > 180f) { num -= 360f; } if (!IsFinite(num) || !IsFinite(val6) || !(((Vector3)(ref val6)).sqrMagnitude > 0.0001f)) { return; } ((Vector3)(ref val6)).Normalize(); Vector3 val7 = val6 * (num * (MathF.PI / 180f) / fixedDeltaTime); Vector3 val8 = val7 - _body.angularVelocity; if (IsFinite(val8)) { val8 = Vector3.ClampMagnitude(val8, 30f); if (((Vector3)(ref val8)).sqrMagnitude > 0.0001f) { _body.AddTorque(val8, (ForceMode)2); } } } internal void DestroyOwnedObjects() { RestoreDetectCollisions(); RestoreMaxAngularVelocity(); RestoreHeldByLocalPlayer(); _beam.Destroy(); } private void RestoreDetectCollisions() { //IL_000f: Unknown result type (might be due to invalid IL or missing references) //IL_001a: Expected O, but got Unknown if (_changedDetectCollisions && (Object)_body != (Object)null) { _body.detectCollisions = _originalDetectCollisions; _changedDetectCollisions = false; } } private void RestoreMaxAngularVelocity() { //IL_000f: Unknown result type (might be due to invalid IL or missing references) //IL_001a: Expected O, but got Unknown if (_changedMaxAngularVelocity && (Object)_body != (Object)null && IsFinite(_originalMaxAngularVelocity) && Mathf.Approximately(_body.maxAngularVelocity, 50f)) { _body.maxAngularVelocity = _originalMaxAngularVelocity; } } private void MaintainHeldByLocalPlayer() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown if ((Object)PhysGrabObject != (Object)null) { ReflectionCache.SetField(PhysGrabObject, "heldByLocalPlayer", value: true); } } private void RestoreHeldByLocalPlayer() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown if (!((Object)PhysGrabObject == (Object)null) && !IsVanillaCurrentLocalGrab(PhysGrabObject)) { ReflectionCache.SetField(PhysGrabObject, "heldByLocalPlayer", value: false); } } private bool IsGrabbedByBlockingPlayer(bool blockLocalActiveGrabber) { //IL_0063: Unknown result type (might be due to invalid IL or missing references) //IL_006e: Expected O, but got Unknown //IL_009c: Unknown result type (might be due to invalid IL or missing references) //IL_00a3: Expected O, but got Unknown //IL_00a5: Unknown result type (might be due to invalid IL or missing references) //IL_00b0: Expected O, but got Unknown object field = ReflectionCache.GetField<object>(PhysGrabObject, "playerGrabbing"); if (!(field is IEnumerable enumerable) || field is string) { return false; } foreach (object item in enumerable) { Object val = (Object)((item is Object) ? item : null); if (val != null) { if (val == (Object)null) { continue; } } else if (item == null) { continue; } PhysGrabber val2 = (PhysGrabber)((item is PhysGrabber) ? item : null); if ((Object)val2 != (Object)null) { if (IsActiveGrabberForObject(val2, PhysGrabObject)) { if (!IsLocalGrabEntry(val2)) { return true; } if (blockLocalActiveGrabber) { return true; } } } else { if (!IsLocalGrabEntry(item)) { return true; } if (blockLocalActiveGrabber) { return true; } } } return false; } private static bool IsActiveGrabberForObject(PhysGrabber grabber, PhysGrabObject physGrabObject) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_0023: Expected O, but got Unknown //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_004d: Expected O, but got Unknown //IL_004d: Expected O, but got Unknown //IL_0061: Unknown result type (might be due to invalid IL or missing references) //IL_006c: Expected O, but got Unknown //IL_008a: 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_009a: Expected O, but got Unknown //IL_009a: Expected O, but got Unknown if ((Object)grabber == (Object)null || !grabber.grabbed || (Object)physGrabObject == (Object)null) { return false; } PhysGrabObject field = ReflectionCache.GetField<PhysGrabObject>(grabber, "grabbedPhysGrabObject"); if ((Object)field == (Object)physGrabObject) { return true; } Transform grabbedObjectTransform = grabber.grabbedObjectTransform; if ((Object)grabbedObjectTransform == (Object)null) { return false; } PhysGrabObject val = ((Component)grabbedObjectTransform).GetComponent<PhysGrabObject>() ?? ((Component)grabbedObjectTransform).GetComponentInParent<PhysGrabObject>(); return (Object)val == (Object)physGrabObject; } private static bool IsLocalGrabEntry(object entry) { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Expected O, but got Unknown //IL_0014: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Expected O, but got Unknown //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Expected O, but got Unknown //IL_0054: Unknown result type (might be due to invalid IL or missing references) //IL_005a: Expected O, but got Unknown //IL_005b: Unknown result type (might be due to invalid IL or missing references) //IL_0066: Expected O, but got Unknown //IL_0086: Unknown result type (might be due to invalid IL or missing references) //IL_008c: Expected O, but got Unknown //IL_008d: Unknown result type (might be due to invalid IL or missing references) //IL_0098: Expected O, but got Unknown //IL_00cf: Unknown result type (might be due to invalid IL or missing references) //IL_00d5: Expected O, but got Unknown //IL_00d6: Unknown result type (might be due to invalid IL or missing references) //IL_00e1: Expected O, but got Unknown PhysGrabber val = (PhysGrabber)((entry is PhysGrabber) ? entry : null); if ((Object)val != (Object)null) { return IsLocalAvatar(val.playerAvatar) || IsLocalComponent((Component)val); } PlayerAvatar val2 = (PlayerAvatar)((entry is PlayerAvatar) ? entry : null); if ((Object)val2 != (Object)null) { return IsLocalAvatar(val2); } Component val3 = (Component)((entry is Component) ? entry : null); if ((Object)val3 != (Object)null) { return IsLocalComponent(val3) || IsLocalAvatar(val3.GetComponent<PlayerAvatar>() ?? val3.GetComponentInParent<PlayerAvatar>()); } GameObject val4 = (GameObject)((entry is GameObject) ? entry : null); return (Object)val4 != (Object)null && IsLocalAvatar(val4.GetComponent<PlayerAvatar>() ?? val4.GetComponentInParent<PlayerAvatar>()); } private static bool IsLocalAvatar(PlayerAvatar avatar) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_001a: Expected O, but got Unknown return (Object)avatar != (Object)null && IsLocalComponent((Component)avatar); } private static bool IsLocalComponent(Component component) { //IL_0008: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Expected O, but got Unknown //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Expected O, but got Unknown //IL_0029: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Expected O, but got Unknown //IL_003e: Expected O, but got Unknown PlayerController instance = PlayerController.instance; return (Object)component != (Object)null && (Object)instance != (Object)null && ((Object)component.gameObject == (Object)((Component)instance).gameObject || component.transform.IsChildOf(((Component)instance).transform)); } private static bool IsVanillaCurrentLocalGrab(PhysGrabObject physGrabObject) { //IL_0008: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Expected O, but got Unknown //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Expected O, but got Unknown //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Expected O, but got Unknown //IL_0064: 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_0074: Expected O, but got Unknown //IL_0074: Expected O, but got Unknown PlayerController instance = PlayerController.instance; if ((Object)instance == (Object)null || (Object)physGrabObject == (Object)null) { return false; } GameObject field = ReflectionCache.GetField<GameObject>(instance, "physGrabObject"); if ((Object)field == (Object)null) { return false; } PhysGrabObject val = field.GetComponent<PhysGrabObject>() ?? field.GetComponentInParent<PhysGrabObject>(); return (Object)val == (Object)physGrabObject; } } private static readonly Color AnchorGreen = new Color(0.25f, 1f, 0.25f, 1f); private static readonly Color ReleaseOrangeRed = new Color(1f, 0.32f, 0f, 1f); private static readonly Color RejectOrange = new Color(1f, 0.55f, 0f, 1f); private const float HoldReleaseSeconds = 0.7f; private readonly List<Anchor> _anchors = new List<Anchor>(); private readonly Dictionary<int, float> _lastHeldObjectDiagnosticAt = new Dictionary<int, float>(); private PhysGrabber _primary; private PendingAnchorData _pendingAnchorData; private bool _fHeld; private bool _fConsumed; private float _fDownAt; private bool _anchorFollowPlayer = true; private bool _anchorPassthroughMode; private void CapturePendingAnchor() { //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Expected O, but got Unknown //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_004c: Expected O, but got Unknown MultigraspPlugin.LogVerbose("CapturePendingAnchor attempt primary=" + ObjectName((Object)_primary)); if (IsPrimaryHolding(_primary)) { Transform val = ResolveAnchorPlayerTransform(_primary); PendingAnchorData pendingAnchorData; if ((Object)val == (Object)null) { MultigraspPlugin.LogVerbose("CapturePendingAnchor failed: player transform unavailable"); } else if (TryCaptureCurrentAnchorData(val, out pendingAnchorData)) { _pendingAnchorData = pendingAnchorData; MultigraspPlugin.LogVerbose("CapturePendingAnchor success target=" + ObjectName(pendingAnchorData.TargetTransform)); LogAnchorDiagnostic($"capture target={ObjectName(pendingAnchorData.TargetTransform)} body={DescribeBody(pendingAnchorData.Body)} grabbedAny={IsGrabbedByAnyPlayer(pendingAnchorData.PhysGrabObject)} object={ObjectName(pendingAnchorData.TargetTransform)}"); } else { MultigraspPlugin.LogVerbose("CapturePendingAnchor failed: current grabbed object could not be captured"); } } else { MultigraspPlugin.LogVerbose("CapturePendingAnchor skipped: primary is not holding an object"); } } private void ClearPendingAnchorData() { _pendingAnchorData = null; } private bool TryCaptureCurrentAnchorData(Transform player, out PendingAnchorData pendingAnchorData) { //IL_0038: 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_0045: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_004b: 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_004e: 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_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_0078: 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_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_008d: 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_0060: Unknown result type (might be due to invalid IL or missing references) //IL_0062: 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_0097: Unknown result type (might be due to invalid IL or missing references) //IL_00a0: Unknown result type (might be due to invalid IL or missing references) //IL_00d3: Unknown result type (might be due to invalid IL or missing references) //IL_00d4: Unknown result type (might be due to invalid IL or missing references) //IL_00d6: Unknown result type (might be due to invalid IL or missing references) //IL_00ef: Unknown result type (might be due to invalid IL or missing references) //IL_00f9: Expected O, but got Unknown pendingAnchorData = null; if (!TryResolveCurrentGrabbed(_primary, out var physGrabObject, out var targetTransform, out var body)) { MultigraspPlugin.LogVerbose("TryCaptureCurrentAnchorData failed: current grabbed object unresolved"); return false; } Vector3 val = _primary.localGrabPosition; Vector3 currentTargetPoint = GetCurrentTargetPoint(_primary, targetTransform, val); if (val == Vector3.zero) { val = targetTransform.InverseTransformPoint(currentTargetPoint); } Vector3 val2 = player.InverseTransformPoint(body.position); Quaternion val3 = Quaternion.Inverse(player.rotation) * body.rotation; if (!IsFinite(val) || !IsFinite(val2) || !IsFinite(val3)) { MultigraspPlugin.LogVerbose("TryCaptureCurrentAnchorData failed: computed anchor data not finite target=" + ObjectName(targetTransform)); return false; } pendingAnchorData = new PendingAnchorData(physGrabObject, body, targetTransform, val, val2, val3); MultigraspPlugin.LogVerbose("TryCaptureCurrentAnchorData success target=" + ObjectName(targetTransform) + " body=" + ObjectName((Object)body)); return true; } private static bool TryResolveCurrentGrabbed(PhysGrabber primary, out PhysGrabObject physGrabObject, out Transform targetTransform, out Rigidbody body) { //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_004c: Expected O, but got Unknown //IL_0050: Unknown result type (might be due to invalid IL or missing references) //IL_005b: Expected O, but got Unknown //IL_0087: Unknown result type (might be due to invalid IL or missing references) //IL_0092: Expected O, but got Unknown //IL_010b: Unknown result type (might be due to invalid IL or missing references) //IL_0116: Expected O, but got Unknown //IL_011a: Unknown result type (might be due to invalid IL or missing references) //IL_0125: Expected O, but got Unknown //IL_013b: Unknown result type (might be due to invalid IL or missing references) //IL_0146: Expected O, but got Unknown //IL_0102: Unknown result type (might be due to invalid IL or missing references) //IL_0108: Expected O, but got Unknown //IL_015e: Unknown result type (might be due to invalid IL or missing references) //IL_0169: Expected O, but got Unknown //IL_018d: Unknown result type (might be due to invalid IL or missing references) //IL_0198: Expected O, but got Unknown //IL_01a6: Unknown result type (might be due to invalid IL or missing references) //IL_01b0: Expected O, but got Unknown physGrabObject = null; targetTransform = null; body = null; if (!IsPrimaryHolding(primary)) { MultigraspPlugin.LogVerbose("TryResolveCurrentGrabbed failed: primary not holding"); return false; } physGrabObject = ReflectionCache.GetField<PhysGrabObject>(primary, "grabbedPhysGrabObject"); targetTransform = primary.grabbedObjectTransform; if ((Object)physGrabObject == (Object)null && (Object)targetTransform != (Object)null) { physGrabObject = ((Component)targetTransform).GetComponent<PhysGrabObject>() ?? ((Component)targetTransform).GetComponentInParent<PhysGrabObject>(); } body = ReflectionCache.GetField<Rigidbody>(primary, "grabbedObject"); if ((Object)body == (Object)null) { PhysGrabObject val = physGrabObject; object obj = (((Object)(object)val != (Object)null) ? ((Component)val).GetComponent<Rigidbody>() : null); if (obj == null) { Transform val2 = targetTransform; obj = (((Object)(object)val2 != (Object)null) ? ((Component)val2).GetComponent<Rigidbody>() : null); if (obj == null) { Transform val3 = targetTransform; obj = (((Object)(object)val3 != (Object)null) ? ((Component)val3).GetComponentInParent<Rigidbody>() : null); } } body = (Rigidbody)obj; } if ((Object)targetTransform == (Object)null && (Object)body != (Object)null) { targetTransform = ((Component)body).transform; } if ((Object)physGrabObject == (Object)null) { MultigraspPlugin.LogVerbose("TryResolveCurrentGrabbed failed: missing PhysGrabObject"); return false; } if ((Object)body == (Object)null) { MultigraspPlugin.LogVerbose("TryResolveCurrentGrabbed failed: missing Rigidbody target=" + ObjectName(targetTransform)); return false; } if ((Object)targetTransform == (Object)null) { MultigraspPlugin.LogVerbose("TryResolveCurrentGrabbed failed: missing target transform body=" + ObjectName((Object)body)); return false; } return true; } private static bool IsPendingAnchorDataValid(PendingAnchorData pendingAnchorData) { if (pendingAnchorData == null || !pendingAnchorData.IsValid) { MultigraspPlugin.LogVerbose("Pending anchor invalid: " + GetPendingAnchorInvalidReason(pendingAnchorData)); return false; } if ((MultigraspPlugin.AllowEnemyAnchors == null || !MultigraspPlugin.AllowEnemyAnchors.Value) && IsEnemyObject(pendingAnchorData.PhysGrabObject, pendingAnchorData.TargetTransform, pendingAnchorData.Body)) { MultigraspPlugin.LogVerbose("Refused to fix enemy/monster object: " + ((Object)pendingAnchorData.TargetTransform).name); return false; } return true; } private void CommitAnchor(PendingAnchorData pendingAnchorData) { //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_004c: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_013f: Unknown result type (might be due to invalid IL or missing references) int num = FindAnchorIndex(pendingAnchorData.PhysGrabObject, pendingAnchorData.TargetTransform); if (num >= 0) { _anchors[num].DestroyOwnedObjects(); } Anchor anchor = new Anchor(pendingAnchorData.PhysGrabObject, pendingAnchorData.Body, pendingAnchorData.TargetTransform, pendingAnchorData.LocalGrabPosition, pendingAnchorData.PlayerLocalBodyPosition, pendingAnchorData.PlayerLocalBodyRotation, _anchorFollowPlayer, _anchorPassthroughMode, $"Multigrasp Anchor Beam {_anchors.Count + 1}"); LogAnchorDiagnostic($"commit target={ObjectName(pendingAnchorData.TargetTransform)} body={DescribeBody(pendingAnchorData.Body)} grabbedAny={IsGrabbedByAnyPlayer(pendingAnchorData.PhysGrabObject)} object={ObjectName(pendingAnchorData.TargetTransform)}"); if (num >= 0) { _anchors[num] = anchor; MultigraspPlugin.LogVerbose("Updated fixed object anchor target=" + ObjectName(pendingAnchorData.TargetTransform)); } else { _anchors.Add(anchor); MultigraspPlugin.LogVerbose("Fixed object anchor added target=" + ObjectName(pendingAnchorData.TargetTransform)); } HudNotifier.Show("Object fixed", AnchorGreen); } private int FindAnchorIndex(PhysGrabObject physGrabObject, Transform targetTransform) { for (int i = 0; i < _anchors.Count; i++) { if (_anchors[i].Matches(physGrabObject, targetTransform)) { return i; } } return -1; } private void TickBeams() { Transform player = ResolveAnchorPlayerTransform(_primary); Transform cameraTransform = GetCameraTransform(_primary); for (int num = _anchors.Count - 1; num >= 0; num--) { if (!_anchors[num].TickBeam(_primary, cameraTransform, player)) { RemoveAnchorAt(num); } } } private void ApplyAnchorForces() { Transform player = ResolveAnchorPlayerTransform(_primary); for (int num = _anchors.Count - 1; num >= 0; num--) { if (!_anchors[num].ApplyForce(player)) { RemoveAnchorAt(num); } } } private void RemoveAnchorAt(int index) { string arg = ((index >= 0 && index < _anchors.Count) ? _anchors[index].TargetName : "<bad-index>"); MultigraspPlugin.LogVerbose($"Removing anchor at index={index} target={arg} countBefore={_anchors.Count}"); _anchors[index].DestroyOwnedObjects(); _anchors.RemoveAt(index); } internal static bool IsGrabbedByAnyPlayer(PhysGrabObject physGrabObject) { //IL_0058: Unknown result type (might be due to invalid IL or missing references) //IL_0063: Expected O, but got Unknown object field = ReflectionCache.GetField<object>(physGrabObject, "playerGrabbing"); if (!(field is IEnumerable enumerable) || field is string) { return false; } foreach (object item in enumerable) { Object val = (Object)((item is Object) ? item : null); if (val != null) { if (val != (Object)null) { return true; } } else if (item != null) { return true; } } return false; } private void Update() { try { HudNotifier.Tick(); ResolvePrimary(); if (!IsUsablePrimary(_primary)) { ReleaseAllAnchors("primary unavailable"); ResetFState(); return; } if (IsLocalPlayerInvalid(_primary)) { ReleaseAllAnchors("player dead/disabled"); ResetFState(); return; } TickFollowToggleInput(); TickPassthroughToggleInput(); TickReleaseCurrentFixedInput(); TickAnchorInput(); TickBeams(); LogHeldFixedObjectDiagnostics(); } catch (Exception ex) { MultigraspPlugin.LogError("Manager update failed", ex); } } private void FixedUpdate() { try { ApplyAnchorForces(); } catch (Exception ex) { MultigraspPlugin.LogError("Anchor force failed", ex); } } internal void RegisterPrimary(PhysGrabber grabber) { if (IsUsablePrimary(grabber)) { _primary = grabber; MultigraspPlugin.LogVerbose("Registered primary " + ((Object)grabber).name); } } internal void ReleaseAllAnchors(string reason) { ClearPendingAnchorData(); if (_anchors.Count > 0) { MultigraspPlugin.LogVerbose("Released all anchors: " + reason); } for (int i = 0; i < _anchors.Count; i++) { _anchors[i].DestroyOwnedObjects(); } _anchors.Clear(); } internal void DestroyOwnedObjects() { ClearPendingAnchorData(); ReleaseAllAnchors("destroy owned objects"); HudNotifier.DestroyOwnedObjects(); } private void ResolvePrimary() { if (IsUsablePrimary(_primary)) { return; } if (IsUsablePrimary(PhysGrabber.instance)) { _primary = PhysGrabber.instance; return; } PhysGrabber[] array = Object.FindObjectsOfType<PhysGrabber>(); PhysGrabber[] array2 = array; foreach (PhysGrabber val in array2) { if (IsUsablePrimary(val)) { _primary = val; MultigraspPlugin.LogVerbose("Fallback selected primary " + ((Object)val).name); break; } } } internal static void LogAnchorDiagnostic(string message) { MultigraspPlugin.LogVerbose("[anchor] " + message); } internal static string DescribeBody(Rigidbody body) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_0020: 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) if ((Object)body == (Object)null) { return "body=none"; } return $"bodyPos={FormatVector(body.position)} bodyVel={FormatVector(body.velocity)} bodyKinematic={body.isKinematic}"; } private static string FormatVector(Vector3 value) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Unknown result type (might be due to invalid IL or missing references) return $"({value.x:0.000},{value.y:0.000},{value.z:0.000})"; } private void LogHeldFixedObjectDiagnostics() { //IL_00d3: Unknown result type (might be due to invalid IL or missing references) //IL_00d8: 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_00dd: Unknown result type (might be due to invalid IL or missing references) //IL_00e2: Unknown result type (might be due to invalid IL or missing references) //IL_00f6: Unknown result type (might be due to invalid IL or missing references) //IL_0101: Expected O, but got Unknown //IL_0149: 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_0118: Unknown result type (might be due to invalid IL or missing references) //IL_011f: Unknown result type (might be due to invalid IL or missing references) //IL_0126: Unknown result type (might be due to invalid IL or missing references) //IL_0128: Unknown result type (might be due to invalid IL or missing references) if (MultigraspPlugin.VerboseLogs == null || !MultigraspPlugin.VerboseLogs.Value || !IsPrimaryHolding(_primary) || !TryResolveCurrentGrabbed(_primary, out var physGrabObject, out var targetTransform, out var body)) { return; } int num = FindAnchorIndex(physGrabObject, targetTransform); if (num < 0) { return; } int instanceID = ((Object)physGrabObject).GetInstanceID(); float realtimeSinceStartup = Time.realtimeSinceStartup; if (!_lastHeldObjectDiagnosticAt.TryGetValue(instanceID, out var value) || !(realtimeSinceStartup - value < 0.75f)) { _lastHeldObjectDiagnosticAt[instanceID] = realtimeSinceStartup; PruneBoundedDiagnostics(_lastHeldObjectDiagnosticAt, 64, realtimeSinceStartup, 10f); Vector3 localGrabPosition = _primary.localGrabPosition; Vector3 val = targetTransform.TransformPoint(localGrabPosition); string text = "desired=unavailable reason=no reliable PhysGrabber.physGrabPoint"; if ((Object)_primary.physGrabPoint != (Object)null) { Vector3 position = _primary.physGrabPoint.position; text = $"desiredSource=physGrabPoint desired={FormatVector(position)} error={Vector3.Distance(val, position):0.000}"; } LogAnchorDiagnostic($"held-fixed-object actualGrab={FormatVector(val)} {text} body={DescribeBody(body)} grabbedAny={IsGrabbedByAnyPlayer(physGrabObject)} object={ObjectName(targetTransform)}"); } } private static void PruneBoundedDiagnostics(Dictionary<int, float> values, int maxCount, float now, float maxAgeSeconds) { if (values.Count <= maxCount) { return; } foreach (int item in new List<int>(values.Keys)) { if (now - values[item] > maxAgeSeconds) { values.Remove(item); } } while (values.Count > maxCount) { int key = 0; float num = float.MaxValue; foreach (KeyValuePair<int, float> value in values) { if (value.Value < num) { key = value.Key; num = value.Value; } } values.Remove(key); } } private static string GetPendingAnchorInvalidReason(PendingAnchorData data) { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Expected O, but got Unknown //IL_003c: Unknown result type (might be due to invalid IL or missing references) //IL_0047: Expected O, but got Unknown //IL_005d: Unknown result type (might be due to invalid IL or missing references) //IL_0068: Expected O, but got Unknown if (data == null) { return "data is null"; } if ((Object)data.PhysGrabObject == (Object)null) { return "missing PhysGrabObject"; } if ((Object)data.Body == (Object)null) { return "missing Rigidbody"; } if ((Object)data.TargetTransform == (Object)null) { return "missing target transform"; } if (!((Behaviour)data.PhysGrabObject).enabled || data.PhysGrabObject.dead) { return "PhysGrabObject disabled/dead target=" + ObjectName(data.TargetTransform); } if (data.Body.isKinematic || !((Component)data.Body).gameObject.activeInHierarchy) { return "Rigidbody kinematic/inactive target=" + ObjectName(data.TargetTransform); } return "unknown target=" + ObjectName(data.TargetTransform); } private static string ObjectName(Transform transform) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown return ((Object)transform != (Object)null) ? ((Object)transform).name : "<null>"; } private static string ObjectName(Object unityObject) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown return (unityObject != (Object)null) ? unityObject.name : "<null>"; } private static Transform ResolveAnchorPlayerTransform(PhysGrabber primary) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Expected O, but got Unknown //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Expected O, but got Unknown //IL_0050: Unknown result type (might be due to invalid IL or missing references) //IL_005b: Expected O, but got Unknown //IL_0063: 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_0074: Expected O, but got Unknown //IL_0074: Expected O, but got Unknown //IL_0081: Unknown result type (might be due to invalid IL or missing references) //IL_008d: Unknown result type (might be due to invalid IL or missing references) //IL_0097: Expected O, but got Unknown //IL_0097: Expected O, but got Unknown if ((Object)primary == (Object)null || (Object)primary.playerAvatar == (Object)null) { return null; } PlayerController instance = PlayerController.instance; if ((Object)instance != (Object)null) { PlayerAvatar playerAvatarScript = instance.playerAvatarScript; if ((Object)playerAvatarScript != (Object)null && ((Object)primary.playerAvatar == (Object)playerAvatarScript || (Object)((Component)primary.playerAvatar).gameObject == (Object)((Component)playerAvatarScript).gameObject)) { return ((Component)instance).transform; } } return ((Component)primary.playerAvatar).transform; } private static bool IsUsablePrimary(PhysGrabber grabber) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Expected O, but got Unknown //IL_0035: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Expected O, but got Unknown return (Object)grabber != (Object)null && grabber.isLocal && (Object)grabber.playerAvatar != (Object)null && (Object)grabber.playerAvatar.localCamera != (Object)null; } private static bool IsLocalPlayerInvalid(PhysGrabber grabber) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_002c: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Expected O, but got Unknown //IL_004a: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Expected O, but got Unknown if ((Object)grabber == (Object)null || !grabber.isLocal) { return true; } PlayerAvatar playerAvatar = grabber.playerAvatar; if ((Object)playerAvatar == (Object)null) { return true; } GameObject gameObject = ((Component)playerAvatar).gameObject; if ((Object)gameObject == (Object)null || !gameObject.activeInHierarchy) { return true; } return ReflectionCache.GetField<bool>(playerAvatar, "deadSet") || ReflectionCache.GetField<bool>(playerAvatar, "isDisabled"); } internal static bool IsEnemyObject(PhysGrabObject physGrabObject, Transform targetTransform, Rigidbody body) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_0033: Expected O, but got Unknown //IL_0053: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Expected O, but got Unknown //IL_0071: Unknown result type (might be due to invalid IL or missing references) //IL_007c: Expected O, but got Unknown //IL_008f: Unknown result type (might be due to invalid IL or missing references) //IL_009a: Expected O, but got Unknown //IL_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00ad: Expected O, but got Unknown //IL_00c5: Unknown result type (might be due to invalid IL or missing references) //IL_00d0: Expected O, but got Unknown if (HasEnemyComponent(((Object)physGrabObject != (Object)null) ? ((Component)physGrabObject).transform : null) || HasEnemyComponent(targetTransform) || HasEnemyComponent(((Object)body != (Object)null) ? ((Component)body).transform : null)) { return true; } return HasEnemyName(((Object)physGrabObject != (Object)null) ? ((Object)physGrabObject).name : null) || HasEnemyName(((Object)targetTransform != (Object)null) ? ((Object)targetTransform).name : null) || HasEnemyName(((Object)targetTransform != (Object)null && (Object)targetTransform.root != (Object)null) ? ((Object)targetTransform.root).name : null) || HasEnemyName(((Object)body != (Object)null) ? ((Object)body).name : null); } private static bool HasEnemyComponent(Transform transform) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Expected O, but got Unknown //IL_0031: Unknown result type (might be due to invalid IL or missing references) //IL_003c: Expected O, but got Unknown //IL_0045: Unknown result type (might be due to invalid IL or missing references) //IL_0050: Expected O, but got Unknown //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_0064: Expected O, but got Unknown //IL_006d: Unknown result type (might be due to invalid IL or missing references) //IL_0078: Expected O, but got Unknown if ((Object)transform == (Object)null) { return false; } return (Object)((Component)transform).GetComponentInParent<EnemyRigidbody>(true) != (Object)null || (Object)((Component)transform).GetComponentInChildren<EnemyRigidbody>(true) != (Object)null || (Object)((Component)transform).GetComponentInParent<Enemy>(true) != (Object)null || (Object)((Component)transform).GetComponentInChildren<Enemy>(true) != (Object)null || (Object)((Component)transform).GetComponentInParent<EnemyParent>(true) != (Object)null; } private static bool HasEnemyName(string objectName) { return objectName != null && (objectName.IndexOf("Enemy", StringComparison.OrdinalIgnoreCase) >= 0 || objectName.IndexOf("Monster", StringComparison.OrdinalIgnoreCase) >= 0); } private static bool IsPrimaryHolding(PhysGrabber primary) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Expected O, but got Unknown //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Expected O, but got Unknown return (Object)primary != (Object)null && primary.grabbed && (Object)primary.grabbedObjectTransform != (Object)null; } private static Transform GetCameraTransform(PhysGrabber primary) { //IL_00ae: Unknown result type (might be due to invalid IL or missing references) //IL_00b5: Expected O, but got Unknown //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0054: Expected O, but got Unknown try { object obj; if ((Object)(object)primary == (Object)null) { obj = null; } else { PlayerAvatar playerAvatar = primary.playerAvatar; if ((Object)(object)playerAvatar == (Object)null) { obj = null; } else { PlayerLocalCamera localCamera = playerAvatar.localCamera; obj = (((Object)(object)localCamera != (Object)null) ? localCamera.GetOverrideTransform() : null); } } return (Transform)obj; } catch { object obj3; if ((Object)(object)primary == (Object)null) { obj3 = null; } else { PlayerAvatar playerAvatar2 = primary.playerAvatar; if ((Object)(object)playerAvatar2 == (Object)null) { obj3 = null; } else { PlayerLocalCamera localCamera2 = playerAvatar2.localCamera; obj3 = (((Object)(object)localCamera2 != (Object)null) ? ((Component)localCamera2).transform : null); } } return (Transform)obj3; } } private static Vector3 GetCurrentTargetPoint(PhysGrabber primary, Transform targetTransform, Vector3 localGrabPosition) { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown //IL_0026: 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_002c: Unknown result type (might be due to invalid IL or missing references) //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_002f: Unknown result type (might be due to invalid IL or missing references) if ((Object)primary.physGrabPoint != (Object)null) { return primary.physGrabPoint.position; } return targetTransform.TransformPoint(localGrabPosition); } internal static bool IsFinite(float value) { return !float.IsNaN(value) && !float.IsInfinity(value); } internal static bool IsFinite(Vector3 value) { //IL_0001: 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_001b: Unknown result type (might be due to invalid IL or missing references) return IsFinite(value.x) && IsFinite(value.y) && IsFinite(value.z); } internal static bool IsFinite(Quaternion value) { //IL_0001: 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_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Unknown result type (might be due to invalid IL or missing references) return IsFinite(value.x) && IsFinite(value.y) && IsFinite(value.z) && IsFinite(value.w); } private void TickAnchorInput() { //IL_0084: 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) if (Input.GetKeyDown((KeyCode)102)) { ResetFState(); _fHeld = true; _fConsumed = false; _fDownAt = Time.unscaledTime; CapturePendingAnchor(); } if (_fHeld && !_fConsumed && Input.GetKey((KeyCode)102) && Time.unscaledTime - _fDownAt >= 0.7f) { ClearPendingAnchorData(); ReleaseAllAnchors("F held"); HudNotifier.Show("All fixed objects released", ReleaseOrangeRed); _fConsumed = true; } if (!Input.GetKeyUp((KeyCode)102)) { return; } if (!_fConsumed && _pendingAnchorData != null) { PendingAnchorData pendingAnchorData = _pendingAnchorData; ClearPendingAnchorData(); if (IsPendingAnchorDataValid(pendingAnchorData)) { CommitAnchor(pendingAnchorData); } else { HudNotifier.Show("Cannot fix object", RejectOrange); } } ResetFState(); } private void ResetFState() { ClearPendingAnchorData(); _fHeld = false; _fConsumed = false; _fDownAt = 0f; } private void TickFollowToggleInput() { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_002d: Expected O, but got Unknown //IL_00b0: Unknown result type (might be due to invalid IL or missing references) if (!Input.GetKeyDown((KeyCode)114)) { return; } Transform val = ResolveAnchorPlayerTransform(_primary); if ((Object)val == (Object)null) { return; } bool anchorFollowPlayer = !_anchorFollowPlayer; _anchorFollowPlayer = anchorFollowPlayer; for (int num = _anchors.Count - 1; num >= 0; num--) { if (!_anchors[num].SetFollowPlayer(_anchorFollowPlayer, val)) { RemoveAnchorAt(num); } } HudNotifier.Show(_anchorFollowPlayer ? "Fixed objects follow player" : "Fixed objects stay in world", AnchorGreen); MultigraspPlugin.LogVerbose(_anchorFollowPlayer ? "Fixed object follow enabled" : "Fixed object follow disabled"); } private void TickPassthroughToggleInput() { //IL_0081: Unknown result type (might be due to invalid IL or missing references) if (!Input.GetKeyDown((KeyCode)118)) { return; } _anchorPassthroughMode = !_anchorPassthroughMode; for (int num = _anchors.Count - 1; num >= 0; num--) { if (!_anchors[num].SetPassthroughMode(_anchorPassthroughMode)) { RemoveAnchorAt(num); } } HudNotifier.Show(_anchorPassthroughMode ? "Fixed objects ignore obstacles" : "Fixed objects collide normally", AnchorGreen); MultigraspPlugin.LogVerbose(_anchorPassthroughMode ? "Fixed object passthrough enabled" : "Fixed object passthrough disabled"); } private void TickReleaseCurrentFixedInput() { //IL_004c: Unknown result type (might be due to invalid IL or missing references) if (Input.GetKeyDown((KeyCode)99) && TryResolveCurrentGrabbed(_primary, out var physGrabObject, out var targetTransform, out var _)) { int num = FindAnchorIndex(physGrabObject, targetTransform); if (num >= 0) { RemoveAnchorAt(num); HudNotifier.Show("Object released", ReleaseOrangeRed); MultigraspPlugin.LogVerbose("Released current fixed object anchor"); } } } } [BepInPlugin("com.zhuanban.repo.multigrasp", "Multigrasp", "1.0.0")] public sealed class MultigraspPlugin : BaseUnityPlugin { public const string PluginGuid = "com.zhuanban.repo.multigrasp"; public const string PluginName = "Multigrasp"; public const string PluginVersion = "1.0.0"; private Harmony _harmony; private MultigraspManager _manager; internal static MultigraspPlugin Instance { get; private set; } internal static ManualLogSource Log { get; private set; } internal static ConfigEntry<bool> VerboseLogs { get; private set; } internal static ConfigEntry<bool> EnableScrollDistanceOverride { get; private set; } internal static ConfigEntry<bool> AllowEnemyAnchors { get; private set; } private void Awake() { //IL_00c0: Unknown result type (might be due to invalid IL or missing references) //IL_00ca: Expected O, but got Unknown Instance = this; Log = ((BaseUnityPlugin)this).Logger; VerboseLogs = ((BaseUnityPlugin)this).Config.Bind<bool>("Logging", "VerboseLogs", false, "When true, console receives verbose logs for Multigrasp debugging."); EnableScrollDistanceOverride = ((BaseUnityPlugin)this).Config.Bind<bool>("Gameplay", "EnableScrollDistanceOverride", true, "When true, objects that force grab distance every frame can still be adjusted with push/pull or mouse scroll while held locally."); AllowEnemyAnchors = ((BaseUnityPlugin)this).Config.Bind<bool>("Gameplay", "AllowEnemyAnchors", false, "When true, Multigrasp allows fixing enemy/monster PhysGrabObjects locally."); LogVerbose($"Startup config: VerboseLogs={VerboseLogs.Value}, EnableScrollDistanceOverride={EnableScrollDistanceOverride.Value}, AllowEnemyAnchors={AllowEnemyAnchors.Value}"); ReflectionCache.Initialize(); _harmony = new Harmony("com.zhuanban.repo.multigrasp"); _harmony.PatchAll(); _manager = ((Component)this).gameObject.AddComponent<MultigraspManager>(); ((BaseUnityPlugin)this).Logger.LogInfo((object)"Multigrasp loaded. Safe local-only anchors active by default."); } private void OnDestroy() { _manager?.DestroyOwnedObjects(); Harmony harmony = _harmony; if (harmony != null) { harmony.UnpatchSelf(); } Instance = null; } internal static void LogInfo(string message) { ManualLogSource log = Log; if (log != null) { log.LogInfo((object)("[Multigrasp] " + message)); } } internal static void LogVerbose(string message) { ConfigEntry<bool> verboseLogs = VerboseLogs; if (verboseLogs != null && verboseLogs.Value) { ManualLogSource log = Log; if (log != null) { log.LogInfo((object)("[Multigrasp verbose] " + message)); } } } internal static void LogWarning(string message) { ManualLogSource log = Log; if (log != null) { log.LogWarning((object)("[Multigrasp] " + message)); } } internal static void LogError(string message, Exception ex = null) { ManualLogSource log = Log; if (log != null) { log.LogError((object)((ex == null) ? ("[Multigrasp] " + message) : $"[Multigrasp] {message}: {ex}")); } } } [HarmonyPatch(typeof(PhysGrabber), "OverrideGrabDistance")] internal static class PhysGrabberOverrideGrabDistancePatch { private sealed class OffsetState { internal Transform TargetTransform; internal float LastForcedDistance; internal float Offset; } private const float PullPushDistanceStep = 0.2f; private static readonly Dictionary<PhysGrabber, OffsetState> OffsetStates = new Dictionary<PhysGrabber, OffsetState>(); private static void Prefix(PhysGrabber __instance, ref float dist) { //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Expected O, but got Unknown PruneDestroyedStates(); ConfigEntry<bool> enableScrollDistanceOverride = MultigraspPlugin.EnableScrollDistanceOverride; if (enableScrollDistanceOverride == null || !enableScrollDistanceOverride.Value) { return; } if (!IsLocalGrabActive(__instance, out var targetTransform)) { if ((Object)__instance != (Object)null) { OffsetStates.Remove(__instance); } return; } OffsetState state = GetState(__instance, targetTransform, dist); float pullPushInput = GetPullPushInput(); if (IsFinite(pullPushInput) && Mathf.Abs(pullPushInput) > 0.0001f) { state.Offset += Mathf.Sign(pullPushInput) * 0.2f; } float num = dist + state.Offset; if (TryGetDistanceBounds(__instance, out var minimumDistance, out var maximumDistance)) { num = Mathf.Clamp(num, minimumDistance, maximumDistance); state.Offset = num - dist; } if (IsFinite(num)) { dist = num; } } private static void PruneDestroyedStates() { //IL_0023: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Expected O, but got Unknown foreach (PhysGrabber item in new List<PhysGrabber>(OffsetStates.Keys)) { if ((Object)item == (Object)null) { OffsetStates.Remove(item); } } } private static bool IsLocalGrabActive(PhysGrabber grabber, out Transform targetTransform) { //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_0010: Expected O, but got Unknown //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_0033: Expected O, but got Unknown targetTransform = null; if ((Object)grabber == (Object)null || !grabber.isLocal || !grabber.grabbed || (Object)grabber.grabbedObjectTransform == (Object)null) { return false; } targetTransform = grabber.grabbedObjectTransform; return true; } private static OffsetState GetState(PhysGrabber grabber, Transform targetTransform, float forcedDistance) { //IL_0030: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Expected O, but got Unknown //IL_0040: Expected O, but got Unknown if (!OffsetStates.TryGetValue(grabber, out var value)) { value = new OffsetState(); OffsetStates[grabber] = value; } if ((Object)value.TargetTransform != (Object)targetTransform || !Mathf.Approximately(value.LastForcedDistance, forcedDistance)) { value.TargetTransform = targetTransform; value.Offset = 0f; } value.LastForcedDistance = forcedDistance; return value; } private static float GetPullPushInput() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown try { return ((Object)InputManager.instance != (Object)null) ? InputManager.instance.KeyPullAndPush() : 0f; } catch { return 0f; } } private static bool TryGetDistanceBounds(PhysGrabber grabber, out float minimumDistance, out float maximumDistance) { minimumDistance = ReflectionCache.GetField<float>(grabber, "minDistanceFromPlayer"); float field = ReflectionCache.GetField<float>(grabber, "grabRange"); float field2 = ReflectionCache.GetField<float>(grabber, "maxDistanceFromPlayer"); maximumDistance = ((field2 > 0f) ? field2 : field); if (field > 0f && maximumDistance > 0f) { maximumDistance = Mathf.Min(field, maximumDistance); } return IsFinite(minimumDistance) && IsFinite(maximumDistance) && maximumDistance > minimumDistance; } private static bool IsFinite(float value) { return !float.IsNaN(value) && !float.IsInfinity(value); } } [HarmonyPatch(typeof(PhysGrabber), "Start")] internal static class PhysGrabberStartPatch { private static void Postfix(PhysGrabber __instance) { MultigraspPlugin instance = MultigraspPlugin.Instance; if ((Object)(object)instance != (Object)null) { ((Component)instance).GetComponent<MultigraspManager>()?.RegisterPrimary(__instance); } } } internal static class ReflectionCache { private struct FieldKey : IEquatable<FieldKey> { private readonly Type _type; private readonly string _name; internal FieldKey(Type type, string name) { _type = type; _name = name; } public bool Equals(FieldKey other) { return _type == other._type && _name == other._name; } public override bool Equals(object obj) { return obj is FieldKey other && Equals(other); } public override int GetHashCode() { return (((_type != null) ? _type.GetHashCode() : 0) * 397) ^ ((_name != null) ? _name.GetHashCode() : 0); } } private static readonly BindingFlags Flags = BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic; private static readonly HashSet<string> WarnedMissingMembers = new HashSet<string>(); private static readonly Dictionary<FieldKey, FieldInfo> CachedFields = new Dictionary<FieldKey, FieldInfo>(); internal static void Initialize() { WarnedMissingMembers.Clear(); CachedFields.Clear(); } internal static T GetField<T>(object target, string name) { FieldInfo fieldInfo = GetFieldInfo(target, name); if (fieldInfo == null) { return default(T); } try { return (fieldInfo.GetValue(target) is T val) ? val : default(T); } catch (Exception ex) { MultigraspPlugin.LogError("Reflection get failed for " + target.GetType().Name + "." + name, ex); return default(T); } } internal static bool SetField<T>(object target, string name, T value) { FieldInfo fieldInfo = GetFieldInfo(target, name); if (fieldInfo == null) { return false; } try { fieldInfo.SetValue(target, value); return true; } catch (Exception ex) { MultigraspPlugin.LogError("Reflection set failed for " + target.GetType().Name + "." + name, ex); return false; } } private static FieldInfo GetFieldInfo(object target, string name) { if (target == null) { return null; } Type type = target.GetType(); FieldKey key = new FieldKey(type, name); if (CachedFields.TryGetValue(key, out var value)) { return value; } FieldInfo field = type.GetField(name, Flags); CachedFields[key] = field; if (field == null) { WarnMissing(type.Name + "." + name); } return field; } private static void WarnMissing(string member) { if (WarnedMissingMembers.Add(member)) { MultigraspPlugin.LogVerbose("Optional reflection member unavailable: " + member); } } } }