当前位置:   article > 正文

WPF之DataGrid控件使用

WPF之DataGrid控件使用

一、DataGrid简介

据微软官方文档介绍,使用该 DataGrid 控件,可以从许多不同的源(如 SQL 数据库、LINQ 查询或任何其他可绑定的数据源)显示和编辑数据。 列可以显示文本、控件(如 ComboBox )或任何其他 WPF 内容(如图像、按钮或模板中包含的任何内容)。 可以使用 DataGridTemplateColumn 来显示模板中定义的数据。 下表列出了默认情况下提供的列类型:
在这里插入图片描述
下表列出了一些常见的任务 DataGrid ,以及如何完成这些任务。 通过查看相关 API,可以找到详细信息和示例代码。
在这里插入图片描述
DataGrid中比较常用的属性有IsReadOnly,该属性设置DataGrid单元格是否可以编辑,既可以对整个DataGrid进行设置,也可以单独对每一列进行设置。
SelectionUnit属性可以设置当鼠标点击DataGrid时获得焦点的是一个单元格或一个单元行,该属性会影响获取单元格的列索引。
CanUserAddRows属性设置是否在编辑行后再增加一行空白行,如果使用了数据源绑定,那么建议设置为False。
AutoGenerateColumns属性,如果使用了数据源绑定,那么应设置为False,否则相同的列会重复出现。
设置DataGrid表头内容居中显示,需要使用DataGrid.ColumnHeaderStyle样式进行设置,而没有可以直接设置居中的属性。

                <DataGrid.ColumnHeaderStyle>
                    <Style TargetType="DataGridColumnHeader">
                        <Setter Property="HorizontalContentAlignment" Value="Center"/>
                        <Setter Property="Background" Value="#f5f5f5"/>
                        <Setter Property="Foreground" Value="Black"/>
                        <Setter Property="BorderThickness" Value="1" />
                        <Setter Property="BorderBrush" Value="Gray" />
                        <Setter Property="Height" Value="30"/>
                        <Setter Property="FontSize" Value="18"/>
                    </Style>
                </DataGrid.ColumnHeaderStyle>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

设置DataGrid单元格内容样式,需要在DataGrid.Resources中定义Style,下方代码中的TargetType="TextBlock"只针对于DataGridTextColumn列类型,如果定义的列为其他类型,则需要另行设置。

                    <DataGrid.Resources>
	                    <Style x:Key="CenterAlignmentStyle01" TargetType="TextBlock">
	                        <Setter Property="TextAlignment" Value="Center"/>
	                        <Setter Property="Height" Value="30"/>
	                        <Setter Property="FontSize" Value="22"/>
	                        <Setter Property="Padding" Value="0,2"/>
	                        <Setter Property="Background" Value="#FFC4F3E2"/>
	                    </Style>
                    </DataGrid.Resources>
                    <DataGridTextColumn Header="表头1" Width="3*" ElementStyle="{StaticResource CenterAlignmentStyle}"/>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

设置DataGrid选中行时单元格变色,需要使用DataGrid.CellStyle样式进行设置

                <DataGrid.CellStyle>
                    <Style TargetType="DataGridCell">
                        <Style.Triggers>
                            <Trigger Property="IsSelected" Value="True">
                                <Setter Property="Background" Value="#FF8CCFEE"/>
                                <Setter Property="Foreground" Value="Black"/>
                            </Trigger>
                            <Trigger Property="IsFocused" Value="True">
                                <Setter Property="Background" Value="#FF62E6A4"/>
                                <Setter Property="Foreground" Value="Black"/>
                            </Trigger>
                        </Style.Triggers>
                    </Style>
                </DataGrid.CellStyle>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

二、DataGrid数据源绑定

在DataGrid进行数据源绑定,可以通过DataGridTextColumn、DataGridComboBoxColumn等几种列类型直接进行绑定,前台代码如下:

    <DataGrid x:Name="DataGrid01" CanUserAddRows="False" CanUserDeleteRows="False">
    	<DataGrid.Columns>
            <DataGridTextColumn Header="字段1" Width="3*" Binding="{Binding Path=Num,Mode=TwoWay,UpdateSourceTrigger=PropertyChanged}"/>
    	</DataGrid.Columns>
    </DataGrid>
  • 1
  • 2
  • 3
  • 4
  • 5

