Не могу найти имя DataGridColumn программно
-
14-10-2019 - |
Вопрос
Я нашел коллекцию столбцов в своем DataGrid и надеялся итерации через нее, чтобы найти определенное имя столбца. Тем не менее, я не могу понять, как обратиться к атрибуту x: name столбца. Этот XAML иллюстрирует мою проблему с DataGridTextColumn и DataGridTemplateColumn:
<t:DataGrid x:Name="dgEmployees" ItemsSource="{Binding Employees}"
AutoGenerateColumns="false" Height="300" >
<t:DataGrid.Columns>
<t:DataGridTextColumn x:Name="FirstName" Header="FirstName"
Binding="{Binding FirstName}" />
<t:DataGridTemplateColumn x:Name="LastName" Header="LastName" >
<t:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding LastName}" />
</DataTemplate>
</t:DataGridTemplateColumn.CellTemplate>
</t:DataGridTemplateColumn>
</t:DataGrid.Columns>
</t:DataGrid>
А вот мой код:
DataGrid dg = this.dgEmployees;
foreach (var column in dg.Columns)
{
System.Console.WriteLine("name: " + (string)column.GetValue(NameProperty));
}
Во время выполнения, значение не присутствует; Column.getValue ничего не возвращает. Используя Snoop, я подтвердил, что нет свойства имен на DataGridTextColumn или DataGridTemplateColumn.
Что мне не хватает?
Решение
У WPF есть две разные, но сходные концепции, x: имя, которое используется для создания поля, которое ссылается на элемент, определенный в XAML, то есть подключение вашего кода-иминда к вашему XAML, и FrameworkElement.name, который уникально называет элемент в namescope.
Если элемент имеет свойство FrameworkElement.Name, x: имя установит это свойство на значение, приведенное в XAML. Тем не менее, есть случаи, когда полезно связывать неразмерные элементы с полями в коде, например, в вашем примере.
Смотрите этот связанный вопрос:
В WPF каковы различия между атрибутами x: имени и имени?
В качестве альтернативы вы можете определить свое собственное подключенное свойство, которое можно использовать для названия столбцов. Прилагаемое свойство определяется следующим образом:
public class DataGridUtil
{
public static string GetName(DependencyObject obj)
{
return (string)obj.GetValue(NameProperty);
}
public static void SetName(DependencyObject obj, string value)
{
obj.SetValue(NameProperty, value);
}
public static readonly DependencyProperty NameProperty =
DependencyProperty.RegisterAttached("Name", typeof(string), typeof(DataGridUtil), new UIPropertyMetadata(""));
}
Затем вы можете назначить имя каждому столбцу ...
xmlns:util="clr-namespace:WPFDataGridExamples"
<t:DataGrid x:Name="dgEmployees" ItemsSource="{Binding Employees}"
AutoGenerateColumns="false" Height="300" >
<t:DataGrid.Columns>
<t:DataGridTextColumn util:DataGridUtil.Name="FirstName" Header="FirstName"
Binding="{Binding FirstName}" />
<t:DataGridTemplateColumn util:DataGridUtil.Name="LastName" Header="LastName" >
<t:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding LastName}" />
</DataTemplate>
</t:DataGridTemplateColumn.CellTemplate>
</t:DataGridTemplateColumn>
</t:DataGrid.Columns>
</t:DataGrid>
Затем обратитесь к этому имени в коде следующим образом:
DataGrid dg = this.dgEmployees;
foreach (var column in dg.Columns)
{
System.Console.WriteLine("name: " + DataGridUtil.GetName(column));
}
надеюсь, это поможет
Другие советы
Вы можете использовать запрос LINQ, чтобы найти имя заголовков столбцов DataGrid
dgvReports.Columns.Select(a=>a.Header.ToString()).ToList()
где dgvreports является названием DataGrid.