Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/wpf/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Wpf 在代码中添加项时,对树视图使用ItemTemplate_Wpf_Xaml_Treeview_Datatemplate_Itemtemplate - Fatal编程技术网

Wpf 在代码中添加项时,对树视图使用ItemTemplate

Wpf 在代码中添加项时,对树视图使用ItemTemplate,wpf,xaml,treeview,datatemplate,itemtemplate,Wpf,Xaml,Treeview,Datatemplate,Itemtemplate,我正在代码隐藏中手动添加TreeViewItems,希望使用DataTemplate显示它们,但不知道如何显示它们。我希望这样做,但项目显示为空标题。我做错了什么 XAML 您的ItemTemplate正在尝试在TextBlocks中呈现“Name”和“Age”属性,但TreeViewItem没有“Age”属性,并且您没有设置其“Name” 因为您使用的是ItemTemplate,所以不需要将TreeViewItems添加到树中。而是直接添加Person实例: _treeView.Items.A

我正在代码隐藏中手动添加TreeViewItems,希望使用DataTemplate显示它们,但不知道如何显示它们。我希望这样做,但项目显示为空标题。我做错了什么

XAML


您的ItemTemplate正在尝试在TextBlocks中呈现“Name”和“Age”属性,但TreeViewItem没有“Age”属性,并且您没有设置其“Name”

因为您使用的是ItemTemplate,所以不需要将TreeViewItems添加到树中。而是直接添加Person实例:

_treeView.Items.Add(new Person { Name = "Sally", Age = 28});
public Window1()
{
    InitializeComponent(); 
    var bob = new Person { Name = "Bob", Age = 34 }; 
    var sally = new Person { Name = "Sally", Age = 28 }; 

    _treeView.Items.Add(bob); 
    _treeView.Items.Add(sally);

    _treeView.ItemContainerGenerator.StatusChanged += (sender, e) =>
    {
        if (_treeView.ItemContainerGenerator.Status != GeneratorStatus.ContainersGenerated) 
            return;

        var sallyItem = _treeView.ItemContainerGenerator.ContainerFromItem(sally) as TreeViewItem;
        sallyItem.Items.Add(new Person { Name = "Joe", Age = 15 });
    };
}
当然,问题是,您的底层对象(“Person”)没有任何层次结构的概念,因此没有简单的方法将“Joe”添加到“Sally”中。有两个更复杂的选项:

您可以尝试处理TreeView.ItemContainerGenerator.StatusChanged事件并等待生成“Sally”项,然后获取该项的句柄并直接添加Joe:

_treeView.Items.Add(new Person { Name = "Sally", Age = 28});
public Window1()
{
    InitializeComponent(); 
    var bob = new Person { Name = "Bob", Age = 34 }; 
    var sally = new Person { Name = "Sally", Age = 28 }; 

    _treeView.Items.Add(bob); 
    _treeView.Items.Add(sally);

    _treeView.ItemContainerGenerator.StatusChanged += (sender, e) =>
    {
        if (_treeView.ItemContainerGenerator.Status != GeneratorStatus.ContainersGenerated) 
            return;

        var sallyItem = _treeView.ItemContainerGenerator.ContainerFromItem(sally) as TreeViewItem;
        sallyItem.Items.Add(new Person { Name = "Joe", Age = 15 });
    };
}
或者,更好的解决方案是,您可以将层次结构概念引入“Person”对象,并使用HierarchycalDataTemplate定义TreeView层次结构:

XAML:


代码:

使用System.Collections.Generic;
使用System.Windows;
名称空间树测试
{
/// 
///Window1.xaml的交互逻辑
/// 
公共部分类Window1:Window
{
公共窗口1()
{
初始化组件();
var bob=新人{Name=“bob”,年龄=34};
var sally=新人{Name=“sally”,年龄=28};
_treeView.Items.Add(bob);
_treeView.Items.Add(sally);
sally.substances.Add(新成员{Name=“Joe”,年龄=15});
}
}
公共阶层人士
{
公众人士()
{
下属=新列表();
}
公共字符串名称{get;set;}
公共整数{get;set;}
公共列表下属{get;private set;}
}
}

这是一种更“面向数据”的显示层次结构的方法,也是一种更好的IMHO方法。

如果您将数据模板从树状视图中拉出来并放入Window.Resources中,它就会起作用。像这样:

<Window.Resources>    
    <DataTemplate DataType={x:type Person}>
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="{Binding Path=Name}" />
            <TextBlock Text="{Binding Path=Age}" />
        </StackPanel>
    </DataTemplate>
</Window.Resources>


不要忘记在Person之前添加正确的名称空间。

两种解决方案都有效。很抱歉花了这么长时间才回复你。我最终没有使用树,而是实现了一个自定义的分层列表框。马特万岁!正是我所需要的(第二种解决方案)
using System.Collections.Generic;
using System.Windows;

namespace TreeTest
{
    /// <summary>
    /// Interaction logic for Window1.xaml
    /// </summary>
    public partial class Window1 : Window
    {
        public Window1()
        {
            InitializeComponent(); 
            var bob = new Person { Name = "Bob", Age = 34 }; 
            var sally = new Person { Name = "Sally", Age = 28 }; 

            _treeView.Items.Add(bob); 
            _treeView.Items.Add(sally);
            sally.Subordinates.Add(new Person { Name = "Joe", Age = 15 });
        }

    }
    public class Person 
    {
        public Person()
        {
            Subordinates = new List<Person>();
        }

        public string Name { get; set; } 
        public int Age { get; set; }
        public List<Person> Subordinates { get; private set;  }
    }
}
<Window.Resources>    
    <DataTemplate DataType={x:type Person}>
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="{Binding Path=Name}" />
            <TextBlock Text="{Binding Path=Age}" />
        </StackPanel>
    </DataTemplate>
</Window.Resources>