【WPF】DataGrid多表头的样式设计
需求
在使用WPF开发时,使用DataGrid
列表显示数据时,有些字段可以进行分组显示,用于更好的表达它们之间存在的某种关系,因此就考虑到要对DataGrid
的表头进行扩展,可以显示多行表头,让这些有关联的字段内容显示的更加明了简洁。
自定义样式
这段自定义样式可以放在MainWindow.xaml
文件中,或者自己定义一个存放样式文件的xaml
进行存放。
这里在模版里面使用的第一个Grid
,是用于总的显示,还有右侧边竖线分割线,嵌入的Grid
用于显示多表头的处理显示功能:第一行为总的信息,第二行为第一行和第三行的分割线,第三行显示的省、市和县。
<Style x:Key="CityStyle" TargetType="DataGridColumnHeader">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate>
<Grid x:Name="Root">
<Grid.ColumnDefinitions>
<ColumnDefinition>
</ColumnDefinition>
<ColumnDefinition Width="Auto">
</ColumnDefinition>
</Grid.ColumnDefinitions>
<Grid
Grid.Column="0"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}">
<Grid.RowDefinitions>
<RowDefinition Height="30">
</RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="30">
</RowDefinition>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="100">
</ColumnDefinition>
<ColumnDefinition Width="Auto">
</ColumnDefinition>
<ColumnDefinition Width="100">
</ColumnDefinition>
<ColumnDefinition Width="Auto">
</ColumnDefinition>
<ColumnDefinition Width="100">
</ColumnDefinition>
</Grid.ColumnDefinitions>
<ContentPresenter
Grid.Row="0"
Grid.Column="0"
Grid.ColumnSpan="5"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Content="户籍信息">
</ContentPresenter>
<Rectangle
Grid.Row="1"
Grid.Column="0"
Grid.ColumnSpan="5"
VerticalAlignment="Stretch" Height="1"
Fill="Black"
Visibility="Visible">
</Rectangle>
<ContentPresenter
Grid.Row="2"
Grid.Column="0"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Content="省">
</ContentPresenter>
<Rectangle
Grid.Row="2"
Grid.Column="1"
Width="1"
VerticalAlignment="Stretch"
Fill="#ccc"
Visibility="Visible">
</Rectangle>
<ContentPresenter
Grid.Row="2"
Grid.Column="2"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Content="市">
</ContentPresenter>
<Rectangle
Grid.Row="2"
Grid.Column="3"
Width="1"
VerticalAlignment="Stretch"
Fill="#ccc"
Visibility="Visible">
</Rectangle>
<ContentPresenter
Grid.Row="2"
Grid.Column="4"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Content="县">
</ContentPresenter>
</Grid>
<Rectangle
Grid.Column="1"
Width="1"
VerticalAlignment="Stretch"
Fill="#ccc"
Visibility="Visible">
</Rectangle>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
窗体布局
<Grid>
<DataGrid
AutoGenerateColumns="False"
CanUserAddRows="False"
ItemsSource="{Binding UserInformations}">
<DataGrid.Columns>
<DataGridTextColumn Width="100" Binding="{Binding UserName}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<Grid HorizontalAlignment="Stretch" VerticalAlignment="Center">
<TextBlock
Margin="5,0,5,0"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Text="姓名"
TextAlignment="Center"
TextWrapping="Wrap">
</TextBlock>
</Grid>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
<DataGridTextColumn.ElementStyle>
<Style>
<Setter Property="TextBlock.TextAlignment" Value="Center">
</Setter>
<Setter Property="TextBlock.TextWrapping" Value="Wrap">
</Setter>
<Setter Property="TextBlock.HorizontalAlignment" Value="Center">
</Setter>
<Setter Property="TextBlock.VerticalAlignment" Value="Center">
</Setter>
</Style>
</DataGridTextColumn.ElementStyle>
</DataGridTextColumn>
<DataGridTemplateColumn HeaderStyle="{StaticResource CityStyle}">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<TextBlock
Width="100"
Margin="0"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Text="{Binding Province}"
TextAlignment="Center">
</TextBlock>
<Rectangle Width="1" Fill="Black">
</Rectangle>
<TextBlock
Width="100"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Text="{Binding City}"
TextAlignment="Center">
</TextBlock>
<Rectangle Width="1" Fill="Black">
</Rectangle>
<TextBlock
Width="100"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Text="{Binding County}"
TextAlignment="Center">
</TextBlock>
</StackPanel>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
<DataGridTextColumn
Width="100"
Binding="{Binding Motto}"
Header="格言">
<DataGridTextColumn.HeaderStyle>
<Style>
<Setter Property="TextBlock.HorizontalAlignment" Value="Stretch">
</Setter>
<Setter Property="TextBlock.TextAlignment" Value="Center">
</Setter>
</Style>
</DataGridTextColumn.HeaderStyle>
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
HorizontalAlignment="Center"
VerticalAlignment="Center"
Text="格言"
TextAlignment="Center"
TextWrapping="Wrap">
</TextBlock>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
<DataGridTextColumn.ElementStyle>
<Style>
<Setter Property="TextBlock.TextAlignment" Value="Center">
</Setter>
<Setter Property="TextBlock.TextWrapping" Value="Wrap">
</Setter>
<Setter Property="TextBlock.HorizontalAlignment" Value="Center">
</Setter>
<Setter Property="TextBlock.VerticalAlignment" Value="Center">
</Setter>
</Style>
</DataGridTextColumn.ElementStyle>
</DataGridTextColumn>
</DataGrid.Columns>
</DataGrid>
</Grid>
在这里的窗体布局中,同时对姓名和格言的表头样式和Cell里面的样式进行了修改。其中DataGridTextColumn.HeaderTemplate
包括的是头部的样式;DataGridTextColumn.ElementStyle
宝开的是Cell的样式。
定义的实体类
public class UserInformation
{
public string UserName { get; set; }
public string Province { get; set; }
public string City { get; set; }
public string County { get; set; }
public int Age { get; set; }
public string Motto { get; set; }
}
ViewModel类的定义
public class MainViewModel:ViewModelBase
{
private string _title;
public string Title
{
get { return _title; }
set { Set(ref _title, value); }
}
private ObservableCollection<UserInformation> _userInformations;
public ObservableCollection<UserInformation> UserInformations
{
get { return _userInformations; }
set { Set(ref _userInformations, value); }
}
public MainViewModel()
{
Title = Guid.NewGuid().ToString();
UserInformations = new ObservableCollection<UserInformation>(new List<UserInformation>()
{
new UserInformation()
{
UserName = "Bob",Age = 32,Province = "山东",City = "济南",County = "天桥",Motto = "会当云绝顶,\r\n一览众山小。"
},
new UserInformation()
{
UserName = "Bob",Age = 32,Province = "山东",City = "济南",County = "天桥",Motto = "会当云绝顶,\r\n一览众山小。"
},
new UserInformation()
{
UserName = "Bob",Age = 32,Province = "山东",City = "济南",County = "天桥",Motto = "会当云绝顶,\r\n一览众山小。"
}
});
}
}
本实例使用了.netcore 3.1
版本进行的开发,但是对于.net framework
同样适用。
MVVM
模式是使用MVVMLightstd10
,可以从nuget上面进行下载。
本示例已上传至GITHUB:https://github.com/mzy666888/MultiHeaderOfDataGridWpfApp
作者:芝麻麻雀
本文版权归作者和博客园共有,欢迎转载,但必须给出原文链接,并保留此段声明,否则保留追究法律责任的权利。