2013-01-03 49 views
0

我想使用HierarchicalDataTemplate遞歸創建其中的項目的擴展器,但是當我使用HierarchicalDataTemplate時,我只能得到顯示的第一級項目。HierarchicalDataTemplate不工作

如果您需要任何信息,請讓我知道。

繼承人的什麼XAML會是什麼樣子,如果我是用手寫:

<GroupBox Header="SectionHeader"> 
    <StackPanel > 
     <Expander VerticalAlignment="Top" Header="SubSectionHeader"> 
      <StackPanel> 
       <Expander VerticalAlignment="Top" Header="SubSectionHeader" Margin="10,0,0,0"> 
        <StackPanel> 
         etc...... 
        </StackPanel> 
       </Expander> 
     </Expander> 
    </StackPanel> 
</GroupBox> 

繼承人是我到目前爲止所。

的XAML:

<ItemsControl Name="lstMain" ItemsSource="{Binding Sections}"> 
    <ItemsControl.ItemTemplate> 
     <DataTemplate> 
      <GroupBox Header="{Binding Section.SectionName}"> 
       <ItemsControl ItemsSource="{Binding SubSections}" ItemTemplate="{StaticResource BinderTemplate}" /> 
      </GroupBox> 
     </DataTemplate> 
    </ItemsControl.ItemTemplate> 
</ItemsControl> 

<HierarchicalDataTemplate x:Key="BinderTemplate" ItemsSource="{Binding Path=SubSections}" DataType="{x:Type local:SubSectionViewModel}"> 
    <StackPanel> 
     <Expander Header="{Binding SubSection.SubSectionName}"/> 
    </StackPanel> 
</HierarchicalDataTemplate> 

數據類:

class TopViewModel 
{ 
    ObservableCollection<SectionViewModel> _sections = new ObservableCollection<SectionViewModel>(); 

    public ObservableCollection<SectionViewModel> Sections 
    { 
     get 
     { 
      return _sections; 
     } 
     set 
     { 
      _sections = value; 
     } 
    } 
} 

public class SectionViewModel 
{ 
    ObservableCollection<MaterialViewModel> _materials = new ObservableCollection<MaterialViewModel>(); 
    ObservableCollection<SubSectionViewModel> _subSections = new ObservableCollection<SubSectionViewModel>(); 
    Section _section; 

    public Section Section 
    { 
     get 
     { 
      return _section; 
     } 
     set 
     { 
      _section = value; 
     } 
    } 

    public string MaterialName 
    { 
     get { return Section.SectionName; } 
     set { Section.SectionName = value; } 
    } 

    public ObservableCollection<MaterialViewModel> Materials 
    { 
     get 
     { 
      return _materials; 
     } 
     set 
     { 
      _materials = value; 
     } 
    } 

    public ObservableCollection<SubSectionViewModel> SubSections 
    { 
     get 
     { 
      return _subSections; 
     } 
     set 
     { 
      _subSections = value; 
     } 
    } 
} 

public class SubSectionViewModel 
{ 
    ObservableCollection<MaterialViewModel> _materials = new ObservableCollection<MaterialViewModel>(); 
    ObservableCollection<SubSectionViewModel> _subSections = new ObservableCollection<SubSectionViewModel>(); 
    SubSection _subSection; 

    public ObservableCollection<MaterialViewModel> Materials 
    { 
     get 
     { 
      return _materials; 
     } 
     set 
     { 
      _materials = value; 
     } 
    } 

    public ObservableCollection<SubSectionViewModel> SubSections 
    { 
     get 
     { 
      return _subSections; 
     } 
     set 
     { 
      _subSections = value; 
     } 
    } 

    public SubSection SubSection 
    { 
     get 
     { 
      return _subSection; 
     } 
     set 
     { 
      _subSection = value; 
     } 
    } 
} 

回答

3

你缺少一個鍵位的HierarchicalDataTemplate - 如何渲染子元素:

