using System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text; using BoneLib; using BoneLib.BoneMenu; using BoneLib.BoneMenu.UI; using Il2CppInterop.Runtime.InteropTypes; using Il2CppInterop.Runtime.InteropTypes.Arrays; using Il2CppSLZ.Bonelab; using Il2CppSLZ.Marrow; using Il2CppSLZ.Marrow.Pool; using Il2CppSLZ.Marrow.Warehouse; using Il2CppSLZ.VRMK; using Il2CppSystem; using Il2CppSystem.Reflection; using Il2CppTMPro; using LabFusion.Entities; using LabFusion.Marrow.Integration; using LabFusion.Player; using LabFusion.SDK.Cosmetics; using LabFusion.SDK.Points; using LocalMirrorMod; using LocalMirrorMod.Fixes; using MelonLoader; using MelonLoader.Preferences; using Microsoft.CodeAnalysis; using UnityEngine; using UnityEngine.Events; using UnityEngine.Rendering; using UnityEngine.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: AssemblyTitle("LocalMirror")] [assembly: AssemblyDescription("Standalone Local Mirror mod for BONELAB")] [assembly: AssemblyProduct("LocalMirror")] [assembly: AssemblyCopyright("Copyright 2026")] [assembly: ComVisible(false)] [assembly: AssemblyFileVersion("1.0.0")] [assembly: MelonInfo(typeof(Main), "LocalMirror", "1.0.0", "MrYetiSpaghetti", null)] [assembly: MelonGame("Stress Level Zero", "BONELAB")] [assembly: MelonPriority(-230)] [assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.0.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace LocalMirrorMod { public static class Config { private const string CategoryId = "LocalMirror"; public static MelonPreferences_Category _category; public static MelonPreferences_Entry MirrorDistance; public static MelonPreferences_Entry MirrorScaleByHeight; public static MelonPreferences_Entry MirrorFollowHead; public static MelonPreferences_Entry MirrorStayInPlace; public static MelonPreferences_Entry LocalMirrorHeldItemAwarenessEnabled; public static MelonPreferences_Entry LocalMirrorSeatAwarenessEnabled; public static MelonPreferences_Entry LocalMirrorProximityAwarenessEnabled; public static MelonPreferences_Entry LocalMirrorProximityRadius; public static MelonPreferences_Entry LocalMirrorProximityVisualEnabled; public static MelonPreferences_Entry LocalMirrorIncludeOthersEnabled; public static MelonPreferences_Entry LocalMirrorShowHolsteredEnabled; public static MelonPreferences_Entry ShowFusionCosmeticsEnabled; private static BoolElement _localMirrorToggleElement; private static BoolElement _mirrorScaleByHeightElement; private static BoolElement _mirrorFollowHeadElement; private static BoolElement _mirrorStayInPlaceElement; private static BoolElement _showHolsteredElement; private static BoolElement _heldItemAwarenessElement; private static BoolElement _seatAwarenessElement; private static BoolElement _proximityAwarenessElement; private static BoolElement _proximityVisualElement; private static BoolElement _includeOthersElement; private static BoolElement _showFusionCosmeticsElement; public static void Initialize() { _category = MelonPreferences.CreateCategory("LocalMirror"); _category.SetFilePath("UserData/LocalMirror.cfg", true, false); MirrorDistance = _category.CreateEntry("MirrorDistance", 1.5f, "Distance in meters from the player chest to the mirror clone", (string)null, false, false, (ValueValidator)null, (string)null); MirrorScaleByHeight = _category.CreateEntry("MirrorScaleByHeight", true, "Scale the mirror distance proportionally to the player's avatar height", (string)null, false, false, (ValueValidator)null, (string)null); MirrorFollowHead = _category.CreateEntry("MirrorFollowHead", false, "Mirror tracks head facing live; when off, facing direction is frozen at enable time", (string)null, false, false, (ValueValidator)null, (string)null); MirrorStayInPlace = _category.CreateEntry("MirrorStayInPlace", false, "Spawn the mirror once at correct distance facing the player, then keep it stationary", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirrorHeldItemAwarenessEnabled = _category.CreateEntry("HeldItemAwareness", true, "Mirror whichever spawnable the player's hand is currently grabbing onto the clone", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirrorSeatAwarenessEnabled = _category.CreateEntry("SeatAwareness", true, "Mirror the vehicle / seat the player is sitting in onto the clone", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirrorProximityAwarenessEnabled = _category.CreateEntry("ProximityAwareness", false, "Mirror any spawnable inside the configured radius of the player onto the clone", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirrorProximityRadius = _category.CreateEntry("ProximityRadius", 2f, "Proximity Awareness radius in meters", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirrorProximityVisualEnabled = _category.CreateEntry("ProximityVisual", true, "Render a white circle ring at the proximity radius around the player", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirrorIncludeOthersEnabled = _category.CreateEntry("IncludeOthers", false, "Include other players' rigs as eligible for the LocalMirror item awareness toggles (held / proximity)", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirrorShowHolsteredEnabled = _category.CreateEntry("ShowHolstered", true, "Show holstered items on the LocalMirror clone (and on remote rig clones when Include Others is on)", (string)null, false, false, (ValueValidator)null, (string)null); ShowFusionCosmeticsEnabled = _category.CreateEntry("ShowFusionCosmetics", false, "Mirror the local player's equipped Fusion cosmetics (and remote players' when Include Others is on) onto the mirror clones", (string)null, false, false, (ValueValidator)null, (string)null); LocalMirror.Distance = MirrorDistance.Value; LocalMirror.ScaleByAvatarHeight = MirrorScaleByHeight.Value; LocalMirror.FollowHead = MirrorFollowHead.Value; LocalMirror.StayInPlace = MirrorStayInPlace.Value; BuildBoneMenu(); } private static void BuildBoneMenu() { //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_002a: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Unknown result type (might be due to invalid IL or missing references) //IL_004f: 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_0134: Unknown result type (might be due to invalid IL or missing references) //IL_0172: Unknown result type (might be due to invalid IL or missing references) //IL_01b0: Unknown result type (might be due to invalid IL or missing references) //IL_01ee: Unknown result type (might be due to invalid IL or missing references) //IL_022c: Unknown result type (might be due to invalid IL or missing references) //IL_026a: Unknown result type (might be due to invalid IL or missing references) //IL_02ed: Unknown result type (might be due to invalid IL or missing references) //IL_032b: Unknown result type (might be due to invalid IL or missing references) //IL_0369: Unknown result type (might be due to invalid IL or missing references) //IL_03a7: Unknown result type (might be due to invalid IL or missing references) Color endColor = default(Color); ((Color)(ref endColor))..ctor(0.75f, 0.75f, 0.75f, 1f); Page val2 = Page.Root.CreatePage(BuildGradientText("LocalMirror", Color.white, endColor), Color.white, 0, true); BoneMenuScrollClamp.Register(val2); BoneMenuScrollButtons.Register(val2); _localMirrorToggleElement = val2.CreateBool("Local Mirror", Color.green, LocalMirror.Enabled, (Action)delegate(bool val) { if (val) { LocalMirror.Enable(); } else { LocalMirror.Disable(); } }); try { LocalMirror.OnEnabledChanged += delegate(bool newState) { try { if (_localMirrorToggleElement != null) { _localMirrorToggleElement.Value = newState; } } catch { } }; } catch { } MenuSliderHelper.RegisterSliderWithType(val2, "Mirror Distance", MirrorDistance.Value, 0.1f, 0.3f, 3f, delegate(float val) { MirrorDistance.Value = val; _category.SaveToFile(false); LocalMirror.Distance = val; }); _mirrorScaleByHeightElement = val2.CreateBool("Distance scales with height", Color.green, MirrorScaleByHeight.Value, (Action)delegate(bool val) { MirrorScaleByHeight.Value = val; _category.SaveToFile(false); LocalMirror.ScaleByAvatarHeight = val; }); _mirrorFollowHeadElement = val2.CreateBool("Mirror follows head", Color.green, MirrorFollowHead.Value, (Action)delegate(bool val) { MirrorFollowHead.Value = val; _category.SaveToFile(false); LocalMirror.FollowHead = val; }); _mirrorStayInPlaceElement = val2.CreateBool("Mirror stays in place", Color.green, MirrorStayInPlace.Value, (Action)delegate(bool val) { MirrorStayInPlace.Value = val; _category.SaveToFile(false); LocalMirror.StayInPlace = val; }); _showHolsteredElement = val2.CreateBool("Show Holstered Items", Color.green, LocalMirrorShowHolsteredEnabled.Value, (Action)delegate(bool val) { LocalMirrorShowHolsteredEnabled.Value = val; _category.SaveToFile(false); }); _heldItemAwarenessElement = val2.CreateBool("Held Item Awareness", Color.green, LocalMirrorHeldItemAwarenessEnabled.Value, (Action)delegate(bool val) { LocalMirrorHeldItemAwarenessEnabled.Value = val; _category.SaveToFile(false); }); _seatAwarenessElement = val2.CreateBool("Seat Awareness", Color.green, LocalMirrorSeatAwarenessEnabled.Value, (Action)delegate(bool val) { LocalMirrorSeatAwarenessEnabled.Value = val; _category.SaveToFile(false); }); _proximityAwarenessElement = val2.CreateBool("Proximity Awareness", Color.green, LocalMirrorProximityAwarenessEnabled.Value, (Action)delegate(bool val) { LocalMirrorProximityAwarenessEnabled.Value = val; _category.SaveToFile(false); }); MenuSliderHelper.RegisterSliderWithType(val2, "Proximity Radius (m)", LocalMirrorProximityRadius.Value, 0.1f, 0.1f, 30f, delegate(float val) { LocalMirrorProximityRadius.Value = val; _category.SaveToFile(false); }); _proximityVisualElement = val2.CreateBool("Proximity Visual", Color.green, LocalMirrorProximityVisualEnabled.Value, (Action)delegate(bool val) { LocalMirrorProximityVisualEnabled.Value = val; _category.SaveToFile(false); }); _includeOthersElement = val2.CreateBool("Include Others", Color.green, LocalMirrorIncludeOthersEnabled.Value, (Action)delegate(bool val) { LocalMirrorIncludeOthersEnabled.Value = val; _category.SaveToFile(false); }); _showFusionCosmeticsElement = val2.CreateBool("Show Fusion Cosmetics", Color.green, ShowFusionCosmeticsEnabled.Value, (Action)delegate(bool val) { ShowFusionCosmeticsEnabled.Value = val; _category.SaveToFile(false); }); val2.CreateFunction("Reset To Default", Color.red, (Action)ResetAllTogglesToDefault); } private static void ResetAllTogglesToDefault() { try { LocalMirror.Disable(); } catch { } ApplySliderPref(MirrorDistance, 1.5f); LocalMirror.Distance = 1.5f; MenuSliderHelper.ResetSlider("Mirror Distance", 1.5f); ApplyBoolDefault(_mirrorScaleByHeightElement, MirrorScaleByHeight, defaultValue: true, delegate { LocalMirror.ScaleByAvatarHeight = true; }, delegate { LocalMirror.ScaleByAvatarHeight = false; }); ApplyBoolDefault(_mirrorFollowHeadElement, MirrorFollowHead, defaultValue: false, delegate { LocalMirror.FollowHead = true; }, delegate { LocalMirror.FollowHead = false; }); ApplyBoolDefault(_mirrorStayInPlaceElement, MirrorStayInPlace, defaultValue: false, delegate { LocalMirror.StayInPlace = true; }, delegate { LocalMirror.StayInPlace = false; }); ApplyBoolDefault(_showHolsteredElement, LocalMirrorShowHolsteredEnabled, defaultValue: true, null, null); ApplyBoolDefault(_heldItemAwarenessElement, LocalMirrorHeldItemAwarenessEnabled, defaultValue: true, null, null); ApplyBoolDefault(_seatAwarenessElement, LocalMirrorSeatAwarenessEnabled, defaultValue: true, null, null); ApplyBoolDefault(_proximityAwarenessElement, LocalMirrorProximityAwarenessEnabled, defaultValue: false, null, null); ApplySliderPref(LocalMirrorProximityRadius, 2f); MenuSliderHelper.ResetSlider("Proximity Radius (m)", 2f); ApplyBoolDefault(_proximityVisualElement, LocalMirrorProximityVisualEnabled, defaultValue: true, null, null); ApplyBoolDefault(_includeOthersElement, LocalMirrorIncludeOthersEnabled, defaultValue: false, null, null); ApplyBoolDefault(_showFusionCosmeticsElement, ShowFusionCosmeticsEnabled, defaultValue: false, null, null); _category.SaveToFile(false); } private static void ApplyBoolDefault(BoolElement element, MelonPreferences_Entry pref, bool defaultValue, Action apply, Action revert) { if (pref != null) { pref.Value = defaultValue; } if (element != null) { element.Value = defaultValue; } try { if (defaultValue) { apply?.Invoke(); } else { revert?.Invoke(); } } catch (Exception ex) { MelonLogger.Warning("[LocalMirror] Reset toggle apply failed: " + ex.Message); } } private static void ApplySliderPref(MelonPreferences_Entry pref, float defaultValue) { if (pref != null) { pref.Value = defaultValue; } } private static string BuildGradientText(string text, Color startColor, Color endColor) { //IL_003a: 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_003d: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Unknown result type (might be due to invalid IL or missing references) //IL_005c: Unknown result type (might be due to invalid IL or missing references) if (string.IsNullOrEmpty(text)) { return text; } StringBuilder stringBuilder = new StringBuilder(text.Length * 22); int length = text.Length; for (int i = 0; i < length; i++) { float num = ((length > 1) ? ((float)i / (float)(length - 1)) : 0f); Color val = Color.Lerp(startColor, endColor, num); int num2 = Mathf.Clamp((int)(val.r * 255f), 0, 255); int num3 = Mathf.Clamp((int)(val.g * 255f), 0, 255); int num4 = Mathf.Clamp((int)(val.b * 255f), 0, 255); stringBuilder.Append("') .Append(text[i]) .Append(""); } return stringBuilder.ToString(); } } public class Main : MelonMod { public const string Version = "1.0.0"; public override void OnInitializeMelon() { ((MelonBase)this).LoggerInstance.Msg("LocalMirror v1.0.0 loading..."); Config.Initialize(); Hooking.OnLevelLoaded += OnLevelLoaded; Hooking.OnSwitchAvatarPostfix += OnAvatarChanged; ((MelonBase)this).LoggerInstance.Msg("LocalMirror v1.0.0 loaded!"); } public override void OnUpdate() { try { LocalMirror.OnUpdate(); } catch { } try { RadialToggle.OnUpdate(); } catch { } try { BoneMenuScrollClamp.OnUpdate(); } catch { } try { MenuSliderHelper.OnUpdate(); } catch { } } public override void OnFixedUpdate() { } public override void OnLateUpdate() { try { LocalMirror.LateEnforce(); } catch { } } private static void OnLevelLoaded(LevelInfo levelInfo) { try { LocalMirror.OnLevelLoaded(); } catch { } try { RadialToggle.OnLevelLoaded(); } catch { } } private static void OnAvatarChanged(Avatar avatar) { try { LocalMirror.OnAvatarChanged(avatar); } catch { } } } } namespace LocalMirrorMod.Fixes { public static class BoneMenuScrollButtons { private static Page _page; private static GameObject _navContainer; private static Sprite _fillSprite; private static Sprite _borderSprite; public static void Register(Page page) { _page = page; Menu.OnPageOpened += OnPageOpened; } private static void OnPageOpened(Page page) { if (page == _page) { if ((Object)(object)_navContainer == (Object)null) { CreateNavButtons(); } if ((Object)(object)_navContainer != (Object)null) { _navContainer.SetActive(true); } } else if ((Object)(object)_navContainer != (Object)null) { _navContainer.SetActive(false); } } private static void CreateNavButtons() { //IL_00f2: Unknown result type (might be due to invalid IL or missing references) //IL_00fe: Unknown result type (might be due to invalid IL or missing references) //IL_010c: Unknown result type (might be due to invalid IL or missing references) //IL_011a: Unknown result type (might be due to invalid IL or missing references) //IL_015b: Unknown result type (might be due to invalid IL or missing references) //IL_0172: Unknown result type (might be due to invalid IL or missing references) //IL_01a1: Unknown result type (might be due to invalid IL or missing references) //IL_01ab: Expected O, but got Unknown //IL_01c9: Unknown result type (might be due to invalid IL or missing references) //IL_01d6: Unknown result type (might be due to invalid IL or missing references) //IL_01eb: Unknown result type (might be due to invalid IL or missing references) //IL_01f8: Unknown result type (might be due to invalid IL or missing references) //IL_0204: Unknown result type (might be due to invalid IL or missing references) //IL_0212: Unknown result type (might be due to invalid IL or missing references) //IL_02d5: Unknown result type (might be due to invalid IL or missing references) //IL_0327: Unknown result type (might be due to invalid IL or missing references) //IL_0331: Unknown result type (might be due to invalid IL or missing references) //IL_033d: Unknown result type (might be due to invalid IL or missing references) //IL_03a1: Unknown result type (might be due to invalid IL or missing references) //IL_03a6: Unknown result type (might be due to invalid IL or missing references) //IL_03be: Unknown result type (might be due to invalid IL or missing references) //IL_03de: Unknown result type (might be due to invalid IL or missing references) //IL_03fe: Unknown result type (might be due to invalid IL or missing references) //IL_041e: Unknown result type (might be due to invalid IL or missing references) //IL_0442: Unknown result type (might be due to invalid IL or missing references) //IL_04cb: Unknown result type (might be due to invalid IL or missing references) //IL_04d0: Unknown result type (might be due to invalid IL or missing references) //IL_04e3: Unknown result type (might be due to invalid IL or missing references) //IL_04ea: Unknown result type (might be due to invalid IL or missing references) //IL_04f5: Unknown result type (might be due to invalid IL or missing references) //IL_0500: Unknown result type (might be due to invalid IL or missing references) //IL_050a: Unknown result type (might be due to invalid IL or missing references) //IL_053e: Unknown result type (might be due to invalid IL or missing references) //IL_0555: Unknown result type (might be due to invalid IL or missing references) //IL_055a: Unknown result type (might be due to invalid IL or missing references) //IL_056d: Unknown result type (might be due to invalid IL or missing references) //IL_0574: Unknown result type (might be due to invalid IL or missing references) //IL_057f: Unknown result type (might be due to invalid IL or missing references) //IL_058a: Unknown result type (might be due to invalid IL or missing references) //IL_0594: Unknown result type (might be due to invalid IL or missing references) //IL_05bc: Unknown result type (might be due to invalid IL or missing references) //IL_04b4: Unknown result type (might be due to invalid IL or missing references) try { GUIMenu instance = GUIMenu.Instance; if ((Object)(object)instance == (Object)null) { return; } Transform val = ((Component)instance).transform.Find("Page/Content"); if ((Object)(object)val == (Object)null) { return; } Transform val2 = val.Find("Interaction"); if ((Object)(object)val2 == (Object)null) { return; } Transform val3 = val2.Find("ScrollUp"); Transform val4 = val2.Find("ScrollDown"); if ((Object)(object)val3 == (Object)null || (Object)(object)val4 == (Object)null) { return; } Transform val5 = val.Find("Viewport"); ScrollRect scrollRect = (((Object)(object)val5 != (Object)null) ? ((Component)val5).GetComponent() : null); if ((Object)(object)scrollRect == (Object)null) { return; } TMP_FontAsset val6 = null; TextMeshProUGUI componentInChildren = ((Component)val).GetComponentInChildren(); if ((Object)(object)componentInChildren != (Object)null) { val6 = ((TMP_Text)componentInChildren).font; } RectTransform component = ((Component)val3).GetComponent(); RectTransform component2 = ((Component)val4).GetComponent(); float y = component.anchoredPosition.y; float y2 = component2.anchoredPosition.y; float num = component.sizeDelta.y; float num2 = component.sizeDelta.x; if (num2 < 1f) { num2 = 40f; } if (num < 1f) { num = 40f; } EnsureSprites(); float num3 = (y + y2) / 2f; float num4 = y - num * component.pivot.y; float num5 = y2 + num * (1f - component2.pivot.y); float num6 = Mathf.Abs(num4 - num5); float num7 = 2f; float num8 = num2 * 6f; _navContainer = new GameObject("LocalMirror_NavButtons"); _navContainer.transform.SetParent(val2, false); RectTransform obj = _navContainer.AddComponent(); obj.anchorMin = component.anchorMin; obj.anchorMax = component.anchorMax; obj.pivot = new Vector2(0.5f, 0.5f); obj.anchoredPosition = new Vector2(component.anchoredPosition.x, num3); obj.sizeDelta = new Vector2(num8, num6); VerticalLayoutGroup obj2 = _navContainer.AddComponent(); ((LayoutGroup)obj2).childAlignment = (TextAnchor)4; ((HorizontalOrVerticalLayoutGroup)obj2).childControlWidth = true; ((HorizontalOrVerticalLayoutGroup)obj2).childControlHeight = true; ((HorizontalOrVerticalLayoutGroup)obj2).childForceExpandWidth = true; ((HorizontalOrVerticalLayoutGroup)obj2).childForceExpandHeight = true; ((HorizontalOrVerticalLayoutGroup)obj2).spacing = num7; string[] array = new string[5] { "Top", "Upper", "Middle", "Lower", "Bottom" }; float[] array2 = new float[5] { 0f, 0.25f, 0.5f, 0.75f, 1f }; GameObject gameObject = ((Component)val3).gameObject; for (int i = 0; i < 5; i++) { float num9 = array2[i]; string text = array[i]; GameObject val7 = Object.Instantiate(gameObject, _navContainer.transform); ((Object)val7).name = text; val7.transform.localRotation = Quaternion.identity; LayoutElement component3 = val7.GetComponent(); if ((Object)(object)component3 != (Object)null) { Object.Destroy((Object)(object)component3); } BoxCollider component4 = val7.GetComponent(); if ((Object)(object)component4 != (Object)null) { float num10 = (num6 - num7 * 4f) / 5f; component4.size = new Vector3(num8, num10, component4.size.z); component4.center = Vector3.zero; } Button component5 = val7.GetComponent