2016-04-22 108 views
2

我有這種類型的XML文檔。帶有Chekbox的TreeView僅適用於兒童

<?xml version="1.0" encoding="utf-8"?> 
<Parameters> 
    <Param Name="Father0_0" ID="1"> 
    <Param0 Name="Father0_1" ID="2"> 
     <Param1 Name="Father0_2" ID="3"> 
     <Param2 Name="Child0_0" ID_ch="1"/> 
     </Param1> 
     <Param1 Name="Father0_3" ID="4"> 
     <Param2 Name="Father0_4" ID="5"> 
      <Param3 Name="Child0_3" ID_ch="2"/> 
     </Param2> 
     </Param1> 
    </Param0> 
    </Param> 
    <Param Name="Father1_0" ID="6"> 
    <Param0 Name="Child1_0" ID_ch="3" /> 
    </Param> 
    <Param Name="Father2_0" ID="7"> 
    <Param1 Name="Child2_0" ID_ch="3"/> 
    </Param> 
<Param Name="Child3_0" ID_ch="4"/> 
</Parameters> 

.CS

所以我打開我的XML

XmlDataProvider _xml = FindResource("xmldata") as XmlDataProvider; 
var xmlDocument = new XmlDocument(); 
xmlDocument.Load("34.xml"); 
_xml.Document = xmlDocument; 

,如果我這樣做如下的XAML描述我得到Chechkboks了在樹視圖的所有項目?

.XAML

<Window.Resources> 
<XmlDataProvider x:Key="xmldata" XPath="Parameters"/> 
<!--The same is done for the Param0,Param1,Param2,Param3 changing DataType=""--> 
<HierarchicalDataTemplate DataType="Param" ItemsSource="{Binding XPath= ./*}"> 
    <StackPanel Orientation="Horizontal"> 
    <CheckBox Margin="5,0,0,0" Content="{Binding [email protected]}" /> 
    </StackPanel> 
</HierarchicalDataTemplate> 
<!--------------------------------> 
</Window.Resources> 
<Grid> 
<TreeView ItemsSource="{Binding Source={StaticResource xmldata}, XPath=Param}" /> 
</Grid> 

如何使CheckBox僅用於兒童。

回答

2

更通用的方法對XML數據的情況下定製TreeView是使自己的數據模板選擇:

public class ItemTemplateSelector : DataTemplateSelector 
{ 
    public DataTemplate ParentTemplate { get; set; } 

    public DataTemplate ChildTemplate { get; set; } 

    public override DataTemplate SelectTemplate(object item, DependencyObject container) 
    { 
     var element = item as XElement; 
     if (element != null) 
     { 
      return element.Elements().Any() ? ParentTemplate : ChildTemplate; 
     } 

     return base.SelectTemplate(item, container); 
    } 
} 

下面是它可以在XAML中使用:

<Window x:Class="WpfApplication2.MainWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:local="clr-namespace:WpfApplication2" 
     Title="MainWindow" Height="350" Width="525"> 

    <Window.Resources> 
     <local:ItemTemplateSelector x:Key="ItemTemplateSelectorKey"> 

      <local:ItemTemplateSelector.ParentTemplate> 
       <HierarchicalDataTemplate ItemsSource="{Binding Elements}"> 
        <TextBlock Text="{Binding Attribute[Name].Value}"/> 
       </HierarchicalDataTemplate> 
      </local:ItemTemplateSelector.ParentTemplate> 

      <local:ItemTemplateSelector.ChildTemplate> 
       <DataTemplate> 
        <CheckBox Content="{Binding Attribute[Name].Value}"/> 
       </DataTemplate> 
      </local:ItemTemplateSelector.ChildTemplate> 

     </local:ItemTemplateSelector> 
    </Window.Resources> 

    <TreeView ItemsSource="{Binding Root.Elements}" 
       ItemTemplateSelector="{StaticResource ItemTemplateSelectorKey}"/> 
</Window> 

代碼隱藏:

public partial class MainWindow : Window 
{ 
    public MainWindow() 
    { 
     InitializeComponent(); 
     DataContext = XDocument.Parse(Properties.Resources.XmlFile); 
    } 
} 

這是結果:

enter image description here

注意,我一直在使用XDocument API,而不是XmlDocument之一。

UPD
ChildTemplate被簡化一點更可讀的,但是這與顯示在內容(例如,參見this答案爲解釋)強調的問題。

+0

完美地工作,僅強調示例,告訴我如何單擊複選框以獲取有關孩子和父母的信息。我的意思是從XML標籤「名稱」,「價值」,「ID」。非常感謝你。 – XmaksasX

+0

當您需要一些複雜的邏輯時,XML不適合您的數據上下文。如果你需要一個類似「當複選框被點擊時,然後做點什麼」的代碼,那麼考慮將你的XML轉換爲視圖模型。 – Dennis

+0

我更正了上面的XML,當我點擊複選框時需要獲取孩子的ID和它的第一個父母的ID – XmaksasX

2

您可以檢查是否TreeViewItem沒有項目,然後是子節點,你可以綁定你CheckBox.Visibility爲:

 <HierarchicalDataTemplate DataType="Param" ItemsSource="{Binding XPath= ./*}"> 
     <StackPanel Orientation="Horizontal"> 
      <CheckBox Margin="5,0,0,0" Content="{Binding [email protected]}" > 
       <CheckBox.Style> 
        <Style TargetType="CheckBox"> 
         <Setter Property="Visibility" Value="Collapsed"/> 
         <Style.Triggers> 
          <DataTrigger Binding="{Binding Items.Count, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type TreeViewItem}}}" Value="0"> 
           <Setter Property="Visibility" Value="Visible"/> 
          </DataTrigger> 
         </Style.Triggers> 
        </Style> 
       </CheckBox.Style> 
      </CheckBox> 
     </StackPanel> 
    </HierarchicalDataTemplate> 
+0

工作但完全隱藏父項的名稱,您需要在stackPanel中添加一個文本框,非常感謝。 – XmaksasX