15

I have a custom title bar and with the window style set to none. On the click of the title bar I check to see if it is a double click (that does window maximize and restore) if it is not double clicked I do Window.DragMove. This works great for the snapping to the side and top. But when I try to drag the window when it is maximized (which would normally restore the window down), it doesn't do anything. Here is my code:

 static Window Window { get { return Application.Current.MainWindow; } } /// <summary> /// TitleBar_MouseDown - Drag if single-click, resize if double-click /// </summary> private static void TitleBar_MouseDown(object sender, MouseButtonEventArgs e) { if (e.ChangedButton == MouseButton.Left) { if (e.ClickCount == 2) { AdjustWindowSize(); } else { Window.DragMove();//Here is where I do the drag move } } } /// <summary> /// Adjusts the WindowSize to correct parameters when Maximize button is clicked /// </summary> internal static void AdjustWindowSize() { if (Window.WindowState == WindowState.Maximized) { SystemCommands.RestoreWindow(Window); } else { SystemCommands.MaximizeWindow(Window); } } #region Button Events /// <summary> /// CloseButton_Clicked /// </summary> public static void Close() { SystemCommands.CloseWindow(Window); } /// <summary> /// MaximizedButton_Clicked /// </summary> public static void Maximize() { AdjustWindowSize(); } /// <summary> /// Minimized Button_Clicked /// </summary> public static void Minimize() { SystemCommands.MinimizeWindow(Window); } #endregion 

Modern UI and MahApps.Metro does it somehow and I looked at their source code briefly but could not find how they do it.

Thanks in advance.

1 Answer 1

45
+50

I am able to get the desired behavior of title bar including aero snap in pure xaml

as result you can see a custom title bar, it is completely draggable, double click to maximize and restore and drag to snap and unsnap.

xaml

<Window x:Class="CSharpWPF.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="MainWindow" > <WindowChrome.WindowChrome> <WindowChrome CaptionHeight="{Binding ActualHeight,ElementName=titlebar}"/> </WindowChrome.WindowChrome> <DockPanel LastChildFill="True"> <Border Background="LightBlue" DockPanel.Dock="Top" Height="25" x:Name="titlebar"> <TextBlock Text="{Binding Title, RelativeSource={RelativeSource FindAncestor,AncestorType=Window},FallbackValue=Title}" Margin="10,0,0,0" VerticalAlignment="Center"> <TextBlock.Effect> <DropShadowEffect Color="White" ShadowDepth="3"/> </TextBlock.Effect> </TextBlock> </Border> <Border BorderBrush="LightGray" BorderThickness="1" Padding="4"> <TextBlock Text="Window content"/> </Border> </DockPanel> </Window> 

result

result

so now you don't need any code behind to handle title bar manually.

Reusable styles

you can also wrap above in a custom style which you can apply on several windows

<Style TargetType="Window" x:Key="CustomTitleBar"> <Setter Property="WindowChrome.WindowChrome"> <Setter.Value> <WindowChrome CaptionHeight="{x:Static SystemParameters.CaptionHeight}" /> </Setter.Value> </Setter> <Setter Property="Template"> <Setter.Value> <ControlTemplate TargetType="Window"> <DockPanel LastChildFill="True"> <Border Background="LightBlue" DockPanel.Dock="Top" Height="{x:Static SystemParameters.CaptionHeight}" x:Name="titlebar"> <Grid> <TextBlock Text="{TemplateBinding Title}" Margin="10,0,0,0" VerticalAlignment="Center"> <TextBlock.Effect> <DropShadowEffect Color="White" ShadowDepth="3"/> </TextBlock.Effect> </TextBlock> </Grid> </Border> <Border Background="{TemplateBinding Background}" BorderBrush="LightGray" BorderThickness="1" Padding="4"> <ContentPresenter/> </Border> </DockPanel> </ControlTemplate> </Setter.Value> </Setter> </Style> 

usage

<Window x:Class="CSharpWPF.View" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="MainWindow" Style="{StaticResource CustomTitleBar}" > <TextBlock Text="Window content"/> </Window> 

How to implement in your code

After looking at your code, I did manage to implement it with very little changes

Changes are

File: CustomChrome.cs

line 41: change CaptionHeight = 36, currently it is 0. this should be equal to your title bar height

var chrome = new WindowChrome() { GlassFrameThickness = new Thickness(-1), CaptionHeight = 36 }; 

line 60: remove ((FrameworkElement)sender).MouseDown += TitleBar_MouseDown; as not required

line 70: remove no more used event TitleBar_MouseDown

File: CornerButtons.xaml

line 13: add WindowChrome.IsHitTestVisibleInChrome="True" to StackPanel

 <StackPanel SnapsToDevicePixels="True" Orientation="Horizontal" WindowChrome.IsHitTestVisibleInChrome="True"> 

File: MainWindow.xaml

line 17: add WindowChrome.IsHitTestVisibleInChrome="True" to StackPanel

<cc:CornerButtons Grid.Column="2"> <StackPanel Orientation="Horizontal" WindowChrome.IsHitTestVisibleInChrome="True"> 

this is all, and your app will have a normal title bar without need to handle custom logic

Sign up to request clarification or add additional context in comments.

15 Comments

I tried that and it did not work. It did some funky stuff then.
could you post a working sample of your app? may I try it here.
do you know how to do that?
did you set WindowChrome.IsHitTestVisibleInChrome="True", this is necessary for those button to work. you can set individually to the buttons too.
Custom window works great however it missing little animations when you maximize and minimize window it just popup suddenly and hide suddenly. Do you know how to accomplish default minimize and maximize effect.
|

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.