<HierarchicalDataTemplate x:Key="BinderTemplate" 
    ItemsSource="{Binding Path=SubSections}" 
    DataType="{x:Type local:SubSectionViewModel}"> 
    <StackPanel> 
     <Expander Header="{Binding SubSection.SubSectionName}"> 
      <ItemsControl Margin="5,0,0,0" 
         ItemsSource="{Binding SubSections}" 
         ItemTemplate="{DynamicResource BinderTemplate}"/> 
     </Expander> 
    </StackPanel> 
</HierarchicalDataTemplate> 

編輯:不要偷@BDE的雷霆,但他/她大部分是正確的使用DataType - 但這是你「簡化」上述XAML的方式:

<Window x:Class="WpfApplication1.Window1" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:local="clr-namespace:WpfApplication1" 
     Title="Window1" Height="300" Width="300"> 
    <Window.Resources> 
     <!-- normal template for sections --> 
     <DataTemplate DataType="{x:Type local:SectionViewModel}"> 
      <GroupBox Header="{Binding Section.SectionName}"> 
       <ItemsControl ItemsSource="{Binding SubSections}"/> 
      </GroupBox> 
     </DataTemplate> 
     <!-- hierarchical template for subsections --> 
     <HierarchicalDataTemplate 
       DataType="{x:Type local:SubSectionViewModel}"> 
      <StackPanel> 
       <Expander Header="{Binding SubSection.SubSectionName}"> 
        <ItemsControl Margin="5,0,0,0" 
         ItemsSource="{Binding SubSections}"/> 
       </Expander> 
      </StackPanel> 
     </HierarchicalDataTemplate> 
    </Window.Resources> 
    <Grid> 
     <!-- 
      no need to specify ItemTemplate if WPF can suss out all the item types 
     --> 
     <ItemsControl Name="lstMain" ItemsSource="{Binding Sections}"/> 
    </Grid> 
</Window> 
+0

Brilliant。謝謝:)我曾嘗試這樣做,但試圖將該模板用作靜態資源而不是動態資源並得到了編譯時錯誤:) – user589195

0

Section.SectionName應MaterialName?

看行:

<ItemsControl ItemsSource="{Binding SubSections}" ItemTemplate="{StaticResource BinderTemplate}" /> 

<HierarchicalDataTemplate x:Key="BinderTemplate" ItemsSource="{Binding Path=SubSections}" DataType="{x:Type local:SubSectionViewModel}"> 

我想,如果杉杉行結合是小節,所以第二行,而不是

{Binding Path=SubSections} 

你可能必須寫

{Binding} 

SubSectionName我找不到你的課程。

請添加更多的類

1

HierarchicalDataTemplate的替代方法是增加一個ItemsControlExpander數據中的模板,並綁定ItemsSource那裏。

此外,由於您在數據模板定義中指定了DataType,所以您不必直接通過頂級ItemsControl的密鑰名稱設置ItemTemplate

如果modifiy您XAML這樣它可能會做你想要什麼:

<DataTemplate DataType="{x:Type local:SubSectionViewModel}"> 
    <StackPanel> 
     <Expander Header="{Binding SubSection.SubSectionName}"> 
      <ItemsControl ItemsSource="{Binding SubSections}"/> 
     </Expander> 
    </StackPanel> 
</DataTemplate> 

<ItemsControl Name="lstMain" ItemsSource="{Binding Sections}"> 
    <ItemsControl.ItemTemplate> 
     <DataTemplate> 
      <GroupBox Header="{Binding Section.SectionName}"> 
       <ItemsControl ItemsSource="{Binding SubSections}"/> 
      </GroupBox> 
     </DataTemplate> 
    </ItemsControl.ItemTemplate> 
</ItemsControl> 
+0

您需要第一個DataTemplate上的數據類型以及template-> type inference才能正常工作(請參閱我的編輯) – JerKimball

+0

同意,如果您希望資源部分中的所有數據模板一起使用。在我發佈的代碼中,由於'SectionViewModel'的模板直接在ItemsControl中指定,而不是在資源中指定,它仍然可以正常工作?看起來它至少在我的測試中起作用。 – WildCrustacean

+0

呵呵。有趣的是,當我在Blend中一起扔出一個快速骨架時,它並沒有推斷出模板類型... – JerKimball