无法以编程方式找到DataGridColumn的名称

Dan*_*l R 5 wpf datagridcolumn wpfdatagrid

我在我的数据网格中找到了Columns集合,并希望迭代它以找到某个列Name.但是,我无法弄清楚如何处理列的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>
Run Code Online (Sandbox Code Playgroud)

这是我的代码:

    DataGrid dg = this.dgEmployees;
    foreach (var column in dg.Columns) 
    {
        System.Console.WriteLine("name: " + (string)column.GetValue(NameProperty));
    }
Run Code Online (Sandbox Code Playgroud)

在运行时,不存在任何值; column.GetValue不返回任何内容.使用Snoop,我确认DataGridTextColumn或DataGridTemplateColumn上没有Name属性.

我错过了什么?

Col*_*inE 13

WPF有两个不同但相似的概念,x:Name,用于创建引用XAML中定义的元素的字段,即将代码隐藏连接到XAML,以及FrameworkElement.Name,它唯一地命名一个元素.名称范围.

如果元素具有FrameworkElement.Name属性,则x:Name将此属性设置为XAML中给定的值.但是,有些情况下将非FrameworkElement元素链接到代码隐藏中的字段很有用,例如在您的示例中.

看到这个相关的问题:

在WPF中,x:Name和Name属性之间有什么区别?

作为替代方案,您可以定义自己的附加属性,该属性可用于命名列.附加属性定义如下:

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(""));

}
Run Code Online (Sandbox Code Playgroud)

然后,您可以为每个列指定一个名称......

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>
Run Code Online (Sandbox Code Playgroud)

然后在代码中访问此名称,如下所示:

DataGrid dg = this.dgEmployees;
foreach (var column in dg.Columns) 
{
    System.Console.WriteLine("name: " + DataGridUtil.GetName(column));
}
Run Code Online (Sandbox Code Playgroud)

希望有所帮助