后台代码如下:

public partial class MainWindow : Window
{
	ObservableCollection<Data> Datas = new ObservableCollection<Data>();//DataGrid01数据源定义
	public MainWindow()
        {
            InitializeComponent();
            this.DataGrid01.ItemsSource = Datas;
        }
}
public class Data : INotifyPropertyChanged
    {
        private string _Num;
        public string Num
        {
            get { return _Num; }
            set
            {
                _Num = value;
                if (PropertyChanged != null)
                {
                    PropertyChanged(this, new PropertyChangedEventArgs("Num"));
                }
            }
        }
        public event PropertyChangedEventHandler PropertyChanged;
        protected virtual void OnPropertyChanged(string propertyName)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
        }
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30

其中Path=Num,Num为DataGrid数据源Data类中的一个成员变量。
也可以使用DataGridTemplateColumn进行绑定,后台代码与上面相同,前台代码如下:

<DataGrid x:Name="DataGrid01" CanUserAddRows="False" CanUserDeleteRows="False">
    	<DataGrid.Columns>
            <DataGridTemplateColumn Header="字段1" Width="3*">
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock  FontSize="16"  Text="{Binding Path=Num,Mode=TwoWay,UpdateSourceTrigger=PropertyChanged}"/>
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>
    	</DataGrid.Columns>
    </DataGrid>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

第一种绑定方式无法直接设置单元格内容样式,需要通过DataGrid.Resources定义Style来设置例如居中,字体大小等格式,而第二种绑定方式可以直接在DataTemplate中设置单元格格式,设置较为方便。
数据绑定后,在后台对数据进行编辑时,前台DataGrid会实时显示编辑后的数据,但DataGrid焦点默认只会聚焦到第一行数据行,而不是正在编辑的数据行,因此需要在后台代码中进行设置,将SelectedItem滚动到当前行,代码如下:

this.DataGrid01.SelectedItem = this.DataGrid01.Items[Index];//Index为待聚焦的行索引
this.DataGrid01.CurrentColumn = this.DataGrid01.Columns[0];
this.DataGrid01.ScrollIntoView(this.DataGrid01.SelectedItem, this.DataGrid01.CurrentColumn);
  • 1
  • 2
  • 3

三、DataGrid单元格编辑触发事件

要实现对DataGrid单元格编辑,需先将DataGrid属性IsReadOnly设置为false,可以在DataGrid定义中设置,这样是对全体单元格只读属性进行设置,也可以在列定义中设置,这样是对单个列字段进行设置。
DataGrid单元格编辑触发方法主要有CellEditEndingBeginningEdit,CellEditEnding是在单元格编辑完成后触发,BeginningEdit是在编辑一开始就触发。
前台xaml代码如下:

<DataGrid x:Name="DataGrid01" CanUserAddRows="False" 
CanUserDeleteRows="False" 
CellEditEnding="DataGrid01_CellEditEnding" 
BeginningEdit="DataGrid01_BeginningEdit"   
AutoGenerateColumns="False"  
SelectionUnit="CellOrRowHeader" 
CanUserSortColumns="False">
</DataGrid>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

后台代码如下:

        /// <summary>
        /// 获取编辑前数据保存至OriginEditData中
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void DataGrid01_BeginningEdit(object sender, DataGridBeginningEditEventArgs e)
        {
            TextBlock textBlock = e.Column.GetCellContent(e.Row) as TextBlock;
            if (textBlock == null)
            {
                return;
            }
            string value = textBlock.Text;
            MessageBox.Show(value);
        }
        /// <summary>
        /// 编辑单元格后对编辑后数据进行判断
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void DataGrid01_CellEditEnding(object sender, DataGridCellEditEndingEventArgs e)
        {
            var cells = this.DataGrid01.SelectedCells;
            int RowIndex = 0;
            int ColumnIndex = 0;
            if (cells.Any())
            {
                RowIndex = this.DataGrid01.Items.IndexOf(cells.First().Item);//获取单元格行索引
                ColumnIndex = cells.First().Column.DisplayIndex;//获取单元格列索引
            }
            string input = (e.EditingElement as TextBox).Text;//获取编辑后数据
            DataGridTextColumn dataGridTextColumn = this.DataGrid01.Columns[ColumnIndex] as DataGridTextColumn;
            Binding binding = dataGridTextColumn.Binding as Binding;
            string field = binding.Path.Path;//获取绑定的数据源的字段名称
            input = input.Replace(" ", "");
            if (input == "")
            {
                (e.EditingElement as TextBox).Text = "";
                MessageBox.Show("输入有误,请重新输入");
                return;
            }
        }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42

