一、ChildWindow
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
namespace WindowsBase
{
public class ChildWindow : Window, INotifyPropertyChanged
{
ResourceDictionary style1;
ControlTemplate childWindowTemplate;
static ChildWindow()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(ChildWindow), new FrameworkPropertyMetadata(typeof(ChildWindow)));
}
public ChildWindow()
{
this.DataContext = this;
style1 = new ResourceDictionary();
style1.Source = new Uri("InstallPackageWPF;component/WindowsBase/ChildWindowStyle.xaml", UriKind.Relative);
this.Style = (System.Windows.Style)style1["ChildWindowStyle"];
}
public override void OnApplyTemplate()
{
childWindowTemplate = (ControlTemplate)style1["ChildWindowTemplate"];
Border borderTitle = (Border)childWindowTemplate.FindName("borderTitle", this);
borderTitle.MouseMove += delegate (object sender, MouseEventArgs e)
{
WindowMove(e);
};
Button minBtn = (Button)childWindowTemplate.FindName("btnMin", this);
minBtn.Click += delegate
{
this.WindowState = WindowState.Minimized;
};
Button closeBtn = (Button)childWindowTemplate.FindName("btnClose", this);
closeBtn.Click += delegate
{
this.Close();
};
}
public void WindowMove(MouseEventArgs e)
{
if (e.LeftButton == MouseButtonState.Pressed)
{
this.DragMove();
}
}
public event PropertyChangedEventHandler PropertyChanged;
protected PropertyChangedEventHandler PropertyChangedHandler
{
get
{
return PropertyChanged;
}
}
public event PropertyChangingEventHandler PropertyChanging;
protected PropertyChangingEventHandler PropertyChangingHandler
{
get
{
return PropertyChanging;
}
}
public void VerifyPropertyName(string propertyName)
{
var myType = GetType();
if (!string.IsNullOrEmpty(propertyName)
&& myType.GetProperty(propertyName) == null)
{
var descriptor = this as ICustomTypeDescriptor;
if (descriptor != null)
{
if (descriptor.GetProperties()
.Cast<PropertyDescriptor>()
.Any(property => property.Name == propertyName))
{
return;
}
}
throw new ArgumentException("Property not found", propertyName);
}
}
public virtual void RaisePropertyChanging(
string propertyName)
{
VerifyPropertyName(propertyName);
var handler = PropertyChanging;
if (handler != null)
{
handler(this, new PropertyChangingEventArgs(propertyName));
}
}
public virtual void RaisePropertyChanged(
string propertyName)
{
VerifyPropertyName(propertyName);
var handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(propertyName));
}
}
protected bool Set<T>(
string propertyName,
ref T field,
T newValue)
{
if (EqualityComparer<T>.Default.Equals(field, newValue))
{
return false;
}
RaisePropertyChanging(propertyName);
field = newValue;
RaisePropertyChanged(propertyName);
return true;
}
protected bool Set<T>(
ref T field,
T newValue,
string propertyName = null)
{
return Set(propertyName, ref field, newValue);
}
}
}
二、ChildWindowStyle
<ResourceDictionary
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<!-- - -->
<PathGeometry x:Key="pathMin">M512-359.489906M498.081951-47.76654M772.963422 362.508895l-528.06716 0c-12.38297 0-22.514491 10.131521-22.514491 22.514491l0 0c0 12.38297 10.131521 22.514491 22.514491 22.514491l528.06716 0c12.38297 0 22.514491-10.131521 22.514491-22.514491l0 0C795.477913 372.640416 785.346392 362.508895 772.963422 362.508895z</PathGeometry>
<!-- x -->
<PathGeometry x:Key="pathClose">M540.672 384l303.104 303.104c8.192 8.192 8.192 20.48 0 28.672s-20.48 8.192-28.672 0l-303.104-303.104L208.896 715.776c-8.192 8.192-20.48 8.192-28.672 0s-8.192-20.48 0-28.672l303.104-303.104-303.104-303.104c-8.192-8.192-8.192-20.48 0-28.672 4.096-4.096 8.192-4.096 16.384-4.096s12.288 0 16.384 4.096l303.104 303.104 303.104-303.104c4.096-4.096 8.192-4.096 16.384-4.096s12.288 0 16.384 4.096c8.192 8.192 8.192 20.48 0 28.672L540.672 384z</PathGeometry>
<!-- Window模板 -->
<ControlTemplate x:Key="ChildWindowTemplate" TargetType="{x:Type Window}">
<ControlTemplate.Resources>
<Storyboard x:Key="closeStoryboard">
<DoubleAnimation
AutoReverse="False"
Storyboard.TargetProperty="RenderTransform.ScaleX"
From="1"
To="0.8"
Duration="0:0:0.3" />
<DoubleAnimation
AutoReverse="False"
Storyboard.TargetProperty="RenderTransform.ScaleY"
From="1"
To="0.8"
Duration="0:0:0.3" />
<DoubleAnimation
AutoReverse="False"
Storyboard.TargetProperty="Opacity"
From="1"
To="0.8"
Duration="0:0:0.3" />
</Storyboard>
</ControlTemplate.Resources>
<Grid
Name="WindowGrid"
Background="Transparent"
RenderTransformOrigin="0.5,0.5">
<Grid.RenderTransform>
<ScaleTransform />
</Grid.RenderTransform>
<Border
Width="{TemplateBinding Width}"
Height="{TemplateBinding Height}"
Background="{TemplateBinding Background}"
CornerRadius="4">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="44" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Border Name="borderTitle" Panel.ZIndex="10">
<Grid Background="Transparent">
<StackPanel HorizontalAlignment="Right"
VerticalAlignment="Top"
Orientation="Horizontal" Margin="0,10,20,0" Panel.ZIndex="1">
<Button x:Name="btnMin" Foreground="White" Width="14" Height="14" Margin="0,0,0,10" Style="{DynamicResource PathButtonStyle}">
<Path Data="{DynamicResource pathMin}"></Path>
</Button>
<!--<Button x:Name="btnMax" Focusable="False" Width="16" Height="16" />-->
<Button x:Name="btnClose" Foreground="White" Width="14" Margin="15,0,0,0" Height="14" Style="{DynamicResource PathButtonStyle}">
<Path Data="{DynamicResource pathClose}"></Path>
</Button>
</StackPanel>
</Grid>
</Border>
<!-- 内容 -->
<Border
Grid.RowSpan="2"
Width="Auto"
Height="Auto">
<AdornerDecorator>
<ContentPresenter />
</AdornerDecorator>
</Border>
</Grid>
</Border>
</Grid>
</ControlTemplate>
<Style x:Key="ChildWindowStyle" TargetType="{x:Type Window}">
<Setter Property="AllowsTransparency" Value="True" />
<Setter Property="WindowStyle" Value="None" />
<Setter Property="ResizeMode" Value="NoResize" />
<Setter Property="Background" Value="Transparent" />
<Setter Property="Template" Value="{StaticResource ChildWindowTemplate}" />
</Style>
</ResourceDictionary>
三、使用
public partial class MainWindow : ChildWindow
{
public MainWindow()
{
InitializeComponent();
this.DataContext = this;
}
}