2011-09-27 72 views
2

我想设置一个Treeview派生类,它可以用作我的应用程序中的所有Treeview实例的公用模板,但需要额外的格式和模板每个实例。如何添加额外的项目模板到扩展WPF树视图

为基础,我有从树视图下降,与常见的样式和一个单一的标准数据模板

<TreeView x:Class="BaseTreeView" ... > 
    <TreeView.ItemContainerStyle> ... </TreeView.ItemContainerStyle> 
    <TreeView.Resources> 
     <HierarchicalDataTemplate ItemsSource="{Binding Children}" DataType="{x:Type local:BaseTreeViewItem}"> 
      <TextBlock Text="{Binding Caption}" /> 
     </HierarchicalDataTemplate> 
    </TreeView.Resources> 
</TreeView> 

然后在每个窗口中的用户控件,我使用这个扩展的树形目录,并添加额外的数据模板我正在显示的具体TreeviewItems。

例如

<Window x:Class="Window1" ... > 
    ... 
    <BaseTreeView ItemsSource="{Binding RootTreeItems}" > 
     <MyTreeView.Resources> 
      <HierarchicalDataTemplate ItemsSource="{Binding Children}" DataType="{x:Type ExtendedTreeViewItem1}"> 
       <StackPanel Orientation="Horizontal"> 
        <Image Source="Images/Image1.png" /> 
        <TextBlock Text="{Binding Caption}" /> 
       </StackPanel> 
      </HierarchicalDataTemplate> 
      <DataTemplate DataType="{x:Type ExtendedTreeViewItem2}"> 
       <StackPanel Orientation="Horizontal"> 
        <Image Source="Images/Image2.png" /> 
        <TextBlock Text="{Binding Caption}" /> 
       </StackPanel> 
      </DataTemplate> 
     </MyTreeView.Resources> 
    </BaseTreeView> 
    ... 
</Window> 

编译没有问题,但在运行时我得到一个错误

“ '设置属性 'System.Windows.ResourceDictionary.DeferrableContent' 引发了异常。'行号“27”和行位置“59”。“

“无法重新初始化ResourceDictionary实例。”

有没有什么办法解决这个问题,或者有人建议一个更好的方法来建立一个基础树视图模板和多个后代版本。

+0

看起来像它的抱怨有关设置资源的两倍,所以你必须删除一个。也许在以后的事件中以编程方式填充基本控件(BaseTreeView)资源?加载,也许? Icky不得不放弃代码,但会解决眼前的问题。 –

回答

0

你可以尝试移动你的模板来<Window.Resources>,而不是<MyTreeView.Resources>

如果它不工作,也许使用DataTemplateSelector最适合你的情况。您可以创建一个DataTemplateSelector类是这样的:

public class ExtendedTreeViewTemplateSelector : DataTemplateSelector 
{ 
    public DataTemplate ExtendedTreeViewItem1Template { get; set; } 
    public DataTemplate ExtendedTreeViewItem2Template { get; set; } 


    public override DataTemplate SelectTemplate(object item, DependencyObject container) 
    { 
     if (item is ExtendedTreeViewItem1) 
      return ExtendedTreeViewItem1Template; 
     if (item is ExtendedTreeViewItem2) 
      return ExtendedTreeViewItem2Template; 
    } 
} 

,然后用它在你的XAML这样的:

<Window x:Class="Window1" ... > 
    <Window.Resources> 
     <HierarchicalDataTemplate x:Key="extendedTreeViewItem1Template" ItemsSource="{Binding Children}" DataType="{x:Type ExtendedTreeViewItem1}"> 
      <StackPanel Orientation="Horizontal"> 
       <Image Source="Images/Image1.png" /> 
       <TextBlock Text="{Binding Caption}" /> 
      </StackPanel> 
     </HierarchicalDataTemplate> 
     <DataTemplate x:Key="extendedTreeViewItem2Template" DataType="{x:Type ExtendedTreeViewItem2}"> 
      <StackPanel Orientation="Horizontal"> 
       <Image Source="Images/Image2.png" /> 
       <TextBlock Text="{Binding Caption}" /> 
      </StackPanel> 
     </DataTemplate> 
     <selector:ExtendedTreeViewTemplateSelector x:Key="treeViewTemplateSelector" 
                ExtendedTreeViewItem1Template="{StaticResource extendedTreeViewItem1Template}" 
                ExtendedTreeViewItem2Template="{StaticResource extendedTreeViewItem2Template}" /> 
    </Window.Resources> 
    ... 
    <BaseTreeView ItemsSource="{Binding RootTreeItems}" 
        ItemTemplateSelector={StaticResource treeViewTemplateSelector}" /> 
    ... 
</Window>