WPF TreeView - 混淆子节点的数据绑定和样式
WPF TreeView - Confusing data binding and style for child nodes
我对 TreeView 的 WPF 数据绑定和样式声明感到困惑,尤其是对于子节点。
我的 ViewModel 包含一个具有以下层次结构的对象:
- Component1
- SubcomponentA
- SubcomponentB
- Component2
- SubcomponentX
- SubcomponentY
- SubcomponentZ
我想修改 XAML 文件,这样我就不必在 .cs 文件中执行任何操作。
这段代码实际有效:
<TreeView Name="tvComponent" ItemsSource="{Binding BpModule.BpComponentPrototypes.Elements}">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding BpSubcomponents.Elements}">
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_run"></CheckBox>
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
但是,我想为根节点和子节点创建不同的样式。
我用几乎完全不同的 XAML 代码尝试了不同的方法。但主要问题是描述子节点与其父节点绑定的依赖关系,因此它们在运行时保持为空。
你能帮帮我吗?
谢谢。
在我看来,您可以使用隐式 DataTemplate
机制(查看 here 到数据类型 属性)。通过这种方式,您可以定义更多 DataTemplates
,其中每个 "linked" 到特定的 Type
.
<TreeView Name="tvComponent" ItemsSource="{Binding BpModule.BpComponentPrototypes.Elements}">
<TreeView.Resources>
<HierarchicalDataTemplate DataType="{x:Type local:RootType}"ItemsSource="{Binding ...}">
...
</HierarchicalDataTemplate>
<HierarchicalDataTemplate DataType="{x:Type local:ComponentType}" ItemsSource="{Binding BpSubcomponents.Elements}">
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_run"></CheckBox>
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</HierarchicalDataTemplate>
<DataTemplate DataType="{x:Type local:SubcomponentType}">
...
</DataTemplate>
</TreeView.Resources>
</TreeView>
否则,您始终可以使用 DataTemplateSelector 创建自己的逻辑,为您选择正确的模板。
好吧,不知何故我实现了为根节点和子节点提供不同的设计。这是 XAML 代码:
<TreeView Name="tvSoftwareComponentPrototypes" ItemsSource="{Binding Path=BpModule.BpComponentPrototypes.Elements}">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding BpSubcomponents.Elements}">
<HierarchicalDataTemplate.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_run"></CheckBox>
<Image Source="/Resources/SubComponent.png" Margin="5,0,3,0" />
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</DataTemplate>
</HierarchicalDataTemplate.ItemTemplate>
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_swc" Checked="cb_swc_Checked" Unchecked="cb_swc_Unchecked"></CheckBox>
<Image Source="/Resources/Component.png" Margin="5,0,3,0" />
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
下一个问题是我无法在运行时访问复选框。
WPF 把我吓坏了:/
编辑:
稍等.. 实际上这很简单,只需将复选框更改为以下 XAML 代码:
<CheckBox Name="cb_swc" IsChecked="{Binding Path=PropertyName, Mode=TwoWay}"/>
我对 TreeView 的 WPF 数据绑定和样式声明感到困惑,尤其是对于子节点。
我的 ViewModel 包含一个具有以下层次结构的对象:
- Component1
- SubcomponentA
- SubcomponentB
- Component2
- SubcomponentX
- SubcomponentY
- SubcomponentZ
我想修改 XAML 文件,这样我就不必在 .cs 文件中执行任何操作。
这段代码实际有效:
<TreeView Name="tvComponent" ItemsSource="{Binding BpModule.BpComponentPrototypes.Elements}">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding BpSubcomponents.Elements}">
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_run"></CheckBox>
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
但是,我想为根节点和子节点创建不同的样式。 我用几乎完全不同的 XAML 代码尝试了不同的方法。但主要问题是描述子节点与其父节点绑定的依赖关系,因此它们在运行时保持为空。
你能帮帮我吗?
谢谢。
在我看来,您可以使用隐式 DataTemplate
机制(查看 here 到数据类型 属性)。通过这种方式,您可以定义更多 DataTemplates
,其中每个 "linked" 到特定的 Type
.
<TreeView Name="tvComponent" ItemsSource="{Binding BpModule.BpComponentPrototypes.Elements}">
<TreeView.Resources>
<HierarchicalDataTemplate DataType="{x:Type local:RootType}"ItemsSource="{Binding ...}">
...
</HierarchicalDataTemplate>
<HierarchicalDataTemplate DataType="{x:Type local:ComponentType}" ItemsSource="{Binding BpSubcomponents.Elements}">
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_run"></CheckBox>
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</HierarchicalDataTemplate>
<DataTemplate DataType="{x:Type local:SubcomponentType}">
...
</DataTemplate>
</TreeView.Resources>
</TreeView>
否则,您始终可以使用 DataTemplateSelector 创建自己的逻辑,为您选择正确的模板。
好吧,不知何故我实现了为根节点和子节点提供不同的设计。这是 XAML 代码:
<TreeView Name="tvSoftwareComponentPrototypes" ItemsSource="{Binding Path=BpModule.BpComponentPrototypes.Elements}">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding BpSubcomponents.Elements}">
<HierarchicalDataTemplate.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_run"></CheckBox>
<Image Source="/Resources/SubComponent.png" Margin="5,0,3,0" />
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</DataTemplate>
</HierarchicalDataTemplate.ItemTemplate>
<StackPanel Orientation="Horizontal">
<CheckBox Name="cb_swc" Checked="cb_swc_Checked" Unchecked="cb_swc_Unchecked"></CheckBox>
<Image Source="/Resources/Component.png" Margin="5,0,3,0" />
<TextBlock Text="{Binding ShortName}" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
下一个问题是我无法在运行时访问复选框。 WPF 把我吓坏了:/
编辑:
稍等.. 实际上这很简单,只需将复选框更改为以下 XAML 代码:
<CheckBox Name="cb_swc" IsChecked="{Binding Path=PropertyName, Mode=TwoWay}"/>