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 EasyHUD v1.0.0
plugins/EasyHUD/EasyHUD.dll
Decompiled 6 days agousing System; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Text; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using HarmonyLib; using Microsoft.CodeAnalysis; using UnityEngine; using UnityEngine.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")] [assembly: AssemblyCompany("EasyHUD")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0")] [assembly: AssemblyProduct("EasyHUD")] [assembly: AssemblyTitle("EasyHUD")] [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 EasyHUD { internal static class EasyHudPanel { private const string PanelName = "EasyHudPanel"; private const string DayTimePanelName = "DayTimePanel"; private const string DefaultFont = "AveriaSansLibre-Bold"; private const string Sep = " "; private const float SidePadding = 12f; private const float FallbackWidth = 250f; private const float FallbackHeight = 30f; private const float FallbackCenterX = -140f; private const float FallbackDayWidth = 200f; private const int ConnectedStatus = 2; private static GameObject panel; private static RectTransform panelRt; private static Image background; private static Text label; private static Outline outline; private static Hud hud; private static RectTransform dayRt; private static float baseY = -25f; private static float baseHeight = 30f; private static Color baseTextColor = new Color(1f, 1f, 1f, 0.792f); private static float timer; private static bool located; private static bool loggedOnce; private static bool loggedFirst; private static Font fontCache; private static string fontCacheName; internal static void OnHudAwake(Hud instance) { hud = instance; located = false; dayRt = null; timer = 999f; } internal static void Destroy() { if ((Object)(object)panel != (Object)null) { Object.Destroy((Object)(object)panel); } panel = null; panelRt = null; background = null; label = null; outline = null; hud = null; dayRt = null; located = false; loggedOnce = false; loggedFirst = false; } internal static void Tick() { if ((Object)(object)panel == (Object)null) { if ((Object)(object)hud == (Object)null || (Object)(object)hud.m_rootObject == (Object)null) { return; } Build(); if ((Object)(object)panel == (Object)null) { return; } } timer += Time.unscaledDeltaTime; float num = Mathf.Max(0.05f, EasyHudPlugin.UpdateInterval.Value); if (!(timer < num)) { timer = 0f; if (!located) { TryLocate(); } Refresh(); } } private static void Build() { //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_000f: Expected O, but got Unknown //IL_0057: 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_0089: 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_00bb: Unknown result type (might be due to invalid IL or missing references) //IL_00de: Unknown result type (might be due to invalid IL or missing references) //IL_00f8: Unknown result type (might be due to invalid IL or missing references) //IL_00fd: 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_011a: Unknown result type (might be due to invalid IL or missing references) //IL_0121: Unknown result type (might be due to invalid IL or missing references) //IL_012c: Unknown result type (might be due to invalid IL or missing references) //IL_0141: Unknown result type (might be due to invalid IL or missing references) //IL_0155: Unknown result type (might be due to invalid IL or missing references) //IL_015f: 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_0205: Unknown result type (might be due to invalid IL or missing references) //IL_021e: Unknown result type (might be due to invalid IL or missing references) //IL_026b: Unknown result type (might be due to invalid IL or missing references) try { panel = new GameObject("EasyHudPanel"); panel.layer = 5; panel.transform.SetParent(hud.m_rootObject.transform, false); panelRt = panel.AddComponent<RectTransform>(); panelRt.anchorMin = new Vector2(1f, 1f); panelRt.anchorMax = new Vector2(1f, 1f); panelRt.pivot = new Vector2(0.5f, 0.5f); panelRt.sizeDelta = new Vector2(250f, 30f); panelRt.anchoredPosition = new Vector2(-365f, baseY); background = panel.AddComponent<Image>(); ((Graphic)background).color = EasyHudPlugin.BackgroundColor.Value; ((Graphic)background).raycastTarget = false; GameObject val = new GameObject("Label") { layer = 5 }; val.transform.SetParent(panel.transform, false); RectTransform obj = val.AddComponent<RectTransform>(); obj.anchorMin = Vector2.zero; obj.anchorMax = Vector2.one; obj.offsetMin = new Vector2(12f, 0f); obj.offsetMax = new Vector2(-12f, 0f); label = val.AddComponent<Text>(); label.font = GetFont(EasyHudPlugin.FontName.Value); label.fontSize = EasyHudPlugin.FontSize.Value; ((Graphic)label).color = EasyHudPlugin.FontColor.Value; label.alignment = (TextAnchor)4; label.horizontalOverflow = (HorizontalWrapMode)1; label.verticalOverflow = (VerticalWrapMode)1; ((Graphic)label).raycastTarget = false; label.supportRichText = false; label.text = ""; outline = val.AddComponent<Outline>(); ((Shadow)outline).effectColor = EasyHudPlugin.OutlineColor.Value; ((Shadow)outline).effectDistance = new Vector2(1f, -1f); ((Shadow)outline).useGraphicAlpha = true; ((Behaviour)outline).enabled = EasyHudPlugin.OutlineEnabled.Value; panel.SetActive(false); TryLocate(); Layout(); EasyHudPlugin.Log.LogInfo((object)string.Format("网络面板已创建:父节点 Hud.m_rootObject,初始位置 {0},字体 {1}。", panelRt.anchoredPosition, ((Object)(object)label.font == (Object)null) ? "(null)" : ((Object)label.font).name)); } catch (Exception ex) { EasyHudPlugin.Log.LogError((object)("创建网络面板失败(游戏本身不受影响):" + ex)); panel = null; } } private static void TryLocate() { //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_00c8: 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) if (located || (Object)(object)hud == (Object)null || (Object)(object)hud.m_rootObject == (Object)null || (Object)(object)panelRt == (Object)null) { return; } Transform val = hud.m_rootObject.transform.Find("DayTimePanel"); if ((Object)(object)val == (Object)null) { return; } dayRt = (RectTransform)(object)((val is RectTransform) ? val : null); if (!((Object)(object)dayRt == (Object)null)) { baseY = dayRt.anchoredPosition.y; if (EasyHudPlugin.MatchDayTimeStyle.Value) { InheritStyle(val, dayRt); } else { ApplyFallbackStyle(); } located = true; EasyHudPlugin.Log.LogInfo((object)string.Format("已找到「{0}」面板并贴到其左侧:它的位置 {1} / 尺寸 {2} → 本面板 y={3:0.#},样式来源={4}", "DayTimePanel", dayRt.anchoredPosition, dayRt.sizeDelta, baseY, EasyHudPlugin.MatchDayTimeStyle.Value ? "继承它的 UI 组件" : "本模组配置")); } } private static void InheritStyle(Transform t, RectTransform drt) { //IL_013e: Unknown result type (might be due to invalid IL or missing references) //IL_0033: 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_0150: 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_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_00c1: Unknown result type (might be due to invalid IL or missing references) //IL_00ee: 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) Image component = ((Component)t).GetComponent<Image>(); if ((Object)(object)component != (Object)null && (Object)(object)background != (Object)null) { background.sprite = component.sprite; background.type = component.type; ((Graphic)background).color = ((Graphic)component).color; ((Behaviour)background).enabled = ((Behaviour)component).enabled; } Text componentInChildren = ((Component)t).GetComponentInChildren<Text>(true); if ((Object)(object)componentInChildren != (Object)null && (Object)(object)label != (Object)null) { label.font = componentInChildren.font; label.fontSize = componentInChildren.fontSize; label.fontStyle = componentInChildren.fontStyle; baseTextColor = ((Graphic)componentInChildren).color; ((Graphic)label).color = baseTextColor; Outline component2 = ((Component)componentInChildren).GetComponent<Outline>(); if ((Object)(object)component2 != (Object)null && (Object)(object)outline != (Object)null) { ((Shadow)outline).effectColor = ((Shadow)component2).effectColor; ((Shadow)outline).effectDistance = ((Shadow)component2).effectDistance; ((Shadow)outline).useGraphicAlpha = ((Shadow)component2).useGraphicAlpha; ((Behaviour)outline).enabled = true; } else if ((Object)(object)outline != (Object)null) { ((Behaviour)outline).enabled = false; } } if (drt.sizeDelta.y > 1f) { baseHeight = drt.sizeDelta.y; } } private static void ApplyFallbackStyle() { //IL_003f: 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_004e: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Unknown result type (might be due to invalid IL or missing references) //IL_009b: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)label != (Object)null) { label.font = GetFont(EasyHudPlugin.FontName.Value); label.fontSize = EasyHudPlugin.FontSize.Value; baseTextColor = EasyHudPlugin.FontColor.Value; ((Graphic)label).color = baseTextColor; } if ((Object)(object)background != (Object)null) { ((Graphic)background).color = EasyHudPlugin.BackgroundColor.Value; ((Behaviour)background).enabled = true; } if ((Object)(object)outline != (Object)null) { ((Shadow)outline).effectColor = EasyHudPlugin.OutlineColor.Value; ((Behaviour)outline).enabled = EasyHudPlugin.OutlineEnabled.Value; } baseHeight = 30f; } private static void Layout() { //IL_0074: 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_0091: 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) //IL_00ee: Unknown result type (might be due to invalid IL or missing references) //IL_00fd: Unknown result type (might be due to invalid IL or missing references) //IL_0127: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)panelRt == (Object)null) { return; } float num = EasyHudPlugin.PanelWidth.Value; if (num <= 0f) { float num2 = (((Object)(object)label == (Object)null) ? 0f : label.preferredWidth); if (num2 < 1f || float.IsNaN(num2)) { num2 = 226f; } num = num2 + 24f; } num = Mathf.Max(60f, Mathf.Ceil(num)); if (Mathf.Abs(panelRt.sizeDelta.x - num) > 0.5f || Mathf.Abs(panelRt.sizeDelta.y - baseHeight) > 0.5f) { panelRt.sizeDelta = new Vector2(num, baseHeight); } float value = EasyHudPlugin.Gap.Value; float num3 = ((!((Object)(object)dayRt != (Object)null)) ? (-240f) : (dayRt.anchoredPosition.x - dayRt.sizeDelta.x * dayRt.pivot.x)); panelRt.anchoredPosition = new Vector2(num3 - value - num * 0.5f, baseY); } private static void Refresh() { //IL_0187: 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) if (!EasyHudPlugin.Enabled.Value) { SetVisible(visible: false); return; } ZNet instance = ZNet.instance; if ((Object)(object)instance == (Object)null) { SetVisible(visible: false); return; } float num = 0f; float num2 = 0f; float num3 = 0f; float num4 = 0f; int num5 = 0; int num6 = 1; int num7 = 0; int num8 = 0; bool flag = false; try { instance.GetNetStats(ref num, ref num2, ref num5, ref num3, ref num4); flag = instance.IsServer(); num6 = instance.GetNrOfPlayers(); num7 = instance.GetPeerConnections(); num8 = StatusOf(); } catch (Exception ex) { if (!loggedOnce) { loggedOnce = true; EasyHudPlugin.Log.LogError((object)("读取网络统计失败:" + ex)); } SetVisible(visible: false); return; } if (EasyHudPlugin.HideWhenSingleplayer.Value && flag && num6 <= 1) { SetVisible(visible: false); return; } SetVisible(visible: true); if (num8 != 2) { label.text = ((num8 == 1) ? "Connecting..." : "Offline"); ((Graphic)label).color = baseTextColor; Layout(); return; } if (EasyHudPlugin.NormalizeOnHost.Value && flag && num7 > 1) { float num9 = num7; num /= num9; num2 /= num9; num3 /= num9; num4 /= num9; num5 = Mathf.RoundToInt((float)num5 / num9); } label.text = Compose(num5, num, num4, num3, num6); if (label.text.Length == 0) { SetVisible(visible: false); return; } ((Graphic)label).color = PickColor(num5, num); Layout(); if (!loggedFirst) { loggedFirst = true; EasyHudPlugin.Log.LogInfo((object)string.Format("首次显示:\"{0}\"(Ping {1}ms / 质量 {2}% / 上行 {3:0.0} 下行 {4:0.0} KB/s / 玩家 {5},本机是{6})", label.text, num5, Mathf.RoundToInt(num * 100f), num3 / 1024f, num4 / 1024f, num6, flag ? "主机" : "客户端")); } } private static string Compose(int ping, float localQuality, float inByteSec, float outByteSec, int players) { StringBuilder stringBuilder = new StringBuilder(96); if (EasyHudPlugin.ShowPing.Value) { stringBuilder.Append("Ping ").Append(ping).Append("ms"); } if (EasyHudPlugin.ShowQuality.Value) { if (stringBuilder.Length > 0) { stringBuilder.Append(" "); } stringBuilder.Append(Mathf.RoundToInt(localQuality * 100f)).Append('%'); } if (EasyHudPlugin.ShowBandwidth.Value) { if (stringBuilder.Length > 0) { stringBuilder.Append(" "); } stringBuilder.Append(EasyHudPlugin.ArrowDown.Value).Append((inByteSec / 1024f).ToString("0.0")).Append(' ') .Append(EasyHudPlugin.ArrowUp.Value) .Append((outByteSec / 1024f).ToString("0.0")) .Append(" KB/s"); } if (EasyHudPlugin.ShowPlayers.Value) { if (stringBuilder.Length > 0) { stringBuilder.Append(" "); } stringBuilder.Append("P ").Append(players); } if (stringBuilder.Length != 0) { return stringBuilder.ToString(); } return ""; } private static Color PickColor(int ping, float localQuality) { //IL_000c: 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_0075: 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_0083: Unknown result type (might be due to invalid IL or missing references) if (!EasyHudPlugin.WarnColors.Value) { return baseTextColor; } int num = Mathf.RoundToInt(localQuality * 100f); if (ping <= 0 && num <= 0) { return baseTextColor; } bool num2 = ping >= EasyHudPlugin.BadPingMs.Value || num <= EasyHudPlugin.BadQualityPct.Value; bool flag = ping >= EasyHudPlugin.WarnPingMs.Value || num <= EasyHudPlugin.WarnQualityPct.Value; if (num2) { return EasyHudPlugin.BadColor.Value; } if (flag) { return EasyHudPlugin.WarnColor.Value; } return baseTextColor; } private static void SetVisible(bool visible) { if ((Object)(object)panel != (Object)null && panel.activeSelf != visible) { panel.SetActive(visible); } } private static int StatusOf() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) try { object obj = ZNet.GetConnectionStatus(); return (obj != null) ? Convert.ToInt32(obj) : 0; } catch { return 0; } } private static Font GetFont(string wanted) { if ((Object)(object)fontCache != (Object)null && fontCacheName == wanted) { return fontCache; } Font val = FindFont(wanted); if ((Object)(object)val == (Object)null && wanted != "AveriaSansLibre-Bold") { val = FindFont("AveriaSansLibre-Bold"); } fontCache = val; fontCacheName = wanted; if ((Object)(object)val == (Object)null) { EasyHudPlugin.Log.LogWarning((object)("找不到字体「" + wanted + "」,文字可能不显示。可在 [4 - Fallback Style] 里改 FontName。")); } return val; } private static Font FindFont(string name) { Font[] array = Resources.FindObjectsOfTypeAll<Font>(); if (array == null) { return null; } foreach (Font val in array) { if ((Object)(object)val != (Object)null && ((Object)val).name == name) { return val; } } return null; } } [BepInPlugin("easyhud.client.only", "EasyHUD", "1.0.0")] public class EasyHudPlugin : BaseUnityPlugin { public const string Guid = "easyhud.client.only"; public const string PluginName = "EasyHUD"; public const string PluginVersion = "1.0.0"; internal static EasyHudPlugin Instance; internal static ManualLogSource Log; internal static ConfigEntry<bool> Enabled; internal static ConfigEntry<bool> HideWhenSingleplayer; internal static ConfigEntry<float> UpdateInterval; internal static ConfigEntry<bool> MatchDayTimeStyle; internal static ConfigEntry<float> PanelWidth; internal static ConfigEntry<float> Gap; internal static ConfigEntry<bool> NormalizeOnHost; internal static ConfigEntry<bool> ShowPing; internal static ConfigEntry<bool> ShowQuality; internal static ConfigEntry<bool> ShowBandwidth; internal static ConfigEntry<bool> ShowPlayers; internal static ConfigEntry<string> ArrowDown; internal static ConfigEntry<string> ArrowUp; internal static ConfigEntry<bool> WarnColors; internal static ConfigEntry<int> WarnPingMs; internal static ConfigEntry<int> BadPingMs; internal static ConfigEntry<int> WarnQualityPct; internal static ConfigEntry<int> BadQualityPct; internal static ConfigEntry<Color> WarnColor; internal static ConfigEntry<Color> BadColor; internal static ConfigEntry<int> FontSize; internal static ConfigEntry<string> FontName; internal static ConfigEntry<Color> FontColor; internal static ConfigEntry<bool> OutlineEnabled; internal static ConfigEntry<Color> OutlineColor; internal static ConfigEntry<Color> BackgroundColor; private Harmony harmony; private bool warnedTick; private void Awake() { Instance = this; Log = ((BaseUnityPlugin)this).Logger; BindConfig(); ApplyPatches(); VerifyPatches(); Log.LogInfo((object)"EasyHUD 1.0.0 已就绪:网络质量 HUD(贴在「天数/时间」面板左侧)。"); } private void OnDestroy() { EasyHudPanel.Destroy(); if (harmony != null) { try { harmony.UnpatchSelf(); } catch { } } } private void Update() { try { EasyHudPanel.Tick(); } catch (Exception ex) { if (!warnedTick) { warnedTick = true; Log.LogError((object)("刷新 HUD 时出错(已停止重复报错):" + ex)); } } } private void BindConfig() { //IL_006e: Unknown result type (might be due to invalid IL or missing references) //IL_0078: Expected O, but got Unknown //IL_00cb: Unknown result type (might be due to invalid IL or missing references) //IL_00d5: Expected O, but got Unknown //IL_0108: Unknown result type (might be due to invalid IL or missing references) //IL_0112: Expected O, but got Unknown //IL_0246: Unknown result type (might be due to invalid IL or missing references) //IL_0250: Expected O, but got Unknown //IL_027f: Unknown result type (might be due to invalid IL or missing references) //IL_0289: Expected O, but got Unknown //IL_02b2: Unknown result type (might be due to invalid IL or missing references) //IL_02bc: Expected O, but got Unknown //IL_02e5: Unknown result type (might be due to invalid IL or missing references) //IL_02ef: Expected O, but got Unknown //IL_0318: Unknown result type (might be due to invalid IL or missing references) //IL_0350: Unknown result type (might be due to invalid IL or missing references) //IL_0388: Unknown result type (might be due to invalid IL or missing references) //IL_0392: Expected O, but got Unknown //IL_03df: Unknown result type (might be due to invalid IL or missing references) //IL_0437: Unknown result type (might be due to invalid IL or missing references) //IL_046f: Unknown result type (might be due to invalid IL or missing references) Enabled = ((BaseUnityPlugin)this).Config.Bind<bool>("1 - General", "Enabled", true, "总开关。关掉后 HUD 会立即隐藏(下次进游戏也保持隐藏)。"); HideWhenSingleplayer = ((BaseUnityPlugin)this).Config.Bind<bool>("1 - General", "HideWhenSingleplayer", true, "单人游戏(自己开着主机、且只有自己一个人)时自动隐藏整个面板。\n单人时游戏本来就没有网络流量,显示出来只会是 0ms / 0%,意义不大。"); UpdateInterval = ((BaseUnityPlugin)this).Config.Bind<float>("1 - General", "UpdateInterval", 0.5f, new ConfigDescription("刷新间隔(秒)。网络统计本身是低频采样的,没必要每帧刷新。\n推荐 0.25 ~ 1.0;调太小只会让数字乱跳,不会更准。", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0.05f, 5f), Array.Empty<object>())); MatchDayTimeStyle = ((BaseUnityPlugin)this).Config.Bind<bool>("1 - General", "MatchDayTimeStyle", true, "自动与「Display Day & Time in HUD」面板保持风格统一:\n运行时找到它的 DayTimePanel,直接继承它的字体、字号、字色、描边、背景、面板高度。\ntrue(推荐)= 你改那个模组的配置,本 HUD 会自动跟着变;\nfalse = 使用下面 [4 - Fallback Style] 里自己的一套样式。"); PanelWidth = ((BaseUnityPlugin)this).Config.Bind<float>("1 - General", "PanelWidth", 0f, new ConfigDescription("面板宽度(像素)。0 = 自动按文字宽度收缩(默认)。\n想让两个面板一样宽,就填它那个 Panel width 的值(默认 200)。", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 1000f), Array.Empty<object>())); Gap = ((BaseUnityPlugin)this).Config.Bind<float>("1 - General", "Gap", 0f, new ConfigDescription("本面板与左侧「天数/时间」面板之间的间距(像素)。0 = 紧贴。", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 200f), Array.Empty<object>())); NormalizeOnHost = ((BaseUnityPlugin)this).Config.Bind<bool>("1 - General", "NormalizeOnHost", true, "自己当主机时,把统计值除以有效连接数(显示平均值)。\n原因:游戏底层的 ZNet.GetNetStats 在主机模式下是**把所有客户端的值累加**的,\n所以原版 F2 面板在主机开 3 人时会显示 300% / 1500ms 这种数字(其实每个人都不差)。\ntrue(默认)= 显示平均值,更容易看懂;false = 和 F2 面板完全一致的累加值。\n(自己是客户端连别人时,这个开关没有任何影响。)"); ShowPing = ((BaseUnityPlugin)this).Config.Bind<bool>("2 - Content", "ShowPing", true, "显示 Ping(毫秒)。格式示例:Ping 42ms"); ShowQuality = ((BaseUnityPlugin)this).Config.Bind<bool>("2 - Content", "ShowQuality", true, "显示连接质量(%)。这是原版 F2 里 `99% / 98%` 的那一项 ——\nSteam 只提供「连接质量」这一个综合指标(0~1),并没有独立的丢包率字段,\n所以本 HUD 用连接质量来反映网络好坏:丢包/延迟一恶化,它就会明显掉下来。"); ShowBandwidth = ((BaseUnityPlugin)this).Config.Bind<bool>("2 - Content", "ShowBandwidth", true, "显示上下行带宽(KB/s)。格式示例:↓3.4 ↑0.8 KB/s"); ShowPlayers = ((BaseUnityPlugin)this).Config.Bind<bool>("2 - Content", "ShowPlayers", true, "显示当前在线玩家数(含主机)。格式示例:P 3"); ArrowDown = ((BaseUnityPlugin)this).Config.Bind<string>("2 - Content", "ArrowDown", "↓", "下行箭头符号。若你的字体显示不出来(变成方块),改成普通字符即可,例如 \"v\" 或 \"DL\"。"); ArrowUp = ((BaseUnityPlugin)this).Config.Bind<string>("2 - Content", "ArrowUp", "↑", "上行箭头符号。同上,显示异常就换成 \"^\" 或 \"UL\"。"); WarnColors = ((BaseUnityPlugin)this).Config.Bind<bool>("3 - Warning Colors", "Enabled", true, "网络变差时改变字色提醒(正常时用和「天数/时间」面板完全相同的字色)。"); WarnPingMs = ((BaseUnityPlugin)this).Config.Bind<int>("3 - Warning Colors", "WarnPingMs", 120, new ConfigDescription("Ping 超过这个值 → 变黄。", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 2000), Array.Empty<object>())); BadPingMs = ((BaseUnityPlugin)this).Config.Bind<int>("3 - Warning Colors", "BadPingMs", 250, new ConfigDescription("Ping 超过这个值 → 变红。", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 5000), Array.Empty<object>())); WarnQualityPct = ((BaseUnityPlugin)this).Config.Bind<int>("3 - Warning Colors", "WarnQualityPct", 80, new ConfigDescription("连接质量低于这个百分比 → 变黄。", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 100), Array.Empty<object>())); BadQualityPct = ((BaseUnityPlugin)this).Config.Bind<int>("3 - Warning Colors", "BadQualityPct", 50, new ConfigDescription("连接质量低于这个百分比 → 变红。", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 100), Array.Empty<object>())); WarnColor = ((BaseUnityPlugin)this).Config.Bind<Color>("3 - Warning Colors", "WarnColor", new Color(1f, 1f, 0.63f, 1f), "警告色(默认亮黄 FFFFA0FF)。"); BadColor = ((BaseUnityPlugin)this).Config.Bind<Color>("3 - Warning Colors", "BadColor", new Color(1f, 0.42f, 0.42f, 1f), "危险色(默认亮红 FF6B6BFF)。"); FontSize = ((BaseUnityPlugin)this).Config.Bind<int>("4 - Fallback Style", "FontSize", 16, new ConfigDescription("字号。仅在 MatchDayTimeStyle=false、或没找到「天数/时间」面板时生效。\n(默认值就是那个模组面板的默认字号,所以看起来仍然一致。)", (AcceptableValueBase)(object)new AcceptableValueRange<int>(6, 72), Array.Empty<object>())); FontName = ((BaseUnityPlugin)this).Config.Bind<string>("4 - Fallback Style", "FontName", "AveriaSansLibre-Bold", "字体名。默认 AveriaSansLibre-Bold = 游戏内置字体,也是「天数/时间」面板用的那个。"); FontColor = ((BaseUnityPlugin)this).Config.Bind<Color>("4 - Fallback Style", "FontColor", new Color(1f, 1f, 1f, 0.792f), "字色(默认 FFFFFFCA,与那个模组面板一致)。"); OutlineEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("4 - Fallback Style", "OutlineEnabled", true, "是否给文字加描边(默认开,和那个模组面板一致)。"); OutlineColor = ((BaseUnityPlugin)this).Config.Bind<Color>("4 - Fallback Style", "OutlineColor", new Color(0f, 0f, 0f, 1f), "描边颜色(默认 000000FF)。"); BackgroundColor = ((BaseUnityPlugin)this).Config.Bind<Color>("4 - Fallback Style", "BackgroundColor", new Color(0f, 0f, 0f, 0.392f), "面板背景色(默认 00000064,半透明黑,与那个模组面板一致)。"); } private void ApplyPatches() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0010: Expected O, but got Unknown harmony = new Harmony("easyhud.client.only"); Type[] array = new Type[1] { typeof(HudAwakePatch) }; foreach (Type type in array) { try { harmony.CreateClassProcessor(type).Patch(); Log.LogInfo((object)(" 已挂载补丁类:" + type.Name)); } catch (Exception ex) { Log.LogError((object)(" 补丁类 " + type.Name + " 挂载失败:" + ex)); } } } private void VerifyPatches() { int num = 0; int num2 = 0; Log.LogInfo((object)"---- 补丁挂载自检 ----"); MethodBase[] array = new MethodBase[1] { AccessTools.Method(typeof(Hud), "Awake", (Type[])null, (Type[])null) }; foreach (MethodBase methodBase in array) { if (methodBase == null) { Log.LogWarning((object)" 找不到目标方法(游戏版本可能已变更)"); continue; } num2++; Patches patchInfo = Harmony.GetPatchInfo(methodBase); int num3 = patchInfo?.Prefixes.Count ?? 0; int num4 = patchInfo?.Postfixes.Count ?? 0; bool flag = num4 >= 1; if (flag) { num++; } Log.LogInfo((object)string.Format(" {0}.{1}() prefix={2} postfix={3} {4}", methodBase.DeclaringType.Name, methodBase.Name, num3, num4, flag ? "OK" : "!! 没挂上")); } Log.LogInfo((object)$"Harmony 补丁挂载完成:{num}/{num2} 成功。"); Log.LogInfo((object)"-----------------------"); } } [HarmonyPatch(typeof(Hud), "Awake")] internal static class HudAwakePatch { [HarmonyPostfix] private static void Postfix(Hud __instance) { EasyHudPanel.OnHudAwake(__instance); } } }