【问题标题】:why the name of the Controls in ItemsControl not displaying in Codebehind file in Wpf为什么 ItemsControl 中的控件名称未显示在 Wpf 的代码隐藏文件中
【发布时间】:2012-05-04 06:51:28
【问题描述】:

我使用 ItemsControl 和 DataTemplate 创建了简单的示例。我想使用文本块中的 C# 代码绑定值。但是我没有在代码隐藏文件中获得文本块名称和数据模板名称,请告诉我为什么。什么如何获取控件的名称?

<ItemsControl ItemsSource="{Binding Path=.}" >
            <ItemsControl.ItemTemplate>
                <DataTemplate x:Name="datatemp">
                        <StackPanel Orientation="Horizontal"> 

<TextBlock  x:Name="Textblock1" Text="{Binding }" FontWeight="Bold" ></TextBlock>
                        <TextBlock Text=", " />
                            <TextBlock Text="{Binding }" x:Name="Textblock2"></TextBlock>
                        <TextBlock Text=", " />
                            <TextBlock Text="{Binding }" x:Name="Textblock3"></TextBlock>
                    </StackPanel>
                </DataTemplate>
            </ItemsControl.ItemTemplate>
        </ItemsControl>

但在代码文件 Textblock1 和其他名称中,即使我只使用了“名称”而不是“x:名称”,也没有显示

【问题讨论】:

  • 你想用数据模板和文本块做什么?

标签: wpf


【解决方案1】:

不会为 DataTemplate 生成任何成员。数据模板仅用于在运行时动态实例化项目,因此在您将项目添加到 ItemsControl 之前,控件甚至不存在,即便如此,我认为 DataTemplate 中各个控件的名称仅对从 DataTemplate 内部使用有用标记。

【讨论】:

  • 谢谢..所以我不能在 DataTempletes 之外使用它们(DT 中的控件)。我说的对吗?
【解决方案2】:

如果需要,您可以在加载 ItemsControl 时生成名称。

    private void OnPopupItemsLoaded(object sender, RoutedEventArgs e)
    {
        var itemsControl = sender as ItemsControl;

        itemsControl.ApplyTemplate();
        var numItems = itemsControl.ItemContainerGenerator.Items.Count();
        for (var i = 0; i < numItems; i++)
        {
            var container = itemsControl.ItemContainerGenerator.ContainerFromIndex(i);
            textBlock = FindVisualChild<TextBlock>(container);
            if (textBlock != null)
            {
                textBlock.Name = SanitizeName(textBlock.Text);
                textBlock.Uid = $"Item{i}";
            }
        }
    }

    private static T FindVisualChild<T>(DependencyObject depObj) where T : DependencyObject
    {
        if (depObj != null)
        {
            for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
            {
                DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
                if (child != null && child is T)
                {
                    return (T)child;
                }

                T childItem = FindVisualChild<T>(child);
                if (childItem != null)
                {
                    return childItem;
                }
            }
        }

        // None found
        return null;
    }

    // FrameworkeElement.Name must start with an underscore or letter and
    // only contain letters, digits, or underscores.
    private string SanitizeName(string textString)
    {
        // Text may start with a digit
        var sanitizedName = "_";

        foreach (var c in textString)
        {
            if (char.IsLetterOrDigit(c))
            {
                sanitizedName += c;
            }
            else
            {
                sanitizedName += "_";
            }
        }

        return sanitizedName;
    }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-08-29
    • 1970-01-01
    • 2012-02-18
    • 1970-01-01
    • 1970-01-01
    • 2017-02-02
    • 2012-12-13
    • 1970-01-01
    相关资源
    最近更新 更多