ntminer 5 tahun lalu
induk
melakukan
32d39a25bd
100 mengubah file dengan 735 tambahan dan 1228 penghapusan
  1. 0 1
      docs/Overclock.md
  2. 1 3
      src/AppModels/AppModels.csproj
  3. 133 3
      src/AppModels/AppRoot.cs
  4. 1 1
      src/AppModels/AppRoot.partials.GpuSpeedViewModels.cs
  5. 1 1
      src/AppModels/AppRoot.partials.GpuViewModels.cs
  6. 31 8
      src/AppModels/AppStatic.cs
  7. 0 14
      src/AppModels/MinerStudio/Messages.cs
  8. 41 39
      src/AppModels/MinerStudio/MinerStudioRoot.partials.MinerClientConsoleViewModel.cs
  9. 31 29
      src/AppModels/MinerStudio/MinerStudioRoot.partials.MinerClientMessagesViewModel.cs
  10. 44 42
      src/AppModels/MinerStudio/MinerStudioRoot.partials.MinerClientOperationResultsViewModel.cs
  11. 1 24
      src/AppModels/MinerStudio/Vms/GpuNameCountViewModel.cs
  12. 2 6
      src/AppModels/MinerStudio/Vms/GpuNameCountsViewModel.cs
  13. 0 20
      src/AppModels/MinerStudio/Vms/GpuNamePageViewModel.cs
  14. 0 104
      src/AppModels/MinerStudio/Vms/GpuNamesViewModel.cs
  15. 2 3
      src/AppModels/MinerStudio/Vms/GpuProfilesPageViewModel.cs
  16. 1 1
      src/AppModels/MinerStudio/Vms/GpuSpeedDataViewModel.cs
  17. 1 1
      src/AppModels/MinerStudio/Vms/GpuSpeedDataViewModels.cs
  18. 4 4
      src/AppModels/MinerStudio/Vms/MineWorkViewModel.cs
  19. 12 19
      src/AppModels/MinerStudio/Vms/MinerClientViewModel.cs
  20. 3 2
      src/AppModels/MinerStudio/Vms/MinerClientsWindowViewModel.cs
  21. 3 3
      src/AppModels/MinerStudio/Vms/OverClockDataViewModel.cs
  22. 1 1
      src/AppModels/MinerStudio/Vms/UserPageViewModel.cs
  23. 2 1
      src/AppModels/Vms/CoinKernelViewModel.cs
  24. 4 0
      src/AppModels/Vms/CoinProfileViewModel.cs
  25. 1 0
      src/AppModels/Vms/CoinViewModel.cs
  26. 0 135
      src/AppModels/Vms/GpuNameViewModel.cs
  27. 1 1
      src/AppModels/Vms/GpuSpeedViewModel.cs
  28. 1 1
      src/AppModels/Vms/GpuStatusBarViewModel.cs
  29. 1 3
      src/AppModels/Vms/GpuViewModel.cs
  30. 1 1
      src/AppModels/Vms/InputSegmentEditViewModel.cs
  31. 2 2
      src/AppModels/Vms/KernelViewModel.cs
  32. 2 1
      src/AppModels/Vms/KernelsWindowViewModel.cs
  33. 2 2
      src/AppModels/Vms/LocalMessagesViewModel.cs
  34. 12 14
      src/AppModels/Vms/MinerProfileViewModel.cs
  35. 1 1
      src/AppModels/Vms/OuterPropertyViewModel.cs
  36. 2 0
      src/AppModels/Vms/PoolViewModel.cs
  37. 0 1
      src/AppModels/Vms/ServerMessageViewModel.cs
  38. 1 1
      src/AppModels/Vms/ServerMessagesViewModel.cs
  39. 1 1
      src/AppModels/Vms/SpeedTableViewModel.cs
  40. 1 1
      src/AppModels/Vms/StateBarViewModel.cs
  41. 42 0
      src/AppModels/Vms/WindowsAutoLogonViewModel.cs
  42. 1 6
      src/AppViews0/AppViewFactory.cs
  43. 11 33
      src/AppViews0/AppViews0.csproj
  44. 0 2
      src/AppViews0/MinerStudio/Views/Design/GpuNamePageViewModel.xaml
  45. 0 2
      src/AppViews0/MinerStudio/Views/Design/GpuNameViewModel.xaml
  46. 0 2
      src/AppViews0/MinerStudio/Views/Design/GpuNamesViewModel.xaml
  47. 1 1
      src/AppViews0/MinerStudio/Views/MinerClientsWindow.xaml.cs
  48. 0 84
      src/AppViews0/MinerStudio/Views/Ucs/GpuNameAdd.xaml
  49. 0 37
      src/AppViews0/MinerStudio/Views/Ucs/GpuNameAdd.xaml.cs
  50. 0 7
      src/AppViews0/MinerStudio/Views/Ucs/GpuNameCounts.xaml
  51. 19 0
      src/AppViews0/MinerStudio/Views/Ucs/GpuNameCounts.xaml.cs
  52. 0 32
      src/AppViews0/MinerStudio/Views/Ucs/GpuNamePage.xaml
  53. 0 33
      src/AppViews0/MinerStudio/Views/Ucs/GpuNamePage.xaml.cs
  54. 0 156
      src/AppViews0/MinerStudio/Views/Ucs/GpuNames.xaml
  55. 0 32
      src/AppViews0/MinerStudio/Views/Ucs/GpuNames.xaml.cs
  56. 0 1
      src/AppViews0/Views/ConsoleWindow.xaml
  57. 1 53
      src/AppViews0/Views/ConsoleWindow.xaml.cs
  58. 2 0
      src/AppViews0/Views/Design/WindowsAutoLogonViewModel.xaml
  59. 4 2
      src/AppViews0/Views/KernelsWindow.xaml
  60. 4 1
      src/AppViews0/Views/KernelsWindow.xaml.cs
  61. 1 0
      src/AppViews0/Views/MainWindow.xaml
  62. 9 1
      src/AppViews0/Views/MainWindow.xaml.cs
  63. 11 4
      src/AppViews0/Views/Ucs/AppMiner.xaml
  64. 2 1
      src/AppViews0/Views/Ucs/CoinKernelEdit.xaml.cs
  65. 2 1
      src/AppViews0/Views/Ucs/KernelEdit.xaml.cs
  66. 4 0
      src/AppViews0/Views/Ucs/OuterProperty.xaml
  67. 14 2
      src/AppViews0/Views/Ucs/ServerMessageEdit.xaml
  68. 7 1
      src/AppViews0/Views/Ucs/ServerMessageEdit.xaml.cs
  69. 1 1
      src/AppViews0/Views/Ucs/ServerMessages.xaml
  70. 1 1
      src/AppViews0/Views/Ucs/SpeedCharts.xaml.cs
  71. 1 2
      src/AppViews0/Views/Ucs/StateBar.xaml
  72. 2 5
      src/AppViews0/Views/Ucs/StateBar.xaml.cs
  73. 81 0
      src/AppViews0/Views/Ucs/WindowsAutoLogon.xaml
  74. 45 0
      src/AppViews0/Views/Ucs/WindowsAutoLogon.xaml.cs
  75. 0 28
      src/BlankWindow/GFramework.BlankWindow.sln
  76. 15 21
      src/MinerClient/App.xaml.cs
  77. 0 24
      src/MinerClient/AtikmdagPatcher/AtikmdagPatcherUtil.cs
  78. TEMPAT SAMPAH
      src/MinerClient/AtikmdagPatcher/atikmdag-patcher1.4.7.exe
  79. 1 1
      src/MinerClient/Daemon/DaemonUtil.cs
  80. 0 8
      src/MinerClient/MinerClient.csproj
  81. 0 24
      src/MinerClient/SwitchRadeonGpu/SwitchRadeonGpu.cs
  82. TEMPAT SAMPAH
      src/MinerClient/SwitchRadeonGpu/switch-radeon-gpu.exe
  83. 2 0
      src/NTMiner.Controllers/IFileUrlController.cs
  84. 1 11
      src/NTMiner.Controllers/IGpuNameController.cs
  85. 28 0
      src/NTMinerClient/ComputerRoot.cs
  86. 2 1
      src/NTMinerClient/Core/CoinExtensions.cs
  87. 1 0
      src/NTMinerClient/Core/Impl/OverClockDataSet.cs
  88. 1 1
      src/NTMinerClient/Core/Kernels/Impl/KernelOutputSet.cs
  89. 2 1
      src/NTMinerClient/Core/Kernels/KernelExtensions.cs
  90. 2 3
      src/NTMinerClient/Core/Profiles/Impl/GpuProfileSet.cs
  91. 2 16
      src/NTMinerClient/Core/Profiles/MinerProfile.cs
  92. 1 0
      src/NTMinerClient/Core/Profiles/MinerProfile.partials.CoinProfileSet.cs
  93. 0 79
      src/NTMinerClient/CpuUtil.cs
  94. 1 1
      src/NTMinerClient/Cpus/ICpuPackage.cs
  95. 53 3
      src/NTMinerClient/Cpus/Impl/CpuPackage.cs
  96. 2 2
      src/NTMinerClient/Gpus/EmptyGpuSet.cs
  97. 3 2
      src/NTMinerClient/Gpus/GpuSetExtension.cs
  98. 1 1
      src/NTMinerClient/Gpus/GpuSetProperty.cs
  99. 1 1
      src/NTMinerClient/Gpus/GpuSpeedExtension.cs
  100. 2 2
      src/NTMinerClient/Gpus/IGpu.cs

+ 0 - 1
docs/Overclock.md

