在封装自定义组件的时候,看到很多类似表格的控件,表格中的数据都不是固定的,每个表格的表条和内容都不一样,如果直接在xaml
文件中定义DataGrid
的话,就显得很麻烦了,可以将期封装成一个动态生成的DataGrid
,只需按照一定规则的数据格式,就可以生成表格。如下所示为封装后的一个动态表格:
1.数据格式
首先来定义一个数据格式,数据格式相对比较简单,只需一个表头字段、内容字段、列宽字段。如下所示:
public class GridInfo {
public string name { get; set; }
public string value { get; set; }
public int column { get; set; }
}
2.创建DataGrid
首先创建一个UserControl
,然后在里面放入一个DataGrid
,并设置样式,如下所示:
<UserControl x:Class="WpfApp1.UCInfoGridColumn"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:WpfApp1"
DataContext="{Binding RelativeSource={RelativeSource Self}}"
mc:Ignorable="d"
d:DesignHeight="450" d:DesignWidth="800">
<UserControl.Resources>
<Style TargetType="DataGrid">
<!--网格线颜色-->
<Setter Property="CanUserResizeColumns" Value="false"/>
<Setter Property="BorderBrush" Value="#0668BA" />
<Setter Property="HorizontalGridLinesBrush">
<Setter.Value>
<SolidColorBrush Color="#0668BA"/>
</Setter.Value>
</Setter>
<Setter Property="VerticalGridLinesBrush">
<Setter.Value>
<SolidColorBrush Color="#0668BA"/>
</Setter.Value>
</Setter>
</Style>
<Style TargetType="DataGridColumnHeader">
<Setter Property="SnapsToDevicePixels" Value="True" />
<Setter Property="Background" Value="White" />
<Setter Property="FontSize" Value="14" />
<Setter Property="FontWeight" Value="Bold" />
<Setter Property="Cursor" Value="Hand" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="DataGridColumnHeader">
<Border x:Name="BackgroundBorder" BorderThickness="0,1,0,1"
BorderBrush="#0668BA"
Width="Auto">
<Grid >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<ContentPresenter Margin="0,0,0,0" VerticalAlignment="Center" HorizontalAlignment="Center"/>
<Path x:Name="SortArrow" Visibility="Collapsed" Data="M0,0 L1,0 0.5,1 z" Stretch="Fill" Grid.Column="2" Width="8" Height="6" Fill="White" Margin="0,0,50,0"
VerticalAlignment="Center" RenderTransformOrigin="1,1" />
<Rectangle Width="1" Fill="#0668BA" HorizontalAlignment="Right" Grid.ColumnSpan="1" />
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
<Setter Property="Height" Value="40"/>
</Style>
<!--行样式触发-->
<!--背景色改变必须先设置cellStyle 因为cellStyle会覆盖rowStyle样式-->
<Style TargetType="DataGridRow">
<Setter Property="Background" Value="#344488" />
<Setter Property="Height" Value="40"/>
<Setter Property="Foreground" Value="White" />
<Style.Triggers>
<!--隔行换色-->
<Trigger Property="AlternationIndex" Value="0" >
<Setter Property="Background" Value="#344488" />
</Trigger>
<Trigger Property="AlternationIndex" Value="1" >
<Setter Property="Background" Value="#344488" />
</Trigger>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background" Value="#344488"/>
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Foreground" Value="White"/>
</Trigger>
</Style.Triggers>
</Style>
<!--单元格样式触发-->
<Style TargetType="DataGridCell">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="DataGridCell">
<TextBlock TextAlignment="Center" VerticalAlignment="Center" >
<ContentPresenter />
</TextBlock>
</ControlTemplate>
</Setter.Value>
</Setter>
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Foreground" Value="White"/>
</Trigger>
</Style.Triggers>
</Style>
</UserControl.Resources>
<Border BorderBrush="#0668BA" BorderThickness="1" CornerRadius="3">
<DataGrid x:Name="dataGrid" HorizontalScrollBarVisibility="Hidden" Foreground="White" Background="#102371"></DataGrid>
</Border>
</UserControl>
3.动态生成表格
在.cs
文件中,添加一个方法,用于传递数据,并根据数据动态生成表格,如下所示:
public void loadData(ObservableCollection<GridInfo> list) {
if (list == null) {
return;
}
//计算出每一列的宽度
double width = this.ActualWidth / list.Count;
dataGrid.Columns.Clear();//每次清空列集合
for (int i = 0; i < list.Count; i++)
{
GridInfo gridInfo = list[i];
DataGridTextColumn textBoxColumn = new DataGridTextColumn();
textBoxColumn.Header = gridInfo.name;
//定义每一列的宽度相同
//textBoxColumn.Width = new DataGridLength(dataGrid.ActualWidth, DataGridLengthUnitType.Star);
textBoxColumn.Width = width * gridInfo.column;//定义每一列的最小宽度
Binding binding = new Binding("value");//设置每一列的binding
//binding.Path = new PropertyPath("name");
binding.Mode = BindingMode.OneWay;
textBoxColumn.Binding = binding;
dataGrid.Columns.Add(textBoxColumn);//将列添加到集合中
}
dataGrid.ItemsSource = list;
dataGrid.AutoGenerateColumns = false;//禁止自动添加列
dataGrid.CanUserAddRows = false;//禁止自动添加行
dataGrid.RowHeaderWidth = 0;//去除第一列多余的空白
}
引入动态表格
创建好表格后,然后再需要地方通过如下方式进行引入:
<local:UCInfoGridColumn Margin="101,54,0,0" VerticalAlignment="Top" Width="549" x:Name="infoGrid"/>
然后在loaded
事件中加入测试数据,来调用loadData
方法动态添加表格信息,如下所示:
private void Page_Loaded(object sender, RoutedEventArgs e)
{
ObservableCollection<GridInfo> list = new ObservableCollection<GridInfo>();
for (int i = 0; i < 3; i++)
{
GridInfo column = new GridInfo();
column.name = "标题" + i;
column.value = "内容" + i;
column.column = 1;
list.Add(column);
}
infoGrid.loadData(list);
}
按以下步骤来做,就可以快速的创建一个自定义的动态表格了。
个人博客
网友评论