1

I need to have the window title of my application change color depending on what color is set in Windows 10 for the WindowChrome.

Is there a WPF property to bind to for the text color that automatically assumes the correct color (either black or white) that is actually legible?

Do you have to calculate the correct color manually and if so, how do you determine the color of the WindowChrome?

La_doc
  • 11
  • 2
  • Why do you want to change title color? What you are trying to achieve/solve? – Sinatr Jul 15 '20 at 11:33
  • The default black window title is illegible if the user has a dark color set for their title bar. – La_doc Jul 15 '20 at 11:36
  • You can get color from [system colors](https://learn.microsoft.com/en-us/archive/blogs/wpf/systemcolors-reference) and then modify it (maybe like [this](https://stackoverflow.com/q/1165107/1997232), see also [this](https://stackoverflow.com/q/35969656/1997232)). If you only want to check which color to use (black or white), then convert color to grayscale and compare it with middle. – Sinatr Jul 15 '20 at 11:44
  • Thank you, thats what I was planning to do, but the Color of the WindowChrome is not included in SystemColors – La_doc Jul 15 '20 at 12:12
  • It should be `ControlBrush` ([source](https://stackoverflow.com/q/4968562/1997232)). – Sinatr Jul 15 '20 at 12:16
  • Thats the background color of the window content, not the accent color set in windows 10 for the WindowChrome – La_doc Jul 15 '20 at 12:19
  • Thanks, I figured it out. The color of the WindowChrome is contained in SystemParameters.WindowGlassBrush – La_doc Jul 15 '20 at 12:21
  • To clarify, do you want the _Accent Color_ or the _window frame color_ (black / white) in dark and light mode? – thatguy Jul 15 '20 at 12:24
  • Welcome to Stack Overflow! Sharing your research helps everyone. Tell us what you've tried and why it didn’t meet your needs. This demonstrates that you’ve taken the time to try to help yourself, it saves us from reiterating obvious answers, and most of all it helps you get a more specific and relevant answer! See also: [ask] – Hille Jul 15 '20 at 13:14
  • @thatguy Ideally the window frame color. Already ran into the problem, that SystemParameters.WindowGlassBrush does not represent the frame color if the Accent color isn't used on window frames. – La_doc Jul 16 '20 at 12:55

1 Answers1

0

In previous versions of Windows, you would use the SystemColors class to get the corresponding colors. However, it does not map to the Windows 10 light and dark mode colors, as you can see in this issue. It will only be useful in in high contrast mode to a certain extent. The SystemParameters.WindowGlassBrush will only give you the accent color, which is not the window chrome color in general, but only if you explicitly apply it to window frames and titles in the system settings.

I have not found any way to either get the window chrome color or the title bar color directly, anywhere.

What you can do instead, is detect if Light Mode or Dark Mode is enabled for apps and change the color in your application depending on it, but you have to define the colors yourself. The following snippet uses the registry to find out which mode is enabled. If the registry key is not defined, it will return null.

var value = Registry.GetValue(@"HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Themes\Personalize", "AppsUseLightTheme", null);
var isAppLightTheme = value != null ? Convert.ToBoolean(value) : (bool?)null;

If you also want to cover the case when the access color is set as window frame or title bar color, use the registry entry below. The problem in this scenario is that Windows will set the title text color to either black or white, depending on the accent color for better readability. As above, you have to handle this manually.

var value = Registry.GetValue(@"HKEY_CURRENT_USER\Software\Microsoft\Windows\DWM", "ColorPrevalence", null);
var isTitleFrameAccentColored = value != null ? Convert.ToBoolean(value) : (bool?)null;

In order to access the registry, you need the Microsoft.Win32 namespace. If you use .NET Core you can install the Microsoft.Win32.Registry package to access the Registry class.

thatguy
  • 21,059
  • 6
  • 30
  • 40