mirror of
https://github.com/Maassoft/ColorControl.git
synced 2026-10-21 16:12:18 -05:00
fix screensaver issue, add eye comfort mode, improve elevated process and add priority/affinity settings to game launcher
This commit is contained in:
1 parent
84cb7e6446
commit
a8d41f67c9
18 files changed
+743
-106
No files matched your search
@@ -18,8 +18,8 @@
|
||||
<PublisherName>Maassoft</PublisherName>
|
||||
<Company>Maassoft</Company>
|
||||
<ApplicationRevision>0</ApplicationRevision>
|
||||
<ApplicationVersion>7.2.0.0</ApplicationVersion>
|
||||
<Version>7.2.0.0</Version>
|
||||
<ApplicationVersion>7.3.0.0</ApplicationVersion>
|
||||
<Version>7.3.0.0</Version>
|
||||
<UseApplicationTrust>false</UseApplicationTrust>
|
||||
<PublishWizardCompleted>true</PublishWizardCompleted>
|
||||
<BootstrapperEnabled>false</BootstrapperEnabled>
|
||||
@@ -89,8 +89,8 @@
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Newtonsoft.Json" Version="13.0.1" />
|
||||
<PackageReference Include="NLog" Version="5.0.1" />
|
||||
<PackageReference Include="NStandard" Version="0.9.13" />
|
||||
<PackageReference Include="NLog" Version="5.0.2" />
|
||||
<PackageReference Include="NStandard" Version="0.10.0.1" />
|
||||
<PackageReference Include="NvAPIWrapper.Net" Version="0.8.1.101" />
|
||||
<PackageReference Include="NWin32" Version="1.2.3" />
|
||||
<PackageReference Include="TaskScheduler" Version="2.10.1" />
|
||||
|
||||
+117
-65
@@ -1,10 +1,10 @@
|
||||
using ColorControl.Forms;
|
||||
using ColorControl.Native;
|
||||
using Microsoft.Win32;
|
||||
using Microsoft.Win32.TaskScheduler;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using NWin32;
|
||||
using NWin32.NativeTypes;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel;
|
||||
@@ -36,52 +36,14 @@ namespace ColorControl.Common
|
||||
Win = 8
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential, Pack = 4)]
|
||||
internal struct POWERBROADCAST_SETTING
|
||||
{
|
||||
public Guid PowerSetting;
|
||||
public uint DataLength;
|
||||
public byte Data;
|
||||
}
|
||||
|
||||
public const int WM_BRINGTOFRONT = NativeConstants.WM_USER + 1;
|
||||
|
||||
public const int ENUM_CURRENT_SETTINGS = -1;
|
||||
public const int ENUM_REGISTRY_SETTINGS = -2;
|
||||
|
||||
public static string PKEY_PNPX_IpAddress = "{656a3bb3-ecc0-43fd-8477-4ae0404a96cd} 12297";
|
||||
public static string PKEY_PNPX_PhysicalAddress = "{656a3bb3-ecc0-43fd-8477-4ae0404a96cd} 12294";
|
||||
public static Guid GUID_CONSOLE_DISPLAY_STATE = Guid.Parse("6FE69556-704A-47A0-8F24-C28D936FDA47");
|
||||
public static int PBT_POWERSETTINGCHANGE = 32787;
|
||||
|
||||
public delegate void PCREATE_PROCESS_NOTIFY_ROUTINE(IntPtr ParentId, IntPtr ProcessId, bool Create);
|
||||
|
||||
public static bool ConsoleOpened { get; private set; }
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
public static extern bool RegisterHotKey(IntPtr hWnd, int id, int fsModifiers, int vlc);
|
||||
[DllImport("user32.dll")]
|
||||
public static extern bool UnregisterHotKey(IntPtr hWnd, int id);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
public static extern bool EnumDisplaySettingsA(string deviceName, int modeNum, out DEVMODEA devMode);
|
||||
|
||||
[DllImport("kernel32.dll", SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool AllocConsole();
|
||||
|
||||
[DllImport("kernel32.dll", SetLastError = true, ExactSpelling = true)]
|
||||
private static extern bool AttachConsole(int processId);
|
||||
|
||||
[DllImport("kernel32.dll", SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool FreeConsole();
|
||||
|
||||
[DllImport(@"User32", SetLastError = true)]
|
||||
public static extern IntPtr RegisterPowerSettingNotification(IntPtr hRecipient, ref Guid PowerSettingGuid, Int32 Flags);
|
||||
|
||||
[DllImport("User32.dll", SetLastError = true)]
|
||||
public static extern bool UnregisterPowerSettingNotification(IntPtr hWnd);
|
||||
public static bool UseDedicatedElevatedProcess = false;
|
||||
|
||||
private static readonly NLog.Logger Logger = NLog.LogManager.GetCurrentClassLogger();
|
||||
private static bool WinKeyDown = false;
|
||||
@@ -208,8 +170,24 @@ namespace ColorControl.Common
|
||||
return keys;
|
||||
}
|
||||
|
||||
internal static bool ExecuteElevated(string args)
|
||||
static bool IsAdministrator()
|
||||
{
|
||||
var identity = WindowsIdentity.GetCurrent();
|
||||
var principal = new WindowsPrincipal(identity);
|
||||
return principal.IsInRole(WindowsBuiltInRole.Administrator);
|
||||
}
|
||||
|
||||
internal static int ExecuteElevated(string args, bool wait = true, bool skipDedicated = false)
|
||||
{
|
||||
if (UseDedicatedElevatedProcess && !skipDedicated)
|
||||
{
|
||||
CheckElevatedProcess();
|
||||
|
||||
WinApi.CopyData.Send(ElevatedProcessWindowHandle, 1, args);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
var info = new ProcessStartInfo(Process.GetCurrentProcess().MainModule.FileName, args)
|
||||
{
|
||||
Verb = "runas", // indicates to elevate privileges
|
||||
@@ -224,14 +202,35 @@ namespace ColorControl.Common
|
||||
try
|
||||
{
|
||||
process.Start();
|
||||
process.WaitForExit(); // sleep calling process thread until evoked process exit
|
||||
return true;
|
||||
|
||||
if (wait)
|
||||
{
|
||||
process.WaitForExit(); // sleep calling process thread until evoked process exit
|
||||
}
|
||||
|
||||
return process.Id;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Logger.Error("ExecuteElevated: " + e.Message);
|
||||
}
|
||||
return false;
|
||||
return 0;
|
||||
}
|
||||
|
||||
private static IntPtr ElevatedProcessWindowHandle = IntPtr.Zero;
|
||||
|
||||
internal static void CheckElevatedProcess()
|
||||
{
|
||||
ElevatedProcessWindowHandle = NativeMethods.FindWindowW(null, "ElevatedForm");
|
||||
|
||||
if (ElevatedProcessWindowHandle == IntPtr.Zero)
|
||||
{
|
||||
ExecuteElevated(StartUpParams.StartElevatedParam, false, true);
|
||||
|
||||
Thread.Sleep(500);
|
||||
|
||||
ElevatedProcessWindowHandle = NativeMethods.FindWindowW(null, "ElevatedForm");
|
||||
}
|
||||
}
|
||||
|
||||
internal static bool IsChromeFixInstalled()
|
||||
@@ -273,21 +272,6 @@ namespace ColorControl.Common
|
||||
return key != null;
|
||||
}
|
||||
|
||||
internal static void GetRegistryKeyValue(string keyname, string valueName, bool deepSearch = false)
|
||||
{
|
||||
var key = Registry.LocalMachine.OpenSubKey(keyname);
|
||||
|
||||
foreach (var subKeyName in key.GetSubKeyNames())
|
||||
{
|
||||
var subKey = key.OpenSubKey(subKeyName);
|
||||
if (subKey.GetValueNames().Contains(valueName))
|
||||
{
|
||||
Thread.Sleep(0);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
internal static bool UpdateShortcut(string path, string arguments, bool removeArguments = false)
|
||||
{
|
||||
if (File.Exists(path))
|
||||
@@ -468,6 +452,8 @@ namespace ColorControl.Common
|
||||
{
|
||||
return descriptionAttribute.Description;
|
||||
}
|
||||
|
||||
return enumName;
|
||||
}
|
||||
|
||||
return null; // could also return string.Empty
|
||||
@@ -510,6 +496,12 @@ namespace ColorControl.Common
|
||||
|
||||
public static void RegisterTask(string taskName, bool enabled)
|
||||
{
|
||||
if (!IsAdministrator())
|
||||
{
|
||||
ExecuteElevated(enabled ? StartUpParams.EnableAutoStartParam : StartUpParams.DisableAutoStartParam);
|
||||
return;
|
||||
}
|
||||
|
||||
var file = Process.GetCurrentProcess().MainModule.FileName;
|
||||
var directory = Path.GetDirectoryName(file);
|
||||
|
||||
@@ -569,13 +561,13 @@ namespace ColorControl.Common
|
||||
{
|
||||
if (clear)
|
||||
{
|
||||
UnregisterHotKey(handle, id);
|
||||
WinApi.UnregisterHotKey(handle, id);
|
||||
}
|
||||
|
||||
if (!string.IsNullOrEmpty(shortcut))
|
||||
{
|
||||
var (mods, key) = ParseShortcut(shortcut);
|
||||
var result = RegisterHotKey(handle, id, mods, key);
|
||||
var result = WinApi.RegisterHotKey(handle, id, mods, key);
|
||||
if (!result)
|
||||
{
|
||||
var errorMessage = new Win32Exception(Marshal.GetLastWin32Error()).Message;
|
||||
@@ -588,6 +580,13 @@ namespace ColorControl.Common
|
||||
return true;
|
||||
}
|
||||
|
||||
public static void CheckWin32Error(string message)
|
||||
{
|
||||
var errorMessage = new Win32Exception(Marshal.GetLastWin32Error()).Message;
|
||||
|
||||
throw new Exception($"{message}: {errorMessage}");
|
||||
}
|
||||
|
||||
public static string FormatKeyboardShortcut(KeyEventArgs keyEvent)
|
||||
{
|
||||
var pressedModifiers = keyEvent.Modifiers;
|
||||
@@ -655,9 +654,9 @@ namespace ColorControl.Common
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!AttachConsole(-1))
|
||||
if (!WinApi.AttachConsole(-1))
|
||||
{
|
||||
AllocConsole();
|
||||
WinApi.AllocConsole();
|
||||
return true;
|
||||
}
|
||||
ConsoleOpened = true;
|
||||
@@ -673,7 +672,7 @@ namespace ColorControl.Common
|
||||
}
|
||||
|
||||
SendKeys.SendWait("{ENTER}");
|
||||
var result = FreeConsole();
|
||||
var result = WinApi.FreeConsole();
|
||||
|
||||
return result;
|
||||
}
|
||||
@@ -692,7 +691,7 @@ namespace ColorControl.Common
|
||||
return null;
|
||||
}
|
||||
|
||||
public static void StartProcess(string fileName, string arguments = null, bool hidden = false, bool wait = false, bool setWorkingDir = false, bool elevate = false)
|
||||
public static void StartProcess(string fileName, string arguments = null, bool hidden = false, bool wait = false, bool setWorkingDir = false, bool elevate = false, uint affinityMask = 0, uint priorityClass = 0)
|
||||
{
|
||||
var process = Process.Start(new ProcessStartInfo(fileName, arguments)
|
||||
{
|
||||
@@ -701,12 +700,65 @@ namespace ColorControl.Common
|
||||
WindowStyle = hidden ? ProcessWindowStyle.Hidden : ProcessWindowStyle.Normal,
|
||||
WorkingDirectory = setWorkingDir ? Path.GetDirectoryName(fileName) : null
|
||||
});
|
||||
|
||||
if (affinityMask > 0)
|
||||
{
|
||||
SetProcessAffinity(process.Id, affinityMask);
|
||||
}
|
||||
|
||||
if (priorityClass > 0 && priorityClass != NativeConstants.NORMAL_PRIORITY_CLASS)
|
||||
{
|
||||
SetProcessPriority(process.Id, priorityClass);
|
||||
}
|
||||
|
||||
if (wait)
|
||||
{
|
||||
process.WaitForExit();
|
||||
}
|
||||
}
|
||||
|
||||
internal static void SetProcessAffinity(int processId, uint affinityMask)
|
||||
{
|
||||
if (!IsAdministrator())
|
||||
{
|
||||
ExecuteElevated($"{StartUpParams.SetProcessAffinityParam} {processId} {affinityMask}");
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
var hProcess = NativeMethods.OpenProcess(NativeConstants.PROCESS_ALL_ACCESS, false, (uint)processId);
|
||||
|
||||
if (hProcess == IntPtr.Zero)
|
||||
{
|
||||
CheckWin32Error($"Unable to set processor affinity on process {processId}");
|
||||
}
|
||||
|
||||
NativeMethods.SetProcessAffinityMask(hProcess, affinityMask);
|
||||
|
||||
//var AffinityMask = (long)process.ProcessorAffinity;
|
||||
//AffinityMask &= 0x000F; // use only any of the first 4 available processors
|
||||
//process.ProcessorAffinity = (IntPtr)AffinityMask;
|
||||
}
|
||||
|
||||
internal static void SetProcessPriority(int processId, uint priorityClass)
|
||||
{
|
||||
if (!IsAdministrator())
|
||||
{
|
||||
ExecuteElevated($"{StartUpParams.SetProcessPriorityParam} {processId} {priorityClass}");
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
var hProcess = NativeMethods.OpenProcess(NativeConstants.PROCESS_ALL_ACCESS, false, (uint)processId);
|
||||
|
||||
if (hProcess == IntPtr.Zero)
|
||||
{
|
||||
CheckWin32Error($"Unable to set process priority on process {processId}");
|
||||
}
|
||||
|
||||
NativeMethods.SetPriorityClass(hProcess, priorityClass);
|
||||
}
|
||||
|
||||
public static string GetResourceFile(string resourceName)
|
||||
{
|
||||
resourceName = "ColorControl.Resources." + resourceName;
|
||||
|
||||
@@ -30,6 +30,7 @@ namespace ColorControl
|
||||
public string AmdQuickAccessShortcut { get; set; }
|
||||
public string LgQuickAccessShortcut { get; set; }
|
||||
public string GameQuickAccessShortcut { get; set; }
|
||||
public bool UseDedicatedElevatedProcess { get; set; }
|
||||
|
||||
public Config()
|
||||
{
|
||||
@@ -41,6 +42,7 @@ namespace ColorControl
|
||||
CheckForUpdates = true;
|
||||
FixChromeFonts = false;
|
||||
UseGdiScaling = true;
|
||||
UseDedicatedElevatedProcess = false;
|
||||
LgPresetsSortState = new ListViewSortState();
|
||||
NvPresetsSortState = new ListViewSortState();
|
||||
AmdPresetsSortState = new ListViewSortState();
|
||||
|
||||
+46
@@ -0,0 +1,46 @@
|
||||
namespace ColorControl.Forms
|
||||
{
|
||||
partial class ElevatedForm
|
||||
{
|
||||
/// <summary>
|
||||
/// Required designer variable.
|
||||
/// </summary>
|
||||
private System.ComponentModel.IContainer components = null;
|
||||
|
||||
/// <summary>
|
||||
/// Clean up any resources being used.
|
||||
/// </summary>
|
||||
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
if (disposing && (components != null))
|
||||
{
|
||||
components.Dispose();
|
||||
}
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
#region Windows Form Designer generated code
|
||||
|
||||
/// <summary>
|
||||
/// Required method for Designer support - do not modify
|
||||
/// the contents of this method with the code editor.
|
||||
/// </summary>
|
||||
private void InitializeComponent()
|
||||
{
|
||||
this.SuspendLayout();
|
||||
//
|
||||
// ElevatedForm
|
||||
//
|
||||
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
|
||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||
this.ClientSize = new System.Drawing.Size(251, 124);
|
||||
this.Name = "ElevatedForm";
|
||||
this.Text = "ElevatedForm";
|
||||
this.ResumeLayout(false);
|
||||
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,93 @@
|
||||
using ColorControl.Native;
|
||||
using NWin32;
|
||||
using System;
|
||||
using System.Drawing;
|
||||
using System.IO;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using System.Windows.Forms;
|
||||
|
||||
namespace ColorControl.Forms
|
||||
{
|
||||
public partial class ElevatedForm : Form
|
||||
{
|
||||
public ElevatedForm()
|
||||
{
|
||||
File.Delete("d:\\Msg.txt");
|
||||
InitializeComponent();
|
||||
|
||||
FormBorderStyle = FormBorderStyle.None;
|
||||
ShowInTaskbar = false;
|
||||
Load += ElevatedForm_Load;
|
||||
Shown += ElevatedForm_Shown;
|
||||
|
||||
var filterStatus = new WinApi.CHANGEFILTERSTRUCT();
|
||||
filterStatus.size = (uint)Marshal.SizeOf(filterStatus);
|
||||
filterStatus.info = 0;
|
||||
|
||||
var result = WinApi.ChangeWindowMessageFilterEx(Handle, NativeConstants.WM_COPYDATA, WinApi.ChangeWindowMessageFilterExAction.Allow, ref filterStatus);
|
||||
//File.AppendAllLines("d:\\Msg.txt", new[] { "ChangeWindowMessageFilterEx result: " + result });
|
||||
|
||||
Task.Run(() => CheckMutexAsync());
|
||||
}
|
||||
|
||||
private void ElevatedForm_Shown(object sender, EventArgs e)
|
||||
{
|
||||
Hide();
|
||||
}
|
||||
|
||||
protected void ElevatedForm_Load(object sender, EventArgs e)
|
||||
{
|
||||
Size = new Size(0, 0);
|
||||
}
|
||||
|
||||
protected override void WndProc(ref Message m)
|
||||
{
|
||||
if (m.Msg == NativeConstants.WM_COPYDATA)
|
||||
{
|
||||
var container = (WinApi.COPYDATASTRUCT)m.GetLParam(typeof(WinApi.COPYDATASTRUCT));
|
||||
var message = Marshal.PtrToStringAnsi(container.lpData);
|
||||
|
||||
File.AppendAllLines("d:\\Msg.txt", new[] { "Message received: " + message });
|
||||
|
||||
HandleMessage(message);
|
||||
|
||||
//Utils.StartProcess("notepad.exe");
|
||||
|
||||
//BackColor = Color.Red;
|
||||
//Text = "AHA!";
|
||||
//MessageForms.WarningOk("Received!");
|
||||
}
|
||||
|
||||
base.WndProc(ref m);
|
||||
}
|
||||
|
||||
private void HandleMessage(string message)
|
||||
{
|
||||
var args = message.Split(' ');
|
||||
|
||||
var startUpParams = StartUpParams.Parse(args);
|
||||
|
||||
Program.HandleStartupParams(startUpParams, null);
|
||||
}
|
||||
|
||||
private void CheckMutexAsync()
|
||||
{
|
||||
var mutex = new Mutex(false, Program.MutexId, out var created);
|
||||
|
||||
File.AppendAllLines("d:\\Msg.txt", new[] { "Mutex created: " + created });
|
||||
|
||||
try
|
||||
{
|
||||
mutex.WaitOne();
|
||||
File.AppendAllLines("d:\\Msg.txt", new[] { "Mutex released?" });
|
||||
}
|
||||
catch (AbandonedMutexException)
|
||||
{
|
||||
File.AppendAllLines("d:\\Msg.txt", new[] { "Mutex abandoned" });
|
||||
}
|
||||
BeginInvoke(() => Application.Exit());
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,60 @@
|
||||
<root>
|
||||
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
|
||||
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
|
||||
<xsd:element name="root" msdata:IsDataSet="true">
|
||||
<xsd:complexType>
|
||||
<xsd:choice maxOccurs="unbounded">
|
||||
<xsd:element name="metadata">
|
||||
<xsd:complexType>
|
||||
<xsd:sequence>
|
||||
<xsd:element name="value" type="xsd:string" minOccurs="0" />
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="name" use="required" type="xsd:string" />
|
||||
<xsd:attribute name="type" type="xsd:string" />
|
||||
<xsd:attribute name="mimetype" type="xsd:string" />
|
||||
<xsd:attribute ref="xml:space" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
<xsd:element name="assembly">
|
||||
<xsd:complexType>
|
||||
<xsd:attribute name="alias" type="xsd:string" />
|
||||
<xsd:attribute name="name" type="xsd:string" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
<xsd:element name="data">
|
||||
<xsd:complexType>
|
||||
<xsd:sequence>
|
||||
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
|
||||
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
|
||||
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
|
||||
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
|
||||
<xsd:attribute ref="xml:space" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
<xsd:element name="resheader">
|
||||
<xsd:complexType>
|
||||
<xsd:sequence>
|
||||
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="name" type="xsd:string" use="required" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
</xsd:choice>
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
</xsd:schema>
|
||||
<resheader name="resmimetype">
|
||||
<value>text/microsoft-resx</value>
|
||||
</resheader>
|
||||
<resheader name="version">
|
||||
<value>2.0</value>
|
||||
</resheader>
|
||||
<resheader name="reader">
|
||||
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
||||
</resheader>
|
||||
<resheader name="writer">
|
||||
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
||||
</resheader>
|
||||
</root>
|
||||
@@ -177,7 +177,7 @@ namespace ColorControl.Forms
|
||||
if (field.Values != null && field.Values.Any())
|
||||
{
|
||||
comboBox.Items.AddRange(field.Values.ToArray());
|
||||
comboBox.SelectedIndex = 0;
|
||||
comboBox.SelectedIndex = field.Value is string strValue ? comboBox.Items.IndexOf(strValue) : 0;
|
||||
}
|
||||
|
||||
control = comboBox;
|
||||
@@ -188,8 +188,9 @@ namespace ColorControl.Forms
|
||||
{
|
||||
Left = 40,
|
||||
Top = top,
|
||||
Width = 200,
|
||||
Height = 100
|
||||
Width = 400,
|
||||
Height = 100,
|
||||
MultiColumn = true
|
||||
};
|
||||
|
||||
top += 80;
|
||||
@@ -197,7 +198,7 @@ namespace ColorControl.Forms
|
||||
|
||||
if (field.Values != null && field.Values.Any())
|
||||
{
|
||||
var compoundValue = (int)field.Value;
|
||||
var compoundValue = field.Value is int ? (int)field.Value : (int)((uint)field.Value);
|
||||
var enumValue = 1;
|
||||
foreach (var value in field.Values)
|
||||
{
|
||||
|
||||
Generated
+78
-15
@@ -79,6 +79,7 @@
|
||||
this.btnApply = new System.Windows.Forms.Button();
|
||||
this.lvNvPresets = new System.Windows.Forms.ListView();
|
||||
this.tabAMD = new System.Windows.Forms.TabPage();
|
||||
this.btnAmdSettings = new System.Windows.Forms.Button();
|
||||
this.chkAmdQuickAccess = new System.Windows.Forms.CheckBox();
|
||||
this.lblAmdPresetName = new System.Windows.Forms.Label();
|
||||
this.edtAmdPresetName = new System.Windows.Forms.TextBox();
|
||||
@@ -170,6 +171,10 @@
|
||||
this.clbLgPower = new System.Windows.Forms.CheckedListBox();
|
||||
this.lblLgError = new System.Windows.Forms.Label();
|
||||
this.tabGameLauncher = new System.Windows.Forms.TabPage();
|
||||
this.btnGameOptions = new System.Windows.Forms.Button();
|
||||
this.mnuGameOptions = new System.Windows.Forms.ContextMenuStrip(this.components);
|
||||
this.miGameProcessorAffinity = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.miGameProcessPriority = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.chkGameQuickAccess = new System.Windows.Forms.CheckBox();
|
||||
this.btnGameSettings = new System.Windows.Forms.Button();
|
||||
this.mnuGameActions = new System.Windows.Forms.ContextMenuStrip(this.components);
|
||||
@@ -246,7 +251,7 @@
|
||||
this.mnuNvSettings = new System.Windows.Forms.ContextMenuStrip(this.components);
|
||||
this.miNvProfileInspector = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.miNvSettings = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.btnAmdSettings = new System.Windows.Forms.Button();
|
||||
this.chkOptionsDedicatedElevatedProcess = new System.Windows.Forms.CheckBox();
|
||||
this.tcMain.SuspendLayout();
|
||||
this.tabNVIDIA.SuspendLayout();
|
||||
this.mnuNvPresets.SuspendLayout();
|
||||
@@ -259,6 +264,7 @@
|
||||
this.mnuLgExpert.SuspendLayout();
|
||||
this.mnuLgButtons.SuspendLayout();
|
||||
this.tabGameLauncher.SuspendLayout();
|
||||
this.mnuGameOptions.SuspendLayout();
|
||||
this.mnuGameActions.SuspendLayout();
|
||||
this.mnuGameAddStep.SuspendLayout();
|
||||
this.tabOptions.SuspendLayout();
|
||||
@@ -794,6 +800,18 @@
|
||||
this.tabAMD.Text = "AMD controller";
|
||||
this.tabAMD.UseVisualStyleBackColor = true;
|
||||
//
|
||||
// btnAmdSettings
|
||||
//
|
||||
this.btnAmdSettings.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
|
||||
this.btnAmdSettings.Location = new System.Drawing.Point(1017, 429);
|
||||
this.btnAmdSettings.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.btnAmdSettings.Name = "btnAmdSettings";
|
||||
this.btnAmdSettings.Size = new System.Drawing.Size(88, 27);
|
||||
this.btnAmdSettings.TabIndex = 60;
|
||||
this.btnAmdSettings.Text = "Settings...";
|
||||
this.btnAmdSettings.UseVisualStyleBackColor = true;
|
||||
this.btnAmdSettings.Click += new System.EventHandler(this.btnAmdSettings_Click);
|
||||
//
|
||||
// chkAmdQuickAccess
|
||||
//
|
||||
this.chkAmdQuickAccess.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
|
||||
@@ -1827,6 +1845,7 @@
|
||||
//
|
||||
// tabGameLauncher
|
||||
//
|
||||
this.tabGameLauncher.Controls.Add(this.btnGameOptions);
|
||||
this.tabGameLauncher.Controls.Add(this.chkGameQuickAccess);
|
||||
this.tabGameLauncher.Controls.Add(this.btnGameSettings);
|
||||
this.tabGameLauncher.Controls.Add(this.chkGameRunAsAdmin);
|
||||
@@ -1854,6 +1873,43 @@
|
||||
this.tabGameLauncher.Text = "Game Launcher";
|
||||
this.tabGameLauncher.UseVisualStyleBackColor = true;
|
||||
//
|
||||
// btnGameOptions
|
||||
//
|
||||
this.btnGameOptions.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
|
||||
this.btnGameOptions.ContextMenuStrip = this.mnuGameOptions;
|
||||
this.btnGameOptions.Enabled = false;
|
||||
this.btnGameOptions.Location = new System.Drawing.Point(785, 439);
|
||||
this.btnGameOptions.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.btnGameOptions.Name = "btnGameOptions";
|
||||
this.btnGameOptions.Size = new System.Drawing.Size(88, 27);
|
||||
this.btnGameOptions.TabIndex = 45;
|
||||
this.btnGameOptions.Text = "Options...";
|
||||
this.btnGameOptions.UseVisualStyleBackColor = true;
|
||||
this.btnGameOptions.Click += new System.EventHandler(this.btnGameOptions_Click);
|
||||
//
|
||||
// mnuGameOptions
|
||||
//
|
||||
this.mnuGameOptions.ImageScalingSize = new System.Drawing.Size(20, 20);
|
||||
this.mnuGameOptions.Items.AddRange(new System.Windows.Forms.ToolStripItem[] {
|
||||
this.miGameProcessorAffinity,
|
||||
this.miGameProcessPriority});
|
||||
this.mnuGameOptions.Name = "mnuLgButtons";
|
||||
this.mnuGameOptions.Size = new System.Drawing.Size(166, 48);
|
||||
//
|
||||
// miGameProcessorAffinity
|
||||
//
|
||||
this.miGameProcessorAffinity.Name = "miGameProcessorAffinity";
|
||||
this.miGameProcessorAffinity.Size = new System.Drawing.Size(165, 22);
|
||||
this.miGameProcessorAffinity.Text = "Processor affinity";
|
||||
this.miGameProcessorAffinity.Click += new System.EventHandler(this.btnGameProcessAffinity_Click);
|
||||
//
|
||||
// miGameProcessPriority
|
||||
//
|
||||
this.miGameProcessPriority.Name = "miGameProcessPriority";
|
||||
this.miGameProcessPriority.Size = new System.Drawing.Size(165, 22);
|
||||
this.miGameProcessPriority.Text = "Process priority";
|
||||
this.miGameProcessPriority.Click += new System.EventHandler(this.miGameProcessPriority_Click);
|
||||
//
|
||||
// chkGameQuickAccess
|
||||
//
|
||||
this.chkGameQuickAccess.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
|
||||
@@ -2522,6 +2578,7 @@
|
||||
//
|
||||
// grpGeneralOptions
|
||||
//
|
||||
this.grpGeneralOptions.Controls.Add(this.chkOptionsDedicatedElevatedProcess);
|
||||
this.grpGeneralOptions.Controls.Add(this.chkGdiScaling);
|
||||
this.grpGeneralOptions.Controls.Add(this.chkCheckForUpdates);
|
||||
this.grpGeneralOptions.Controls.Add(this.chkMinimizeToSystemTray);
|
||||
@@ -2540,7 +2597,7 @@
|
||||
// chkGdiScaling
|
||||
//
|
||||
this.chkGdiScaling.AutoSize = true;
|
||||
this.chkGdiScaling.Location = new System.Drawing.Point(238, 75);
|
||||
this.chkGdiScaling.Location = new System.Drawing.Point(238, 72);
|
||||
this.chkGdiScaling.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.chkGdiScaling.Name = "chkGdiScaling";
|
||||
this.chkGdiScaling.Size = new System.Drawing.Size(197, 19);
|
||||
@@ -2552,7 +2609,7 @@
|
||||
// chkCheckForUpdates
|
||||
//
|
||||
this.chkCheckForUpdates.AutoSize = true;
|
||||
this.chkCheckForUpdates.Location = new System.Drawing.Point(238, 48);
|
||||
this.chkCheckForUpdates.Location = new System.Drawing.Point(238, 47);
|
||||
this.chkCheckForUpdates.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.chkCheckForUpdates.Name = "chkCheckForUpdates";
|
||||
this.chkCheckForUpdates.Size = new System.Drawing.Size(197, 19);
|
||||
@@ -2576,7 +2633,7 @@
|
||||
// chkMinimizeOnClose
|
||||
//
|
||||
this.chkMinimizeOnClose.AutoSize = true;
|
||||
this.chkMinimizeOnClose.Location = new System.Drawing.Point(7, 75);
|
||||
this.chkMinimizeOnClose.Location = new System.Drawing.Point(7, 72);
|
||||
this.chkMinimizeOnClose.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.chkMinimizeOnClose.Name = "chkMinimizeOnClose";
|
||||
this.chkMinimizeOnClose.Size = new System.Drawing.Size(122, 19);
|
||||
@@ -2588,7 +2645,7 @@
|
||||
// chkStartMinimized
|
||||
//
|
||||
this.chkStartMinimized.AutoSize = true;
|
||||
this.chkStartMinimized.Location = new System.Drawing.Point(7, 48);
|
||||
this.chkStartMinimized.Location = new System.Drawing.Point(7, 47);
|
||||
this.chkStartMinimized.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.chkStartMinimized.Name = "chkStartMinimized";
|
||||
this.chkStartMinimized.Size = new System.Drawing.Size(109, 19);
|
||||
@@ -2767,17 +2824,17 @@
|
||||
this.miNvSettings.Text = "Settings";
|
||||
this.miNvSettings.Click += new System.EventHandler(this.miNvSettings_Click);
|
||||
//
|
||||
// btnAmdSettings
|
||||
// chkOptionsDedicatedElevatedProcess
|
||||
//
|
||||
this.btnAmdSettings.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
|
||||
this.btnAmdSettings.Location = new System.Drawing.Point(1017, 429);
|
||||
this.btnAmdSettings.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.btnAmdSettings.Name = "btnAmdSettings";
|
||||
this.btnAmdSettings.Size = new System.Drawing.Size(88, 27);
|
||||
this.btnAmdSettings.TabIndex = 60;
|
||||
this.btnAmdSettings.Text = "Settings...";
|
||||
this.btnAmdSettings.UseVisualStyleBackColor = true;
|
||||
this.btnAmdSettings.Click += new System.EventHandler(this.btnAmdSettings_Click);
|
||||
this.chkOptionsDedicatedElevatedProcess.AutoSize = true;
|
||||
this.chkOptionsDedicatedElevatedProcess.Location = new System.Drawing.Point(7, 97);
|
||||
this.chkOptionsDedicatedElevatedProcess.Margin = new System.Windows.Forms.Padding(4, 3, 4, 3);
|
||||
this.chkOptionsDedicatedElevatedProcess.Name = "chkOptionsDedicatedElevatedProcess";
|
||||
this.chkOptionsDedicatedElevatedProcess.Size = new System.Drawing.Size(190, 19);
|
||||
this.chkOptionsDedicatedElevatedProcess.TabIndex = 8;
|
||||
this.chkOptionsDedicatedElevatedProcess.Text = "Use dedicated elevated process";
|
||||
this.chkOptionsDedicatedElevatedProcess.UseVisualStyleBackColor = true;
|
||||
this.chkOptionsDedicatedElevatedProcess.CheckedChanged += new System.EventHandler(this.chkOptionsDedicatedElevatedProcess_CheckedChanged);
|
||||
//
|
||||
// MainForm
|
||||
//
|
||||
@@ -2815,6 +2872,7 @@
|
||||
this.mnuLgButtons.ResumeLayout(false);
|
||||
this.tabGameLauncher.ResumeLayout(false);
|
||||
this.tabGameLauncher.PerformLayout();
|
||||
this.mnuGameOptions.ResumeLayout(false);
|
||||
this.mnuGameActions.ResumeLayout(false);
|
||||
this.mnuGameAddStep.ResumeLayout(false);
|
||||
this.tabOptions.ResumeLayout(false);
|
||||
@@ -3062,6 +3120,11 @@
|
||||
private System.Windows.Forms.ToolStripMenuItem miNvSettings;
|
||||
private System.Windows.Forms.CheckBox chkAmdQuickAccess;
|
||||
private System.Windows.Forms.Button btnAmdSettings;
|
||||
private System.Windows.Forms.Button btnGameOptions;
|
||||
private System.Windows.Forms.ContextMenuStrip mnuGameOptions;
|
||||
private System.Windows.Forms.ToolStripMenuItem miGameProcessorAffinity;
|
||||
private System.Windows.Forms.ToolStripMenuItem miGameProcessPriority;
|
||||
private System.Windows.Forms.CheckBox chkOptionsDedicatedElevatedProcess;
|
||||
}
|
||||
}
|
||||
|
||||
+95
-10
@@ -1,6 +1,7 @@
|
||||
using ATI.ADL;
|
||||
using ColorControl.Common;
|
||||
using ColorControl.Forms;
|
||||
using ColorControl.Native;
|
||||
using ColorControl.Services.AMD;
|
||||
using ColorControl.Services.Common;
|
||||
using ColorControl.Services.GameLauncher;
|
||||
@@ -147,7 +148,7 @@ namespace ColorControl
|
||||
InitInfo();
|
||||
|
||||
UserSessionInfo.Install();
|
||||
_screenStateNotify = Utils.RegisterPowerSettingNotification(Handle, ref Utils.GUID_CONSOLE_DISPLAY_STATE, 0);
|
||||
_screenStateNotify = WinApi.RegisterPowerSettingNotification(Handle, ref Utils.GUID_CONSOLE_DISPLAY_STATE, 0);
|
||||
|
||||
//Scale(new SizeF(1.25F, 1.25F));
|
||||
|
||||
@@ -716,9 +717,9 @@ namespace ColorControl
|
||||
}
|
||||
else if (m.Msg == NativeConstants.WM_POWERBROADCAST)
|
||||
{
|
||||
if (m.WParam.ToInt32() == Utils.PBT_POWERSETTINGCHANGE)
|
||||
if (m.WParam.ToInt32() == WinApi.PBT_POWERSETTINGCHANGE)
|
||||
{
|
||||
var ps = Marshal.PtrToStructure<Utils.POWERBROADCAST_SETTING>(m.LParam);
|
||||
var ps = Marshal.PtrToStructure<WinApi.POWERBROADCAST_SETTING>(m.LParam);
|
||||
|
||||
Logger.Debug($"PBT_POWERSETTINGCHANGE: {ps.Data}");
|
||||
|
||||
@@ -783,7 +784,7 @@ namespace ColorControl
|
||||
|
||||
if (_screenStateNotify != IntPtr.Zero)
|
||||
{
|
||||
Utils.UnregisterPowerSettingNotification(_screenStateNotify);
|
||||
WinApi.UnregisterPowerSettingNotification(_screenStateNotify);
|
||||
_screenStateNotify = IntPtr.Zero;
|
||||
}
|
||||
}
|
||||
@@ -816,7 +817,7 @@ namespace ColorControl
|
||||
return;
|
||||
}
|
||||
var enabled = chkStartAfterLogin.Checked;
|
||||
Utils.ExecuteElevated(enabled ? StartUpParams.EnableAutoStartParam : StartUpParams.DisableAutoStartParam);
|
||||
Utils.RegisterTask(Program.TS_TASKNAME, enabled);
|
||||
}
|
||||
|
||||
private void LoadConfig()
|
||||
@@ -828,6 +829,7 @@ namespace ColorControl
|
||||
edtDelayDisplaySettings.Value = _config.DisplaySettingsDelay;
|
||||
edtBlankScreenSaverShortcut.Text = _config.ScreenSaverShortcut;
|
||||
chkGdiScaling.Checked = _config.UseGdiScaling;
|
||||
chkOptionsDedicatedElevatedProcess.Checked = _config.UseDedicatedElevatedProcess;
|
||||
|
||||
if (!string.IsNullOrEmpty(_config.ScreenSaverShortcut))
|
||||
{
|
||||
@@ -1589,7 +1591,7 @@ namespace ColorControl
|
||||
|
||||
if (!string.IsNullOrEmpty(preset.shortcut))
|
||||
{
|
||||
Utils.UnregisterHotKey(Handle, preset.id);
|
||||
WinApi.UnregisterHotKey(Handle, preset.id);
|
||||
}
|
||||
|
||||
_nvService.GetPresets().Remove(preset);
|
||||
@@ -1944,7 +1946,7 @@ namespace ColorControl
|
||||
|
||||
if (!string.IsNullOrEmpty(preset.shortcut))
|
||||
{
|
||||
Utils.UnregisterHotKey(Handle, preset.id);
|
||||
WinApi.UnregisterHotKey(Handle, preset.id);
|
||||
}
|
||||
|
||||
_lgService.GetPresets().Remove(preset);
|
||||
@@ -2729,7 +2731,7 @@ Do you want to continue?";
|
||||
|
||||
if (!string.IsNullOrEmpty(preset.shortcut))
|
||||
{
|
||||
Utils.UnregisterHotKey(Handle, preset.id);
|
||||
WinApi.UnregisterHotKey(Handle, preset.id);
|
||||
}
|
||||
|
||||
_amdService.GetPresets().Remove(preset);
|
||||
@@ -3408,7 +3410,7 @@ The InStart and Software Update items are now visible under the Expert-button."
|
||||
|
||||
if (string.IsNullOrEmpty(text))
|
||||
{
|
||||
Utils.UnregisterHotKey(Handle, SHORTCUTID_GAMEBAR);
|
||||
WinApi.UnregisterHotKey(Handle, SHORTCUTID_GAMEBAR);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -3737,7 +3739,7 @@ The InStart and Software Update items are now visible under the Expert-button."
|
||||
|
||||
if (!string.IsNullOrEmpty(preset.shortcut))
|
||||
{
|
||||
Utils.UnregisterHotKey(Handle, preset.id);
|
||||
WinApi.UnregisterHotKey(Handle, preset.id);
|
||||
}
|
||||
|
||||
_gameService.GetPresets().Remove(preset);
|
||||
@@ -3989,5 +3991,88 @@ The InStart and Software Update items are now visible under the Expert-button."
|
||||
|
||||
Utils.RegisterShortcut(Handle, SHORTCUTID_AMDQA, _config.AmdQuickAccessShortcut, clear);
|
||||
}
|
||||
|
||||
private void btnGameProcessAffinity_Click(object sender, EventArgs e)
|
||||
{
|
||||
var preset = GetSelectedGamePreset();
|
||||
|
||||
if (preset == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var numberOfProcessors = Environment.ProcessorCount;
|
||||
|
||||
var options = Enumerable.Range(0, numberOfProcessors).Select(i => $"CPU #{i}");
|
||||
|
||||
var values = MessageForms.ShowDialog("Set processor affinity", new[] {
|
||||
new MessageForms.FieldDefinition
|
||||
{
|
||||
Label = "Set desired processors which are allowed to run program",
|
||||
FieldType = MessageForms.FieldType.Flags,
|
||||
Values = options,
|
||||
Value = preset.ProcessAffinityMask
|
||||
}
|
||||
});
|
||||
|
||||
if (!values.Any())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var value = values.First().Value;
|
||||
|
||||
preset.ProcessAffinityMask = (uint)(int)value;
|
||||
}
|
||||
|
||||
private void btnGameOptions_Click(object sender, EventArgs e)
|
||||
{
|
||||
mnuGameOptions.Show(btnGameOptions, btnGameOptions.PointToClient(Cursor.Position));
|
||||
}
|
||||
|
||||
private void miGameProcessPriority_Click(object sender, EventArgs e)
|
||||
{
|
||||
var preset = GetSelectedGamePreset();
|
||||
|
||||
if (preset == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var dropDownValues = Utils.GetDescriptions<GamePriorityClass>();
|
||||
|
||||
var values = MessageForms.ShowDialog("Set process priority", new[] {
|
||||
new MessageForms.FieldDefinition
|
||||
{
|
||||
Label = "Set desired process priority",
|
||||
FieldType = MessageForms.FieldType.DropDown,
|
||||
Values = dropDownValues,
|
||||
Value = preset.ProcessPriorityClass > 0 ? ((GamePriorityClass)preset.ProcessPriorityClass).GetDescription() : GamePriorityClass.Normal.GetDescription()
|
||||
}
|
||||
});
|
||||
|
||||
if (!values.Any())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var value = values.First().Value.ToString();
|
||||
var enumName = Utils.GetEnumNameByDescription(typeof(GamePriorityClass), value);
|
||||
if (enumName != null)
|
||||
{
|
||||
value = enumName;
|
||||
}
|
||||
|
||||
var enumValue = Enum.Parse(typeof(GamePriorityClass), value);
|
||||
|
||||
preset.ProcessPriorityClass = (uint)(int)enumValue;
|
||||
|
||||
}
|
||||
|
||||
private void chkOptionsDedicatedElevatedProcess_CheckedChanged(object sender, EventArgs e)
|
||||
{
|
||||
_config.UseDedicatedElevatedProcess = chkOptionsDedicatedElevatedProcess.Checked;
|
||||
Utils.UseDedicatedElevatedProcess = _config.UseDedicatedElevatedProcess;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -69,8 +69,11 @@
|
||||
<metadata name="mnuLgButtons.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<value>147, 17</value>
|
||||
</metadata>
|
||||
<metadata name="mnuGameOptions.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<value>705, 16</value>
|
||||
</metadata>
|
||||
<metadata name="mnuGameActions.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<value>418, 15</value>
|
||||
<value>414, 15</value>
|
||||
</metadata>
|
||||
<metadata name="mnuGameAddStep.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<value>416, 50</value>
|
||||
|
||||
@@ -0,0 +1,135 @@
|
||||
using NWin32.NativeTypes;
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
namespace ColorControl.Native
|
||||
{
|
||||
public static class WinApi
|
||||
{
|
||||
[StructLayout(LayoutKind.Sequential, Pack = 4)]
|
||||
internal struct POWERBROADCAST_SETTING
|
||||
{
|
||||
public Guid PowerSetting;
|
||||
public uint DataLength;
|
||||
public byte Data;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct COPYDATASTRUCT
|
||||
{
|
||||
public IntPtr dwData; // in C/C++ this is an UINT_PTR, not an UINT
|
||||
public int cbData;
|
||||
public IntPtr lpData;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct CopyData : IDisposable
|
||||
{
|
||||
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = false)]
|
||||
static extern IntPtr SendMessageTimeout(IntPtr hWnd, uint Msg, IntPtr wParam, ref CopyData target,
|
||||
SendMessageTimeoutFlags fuFlags, uint uTimeout, out UIntPtr lpdwResult);
|
||||
|
||||
[Flags]
|
||||
enum SendMessageTimeoutFlags : uint
|
||||
{
|
||||
SMTO_NORMAL = 0x0,
|
||||
SMTO_BLOCK = 0x1,
|
||||
SMTO_ABORTIFHUNG = 0x2,
|
||||
SMTO_NOTIMEOUTIFNOTHUNG = 0x8
|
||||
}
|
||||
const uint WM_COPYDATA = 0x4A;
|
||||
|
||||
public IntPtr dwData;
|
||||
public int cbData;
|
||||
public IntPtr lpData;
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
if (lpData != IntPtr.Zero)
|
||||
{
|
||||
Marshal.FreeCoTaskMem(lpData);
|
||||
lpData = IntPtr.Zero;
|
||||
cbData = 0;
|
||||
}
|
||||
}
|
||||
public string AsAnsiString
|
||||
{
|
||||
get { return Marshal.PtrToStringAnsi(lpData, cbData); }
|
||||
}
|
||||
public string AsUnicodeString
|
||||
{
|
||||
get { return Marshal.PtrToStringUni(lpData); }
|
||||
}
|
||||
public static CopyData CreateForString(int dwData, string value, bool Unicode = false)
|
||||
{
|
||||
var result = new CopyData();
|
||||
result.dwData = (IntPtr)dwData;
|
||||
result.lpData = Unicode ? Marshal.StringToCoTaskMemUni(value) : Marshal.StringToCoTaskMemAnsi(value);
|
||||
result.cbData = value.Length + 2;
|
||||
return result;
|
||||
}
|
||||
|
||||
public static UIntPtr Send(IntPtr targetHandle, int dwData, string value, uint timeoutMs = 1000, bool Unicode = false)
|
||||
{
|
||||
var cds = CreateForString(dwData, value, Unicode);
|
||||
UIntPtr result;
|
||||
SendMessageTimeout(targetHandle, WM_COPYDATA, IntPtr.Zero, ref cds, SendMessageTimeoutFlags.SMTO_NORMAL, timeoutMs, out result);
|
||||
cds.Dispose();
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
public enum MessageFilterInfo : uint
|
||||
{
|
||||
None = 0, AlreadyAllowed = 1, AlreadyDisAllowed = 2, AllowedHigher = 3
|
||||
};
|
||||
|
||||
public enum ChangeWindowMessageFilterExAction : uint
|
||||
{
|
||||
Reset = 0, Allow = 1, DisAllow = 2
|
||||
};
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct CHANGEFILTERSTRUCT
|
||||
{
|
||||
public uint size;
|
||||
public MessageFilterInfo info;
|
||||
}
|
||||
|
||||
public const int ENUM_CURRENT_SETTINGS = -1;
|
||||
public const int ENUM_REGISTRY_SETTINGS = -2;
|
||||
|
||||
public static int PBT_POWERSETTINGCHANGE = 32787;
|
||||
|
||||
public delegate void PCREATE_PROCESS_NOTIFY_ROUTINE(IntPtr ParentId, IntPtr ProcessId, bool Create);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
public static extern bool RegisterHotKey(IntPtr hWnd, int id, int fsModifiers, int vlc);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
public static extern bool UnregisterHotKey(IntPtr hWnd, int id);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
public static extern bool EnumDisplaySettingsA(string deviceName, int modeNum, out DEVMODEA devMode);
|
||||
|
||||
[DllImport("kernel32.dll", SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool AllocConsole();
|
||||
|
||||
[DllImport("kernel32.dll", SetLastError = true, ExactSpelling = true)]
|
||||
public static extern bool AttachConsole(int processId);
|
||||
|
||||
[DllImport("kernel32.dll", SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool FreeConsole();
|
||||
|
||||
[DllImport(@"User32", SetLastError = true)]
|
||||
public static extern IntPtr RegisterPowerSettingNotification(IntPtr hRecipient, ref Guid PowerSettingGuid, Int32 Flags);
|
||||
|
||||
[DllImport("User32.dll", SetLastError = true)]
|
||||
public static extern bool UnregisterPowerSettingNotification(IntPtr hWnd);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
public static extern bool ChangeWindowMessageFilterEx(IntPtr hWnd, uint msg, ChangeWindowMessageFilterExAction action, ref CHANGEFILTERSTRUCT changeInfo);
|
||||
}
|
||||
}
|
||||
+38
-3
@@ -1,4 +1,5 @@
|
||||
using ColorControl.Common;
|
||||
using ColorControl.Forms;
|
||||
using ColorControl.Services.AMD;
|
||||
using ColorControl.Services.LG;
|
||||
using ColorControl.Services.NVIDIA;
|
||||
@@ -21,6 +22,8 @@ namespace ColorControl
|
||||
public static Config Config { get; private set; }
|
||||
public static AppContext AppContext { get; private set; }
|
||||
|
||||
public static string MutexId { get; private set; }
|
||||
|
||||
private static readonly Logger Logger = LogManager.GetCurrentClassLogger();
|
||||
|
||||
/// <summary>
|
||||
@@ -29,6 +32,8 @@ namespace ColorControl
|
||||
[STAThread]
|
||||
static void Main(string[] args)
|
||||
{
|
||||
MutexId = $"Global\\{typeof(MainForm).GUID}";
|
||||
|
||||
var currentDomain = AppDomain.CurrentDomain;
|
||||
// Handler for unhandled exceptions.
|
||||
currentDomain.UnhandledException += GlobalUnhandledExceptionHandler;
|
||||
@@ -63,8 +68,7 @@ namespace ColorControl
|
||||
Utils.CloseConsole();
|
||||
}
|
||||
|
||||
string mutexId = $"Global\\{typeof(MainForm).GUID}";
|
||||
var mutex = new Mutex(true, mutexId, out var mutexCreated);
|
||||
var mutex = new Mutex(true, MutexId, out var mutexCreated);
|
||||
try
|
||||
{
|
||||
if (!mutexCreated)
|
||||
@@ -81,11 +85,13 @@ namespace ColorControl
|
||||
}
|
||||
else
|
||||
{
|
||||
mutex.WaitOne();
|
||||
try
|
||||
{
|
||||
Application.EnableVisualStyles();
|
||||
Application.SetCompatibleTextRenderingDefault(false);
|
||||
Application.Run(new MainForm(AppContext));
|
||||
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@@ -135,9 +141,11 @@ namespace ColorControl
|
||||
Logger.Error($"LoadConfig: {ex.Message}");
|
||||
}
|
||||
Config ??= new Config();
|
||||
|
||||
Utils.UseDedicatedElevatedProcess = Config.UseDedicatedElevatedProcess;
|
||||
}
|
||||
|
||||
private static bool HandleStartupParams(StartUpParams startUpParams, Process existingProcess)
|
||||
public static bool HandleStartupParams(StartUpParams startUpParams, Process existingProcess)
|
||||
{
|
||||
if (startUpParams.ActivateChromeFontFix || startUpParams.DeactivateChromeFontFix)
|
||||
{
|
||||
@@ -149,6 +157,21 @@ namespace ColorControl
|
||||
Utils.RegisterTask(TS_TASKNAME, startUpParams.EnableAutoStart);
|
||||
return true;
|
||||
}
|
||||
if (startUpParams.SetProcessAffinity)
|
||||
{
|
||||
Utils.SetProcessAffinity(startUpParams.ProcessId, startUpParams.AffinityMask);
|
||||
return true;
|
||||
}
|
||||
if (startUpParams.SetProcessPriority)
|
||||
{
|
||||
Utils.SetProcessPriority(startUpParams.ProcessId, startUpParams.PriorityClass);
|
||||
return true;
|
||||
}
|
||||
if (startUpParams.StartElevated)
|
||||
{
|
||||
StartElevated();
|
||||
return true;
|
||||
}
|
||||
|
||||
var useConsole = startUpParams.NoGui || existingProcess != null;
|
||||
|
||||
@@ -228,6 +251,18 @@ namespace ColorControl
|
||||
return result;
|
||||
}
|
||||
|
||||
private static void StartElevated()
|
||||
{
|
||||
try
|
||||
{
|
||||
Application.Run(new ElevatedForm());
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
MessageBox.Show("Error while initializing elevated application: " + ex.ToLogString(Environment.StackTrace), "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
|
||||
public static int EnumThreadWindows(IntPtr handle, IntPtr param)
|
||||
{
|
||||
NativeMethods.SendMessageW(handle, Utils.WM_BRINGTOFRONT, UIntPtr.Zero, IntPtr.Zero);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
using ColorControl.Common;
|
||||
using ColorControl.Native;
|
||||
using NWin32;
|
||||
using NWin32.NativeTypes;
|
||||
using System;
|
||||
@@ -101,7 +101,7 @@ namespace ColorControl.Services.Common
|
||||
{
|
||||
DEVMODEA devMode;
|
||||
// NativeMethods defines modeNum as an 'uint' but we need to pass '-1'
|
||||
if (Utils.EnumDisplaySettingsA(displayName, Utils.ENUM_CURRENT_SETTINGS, out devMode))
|
||||
if (WinApi.EnumDisplaySettingsA(displayName, WinApi.ENUM_CURRENT_SETTINGS, out devMode))
|
||||
{
|
||||
return devMode.dmDisplayFrequency;
|
||||
}
|
||||
|
||||
@@ -1,8 +1,19 @@
|
||||
using ColorControl.Services.Common;
|
||||
using NWin32;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace ColorControl.Services.GameLauncher
|
||||
{
|
||||
public enum GamePriorityClass
|
||||
{
|
||||
Idle = NativeConstants.IDLE_PRIORITY_CLASS,
|
||||
BelowNormal = NativeConstants.BELOW_NORMAL_PRIORITY_CLASS,
|
||||
Normal = NativeConstants.NORMAL_PRIORITY_CLASS,
|
||||
AboveNormal = NativeConstants.ABOVE_NORMAL_PRIORITY_CLASS,
|
||||
High = NativeConstants.HIGH_PRIORITY_CLASS,
|
||||
RealTime = NativeConstants.REALTIME_PRIORITY_CLASS
|
||||
}
|
||||
|
||||
class GamePreset : PresetBase
|
||||
{
|
||||
public string Path { get; set; }
|
||||
@@ -10,6 +21,8 @@ namespace ColorControl.Services.GameLauncher
|
||||
public bool RunAsAdministrator { get; set; }
|
||||
public List<string> PreLaunchSteps { get; set; }
|
||||
public List<string> PostLaunchSteps { get; set; }
|
||||
public uint ProcessAffinityMask { get; set; }
|
||||
public uint ProcessPriorityClass { get; set; }
|
||||
|
||||
public GamePreset() : base()
|
||||
{
|
||||
|
||||
@@ -133,7 +133,7 @@ namespace ColorControl.Services.GameLauncher
|
||||
|
||||
if (!string.IsNullOrEmpty(preset.Path))
|
||||
{
|
||||
Utils.StartProcess(preset.Path, preset.Parameters, setWorkingDir: true, elevate: preset.RunAsAdministrator);
|
||||
Utils.StartProcess(preset.Path, preset.Parameters, setWorkingDir: true, elevate: preset.RunAsAdministrator, affinityMask: preset.ProcessAffinityMask, priorityClass: preset.ProcessPriorityClass);
|
||||
}
|
||||
|
||||
_lastAppliedPreset = preset;
|
||||
|
||||
@@ -150,6 +150,7 @@ namespace ColorControl.Services.LG
|
||||
AddGenericPictureAction("gamma", typeof(GammaExp));
|
||||
AddGenericPictureAction("colorTemperature", minValue: 0, maxValue: 50, title: "Color Temperature");
|
||||
AddGenericPictureAction("whiteBalanceColorTemperature", typeof(WhiteBalanceColorTemperature), title: "White Balance Color Temperature");
|
||||
AddGenericPictureAction("eyeComfortMode", typeof(OffToOn), title: "Eye Comfort Mode");
|
||||
//AddGenericPictureAction("dynamicColor", typeof(OffToAuto));
|
||||
//AddGenericPictureAction("superResolution", typeof(OffToAuto));
|
||||
AddGenericPictureAction("peakBrightness", typeof(OffToHigh), title: "Peak Brightness");
|
||||
|
||||
@@ -654,7 +654,7 @@ namespace ColorControl.Services.LG
|
||||
Logger.Debug($"Screensaver check: powering off tv {device.Name} because of screensaver");
|
||||
try
|
||||
{
|
||||
_poweredOffByScreenSaver = await device.PowerOff().WaitAsync(TimeSpan.FromSeconds(5));
|
||||
_poweredOffByScreenSaver = await device.PowerOff(true).WaitAsync(TimeSpan.FromSeconds(5));
|
||||
}
|
||||
catch (TimeoutException)
|
||||
{
|
||||
|
||||
@@ -14,6 +14,9 @@ namespace ColorControl
|
||||
public const string NoGuiParam = "--nogui";
|
||||
public const string EnableAutoStartParam = "--enable-auto-start";
|
||||
public const string DisableAutoStartParam = "--disable-auto-start";
|
||||
public const string SetProcessAffinityParam = "--set-process-affinity";
|
||||
public const string SetProcessPriorityParam = "--set-process-priority";
|
||||
public const string StartElevatedParam = "--elevated";
|
||||
|
||||
public bool RunningFromScheduledTask { get; private set; }
|
||||
public bool ActivateChromeFontFix { get; private set; }
|
||||
@@ -28,6 +31,12 @@ namespace ColorControl
|
||||
public bool NoGui { get; set; }
|
||||
public bool EnableAutoStart { get; private set; }
|
||||
public bool DisableAutoStart { get; private set; }
|
||||
public bool SetProcessAffinity { get; private set; }
|
||||
public int ProcessId { get; private set; }
|
||||
public uint AffinityMask { get; private set; }
|
||||
public bool SetProcessPriority { get; private set; }
|
||||
public uint PriorityClass { get; private set; }
|
||||
public bool StartElevated { get; private set; }
|
||||
|
||||
public static StartUpParams Parse(IEnumerable<string> args)
|
||||
{
|
||||
@@ -54,6 +63,28 @@ namespace ColorControl
|
||||
settings.LgPresetName = arg;
|
||||
break;
|
||||
}
|
||||
case SetProcessAffinityParam:
|
||||
{
|
||||
if (settings.ProcessId == 0)
|
||||
{
|
||||
settings.ProcessId = int.Parse(arg);
|
||||
continue;
|
||||
}
|
||||
|
||||
settings.AffinityMask = uint.Parse(arg);
|
||||
break;
|
||||
}
|
||||
case SetProcessPriorityParam:
|
||||
{
|
||||
if (settings.ProcessId == 0)
|
||||
{
|
||||
settings.ProcessId = int.Parse(arg);
|
||||
continue;
|
||||
}
|
||||
|
||||
settings.PriorityClass = uint.Parse(arg);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
parseNameParam = string.Empty;
|
||||
@@ -116,6 +147,23 @@ namespace ColorControl
|
||||
settings.DisableAutoStart = true;
|
||||
break;
|
||||
}
|
||||
case SetProcessAffinityParam:
|
||||
{
|
||||
settings.SetProcessAffinity = true;
|
||||
parseNameParam = SetProcessAffinityParam;
|
||||
break;
|
||||
}
|
||||
case SetProcessPriorityParam:
|
||||
{
|
||||
settings.SetProcessPriority = true;
|
||||
parseNameParam = SetProcessPriorityParam;
|
||||
break;
|
||||
}
|
||||
case StartElevatedParam:
|
||||
{
|
||||
settings.StartElevated = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return settings;
|
||||
|
||||
Reference in new issue
Block a user