0

I've looked in this article about getting "dark mode" titlebar in winforms WinForms Dark title bar on Windows 10

its obvious you can get the window handle like this (In WPF) instead of using this.Handle

IntPtr hWnd = new WindowInteropHelper(GetWindow(this)).EnsureHandle();

So it works

Click here to see image (I don't have rep yet)

But I was wondering if I could do this with any color..

Windows 10 and 11 have a setting to turn on any titlebar color in settings, but I was wondering if I could get the hWnd and do this myself per application, since I can turn it to black, why not any other color?

Sir Rufo
  • 18,395
  • 2
  • 39
  • 73
hexeditor
  • 109
  • 1
  • 11

2 Answers2

3

You can take three approaches to this problem...

1: The hard one, what you are trying to do is modify the non-client area which is controlled by Windows.

The downside is this is possible only through the Windows' kernel methods, and you're in .NET, not C/C++. However, there is P/Invoke at our disposal. Indeed, the whole of the Windows Form UI and console application I/O methods are offered as wrappers that make system calls under the hood. Hence, as documented in MSDN, it is completely possible to use P/Invoke to access those methods that are needed to set up the non–client area.

As said prior, this is a "harder than currently necessary" solution.


2: The easier one, making your own title bar with XAML

Luckily, as of .NET 4.5, you can use the WindowChrome class to adjust the non-client area somewhat to your needs, you can set the WindowStyle to none and can add a custom title bar to your application that can have any color you like, and can look like the title bar from Windows or other OS'

To get yourself started on WindowChrome you can go to these following articles WindowChrome Class and Experiments with WindowChrome.

The basis of your code right below the <Window [...]>

<WindowChrome.WindowChrome>
        <WindowChrome 
        CaptionHeight="0"
        ResizeBorderThickness="5" />
    </WindowChrome.WindowChrome>

And make sure you add WindowStyle="None" to remove the titlebar and its components


3: The easiest one, using a third-party library.

You can also use a third-party components system like MahApps.Metro for WPF. You should be able to Customize the title bar color as far as I am aware.

The end result can look something like this:

MahApps.Metro

SimpleCoder
  • 474
  • 4
  • 18
  • Yes, I've used WindowChrome before but I want to mofify the windows hWnd, is there any dwm command used to change the titlebar color? – hexeditor Mar 05 '22 at 15:07
  • @Display as mentioned you can't really control it that much, there is no way of specifying the color of the titlebar apart from modifying WindowChrome or using C/C++ that I know of. – SimpleCoder Mar 05 '22 at 15:10
  • @Display As far as I know, not even the SDK has the ability to customize it that easily, it's very likely they didn't code that in and are rather using the accent color from Windows as an option. Even if it is coded in there, you would most likely need C/C++ – SimpleCoder Mar 05 '22 at 15:16
  • 3
    @Display This is doable on Windows 11 now; there is finally a documented DWM attribute for setting the title bar color (DWMWA_CAPTION_COLOR): https://twitter.com/zodiacon/status/1416734060278341633 Documentation: https://learn.microsoft.com/en-us/windows/win32/api/dwmapi/ne-dwmapi-dwmwindowattribute Example of calling it in C# using CsWin32: https://github.com/rgwood/MaximalWebView/blob/1122ceb4951f42129f03214bdd4c6e3a52613ddf/MaximalWebView/Program.cs#L297 – Reilly Wood Mar 05 '22 at 17:05
  • How do I do this in c# (the color) I keep getting errors – hexeditor Mar 26 '22 at 19:49
  • @DISPLAYNAME you could open another question on here and describe what you have tried and the errors you were/are getting. – SimpleCoder Mar 26 '22 at 20:21
  • Thanks, I already figured it out, so im fine now – hexeditor Mar 27 '22 at 19:44
3

People have been wanting to see how I got this to work

Put this under your class

[DllImport("DwmApi")] 
private static extern int DwmSetWindowAttribute(IntPtr hwnd, int attr, int[] attrValue, int attrSize);
const int DWWMA_CAPTION_COLOR = 35;


in whatever function (main?)

get the window handle or hwnd like this

IntPtr hWnd = new WindowInteropHelper(this).EnsureHandle();

then define the color

int[] colorstr = new int[]{0xFF00FF};

the 0x string thing is formatted like this 0xRRGGBB replace the letters to their corresponding values

then make it happen

DwmSetWindowAttribute(hWnd, DWWMA_CAPTION_COLOR, colorstr, 4);

note: this only works in windows 11


here is the complete version if your lazy

class MainWindow : Window
{

     [DllImport("DwmApi")] 
     private static extern int DwmSetWindowAttribute(IntPtr hwnd, int attr, int[] attrValue, int attrSize);
     const int DWWMA_CAPTION_COLOR = 35;

     public MainWindow()
     {
          IntPtr hWnd = new WindowInteropHelper(this).EnsureHandle();
          int[] colorstr = new int[]{0xFF00FF};
          DwmSetWindowAttribute(hWnd, DWWMA_CAPTION_COLOR, colorstr, 4);
     }

}

oh yes and import these

using System;
using System.Diagnostics;
using System.Runtime.InteropServices;
using System.Windows;
using System.Windows.Input;
using System.Windows.Interop;
using System.Windows.Media;

Edit: the color goes in the BGR format, so make sure it goes blue, green, red and not red, green blue

hexeditor
  • 109
  • 1
  • 11