using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text.RegularExpressions; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using HarmonyLib; using Microsoft.CodeAnalysis; using TMPro; using UnityEngine; using UnityEngine.SceneManagement; using UnityEngine.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("BetterPlayerDistance")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyDescription("High Performance Distance Display")] [assembly: AssemblyFileVersion("0.1.15.0")] [assembly: AssemblyInformationalVersion("0.1.15+1ab1609b58ebf16f635f7263a765678f8834176e")] [assembly: AssemblyProduct("BetterPlayerDistance")] [assembly: AssemblyTitle("BetterPlayerDistance")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("0.1.15.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 BetterPlayerDistance { public enum TriggerModeEnum { Toggle, Hold, AlwaysOn } public static class Configuration { public static ConfigEntry ShowName; public static ConfigEntry ShowDistance; public static ConfigEntry ToggleKey; public static ConfigEntry TriggerMode; public static ConfigEntry ToggleDuration; public static ConfigEntry HoldKeepDuration; public static ConfigEntry MinDistance; public static ConfigEntry MaxDistance; public static ConfigEntry NameFontSize; public static ConfigEntry DistFontSize; public static ConfigEntry GlobalOpacity; public const float FixedShadowSpread = 1.5f; public const float FixedShadowAlpha = 0.8f; public const bool FixedHighQuality = false; public static readonly Color FixedShadowColor = new Color(0.267f, 0.275f, 0.216f, 1f); public static ConfigEntry DebugMode; public static ConfigEntry DebugMenuKey; public static ConfigEntry DisableTMPWarnings; private const string CAT_BASIC = "1. 基础 (Basic)"; private const string CAT_UI = "2. 界面 (UI)"; private const string CAT_DEBUG = "3. 调试 (Debug)"; public static void Initialize(ConfigFile config) { //IL_0033: Unknown result type (might be due to invalid IL or missing references) //IL_003d: Expected O, but got Unknown //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0075: Expected O, but got Unknown //IL_00a3: Unknown result type (might be due to invalid IL or missing references) //IL_00ad: Expected O, but got Unknown //IL_0111: Unknown result type (might be due to invalid IL or missing references) //IL_011b: Expected O, but got Unknown //IL_0149: Unknown result type (might be due to invalid IL or missing references) //IL_0153: Expected O, but got Unknown //IL_0181: Unknown result type (might be due to invalid IL or missing references) //IL_018b: Expected O, but got Unknown //IL_01b9: Unknown result type (might be due to invalid IL or missing references) //IL_01c3: Expected O, but got Unknown //IL_01f1: Unknown result type (might be due to invalid IL or missing references) //IL_01fb: Expected O, but got Unknown ToggleKey = config.Bind("1. 基础 (Basic)", "快捷键 (Hotkey)", (KeyCode)99, "显示/隐藏玩家标签的按键(常显模式下忽略)。\nToggle player labels on/off (ignored in AlwaysOn mode)."); TriggerMode = config.Bind("1. 基础 (Basic)", "显示模式 (Display Mode)", TriggerModeEnum.Hold, new ConfigDescription("Hold=按住显示;Toggle=切换开关;AlwaysOn=常显(始终显示所有在场玩家)。\nHold = press to show; Toggle = press to switch; AlwaysOn = always display every in-game player.", (AcceptableValueBase)null, Array.Empty())); ToggleDuration = config.Bind("1. 基础 (Basic)", "切换显示时长 (Toggle Duration)", 10f, new ConfigDescription("Toggle 模式下按一次后保持显示的秒数。\nHow many seconds labels stay visible after a single press in Toggle mode.", (AcceptableValueBase)(object)new AcceptableValueRange(10f, 9999f), Array.Empty())); HoldKeepDuration = config.Bind("1. 基础 (Basic)", "松手保持时长 (Hold Release Linger)", 1f, new ConfigDescription("Hold 模式下松开按键后继续显示的秒数。\nHow many extra seconds labels linger after the key is released in Hold mode.", (AcceptableValueBase)(object)new AcceptableValueRange(0f, 10f), Array.Empty())); ShowName = config.Bind("2. 界面 (UI)", "显示名称 (Show Name)", true, "是否显示玩家名字。\nWhether to display the player name."); ShowDistance = config.Bind("2. 界面 (UI)", "显示距离 (Show Distance)", true, "是否显示距离数值。\nWhether to display the distance number."); MinDistance = config.Bind("2. 界面 (UI)", "最小显示距离 (Min Display Distance)", 15f, new ConfigDescription("小于此距离不显示(米)。\nPlayers closer than this distance are hidden (meters).", (AcceptableValueBase)(object)new AcceptableValueRange(0f, 50f), Array.Empty())); MaxDistance = config.Bind("2. 界面 (UI)", "最大显示距离 (Max Display Distance)", 1000f, new ConfigDescription("超过此距离不显示(米)。\nPlayers farther than this distance are hidden (meters).", (AcceptableValueBase)(object)new AcceptableValueRange(50f, 1500f), Array.Empty())); NameFontSize = config.Bind("2. 界面 (UI)", "名字字号 (Name Font Size)", 16f, new ConfigDescription("玩家名字字体大小。\nFont size for the player name.", (AcceptableValueBase)(object)new AcceptableValueRange(9f, 60f), Array.Empty())); DistFontSize = config.Bind("2. 界面 (UI)", "距离字号 (Distance Font Size)", 17f, new ConfigDescription("距离数值字体大小。\nFont size for the distance number.", (AcceptableValueBase)(object)new AcceptableValueRange(9f, 60f), Array.Empty())); GlobalOpacity = config.Bind("2. 界面 (UI)", "整体透明度 (Global Opacity)", 0.85f, new ConfigDescription("整体不透明度 (0-1)。\nOverall opacity (0-1).", (AcceptableValueBase)(object)new AcceptableValueRange(0f, 1f), Array.Empty())); DebugMode = config.Bind("3. 调试 (Debug)", "启用调试工具 (Enable Debug Tools)", true, "Insert 键呼出调试控制台。\nPress Insert to summon the debug console."); DebugMenuKey = config.Bind("3. 调试 (Debug)", "调试菜单键 (Debug Menu Key)", (KeyCode)277, "打开调试控制台的按键。\nKey used to open the debug console."); DisableTMPWarnings = config.Bind("3. 调试 (Debug)", "禁用全局TMP缺字警告 (Disable TMP Missing-Glyph Warnings)", true, "开启后将禁止 TextMeshPro 向控制台输出缺字警告,可显著解决特殊字符导致的掉帧问题(开发者请关闭)。\nWhen on, suppresses TextMeshPro missing-glyph warnings to avoid console spam and frame drops (developers should disable this)."); } } public class OverlayManager { private Canvas _canvas; private GameObject _labelPrefab; private Transform _canvasTransform; private List _availableFonts = new List(); private int _currentFontIndex; private TMP_FontAsset _currentFont; private readonly Dictionary _activeLabels = new Dictionary(); private bool _shouldShowLabels; private float _hideTimeTimestamp; private bool _initialized; private float _lastGlobalOpacity = -1f; private bool _lastDisableWarnings = true; private TriggerModeEnum _lastTriggerMode; private float _nextFontCheckTime; private bool _isUsingFallbackFont; public int ActiveCount => _activeLabels.Count; public string CurrentFontName { get { if (!((Object)(object)_currentFont != (Object)null)) { return "None"; } return ((Object)_currentFont).name; } } public OverlayManager() { SceneManager.sceneLoaded += OnSceneLoaded; } public void Dispose() { SceneManager.sceneLoaded -= OnSceneLoaded; ClearAllLabels(); if ((Object)(object)_canvas != (Object)null) { Object.Destroy((Object)(object)((Component)_canvas).gameObject); } } public void TryInitialize() { if (_initialized) { return; } try { CreateCanvasSystem(); _initialized = true; Plugin.Log.LogInfo((object)"OverlayManager: Initialized."); } catch (Exception arg) { Plugin.Log.LogError((object)$"Init Failed: {arg}"); } } private void OnSceneLoaded(Scene scene, LoadSceneMode mode) { ClearAllLabels(); _availableFonts.Clear(); _initialized = false; } private void ClearAllLabels() { foreach (PlayerLabel value in _activeLabels.Values) { value.Destroy(); } _activeLabels.Clear(); } public void UpdateInput() { if (!_initialized || (Object)(object)_canvas == (Object)null) { TryInitialize(); } else { HandleInput(); } } public void LateUpdate() { if (Configuration.ShowName == null || Configuration.ShowDistance == null) { return; } if (!Configuration.ShowName.Value && !Configuration.ShowDistance.Value) { if (_activeLabels.Count > 0) { ClearAllLabels(); } } else { if (!_initialized || (Object)(object)_canvas == (Object)null) { return; } if (Configuration.DisableTMPWarnings != null && _lastDisableWarnings != Configuration.DisableTMPWarnings.Value) { ApplyTMPSettings(); _lastDisableWarnings = Configuration.DisableTMPWarnings.Value; } if (_isUsingFallbackFont && Time.time > _nextFontCheckTime) { _nextFontCheckTime = Time.time + 1f; TryFindBetterFont(); } bool flag = Mathf.Abs(_lastGlobalOpacity - Configuration.GlobalOpacity.Value) > 0.01f; foreach (int item in _activeLabels.Keys.ToList()) { PlayerLabel playerLabel = _activeLabels[item]; if (!playerLabel.IsValid()) { playerLabel.SetVisible(visible: false); continue; } if (flag) { playerLabel.RefreshStyle(); } playerLabel.UpdateState(_shouldShowLabels); } if (flag) { _lastGlobalOpacity = Configuration.GlobalOpacity.Value; } } } public void RegisterCharacter(Character c) { if (!_initialized) { TryInitialize(); } if (!((Object)(object)c == (Object)null) && !((Object)(object)c == (Object)(object)Character.localCharacter)) { string text = Tracking.ExtractDisplayName(((Object)c).name); if (!(text == "Bot")) { Transform val = ((Component)c).transform.Find("Scout/Misc/CharacterLight"); Transform trackTarget = (((Object)(object)val != (Object)null) ? val : ((Component)c).transform); RegisterGenericTarget(((Component)c).gameObject, trackTarget, text); } } } public void RegisterFakeTarget(GameObject root, string customName) { if (!_initialized) { TryInitialize(); } if (!((Object)(object)root == (Object)null)) { Transform val = root.transform.Find("Scout/Misc/CharacterLight"); Transform trackTarget = (((Object)(object)val != (Object)null) ? val : root.transform); RegisterGenericTarget(root, trackTarget, customName); } } private void RegisterGenericTarget(GameObject owner, Transform trackTarget, string displayName) { int instanceID = ((Object)owner).GetInstanceID(); if (!_activeLabels.ContainsKey(instanceID)) { if ((Object)(object)_currentFont == (Object)null) { InitializeFonts(); } GameObject val = Object.Instantiate(_labelPrefab, _canvasTransform); val.SetActive(true); SetLayerRecursively(val, 5); PlayerLabel value = new PlayerLabel(trackTarget, val, _currentFont, displayName); _activeLabels.Add(instanceID, value); } } public void UnregisterCharacter(GameObject owner) { if (!((Object)(object)owner == (Object)null)) { int instanceID = ((Object)owner).GetInstanceID(); if (_activeLabels.TryGetValue(instanceID, out var value)) { value.Destroy(); _activeLabels.Remove(instanceID); } } } public void UnregisterTarget(GameObject owner) { UnregisterCharacter(owner); } public void CycleFont(int direction) { if (_availableFonts.Count == 0) { InitializeFonts(); } if (_availableFonts.Count == 0) { return; } _currentFontIndex += direction; if (_currentFontIndex >= _availableFonts.Count) { _currentFontIndex = 0; } if (_currentFontIndex < 0) { _currentFontIndex = _availableFonts.Count - 1; } _currentFont = _availableFonts[_currentFontIndex]; _isUsingFallbackFont = false; foreach (PlayerLabel value in _activeLabels.Values) { value.SetFont(_currentFont); } Plugin.Log.LogInfo((object)("Switched Font to: " + ((Object)_currentFont).name)); } private void HandleInput() { //IL_006a: 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_0115: Unknown result type (might be due to invalid IL or missing references) if (Configuration.TriggerMode == null) { return; } TriggerModeEnum value = Configuration.TriggerMode.Value; if (value != _lastTriggerMode) { _hideTimeTimestamp = 0f; _shouldShowLabels = false; _lastTriggerMode = value; Plugin.Log.LogInfo((object)$"Mode changed to {value}, state reset."); } switch (value) { case TriggerModeEnum.AlwaysOn: _shouldShowLabels = true; return; case TriggerModeEnum.Toggle: if (Configuration.ToggleKey != null && Input.GetKeyDown(Configuration.ToggleKey.Value)) { float num = ((Configuration.ToggleDuration != null) ? Configuration.ToggleDuration.Value : 10f); if (Time.time < _hideTimeTimestamp) { _hideTimeTimestamp = Time.time; } else { _hideTimeTimestamp = Time.time + num; } } _shouldShowLabels = Time.time < _hideTimeTimestamp; return; } float num2 = ((Configuration.HoldKeepDuration != null) ? Configuration.HoldKeepDuration.Value : 1f); if (Configuration.ToggleKey != null) { if (Input.GetKey(Configuration.ToggleKey.Value)) { _hideTimeTimestamp = Time.time + num2 + 0.1f; } else if (Input.GetKeyUp(Configuration.ToggleKey.Value)) { _hideTimeTimestamp = Time.time + num2; } } _shouldShowLabels = Time.time < _hideTimeTimestamp; } private void CreateCanvasSystem() { //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Expected O, but got Unknown //IL_0072: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_canvas != (Object)null)) { ApplyTMPSettings(); InitializeFonts(); GameObject val = new GameObject("DistanceDisplayCanvas"); Object.DontDestroyOnLoad((Object)(object)val); val.layer = 5; _canvas = val.AddComponent(); _canvas.renderMode = (RenderMode)0; _canvas.sortingOrder = 999; CanvasScaler obj = val.AddComponent(); obj.uiScaleMode = (ScaleMode)1; obj.referenceResolution = new Vector2(1920f, 1080f); val.AddComponent(); _canvasTransform = val.transform; CreateLabelPrefab(); } } private void ApplyTMPSettings() { if (Configuration.DisableTMPWarnings == null || !Configuration.DisableTMPWarnings.Value) { return; } try { TMP_Settings val = Resources.Load("TMP Settings"); if ((Object)(object)val == (Object)null) { val = Resources.FindObjectsOfTypeAll().FirstOrDefault(); } if (!((Object)(object)val != (Object)null)) { return; } FieldInfo field = typeof(TMP_Settings).GetField("m_warningsDisabled", BindingFlags.Instance | BindingFlags.NonPublic); if (field != null) { field.SetValue(val, true); Plugin.Log.LogInfo((object)"TMP Warnings disabled (Reflection)."); return; } PropertyInfo property = typeof(TMP_Settings).GetProperty("warningsDisabled", BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public); if (property != null && property.CanWrite) { property.SetValue(val, true); } } catch (Exception) { } } private void InitializeFonts() { _availableFonts.Clear(); try { TMP_FontAsset[] array = Resources.FindObjectsOfTypeAll(); if (array != null) { TMP_FontAsset[] array2 = array; foreach (TMP_FontAsset val in array2) { if ((Object)(object)val != (Object)null && !string.IsNullOrEmpty(((Object)val).name) && (Object)(object)val.atlasTexture != (Object)null) { _availableFonts.Add(val); } } } _availableFonts.Sort((TMP_FontAsset a, TMP_FontAsset b) => string.Compare(((Object)a).name, ((Object)b).name)); } catch { } if (_availableFonts.Count > 0) { TMP_FontAsset val2 = ((IEnumerable)_availableFonts).FirstOrDefault((Func)((TMP_FontAsset f) => ((Object)f).name.IndexOf("Daruma", StringComparison.OrdinalIgnoreCase) >= 0)) ?? ((IEnumerable)_availableFonts).FirstOrDefault((Func)((TMP_FontAsset f) => ((Object)f).name.IndexOf("Noto", StringComparison.OrdinalIgnoreCase) >= 0)) ?? ((IEnumerable)_availableFonts).FirstOrDefault((Func)((TMP_FontAsset f) => ((Object)f).name.IndexOf("Liberation", StringComparison.OrdinalIgnoreCase) >= 0)); if ((Object)(object)val2 != (Object)null) { _currentFont = val2; _currentFontIndex = _availableFonts.IndexOf(val2); } else { _currentFont = _availableFonts[0]; _currentFontIndex = 0; } if (((Object)_currentFont).name.IndexOf("Daruma", StringComparison.OrdinalIgnoreCase) >= 0) { _isUsingFallbackFont = false; } else { _isUsingFallbackFont = true; } } } private void TryFindBetterFont() { try { TMP_FontAsset val = ((IEnumerable)Resources.FindObjectsOfTypeAll()).FirstOrDefault((Func)((TMP_FontAsset f) => (Object)(object)f != (Object)null && ((Object)f).name.IndexOf("Daruma", StringComparison.OrdinalIgnoreCase) >= 0 && (Object)(object)f.atlasTexture != (Object)null)); if (!((Object)(object)val != (Object)null)) { return; } if (!_availableFonts.Contains(val)) { _availableFonts.Add(val); } _availableFonts.Sort((TMP_FontAsset a, TMP_FontAsset b) => string.Compare(((Object)a).name, ((Object)b).name)); _currentFont = val; _currentFontIndex = _availableFonts.IndexOf(val); _isUsingFallbackFont = false; foreach (PlayerLabel value in _activeLabels.Values) { value.SetFont(_currentFont); } Plugin.Log.LogInfo((object)("Auto-recovered Font to: " + ((Object)val).name)); } catch { } } private void CreateLabelPrefab() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0010: Expected O, but got Unknown _labelPrefab = new GameObject("LabelPrefab"); _labelPrefab.transform.SetParent(_canvasTransform); _labelPrefab.layer = 5; _labelPrefab.SetActive(false); CanvasGroup obj = _labelPrefab.AddComponent(); obj.alpha = 0f; obj.blocksRaycasts = false; obj.interactable = false; } private void SetLayerRecursively(GameObject obj, int newLayer) { //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_002b: Expected O, but got Unknown if ((Object)(object)obj == (Object)null) { return; } obj.layer = newLayer; foreach (Transform item in obj.transform) { Transform val = item; if ((Object)(object)val != (Object)null) { SetLayerRecursively(((Component)val).gameObject, newLayer); } } } } public class PlayerLabel { private Transform _targetPoint; private GameObject _rootObj; private RectTransform _rootRect; private CanvasGroup _canvasGroup; private TextMeshProUGUI _mainText; private List _shadowTexts = new List(); private string _displayName; private Camera _mainCam; private const float FADE_TIME = 0.4f; private static readonly Regex ColorTagRegex = new Regex("|<\\/color>", RegexOptions.IgnoreCase); private readonly Vector2[] _offsets = (Vector2[])(object)new Vector2[8] { new Vector2(0f, 1f), new Vector2(0f, -1f), new Vector2(-1f, 0f), new Vector2(1f, 0f), new Vector2(-1f, 1f), new Vector2(1f, 1f), new Vector2(-1f, -1f), new Vector2(1f, -1f) }; public PlayerLabel(Transform target, GameObject rootUiObj, TMP_FontAsset font, string name) { //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0023: 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_004a: 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_0060: Unknown result type (might be due to invalid IL or missing references) //IL_0065: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_007b: 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_0091: Unknown result type (might be due to invalid IL or missing references) //IL_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00a7: Unknown result type (might be due to invalid IL or missing references) //IL_00b8: Unknown result type (might be due to invalid IL or missing references) //IL_00bd: Unknown result type (might be due to invalid IL or missing references) //IL_0124: Unknown result type (might be due to invalid IL or missing references) //IL_0129: Unknown result type (might be due to invalid IL or missing references) //IL_013f: Unknown result type (might be due to invalid IL or missing references) //IL_016d: Unknown result type (might be due to invalid IL or missing references) //IL_0173: Expected O, but got Unknown _targetPoint = target; _rootObj = rootUiObj; _rootRect = _rootObj.GetComponent(); _canvasGroup = _rootObj.GetComponent(); _displayName = name; _mainCam = Camera.main; for (int i = 0; i < 8; i++) { GameObject val = new GameObject($"Shadow_{i}"); val.transform.SetParent(_rootObj.transform); val.layer = 5; TextMeshProUGUI val2 = val.AddComponent(); SetupTextCommon(val2, font); _shadowTexts.Add(val2); } GameObject val3 = new GameObject("MainText"); val3.transform.SetParent(_rootObj.transform); val3.layer = 5; _mainText = val3.AddComponent(); SetupTextCommon(_mainText, font); RefreshStyle(); } private void SetupTextCommon(TextMeshProUGUI tmp, TMP_FontAsset font) { //IL_003d: Unknown result type (might be due to invalid IL or missing references) ((TMP_Text)tmp).alignment = (TextAlignmentOptions)514; ((Graphic)tmp).raycastTarget = false; ((TMP_Text)tmp).overflowMode = (TextOverflowModes)0; ((TMP_Text)tmp).enableWordWrapping = false; ((TMP_Text)tmp).richText = true; if ((Object)(object)font != (Object)null) { ((TMP_Text)tmp).font = font; } ((TMP_Text)tmp).rectTransform.anchoredPosition = Vector2.zero; } public bool IsValid() { if ((Object)(object)_targetPoint != (Object)null) { return ((Component)_targetPoint).gameObject.activeInHierarchy; } return false; } public void SetFont(TMP_FontAsset font) { if ((Object)(object)_mainText != (Object)null) { ((TMP_Text)_mainText).font = font; } foreach (TextMeshProUGUI shadowText in _shadowTexts) { ((TMP_Text)shadowText).font = font; } } public void RefreshStyle() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Unknown result type (might be due to invalid IL or missing references) //IL_0064: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_007c: Unknown result type (might be due to invalid IL or missing references) _ = Configuration.FixedShadowColor; Color fixedShadowColor = Configuration.FixedShadowColor; fixedShadowColor.a = 0.8f; Color color = default(Color); ((Color)(ref color))..ctor(0.875f, 0.855f, 0.761f, 1f); ((Graphic)_mainText).color = color; float num = 1.5f; for (int i = 0; i < 8 && i < _shadowTexts.Count; i++) { TextMeshProUGUI obj = _shadowTexts[i]; ((Graphic)obj).color = fixedShadowColor; ((TMP_Text)obj).rectTransform.anchoredPosition = _offsets[i] * num; } } public void UpdateState(bool globalShow) { //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_007f: Unknown result type (might be due to invalid IL or missing references) //IL_0084: Unknown result type (might be due to invalid IL or missing references) //IL_0089: Unknown result type (might be due to invalid IL or missing references) //IL_0095: 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_00b1: Unknown result type (might be due to invalid IL or missing references) //IL_00b2: Unknown result type (might be due to invalid IL or missing references) //IL_00b7: Unknown result type (might be due to invalid IL or missing references) //IL_00e8: Unknown result type (might be due to invalid IL or missing references) //IL_00f5: Unknown result type (might be due to invalid IL or missing references) //IL_0102: Unknown result type (might be due to invalid IL or missing references) //IL_010f: Unknown result type (might be due to invalid IL or missing references) //IL_011c: Unknown result type (might be due to invalid IL or missing references) //IL_01b9: Unknown result type (might be due to invalid IL or missing references) //IL_01ba: Unknown result type (might be due to invalid IL or missing references) //IL_01bf: Unknown result type (might be due to invalid IL or missing references) //IL_01cc: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_rootObj == (Object)null || (Object)(object)_canvasGroup == (Object)null) { return; } if ((Object)(object)_mainCam == (Object)null) { _mainCam = Camera.main; } if ((Object)(object)_mainCam == (Object)null || (Object)(object)_targetPoint == (Object)null) { _canvasGroup.alpha = 0f; SetVisible(visible: false); return; } Vector3 val = _targetPoint.position + Vector3.up * 1.2f; float num = Vector3.Distance(((Component)_mainCam).transform.position, _targetPoint.position); Vector3 val2 = _mainCam.WorldToViewportPoint(val); bool flag = globalShow; if (Configuration.MinDistance != null && num < Configuration.MinDistance.Value) { flag = false; } else if (Configuration.MaxDistance != null && num > Configuration.MaxDistance.Value) { flag = false; } if (val2.z <= 0f || val2.x < 0f || val2.x > 1f || val2.y < 0f || val2.y > 1f) { _canvasGroup.alpha = 0f; SetVisible(visible: false); return; } float num2 = 2.5f; float num3 = ((Configuration.GlobalOpacity != null && flag) ? Configuration.GlobalOpacity.Value : 0f); float num4 = Mathf.MoveTowards(_canvasGroup.alpha, num3, num2 * Time.deltaTime); bool flag2 = flag || num4 > 0.01f; SetVisible(flag2); _canvasGroup.alpha = num4; if (!flag2) { return; } Vector3 position = _mainCam.WorldToScreenPoint(val); _rootObj.transform.position = position; string text = ""; if (Configuration.NameFontSize != null) { float value = Configuration.NameFontSize.Value; float value2 = Configuration.DistFontSize.Value; bool value3 = Configuration.ShowName.Value; bool value4 = Configuration.ShowDistance.Value; if (value3) { text += $"{_displayName}"; } if (value3 && value4) { text += "\n"; } if (value4) { text += $"{num:F0}m"; } } ((TMP_Text)_mainText).text = text; string text2 = ColorTagRegex.Replace(text, string.Empty); foreach (TextMeshProUGUI shadowText in _shadowTexts) { ((TMP_Text)shadowText).text = text2; } } public void SetVisible(bool visible) { if (!((Object)(object)_rootObj == (Object)null) && _rootObj.activeSelf != visible) { _rootObj.SetActive(visible); } } public void Destroy() { if ((Object)(object)_rootObj != (Object)null) { Object.Destroy((Object)(object)_rootObj); } } } [BepInPlugin("com.AiAe.betterplayerdistance", "Better Player Distance", "0.1.15")] public class Plugin : BaseUnityPlugin { public static Plugin Instance; public static ManualLogSource Log; public static OverlayManager Overlay; private Harmony _harmony; private bool _showDebugMenu; private string _debugNameInput = "测试员01"; private List _fakePlayers = new List(); private Rect _debugWindowRect = new Rect(20f, 20f, 350f, 500f); private bool _hasLoggedError; private bool _isConfigLoaded; private void Awake() { //IL_004b: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Expected O, but got Unknown Instance = this; Log = ((BaseUnityPlugin)this).Logger; try { Configuration.Initialize(((BaseUnityPlugin)this).Config); _isConfigLoaded = true; } catch (Exception arg) { Log.LogError((object)$"Config Init Failed: {arg}"); _isConfigLoaded = false; } try { _harmony = new Harmony("com.AiAe.betterplayerdistance"); _harmony.PatchAll(); } catch { } Overlay = new OverlayManager(); Log.LogInfo((object)"BetterPlayerDistance v0.1.15 (AIAE) Loaded."); } private void Start() { if (Overlay != null) { Overlay.TryInitialize(); } } private void Update() { //IL_0005: Unknown result type (might be due to invalid IL or missing references) if (Input.GetKeyDown(Configuration.DebugMenuKey.Value)) { _showDebugMenu = !_showDebugMenu; if (_showDebugMenu) { Cursor.visible = true; Cursor.lockState = (CursorLockMode)0; } } if (Overlay == null) { return; } try { Overlay.UpdateInput(); } catch (Exception arg) { if (!_hasLoggedError) { Log.LogError((object)$"Overlay Input Error: {arg}"); _hasLoggedError = true; } } } private void LateUpdate() { if (Overlay == null) { return; } try { Overlay.LateUpdate(); } catch (Exception arg) { if (!_hasLoggedError) { Log.LogError((object)$"Overlay Render Error: {arg}"); _hasLoggedError = true; } } } private void OnDestroy() { Harmony harmony = _harmony; if (harmony != null) { harmony.UnpatchSelf(); } Overlay?.Dispose(); } private void OnGUI() { //IL_003d: 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_005a: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Expected O, but got Unknown //IL_0064: 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 (!_showDebugMenu || !Configuration.DebugMode.Value) { return; } if (_showDebugMenu) { Cursor.visible = true; Cursor.lockState = (CursorLockMode)0; } GUI.backgroundColor = new Color(0.1f, 0.1f, 0.1f, 0.95f); try { _debugWindowRect = GUI.Window(888, _debugWindowRect, new WindowFunction(DrawDebugWindow), "调试控制台 / Debug Console [Insert]"); } catch { } } private void DrawDebugWindow(int windowID) { //IL_0014: Unknown result type (might be due to invalid IL or missing references) GUI.DragWindow(new Rect(0f, 0f, 10000f, 20f)); GUILayout.BeginVertical(Array.Empty()); GUILayout.Label("BetterPlayerDistance (AIAE) v0.1.15", Array.Empty()); if (!_isConfigLoaded) { GUILayout.Label("严重错误 / Fatal: 配置文件加载失败!Config init failed.", Array.Empty()); GUILayout.Label("请删除 BepInEx/config 下的 .cfg 文件并重启。\nDelete the .cfg under BepInEx/config and restart.", Array.Empty()); } else { string text = ((Configuration.TriggerMode != null) ? Configuration.TriggerMode.Value.ToString() : "Error"); GUILayout.Label("当前模式 / Mode: " + text + "", Array.Empty()); } GUILayout.Label(string.Format("状态 / State: {0} | 标签数 / Labels: {1}", (Overlay != null) ? "Active" : "Null", Overlay?.ActiveCount ?? 0), Array.Empty()); GUILayout.Label("字体 / Font: " + (Overlay?.CurrentFontName ?? "Unknown"), Array.Empty()); GUILayout.Space(5f); GUILayout.Label("--- 性能 / Performance ---", Array.Empty()); if (Configuration.DisableTMPWarnings != null) { string text2 = (Configuration.DisableTMPWarnings.Value ? "开启 / On" : "关闭 / Off"); if (GUILayout.Button("禁用TMP警告 / Disable TMP Warnings: [" + text2 + "]", Array.Empty())) { Configuration.DisableTMPWarnings.Value = !Configuration.DisableTMPWarnings.Value; } } else { GUILayout.Label("Config Error: DisableTMPWarnings is NULL", Array.Empty()); } GUILayout.Space(5f); GUILayout.Label("--- 假人测试 / Fake Players ---", Array.Empty()); _debugNameInput = GUILayout.TextField(_debugNameInput, 20, Array.Empty()); GUILayout.BeginHorizontal(Array.Empty()); if (GUILayout.Button("生成-前方 / Spawn (Front)", Array.Empty())) { SpawnFakeSafe(_debugNameInput, isColorful: false); } if (GUILayout.Button("生成-彩名 / Spawn (Colored)", Array.Empty())) { SpawnFakeSafe(_debugNameInput, isColorful: true); } GUILayout.EndHorizontal(); if (GUILayout.Button("清除所有假人 / Clear All Fakes", Array.Empty())) { ClearFakePlayers(); } GUILayout.Space(5f); GUILayout.Label("--- 工具 / Tools ---", Array.Empty()); if (GUILayout.Button("扫描全图实体 / Scan Entities (see console)", Array.Empty())) { ScanAllCharacters(); } GUILayout.Space(5f); GUILayout.Label("--- 实时预览 / Live Preview ---", Array.Empty()); if (GUILayout.Button("切换字体 / Cycle Font (Preview)", Array.Empty())) { Overlay.CycleFont(1); } GUILayout.EndVertical(); } private void ScanAllCharacters() { //IL_0047: 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) if (!((Object)(object)Camera.main == (Object)null)) { Character[] array = Object.FindObjectsOfType(); Log.LogInfo((object)$"--- 扫描开始: 发现 {array.Length} 个 Character 对象 ---"); Character[] array2 = array; foreach (Character val in array2) { float num = Vector3.Distance(((Component)Camera.main).transform.position, ((Component)val).transform.position); string name = ((Object)val).name; string text = Tracking.ExtractDisplayName(((Object)val).name); bool activeInHierarchy = ((Component)val).gameObject.activeInHierarchy; Log.LogInfo((object)$"[实体] ObjName: {name} | Display: {text} | Dist: {num:F1}m | Active: {activeInHierarchy}"); } Log.LogInfo((object)"--- 扫描结束 ---"); } } private void SpawnFakeSafe(string nickName, bool isColorful) { //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_0079: 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_0045: Unknown result type (might be due to invalid IL or missing references) //IL_0054: Unknown result type (might be due to invalid IL or missing references) //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_008d: 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_00b5: Unknown result type (might be due to invalid IL or missing references) //IL_00c0: Unknown result type (might be due to invalid IL or missing references) //IL_00c6: Expected O, but got Unknown //IL_00de: Unknown result type (might be due to invalid IL or missing references) //IL_00ed: Unknown result type (might be due to invalid IL or missing references) //IL_00f4: Expected O, but got Unknown //IL_010e: Unknown result type (might be due to invalid IL or missing references) //IL_011d: Unknown result type (might be due to invalid IL or missing references) //IL_0122: Unknown result type (might be due to invalid IL or missing references) //IL_0149: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)Camera.main == (Object)null)) { GameObject val = GameObject.CreatePrimitive((PrimitiveType)1); int num = Random.Range(100, 999); ((Object)val).name = $"Fake_{num}"; Vector3 position = (isColorful ? (((Component)Camera.main).transform.position + Random.insideUnitSphere * 10f) : (((Component)Camera.main).transform.position + ((Component)Camera.main).transform.forward * 20f)); position.y = ((Component)Camera.main).transform.position.y - 1f; val.transform.position = position; GameObject val2 = new GameObject("Scout"); val2.transform.SetParent(val.transform, false); val2.transform.localPosition = Vector3.zero; GameObject val3 = new GameObject("Misc"); val3.transform.SetParent(val2.transform, false); val3.transform.localPosition = Vector3.zero; GameObject val4 = new GameObject("CharacterLight"); val4.transform.SetParent(val3.transform, false); val4.transform.localPosition = new Vector3(0f, 1.8f, 0f); string text = nickName; text = ((!isColorful) ? $"{nickName}:{num}" : $"字:{num}"); Overlay.RegisterFakeTarget(val, text); _fakePlayers.Add(val); } } private void ClearFakePlayers() { foreach (GameObject fakePlayer in _fakePlayers) { if ((Object)(object)fakePlayer != (Object)null) { Overlay.UnregisterCharacter(fakePlayer); Object.Destroy((Object)(object)fakePlayer); } } _fakePlayers.Clear(); } } public static class Tracking { public static string ExtractDisplayName(string objName) { if (string.IsNullOrEmpty(objName)) { return "Unknown"; } int num = objName.IndexOf('['); int num2 = objName.LastIndexOf(':'); if (num != -1 && num2 != -1 && num2 > num) { return objName.Substring(num + 1, num2 - num - 1).Trim(); } return objName; } } [HarmonyPatch(typeof(Character))] public static class CharacterPatches { [HarmonyPatch("Awake")] [HarmonyPostfix] public static void Awake_Postfix(Character __instance) { Plugin.Overlay?.RegisterCharacter(__instance); } [HarmonyPatch("OnDestroy")] [HarmonyPostfix] public static void OnDestroy_Postfix(Character __instance) { Plugin.Overlay?.UnregisterCharacter(((Component)__instance).gameObject); } } }