四、DataGrid增加删除行

当DataGrid绑定数据源时,删除和增加行应对数据源进行操作,如下所示,使用PreviewKeyDown方法,根据键盘按键进行增加和删除行操作:

        /// <summary>
        /// 根据按键进行删除和增加行操作,用户需选择3个以上单元格才能触发操作
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void DataGrid01_PreviewKeyDown(object sender, KeyEventArgs e)
        {
            var cells = this.DataGrid01.SelectedCells;
            int count = cells.Count;
            if (count > 2)
            {
                if (e.Key == Key.Back)//Backspace键
                {
                    //删除DataGrid的行是通过移除与之绑定的数据源中的元素来实现的
                    int RowIndex = this.DataGrid01.Items.IndexOf(cells.First().Item);
                    Datas.RemoveAt(RowIndex);//Datas为DataGrid绑定的数据源
                    //if (this.DataGrid01.SelectedItems != null && this.DataGrid01.SelectedItems.Count > 0)
                    //{
                        //for (int i = this.DataGrid01.SelectedItems.Count - 1; i >= 0; i--)
                        //{
                            //Datas.Remove(this.DataGrid01.SelectedItems[i] as Data);
                        //}
                    //}//删除行的另一种方法
                    e.Handled = true;//将按键事件标记为已处理,不再发送到操作系统中
                    return;
                }
                if (e.Key == Key.Return)//Enter键
                {
                    Data data = new Data();
                    Datas.Add(data);
                    e.Handled = true;
                    return;
                }
            }
        }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35

五、DataGrid数据触发器

在DataGrid中显示数据时,有时需要实现当某一字段的数据为特定值时,该数据所在的单元行更改如背景色等样式,这时可以使用Style.Triggers进行设置,前台代码如下:

<DataGrid.RowHeaderStyle>
    <Style TargetType="DataGridRowHeader">
        <Style.Triggers>
            <DataTrigger Binding="{Binding Type}" Value="1">
                <Setter Property="Background"  Value="Red"></Setter>
            </DataTrigger>
            <DataTrigger Binding="{Binding Type}" Value="0">
                <Setter Property="Background" Value="White"></Setter>                                                        
            </DataTrigger>
        </Style.Triggers>
    </Style>
</DataGrid.RowHeaderStyle>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

代码中绑定的Type是DataGrid绑定的数据源中的某一成员名,当值为1时背景变红,为0时背景变白。

参考文档

DataGrid 类
WPF的DataGrid用法
WPF:获取DataGrid控件单元格DataGridCell
获取wpf datagrid当前被编辑单元格的内容
Wpf DataGrid动态添加列,行数据(一)
WPF DataGrid 编辑和新增行问题
[Silverlight学习笔记]如何获取ItemsControl的DataTemplate中定义的控件?
DataGrid中的子控件Combox之数据源绑定(WPF)
WPF DataGrid 新增、删除行
WPF-DataGrid-获取选中单元所在行数和列数
关于c#:WPF DataGrid-新行事件?
WPF中DataGrid 动态增加列
【WPF】设置DataGrid表头内容居中显示
WPF 修改DataGrid选中行时的颜色
WPF DataGridComboBoxColumn使用(绝对良心版)
WPF 后台创建 DateTemplate
将DataGrid的SelectedItem滚动到第一行(WPF)
DataGridComboBoxColumn绑定后显示空白的问题
WPF:后台获取DataGrid列的绑定字段。
WPF DataGrid 触发器
DataGrid根据值改变行样式-DataTrigger触发器
AutoGenerateColumns的使用属性介绍
WPF datagrid AutoGenerateColumns隐藏部分列

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/不正经/article/detail/582844
推荐阅读
相关标签
  

闽ICP备14008679号