From d3f4f7eee5fb6df4b83bf74fddc7d273bf29c269 Mon Sep 17 00:00:00 2001 From: haihaihailailo <131809683+hhaaaa4@users.noreply.github.com> Date: Sat, 18 Apr 2026 14:42:40 +0700 Subject: [PATCH 1/7] Add PreferredGpu field to Settings --- src/Core/Settings.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Core/Settings.cs b/src/Core/Settings.cs index a21252d..a91d909 100644 --- a/src/Core/Settings.cs +++ b/src/Core/Settings.cs @@ -33,6 +33,7 @@ public class Settings public string LastAutoNetwork { get; set; } = ""; public string PreferredDisk { get; set; } = ""; public string LastAutoDisk { get; set; } = ""; + public string PreferredGpu { get; set; } = ""; // ★★★ [新增] 首选显卡 (空=自动选第一块) ★★★ // ★★★ [新增] 首选风扇 ★★★ public string PreferredCpuFan { get; set; } = ""; From f1a7fc5cb04f36f74f5d6274f81a34af76206393 Mon Sep 17 00:00:00 2001 From: haihaihailailo <131809683+hhaaaa4@users.noreply.github.com> Date: Sat, 18 Apr 2026 14:45:58 +0700 Subject: [PATCH 2/7] Add GPU filtering in hardware services --- .../HardwareServices/HardwareScanner.cs | 20 +++++++++++++ .../HardwareServices/HardwareValueProvider.cs | 14 +++++++-- src/System/HardwareServices/SensorMap.cs | 29 ++++++++++++++++++- 3 files changed, 60 insertions(+), 3 deletions(-) diff --git a/src/System/HardwareServices/HardwareScanner.cs b/src/System/HardwareServices/HardwareScanner.cs index 4c8efb4..2b52e46 100644 --- a/src/System/HardwareServices/HardwareScanner.cs +++ b/src/System/HardwareServices/HardwareScanner.cs @@ -14,6 +14,7 @@ public static class HardwareScanner private static List? _cachedNetworkList = null; private static List? _cachedDiskList = null; private static List? _cachedMoboTempList = null; + private static List? _cachedGpuList = null; // ★★★ [新增] GPU 列表缓存 ★★★ /// /// 清除所有扫描缓存 @@ -24,6 +25,7 @@ public static void ClearCache() _cachedNetworkList = null; _cachedDiskList = null; _cachedMoboTempList = null; + _cachedGpuList = null; // ★★★ [新增] ★★★ } /// @@ -73,6 +75,24 @@ public static List ListAllDisks(IComputer computer) return list.ToList(); } + /// + /// ★★★ [新增] 列出所有显卡名称 (支持 NVIDIA / AMD / Intel) ★★★ + /// + public static List ListAllGpus(IComputer computer) + { + if (_cachedGpuList != null && _cachedGpuList.Count > 0) + return _cachedGpuList.ToList(); + + var list = computer.Hardware + .Where(h => h.HardwareType == HardwareType.GpuNvidia || + h.HardwareType == HardwareType.GpuAmd || + h.HardwareType == HardwareType.GpuIntel) + .Select(h => h.Name).Distinct().ToList(); + + if (list.Count > 0) _cachedGpuList = list; + return list.ToList(); + } + /// /// 列出所有风扇传感器 (排除 CPU/GPU 等核心自带风扇,主要针对主板/机箱风扇) /// diff --git a/src/System/HardwareServices/HardwareValueProvider.cs b/src/System/HardwareServices/HardwareValueProvider.cs index 4dd9541..cd2f4b9 100644 --- a/src/System/HardwareServices/HardwareValueProvider.cs +++ b/src/System/HardwareServices/HardwareValueProvider.cs @@ -36,6 +36,7 @@ public class HardwareValueProvider : IDisposable private string _lastPrefMoboTemp = ""; private string _lastPrefDisk = ""; private string _lastPrefNet = ""; + private string _lastPrefGpu = ""; // ★★★ [新增] 用户首选显卡 ★★★ public HardwareValueProvider(Computer c, Settings s, SensorMap map, NetworkManager net, DiskManager disk, FpsCounter fpsCounter,PerformanceCounterManager perfManager, object syncLock, Dictionary lastValid) { @@ -65,6 +66,7 @@ public void PreCacheAllSensors(SensorMap map) _lastPrefMoboTemp = _cfg.PreferredMoboTemp; _lastPrefDisk = _cfg.PreferredDisk; _lastPrefNet = _cfg.PreferredNetwork; + _lastPrefGpu = _cfg.PreferredGpu ?? ""; // ★★★ [新增] ★★★ // 1. 预查找用户指定的首选传感器 (风扇、水泵、主板温度) string[] preferredKeys = { "CPU.Fan", "CPU.Pump", "CASE.Fan", "MOBO.Temp" }; @@ -188,8 +190,16 @@ public void OnUpdateTickStarted() { _tickCache.Clear(); - // 自动检测配置变更:如果用户更改了首选风扇/磁盘,立即自动预热 - if (_lastPrefCpuFan != _cfg.PreferredCpuFan || + // ★★★ [新增] 检测 PreferredGpu 变更:需要重建 SensorMap (过滤逻辑在 Rebuild 里) ★★★ + bool gpuChanged = _lastPrefGpu != (_cfg.PreferredGpu ?? ""); + if (gpuChanged) + { + _sensorMap.Rebuild(_computer, _cfg); + } + + // 自动检测配置变更:如果用户更改了首选风扇/磁盘/显卡,立即自动预热 + if (gpuChanged || + _lastPrefCpuFan != _cfg.PreferredCpuFan || _lastPrefCpuPump != _cfg.PreferredCpuPump || _lastPrefCaseFan != _cfg.PreferredCaseFan || _lastPrefMoboTemp != _cfg.PreferredMoboTemp || diff --git a/src/System/HardwareServices/SensorMap.cs b/src/System/HardwareServices/SensorMap.cs index 4e1e891..fc01c9f 100644 --- a/src/System/HardwareServices/SensorMap.cs +++ b/src/System/HardwareServices/SensorMap.cs @@ -62,6 +62,18 @@ public void Clear() } } + /// + /// ★★★ [新增] 使映射失效,强制下次 EnsureFresh 时重建 ★★★ + /// 用于 PreferredGpu 等配置变更后立即生效 + /// + public void Invalidate() + { + lock (_lock) + { + _lastMapBuild = DateTime.MinValue; + } + } + public bool TryGetSensor(string key, out ISensor? sensor) @@ -100,11 +112,26 @@ public void Rebuild(Computer computer, Settings cfg) // ★ 签名修改 // 但为了保持原代码结构,我们依然用candidates收集主板相关数据 var candidatesMoboTemps = new List(capacity: 10); // 预设容量,减少扩容开销 + // ★★★ [新增] 读取用户首选显卡配置 (空=自动选第一块) ★★★ + string prefGpu = cfg.PreferredGpu ?? ""; + // 局部递归函数 void RegisterTo(IHardware hw) { //hw.Update(); + // ★★★ [新增] 首选显卡过滤:如果用户指定了首选 GPU,非匹配 GPU 完全跳过 ★★★ + // 这样 newGpu 和 newMap["GPU.*"] 都只会来自用户指定的显卡 + bool isGpuHw = hw.HardwareType == HardwareType.GpuNvidia || + hw.HardwareType == HardwareType.GpuAmd || + hw.HardwareType == HardwareType.GpuIntel; + if (isGpuHw && !string.IsNullOrEmpty(prefGpu) && + !hw.Name.Equals(prefGpu, StringComparison.OrdinalIgnoreCase)) + { + // 不处理该 GPU 的任何数据,也不递归其 SubHardware + return; + } + // --- 填充 CPU 缓存 (用于加权平均) --- if (hw.HardwareType == HardwareType.Cpu) { @@ -282,4 +309,4 @@ void RegisterTo(IHardware hw) // 复用 HardwareRules 的字符串匹配,避免重复造轮子 public static bool Has(string source, string sub) => HardwareRules.Has(source, sub); } -} \ No newline at end of file +} From 704ba9a2c1cf0afb1425f90a025e9ede293895c1 Mon Sep 17 00:00:00 2001 From: haihaihailailo <131809683+hhaaaa4@users.noreply.github.com> Date: Sat, 18 Apr 2026 14:47:25 +0700 Subject: [PATCH 3/7] Add files via upload --- src/System/HardwareMonitor.cs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/System/HardwareMonitor.cs b/src/System/HardwareMonitor.cs index bf27da6..a6596c8 100644 --- a/src/System/HardwareMonitor.cs +++ b/src/System/HardwareMonitor.cs @@ -497,6 +497,8 @@ public static string GenerateSmartName(ISensor sensor, IHardware hardware) => public static List ListAllDisks() => HardwareScanner.ListAllDisks(Instance!._computer); + public static List ListAllGpus() => HardwareScanner.ListAllGpus(Instance!._computer); // ★★★ [新增] ★★★ + public static List ListAllFans() => HardwareScanner.ListAllFans(Instance!._computer, Instance!._lock); public static List ListAllMoboTemps() => HardwareScanner.ListAllMoboTemps(Instance!._computer, Instance!._lock); From 18d76a985c3270f0ffe351d8b03e3a0811c18f12 Mon Sep 17 00:00:00 2001 From: haihaihailailo <131809683+hhaaaa4@users.noreply.github.com> Date: Sat, 18 Apr 2026 14:47:56 +0700 Subject: [PATCH 4/7] Add files via upload --- src/UI/Settings/SystemHardwarPage.cs | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/UI/Settings/SystemHardwarPage.cs b/src/UI/Settings/SystemHardwarPage.cs index 76e33d6..80ff12a 100644 --- a/src/UI/Settings/SystemHardwarPage.cs +++ b/src/UI/Settings/SystemHardwarPage.cs @@ -17,6 +17,7 @@ public class SystemHardwarPage : SettingsPageBase // ★★★ 修复:类型更正为 LiteComboBox ★★★ private LiteComboBox _cbDisk, _cbNet, _cbMobo; + private LiteComboBox _cbGpu; // ★★★ [新增] 显卡下拉 ★★★ private LiteComboBox _cbFanCpu, _cbFanPump, _cbFanCase; public SystemHardwarPage() @@ -54,10 +55,11 @@ private async void PopulateAsyncData() // 1. 并行等待所有数据返回 (使用 HardwareScanner) var taskDisks = Task.Run(() => HardwareScanner.ListAllDisks(HardwareMonitor.Instance.ComputerInstance)); var taskNets = Task.Run(() => HardwareScanner.ListAllNetworks(HardwareMonitor.Instance.ComputerInstance)); + var taskGpus = Task.Run(() => HardwareScanner.ListAllGpus(HardwareMonitor.Instance.ComputerInstance)); // ★★★ [新增] ★★★ var taskFans = Task.Run(() => HardwareScanner.ListAllFans(HardwareMonitor.Instance.ComputerInstance, HardwareMonitor.Instance.SyncLock)); var taskMobo = Task.Run(() => HardwareScanner.ListAllMoboTemps(HardwareMonitor.Instance.ComputerInstance, HardwareMonitor.Instance.SyncLock)); - await Task.WhenAll(taskDisks, taskNets, taskFans, taskMobo); + await Task.WhenAll(taskDisks, taskNets, taskGpus, taskFans, taskMobo); // 2. ★★★ 锁定全局布局 (防止每填一个框就重绘一次) ★★★ this.SuspendLayout(); @@ -86,6 +88,7 @@ void FillSync(LiteComboBox combo, List data, string currentVal) // 3. 瞬间填入所有数据 (因为布局被挂起,用户看不见中间过程) FillSync(_cbDisk, taskDisks.Result, Config.PreferredDisk); FillSync(_cbNet, taskNets.Result, Config.PreferredNetwork); + FillSync(_cbGpu, taskGpus.Result, Config.PreferredGpu); // ★★★ [新增] ★★★ FillSync(_cbMobo, taskMobo.Result, Config.PreferredMoboTemp); // Fan 的数据是复用的 @@ -137,6 +140,11 @@ private void CreateSourceCard() () => Config?.PreferredDisk ?? strAuto, v => { if(Config!=null) Config.PreferredDisk = (v == strAuto ? "" : v); }); + // ★★★ [新增] 显卡来源下拉:多显卡设备 (笔记本核显+独显) 可选择显示哪块 ★★★ + _cbGpu = (LiteComboBox)group.AddCombo(this, "Menu.GpuSource", new List { strAuto }, + () => Config?.PreferredGpu ?? strAuto, + v => { if (Config != null) Config.PreferredGpu = (v == strAuto ? "" : v); }); + _cbNet = (LiteComboBox)group.AddCombo(this, "Menu.NetworkSource", new List { strAuto }, () => Config?.PreferredNetwork ?? strAuto, v => { if (Config != null) Config.PreferredNetwork = (v == strAuto ? "" : v); }); From 9bc438bedeac39951f5587cffb861e8823c81f04 Mon Sep 17 00:00:00 2001 From: haihaihailailo <131809683+hhaaaa4@users.noreply.github.com> Date: Sat, 18 Apr 2026 14:48:23 +0700 Subject: [PATCH 5/7] Add files via upload --- resources/lang/en.json | 1 + resources/lang/zh.json | 1 + 2 files changed, 2 insertions(+) diff --git a/resources/lang/en.json b/resources/lang/en.json index 5dd9fb5..bc73c6d 100644 --- a/resources/lang/en.json +++ b/resources/lang/en.json @@ -220,6 +220,7 @@ "HardwareSettings": "Source", "DiskSource": "Disk", + "GpuSource": "GPU", "NetworkSource": "Network", "Auto": "Auto", "UseWinPerCounters": "Use Sys Counters", diff --git a/resources/lang/zh.json b/resources/lang/zh.json index cc3abe1..819bd76 100644 --- a/resources/lang/zh.json +++ b/resources/lang/zh.json @@ -220,6 +220,7 @@ "HardwareSettings": "硬件与传感器设置", "DiskSource": "首选磁盘", + "GpuSource": "首选显卡", "NetworkSource": "首选网卡", "Auto": "自动模式", "UseWinPerCounters": "优先使用系统计数器", From 300fe4595cd7340eba20a7b54afb888deed383b3 Mon Sep 17 00:00:00 2001 From: haihaihailailo <131809683+haihaihailailo@users.noreply.github.com> Date: Fri, 1 May 2026 17:45:00 +0700 Subject: [PATCH 6/7] Optimize hardware scanner list materialization --- .../HardwareServices/HardwareScanner.cs | 26 +++++++++---------- 1 file changed, 12 insertions(+), 14 deletions(-) diff --git a/src/System/HardwareServices/HardwareScanner.cs b/src/System/HardwareServices/HardwareScanner.cs index 2b52e46..32e8b68 100644 --- a/src/System/HardwareServices/HardwareScanner.cs +++ b/src/System/HardwareServices/HardwareScanner.cs @@ -49,14 +49,14 @@ public static string GenerateSmartName(ISensor sensor, IHardware hardware, IComp public static List ListAllNetworks(IComputer computer) { if (_cachedNetworkList != null && _cachedNetworkList.Count > 0) - return _cachedNetworkList.ToList(); + return new List(_cachedNetworkList); var list = computer.Hardware .Where(h => h.HardwareType == HardwareType.Network) .Select(h => h.Name).Distinct().ToList(); if (list.Count > 0) _cachedNetworkList = list; - return list.ToList(); + return list; } /// @@ -65,14 +65,14 @@ public static List ListAllNetworks(IComputer computer) public static List ListAllDisks(IComputer computer) { if (_cachedDiskList != null && _cachedDiskList.Count > 0) - return _cachedDiskList.ToList(); + return new List(_cachedDiskList); var list = computer.Hardware .Where(h => h.HardwareType == HardwareType.Storage) .Select(h => h.Name).Distinct().ToList(); if (list.Count > 0) _cachedDiskList = list; - return list.ToList(); + return list; } /// @@ -81,7 +81,7 @@ public static List ListAllDisks(IComputer computer) public static List ListAllGpus(IComputer computer) { if (_cachedGpuList != null && _cachedGpuList.Count > 0) - return _cachedGpuList.ToList(); + return new List(_cachedGpuList); var list = computer.Hardware .Where(h => h.HardwareType == HardwareType.GpuNvidia || @@ -90,7 +90,7 @@ public static List ListAllGpus(IComputer computer) .Select(h => h.Name).Distinct().ToList(); if (list.Count > 0) _cachedGpuList = list; - return list.ToList(); + return list; } /// @@ -99,7 +99,7 @@ public static List ListAllGpus(IComputer computer) public static List ListAllFans(IComputer computer, object syncLock) { if (_cachedFanList != null && _cachedFanList.Count > 0) - return _cachedFanList.ToList(); + return new List(_cachedFanList); var list = new List(); lock (syncLock) @@ -124,10 +124,9 @@ void Scan(IHardware hw) foreach (var hw in computer.Hardware) Scan(hw); } - list.Sort(); - var final = list.Distinct().ToList(); + var final = list.Distinct().OrderBy(name => name).ToList(); if (final.Count > 0) _cachedFanList = final; - return final.ToList(); + return final; } /// @@ -136,7 +135,7 @@ void Scan(IHardware hw) public static List ListAllMoboTemps(IComputer computer, object syncLock) { if (_cachedMoboTempList != null && _cachedMoboTempList.Count > 0) - return _cachedMoboTempList.ToList(); + return new List(_cachedMoboTempList); var list = new List(); lock (syncLock) @@ -161,10 +160,9 @@ void Scan(IHardware hw) foreach (var hw in computer.Hardware) Scan(hw); } - list.Sort(); - var final = list.Distinct().ToList(); + var final = list.Distinct().OrderBy(name => name).ToList(); if (final.Count > 0) _cachedMoboTempList = final; - return final.ToList(); + return final; } } } From baa0bc362257a88824f4f8e8644307f0777539dc Mon Sep 17 00:00:00 2001 From: haihaihailailo <131809683+haihaihailailo@users.noreply.github.com> Date: Fri, 1 May 2026 17:48:54 +0700 Subject: [PATCH 7/7] Add packaging script for release zip --- scripts/package.ps1 | 24 +++++++++++++++++ .../HardwareServices/HardwareScanner.cs | 26 +++++++++---------- 2 files changed, 36 insertions(+), 14 deletions(-) create mode 100644 scripts/package.ps1 diff --git a/scripts/package.ps1 b/scripts/package.ps1 new file mode 100644 index 0000000..a56aad6 --- /dev/null +++ b/scripts/package.ps1 @@ -0,0 +1,24 @@ +param( + [string]$Runtime = "win-x64", + [string]$Configuration = "Release", + [string]$Version = "dev" +) + +$ErrorActionPreference = "Stop" + +if (-not (Get-Command dotnet -ErrorAction SilentlyContinue)) { + Write-Error "dotnet CLI not found. Please install .NET SDK 8+ and retry." +} + +$outDir = Join-Path $PSScriptRoot "artifacts/$Runtime" +$publishDir = Join-Path $outDir "publish" +New-Item -ItemType Directory -Force -Path $publishDir | Out-Null + +dotnet publish "$PSScriptRoot/../LiteMonitor.csproj" -c $Configuration -r $Runtime --self-contained false -o $publishDir + +$zipName = "LiteMonitor_v$Version-$Runtime.zip" +$zipPath = Join-Path $outDir $zipName +if (Test-Path $zipPath) { Remove-Item $zipPath -Force } +Compress-Archive -Path (Join-Path $publishDir '*') -DestinationPath $zipPath + +Write-Host "Package created: $zipPath" diff --git a/src/System/HardwareServices/HardwareScanner.cs b/src/System/HardwareServices/HardwareScanner.cs index 2b52e46..32e8b68 100644 --- a/src/System/HardwareServices/HardwareScanner.cs +++ b/src/System/HardwareServices/HardwareScanner.cs @@ -49,14 +49,14 @@ public static string GenerateSmartName(ISensor sensor, IHardware hardware, IComp public static List ListAllNetworks(IComputer computer) { if (_cachedNetworkList != null && _cachedNetworkList.Count > 0) - return _cachedNetworkList.ToList(); + return new List(_cachedNetworkList); var list = computer.Hardware .Where(h => h.HardwareType == HardwareType.Network) .Select(h => h.Name).Distinct().ToList(); if (list.Count > 0) _cachedNetworkList = list; - return list.ToList(); + return list; } /// @@ -65,14 +65,14 @@ public static List ListAllNetworks(IComputer computer) public static List ListAllDisks(IComputer computer) { if (_cachedDiskList != null && _cachedDiskList.Count > 0) - return _cachedDiskList.ToList(); + return new List(_cachedDiskList); var list = computer.Hardware .Where(h => h.HardwareType == HardwareType.Storage) .Select(h => h.Name).Distinct().ToList(); if (list.Count > 0) _cachedDiskList = list; - return list.ToList(); + return list; } /// @@ -81,7 +81,7 @@ public static List ListAllDisks(IComputer computer) public static List ListAllGpus(IComputer computer) { if (_cachedGpuList != null && _cachedGpuList.Count > 0) - return _cachedGpuList.ToList(); + return new List(_cachedGpuList); var list = computer.Hardware .Where(h => h.HardwareType == HardwareType.GpuNvidia || @@ -90,7 +90,7 @@ public static List ListAllGpus(IComputer computer) .Select(h => h.Name).Distinct().ToList(); if (list.Count > 0) _cachedGpuList = list; - return list.ToList(); + return list; } /// @@ -99,7 +99,7 @@ public static List ListAllGpus(IComputer computer) public static List ListAllFans(IComputer computer, object syncLock) { if (_cachedFanList != null && _cachedFanList.Count > 0) - return _cachedFanList.ToList(); + return new List(_cachedFanList); var list = new List(); lock (syncLock) @@ -124,10 +124,9 @@ void Scan(IHardware hw) foreach (var hw in computer.Hardware) Scan(hw); } - list.Sort(); - var final = list.Distinct().ToList(); + var final = list.Distinct().OrderBy(name => name).ToList(); if (final.Count > 0) _cachedFanList = final; - return final.ToList(); + return final; } /// @@ -136,7 +135,7 @@ void Scan(IHardware hw) public static List ListAllMoboTemps(IComputer computer, object syncLock) { if (_cachedMoboTempList != null && _cachedMoboTempList.Count > 0) - return _cachedMoboTempList.ToList(); + return new List(_cachedMoboTempList); var list = new List(); lock (syncLock) @@ -161,10 +160,9 @@ void Scan(IHardware hw) foreach (var hw in computer.Hardware) Scan(hw); } - list.Sort(); - var final = list.Distinct().ToList(); + var final = list.Distinct().OrderBy(name => name).ToList(); if (final.Count > 0) _cachedMoboTempList = final; - return final.ToList(); + return final; } } }