【问题标题】:WPF Treeview - Binding to a collection with different depths, and styling differentlyWPF Treeview - 绑定到具有不同深度的集合,并且样式不同
【发布时间】:2010-10-20 06:02:46
【问题描述】:

为这篇长文道歉 -- 阅读了一些关于此的主题,但仍然难以实施。基本上,我有一个对象集合,定义为:

public class LibData
{
    public string Name { get; set; }
    ObservableCollection<LibObject> _list;
    public ObservableCollection<LibObject> List { get { return _list; } }

    public LibData(string name, LibDataType type)
    {
        this.Name = name;
        _list = new ObservableCollection<LibObject>();
    }
}

和对象:

public class LibObject
{
    public string Name { get; set; }

    public LibObject(string name)
    {
        this.Name = name;
    }
}

我的主要问题是在 XAML 中,以及这个 TreeView 的样式。我需要为“根”项目设置特定样式,并为“叶子”设置特定样式。问题是,绑定列表中的一项是“Root->Leaf”,另一项是“Root->Child->Leaf”。 我试过这个:

<TreeView x:Name="myTree" ItemsSource="{x:Static local:myDataList}">
     <TreeView.ItemTemplate>
         <HierarchicalDataTemplate ItemsSource="{Binding Path=List}" >
             <Grid>
                 <StackPanel Orientation="Horizontal">
                      <TextBlock Text="{Binding Path=Name}" />
                      <CheckBox IsChecked="True" Content="HeaderCheckbox"/>
                 </StackPanel>
             </Grid>
         <HierarchicalDataTemplate.ItemTemplate >
              <DataTemplate>
                  <Grid>
            <StackPanel Orientation="Horizontal">
                <CheckBox IsChecked="True" Content="LeafCheckbox" />
                <TextBlock Text="{Binding Path=Name}"/>
            </StackPanel>
                  </Grid>
              </DataTemplate>
          </HierarchicalDataTemplate.ItemTemplate>
      </HierarchicalDataTemplate>
  </TreeView.ItemTemplate>

这显然适用于“Root->Leaf”项目,但不适用于“Root-Child-Leaf”。 XAML 实现似乎更像是一种“硬编码”解决方案,我知道项目布局始终是“根-> 叶”——如何使这个动态化? 同样,我已经看到了不同级别的解决方案(包括使用转换器),但我遇到的问题是我需要特定的样式来根和叶,而两者之间的级别不需要任何东西。 我想知道我是否完全看错了......

【问题讨论】:

    标签: wpf treeview


    【解决方案1】:

    简单的方法来做到这一点。从 TreeView 中拉出 DataTemplates 并将它们放在资源部分中。为每个 DataTemplate 指定 DataType 属性,但不要包含键。 TreeView 上的 ItemTemplateSelector(DataTemplateSelector 类型的属性)将发挥魔力,使用适合正确项目类型的 DataTemplate。

    为 Root 和 Child 类型创建 HierarchicalDataTemplate,为 Leaf 类型创建 DataTemplate。

    类似这样的:

    <Window.Resources>
        <ResourceDictionary>
    
            <DataTemplate DataType="{x:Type local:Leaf}">
                <Grid>
                    <StackPanel Orientation="Horizontal">
                        <CheckBox IsChecked="True" Content="LeafCheckbox" />
                        <TextBlock Text="{Binding Path=SomeValue}"/>
                    </StackPanel>
                </Grid>
            </DataTemplate>
    
            <HierarchicalDataTemplate DataType="{x:Type local:Child}"
                                      ItemsSource="{Binding Children}">
                <StackPanel Orientation="Horizontal">
                    <TextBlock Text="Child " />
                    <TextBlock Text="{Binding Path=SomeValue}" />
                </StackPanel>
            </HierarchicalDataTemplate>
    
            <HierarchicalDataTemplate DataType="{x:Type local:Root}"
                                      ItemsSource="{Binding Children}">
                <Grid>
                    <StackPanel Orientation="Horizontal">
                        <TextBlock Text="Root " />
                        <TextBlock Text="{Binding Path=SomeValue}" />
                    </StackPanel>
                </Grid>
            </HierarchicalDataTemplate>
    
        </ResourceDictionary>
    </Window.Resources>
    
    <Grid>
        <TreeView x:Name="myTree" ItemsSource="{Binding}" />
    </Grid>
    

    【讨论】:

    • 从树视图资源中取出模板的部分是否重要?我没有提到这一点,但我在向导中使用它,每个“窗口”实际上是一个 PageFunction - 据我了解,没有资源。
    • 是的,有必要将 DataTemplates 从 TreeView 中取出。您希望这样做,因为您不想直接指定 ItemTemplate,因为在这种情况下,模板应根据项目类型而更改。在我匆忙的示例中,我将 DataTemplates 放在 Window.Resources 中,但这也可以很容易地放在 TreeView.Resources 中。
    • 哦,我明白了——所以把它放在 子句中就可以了。凉爽的。我会试一试。谢谢。
    • 更改了我的数据结构并使用了您的方法 - 效果很好
    猜你喜欢
    • 1970-01-01
    • 2020-06-10
    • 2018-07-16
    • 2015-06-29
    • 1970-01-01
    • 1970-01-01
    • 2013-08-31
    • 2010-12-27
    • 1970-01-01
    相关资源
    最近更新 更多