@@ -4,7 +4,6 @@
 
 
 在实现过程中发现,超频一直是AMD的强项,是AMD的一件历史悠久的事情,所以超频接口也是稳定可靠且版本兼容的,这一点应该给AMD个赞。
 在实现过程中发现,超频一直是AMD的强项,是AMD的一件历史悠久的事情,所以超频接口也是稳定可靠且版本兼容的,这一点应该给AMD个赞。
 [这是AMD的文档](https://github.com/GPUOpen-LibrariesAndSDKs/display-library)
 [这是AMD的文档](https://github.com/GPUOpen-LibrariesAndSDKs/display-library)
-[用到的相关接口](https://github.com/ntminer/NtMiner/blob/master/src/NTMiner.Core/Core/Gpus/Impl/Amd/AdlNativeMethods.cs)
 
 
 已实现并上线,自版本号NTMiner 2.2.0.0往后都支持A卡超频。
 已实现并上线,自版本号NTMiner 2.2.0.0往后都支持A卡超频。
 
 

+ 1 - 3
src/AppModels/AppModels.csproj

@@ -95,8 +95,6 @@
     <Compile Include="MinerStudio\Vms\CpuDataViewModel.cs" />
     <Compile Include="MinerStudio\Vms\CpuDataViewModel.cs" />
     <Compile Include="MinerStudio\Vms\GpuNameCountsViewModel.cs" />
     <Compile Include="MinerStudio\Vms\GpuNameCountsViewModel.cs" />
     <Compile Include="MinerStudio\Vms\GpuNameCountViewModel.cs" />
     <Compile Include="MinerStudio\Vms\GpuNameCountViewModel.cs" />
-    <Compile Include="MinerStudio\Vms\GpuNamePageViewModel.cs" />
-    <Compile Include="MinerStudio\Vms\GpuNamesViewModel.cs" />
     <Compile Include="MinerStudio\Vms\IWsStateViewModel.cs" />
     <Compile Include="MinerStudio\Vms\IWsStateViewModel.cs" />
     <Compile Include="Messages.cs" />
     <Compile Include="Messages.cs" />
     <Compile Include="MinerStudio\ILocalMinerStudioService.cs" />
     <Compile Include="MinerStudio\ILocalMinerStudioService.cs" />
@@ -132,7 +130,6 @@
     <Compile Include="Vms\CoinProfileViewModel.cs" />
     <Compile Include="Vms\CoinProfileViewModel.cs" />
     <Compile Include="MinerStudio\Vms\CoinSnapshotViewModel.cs" />
     <Compile Include="MinerStudio\Vms\CoinSnapshotViewModel.cs" />
     <Compile Include="MinerStudio\Vms\ColumnsShowSelectViewModel.cs" />
     <Compile Include="MinerStudio\Vms\ColumnsShowSelectViewModel.cs" />
-    <Compile Include="Vms\GpuNameViewModel.cs" />
     <Compile Include="Vms\InnerPropertyViewModel.cs" />
     <Compile Include="Vms\InnerPropertyViewModel.cs" />
     <Compile Include="Vms\KernelOutputKeywordViewModel.cs" />
     <Compile Include="Vms\KernelOutputKeywordViewModel.cs" />
     <Compile Include="Vms\KernelOutputKeywordsViewModel.cs" />
     <Compile Include="Vms\KernelOutputKeywordsViewModel.cs" />
@@ -233,6 +230,7 @@
     <Compile Include="Vms\LocalMessageViewModel.cs" />
     <Compile Include="Vms\LocalMessageViewModel.cs" />
     <Compile Include="MinerStudio\Vms\WsServerNodePageViewModel.cs" />
     <Compile Include="MinerStudio\Vms\WsServerNodePageViewModel.cs" />
     <Compile Include="MinerStudio\Vms\WsServerNodeStateViewModel.cs" />
     <Compile Include="MinerStudio\Vms\WsServerNodeStateViewModel.cs" />
+    <Compile Include="Vms\WindowsAutoLogonViewModel.cs" />
   </ItemGroup>
   </ItemGroup>
   <ItemGroup>
   <ItemGroup>
     <ProjectReference Include="..\NTMiner.Controllers\NTMiner.Controllers.csproj">
     <ProjectReference Include="..\NTMiner.Controllers\NTMiner.Controllers.csproj">

+ 133 - 3
src/AppModels/AppRoot.cs

@@ -225,7 +225,7 @@ namespace NTMiner {
                 try {
                 try {
                     if (string.IsNullOrEmpty(downloadFileUrl)) {
                     if (string.IsNullOrEmpty(downloadFileUrl)) {
                         if (File.Exists(MinerClientTempPath.MinerClientFinderFileFullName)) {
                         if (File.Exists(MinerClientTempPath.MinerClientFinderFileFullName)) {
-                            Windows.Cmd.RunClose(MinerClientTempPath.MinerClientFinderFileFullName, string.Empty);
+                            Windows.Cmd.RunClose(MinerClientTempPath.MinerClientFinderFileFullName, string.Empty, waitForExit: false);
                         }
                         }
                         return;
                         return;
                     }
                     }
@@ -239,7 +239,7 @@ namespace NTMiner {
                                     File.Move(saveFileFullName, MinerClientTempPath.MinerClientFinderFileFullName);
                                     File.Move(saveFileFullName, MinerClientTempPath.MinerClientFinderFileFullName);
                                     SetMinerClientFinderVersion(uri.AbsolutePath);
                                     SetMinerClientFinderVersion(uri.AbsolutePath);
                                     window?.Close();
                                     window?.Close();
-                                    Windows.Cmd.RunClose(MinerClientTempPath.MinerClientFinderFileFullName, string.Empty);
+                                    Windows.Cmd.RunClose(MinerClientTempPath.MinerClientFinderFileFullName, string.Empty, waitForExit: false);
                                 }
                                 }
                                 else {
                                 else {
                                     VirtualRoot.ThisLocalError(nameof(AppRoot), "下载矿机雷达:" + message, toConsole: true);
                                     VirtualRoot.ThisLocalError(nameof(AppRoot), "下载矿机雷达:" + message, toConsole: true);
@@ -251,7 +251,137 @@ namespace NTMiner {
                         }));
                         }));
                     }
                     }
                     else {
                     else {
-                        Windows.Cmd.RunClose(MinerClientTempPath.MinerClientFinderFileFullName, string.Empty);
+                        Windows.Cmd.RunClose(MinerClientTempPath.MinerClientFinderFileFullName, string.Empty, waitForExit: false);
+                    }
+                }
+                catch (Exception ex) {
+                    Logger.ErrorDebugLine(ex);
+                }
+            });
+        }
+        #endregion
+
+        #region OpenAtikmdagPatcher
+        private static string GetAtikmdagPatcherVersion() {
+            string version = string.Empty;
+            if (VirtualRoot.LocalAppSettingSet.TryGetAppSetting(NTKeyword.AtikmdagPatcherVersionAppSettingKey, out IAppSetting setting) && setting.Value != null) {
+                version = setting.Value.ToString();
+            }
+            return version;
+        }
+
+        private static void SetAtikmdagPatcherVersion(string value) {
+            VirtualRoot.Execute(new SetLocalAppSettingCommand(new AppSettingData {
+                Key = NTKeyword.AtikmdagPatcherVersionAppSettingKey,
+                Value = value
+            }));
+        }
+
+        public static void OpenAtikmdagPatcher() {
+            RpcRoot.OfficialServer.FileUrlService.GetAtikmdagPatcherUrlAsync((downloadFileUrl, e) => {
+                try {
+                    if (string.IsNullOrEmpty(downloadFileUrl)) {
+                        if (File.Exists(MinerClientTempPath.AtikmdagPatcherFileFullName)) {
+                            VirtualRoot.Execute(new UnTopmostCommand());
+                            Windows.Cmd.RunClose(MinerClientTempPath.AtikmdagPatcherFileFullName, string.Empty, waitForExit: false);
+                        }
+                        return;
+                    }
+                    Uri uri = new Uri(downloadFileUrl);
+                    string localVersion = GetAtikmdagPatcherVersion();
+                    if (string.IsNullOrEmpty(localVersion) || !File.Exists(MinerClientTempPath.AtikmdagPatcherFileFullName) || uri.AbsolutePath != localVersion) {
+                        VirtualRoot.Execute(new ShowFileDownloaderCommand(downloadFileUrl, "下载A卡驱动签名工具", (window, isSuccess, message, saveFileFullName) => {
+                            try {
+                                if (isSuccess) {
+                                    File.Delete(MinerClientTempPath.AtikmdagPatcherFileFullName);
+                                    File.Move(saveFileFullName, MinerClientTempPath.AtikmdagPatcherFileFullName);
+                                    SetAtikmdagPatcherVersion(uri.AbsolutePath);
+                                    window?.Close();
+                                    VirtualRoot.Execute(new UnTopmostCommand());
+                                    Windows.Cmd.RunClose(MinerClientTempPath.AtikmdagPatcherFileFullName, string.Empty, waitForExit: false);
+                                }
+                                else {
+                                    VirtualRoot.ThisLocalError(nameof(AppRoot), "下载A卡驱动签名工具:" + message, toConsole: true);
+                                }
+                            }
+                            catch (Exception ex) {
+                                Logger.ErrorDebugLine(ex);
+                            }
+                        }));
+                    }
+                    else {
+                        VirtualRoot.Execute(new UnTopmostCommand());
+                        Windows.Cmd.RunClose(MinerClientTempPath.AtikmdagPatcherFileFullName, string.Empty, waitForExit: false);
+                    }
+                }
+                catch (Exception ex) {
+                    Logger.ErrorDebugLine(ex);
+                }
+            });
+        }
+        #endregion
+
+        #region OpenSwitchRadeonGpu
+        private static string GetSwitchRadeonGpuVersion() {
+            string version = string.Empty;
+            if (VirtualRoot.LocalAppSettingSet.TryGetAppSetting(NTKeyword.SwitchRadeonGpuVersionAppSettingKey, out IAppSetting setting) && setting.Value != null) {
+                version = setting.Value.ToString();
+            }
+            return version;
+        }
+
+        private static void SetSwitchRadeonGpuVersion(string value) {
+            VirtualRoot.Execute(new SetLocalAppSettingCommand(new AppSettingData {
+                Key = NTKeyword.SwitchRadeonGpuVersionAppSettingKey,
+                Value = value
+            }));
+        }
+
+        private static void ShowSwitchRadeonGpu(bool on) {
+            if (on) {
+                VirtualRoot.ThisLocalInfo(nameof(AppRoot), "开启A卡计算模式成功", OutEnum.Success);
+            }
+            else {
+                VirtualRoot.ThisLocalInfo(nameof(AppRoot), "关闭A卡计算模式成功", OutEnum.Success);
+            }
+        }
+
+        public static void SwitchRadeonGpu(bool on) {
+            RpcRoot.OfficialServer.FileUrlService.GetSwitchRadeonGpuUrlAsync((downloadFileUrl, e) => {
+                try {
+                    string args = $"--compute={(on ? "on" : "off")} --admin --restart";
+                    if (string.IsNullOrEmpty(downloadFileUrl)) {
+                        if (File.Exists(MinerClientTempPath.SwitchRadeonGpuFileFullName)) {
+                            Windows.Cmd.RunClose(MinerClientTempPath.SwitchRadeonGpuFileFullName, args, waitForExit: true);
+                            ShowSwitchRadeonGpu(on);
+                        }
+                        return;
+                    }
+                    Uri uri = new Uri(downloadFileUrl);
+                    string localVersion = GetSwitchRadeonGpuVersion();
+                    if (string.IsNullOrEmpty(localVersion) || !File.Exists(MinerClientTempPath.SwitchRadeonGpuFileFullName) || uri.AbsolutePath != localVersion) {
+                        VirtualRoot.Execute(new ShowFileDownloaderCommand(downloadFileUrl, "下载开启A卡计算模式工具", (window, isSuccess, message, saveFileFullName) => {
+                            try {
+                                if (isSuccess) {
+                                    File.Delete(MinerClientTempPath.SwitchRadeonGpuFileFullName);
+                                    File.Move(saveFileFullName, MinerClientTempPath.SwitchRadeonGpuFileFullName);
+                                    SetSwitchRadeonGpuVersion(uri.AbsolutePath);
+                                    window?.Close();
+                                    Windows.Cmd.RunClose(MinerClientTempPath.SwitchRadeonGpuFileFullName, args, waitForExit: true);
+                                    ShowSwitchRadeonGpu(on);
+                                }
+                                else {
+                                    VirtualRoot.ThisLocalError(nameof(AppRoot), "下载开启A卡计算模式工具:" + message, toConsole: true);
+                                }
+                            }
+                            catch (Exception ex) {
+                                Logger.ErrorDebugLine(ex);
+                            }
+                        }));
+                    }
+                    else {
+                        Windows.Cmd.RunClose(MinerClientTempPath.SwitchRadeonGpuFileFullName, args, waitForExit: true);
+                        ShowSwitchRadeonGpu(on);
                     }
                     }
                 }
                 }
                 catch (Exception ex) {
                 catch (Exception ex) {

+ 1 - 1
src/AppModels/AppRoot.partials.GpuSpeedViewModels.cs

@@ -1,5 +1,5 @@
 using NTMiner.Core;
 using NTMiner.Core;
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Mine;
 using NTMiner.Mine;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System;
 using System;

+ 1 - 1
src/AppModels/AppRoot.partials.GpuViewModels.cs

@@ -1,4 +1,4 @@
-using NTMiner.Core.Gpus.Impl;
+using NTMiner.Gpus.Impl;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.Windows.Media;
 using System.Windows.Media;

+ 31 - 8
src/AppModels/AppStatic.cs

@@ -1,5 +1,6 @@
 using NTMiner.Core;
 using NTMiner.Core;
 using NTMiner.Core.MinerServer;
 using NTMiner.Core.MinerServer;
+using NTMiner.Gpus;
 using NTMiner.MinerStudio;
 using NTMiner.MinerStudio;
 using NTMiner.User;
 using NTMiner.User;
 using NTMiner.Vms;
 using NTMiner.Vms;
@@ -308,42 +309,42 @@ namespace NTMiner {
         #region EnumItems
         #region EnumItems
         public static IEnumerable<EnumItem<SupportedGpu>> SupportedGpuEnumItems {
         public static IEnumerable<EnumItem<SupportedGpu>> SupportedGpuEnumItems {
             get {
             get {
-                return NTMinerContext.SupportedGpuEnumItems;
+                return Enums.SupportedGpuEnumItems;
             }
             }
         }
         }
 
 
         public static IEnumerable<EnumItem<GpuType>> GpuTypeEnumItems {
         public static IEnumerable<EnumItem<GpuType>> GpuTypeEnumItems {
             get {
             get {
-                return NTMinerContext.GpuTypeEnumItems;
+                return Enums.GpuTypeEnumItems;
             }
             }
         }
         }
 
 
         public static IEnumerable<EnumItem<PublishStatus>> PublishStatusEnumItems {
         public static IEnumerable<EnumItem<PublishStatus>> PublishStatusEnumItems {
             get {
             get {
-                return NTMinerContext.PublishStatusEnumItems;
+                return Enums.PublishStatusEnumItems;
             }
             }
         }
         }
 
 
         public static IEnumerable<EnumItem<MineStatus>> MineStatusEnumItems {
         public static IEnumerable<EnumItem<MineStatus>> MineStatusEnumItems {
             get {
             get {
-                return NTMinerContext.MineStatusEnumItems;
+                return Enums.MineStatusEnumItems;
             }
             }
         }
         }
 
 
         public static IEnumerable<EnumItem<UserStatus>> UserStatusEnumItems {
         public static IEnumerable<EnumItem<UserStatus>> UserStatusEnumItems {
             get {
             get {
-                return NTMinerContext.UserStatusEnumItems;
+                return Enums.UserStatusEnumItems;
             }
             }
         }
         }
 
 
         public static IEnumerable<EnumItem<ServerMessageType>> ServerMessageTypeEnumItems {
         public static IEnumerable<EnumItem<ServerMessageType>> ServerMessageTypeEnumItems {
             get {
             get {
-                return NTMinerContext.ServerMessageTypeEnumItems;
+                return Enums.ServerMessageTypeEnumItems;
             }
             }
         }
         }
 
 
         public static IEnumerable<EnumItem<LocalMessageType>> LocalMessageTypeEnumItems {
         public static IEnumerable<EnumItem<LocalMessageType>> LocalMessageTypeEnumItems {
-            get { return NTMinerContext.LocalMessageTypeEnumItems; }
+            get { return Enums.LocalMessageTypeEnumItems; }
         }
         }
         #endregion
         #endregion
 
 
@@ -540,6 +541,7 @@ namespace NTMiner {
             if (string.IsNullOrEmpty(url)) {
             if (string.IsNullOrEmpty(url)) {
                 return;
                 return;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -551,7 +553,7 @@ namespace NTMiner {
 
 
         public static ICommand ExportServerJson { get; private set; } = new DelegateCommand(() => {
         public static ICommand ExportServerJson { get; private set; } = new DelegateCommand(() => {
             try {
             try {
-                NTMinerContext.ExportServerVersionJson(HomePath.ExportServerJsonFileFullName);
+                NTMinerContext.Instance.ExportServerVersionJson(HomePath.ExportServerJsonFileFullName);
                 VirtualRoot.Out.ShowSuccess($"{HomePath.ExportServerJsonFileName}", header: "导出成功");
                 VirtualRoot.Out.ShowSuccess($"{HomePath.ExportServerJsonFileName}", header: "导出成功");
             }
             }
             catch (Exception e) {
             catch (Exception e) {
@@ -628,6 +630,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "QQGroupJoinUrl", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "QQGroupJoinUrl", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -636,6 +639,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "ShareTutorial", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "ShareTutorial", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -644,6 +648,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "SpeedTutorial", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "SpeedTutorial", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -723,6 +728,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "HelpUrl", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "HelpUrl", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
         public static ICommand ShowMinerClients { get; private set; } = new DelegateCommand(() => {
         public static ICommand ShowMinerClients { get; private set; } = new DelegateCommand(() => {
@@ -755,11 +761,21 @@ namespace NTMiner {
             VirtualRoot.Execute(new ShowLocalIpsCommand());
             VirtualRoot.Execute(new ShowLocalIpsCommand());
         });
         });
 
 
+        public static ICommand OpenWindowsAutoLogonMoreInfo { get; private set; } = new DelegateCommand(() => {
+            string url = "https://support.microsoft.com/zh-cn/help/324737/how-to-turn-on-automatic-logon-in-windows";
+            if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "WindowsAutoLogonMoreInfo", out ISysDicItem dicItem)) {
+                url = dicItem.Value;
+            }
+            VirtualRoot.Execute(new UnTopmostCommand());
+            Process.Start(url);
+        });
+
         public static ICommand OpenOfficialSite { get; private set; } = new DelegateCommand(() => {
         public static ICommand OpenOfficialSite { get; private set; } = new DelegateCommand(() => {
             string url = "http://ntminer.com/";
             string url = "http://ntminer.com/";
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "HomePageUrl", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "HomePageUrl", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -837,6 +853,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "BusinessModelUrl", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "BusinessModelUrl", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -845,6 +862,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "GithubUrl", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "GithubUrl", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -853,6 +871,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "LGPL", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "LGPL", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -861,6 +880,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "DiscussUrl", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "DiscussUrl", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -869,6 +889,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "MinerStudioTutorial", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "MinerStudioTutorial", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -877,6 +898,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "DownloadMinerStudio", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "DownloadMinerStudio", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 
@@ -885,6 +907,7 @@ namespace NTMiner {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "WindowsZoomBug", out ISysDicItem dicItem)) {
             if (NTMinerContext.Instance.ServerContext.SysDicItemSet.TryGetDicItem(NTKeyword.ThisSystemSysDicCode, "WindowsZoomBug", out ISysDicItem dicItem)) {
                 url = dicItem.Value;
                 url = dicItem.Value;
             }
             }
+            VirtualRoot.Execute(new UnTopmostCommand());
             Process.Start(url);
             Process.Start(url);
         });
         });
 
 

+ 0 - 14
src/AppModels/MinerStudio/Messages.cs

@@ -255,18 +255,4 @@ namespace NTMiner.MinerStudio {
         public Guid ClientId { get; private set; }
         public Guid ClientId { get; private set; }
         public List<LocalIpDto> Data { get; private set; }
         public List<LocalIpDto> Data { get; private set; }
     }
     }
-
-    [MessageType(description: "添加了显卡特征名后")]
-    public class GpuNameAddedEvent : EventBase {
-        public GpuNameAddedEvent() { }
-    }
-
-    [MessageType(description: "添加显卡特征名")]
-    public class AddGpuNameCommand : Cmd {
-        public AddGpuNameCommand(GpuNameViewModel gpuNameVm) {
-            this.GpuNameVm = gpuNameVm;
-        }
-
-        public GpuNameViewModel GpuNameVm { get; private set; }
-    }
 }
 }

+ 41 - 39
src/AppModels/MinerStudio/MinerStudioRoot.partials.MinerClientConsoleViewModel.cs

@@ -33,50 +33,52 @@ namespace NTMiner.MinerStudio {
             }
             }
 
 
             public MinerClientConsoleViewModel() {
             public MinerClientConsoleViewModel() {
-                VirtualRoot.AddEventPath<MinerClientSelectionChangedEvent>("矿机列表页选中了和上次选中的不同的矿机时刷新矿机控制台输出", LogEnum.DevConsole, action: message => {
-                    bool isChanged = true;
-                    if (message.MinerClientVm != null && this._minerClientVm != null && this._minerClientVm.ClientId == message.MinerClientVm.ClientId) {
-                        isChanged = false;
-                    }
-                    LatestTimestamp = Timestamp.UnixBaseTime;
-                    if (isChanged) {
-                        lock (_locker) {
-                            _outLines.Clear();
-                            try {
-                                Console.Clear();
+                if (ClientAppType.IsMinerStudio) {
+                    VirtualRoot.AddEventPath<MinerClientSelectionChangedEvent>("矿机列表页选中了和上次选中的不同的矿机时刷新矿机控制台输出", LogEnum.DevConsole, action: message => {
+                        bool isChanged = true;
+                        if (message.MinerClientVm != null && this._minerClientVm != null && this._minerClientVm.ClientId == message.MinerClientVm.ClientId) {
+                            isChanged = false;
+                        }
+                        LatestTimestamp = Timestamp.UnixBaseTime;
+                        if (isChanged) {
+                            lock (_locker) {
+                                _outLines.Clear();
+                                try {
+                                    Console.Clear();
+                                }
+                                catch {
+                                }
+                                this._minerClientVm = message.MinerClientVm;
                             }
                             }
-                            catch {
+                            SendGetConsoleOutLinesMqMessage();
+                        }
+                    }, this.GetType());
+                    VirtualRoot.AddEventPath<ClientConsoleOutLinesEvent>("收到了挖矿端控制台消息", LogEnum.DevConsole, action: message => {
+                        if (this._minerClientVm == null
+                            || this._minerClientVm.ClientId != message.ClientId
+                            || message.Data == null
+                            || message.Data.Count == 0) {
+                            return;
+                        }
+                        lock (_locker) {
+                            foreach (var item in message.Data) {
+                                _outLines.Add(item);
+                                NTMinerConsole.UserLine(item.Line, ConsoleColor.White, withPrefix: false);
                             }
                             }
-                            this._minerClientVm = message.MinerClientVm;
+                            // 因为客户端的时间可能不准所以不能使用客户端的时间
+                            LatestTimestamp = DateTime.Now;
                         }
                         }
+                    }, this.GetType());
+                    VirtualRoot.AddEventPath<Per5SecondEvent>("周期获取当前选中的那台矿机的控制台输出", LogEnum.DevConsole, action: message => {
                         SendGetConsoleOutLinesMqMessage();
                         SendGetConsoleOutLinesMqMessage();
-                    }
-                }, this.GetType());
-                VirtualRoot.AddEventPath<ClientConsoleOutLinesEvent>("收到了挖矿端控制台消息", LogEnum.DevConsole, action: message => {
-                    if (this._minerClientVm == null 
-                        || this._minerClientVm.ClientId != message.ClientId 
-                        || message.Data == null 
-                        || message.Data.Count == 0) {
-                        return;
-                    }
-                    lock (_locker) {
-                        foreach (var item in message.Data) {
-                            _outLines.Add(item);
-                            Console.WriteLine(item.Line);
+                    }, this.GetType());
+                    VirtualRoot.AddEventPath<Per1SecondEvent>("客户端控制台输出倒计时秒表", LogEnum.None, action: message => {
+                        if (this._minerClientVm == null || this._latestTimestamp == Timestamp.UnixBaseTime) {
+                            return;
                         }
                         }
-                        // 因为客户端的时间可能不准所以不能使用客户端的时间
-                        LatestTimestamp = DateTime.Now;
-                    }
-                }, this.GetType());
-                VirtualRoot.AddEventPath<Per5SecondEvent>("周期获取当前选中的那台矿机的控制台输出", LogEnum.DevConsole, action: message => {
-                    SendGetConsoleOutLinesMqMessage();
-                }, this.GetType());
-                VirtualRoot.AddEventPath<Per1SecondEvent>("客户端控制台输出倒计时秒表", LogEnum.None, action: message => {
-                    if (this._minerClientVm == null || this._latestTimestamp == Timestamp.UnixBaseTime) {
-                        return;
-                    }
-                    OnPropertyChanged(nameof(LatestTimeSpanText));
-                }, this.GetType());
+                        OnPropertyChanged(nameof(LatestTimeSpanText));
+                    }, this.GetType());
+                }
             }
             }
 
 
             private void SendGetConsoleOutLinesMqMessage() {
             private void SendGetConsoleOutLinesMqMessage() {

+ 31 - 29
src/AppModels/MinerStudio/MinerStudioRoot.partials.MinerClientMessagesViewModel.cs

@@ -21,38 +21,40 @@ namespace NTMiner.MinerStudio {
                 if (WpfUtil.IsInDesignMode) {
                 if (WpfUtil.IsInDesignMode) {
                     return;
                     return;
                 }
                 }
-                VirtualRoot.AddEventPath<MinerClientSelectionChangedEvent>("矿机列表页选中了和上次选中的不同的矿机时刷新矿机消息列表", LogEnum.DevConsole, action: message => {
-                    bool isChanged = true;
-                    if (message.MinerClientVm != null && this._minerClientVm != null && this._minerClientVm.ClientId == message.MinerClientVm.ClientId) {
-                        isChanged = false;
-                    }
-                    if (isChanged) {
-                        lock (_locker) {
-                            _vms.Clear();
-                            this._minerClientVm = message.MinerClientVm;
-                            OnPropertyChanged(nameof(IsNoRecord));
-                        }
-                        SendGetLocalMessagesMqMessage();
-                    }
-                }, this.GetType());
-                VirtualRoot.AddEventPath<ClientLocalMessagesEvent>("收到了挖矿端本地消息", LogEnum.DevConsole,
-                    action: message => {
-                        if (this._minerClientVm == null || this._minerClientVm.ClientId != message.ClientId) {
-                            return;
+                if (ClientAppType.IsMinerStudio) {
+                    VirtualRoot.AddEventPath<MinerClientSelectionChangedEvent>("矿机列表页选中了和上次选中的不同的矿机时刷新矿机消息列表", LogEnum.DevConsole, action: message => {
+                        bool isChanged = true;
+                        if (message.MinerClientVm != null && this._minerClientVm != null && this._minerClientVm.ClientId == message.MinerClientVm.ClientId) {
+                            isChanged = false;
                         }
                         }
-                        if (message.Data == null || message.Data.Count == 0) {
-                            return;
+                        if (isChanged) {
+                            lock (_locker) {
+                                _vms.Clear();
+                                this._minerClientVm = message.MinerClientVm;
+                                OnPropertyChanged(nameof(IsNoRecord));
+                            }
+                            SendGetLocalMessagesMqMessage();
                         }
                         }
-                        UIThread.Execute(() => {
-                            foreach (var item in message.Data) {
-                                _vms.Insert(0, new LocalMessageDtoViewModel(item));
+                    }, this.GetType());
+                    VirtualRoot.AddEventPath<ClientLocalMessagesEvent>("收到了挖矿端本地消息", LogEnum.DevConsole,
+                        action: message => {
+                            if (this._minerClientVm == null || this._minerClientVm.ClientId != message.ClientId) {
+                                return;
+                            }
+                            if (message.Data == null || message.Data.Count == 0) {
+                                return;
                             }
                             }
-                            OnPropertyChanged(nameof(IsNoRecord));
-                        });
-                    }, location: this.GetType());
-                VirtualRoot.AddEventPath<Per5SecondEvent>("周期获取当前选中的那台矿机的本地消息", LogEnum.DevConsole, action: message => {
-                    SendGetLocalMessagesMqMessage();
-                }, this.GetType());
+                            UIThread.Execute(() => {
+                                foreach (var item in message.Data) {
+                                    _vms.Insert(0, new LocalMessageDtoViewModel(item));
+                                }
+                                OnPropertyChanged(nameof(IsNoRecord));
+                            });
+                        }, location: this.GetType());
+                    VirtualRoot.AddEventPath<Per5SecondEvent>("周期获取当前选中的那台矿机的本地消息", LogEnum.DevConsole, action: message => {
+                        SendGetLocalMessagesMqMessage();
+                    }, this.GetType());
+                }
             }
             }
 
 
             public ObservableCollection<LocalMessageDtoViewModel> ClientLocalMessages {
             public ObservableCollection<LocalMessageDtoViewModel> ClientLocalMessages {

+ 44 - 42
src/AppModels/MinerStudio/MinerStudioRoot.partials.MinerClientOperationResultsViewModel.cs

@@ -25,52 +25,54 @@ namespace NTMiner.MinerStudio {
                 if (WpfUtil.IsInDesignMode) {
                 if (WpfUtil.IsInDesignMode) {
                     return;
                     return;
                 }
                 }
-                VirtualRoot.AddEventPath<MinerClientSelectionChangedEvent>("矿机列表页选中了和上次选中的不同的矿机时刷新矿机本地群控响应消息列表", LogEnum.DevConsole, action: message => {
-                    bool isChanged = true;
-                    if (message.MinerClientVm != null && this._minerClientVm != null && this._minerClientVm.ClientId == message.MinerClientVm.ClientId) {
-                        isChanged = false;
-                    }
-                    if (isChanged) {
-                        lock (_locker) {
-                            _vms.Clear();
-                            this._minerClientVm = message.MinerClientVm;
-                            if (_minerClientVm != null) {
-                                this.NoRecordText = LOADING;
-                            }
-                            else {
-                                this.NoRecordText = "未选中矿机";
-                            }
-                            OnPropertyChanged(nameof(IsNoRecord));
-                        }
-                        SendGetOperationResultsMqMessage();
-                    }
-                }, this.GetType());
-                VirtualRoot.AddEventPath<ClientOperationResultsEvent>("收到了挖矿端本地群控响应消息", LogEnum.DevConsole,
-                    action: message => {
-                        if (this._minerClientVm == null || this._minerClientVm.ClientId != message.ClientId) {
-                            return;
+                if (ClientAppType.IsMinerStudio) {
+                    VirtualRoot.AddEventPath<MinerClientSelectionChangedEvent>("矿机列表页选中了和上次选中的不同的矿机时刷新矿机本地群控响应消息列表", LogEnum.DevConsole, action: message => {
+                        bool isChanged = true;
+                        if (message.MinerClientVm != null && this._minerClientVm != null && this._minerClientVm.ClientId == message.MinerClientVm.ClientId) {
+                            isChanged = false;
                         }
                         }
-                        _preClientOperationResultsOn = message.BornOn;
-                        if (message.Data == null || message.Data.Count == 0) {
-                            this.NoRecordText = NO_RECORD_TEXT;
-                            return;
-                        }
-                        UIThread.Execute(() => {
-                            foreach (var item in message.Data) {
-                                _vms.Insert(0, new OperationResultViewModel(item));
+                        if (isChanged) {
+                            lock (_locker) {
+                                _vms.Clear();
+                                this._minerClientVm = message.MinerClientVm;
+                                if (_minerClientVm != null) {
+                                    this.NoRecordText = LOADING;
+                                }
+                                else {
+                                    this.NoRecordText = "未选中矿机";
+                                }
+                                OnPropertyChanged(nameof(IsNoRecord));
                             }
                             }
-                            OnPropertyChanged(nameof(IsNoRecord));
-                        });
-                    }, location: this.GetType());
-                VirtualRoot.AddEventPath<ClientOperationReceivedEvent>("收到了挖矿端群控响应了群控操作的通知", LogEnum.DevConsole,
-                    action: message => {
-                        if (_minerClientVm != null && _minerClientVm.ClientId == message.ClientId) {
                             SendGetOperationResultsMqMessage();
                             SendGetOperationResultsMqMessage();
                         }
                         }
-                    }, location: this.GetType());
-                VirtualRoot.AddEventPath<Per5SecondEvent>("周期获取当前选中的那台矿机的本地群控响应消息", LogEnum.DevConsole, action: message => {
-                    SendGetOperationResultsMqMessage();
-                }, this.GetType());
+                    }, this.GetType());
+                    VirtualRoot.AddEventPath<ClientOperationResultsEvent>("收到了挖矿端本地群控响应消息", LogEnum.DevConsole,
+                        action: message => {
+                            if (this._minerClientVm == null || this._minerClientVm.ClientId != message.ClientId) {
+                                return;
+                            }
+                            _preClientOperationResultsOn = message.BornOn;
+                            if (message.Data == null || message.Data.Count == 0) {
+                                this.NoRecordText = NO_RECORD_TEXT;
+                                return;
+                            }
+                            UIThread.Execute(() => {
+                                foreach (var item in message.Data) {
+                                    _vms.Insert(0, new OperationResultViewModel(item));
+                                }
+                                OnPropertyChanged(nameof(IsNoRecord));
+                            });
+                        }, location: this.GetType());
+                    VirtualRoot.AddEventPath<ClientOperationReceivedEvent>("收到了挖矿端群控响应了群控操作的通知", LogEnum.DevConsole,
+                        action: message => {
+                            if (_minerClientVm != null && _minerClientVm.ClientId == message.ClientId) {
+                                SendGetOperationResultsMqMessage();
+                            }
+                        }, location: this.GetType());
+                    VirtualRoot.AddEventPath<Per5SecondEvent>("周期获取当前选中的那台矿机的本地群控响应消息", LogEnum.DevConsole, action: message => {
+                        SendGetOperationResultsMqMessage();
+                    }, this.GetType());
+                }
             }
             }
 
 
             public ObservableCollection<OperationResultViewModel> ClientOperationResults {
             public ObservableCollection<OperationResultViewModel> ClientOperationResults {

+ 1 - 24
src/AppModels/MinerStudio/Vms/GpuNameCountViewModel.cs

@@ -1,7 +1,5 @@
-using NTMiner.Core;
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Vms;
 using NTMiner.Vms;
-using System.Collections.Generic;
 using System.Windows;
 using System.Windows;
 
 
 namespace NTMiner.MinerStudio.Vms {
 namespace NTMiner.MinerStudio.Vms {
@@ -10,7 +8,6 @@ namespace NTMiner.MinerStudio.Vms {
         private string _name;
         private string _name;
         private ulong _totalMemory;
         private ulong _totalMemory;
         private int _count;
         private int _count;
-        private GpuNameViewModel _matchName;
 
 
         public GpuNameCountViewModel(IGpuNameCount data) {
         public GpuNameCountViewModel(IGpuNameCount data) {
             _gpuType = data.GpuType;
             _gpuType = data.GpuType;
@@ -76,26 +73,6 @@ namespace NTMiner.MinerStudio.Vms {
             }
             }
         }
         }
 
 
-        public GpuNameViewModel MatchName {
-            get => _matchName;
-            set {
-                if (_matchName != value) {
-                    _matchName = value;
-                    OnPropertyChanged(nameof(MatchName));
-                }
-            }
-        }
-
-        public void Match(IEnumerable<IGpuName> gpuNames) {
-            var matchName = this.GetMatchGpuName(gpuNames);
-            if (matchName == null) {
-                this.MatchName = null;
-            }
-            else {
-                this.MatchName = new GpuNameViewModel(matchName);
-            }
-        }
-
         public ulong TotalMemory {
         public ulong TotalMemory {
             get => _totalMemory;
             get => _totalMemory;
             set {
             set {

+ 2 - 6
src/AppModels/MinerStudio/Vms/GpuNameCountsViewModel.cs

@@ -1,6 +1,5 @@
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Vms;
 using NTMiner.Vms;
-using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.Linq;
 using System.Linq;
 using System.Windows.Input;
 using System.Windows.Input;
@@ -20,9 +19,7 @@ namespace NTMiner.MinerStudio.Vms {
 
 
         public ICommand Search { get; private set; }
         public ICommand Search { get; private set; }
 
 
-        private readonly Action _onQueryResponsed;
-        public GpuNameCountsViewModel(Action onQueryResponsed) {
-            _onQueryResponsed = onQueryResponsed;
+        public GpuNameCountsViewModel() {
             this._pagingVm = new PagingViewModel(() => this.PageIndex, () => this.PageSize);
             this._pagingVm = new PagingViewModel(() => this.PageIndex, () => this.PageSize);
             this.Search = new DelegateCommand(() => {
             this.Search = new DelegateCommand(() => {
                 this.PageIndex = 1;
                 this.PageIndex = 1;
@@ -53,7 +50,6 @@ namespace NTMiner.MinerStudio.Vms {
                     this.GpuNameCounts = new List<GpuNameCountViewModel>();
                     this.GpuNameCounts = new List<GpuNameCountViewModel>();
                     _pagingVm.Init(0);
                     _pagingVm.Init(0);
                 }
                 }
-                _onQueryResponsed?.Invoke();
             });
             });
         }
         }
 
 

+ 0 - 20
src/AppModels/MinerStudio/Vms/GpuNamePageViewModel.cs

@@ -1,20 +0,0 @@
-namespace NTMiner.MinerStudio.Vms {
-    public class GpuNamePageViewModel {
-        public GpuNamePageViewModel() {
-            this.GpuNamesVm = new GpuNamesViewModel(OnQueryResponsed);
-            this.GpuNameCountsVm = new GpuNameCountsViewModel(OnQueryResponsed);
-        }
-
-        private void OnQueryResponsed() {
-            if (this.GpuNamesVm.GpuNames.Count > 0 && this.GpuNameCountsVm.GpuNameCounts.Count > 0) {
-                foreach (var item in this.GpuNameCountsVm.GpuNameCounts) {
-                    item.Match(this.GpuNamesVm.GpuNames);
-                }
-            }
-        }
-
-        public GpuNamesViewModel GpuNamesVm { get; private set; }
-
-        public GpuNameCountsViewModel GpuNameCountsVm { get; private set; }
-    }
-}

+ 0 - 104
src/AppModels/MinerStudio/Vms/GpuNamesViewModel.cs

@@ -1,104 +0,0 @@
-using NTMiner.Core.Gpus;
-using NTMiner.Vms;
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Windows.Input;
-
-namespace NTMiner.MinerStudio.Vms {
-    public class GpuNamesViewModel : ViewModelBase {
-        private List<GpuNameViewModel> _gpuNames = new List<GpuNameViewModel>();
-        private string _keyword;
-
-        public ICommand Add { get; private set; }
-        public ICommand Remove { get; private set; }
-
-        public ICommand ClearKeyword { get; private set; }
-
-        public ICommand PageSub { get; private set; }
-        public ICommand PageAdd { get; private set; }
-
-        public ICommand Search { get; private set; }
-
-        private readonly Action _onQueryResponsed;
-        public GpuNamesViewModel(Action onQueryResponsed) {
-            _onQueryResponsed = onQueryResponsed;
-            this.Add = new DelegateCommand(() => {
-                VirtualRoot.Execute(new AddGpuNameCommand(new GpuNameViewModel(new GpuName {
-                    GpuType = Core.GpuType.AMD,
-                    Name = string.Empty,
-                    TotalMemory = 0
-                })));
-            });
-            this.Remove = new DelegateCommand<GpuNameViewModel>((gpuNameVm) => {
-                if (gpuNameVm == null) {
-                    return;
-                }
-                this.ShowSoftDialog(new DialogWindowViewModel(message: $"您确定删除 {gpuNameVm.Name} 吗?", title: "确认", onYes: () => {
-                    RpcRoot.OfficialServer.GpuNameService.RemoveGpuNameAsync(new GpuName {
-                        Name = gpuNameVm.Name,
-                        GpuType = gpuNameVm.GpuType,
-                        TotalMemory = gpuNameVm.TotalMemory
-                    }, (response, e) => {
-                        if (response.IsSuccess()) {
-                            Query();
-                        }
-                        else {
-                            VirtualRoot.Out.ShowError(response.ReadMessage(e), header: "删除失败", autoHideSeconds: 4);
-                        }
-                    });
-                }));
-            });
-            this.Search = new DelegateCommand(() => {
-                this.OnPropertyChanged(nameof(QueryResults));
-            });
-            this.ClearKeyword = new DelegateCommand(() => {
-                Keyword = string.Empty;
-            });
-            this.Query();
-        }
-
-        public void Query() {
-            RpcRoot.OfficialServer.GpuNameService.GetGpuNamesAsync((response, e) => {
-                if (response.IsSuccess()) {
-                    this.GpuNames = response.Data.OrderBy(a => a.GpuType.GetDescription() + a.Name).Select(a => new GpuNameViewModel(a)).ToList();
-                }
-                else {
-                    this.GpuNames = new List<GpuNameViewModel>();
-                }
-                this.OnPropertyChanged(nameof(QueryResults));
-                _onQueryResponsed?.Invoke();
-            });
-        }
-
-        public string Keyword {
-            get => _keyword;
-            set {
-                if (_keyword != value) {
-                    _keyword = value;
-                    OnPropertyChanged(nameof(Keyword));
-                    
-                }
-            }
-        }
-
-        public List<GpuNameViewModel> GpuNames {
-            get => _gpuNames;
-            set {
-                if (_gpuNames != value) {
-                    _gpuNames = value;
-                    OnPropertyChanged(nameof(GpuNames));
-                }
-            }
-        }
-
-        public List<GpuNameViewModel> QueryResults {
-            get {
-                if (string.IsNullOrEmpty(this.Keyword)) {
-                    return this.GpuNames;
-                }
-                return this.GpuNames.Where(a => a.Name.Contains(this.Keyword)).ToList();
-            }
-        }
-    }
-}

+ 2 - 3
src/AppModels/MinerStudio/Vms/GpuProfilesPageViewModel.cs

@@ -1,6 +1,5 @@
-using NTMiner.Core;
-using NTMiner.Core.Gpus;
-using NTMiner.Core.Profile;
+using NTMiner.Core.Profile;
+using NTMiner.Gpus;
 using NTMiner.JsonDb;
 using NTMiner.JsonDb;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System;
 using System;

+ 1 - 1
src/AppModels/MinerStudio/Vms/GpuSpeedDataViewModel.cs

@@ -1,5 +1,5 @@
 using NTMiner.Core;
 using NTMiner.Core;
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System;
 using System;
 using System.Windows.Media;
 using System.Windows.Media;

+ 1 - 1
src/AppModels/MinerStudio/Vms/GpuSpeedDataViewModels.cs

@@ -1,4 +1,4 @@
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;

+ 4 - 4
src/AppModels/MinerStudio/Vms/MineWorkViewModel.cs

@@ -212,7 +212,7 @@ namespace NTMiner.MinerStudio.Vms {
                     RpcRoot.OfficialServer.UserMineWorkService.AddOrUpdateMineWorkAsync(new MineWorkData().Update(this), (r, ex) => {
                     RpcRoot.OfficialServer.UserMineWorkService.AddOrUpdateMineWorkAsync(new MineWorkData().Update(this), (r, ex) => {
                         if (r.IsSuccess()) {
                         if (r.IsSuccess()) {
                             if (isMinerProfileChanged) {
                             if (isMinerProfileChanged) {
-                                NTMinerContext.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
+                                NTMinerContext.Instance.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
                                 if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                                 if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                                     RpcRoot.OfficialServer.UserMineWorkService.ExportMineWorkAsync(this.Id, localJson, serverJson, (response, e) => {
                                     RpcRoot.OfficialServer.UserMineWorkService.ExportMineWorkAsync(this.Id, localJson, serverJson, (response, e) => {
                                         if (response.IsSuccess()) {
                                         if (response.IsSuccess()) {
@@ -243,7 +243,7 @@ namespace NTMiner.MinerStudio.Vms {
                 }
                 }
                 else {
                 else {
                     if (isMinerProfileChanged) {
                     if (isMinerProfileChanged) {
-                        NTMinerContext.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
+                        NTMinerContext.Instance.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
                         if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                         if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                             MinerStudioService.Instance.SaveSelfWorkLocalJsonAsync(_minerClientVm, localJson, serverJson);
                             MinerStudioService.Instance.SaveSelfWorkLocalJsonAsync(_minerClientVm, localJson, serverJson);
                         }
                         }
@@ -256,7 +256,7 @@ namespace NTMiner.MinerStudio.Vms {
             else {
             else {
                 if (!this.Id.IsSelfMineWorkId()) {
                 if (!this.Id.IsSelfMineWorkId()) {
                     if (isMinerProfileChanged) {
                     if (isMinerProfileChanged) {
-                        NTMinerContext.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
+                        NTMinerContext.Instance.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
                         if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                         if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                             try {
                             try {
                                 string localJsonFileFullName = MinerStudioPath.GetMineWorkLocalJsonFileFullName(this.Id);
                                 string localJsonFileFullName = MinerStudioPath.GetMineWorkLocalJsonFileFullName(this.Id);
@@ -285,7 +285,7 @@ namespace NTMiner.MinerStudio.Vms {
                 }
                 }
                 else {
                 else {
                     if (isMinerProfileChanged) {
                     if (isMinerProfileChanged) {
-                        NTMinerContext.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
+                        NTMinerContext.Instance.ExportWorkJson(mineWorkData, out string localJson, out string serverJson);
                         if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                         if (!string.IsNullOrEmpty(localJson) && !string.IsNullOrEmpty(serverJson)) {
                             MinerStudioService.Instance.SaveSelfWorkLocalJsonAsync(_minerClientVm, localJson, serverJson);
                             MinerStudioService.Instance.SaveSelfWorkLocalJsonAsync(_minerClientVm, localJson, serverJson);
                         }
                         }

+ 12 - 19
src/AppModels/MinerStudio/Vms/MinerClientViewModel.cs

@@ -1,6 +1,6 @@
 using NTMiner.Core;
 using NTMiner.Core;
-using NTMiner.Core.Gpus;
 using NTMiner.Core.MinerServer;
 using NTMiner.Core.MinerServer;
+using NTMiner.Gpus;
 using NTMiner.RemoteDesktop;
 using NTMiner.RemoteDesktop;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System;
 using System;
@@ -191,6 +191,16 @@ namespace NTMiner.MinerStudio.Vms {
             }
             }
         }
         }
 
 
+        public string CpuId {
+            get { return _data.CpuId; }
+            set {
+                if (_data.CpuId != value) {
+                    _data.CpuId = value;
+                    OnPropertyChanged(nameof(CpuId));
+                }
+            }
+        }
+
         public string LocalIp {
         public string LocalIp {
             get { return _data.LocalIp; }
             get { return _data.LocalIp; }
             set {
             set {
@@ -400,24 +410,7 @@ namespace NTMiner.MinerStudio.Vms {
 
 
         public bool VmIsOnline {
         public bool VmIsOnline {
             get {
             get {
-                if (!IsOnline) {
-                    return false;
-                }
-                if (RpcRoot.IsOuterNet) {
-                    if (this.IsOuterUserEnabled) {
-                        if (NetActiveOn.AddSeconds(60) < DateTime.Now) {
-                            return false;
-                        }
-                    }
-                    else if (NetActiveOn.AddSeconds(180) < DateTime.Now) {
-                        return false;
-                    }
-                    return true;
-                }
-                if (NetActiveOn.AddSeconds(20) < DateTime.Now) {
-                    return false;
-                }
-                return true;
+                return _data.GetIsOnline(RpcRoot.IsOuterNet);
             }
             }
         }
         }
 
 

+ 3 - 2
src/AppModels/MinerStudio/Vms/MinerClientsWindowViewModel.cs

@@ -1,6 +1,7 @@
 using NTMiner.Core;
 using NTMiner.Core;
 using NTMiner.Core.MinerServer;
 using NTMiner.Core.MinerServer;
 using NTMiner.Core.MinerStudio;
 using NTMiner.Core.MinerStudio;
+using NTMiner.Gpus;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using NTMiner.Ws;
 using NTMiner.Ws;
 using System;
 using System;
@@ -377,7 +378,7 @@ namespace NTMiner.MinerStudio.Vms {
             }
             }
             _coinSnapshotVms = new List<CoinSnapshotViewModel> { CoinSnapshotViewModel.PleaseSelect };
             _coinSnapshotVms = new List<CoinSnapshotViewModel> { CoinSnapshotViewModel.PleaseSelect };
             _coinSnapshotVms.AddRange(AppRoot.CoinVms.AllCoins.Select(a => new CoinSnapshotViewModel(a, new CoinSnapshotDataViewModel(CoinSnapshotData.CreateEmpty(a.Code)))));
             _coinSnapshotVms.AddRange(AppRoot.CoinVms.AllCoins.Select(a => new CoinSnapshotViewModel(a, new CoinSnapshotDataViewModel(CoinSnapshotData.CreateEmpty(a.Code)))));
-            this._mineStatusEnumItem = NTMinerContext.MineStatusEnumItems.FirstOrDefault(a => a.Value == MineStatus.All);
+            this._mineStatusEnumItem = Enums.MineStatusEnumItems.FirstOrDefault(a => a.Value == MineStatus.All);
             this._pool = string.Empty;
             this._pool = string.Empty;
             this._wallet = string.Empty;
             this._wallet = string.Empty;
             this.OneKeySetting = new DelegateCommand(() => {
             this.OneKeySetting = new DelegateCommand(() => {
@@ -1665,7 +1666,7 @@ namespace NTMiner.MinerStudio.Vms {
 
 
         public EnumItem<GpuType> GpuTypeEnumItem {
         public EnumItem<GpuType> GpuTypeEnumItem {
             get {
             get {
-                return NTMinerContext.GpuTypeEnumItems.FirstOrDefault(a => a.Value == GpuType);
+                return Enums.GpuTypeEnumItems.FirstOrDefault(a => a.Value == GpuType);
             }
             }
             set {
             set {
                 if (GpuType != value.Value) {
                 if (GpuType != value.Value) {

+ 3 - 3
src/AppModels/MinerStudio/Vms/OverClockDataViewModel.cs

@@ -1,5 +1,5 @@
-using NTMiner.Core;
-using NTMiner.Core.MinerServer;
+using NTMiner.Core.MinerServer;
+using NTMiner.Gpus;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System;
 using System;
 using System.Linq;
 using System.Linq;
@@ -133,7 +133,7 @@ namespace NTMiner.MinerStudio.Vms {
 
 
         public EnumItem<GpuType> GpuTypeEnumItem {
         public EnumItem<GpuType> GpuTypeEnumItem {
             get {
             get {
-                return NTMinerContext.GpuTypeEnumItems.FirstOrDefault(a => a.Value == GpuType);
+                return Enums.GpuTypeEnumItems.FirstOrDefault(a => a.Value == GpuType);
             }
             }
             set {
             set {
                 if (GpuType != value.Value) {
                 if (GpuType != value.Value) {

+ 1 - 1
src/AppModels/MinerStudio/Vms/UserPageViewModel.cs

@@ -33,7 +33,7 @@ namespace NTMiner.MinerStudio.Vms {
             if (WpfUtil.IsInDesignMode) {
             if (WpfUtil.IsInDesignMode) {
                 return;
                 return;
             }
             }
-            this._userStatusEnumItem = NTMinerContext.UserStatusEnumItems.FirstOrDefault(a => a.Value == UserStatus.All);
+            this._userStatusEnumItem = Enums.UserStatusEnumItems.FirstOrDefault(a => a.Value == UserStatus.All);
             this.PageUp = new DelegateCommand(() => {
             this.PageUp = new DelegateCommand(() => {
                 this.PageIndex -= 1;
                 this.PageIndex -= 1;
             });
             });

+ 2 - 1
src/AppModels/Vms/CoinKernelViewModel.cs

@@ -1,5 +1,6 @@
 using NTMiner.Core;
 using NTMiner.Core;
 using NTMiner.Core.Kernels;
 using NTMiner.Core.Kernels;
+using NTMiner.Gpus;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.Linq;
 using System.Linq;
@@ -442,7 +443,7 @@ namespace NTMiner.Vms {
 
 
         public EnumItem<SupportedGpu> SupportedGpuEnumItem {
         public EnumItem<SupportedGpu> SupportedGpuEnumItem {
             get {
             get {
-                return NTMinerContext.SupportedGpuEnumItems.FirstOrDefault(a => a.Value == SupportedGpu);
+                return Enums.SupportedGpuEnumItems.FirstOrDefault(a => a.Value == SupportedGpu);
             }
             }
             set {
             set {
                 if (SupportedGpu != value.Value) {
                 if (SupportedGpu != value.Value) {

+ 4 - 0
src/AppModels/Vms/CoinProfileViewModel.cs

@@ -31,11 +31,15 @@ namespace NTMiner.Vms {
                 string wallet = this.Wallet ?? "无";
                 string wallet = this.Wallet ?? "无";
                 Clipboard.SetDataObject(wallet, true);
                 Clipboard.SetDataObject(wallet, true);
                 VirtualRoot.Out.ShowSuccess(wallet, header: "复制成功");
                 VirtualRoot.Out.ShowSuccess(wallet, header: "复制成功");
+            }, ()=> {
+                return this.SelectedWallet != null && !string.IsNullOrEmpty(this.SelectedWallet.Address);
             });
             });
             this.CopyDualCoinWallet = new DelegateCommand(() => {
             this.CopyDualCoinWallet = new DelegateCommand(() => {
                 string wallet = this.DualCoinWallet ?? "无";
                 string wallet = this.DualCoinWallet ?? "无";
                 Clipboard.SetDataObject(wallet, true);
                 Clipboard.SetDataObject(wallet, true);
                 VirtualRoot.Out.ShowSuccess(wallet, header: "复制成功");
                 VirtualRoot.Out.ShowSuccess(wallet, header: "复制成功");
+            }, ()=> {
+                return this.SelectedDualCoinWallet != null && !string.IsNullOrEmpty(this.SelectedDualCoinWallet.Address);
             });
             });
             this.HideWallet = new DelegateCommand(() => {
             this.HideWallet = new DelegateCommand(() => {
                 this.IsHideWallet = true;
                 this.IsHideWallet = true;

+ 1 - 0
src/AppModels/Vms/CoinViewModel.cs

@@ -1,4 +1,5 @@
 using NTMiner.Core;
 using NTMiner.Core;
+using NTMiner.Gpus;
 using NTMiner.MinerStudio;
 using NTMiner.MinerStudio;
 using NTMiner.MinerStudio.Vms;
 using NTMiner.MinerStudio.Vms;
 using System;
 using System;

+ 0 - 135
src/AppModels/Vms/GpuNameViewModel.cs

@@ -1,135 +0,0 @@
-using NTMiner.Core;
-using NTMiner.Core.Gpus;
-using NTMiner.MinerStudio;
-using System;
-using System.Linq;
-using System.Windows;
-using System.Windows.Input;
-
-namespace NTMiner.Vms {
-    public class GpuNameViewModel : ViewModelBase, IGpuName {
-        public Guid Id { get; private set; } = Guid.NewGuid();
-
-        private GpuType _gpuType;
-        private string _name;
-        private ulong _totalMemory;
-
-        public ICommand Save { get; private set; }
-
-        [Obsolete(NTKeyword.WpfDesignOnly)]
-        public GpuNameViewModel() {
-            if (!WpfUtil.IsInDesignMode) {
-                throw new InvalidProgramException();
-            }
-        }
-
-        public GpuNameViewModel(IGpuName data) {
-            _gpuType = data.GpuType;
-            _name = data.Name;
-            _totalMemory = data.TotalMemory;
-            this.Save = new DelegateCommand(() => {
-                if (this.GpuType == GpuType.Empty) {
-                    VirtualRoot.Out.ShowError("未指定显卡类型");
-                    return;
-                }
-                if (string.IsNullOrEmpty(this.Name)) {
-                    VirtualRoot.Out.ShowError("名称是必须的");
-                    return;
-                }
-                if (this.TotalMemoryGb <= 0) {
-                    VirtualRoot.Out.ShowError("显存不正确");
-                    return;
-                }
-                RpcRoot.OfficialServer.GpuNameService.SetGpuNameAsync(new GpuName {
-                    GpuType = this.GpuType,
-                    Name = this.Name,
-                    TotalMemory = this.TotalMemory
-                }, (response, e) => {
-                    if (response.IsSuccess()) {
-                        VirtualRoot.RaiseEvent(new GpuNameAddedEvent());
-                        VirtualRoot.Execute(new CloseWindowCommand(this.Id));
-                    }
-                    else {
-                        VirtualRoot.Out.ShowError(response.ReadMessage(e), autoHideSeconds: 4);
-                    }
-                });
-            });
-        }
-
-        public GpuType GpuType {
-            get => _gpuType;
-            set {
-                if (_gpuType != value) {
-                    _gpuType = value;
-                    OnPropertyChanged(nameof(GpuType));
-                    OnPropertyChanged(nameof(IsNvidiaIconVisible));
-                    OnPropertyChanged(nameof(IsAmdIconVisible));
-                }
-            }
-        }
-
-        public string Name {
-            get => _name;
-            set {
-                if (_name != value) {
-                    _name = value;
-                    OnPropertyChanged(nameof(Name));
-                }
-            }
-        }
-
-        public ulong TotalMemory {
-            get => _totalMemory;
-            set {
-                if (_totalMemory != value) {
-                    _totalMemory = value;
-                    OnPropertyChanged(nameof(TotalMemory));
-                }
-            }
-        }
-
-        public int TotalMemoryGb {
-            get {
-                return GpuName.ConvertToGb(this.TotalMemory);
-            }
-            set {
-                this.TotalMemory = NTKeyword.ULongG * (ulong)value;
-                OnPropertyChanged(nameof(TotalMemoryGb));
-            }
-        }
-
-        public Visibility IsNvidiaIconVisible {
-            get {
-                if (GpuType == GpuType.NVIDIA) {
-                    return Visibility.Visible;
-                }
-                return Visibility.Collapsed;
-            }
-        }
-
-        public Visibility IsAmdIconVisible {
-            get {
-                if (GpuType == GpuType.AMD) {
-                    return Visibility.Visible;
-                }
-                return Visibility.Collapsed;
-            }
-        }
-
-        public EnumItem<GpuType> GpuTypeEnumItem {
-            get {
-                return NTMinerContext.GpuTypeEnumItems.FirstOrDefault(a => a.Value == GpuType);
-            }
-            set {
-                if (GpuType != value.Value) {
-                    GpuType = value.Value;
-                    OnPropertyChanged(nameof(GpuTypeEnumItem));
-                }
-            }
-        }
-
-        public bool IsValid() {
-            return GpuName.IsValid(this.GpuType, this.Name, this.TotalMemory);
-        }
-    }
-}

+ 1 - 1
src/AppModels/Vms/GpuSpeedViewModel.cs

@@ -1,5 +1,5 @@
 using NTMiner.Core;
 using NTMiner.Core;
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using System;
 using System;
 using System.Linq;
 using System.Linq;
 using System.Windows.Input;
 using System.Windows.Input;

+ 1 - 1
src/AppModels/Vms/GpuStatusBarViewModel.cs

@@ -1,4 +1,4 @@
-using NTMiner.Core;
+using NTMiner.Gpus;
 using System.Linq;
 using System.Linq;
 using System.Windows.Media;
 using System.Windows.Media;
 
 

+ 1 - 3
src/AppModels/Vms/GpuViewModel.cs

@@ -1,6 +1,4 @@
-using NTMiner.Core;
-using NTMiner.Core.Gpus;
-using NTMiner.Core.MinerClient;
+using NTMiner.Gpus;
 using System;
 using System;
 using System.Linq;
 using System.Linq;
 using System.Windows.Media;
 using System.Windows.Media;

+ 1 - 1
src/AppModels/Vms/InputSegmentEditViewModel.cs

@@ -118,7 +118,7 @@ namespace NTMiner.Vms {
 
 
         public EnumItem<SupportedGpu> TargetGpuEnumItem {
         public EnumItem<SupportedGpu> TargetGpuEnumItem {
             get {
             get {
-                return NTMinerContext.SupportedGpuEnumItems.FirstOrDefault(a => a.Value == TargetGpu);
+                return Enums.SupportedGpuEnumItems.FirstOrDefault(a => a.Value == TargetGpu);
             }
             }
             set {
             set {
                 if (TargetGpu != value.Value) {
                 if (TargetGpu != value.Value) {

+ 2 - 2
src/AppModels/Vms/KernelViewModel.cs

@@ -378,7 +378,7 @@ namespace NTMiner.Vms {
 
 
         public string SupportedCoins {
         public string SupportedCoins {
             get {
             get {
-                StringBuilder sb = new StringBuilder();
+                StringBuilder sb = new StringBuilder("可挖:");
                 int len = sb.Length;
                 int len = sb.Length;
                 foreach (var coinVm in SupportedCoinVms.OrderBy(a => a.Code)) {
                 foreach (var coinVm in SupportedCoinVms.OrderBy(a => a.Code)) {
                     if (len != sb.Length) {
                     if (len != sb.Length) {
@@ -441,7 +441,7 @@ namespace NTMiner.Vms {
 
 
         public EnumItem<PublishStatus> PublishStateEnumItem {
         public EnumItem<PublishStatus> PublishStateEnumItem {
             get {
             get {
-                return NTMinerContext.PublishStatusEnumItems.FirstOrDefault(a => a.Value == PublishState);
+                return Enums.PublishStatusEnumItems.FirstOrDefault(a => a.Value == PublishState);
             }
             }
             set {
             set {
                 if (PublishState != value.Value) {
                 if (PublishState != value.Value) {

+ 2 - 1
src/AppModels/Vms/KernelsWindowViewModel.cs

@@ -169,7 +169,8 @@ namespace NTMiner.Vms {
                     query = query.
                     query = query.
                         Where(a => (!string.IsNullOrEmpty(a.Code) && a.Code.IgnoreCaseContains(Keyword))
                         Where(a => (!string.IsNullOrEmpty(a.Code) && a.Code.IgnoreCaseContains(Keyword))
                             || (!string.IsNullOrEmpty(a.Version) && a.Version.IgnoreCaseContains(Keyword))
                             || (!string.IsNullOrEmpty(a.Version) && a.Version.IgnoreCaseContains(Keyword))
-                            || (!string.IsNullOrEmpty(a.Notice) && a.Notice.IgnoreCaseContains(Keyword)));
+                            || (!string.IsNullOrEmpty(a.Notice) && a.Notice.IgnoreCaseContains(Keyword))
+                            || (!string.IsNullOrEmpty(a.Package) && a.Package.IgnoreCaseContains(Keyword)));
                 }
                 }
                 if (SelectedCoinVm != null && SelectedCoinVm != CoinViewModel.PleaseSelect) {
                 if (SelectedCoinVm != null && SelectedCoinVm != CoinViewModel.PleaseSelect) {
                     query = query.Where(a => a.SupportedCoinVms.Contains(SelectedCoinVm));
                     query = query.Where(a => a.SupportedCoinVms.Contains(SelectedCoinVm));

+ 2 - 2
src/AppModels/Vms/LocalMessagesViewModel.cs

@@ -28,7 +28,7 @@
             get {
             get {
                 // 只有挖矿端有This和Kernel两个频道
                 // 只有挖矿端有This和Kernel两个频道
                 if (ClientAppType.IsMinerClient) {
                 if (ClientAppType.IsMinerClient) {
-                    foreach (var item in NTMinerContext.LocalMessageChannelEnumItems) {
+                    foreach (var item in Enums.LocalMessageChannelEnumItems) {
                         yield return item;
                         yield return item;
                     }
                     }
                 }
                 }
@@ -54,7 +54,7 @@
             }
             }
             foreach (var messageChannel in LocalMessageChannelEnumItems) {
             foreach (var messageChannel in LocalMessageChannelEnumItems) {
                 var values = new Dictionary<LocalMessageType, MessageTypeItem<LocalMessageType>>();
                 var values = new Dictionary<LocalMessageType, MessageTypeItem<LocalMessageType>>();
-                foreach (var messageType in NTMinerContext.LocalMessageTypeEnumItems) {
+                foreach (var messageType in Enums.LocalMessageTypeEnumItems) {
                     values.Add(messageType.Value, new MessageTypeItem<LocalMessageType>(messageType, LocalMessageViewModel.GetIcon, LocalMessageViewModel.GetIconFill, RefreshQueryResults));
                     values.Add(messageType.Value, new MessageTypeItem<LocalMessageType>(messageType, LocalMessageViewModel.GetIcon, LocalMessageViewModel.GetIconFill, RefreshQueryResults));
                 }
                 }
                 _count.Add(messageChannel, values);
                 _count.Add(messageChannel, values);

+ 12 - 14
src/AppModels/Vms/MinerProfileViewModel.cs

@@ -48,6 +48,10 @@ namespace NTMiner.Vms {
                 IsConnecting = true;
                 IsConnecting = true;
             });
             });
             if (ClientAppType.IsMinerClient) {
             if (ClientAppType.IsMinerClient) {
+                VirtualRoot.AddCmdPath<SetAutoStartCommand>(message => {
+                    this.IsAutoStart = message.IsAutoStart;
+                    this.IsAutoBoot = message.IsAutoBoot;
+                }, this.GetType(), LogEnum.None);
                 VirtualRoot.AddEventPath<StartingMineFailedEvent>("开始挖矿失败", LogEnum.DevConsole,
                 VirtualRoot.AddEventPath<StartingMineFailedEvent>("开始挖矿失败", LogEnum.DevConsole,
                     action: message => {
                     action: message => {
                         IsMining = false;
                         IsMining = false;
@@ -121,11 +125,8 @@ namespace NTMiner.Vms {
             });
             });
             AppRoot.AddCmdPath<RefreshAutoBootStartCommand>("刷新开机启动和自动挖矿的展示", LogEnum.DevConsole,
             AppRoot.AddCmdPath<RefreshAutoBootStartCommand>("刷新开机启动和自动挖矿的展示", LogEnum.DevConsole,
                 action: message => {
                 action: message => {
-                    MinerProfileData data = NTMinerContext.Instance.ServerContext.CreateLocalRepository<MinerProfileData>().GetByKey(this.Id);
-                    if (data != null) {
-                        this.IsAutoBoot = data.IsAutoBoot;
-                        this.IsAutoStart = data.IsAutoStart;
-                    }
+                    this.OnPropertyChanged(nameof(IsAutoBoot));
+                    this.OnPropertyChanged(nameof(IsAutoStart));
                 }, location: this.GetType());
                 }, location: this.GetType());
             AppRoot.AddEventPath<MinerProfilePropertyChangedEvent>("MinerProfile设置变更后刷新VM内存", LogEnum.DevConsole,
             AppRoot.AddEventPath<MinerProfilePropertyChangedEvent>("MinerProfile设置变更后刷新VM内存", LogEnum.DevConsole,
                 action: message => {
                 action: message => {
@@ -148,9 +149,6 @@ namespace NTMiner.Vms {
             VirtualRoot.AddEventPath<CoinVmRemovedEvent>("Vm集删除了新币种后刷新MinerProfileVm内存", LogEnum.DevConsole, action: message => {
             VirtualRoot.AddEventPath<CoinVmRemovedEvent>("Vm集删除了新币种后刷新MinerProfileVm内存", LogEnum.DevConsole, action: message => {
                 OnPropertyChanged(nameof(CoinVm));
                 OnPropertyChanged(nameof(CoinVm));
             }, this.GetType());
             }, this.GetType());
-            if ((IsAutoStart || CommandLineArgs.IsAutoStart) && IsNoUi) {
-                NTMinerConsole.Disable();
-            }
         }
         }
 
 
         public void RefreshWsDaemonState() {
         public void RefreshWsDaemonState() {
@@ -416,10 +414,10 @@ namespace NTMiner.Vms {
         }
         }
 
 
         public bool IsNoUi {
         public bool IsNoUi {
-            get { return NTMinerContext.Instance.MinerProfile.IsNoUi; }
+            get { return NTMinerRegistry.GetIsNoUi(); }
             set {
             set {
-                if (NTMinerContext.Instance.MinerProfile.IsNoUi != value) {
-                    NTMinerContext.Instance.MinerProfile.SetMinerProfileProperty(nameof(IsNoUi), value);
+                if (NTMinerRegistry.GetIsNoUi() != value) {
+                    NTMinerRegistry.SetIsNoUi(value);
                     OnPropertyChanged(nameof(IsNoUi));
                     OnPropertyChanged(nameof(IsNoUi));
                 }
                 }
             }
             }
@@ -498,10 +496,10 @@ namespace NTMiner.Vms {
         }
         }
 
 
         public bool IsAutoStart {
         public bool IsAutoStart {
-            get => NTMinerContext.Instance.MinerProfile.IsAutoStart;
+            get => NTMinerRegistry.GetIsAutoStart();
             set {
             set {
-                if (NTMinerContext.Instance.MinerProfile.IsAutoStart != value) {
-                    NTMinerContext.Instance.MinerProfile.SetMinerProfileProperty(nameof(IsAutoStart), value);
+                if (NTMinerRegistry.GetIsAutoStart() != value) {
+                    NTMinerRegistry.SetIsAutoStart(value);
                     OnPropertyChanged(nameof(IsAutoStart));
                     OnPropertyChanged(nameof(IsAutoStart));
                 }
                 }
             }
             }

+ 1 - 1
src/AppModels/Vms/OuterPropertyViewModel.cs

@@ -1,4 +1,4 @@
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Windows;
 using NTMiner.Windows;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.Linq;
 using System.Linq;

+ 2 - 0
src/AppModels/Vms/PoolViewModel.cs

@@ -134,6 +134,7 @@ namespace NTMiner.Vms {
                 if ((!this.IsUserMode && (wallet == null || string.IsNullOrEmpty(wallet.Address))) ||
                 if ((!this.IsUserMode && (wallet == null || string.IsNullOrEmpty(wallet.Address))) ||
                     (this.IsUserMode && string.IsNullOrEmpty(this.PoolProfileVm.UserName))) {
                     (this.IsUserMode && string.IsNullOrEmpty(this.PoolProfileVm.UserName))) {
                     if (!string.IsNullOrEmpty(Website)) {
                     if (!string.IsNullOrEmpty(Website)) {
+                        VirtualRoot.Execute(new UnTopmostCommand());
                         Process.Start(Website);
                         Process.Start(Website);
                     }
                     }
                     return;
                     return;
@@ -147,6 +148,7 @@ namespace NTMiner.Vms {
                         url = url.Replace("{wallet}", wallet.Address);
                         url = url.Replace("{wallet}", wallet.Address);
                     }
                     }
                     url = url.Replace("{worker}", NTMinerContext.Instance.MinerProfile.MinerName);
                     url = url.Replace("{worker}", NTMinerContext.Instance.MinerProfile.MinerName);
+                    VirtualRoot.Execute(new UnTopmostCommand());
                     Process.Start(url);
                     Process.Start(url);
                 }
                 }
             });
             });

+ 0 - 1
src/AppModels/Vms/ServerMessageViewModel.cs

@@ -1,5 +1,4 @@
 using NTMiner.Core.MinerServer;
 using NTMiner.Core.MinerServer;
-using NTMiner.Views;
 using System;
 using System;
 using System.Windows.Input;
 using System.Windows.Input;
 using System.Windows.Media;
 using System.Windows.Media;

+ 1 - 1
src/AppModels/Vms/ServerMessagesViewModel.cs

@@ -21,7 +21,7 @@ namespace NTMiner.Vms {
             if (WpfUtil.IsInDesignMode) {
             if (WpfUtil.IsInDesignMode) {
                 return;
                 return;
             }
             }
-            foreach (var messageType in NTMinerContext.ServerMessageTypeEnumItems) {
+            foreach (var messageType in Enums.ServerMessageTypeEnumItems) {
                 _count.Add(messageType.Value, new MessageTypeItem<ServerMessageType>(messageType, ServerMessageViewModel.GetIcon, ServerMessageViewModel.GetIconFill, RefreshQueryResults));
                 _count.Add(messageType.Value, new MessageTypeItem<ServerMessageType>(messageType, ServerMessageViewModel.GetIcon, ServerMessageViewModel.GetIconFill, RefreshQueryResults));
             }
             }
             Init();
             Init();

+ 1 - 1
src/AppModels/Vms/SpeedTableViewModel.cs

@@ -1,4 +1,4 @@
-using NTMiner.Core;
+using NTMiner.Gpus;
 using System.Windows;
 using System.Windows;
 
 
 namespace NTMiner.Vms {
 namespace NTMiner.Vms {

+ 1 - 1
src/AppModels/Vms/StateBarViewModel.cs

@@ -134,7 +134,7 @@ namespace NTMiner.Vms {
 
 
         public void SetCheckUpdateForeground(bool isLatest) {
         public void SetCheckUpdateForeground(bool isLatest) {
             if (isLatest) {
             if (isLatest) {
-                CheckUpdateForeground = AppUtil.GetResource<SolidColorBrush>("LableColor");
+                CheckUpdateForeground = AppUtil.GetResource<SolidColorBrush>("BtnBackground");
             }
             }
             else {
             else {
                 CheckUpdateForeground = WpfUtil.RedBrush;
                 CheckUpdateForeground = WpfUtil.RedBrush;

+ 42 - 0
src/AppModels/Vms/WindowsAutoLogonViewModel.cs

@@ -0,0 +1,42 @@
+using System;
+using System.Windows.Input;
+
+namespace NTMiner.Vms {
+    public class WindowsAutoLogonViewModel : ViewModelBase {
+        public Guid Id { get; private set; } = Guid.NewGuid();
+        private string _userName;
+        private string _password;
+
+        public ICommand Ok { get; private set; }
+
+        public WindowsAutoLogonViewModel() {
+            this.Ok = new DelegateCommand(() => {
+                if (string.IsNullOrEmpty(this.UserName) || string.IsNullOrEmpty(this.Password)) {
+                    VirtualRoot.Out.ShowError("用户名或密码不能为空");
+                    return;
+                }
+                Windows.OS.Instance.SetAutoLogon(this.UserName, this.Password);
+                VirtualRoot.Execute(new CloseWindowCommand(this.Id));
+            });
+        }
+
+        public string UserName {
+            get => _userName;
+            set {
+                if (_userName != value) {
+                    _userName = value;
+                    OnPropertyChanged(nameof(UserName));
+                }
+            }
+        }
+        public string Password {
+            get => _password;
+            set {
+                if (_password != value) {
+                    _password = value;
+                    OnPropertyChanged(nameof(Password));
+                }
+            }
+        }
+    }
+}

+ 1 - 6
src/AppViews0/AppViewFactory.cs

@@ -290,12 +290,7 @@ namespace NTMiner {
             }, location: location);
             }, location: location);
             VirtualRoot.AddCmdPath<ShowGpuNamePageCommand>(action: message => {
             VirtualRoot.AddCmdPath<ShowGpuNamePageCommand>(action: message => {
                 UIThread.Execute(() => {
                 UIThread.Execute(() => {
-                    MinerStudioUcs.GpuNamePage.ShowWindow();
-                });
-            }, location: location);
-            VirtualRoot.AddCmdPath<AddGpuNameCommand>(action: message => {
-                UIThread.Execute(() => {
-                    MinerStudioUcs.GpuNameAdd.ShowWindow(message.GpuNameVm);
+                    MinerStudioUcs.GpuNameCounts.ShowWindow();
                 });
                 });
             }, location: location);
             }, location: location);
             VirtualRoot.AddCmdPath<ShowChangePassword>(action: message => {
             VirtualRoot.AddCmdPath<ShowChangePassword>(action: message => {

+ 11 - 33
src/AppViews0/AppViews0.csproj

@@ -96,18 +96,9 @@
     <Compile Include="MinerStudio\Views\Ucs\ColumnsShowEdit.xaml.cs">
     <Compile Include="MinerStudio\Views\Ucs\ColumnsShowEdit.xaml.cs">
       <DependentUpon>ColumnsShowEdit.xaml</DependentUpon>
       <DependentUpon>ColumnsShowEdit.xaml</DependentUpon>
     </Compile>
     </Compile>
-    <Compile Include="MinerStudio\Views\Ucs\GpuNamePage.xaml.cs">
-      <DependentUpon>GpuNamePage.xaml</DependentUpon>
-    </Compile>
-    <Compile Include="MinerStudio\Views\Ucs\GpuNames.xaml.cs">
-      <DependentUpon>GpuNames.xaml</DependentUpon>
-    </Compile>
     <Compile Include="MinerStudio\Views\Ucs\GpuNameCounts.xaml.cs">
     <Compile Include="MinerStudio\Views\Ucs\GpuNameCounts.xaml.cs">
       <DependentUpon>GpuNameCounts.xaml</DependentUpon>
       <DependentUpon>GpuNameCounts.xaml</DependentUpon>
     </Compile>
     </Compile>
-    <Compile Include="MinerStudio\Views\Ucs\GpuNameAdd.xaml.cs">
-      <DependentUpon>GpuNameAdd.xaml</DependentUpon>
-    </Compile>
     <Compile Include="SafeNativeMethods.cs" />
     <Compile Include="SafeNativeMethods.cs" />
     <Compile Include="Views\ConsoleWindow.xaml.cs">
     <Compile Include="Views\ConsoleWindow.xaml.cs">
       <DependentUpon>ConsoleWindow.xaml</DependentUpon>
       <DependentUpon>ConsoleWindow.xaml</DependentUpon>
@@ -157,6 +148,9 @@
     <Compile Include="MinerStudio\Views\Ucs\WsServerNodePage.xaml.cs">
     <Compile Include="MinerStudio\Views\Ucs\WsServerNodePage.xaml.cs">
       <DependentUpon>WsServerNodePage.xaml</DependentUpon>
       <DependentUpon>WsServerNodePage.xaml</DependentUpon>
     </Compile>
     </Compile>
+    <Compile Include="Views\Ucs\WindowsAutoLogon.xaml.cs">
+      <DependentUpon>WindowsAutoLogon.xaml</DependentUpon>
+    </Compile>
     <Compile Include="Views\Ucs\SignUpPage.xaml.cs">
     <Compile Include="Views\Ucs\SignUpPage.xaml.cs">
       <DependentUpon>SignUpPage.xaml</DependentUpon>
       <DependentUpon>SignUpPage.xaml</DependentUpon>
     </Compile>
     </Compile>
@@ -415,18 +409,6 @@
     <Compile Include="Views\Ucs\CoinPage.xaml.cs">
     <Compile Include="Views\Ucs\CoinPage.xaml.cs">
       <DependentUpon>CoinPage.xaml</DependentUpon>
       <DependentUpon>CoinPage.xaml</DependentUpon>
     </Compile>
     </Compile>
-    <Page Include="MinerStudio\Views\Design\GpuNamePageViewModel.xaml">
-      <Generator>MSBuild:Compile</Generator>
-      <SubType>Designer</SubType>
-    </Page>
-    <Page Include="MinerStudio\Views\Design\GpuNameViewModel.xaml">
-      <Generator>MSBuild:Compile</Generator>
-      <SubType>Designer</SubType>
-    </Page>
-    <Page Include="MinerStudio\Views\Design\GpuNamesViewModel.xaml">
-      <Generator>MSBuild:Compile</Generator>
-      <SubType>Designer</SubType>
-    </Page>
     <Page Include="MinerStudio\Views\Design\GpuNameCountsViewModel.xaml">
     <Page Include="MinerStudio\Views\Design\GpuNameCountsViewModel.xaml">
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
@@ -467,22 +449,10 @@
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
     </Page>
     </Page>
-    <Page Include="MinerStudio\Views\Ucs\GpuNamePage.xaml">
-      <Generator>MSBuild:Compile</Generator>
-      <SubType>Designer</SubType>
-    </Page>
-    <Page Include="MinerStudio\Views\Ucs\GpuNames.xaml">
-      <Generator>MSBuild:Compile</Generator>
-      <SubType>Designer</SubType>
-    </Page>
     <Page Include="MinerStudio\Views\Ucs\GpuNameCounts.xaml">
     <Page Include="MinerStudio\Views\Ucs\GpuNameCounts.xaml">
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
     </Page>
     </Page>
-    <Page Include="MinerStudio\Views\Ucs\GpuNameAdd.xaml">
-      <Generator>MSBuild:Compile</Generator>
-      <SubType>Designer</SubType>
-    </Page>
     <Page Include="Views\ConsoleWindow.xaml">
     <Page Include="Views\ConsoleWindow.xaml">
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
@@ -511,6 +481,10 @@
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
     </Page>
     </Page>
+    <Page Include="Views\Design\WindowsAutoLogonViewModel.xaml">
+      <Generator>MSBuild:Compile</Generator>
+      <SubType>Designer</SubType>
+    </Page>
     <Page Include="Views\Design\ToolboxViewModel.xaml">
     <Page Include="Views\Design\ToolboxViewModel.xaml">
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
@@ -779,6 +753,10 @@
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
     </Page>
     </Page>
+    <Page Include="Views\Ucs\WindowsAutoLogon.xaml">
+      <Generator>MSBuild:Compile</Generator>
+      <SubType>Designer</SubType>
+    </Page>
     <Page Include="Views\Ucs\SignUpPage.xaml">
     <Page Include="Views\Ucs\SignUpPage.xaml">
       <Generator>MSBuild:Compile</Generator>
       <Generator>MSBuild:Compile</Generator>
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>

+ 0 - 2
src/AppViews0/MinerStudio/Views/Design/GpuNamePageViewModel.xaml

@@ -1,2 +0,0 @@
-<vm:GpuNamePageViewModel xmlns:vm="clr-namespace:NTMiner.MinerStudio.Vms;assembly=AppModels">
-</vm:GpuNamePageViewModel>

+ 0 - 2
src/AppViews0/MinerStudio/Views/Design/GpuNameViewModel.xaml

@@ -1,2 +0,0 @@
-<vm:GpuNameViewModel xmlns:vm="clr-namespace:NTMiner.Vms;assembly=AppModels">
-</vm:GpuNameViewModel>

+ 0 - 2
src/AppViews0/MinerStudio/Views/Design/GpuNamesViewModel.xaml

@@ -1,2 +0,0 @@
-<vm:GpuNamesViewModel xmlns:vm="clr-namespace:NTMiner.MinerStudio.Vms;assembly=AppModels">
-</vm:GpuNamesViewModel>

+ 1 - 1
src/AppViews0/MinerStudio/Views/MinerClientsWindow.xaml.cs

@@ -154,7 +154,7 @@ namespace NTMiner.MinerStudio.Views {
                     }
                     }
                     #endregion
                     #endregion
                 }, location: this.GetType());
                 }, location: this.GetType());
-            NotiCenterWindow.Bind(this, ownerIsTopMost: true);
+            NotiCenterWindow.Bind(this, ownerIsTopmost: true);
             MinerStudioRoot.MinerClientsWindowVm.QueryMinerClients();
             MinerStudioRoot.MinerClientsWindowVm.QueryMinerClients();
         }
         }
 
 

+ 0 - 84
src/AppViews0/MinerStudio/Views/Ucs/GpuNameAdd.xaml

@@ -1,84 +0,0 @@
-<UserControl 
-    x:Class="NTMiner.MinerStudio.Views.Ucs.GpuNameAdd"
-	xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
-	xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
-	xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
-	xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
-	xmlns:sys="clr-namespace:System;assembly=mscorlib"
-	xmlns:vm="clr-namespace:NTMiner.MinerStudio.Vms;assembly=AppModels"
-	xmlns:controls="clr-namespace:NTMiner.Controls;assembly=NTMinerWpf"
-	mc:Ignorable="d"
-	d:DataContext="{d:DesignData Source=../Design/GpuNameViewModel.xaml}"
-	xmlns:app="clr-namespace:NTMiner;assembly=AppModels"
-	xmlns:local="clr-namespace:NTMiner.Views.Ucs" 
-    d:DesignWidth="320"
-    Background="White">
-	<UserControl.Resources>
-		<Style x:Key="LblTb" TargetType="TextBlock" BasedOn="{StaticResource LblTbBase}">
-			<Setter Property="Width" Value="70"></Setter>
-		</Style>
-	</UserControl.Resources>
-	<StackPanel Margin="10">
-        <WrapPanel Margin="0 2">
-            <TextBlock Style="{StaticResource LblTb}">显卡类型</TextBlock>
-            <controls:KbComboBox 
-				Width="100" ItemsSource="{x:Static app:AppStatic.GpuTypeEnumItems}"
-				DisplayMemberPath="Description"
-				SelectedItem="{Binding GpuTypeEnumItem}">
-            </controls:KbComboBox>
-            <Path
-				Margin="4 0 0 0"
-				Width="18"
-				Height="14"
-				ToolTip="NVIDIA"
-				Visibility="{Binding IsNvidiaIconVisible}"
-				Data="{StaticResource Icon_Nvidia}"
-				Fill="Green"
-				Stretch="Fill" />
-            <Path
-				Margin="4 0 0 0"
-				Width="16"
-				Height="14"
-				ToolTip="AMD"
-				Visibility="{Binding IsAmdIconVisible}"
-				Data="{StaticResource Icon_AMD}"
-				Fill="Red"
-				Stretch="Fill" />
-        </WrapPanel>
-        
-		<WrapPanel Margin="0 2">
-			<TextBlock Style="{StaticResource LblTb}">名称:</TextBlock>
-			<TextBox x:Name="TbName" Width="210" VerticalContentAlignment="Center" Text="{Binding Name, ValidatesOnExceptions=True}">
-			</TextBox>
-		</WrapPanel>
-
-        <WrapPanel Margin="0 2">
-            <TextBlock Style="{StaticResource LblTb}">显存:</TextBlock>
-            <TextBox Width="210" VerticalContentAlignment="Center" Text="{Binding TotalMemoryGb, ValidatesOnExceptions=True}">
-            </TextBox>
-            <TextBlock Padding="2 0" VerticalAlignment="Center" Text="G"></TextBlock>
-        </WrapPanel>
-        
-        <controls:KbButton
-			Command="{Binding Save}" 
-			Margin="0 10 0 0"
-			Padding="15 2"
-			HorizontalAlignment="Center"
-			Background="{StaticResource BtnBackground}"
-			Foreground="{StaticResource BtnForeground}"
-			CornerRadius="2">
-			<WrapPanel>
-				<Path
-					Width="12"
-					Height="12"
-					Data="{StaticResource Icon_Ok}"
-					Fill="{StaticResource BtnForeground}"
-					Stretch="Fill" />
-				<TextBlock
-					Padding="4"
-					VerticalAlignment="Center"
-					Text="确定" />
-			</WrapPanel>
-		</controls:KbButton>
-	</StackPanel>
-</UserControl>

+ 0 - 37
src/AppViews0/MinerStudio/Views/Ucs/GpuNameAdd.xaml.cs

@@ -1,37 +0,0 @@
-using NTMiner.Views;
-using NTMiner.Vms;
-using System.Windows.Controls;
-
-namespace NTMiner.MinerStudio.Views.Ucs {
-    public partial class GpuNameAdd : UserControl {
-        public static void ShowWindow(GpuNameViewModel source) {
-            ContainerWindow.ShowWindow(new ContainerWindowViewModel {
-                Title = "添加显卡特征名",
-                FormType = FormType.Add,
-                IsMaskTheParent = true,
-                Width = 320,
-                FooterVisible = System.Windows.Visibility.Collapsed,
-                CloseVisible = System.Windows.Visibility.Visible,
-                IconName = "Icon_Gpu"
-            }, ucFactory: (window) => {
-                GpuNameViewModel vm = new GpuNameViewModel(source);
-                window.AddCloseWindowOnecePath(vm.Id);
-                return new GpuNameAdd(vm);
-            }, beforeShow: (window, uc) => {
-                uc.DoFocus();
-            }, fixedSize: true);
-        }
-
-        public GpuNameViewModel Vm { get; private set; }
-
-        public GpuNameAdd(GpuNameViewModel vm) {
-            this.Vm = vm;
-            this.DataContext = vm;
-            InitializeComponent();
-        }
-
-        private void DoFocus() {
-            TbName.Focus();
-        }
-    }
-}

+ 0 - 7
src/AppViews0/MinerStudio/Views/Ucs/GpuNameCounts.xaml

@@ -88,13 +88,6 @@
                         </DataTemplate>
                         </DataTemplate>
                     </DataGridTemplateColumn.CellTemplate>
                     </DataGridTemplateColumn.CellTemplate>
                 </DataGridTemplateColumn>
                 </DataGridTemplateColumn>
-                <DataGridTemplateColumn Width="100" IsReadOnly="True" Header="匹配">
-                    <DataGridTemplateColumn.CellTemplate>
-                        <DataTemplate>
-                            <TextBlock Text="{Binding MatchName.Name}"></TextBlock>
-                        </DataTemplate>
-                    </DataGridTemplateColumn.CellTemplate>
-                </DataGridTemplateColumn>
                 <DataGridTemplateColumn Width="100" IsReadOnly="True" Header="显存">
                 <DataGridTemplateColumn Width="100" IsReadOnly="True" Header="显存">
                     <DataGridTemplateColumn.CellTemplate>
                     <DataGridTemplateColumn.CellTemplate>
                         <DataTemplate>
                         <DataTemplate>

+ 19 - 0
src/AppViews0/MinerStudio/Views/Ucs/GpuNameCounts.xaml.cs

@@ -1,14 +1,33 @@
 using NTMiner.MinerStudio.Vms;
 using NTMiner.MinerStudio.Vms;
+using NTMiner.Views;
+using NTMiner.Vms;
 using System.Windows;
 using System.Windows;
 using System.Windows.Controls;
 using System.Windows.Controls;
 using System.Windows.Input;
 using System.Windows.Input;
 
 
 namespace NTMiner.MinerStudio.Views.Ucs {
 namespace NTMiner.MinerStudio.Views.Ucs {
     public partial class GpuNameCounts : UserControl {
     public partial class GpuNameCounts : UserControl {
+        public static void ShowWindow() {
+            ContainerWindow.ShowWindow(new ContainerWindowViewModel {
+                Title = "Gpu名",
+                IconName = "Icon_Gpu",
+                Width = 800,
+                Height = 700,
+                IsMaskTheParent = false,
+                IsChildWindow = true,
+                CloseVisible = Visibility.Visible,
+                FooterVisible = Visibility.Collapsed
+            }, ucFactory: (window) => new GpuNameCounts());
+        }
+
+        public GpuNameCountsViewModel Vm { get; private set; }
+
         public GpuNameCounts() {
         public GpuNameCounts() {
             if (WpfUtil.IsInDesignMode) {
             if (WpfUtil.IsInDesignMode) {
                 return;
                 return;
             }
             }
+            this.Vm = new GpuNameCountsViewModel();
+            this.DataContext = this.Vm;
             InitializeComponent();
             InitializeComponent();
         }
         }
 
 

+ 0 - 32
src/AppViews0/MinerStudio/Views/Ucs/GpuNamePage.xaml

@@ -1,32 +0,0 @@
-<UserControl 
-    x:Class="NTMiner.MinerStudio.Views.Ucs.GpuNamePage"
-	xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
-	xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
-	xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
-	xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
-	xmlns:sys="clr-namespace:System;assembly=mscorlib"
-	xmlns:controls="clr-namespace:NTMiner.Controls;assembly=NTMinerWpf"
-	xmlns:local="clr-namespace:NTMiner.Views.Ucs"
-	xmlns:app="clr-namespace:NTMiner;assembly=AppModels"
-	xmlns:vm="clr-namespace:NTMiner.MinerStudio.Vms;assembly=AppModels"
-	xmlns:uc="clr-namespace:NTMiner.MinerStudio.Views.Ucs"
-    Background="White"
-	mc:Ignorable="d" 
-    d:DesignHeight="700" 
-    d:DesignWidth="1400"
-    d:DataContext="{d:DesignData Source=../Design/GpuNamePageViewModel.xaml}">
-    <Grid Background="{StaticResource ToolbarBackground}">
-        <Grid.ColumnDefinitions>
-            <ColumnDefinition Width="3*"></ColumnDefinition>
-            <ColumnDefinition Width="7*"></ColumnDefinition>
-        </Grid.ColumnDefinitions>
-        <Grid.RowDefinitions>
-            <RowDefinition Height="Auto"></RowDefinition>
-            <RowDefinition Height="*"></RowDefinition>
-        </Grid.RowDefinitions>
-        <TextBlock Padding="4" Text="显卡特征名"></TextBlock>
-        <TextBlock Padding="4" Grid.Column="1" Text="显卡名统计"></TextBlock>
-        <uc:GpuNames Grid.Row="1" DataContext="{Binding GpuNamesVm}"></uc:GpuNames>
-        <uc:GpuNameCounts Grid.Row="1" Grid.Column="1" DataContext="{Binding GpuNameCountsVm}"></uc:GpuNameCounts>
-    </Grid>
-</UserControl>

+ 0 - 33
src/AppViews0/MinerStudio/Views/Ucs/GpuNamePage.xaml.cs

@@ -1,33 +0,0 @@
-using NTMiner.MinerStudio.Vms;
-using NTMiner.Views;
-using NTMiner.Vms;
-using System.Windows;
-using System.Windows.Controls;
-
-namespace NTMiner.MinerStudio.Views.Ucs {
-    public partial class GpuNamePage : UserControl {
-        public static void ShowWindow() {
-            ContainerWindow.ShowWindow(new ContainerWindowViewModel {
-                Title = "Gpu名",
-                IconName = "Icon_Gpu",
-                Width = 1400,
-                Height = 700,
-                IsMaskTheParent = false,
-                IsChildWindow = true,
-                CloseVisible = Visibility.Visible,
-                FooterVisible = Visibility.Collapsed
-            }, ucFactory: (window) => new GpuNamePage());
-        }
-
-        public GpuNamePageViewModel Vm { get; private set; }
-
-        public GpuNamePage() {
-            if (WpfUtil.IsInDesignMode) {
-                return;
-            }
-            this.Vm = new GpuNamePageViewModel();
-            this.DataContext = this.Vm;
-            InitializeComponent();
-        }
-    }
-}

+ 0 - 156
src/AppViews0/MinerStudio/Views/Ucs/GpuNames.xaml

@@ -1,156 +0,0 @@
-<UserControl 
-    x:Class="NTMiner.MinerStudio.Views.Ucs.GpuNames"
-	xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
-	xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
-	xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
-	xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
-	xmlns:sys="clr-namespace:System;assembly=mscorlib"
-	xmlns:controls="clr-namespace:NTMiner.Controls;assembly=NTMinerWpf"
-	xmlns:local="clr-namespace:NTMiner.Views.Ucs"
-	xmlns:app="clr-namespace:NTMiner;assembly=AppModels"
-	xmlns:vm="clr-namespace:NTMiner.MinerStudio.Vms;assembly=AppModels"
-    Background="White"
-	mc:Ignorable="d" 
-    d:DesignHeight="700" 
-    d:DesignWidth="400"
-    d:DataContext="{d:DesignData Source=../Design/GpuNamesViewModel.xaml}">
-    <Grid Background="{StaticResource ToolbarBackground}">
-        <Grid.RowDefinitions>
-            <RowDefinition Height="Auto"></RowDefinition>
-            <RowDefinition Height="*"></RowDefinition>
-            <RowDefinition Height="Auto"></RowDefinition>
-        </Grid.RowDefinitions>
-        <WrapPanel>
-            <Path 
-                Margin="4 0 0 0"
-				Width="12"
-				Height="12"
-				Fill="{StaticResource BtnBackground}"
-				Stretch="Fill"
-				Data="{StaticResource Icon_Search}"></Path>
-            <TextBlock Padding="2 6">搜索</TextBlock>
-            <controls:KbTextBox 
-				x:Name="TbKeyword" Width="154" Height="24"
-				Text="{Binding Keyword, UpdateSourceTrigger=LostFocus}" 
-				LostFocus="TbKeyword_LostFocus"
-				VerticalContentAlignment="Center"
-				Hint="输入显卡名关键字然后回车"
-                ToolTip="输入显卡名关键字然后回车"
-				BorderBrush="{StaticResource LightLineColor}"
-				BorderThickness="1"
-				Background="White"
-                KeyUp="TbKeyword_KeyUp"
-				SelectedColor="#409EFF" />
-            <controls:KbButton 
-				Height="20"
-				Background="Transparent" BorderThickness="0"
-				Command="{Binding ClearKeyword}"
-				Visibility="{Binding ElementName=TbKeyword,Path=Text, Converter={StaticResource NotNullOrEmptyVisibilityConverter}}"
-				Margin="-14 0 0 0" HorizontalAlignment="Left">
-                <Path
-					Width="8"
-					Height="8"
-					Data="{StaticResource Icon_Close}"
-					Fill="{StaticResource BtnBackground}"
-					Stretch="Fill" />
-            </controls:KbButton>
-        </WrapPanel>
-		<DataGrid 
-            Grid.Row="1"
-            Margin="0" 
-            ItemsSource="{Binding QueryResults}" 
-			BorderThickness="0">
-			<DataGrid.Resources>
-				<controls:BindingProxy x:Key="proxy" Data="{Binding}" />
-			</DataGrid.Resources>
-            <DataGrid.Columns>
-                <DataGridTemplateColumn Width="32" IsReadOnly="True">
-                    <DataGridTemplateColumn.Header>
-                        <controls:KbButton 
-							Command="{Binding Data.Add, Source={StaticResource proxy}}" 
-                            Background="Transparent" BorderThickness="0"
-							Margin="2 0"
-							CornerRadius="2">
-                            <WrapPanel>
-                                <Path
-									Width="18"
-									Height="18"
-									Data="{StaticResource Icon_Add}"
-									Fill="{StaticResource BtnBackground}"
-									Stretch="Fill" />
-                            </WrapPanel>
-                        </controls:KbButton>
-                    </DataGridTemplateColumn.Header>
-                    <DataGridTemplateColumn.CellTemplate>
-                        <DataTemplate>
-                            <controls:KbButton 
-								Command="{Binding Data.Remove, Source={StaticResource proxy}}" 
-                                CommandParameter="{Binding}"
-                                Background="Transparent" BorderThickness="0"
-								Margin="2 0"
-								CornerRadius="2">
-                                <WrapPanel>
-                                    <Path
-										Width="18"
-										Height="18"
-										Data="{StaticResource Icon_Delete}"
-										Fill="{StaticResource BtnBackground}"
-										Stretch="Fill" />
-                                </WrapPanel>
-                            </controls:KbButton>
-                        </DataTemplate>
-                    </DataGridTemplateColumn.CellTemplate>
-                </DataGridTemplateColumn>
-                <DataGridTemplateColumn Width="50" IsReadOnly="True" Header="卡型">
-                    <DataGridTemplateColumn.CellTemplate>
-                        <DataTemplate>
-                            <WrapPanel>
-                                <Path
-							        Width="20"
-							        Height="16"
-							        Data="{StaticResource Icon_AMD}"
-                                    Visibility="{Binding IsAmdIconVisible}"
-							        Fill="Red"
-							        Stretch="Fill">
-                                </Path>
-                                <Path
-							        Width="20"
-							        Height="16"
-                                    Visibility="{Binding IsNvidiaIconVisible}"
-							        Data="{StaticResource Icon_Nvidia}"
-							        Fill="Green"
-							        Stretch="Fill">
-                                </Path>
-                            </WrapPanel>
-                        </DataTemplate>
-                    </DataGridTemplateColumn.CellTemplate>
-                </DataGridTemplateColumn>
-                <DataGridTemplateColumn Width="*" IsReadOnly="True" Header="名称">
-                    <DataGridTemplateColumn.CellTemplate>
-                        <DataTemplate>
-                            <TextBox IsReadOnly="True" BorderThickness="0" Text="{Binding Name,Mode=OneTime}"></TextBox>
-                        </DataTemplate>
-                    </DataGridTemplateColumn.CellTemplate>
-                </DataGridTemplateColumn>
-				<DataGridTemplateColumn Width="100" IsReadOnly="True" Header="显存">
-					<DataGridTemplateColumn.CellTemplate>
-						<DataTemplate>
-                            <WrapPanel>
-                                <TextBlock Text="{Binding TotalMemoryGb}"></TextBlock>
-                                <TextBlock Text=" G"></TextBlock>
-                            </WrapPanel>
-						</DataTemplate>
-					</DataGridTemplateColumn.CellTemplate>
-                </DataGridTemplateColumn>
-            </DataGrid.Columns>
-		</DataGrid>
-        <TextBlock Grid.Row="1" Visibility="{Binding QueryResults,Converter={StaticResource NoRecordVisibilityConverter}}" Foreground="Red" HorizontalAlignment="Center" VerticalAlignment="Center">没有记录</TextBlock>
-        <Border Grid.Row="2" Height="35">
-            <WrapPanel VerticalAlignment="Center">
-                <TextBlock Margin="4 0 0 0" Foreground="{StaticResource LableColor}" Text="共"></TextBlock>
-                <TextBlock Padding="4 0" Text="{Binding GpuNames.Count}"></TextBlock>
-                <TextBlock Foreground="{StaticResource LableColor}" Text="条"></TextBlock>
-            </WrapPanel>
-        </Border>
-    </Grid>
-</UserControl>

+ 0 - 32
src/AppViews0/MinerStudio/Views/Ucs/GpuNames.xaml.cs

@@ -1,32 +0,0 @@
-using NTMiner.MinerStudio.Vms;
-using System.Windows;
-using System.Windows.Controls;
-using System.Windows.Input;
-
-namespace NTMiner.MinerStudio.Views.Ucs {
-    public partial class GpuNames : UserControl {
-        public GpuNames() {
-            if (WpfUtil.IsInDesignMode) {
-                return;
-            }
-            InitializeComponent();
-            this.OnLoaded(onLoad: window => {
-                window.AddEventPath<GpuNameAddedEvent>("添加了显卡特征名后刷新显卡特征名列表", LogEnum.DevConsole, action: message => {
-                    UIThread.Execute(() => {
-                        ((GpuNamesViewModel)this.DataContext).Query();
-                    });
-                }, typeof(GpuNames));
-            });
-        }
-
-        private void TbKeyword_LostFocus(object sender, RoutedEventArgs e) {
-            ((GpuNamesViewModel)this.DataContext).Search.Execute(null);
-        }
-
-        private void TbKeyword_KeyUp(object sender, KeyEventArgs e) {
-            if (e.Key == Key.Enter) {
-                ((GpuNamesViewModel)this.DataContext).Keyword = this.TbKeyword.Text;
-            }
-        }
-    }
-}

+ 0 - 1
src/AppViews0/Views/ConsoleWindow.xaml

@@ -15,7 +15,6 @@
     Title="Windows控制台窗口">
     Title="Windows控制台窗口">
     <!--窗口不能透明否则在远程桌面时无法显现-->
     <!--窗口不能透明否则在远程桌面时无法显现-->
     <Grid>
     <Grid>
-        <TextBlock Foreground="White" HorizontalAlignment="Center" FontSize="50" Text="Windows控制台窗口"></TextBlock>
         <controls:KbLinkButton
         <controls:KbLinkButton
             x:Name="LbtnWindowsZoomBug"
             x:Name="LbtnWindowsZoomBug"
             Visibility="Collapsed"
             Visibility="Collapsed"

+ 1 - 53
src/AppViews0/Views/ConsoleWindow.xaml.cs

@@ -19,19 +19,7 @@ namespace NTMiner.Views {
                 SafeNativeMethods.SetWindowLong(console, SafeNativeMethods.GWL_STYLE, SafeNativeMethods.WS_VISIBLE);
                 SafeNativeMethods.SetWindowLong(console, SafeNativeMethods.GWL_STYLE, SafeNativeMethods.WS_VISIBLE);
                 SafeNativeMethods.SetParent(console, _thisWindowHandle);
                 SafeNativeMethods.SetParent(console, _thisWindowHandle);
                 hwndSource = PresentationSource.FromVisual((Visual)sender) as HwndSource;
                 hwndSource = PresentationSource.FromVisual((Visual)sender) as HwndSource;
-                hwndSource.AddHook(new HwndSourceHook(WndProc));
-                if (AppUtil.IsHotKeyEnabled) {
-                    HotKeyUtil.RegHotKey = (key) => {
-                        if (!RegHotKey(key, out string message)) {
-                            VirtualRoot.Out.ShowError(message, autoHideSeconds: 4);
-                            return false;
-                        }
-                        else {
-                            VirtualRoot.Out.ShowSuccess($"热键Ctrl + Alt + {key.ToString()} 设置成功");
-                            return true;
-                        }
-                    };
-                }
+                hwndSource.AddHook(new HwndSourceHook(Win32Proc.WindowProc));
             };
             };
             // 延迟展示从而避免不需要展示红字的时候看到红字
             // 延迟展示从而避免不需要展示红字的时候看到红字
             VirtualRoot.AddOnecePath<HasBoot1SecondEvent>("启动一会后显式指引解决WindowsZoomBug的一行红字", LogEnum.None, action: message => {
             VirtualRoot.AddOnecePath<HasBoot1SecondEvent>("启动一会后显式指引解决WindowsZoomBug的一行红字", LogEnum.None, action: message => {
@@ -40,49 +28,9 @@ namespace NTMiner.Views {
         }
         }
 
 
         protected override void OnClosed(EventArgs e) {
         protected override void OnClosed(EventArgs e) {
-            if (AppUtil.IsHotKeyEnabled) {
-                SystemHotKey.UnRegHotKey(_thisWindowHandle, c_hotKeyId);
-            }
             hwndSource?.Dispose();
             hwndSource?.Dispose();
             hwndSource = null;
             hwndSource = null;
             base.OnClosed(e);
             base.OnClosed(e);
-            Application.Current.Shutdown();
-        }
-
-        private bool RegHotKey(System.Windows.Forms.Keys key, out string message) {
-            if (!SystemHotKey.RegHotKey(_thisWindowHandle, c_hotKeyId, SystemHotKey.KeyModifiers.Alt | SystemHotKey.KeyModifiers.Ctrl, key, out message)) {
-                message = $"Ctrl + Alt + {key.ToString()} " + message;
-                return false;
-            }
-            else {
-                return true;
-            }
-        }
-
-        protected override void OnContentRendered(EventArgs e) {
-            base.OnContentRendered(e);
-            if (AppUtil.IsHotKeyEnabled) {
-                Enum.TryParse(HotKeyUtil.GetHotKey(), out System.Windows.Forms.Keys hotKey);
-                if (!RegHotKey(hotKey, out string message)) {
-                    VirtualRoot.Out.ShowWarn(message, header: "热键设置失败", toConsole: true);
-                }
-            }
-        }
-
-        private const int WM_HOTKEY = 0x312;
-        private const int c_hotKeyId = 1; //热键ID(自定义)
-        private IntPtr WndProc(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handled) {
-            switch (msg) {
-                case WM_HOTKEY:
-                    int tmpWParam = wParam.ToInt32();
-                    if (tmpWParam == c_hotKeyId) {
-                        VirtualRoot.Execute(new ShowMainWindowCommand(isToggle: true));
-                    }
-                    break;
-                default:
-                    break;
-            }
-            return Win32Proc.WindowProc(hwnd, msg, wParam, lParam, ref handled);
         }
         }
 
 
         private int _marginLeft, _marginTop, _height, _width;
         private int _marginLeft, _marginTop, _height, _width;

+ 2 - 0
src/AppViews0/Views/Design/WindowsAutoLogonViewModel.xaml

@@ -0,0 +1,2 @@
+<vm:WindowsAutoLogonViewModel xmlns:vm="clr-namespace:NTMiner.Vms;assembly=AppModels">
+</vm:WindowsAutoLogonViewModel>

+ 4 - 2
src/AppViews0/Views/KernelsWindow.xaml

@@ -292,9 +292,11 @@
                             <DataTemplate>
                             <DataTemplate>
                                 <StackPanel Margin="4 0 0 0">
                                 <StackPanel Margin="4 0 0 0">
                                     <TextBlock Text="{Binding Code}" VerticalAlignment="Center" FontSize="14" FontWeight="Bold"></TextBlock>
                                     <TextBlock Text="{Binding Code}" VerticalAlignment="Center" FontSize="14" FontWeight="Bold"></TextBlock>
-                                    <TextBlock 
+                                    <TextBox 
+                                        IsReadOnly="True"
+                                        BorderThickness="0"
 										Foreground="Green" 
 										Foreground="Green" 
-										Text="{Binding SupportedCoins}"></TextBlock>
+										Text="{Binding SupportedCoins,Mode=OneWay}"></TextBox>
                                 </StackPanel>
                                 </StackPanel>
                             </DataTemplate>
                             </DataTemplate>
                         </DataGridTemplateColumn.CellTemplate>
                         </DataGridTemplateColumn.CellTemplate>

+ 4 - 1
src/AppViews0/Views/KernelsWindow.xaml.cs

@@ -7,7 +7,7 @@ namespace NTMiner.Views {
     public partial class KernelsWindow : BlankWindow {
     public partial class KernelsWindow : BlankWindow {
         private static readonly object _locker = new object();
         private static readonly object _locker = new object();
         private static KernelsWindow _instance = null;
         private static KernelsWindow _instance = null;
-        public static void ShowWindow() {
+        public static void ShowWindow(string keyword = null) {
             if (_instance == null) {
             if (_instance == null) {
                 lock (_locker) {
                 lock (_locker) {
                     if (_instance == null) {
                     if (_instance == null) {
@@ -19,6 +19,9 @@ namespace NTMiner.Views {
             else {
             else {
                 _instance.ShowWindow(false);
                 _instance.ShowWindow(false);
             }
             }
+            if (keyword != null) {
+                _instance.Vm.Keyword = keyword;
+            }
         }
         }
 
 
         public KernelsWindowViewModel Vm { get; private set; }
         public KernelsWindowViewModel Vm { get; private set; }

+ 1 - 0
src/AppViews0/Views/MainWindow.xaml

@@ -17,6 +17,7 @@
     WindowStyle="None"
     WindowStyle="None"
 	Background="Transparent"
 	Background="Transparent"
     AllowsTransparency="True"
     AllowsTransparency="True"
+    Topmost="True"
 	WindowStartupLocation="CenterScreen"
 	WindowStartupLocation="CenterScreen"
 	MouseDown="Window_MouseDown"
 	MouseDown="Window_MouseDown"
     d:DataContext="{d:DesignData Source=Design/MainWindowViewModel.xaml}">
     d:DataContext="{d:DesignData Source=Design/MainWindowViewModel.xaml}">

+ 9 - 1
src/AppViews0/Views/MainWindow.xaml.cs

@@ -5,6 +5,7 @@ using System;
 using System.ComponentModel;
 using System.ComponentModel;
 using System.Windows;
 using System.Windows;
 using System.Windows.Controls;
 using System.Windows.Controls;
+using System.Windows.Forms.VisualStyles;
 using System.Windows.Input;
 using System.Windows.Input;
 using System.Windows.Interop;
 using System.Windows.Interop;
 using System.Windows.Media;
 using System.Windows.Media;
@@ -157,10 +158,17 @@ namespace NTMiner.Views {
                 }
                 }
                 #endregion
                 #endregion
             };
             };
-            NotiCenterWindow.Bind(this, ownerIsTopMost: true);
+            NotiCenterWindow.Bind(this, ownerIsTopmost: true);
             this.LocationChanged += (sender, e) => {
             this.LocationChanged += (sender, e) => {
                 MoveConsoleWindow();
                 MoveConsoleWindow();
             };
             };
+            VirtualRoot.AddCmdPath<UnTopmostCommand>(action: message => {
+                UIThread.Execute(() => {
+                    if (this.Topmost) {
+                        this.Topmost = false;
+                    }
+                });
+            }, this.GetType());
             VirtualRoot.AddCmdPath<CloseMainWindowCommand>(action: message => {
             VirtualRoot.AddCmdPath<CloseMainWindowCommand>(action: message => {
                 UIThread.Execute(() => {
                 UIThread.Execute(() => {
                     if (message.IsAutoNoUi) {
                     if (message.IsAutoNoUi) {

+ 11 - 4
src/AppViews0/Views/Ucs/AppMiner.xaml

@@ -18,6 +18,7 @@
         <controls:KbMuiltilineTextBox 
         <controls:KbMuiltilineTextBox 
 			Background="Transparent"
 			Background="Transparent"
 			FontFamily="Courier New"
 			FontFamily="Courier New"
+            FontSize="14"
 			Text="{x:Static app:AppStatic.AppMinerIntro}"
 			Text="{x:Static app:AppStatic.AppMinerIntro}"
 			BorderThickness="0" IsReadOnly="True" 
 			BorderThickness="0" IsReadOnly="True" 
 			Padding="0 2 16 0" Foreground="White">
 			Padding="0 2 16 0" Foreground="White">
@@ -67,6 +68,7 @@
 				BorderThickness="0"
 				BorderThickness="0"
 				Foreground="LightGray"						
 				Foreground="LightGray"						
 				IsReadOnly="True" 
 				IsReadOnly="True" 
+				FontSize="14"
 				Text="{Binding MinerProfile.ArgsAssembly, Mode=OneWay}"></controls:KbMuiltilineTextBox>
 				Text="{Binding MinerProfile.ArgsAssembly, Mode=OneWay}"></controls:KbMuiltilineTextBox>
         </Grid>
         </Grid>
         <StackPanel Grid.Row="2">
         <StackPanel Grid.Row="2">
@@ -79,7 +81,7 @@
 					Data="{StaticResource Icon_Notice}"
 					Data="{StaticResource Icon_Notice}"
 					Fill="LightGray"
 					Fill="LightGray"
 					Stretch="Fill" />
 					Stretch="Fill" />
-                <TextBlock Foreground="LightGray" VerticalAlignment="Top" Text="{Binding MinerProfile.CoinVm.Code}"></TextBlock>
+                <TextBlock Foreground="LightGray" VerticalAlignment="Top" FontSize="14" Text="{Binding MinerProfile.CoinVm.Code}"></TextBlock>
                 <controls:KbMuiltilineTextBox 
                 <controls:KbMuiltilineTextBox 
 					FontFamily="Courier New"
 					FontFamily="Courier New"
 					Background="Transparent"
 					Background="Transparent"
@@ -87,6 +89,7 @@
 					Padding="0 2 16 2"
 					Padding="0 2 16 2"
 					Foreground="Yellow"
 					Foreground="Yellow"
 					IsReadOnly="True" 
 					IsReadOnly="True" 
+					FontSize="14"
 					Text="{Binding MinerProfile.CoinVm.Notice, Mode=OneWay}"></controls:KbMuiltilineTextBox>
 					Text="{Binding MinerProfile.CoinVm.Notice, Mode=OneWay}"></controls:KbMuiltilineTextBox>
             </WrapPanel>
             </WrapPanel>
             <WrapPanel Visibility="{Binding MinerProfile.CoinVm.CoinProfile.MainCoinPool.Notice, Converter={StaticResource NotNullOrEmptyVisibilityConverter}}">
             <WrapPanel Visibility="{Binding MinerProfile.CoinVm.CoinProfile.MainCoinPool.Notice, Converter={StaticResource NotNullOrEmptyVisibilityConverter}}">
@@ -98,7 +101,7 @@
 					Data="{StaticResource Icon_Notice}"
 					Data="{StaticResource Icon_Notice}"
 					Fill="LightGray"
 					Fill="LightGray"
 					Stretch="Fill" />
 					Stretch="Fill" />
-                <TextBlock Foreground="LightGray" VerticalAlignment="Top" Text="{Binding MinerProfile.CoinVm.CoinProfile.MainCoinPool.Name}"></TextBlock>
+                <TextBlock Foreground="LightGray" VerticalAlignment="Top" FontSize="14" Text="{Binding MinerProfile.CoinVm.CoinProfile.MainCoinPool.Name}"></TextBlock>
                 <controls:KbMuiltilineTextBox 
                 <controls:KbMuiltilineTextBox 
 					FontFamily="Courier New"
 					FontFamily="Courier New"
 					Background="Transparent"
 					Background="Transparent"
@@ -106,6 +109,7 @@
 					Padding="0 2 16 2"
 					Padding="0 2 16 2"
 					Foreground="Yellow"
 					Foreground="Yellow"
 					IsReadOnly="True" 
 					IsReadOnly="True" 
+					FontSize="14"
 					Text="{Binding MinerProfile.CoinVm.CoinProfile.MainCoinPool.Notice, Mode=OneWay}"></controls:KbMuiltilineTextBox>
 					Text="{Binding MinerProfile.CoinVm.CoinProfile.MainCoinPool.Notice, Mode=OneWay}"></controls:KbMuiltilineTextBox>
             </WrapPanel>
             </WrapPanel>
             <WrapPanel Visibility="{Binding MinerProfile.CoinVm.CoinKernel.CoinKernelProfile.IsDualCoinEnabled, Converter={StaticResource BoolToVisibilityConverter}}">
             <WrapPanel Visibility="{Binding MinerProfile.CoinVm.CoinKernel.CoinKernelProfile.IsDualCoinEnabled, Converter={StaticResource BoolToVisibilityConverter}}">
@@ -119,7 +123,7 @@
 							Data="{StaticResource Icon_Notice}"
 							Data="{StaticResource Icon_Notice}"
 							Fill="LightGray"
 							Fill="LightGray"
 							Stretch="Fill" />
 							Stretch="Fill" />
-                        <TextBlock Foreground="LightGray" VerticalAlignment="Top" Text="{Binding MinerProfile.CoinVm.CoinKernel.CoinKernelProfile.SelectedDualCoin.CoinProfile.DualCoinPool.Name}"></TextBlock>
+                        <TextBlock Foreground="LightGray" VerticalAlignment="Top" FontSize="14" Text="{Binding MinerProfile.CoinVm.CoinKernel.CoinKernelProfile.SelectedDualCoin.CoinProfile.DualCoinPool.Name}"></TextBlock>
                         <controls:KbMuiltilineTextBox 
                         <controls:KbMuiltilineTextBox 
 							FontFamily="Courier New"
 							FontFamily="Courier New"
 							Background="Transparent"
 							Background="Transparent"
@@ -127,6 +131,7 @@
 							Padding="0 2 16 2"
 							Padding="0 2 16 2"
 							Foreground="Yellow"
 							Foreground="Yellow"
 							IsReadOnly="True" 
 							IsReadOnly="True" 
+							FontSize="14"
 							Text="{Binding MinerProfile.CoinVm.CoinKernel.CoinKernelProfile.SelectedDualCoin.CoinProfile.DualCoinPool.Notice, Mode=OneWay}"></controls:KbMuiltilineTextBox>
 							Text="{Binding MinerProfile.CoinVm.CoinKernel.CoinKernelProfile.SelectedDualCoin.CoinProfile.DualCoinPool.Notice, Mode=OneWay}"></controls:KbMuiltilineTextBox>
                     </WrapPanel>
                     </WrapPanel>
                 </WrapPanel>
                 </WrapPanel>
@@ -140,12 +145,13 @@
 					Data="{StaticResource Icon_Notice}"
 					Data="{StaticResource Icon_Notice}"
 					Fill="LightGray"
 					Fill="LightGray"
 					Stretch="Fill" />
 					Stretch="Fill" />
-                <TextBlock Foreground="LightGray" VerticalAlignment="Top" Text="{Binding MinerProfile.CoinVm.CoinKernel.Kernel.FullName, Mode=OneWay}"></TextBlock>
+                <TextBlock Foreground="LightGray" VerticalAlignment="Top" FontSize="14" Text="{Binding MinerProfile.CoinVm.CoinKernel.Kernel.FullName, Mode=OneWay}"></TextBlock>
                 <WrapPanel>
                 <WrapPanel>
                     <controls:KbMuiltilineTextBox 
                     <controls:KbMuiltilineTextBox 
 						Background="Transparent"
 						Background="Transparent"
 						FontFamily="Courier New"
 						FontFamily="Courier New"
 						ToolTip="币种内核公告"
 						ToolTip="币种内核公告"
+						FontSize="14"
 						Text="{Binding MinerProfile.CoinVm.CoinKernel.Notice, Mode=OneWay}"
 						Text="{Binding MinerProfile.CoinVm.CoinKernel.Notice, Mode=OneWay}"
 						Visibility="{Binding MinerProfile.CoinVm.CoinKernel.Notice,Converter={StaticResource NotNullOrEmptyVisibilityConverter}}"
 						Visibility="{Binding MinerProfile.CoinVm.CoinKernel.Notice,Converter={StaticResource NotNullOrEmptyVisibilityConverter}}"
 						BorderThickness="0" IsReadOnly="True" 
 						BorderThickness="0" IsReadOnly="True" 
@@ -155,6 +161,7 @@
 						Background="Transparent"
 						Background="Transparent"
 						FontFamily="Courier New"
 						FontFamily="Courier New"
 						ToolTip="内核公告"
 						ToolTip="内核公告"
+						FontSize="14"
 						Text="{Binding MinerProfile.CoinVm.CoinKernel.Kernel.Notice, Mode=OneWay}"
 						Text="{Binding MinerProfile.CoinVm.CoinKernel.Kernel.Notice, Mode=OneWay}"
 						Visibility="{Binding MinerProfile.CoinVm.CoinKernel.Kernel.Notice,Converter={StaticResource NotNullOrEmptyVisibilityConverter}}"
 						Visibility="{Binding MinerProfile.CoinVm.CoinKernel.Kernel.Notice,Converter={StaticResource NotNullOrEmptyVisibilityConverter}}"
 						BorderThickness="0" IsReadOnly="True" 
 						BorderThickness="0" IsReadOnly="True" 

+ 2 - 1
src/AppViews0/Views/Ucs/CoinKernelEdit.xaml.cs

@@ -14,7 +14,8 @@ namespace NTMiner.Views.Ucs {
                 Width = 700,
                 Width = 700,
                 IsMaskTheParent = true,
                 IsMaskTheParent = true,
                 IconName = "Icon_Kernel",
                 IconName = "Icon_Kernel",
-                CloseVisible = Visibility.Visible
+                CloseVisible = Visibility.Visible,
+                FooterVisible = Visibility.Collapsed
             }, ucFactory: (window) =>
             }, ucFactory: (window) =>
             {
             {
                 CoinKernelViewModel vm = new CoinKernelViewModel(source);
                 CoinKernelViewModel vm = new CoinKernelViewModel(source);

+ 2 - 1
src/AppViews0/Views/Ucs/KernelEdit.xaml.cs

@@ -14,7 +14,8 @@ namespace NTMiner.Views.Ucs {
                 IconName = "Icon_Kernel",
                 IconName = "Icon_Kernel",
                 IsMaskTheParent = true,
                 IsMaskTheParent = true,
                 Width = 620,
                 Width = 620,
-                CloseVisible = Visibility.Visible
+                CloseVisible = Visibility.Visible,
+                FooterVisible = Visibility.Collapsed
             }, ucFactory: (window) => {
             }, ucFactory: (window) => {
                 KernelViewModel vm = new KernelViewModel(source);
                 KernelViewModel vm = new KernelViewModel(source);
                 window.AddCloseWindowOnecePath(vm.Id);
                 window.AddCloseWindowOnecePath(vm.Id);

+ 4 - 0
src/AppViews0/Views/Ucs/OuterProperty.xaml

@@ -80,6 +80,10 @@
 							<TextBlock Style="{StaticResource LblTb}" Text="CPU名称"></TextBlock>
 							<TextBlock Style="{StaticResource LblTb}" Text="CPU名称"></TextBlock>
                             <TextBox Text="{Binding Cpu.Name,Mode=OneWay}"></TextBox>
                             <TextBox Text="{Binding Cpu.Name,Mode=OneWay}"></TextBox>
                         </WrapPanel>
                         </WrapPanel>
+                        <WrapPanel>
+                            <TextBlock Style="{StaticResource LblTb}" Text="CPU ID"></TextBlock>
+                            <TextBox Text="{Binding Cpu.CpuId,Mode=OneWay}"></TextBox>
+                        </WrapPanel>
                         <WrapPanel>
                         <WrapPanel>
                             <TextBlock Style="{StaticResource LblTb}" Text="CPU标识名"></TextBlock>
                             <TextBlock Style="{StaticResource LblTb}" Text="CPU标识名"></TextBlock>
                             <TextBox Text="{Binding Cpu.Identifier,Mode=OneWay}"></TextBox>
                             <TextBox Text="{Binding Cpu.Identifier,Mode=OneWay}"></TextBox>

+ 14 - 2
src/AppViews0/Views/Ucs/ServerMessageEdit.xaml

@@ -24,6 +24,7 @@
             <TextBox Width="160" Background="White" Text="{Binding Provider, ValidatesOnExceptions=True}">
             <TextBox Width="160" Background="White" Text="{Binding Provider, ValidatesOnExceptions=True}">
             </TextBox>
             </TextBox>
             <ListBox 
             <ListBox 
+                Margin="4 0 0 0"
 				Background="Transparent"
 				Background="Transparent"
 				ItemsSource="{x:Static app:AppStatic.ServerMessageTypeEnumItems}"
 				ItemsSource="{x:Static app:AppStatic.ServerMessageTypeEnumItems}"
 				SelectedItem="{Binding ServerMessageTypeEnumItem}"
 				SelectedItem="{Binding ServerMessageTypeEnumItem}"
@@ -45,8 +46,19 @@
             </ListBox>
             </ListBox>
         </WrapPanel>
         </WrapPanel>
         <WrapPanel Margin="0 2">
         <WrapPanel Margin="0 2">
-            <TextBlock Style="{StaticResource LblTb}">内容</TextBlock>
-            <TextBox Width="440" Text="{Binding Content, ValidatesOnExceptions=True}">
+            <TextBlock Style="{StaticResource LblTb}" VerticalAlignment="Top">内容</TextBlock>
+            <TextBox 
+                x:Name="TbContent"
+                Width="440" Height="50" 
+                VerticalContentAlignment="Top" 
+                TextWrapping="Wrap" 
+                AcceptsReturn="True" 
+                Text="{Binding Content, ValidatesOnExceptions=True}">
+                <TextBox.ContextMenu>
+                    <ContextMenu>
+                        <MenuItem Header="查找内核" Click="FindKernel_Click"></MenuItem>
+                    </ContextMenu>
+                </TextBox.ContextMenu>
             </TextBox>
             </TextBox>
         </WrapPanel>
         </WrapPanel>
         <controls:KbButton
         <controls:KbButton

+ 7 - 1
src/AppViews0/Views/Ucs/ServerMessageEdit.xaml.cs

@@ -9,7 +9,8 @@ namespace NTMiner.Views.Ucs {
                 IsMaskTheParent = true,
                 IsMaskTheParent = true,
                 Width = 540,
                 Width = 540,
                 FormType = formType,
                 FormType = formType,
-                CloseVisible = System.Windows.Visibility.Visible
+                CloseVisible = System.Windows.Visibility.Visible,
+                FooterVisible = System.Windows.Visibility.Collapsed
             }, ucFactory: (window) =>
             }, ucFactory: (window) =>
             {
             {
                 ServerMessageViewModel vm = new ServerMessageViewModel(data);
                 ServerMessageViewModel vm = new ServerMessageViewModel(data);
@@ -22,5 +23,10 @@ namespace NTMiner.Views.Ucs {
             this.DataContext = vm;
             this.DataContext = vm;
             InitializeComponent();
             InitializeComponent();
         }
         }
+
+        private void FindKernel_Click(object sender, System.Windows.RoutedEventArgs e) {
+            string keyword = this.TbContent.SelectedText;
+            KernelsWindow.ShowWindow(keyword);
+        }
     }
     }
 }
 }

+ 1 - 1
src/AppViews0/Views/Ucs/ServerMessages.xaml

@@ -194,7 +194,7 @@
                     </DataGridTemplateColumn.HeaderTemplate>
                     </DataGridTemplateColumn.HeaderTemplate>
                     <DataGridTemplateColumn.CellTemplate>
                     <DataGridTemplateColumn.CellTemplate>
                         <DataTemplate>
                         <DataTemplate>
-                            <TextBlock Text="{Binding Content}" ToolTip="{Binding Content}" Foreground="{Binding IconFill}"></TextBlock>
+                            <TextBlock Text="{Binding Content}" TextWrapping="Wrap" ToolTip="{Binding Content}" Foreground="{Binding IconFill}"></TextBlock>
                         </DataTemplate>
                         </DataTemplate>
                     </DataGridTemplateColumn.CellTemplate>
                     </DataGridTemplateColumn.CellTemplate>
                 </DataGridTemplateColumn>
                 </DataGridTemplateColumn>

+ 1 - 1
src/AppViews0/Views/Ucs/SpeedCharts.xaml.cs

@@ -1,6 +1,6 @@
 using LiveCharts;
 using LiveCharts;
 using LiveCharts.Wpf;
 using LiveCharts.Wpf;
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Vms;
 using NTMiner.Vms;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;

+ 1 - 2
src/AppViews0/Views/Ucs/StateBar.xaml

@@ -314,7 +314,7 @@
 							Width="14"
 							Width="14"
 							Height="13"
 							Height="13"
 							Data="{StaticResource Icon_Update}"
 							Data="{StaticResource Icon_Update}"
-							Fill="{StaticResource BtnBackground}"
+							Fill="{Binding CheckUpdateForeground}"
 							Stretch="Fill" />
 							Stretch="Fill" />
                         <Path 
                         <Path 
                             x:Name="LoadingIcon"
                             x:Name="LoadingIcon"
@@ -328,7 +328,6 @@
                                 <RotateTransform Angle="0" CenterX="7" CenterY="7"></RotateTransform>
                                 <RotateTransform Angle="0" CenterX="7" CenterY="7"></RotateTransform>
                             </Path.RenderTransform>
                             </Path.RenderTransform>
                         </Path>
                         </Path>
-                        <TextBlock Foreground="{Binding CheckUpdateForeground}">更新</TextBlock>
                         <TextBlock
                         <TextBlock
 						    Margin="2 0 0 0"
 						    Margin="2 0 0 0"
                             Foreground="{StaticResource LableColor}"
                             Foreground="{StaticResource LableColor}"

+ 2 - 5
src/AppViews0/Views/Ucs/StateBar.xaml.cs

@@ -32,10 +32,11 @@ namespace NTMiner.Views.Ucs {
                             Vm.PoolDelayText = message.PoolDelayText;
                             Vm.PoolDelayText = message.PoolDelayText;
                         }
                         }
                     }, location: this.GetType());
                     }, location: this.GetType());
-                window.AddEventPath<MineStartedEvent>("开始挖矿后清空矿池延时", LogEnum.DevConsole,
+                window.AddEventPath<MineStartedEvent>("开始挖矿后清空矿池延时 & 挖矿开始后将内核自我重启计数清零", LogEnum.DevConsole,
                     action: message => {
                     action: message => {
                         Vm.PoolDelayText = string.Empty;
                         Vm.PoolDelayText = string.Empty;
                         Vm.DualPoolDelayText = string.Empty;
                         Vm.DualPoolDelayText = string.Empty;
+                        Vm.OnPropertyChanged(nameof(Vm.KernelSelfRestartCountText));
                     }, location: this.GetType());
                     }, location: this.GetType());
                 window.AddEventPath<MineStopedEvent>("停止挖矿后将清空矿池延时", LogEnum.DevConsole,
                 window.AddEventPath<MineStopedEvent>("停止挖矿后将清空矿池延时", LogEnum.DevConsole,
                     action: message => {
                     action: message => {
@@ -71,10 +72,6 @@ namespace NTMiner.Views.Ucs {
                     action: message => {
                     action: message => {
                         Vm.OnPropertyChanged(nameof(Vm.KernelSelfRestartCountText));
                         Vm.OnPropertyChanged(nameof(Vm.KernelSelfRestartCountText));
                     }, location: this.GetType());
                     }, location: this.GetType());
-                window.AddEventPath<MineStartedEvent>("挖矿开始后将内核自我重启计数清零", LogEnum.DevConsole,
-                    action: message => {
-                        Vm.OnPropertyChanged(nameof(Vm.KernelSelfRestartCountText));
-                    }, location: this.GetType());
                 window.AddCmdPath<RefreshIsRemoteDesktopEnabledCommand>(LogEnum.DevConsole, 
                 window.AddCmdPath<RefreshIsRemoteDesktopEnabledCommand>(LogEnum.DevConsole, 
                     action: message => {
                     action: message => {
                         Vm.RefreshIsRemoteDesktopEnabled();
                         Vm.RefreshIsRemoteDesktopEnabled();

+ 81 - 0
src/AppViews0/Views/Ucs/WindowsAutoLogon.xaml

@@ -0,0 +1,81 @@
+<UserControl 
+    x:Class="NTMiner.Views.Ucs.WindowsAutoLogon"
+	xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
+	xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
+	xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
+	xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
+	xmlns:blankWindow="http://NTMiner.com"
+	xmlns:sys="clr-namespace:System;assembly=mscorlib"
+	xmlns:controls="clr-namespace:NTMiner.Controls;assembly=NTMinerWpf"
+	xmlns:wpf="clr-namespace:NTMiner;assembly=NTMinerWpf"
+	xmlns:local="clr-namespace:NTMiner.Views.Ucs"
+	xmlns:vm="clr-namespace:NTMiner.Vms;assembly=AppModels"
+	xmlns:app="clr-namespace:NTMiner;assembly=AppModels"
+	mc:Ignorable="d" d:DesignHeight="160" d:DesignWidth="380"
+    d:DataContext="{d:DesignData Source=../Design/WindowsAutoLogonViewModel.xaml}">
+    <Grid Margin="20 10">
+        <Grid.ColumnDefinitions>
+            <ColumnDefinition Width="Auto"></ColumnDefinition>
+            <ColumnDefinition Width="200"></ColumnDefinition>
+        </Grid.ColumnDefinitions>
+        <Grid.RowDefinitions>
+            <RowDefinition Height="Auto"></RowDefinition>
+            <RowDefinition Height="Auto"></RowDefinition>
+            <RowDefinition Height="Auto"></RowDefinition>
+            <RowDefinition Height="*"></RowDefinition>
+        </Grid.RowDefinitions>
+        <TextBlock 
+			Grid.Row="0" Grid.Column="0" 
+            Style="{StaticResource LblTbBase}"
+			Text="Windows 登录名"></TextBlock>
+        <TextBox 
+            x:Name="TbLoginName"
+			Grid.Row="0" Grid.Column="1" Margin="0 2"
+            ToolTip="填写在挖矿端注册的群控登录名"
+			Text="{Binding UserName}" Background="White" 
+			VerticalContentAlignment="Center"></TextBox>
+
+        <TextBlock 
+			Grid.Row="1" Grid.Column="0"
+            Style="{StaticResource LblTbBase}"
+			Text="Windows 密码"></TextBlock>
+        <PasswordBox 
+			Grid.Row="1" Grid.Column="1" Margin="0 2" Height="26"
+			x:Name="PbPassword" VerticalContentAlignment="Center" 
+            Background="White" controls:PasswordBoxHelper.Attach="true" 
+            controls:PasswordBoxHelper.Password="{Binding Password, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/>
+
+        <WrapPanel Grid.Row="2" Grid.Column="2" Margin="0 8 0 0">
+            <controls:KbButton
+				IsDefault="True"
+				Padding="15 2"
+                Command="{Binding Ok}"
+				Background="{StaticResource BtnBackground}"
+				Foreground="{StaticResource BtnForeground}"
+				CornerRadius="2">
+                <WrapPanel>
+                    <Path
+						Width="12"
+						Height="12"
+						Data="{StaticResource Icon_Ok}"
+						Fill="{StaticResource BtnForeground}"
+						Stretch="Fill" />
+                    <TextBlock
+						Padding="0 4"
+						VerticalAlignment="Center"
+						Text="确定" />
+                </WrapPanel>
+            </controls:KbButton>
+        </WrapPanel>
+        <WrapPanel Grid.Row="3" Grid.ColumnSpan="2" HorizontalAlignment="Center" VerticalAlignment="Center">
+            <TextBlock Foreground="Red">注意:该操作有一定的安全风险。</TextBlock>
+            <controls:KbLinkButton
+				Padding="0"
+				Command="{x:Static app:AppStatic.OpenWindowsAutoLogonMoreInfo}"
+				KbDisplayLine="False"
+				Content="了解详情"
+				Background="Transparent">
+            </controls:KbLinkButton>
+        </WrapPanel>
+    </Grid>
+</UserControl>

+ 45 - 0
src/AppViews0/Views/Ucs/WindowsAutoLogon.xaml.cs

@@ -0,0 +1,45 @@
+using NTMiner.Vms;
+using System.Windows.Controls;
+
+namespace NTMiner.Views.Ucs {
+    public partial class WindowsAutoLogon : UserControl {
+        public static void ShowWindow() {
+            ContainerWindow.ShowWindow(new ContainerWindowViewModel {
+                Title = "Windows 2004或更高版本的Windows",
+                IconName = "Icon_User",
+                Width = 380,
+                Height = 180,
+                CloseVisible = System.Windows.Visibility.Visible,
+                FooterVisible = System.Windows.Visibility.Collapsed,
+                IsMaskTheParent = true,
+                IsChildWindow = true
+            }, ucFactory: (window) => {
+                WindowsAutoLogonViewModel vm = new WindowsAutoLogonViewModel();
+                window.AddCloseWindowOnecePath(vm.Id);
+                return new WindowsAutoLogon(vm);
+            }, beforeShow: (window, uc)=> {
+                uc.PasswordFocus();
+            }, fixedSize: true);
+        }
+
+        public WindowsAutoLogonViewModel Vm { get; private set; }
+
+        public WindowsAutoLogon(WindowsAutoLogonViewModel vm) {
+            if (WpfUtil.IsInDesignMode) {
+                return;
+            }
+            this.Vm = vm;
+            this.DataContext = this.Vm;
+            InitializeComponent();
+        }
+
+        public void PasswordFocus() {
+            if (string.IsNullOrEmpty(this.TbLoginName.Text)) {
+                this.TbLoginName.Focus();
+            }
+            else {
+                this.PbPassword.Focus();
+            }
+        }
+    }
+}

+ 0 - 28
src/BlankWindow/GFramework.BlankWindow.sln

@@ -1,28 +0,0 @@
-
-Microsoft Visual Studio Solution File, Format Version 12.00
-# Visual Studio 14
-VisualStudioVersion = 14.0.23107.0
-MinimumVisualStudioVersion = 10.0.40219.1
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GFramework.BlankWindow", "GFramework.BlankWindow\GFramework.BlankWindow.csproj", "{B7107A67-A76E-4313-8C5B-3265DDE238B6}"
-EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GFramework.BlankWindow.Demo", "GFramework.BlankWindow.Demo\GFramework.BlankWindow.Demo.csproj", "{258F1E45-C0DF-4282-9102-25D3F24FC190}"
-EndProject
-Global
-	GlobalSection(SolutionConfigurationPlatforms) = preSolution
-		Debug|Any CPU = Debug|Any CPU
-		Release|Any CPU = Release|Any CPU
-	EndGlobalSection
-	GlobalSection(ProjectConfigurationPlatforms) = postSolution
-		{B7107A67-A76E-4313-8C5B-3265DDE238B6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
-		{B7107A67-A76E-4313-8C5B-3265DDE238B6}.Debug|Any CPU.Build.0 = Debug|Any CPU
-		{B7107A67-A76E-4313-8C5B-3265DDE238B6}.Release|Any CPU.ActiveCfg = Release|Any CPU
-		{B7107A67-A76E-4313-8C5B-3265DDE238B6}.Release|Any CPU.Build.0 = Release|Any CPU
-		{258F1E45-C0DF-4282-9102-25D3F24FC190}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
-		{258F1E45-C0DF-4282-9102-25D3F24FC190}.Debug|Any CPU.Build.0 = Debug|Any CPU
-		{258F1E45-C0DF-4282-9102-25D3F24FC190}.Release|Any CPU.ActiveCfg = Release|Any CPU
-		{258F1E45-C0DF-4282-9102-25D3F24FC190}.Release|Any CPU.Build.0 = Release|Any CPU
-	EndGlobalSection
-	GlobalSection(SolutionProperties) = preSolution
-		HideSolutionNode = FALSE
-	EndGlobalSection
-EndGlobal

+ 15 - 21
src/MinerClient/App.xaml.cs

@@ -1,5 +1,6 @@
 using NTMiner.Core;
 using NTMiner.Core;
 using NTMiner.Core.MinerClient;
 using NTMiner.Core.MinerClient;
+using NTMiner.Gpus;
 using NTMiner.Mine;
 using NTMiner.Mine;
 using NTMiner.Notifications;
 using NTMiner.Notifications;
 using NTMiner.RemoteDesktop;
 using NTMiner.RemoteDesktop;
@@ -15,14 +16,13 @@ using System.Windows;
 
 
 namespace NTMiner {
 namespace NTMiner {
     public partial class App : Application {
     public partial class App : Application {
-        public static readonly string SwitchRadeonGpuResourceName = "switch-radeon-gpu.exe";
-        public static readonly string SwitchRadeonGpuFileFullName = Path.Combine(TempPath.TempDirFullName, SwitchRadeonGpuResourceName);
-        public static readonly string AtikmdagPatcherResourceName = "atikmdag-patcher1.4.7.exe";
-        public static readonly string AtikmdagPatcherFileFullName = Path.Combine(TempPath.TempDirFullName, AtikmdagPatcherResourceName);
         public static readonly string BlockWAUResourceName = "BlockWAU.bat";
         public static readonly string BlockWAUResourceName = "BlockWAU.bat";
         public static readonly string BlockWAUFileFullName = Path.Combine(TempPath.TempDirFullName, BlockWAUResourceName);
         public static readonly string BlockWAUFileFullName = Path.Combine(TempPath.TempDirFullName, BlockWAUResourceName);
 
 
         public App() {
         public App() {
+            if ((NTMinerRegistry.GetIsAutoStart() || CommandLineArgs.IsAutoStart) && NTMinerRegistry.GetIsNoUi()) {
+                NTMinerConsole.Disable();
+            }
             VirtualRoot.SetOut(NotiCenterWindowViewModel.Instance);
             VirtualRoot.SetOut(NotiCenterWindowViewModel.Instance);
             Logger.SetDir(MinerClientTempPath.TempLogsDirFullName);
             Logger.SetDir(MinerClientTempPath.TempLogsDirFullName);
             WpfUtil.Init();
             WpfUtil.Init();
@@ -43,7 +43,6 @@ namespace NTMiner {
         protected override void OnStartup(StartupEventArgs e) {
         protected override void OnStartup(StartupEventArgs e) {
             BuildCommonPaths();
             BuildCommonPaths();
 
 
-            NotiCenterWindow.ShowWindow();
             // 升级挖矿端
             // 升级挖矿端
             if (!string.IsNullOrEmpty(CommandLineArgs.Upgrade)) {
             if (!string.IsNullOrEmpty(CommandLineArgs.Upgrade)) {
                 // 启动计时器以放置后续的逻辑中用到计时器
                 // 启动计时器以放置后续的逻辑中用到计时器
@@ -60,6 +59,7 @@ namespace NTMiner {
 
 
         private void DoRun() {
         private void DoRun() {
             if (AppUtil.GetMutex(NTKeyword.MinerClientAppMutex)) {
             if (AppUtil.GetMutex(NTKeyword.MinerClientAppMutex)) {
+                NotiCenterWindow.ShowWindow();
                 Logger.InfoDebugLine($"==================NTMiner.exe {EntryAssemblyInfo.CurrentVersionStr}==================");
                 Logger.InfoDebugLine($"==================NTMiner.exe {EntryAssemblyInfo.CurrentVersionStr}==================");
                 // 在另一个UI线程运行欢迎界面以确保欢迎界面的响应不被耗时的主界面初始化过程阻塞
                 // 在另一个UI线程运行欢迎界面以确保欢迎界面的响应不被耗时的主界面初始化过程阻塞
                 // 注意:必须确保SplashWindow没有用到任何其它界面用到的依赖对象
                 // 注意:必须确保SplashWindow没有用到任何其它界面用到的依赖对象
@@ -101,7 +101,7 @@ namespace NTMiner {
                     UIThread.Execute(() => {
                     UIThread.Execute(() => {
                         Window mainWindow = null;
                         Window mainWindow = null;
                         AppRoot.NotifyIcon = ExtendedNotifyIcon.Create("开源矿工", isMinerStudio: false);
                         AppRoot.NotifyIcon = ExtendedNotifyIcon.Create("开源矿工", isMinerStudio: false);
-                        if (NTMinerContext.Instance.MinerProfile.IsNoUi && NTMinerContext.Instance.MinerProfile.IsAutoStart) {
+                        if (NTMinerRegistry.GetIsNoUi() && NTMinerRegistry.GetIsAutoStart()) {
                             ConsoleWindow.Instance.Hide();
                             ConsoleWindow.Instance.Hide();
                             VirtualRoot.Out.ShowSuccess("以无界面模式启动,可在选项页调整设置", header: "开源矿工");
                             VirtualRoot.Out.ShowSuccess("以无界面模式启动,可在选项页调整设置", header: "开源矿工");
                         }
                         }
@@ -278,26 +278,14 @@ namespace NTMiner {
             #region 处理开启A卡计算模式
             #region 处理开启A卡计算模式
             VirtualRoot.AddCmdPath<SwitchRadeonGpuCommand>(action: message => {
             VirtualRoot.AddCmdPath<SwitchRadeonGpuCommand>(action: message => {
                 if (NTMinerContext.Instance.GpuSet.GpuType == GpuType.AMD) {
                 if (NTMinerContext.Instance.GpuSet.GpuType == GpuType.AMD) {
-                    SwitchRadeonGpu.SwitchRadeonGpu.Run(message.On).ContinueWith(t => {
-                        if (t.Exception == null) {
-                            if (message.On) {
-                                VirtualRoot.ThisLocalInfo(nameof(App), "开启A卡计算模式成功", OutEnum.Success);
-                            }
-                            else {
-                                VirtualRoot.ThisLocalInfo(nameof(App), "关闭A卡计算模式成功", OutEnum.Success);
-                            }
-                        }
-                        else {
-                            VirtualRoot.Out.ShowError(t.Exception.Message, autoHideSeconds: 4);
-                        }
-                    });
+                    AppRoot.SwitchRadeonGpu(message.On);
                 }
                 }
             }, location: this.GetType());
             }, location: this.GetType());
             #endregion
             #endregion
             #region 处理A卡驱动签名
             #region 处理A卡驱动签名
             VirtualRoot.AddCmdPath<AtikmdagPatcherCommand>(action: message => {
             VirtualRoot.AddCmdPath<AtikmdagPatcherCommand>(action: message => {
                 if (NTMinerContext.Instance.GpuSet.GpuType == GpuType.AMD) {
                 if (NTMinerContext.Instance.GpuSet.GpuType == GpuType.AMD) {
-                    AtikmdagPatcher.AtikmdagPatcherUtil.Run();
+                    AppRoot.OpenAtikmdagPatcher();
                 }
                 }
             }, location: this.GetType());
             }, location: this.GetType());
             #endregion
             #endregion
@@ -321,7 +309,13 @@ namespace NTMiner {
                 if (NTMiner.Windows.OS.Instance.IsAutoAdminLogon) {
                 if (NTMiner.Windows.OS.Instance.IsAutoAdminLogon) {
                     return;
                     return;
                 }
                 }
-                NTMiner.Windows.Cmd.RunClose("control", "userpasswords2");
+                if (NTMiner.Windows.OS.Instance.IsGEWindows2004) {
+                    WindowsAutoLogon.ShowWindow();
+                }
+                else {
+                    VirtualRoot.Execute(new UnTopmostCommand());
+                    NTMiner.Windows.Cmd.RunClose("control", "userpasswords2");
+                }
             }, location: this.GetType());
             }, location: this.GetType());
             #endregion
             #endregion
         }
         }

+ 0 - 24
src/MinerClient/AtikmdagPatcher/AtikmdagPatcherUtil.cs

@@ -1,24 +0,0 @@
-using System;
-using System.Reflection;
-using System.Threading.Tasks;
-
-/// <summary>
-/// 注意不要挪动这里的命名空间也不要挪动该代码文件所处的程序集
-/// 嵌入的资源的位置和命名空间有关契约关系
-/// </summary>
-namespace NTMiner.AtikmdagPatcher {
-    public static class AtikmdagPatcherUtil {
-        public static Task Run() {
-            return Task.Factory.StartNew(() => {
-                ExtractManifestResource();
-                Windows.Cmd.RunClose(App.AtikmdagPatcherFileFullName, string.Empty, waitForExit: false);
-            });
-        }
-
-        private static void ExtractManifestResource() {
-            Type type = typeof(AtikmdagPatcherUtil);
-            Assembly assembly = type.Assembly;
-            assembly.ExtractManifestResource(type, App.AtikmdagPatcherResourceName, App.AtikmdagPatcherFileFullName);
-        }
-    }
-}

TEMPAT SAMPAH
src/MinerClient/AtikmdagPatcher/atikmdag-patcher1.4.7.exe


+ 1 - 1
src/MinerClient/Daemon/DaemonUtil.cs

@@ -49,7 +49,7 @@ namespace NTMiner.Daemon {
         private static void ExtractRunNTMinerDaemonAsync() {
         private static void ExtractRunNTMinerDaemonAsync() {
             Task.Factory.StartNew(() => {
             Task.Factory.StartNew(() => {
                 ExtractResource(NTKeyword.NTMinerDaemonFileName);
                 ExtractResource(NTKeyword.NTMinerDaemonFileName);
-                Windows.Cmd.RunClose(MinerClientTempPath.DaemonFileFullName, string.Empty, waitForExit: true, createNoWindow: !DevMode.IsDevMode);
+                Windows.Cmd.RunClose(MinerClientTempPath.DaemonFileFullName, "--bootByMinerClient", waitForExit: true, createNoWindow: !DevMode.IsDevMode);
                 Logger.OkDebugLine("守护进程启动成功");
                 Logger.OkDebugLine("守护进程启动成功");
             });
             });
         }
         }

+ 0 - 8
src/MinerClient/MinerClient.csproj

@@ -114,9 +114,7 @@
   </ItemGroup>
   </ItemGroup>
   <ItemGroup>
   <ItemGroup>
     <Compile Include="App.xaml.cs" />
     <Compile Include="App.xaml.cs" />
-    <Compile Include="AtikmdagPatcher\AtikmdagPatcherUtil.cs" />
     <Compile Include="NoDevFee\NoDevFeeUtil.cs" />
     <Compile Include="NoDevFee\NoDevFeeUtil.cs" />
-    <Compile Include="SwitchRadeonGpu\SwitchRadeonGpu.cs" />
     <Compile Include="Windows\WindowsUtil.cs" />
     <Compile Include="Windows\WindowsUtil.cs" />
   </ItemGroup>
   </ItemGroup>
   <ItemGroup>
   <ItemGroup>
@@ -223,12 +221,6 @@
       <SubType>Designer</SubType>
       <SubType>Designer</SubType>
     </ApplicationDefinition>
     </ApplicationDefinition>
   </ItemGroup>
   </ItemGroup>
-  <ItemGroup>
-    <EmbeddedResource Include="SwitchRadeonGpu\switch-radeon-gpu.exe" />
-  </ItemGroup>
-  <ItemGroup>
-    <EmbeddedResource Include="AtikmdagPatcher\atikmdag-patcher1.4.7.exe" />
-  </ItemGroup>
   <ItemGroup>
   <ItemGroup>
     <SplashScreen Include="splashWindow.png" />
     <SplashScreen Include="splashWindow.png" />
   </ItemGroup>
   </ItemGroup>

+ 0 - 24
src/MinerClient/SwitchRadeonGpu/SwitchRadeonGpu.cs

@@ -1,24 +0,0 @@
-using System;
-using System.Reflection;
-using System.Threading.Tasks;
-
-/// <summary>
-/// 注意不要挪动这里的命名空间也不要挪动该代码文件所处的程序集
-/// 嵌入的资源的位置和命名空间有关契约关系
-/// </summary>
-namespace NTMiner.SwitchRadeonGpu {
-    public static class SwitchRadeonGpu {
-        public static Task Run(bool on) {
-            return Task.Factory.StartNew(() => {
-                ExtractManifestResource();
-                Windows.Cmd.RunClose(App.SwitchRadeonGpuFileFullName, $"--compute={(on ? "on" : "off")} --admin --restart", waitForExit: true);
-            });
-        }
-
-        private static void ExtractManifestResource() {
-            Type type = typeof(SwitchRadeonGpu);
-            Assembly assembly = type.Assembly;
-            assembly.ExtractManifestResource(type, App.SwitchRadeonGpuResourceName, App.SwitchRadeonGpuFileFullName);
-        }
-    }
-}

TEMPAT SAMPAH
src/MinerClient/SwitchRadeonGpu/switch-radeon-gpu.exe


+ 2 - 0
src/NTMiner.Controllers/IFileUrlController.cs

@@ -17,6 +17,8 @@ namespace NTMiner.Controllers {
         string NTMinerUpdaterUrl();
         string NTMinerUpdaterUrl();
         string MinerClientFinderUrl();
         string MinerClientFinderUrl();
         string LiteDbExplorerUrl();
         string LiteDbExplorerUrl();
+        string AtikmdagPatcherUrl();
+        string SwitchRadeonGpuUrl();
         string PackageUrl(PackageUrlRequest request);
         string PackageUrl(PackageUrlRequest request);
     }
     }
 }
 }

+ 1 - 11
src/NTMiner.Controllers/IGpuNameController.cs

@@ -1,20 +1,10 @@
-using NTMiner.Core.Gpus;
-using System.Collections.Generic;
+using NTMiner.Gpus;
 
 
 namespace NTMiner.Controllers {
 namespace NTMiner.Controllers {
     public interface IGpuNameController {
     public interface IGpuNameController {
-        DataResponse<List<GpuName>> GpuNames(object requestss);
         /// <summary>
         /// <summary>
         /// 需签名
         /// 需签名
         /// </summary>
         /// </summary>
         QueryGpuNameCountsResponse QueryGpuNameCounts(QueryGpuNameCountsRequest request);
         QueryGpuNameCountsResponse QueryGpuNameCounts(QueryGpuNameCountsRequest request);
-        /// <summary>
-        /// 需签名
-        /// </summary>
-        ResponseBase SetGpuName(DataRequest<GpuName> request);
-        /// <summary>
-        /// 需签名
-        /// </summary>
-        ResponseBase RemoveGpuName(DataRequest<GpuName> request);
     }
     }
 }
 }

+ 28 - 0
src/NTMinerClient/ComputerRoot.cs

@@ -0,0 +1,28 @@
+using OpenHardwareMonitor.Hardware;
+
+namespace NTMiner {
+    public static class ComputerRoot {
+        private static readonly object _locker = new object();
+        #region 电脑硬件
+        private static Computer _computer = null;
+        public static Computer Computer {
+            get {
+                if (_computer == null) {
+                    lock (_locker) {
+                        if (_computer == null) {
+                            _computer = new Computer();
+                            _computer.Open();
+                            _computer.CPUEnabled = true;
+                            VirtualRoot.AddEventPath<AppExitEvent>($"程序退出时关闭OpenHardwareMonitor", LogEnum.None,
+                                message => {
+                                    _computer?.Close();
+                                }, typeof(VirtualRoot));
+                        }
+                    }
+                }
+                return _computer;
+            }
+        }
+        #endregion
+    }
+}

+ 2 - 1
src/NTMinerClient/Core/CoinExtensions.cs

@@ -1,4 +1,5 @@
-using System;
+using NTMiner.Gpus;
+using System;
 
 
 namespace NTMiner.Core {
 namespace NTMiner.Core {
     public static class CoinExtensions {
     public static class CoinExtensions {

+ 1 - 0
src/NTMinerClient/Core/Impl/OverClockDataSet.cs

@@ -1,4 +1,5 @@
 using NTMiner.Core.MinerServer;
 using NTMiner.Core.MinerServer;
+using NTMiner.Gpus;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.Linq;
 using System.Linq;

+ 1 - 1
src/NTMinerClient/Core/Kernels/Impl/KernelOutputSet.cs

@@ -1,4 +1,4 @@
-using NTMiner.Core.Gpus;
+using NTMiner.Gpus;
 using NTMiner.Mine;
 using NTMiner.Mine;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;

+ 2 - 1
src/NTMinerClient/Core/Kernels/KernelExtensions.cs

@@ -1,4 +1,5 @@
-using System;
+using NTMiner.Gpus;
+using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.IO;
 using System.IO;
 using System.Linq;
 using System.Linq;

+ 2 - 3
src/NTMinerClient/Core/Profiles/Impl/GpuProfileSet.cs

@@ -1,7 +1,6 @@
-using NTMiner.Core.Gpus;
+using NTMiner.Core.Profile;
+using NTMiner.Gpus;
 using NTMiner.JsonDb;
 using NTMiner.JsonDb;
-using NTMiner.Core.MinerClient;
-using NTMiner.Core.Profile;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.Linq;
 using System.Linq;

+ 2 - 16
src/NTMinerClient/Core/Profiles/MinerProfile.cs

@@ -157,7 +157,7 @@ namespace NTMiner.Core.Profiles {
         public string MinerName {
         public string MinerName {
             get {
             get {
                 if (string.IsNullOrEmpty(_data.MinerName)) {
                 if (string.IsNullOrEmpty(_data.MinerName)) {
-                    _data.MinerName = NTMinerContext.ThisPcName;
+                    _data.MinerName = NTKeyword.GetSafeMinerName(NTMinerContext.ThisPcName);
                 }
                 }
                 return _data.MinerName;
                 return _data.MinerName;
             }
             }
@@ -165,7 +165,7 @@ namespace NTMiner.Core.Profiles {
                 if (string.IsNullOrEmpty(value)) {
                 if (string.IsNullOrEmpty(value)) {
                     value = NTMinerContext.ThisPcName;
                     value = NTMinerContext.ThisPcName;
                 }
                 }
-                value = new string(value.ToCharArray().Where(a => !NTKeyword.InvalidMinerNameChars.Contains(a)).ToArray());
+                value = NTKeyword.GetSafeMinerName(value);
                 _data.MinerName = value;
                 _data.MinerName = value;
             }
             }
         }
         }
@@ -419,13 +419,6 @@ namespace NTMiner.Core.Profiles {
             }
             }
         }
         }
 
 
-        public bool IsNoUi {
-            get => _data.IsNoUi;
-            private set {
-                _data.IsNoUi = value;
-            }
-        }
-
         public bool IsAutoNoUi {
         public bool IsAutoNoUi {
             get => _data.IsAutoNoUi;
             get => _data.IsAutoNoUi;
             private set {
             private set {
@@ -468,13 +461,6 @@ namespace NTMiner.Core.Profiles {
             }
             }
         }
         }
 
 
-        public bool IsAutoStart {
-            get => _data.IsAutoStart;
-            private set {
-                _data.IsAutoStart = value;
-            }
-        }
-
         public bool IsCreateShortcut {
         public bool IsCreateShortcut {
             get => _data.IsCreateShortcut;
             get => _data.IsCreateShortcut;
             private set {
             private set {

+ 1 - 0
src/NTMinerClient/Core/Profiles/MinerProfile.partials.CoinProfileSet.cs

@@ -1,4 +1,5 @@
 using NTMiner.Core.Profile;
 using NTMiner.Core.Profile;
+using NTMiner.Gpus;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
 using System.Linq;
 using System.Linq;

+ 0 - 79
src/NTMinerClient/CpuUtil.cs

@@ -1,79 +0,0 @@
-using OpenHardwareMonitor.Hardware;
-
-namespace NTMiner {
-    public static class CpuUtil {
-        private static readonly object _locker = new object();
-        #region 电脑硬件
-        private static Computer _computer = null;
-        public static Computer Computer {
-            get {
-                if (_computer == null) {
-                    lock (_locker) {
-                        if (_computer == null) {
-                            _computer = new Computer();
-                            _computer.Open();
-                            _computer.CPUEnabled = true;
-                            VirtualRoot.AddEventPath<AppExitEvent>($"程序退出时关闭OpenHardwareMonitor", LogEnum.None,
-                                message => {
-                                    _computer?.Close();
-                                }, typeof(VirtualRoot));
-                        }
-                    }
-                }
-                return _computer;
-            }
-        }
-        #endregion
-
-        public static float GetTemperature() {
-            var computer = Computer;
-            for (int i = 0; i < computer.Hardware.Length; i++) {
-                var hardware = computer.Hardware[i];
-                if (hardware.HardwareType == HardwareType.CPU) {
-                    hardware.Update();
-                    bool isCPUPackageReaded = false;
-                    for (int j = 0; j < hardware.Sensors.Length; j++) {
-                        switch (hardware.Sensors[j].SensorType) {
-                            case SensorType.Voltage:
-                                break;
-                            case SensorType.Clock:
-                                break;
-                            case SensorType.Temperature:
-                                if (!isCPUPackageReaded) {
-                                    if (hardware.Sensors[j].Name == "CPU Package") {
-                                        isCPUPackageReaded = true;
-                                        float? t = hardware.Sensors[j].Value;
-                                        if (t.HasValue) {
-                                            return t.Value;
-                                        }
-                                    }
-                                }
-                                break;
-                            case SensorType.Load:
-                                break;
-                            case SensorType.Fan:
-                                break;
-                            case SensorType.Flow:
-                                break;
-                            case SensorType.Control:
-                                break;
-                            case SensorType.Level:
-                                break;
-                            case SensorType.Factor:
-                                break;
-                            case SensorType.Power:
-                                break;
-                            case SensorType.Data:
-                                break;
-                            case SensorType.SmallData:
-                                break;
-                            default:
-                                break;
-                        }
-                    }
-                }
-            }
-            return 0.0f;
-        }
-    }
-}

+ 1 - 1
src/NTMinerClient/Core/Cpus/ICpuPackage.cs → src/NTMinerClient/Cpus/ICpuPackage.cs

@@ -1,6 +1,6 @@
 using System;
 using System;
 
 
-namespace NTMiner.Core.Cpus {
+namespace NTMiner.Cpus {
     /// <summary>
     /// <summary>
     /// 指的是整个CPU包,而不是单个CPU核。
     /// 指的是整个CPU包,而不是单个CPU核。
     /// </summary>
     /// </summary>

+ 53 - 3
src/NTMinerClient/Core/Cpus/Impl/CpuPackage.cs → src/NTMinerClient/Cpus/Impl/CpuPackage.cs

@@ -1,8 +1,10 @@
 using NTMiner.Core.Profile;
 using NTMiner.Core.Profile;
+using OpenHardwareMonitor.Hardware;
 using System;
 using System;
+using System.Linq;
 using System.Threading.Tasks;
 using System.Threading.Tasks;
 
 
-namespace NTMiner.Core.Cpus.Impl {
+namespace NTMiner.Cpus.Impl {
     public class CpuPackage : ICpuPackage {
     public class CpuPackage : ICpuPackage {
         private readonly IMinerProfile _minerProfile;
         private readonly IMinerProfile _minerProfile;
         public CpuPackage(IMinerProfile minerProfile) {
         public CpuPackage(IMinerProfile minerProfile) {
@@ -14,7 +16,7 @@ namespace NTMiner.Core.Cpus.Impl {
             if (ClientAppType.IsMinerClient) {
             if (ClientAppType.IsMinerClient) {
                 Task.Factory.StartNew(() => {
                 Task.Factory.StartNew(() => {
                     // 注意:第一次GetTemperature请求约需要160毫秒,所以提前在非UI线程做第一次请求。
                     // 注意:第一次GetTemperature请求约需要160毫秒,所以提前在非UI线程做第一次请求。
-                    CpuUtil.GetTemperature();
+                    GetTemperature();
                     VirtualRoot.AddEventPath<Per2SecondEvent>("周期更新CpuAll的状态", LogEnum.None,
                     VirtualRoot.AddEventPath<Per2SecondEvent>("周期更新CpuAll的状态", LogEnum.None,
                         action: message => {
                         action: message => {
                             Task.Factory.StartNew(() => {
                             Task.Factory.StartNew(() => {
@@ -72,7 +74,7 @@ namespace NTMiner.Core.Cpus.Impl {
         private void Update() {
         private void Update() {
             bool isChanged = false;
             bool isChanged = false;
             // 该操作约耗时100毫秒
             // 该操作约耗时100毫秒
-            int temperature = (int)CpuUtil.GetTemperature();
+            int temperature = (int)GetTemperature();
             double performance = Windows.Cpu.Instance.GetCurrentCpuUsage();
             double performance = Windows.Cpu.Instance.GetCurrentCpuUsage();
             if (performance != this.Performance) {
             if (performance != this.Performance) {
                 isChanged = true;
                 isChanged = true;
@@ -102,5 +104,53 @@ namespace NTMiner.Core.Cpus.Impl {
 
 
         public DateTime HighTemperatureOn { get; set; }
         public DateTime HighTemperatureOn { get; set; }
         public DateTime LowTemperatureOn { get; set; }
         public DateTime LowTemperatureOn { get; set; }
+
+        public static float GetTemperature() {
+            var computer = ComputerRoot.Computer;
+            bool isSingleCore = computer.Hardware.Count(a => a.HardwareType == HardwareType.CPU) == 1;
+            for (int i = 0; i < computer.Hardware.Length; i++) {
+                var hardware = computer.Hardware[i];
+                if (hardware.HardwareType == HardwareType.CPU) {
+                    hardware.Update();
+                    for (int j = 0; j < hardware.Sensors.Length; j++) {
+                        switch (hardware.Sensors[j].SensorType) {
+                            case SensorType.Voltage:
+                                break;
+                            case SensorType.Clock:
+                                break;
+                            case SensorType.Temperature:
+                                if (isSingleCore || hardware.Sensors[j].Name == "CPU Package") {
+                                    float? t = hardware.Sensors[j].Value;
+                                    if (t.HasValue) {
+                                        return t.Value;
+                                    }
+                                }
+                                break;
+                            case SensorType.Load:
+                                break;
+                            case SensorType.Fan:
+                                break;
+                            case SensorType.Flow:
+                                break;
+                            case SensorType.Control:
+                                break;
+                            case SensorType.Level:
+                                break;
+                            case SensorType.Factor:
+                                break;
+                            case SensorType.Power:
+                                break;
+                            case SensorType.Data:
+                                break;
+                            case SensorType.SmallData:
+                                break;
+                            default:
+                                break;
+                        }
+                    }
+                }
+            }
+            return 0.0f;
+        }
     }
     }
 }
 }

+ 2 - 2
src/NTMinerClient/Core/Gpus/EmptyGpuSet.cs → src/NTMinerClient/Gpus/EmptyGpuSet.cs

@@ -1,8 +1,8 @@
-using NTMiner.Core.Gpus.Impl;
+using NTMiner.Gpus.Impl;
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
 
 
-namespace NTMiner.Core.Gpus {
+namespace NTMiner.Gpus {
     public class EmptyGpuSet : IGpuSet {
     public class EmptyGpuSet : IGpuSet {
         public static EmptyGpuSet Instance { get; private set; } = new EmptyGpuSet();
         public static EmptyGpuSet Instance { get; private set; } = new EmptyGpuSet();
 
 

+ 3 - 2
src/NTMinerClient/Core/Gpus/GpuSetExtension.cs → src/NTMinerClient/Gpus/GpuSetExtension.cs

@@ -1,7 +1,8 @@
-using System.Collections.Generic;
+using NTMiner.Core;
+using System.Collections.Generic;
 using System.Linq;
 using System.Linq;
 
 
-namespace NTMiner.Core.Gpus {
+namespace NTMiner.Gpus {
     public static class GpuSetExtension {
     public static class GpuSetExtension {
         public static bool GetIsUseDevice(this IGpuSet gpuSet, int gpuIndex) {
         public static bool GetIsUseDevice(this IGpuSet gpuSet, int gpuIndex) {
             if (gpuIndex < 0 || gpuIndex >= gpuSet.Count) {
             if (gpuIndex < 0 || gpuIndex >= gpuSet.Count) {

+ 1 - 1
src/NTMinerClient/Core/Gpus/GpuSetProperty.cs → src/NTMinerClient/Gpus/GpuSetProperty.cs

@@ -1,4 +1,4 @@
-namespace NTMiner.Core.Gpus {
+namespace NTMiner.Gpus {
     public class GpuSetProperty {
     public class GpuSetProperty {
         public const string DRIVER_VERSION = "DriverVersion";
         public const string DRIVER_VERSION = "DriverVersion";
         public GpuSetProperty(string code, string name, object value) {
         public GpuSetProperty(string code, string name, object value) {

+ 1 - 1
src/NTMinerClient/Core/Gpus/GpuSpeedExtension.cs → src/NTMinerClient/Gpus/GpuSpeedExtension.cs

@@ -1,7 +1,7 @@
 using NTMiner.Core.MinerClient;
 using NTMiner.Core.MinerClient;
 using System.Collections.Generic;
 using System.Collections.Generic;
 
 
-namespace NTMiner.Core.Gpus {
+namespace NTMiner.Gpus {
 
 
     public static class GpuSpeedExtension {
     public static class GpuSpeedExtension {
         public static List<IGpuSpeed> GetGpuSpeedHistory(this IGpu gpu) {
         public static List<IGpuSpeed> GetGpuSpeedHistory(this IGpu gpu) {

+ 2 - 2
src/NTMinerClient/Core/Gpus/IGpu.cs → src/NTMinerClient/Gpus/IGpu.cs

@@ -1,6 +1,6 @@
-using NTMiner.Core.MinerClient;
+using NTMiner.Core;
 
 
-namespace NTMiner.Core.Gpus {
+namespace NTMiner.Gpus {
     public interface IGpu : IGpuStaticData, IOverClockInput {
     public interface IGpu : IGpuStaticData, IOverClockInput {
         int Temperature { get; }
         int Temperature { get; }
         uint FanSpeed { get; set; }
         uint FanSpeed { get; set; }

Beberapa file tidak ditampilkan karena terlalu banyak file yang berubah dalam diff ini