TreeView 未从 XML 填充

TreeView not filling from XML

我已经准备好接受虐待了。我不明白为什么这不起作用。

这是相关的 XAML:

<Window.Resources>
    <XmlDataProvider x:Key="Family" Source="TestArmy1.xml" XPath="/Army"/>
</Window.Resources>

// 截图

  <TreeView Name="OOB" Height="880" Background="#00000000" 
            BorderBrush="#00000000"  Padding="100,1,1,50" UseLayoutRounding="False"
            MouseRightButtonDown="TreeViewPreviewRightButtonDown" DataContext="{StaticResource Family}" ItemsSource="{Binding XPath=Commander}" FontSize="12" />

这是 C# 代码:

        //This is for dynamically building a treeview with templates from an XML file
        XmlTextReader xmlReader1 = new XmlTextReader("HierarchicalDataTemplate1.xml");
        HierarchicalDataTemplate hierarchicalDataTemplate1 = XamlReader.Load(xmlReader1) as HierarchicalDataTemplate;

        XmlTextReader xmlReader2 = new XmlTextReader("HierarchicalDataTemplate2.xml");
        HierarchicalDataTemplate hierarchicalDataTemplate2 = XamlReader.Load(xmlReader2) as HierarchicalDataTemplate;
        hierarchicalDataTemplate1.ItemTemplate = hierarchicalDataTemplate2;

        XmlTextReader xmlReader3 = new XmlTextReader("HierarchicalDataTemplate3.xml");
        HierarchicalDataTemplate hierarchicalDataTemplate3 = XamlReader.Load(xmlReader3) as HierarchicalDataTemplate;
        hierarchicalDataTemplate2.ItemTemplate = hierarchicalDataTemplate3;

    OOB.ItemTemplate = hierarchicalDataTemplate1;

    Thread updateThread = new Thread(new ParameterizedThreadStart(UpdateTree));
    updateThread.Start(this);

以及构建 TreeView 的代码:

  private void UpdateTree(object obj)
    {
        if (File.Exists("TestArmy1.xml") == false)
        {
            MessageBox.Show("Unable to open\nTestArmy1.xml");
            return;
        }

        MainWindow window = (MainWindow)obj;
        window.Dispatcher.Invoke(DispatcherPriority.Send, new Action(RebuildTree));
    }

    private void RebuildTree()
    {
        XmlDataProvider provider = new XmlDataProvider();
        XmlDocument xmlFile = new XmlDocument();
        xmlFile.Load("TestArmy1.xml");
        provider.Document = xmlFile;
        provider.XPath = "/Army";

        OOB.DataContext = provider;

        XmlNode node = xmlFile.DocumentElement.SelectSingleNode("ArmyName");
        ArmyNameString = node.InnerText;
        ArmyNameTitle.Content = ArmyNameString;

    }

这是已加载的 XML 文件 TestArmy1.xml(现已精简):

<?xml version="1.0" encoding="UTF-8"?>
<Army>
    <ArmyName>The Army of Northern Virginia</ArmyName>
     <Commander> 
         <CommanderName>The Emperor With the Very Long Name!</CommanderName>
         <CommanderLeadership>94</CommanderLeadership> 
            <Division>
                <DivisionCommanderName>Major General William T. Sherman</DivisionCommanderName>
                <DivisionCommanderLeadership>78</DivisionCommanderLeadership>
                    <Unit>
                        <UnitName>'Chasseurs à Cheval Garde"</UnitName>
                        <UnitType>Cavalry</UnitType>
                        <UnitKStrength>3</UnitKStrength>
                        <UnitStrength>456</UnitStrength>
                        <UnitQuality>10</UnitQuality>
                        <UnitMorale>7</UnitMorale>
                        <UnitLeadership>7</UnitLeadership>
                        <UnitAmmunition>99</UnitAmmunition>
                    </Unit>
                </Division>
            <Division>
                <DivisionCommanderName>Marshal Ney</DivisionCommanderName>
                <DivisionCommanderLeadership>8</DivisionCommanderLeadership>
            </Division>
    </Commander>
</Army>

这是 HierarchicalDataTemplate1:​​

<HierarchicalDataTemplate 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    ItemsSource="{Binding XPath=Commander}"
    >

  <Grid Height="62" Width="auto">
        <Grid Height="61" HorizontalAlignment="Left" Margin="0,0,0,0" Name="grid1" VerticalAlignment="Top" Width="auto">
            <Grid.ColumnDefinitions>
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                 <ColumnDefinition Width="auto" />
            </Grid.ColumnDefinitions>
            <Grid.RowDefinitions>
                <RowDefinition Height="25" />
                <RowDefinition Height="30" />
            </Grid.RowDefinitions>
            <Image Source= "HeadQuarters.png" Grid.Column="1" Grid.RowSpan="2" HorizontalAlignment="Center" Stretch="None" OpacityMask="White"></Image>
            <Label Content="{Binding XPath=CommanderName}" Height="54" HorizontalAlignment="Left" Name="label1" VerticalAlignment="Top" FontFamily="K22 Monastic" FontSize="36"  Margin="2,4,0,6" Grid.RowSpan="2" Grid.Column="2" />
            <Label Content="Leadership:"  HorizontalAlignment="Left" Margin="5,0,0,0" VerticalAlignment="Bottom"  Grid.Column="3" />
            <ProgressBar  HorizontalAlignment="Left" Height="20" Name="CommanderLeadershipProgressBar" VerticalAlignment="Top" Width="150" Grid.Column="3" Grid.Row="2" Margin="10,0,0,0" Minimum="1" Maximum="100" Value="{Binding XPath=CommanderLeadership}" />
        <TextBlock Text="{Binding ElementName=CommanderLeadershipProgressBar, Path=Value, StringFormat={}{0:0}%}" HorizontalAlignment="Center" VerticalAlignment="Top" Grid.Column="3" Grid.Row="2"  />
            <Button Content="Create Subordinate Unit" Height="35" Width="auto" HorizontalAlignment="Left" Margin="10,0,50,0" Name="button1" VerticalAlignment="Center"  Grid.Column="4" Grid.RowSpan="2" />

        </Grid>
</Grid>

这是 HierarchialDataTemplate2:

<HierarchicalDataTemplate 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    ItemsSource="{Binding XPath=Commander}"
    >

  <Grid Height="62" Width="auto">
        <Grid Height="61" HorizontalAlignment="Left" Margin="0,0,0,0" Name="grid1" VerticalAlignment="Top" Width="auto">
            <Grid.ColumnDefinitions>
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                 <ColumnDefinition Width="auto" />
            </Grid.ColumnDefinitions>
            <Grid.RowDefinitions>
                <RowDefinition Height="25" />
                <RowDefinition Height="30" />
            </Grid.RowDefinitions>
            <Image Source= "HeadQuarters.png" Grid.Column="1" Grid.RowSpan="2" HorizontalAlignment="Center" Stretch="None" OpacityMask="White"></Image>
            <Label Content="{Binding XPath=CommanderName}" Height="54" HorizontalAlignment="Left" Name="label1" VerticalAlignment="Top" FontFamily="K22 Monastic" FontSize="36"  Margin="2,4,0,6" Grid.RowSpan="2" Grid.Column="2" />
            <Label Content="Leadership:"  HorizontalAlignment="Left" Margin="5,0,0,0" VerticalAlignment="Bottom"  Grid.Column="3" />
            <ProgressBar  HorizontalAlignment="Left" Height="20" Name="CommanderLeadershipProgressBar" VerticalAlignment="Top" Width="150" Grid.Column="3" Grid.Row="2" Margin="10,0,0,0" Minimum="1" Maximum="100" Value="{Binding XPath=CommanderLeadership}" />
        <TextBlock Text="{Binding ElementName=CommanderLeadershipProgressBar, Path=Value, StringFormat={}{0:0}%}" HorizontalAlignment="Center" VerticalAlignment="Top" Grid.Column="3" Grid.Row="2"  />
            <Button Content="Create Subordinate Unit" Height="35" Width="auto" HorizontalAlignment="Left" Margin="10,0,50,0" Name="button1" VerticalAlignment="Center"  Grid.Column="4" Grid.RowSpan="2" />

        </Grid>
</Grid>

这是 HierarchicalDataTemplate3:

<HierarchicalDataTemplate 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    ItemsSource="{Binding XPath=Unit}"
    >

  <Grid Height="62" Width="auto">
        <Grid Height="61" HorizontalAlignment="Left" Margin="0,0,0,0" Name="grid1" VerticalAlignment="Top" Width="auto">
            <Grid.ColumnDefinitions>
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                <ColumnDefinition Width="auto" />
                 <ColumnDefinition Width="auto" />
            </Grid.ColumnDefinitions>
            <Grid.RowDefinitions>
                <RowDefinition Height="25" />
                <RowDefinition Height="30" />
            </Grid.RowDefinitions>

            <Label Content="{Binding XPath=UnitName}" Height="54" HorizontalAlignment="Left" Name="label4" VerticalAlignment="Top" FontFamily="K22 Monastic" FontSize="36"  Margin="2,4,0,6" Grid.RowSpan="2" Grid.Column="2" />

        </Grid>
</Grid>

这是(新)输出:

就目前而言这很好(如果有人感兴趣,我正在为兵棋构建所谓的战斗序列 Table)。但它不会继续构建整个 TreeView。我认为它只是读取第一个节点并停止。

我错过了什么?谢谢您的帮助。随意打我。

如果我理解你的问题和问题是正确的,那么可能是 Division 的 Commander 的子节点没有渲染?

在这种情况下,您应该将 HierarchicalDataSource 的 ItemsSource 设置为 "Division" 而不是 Commander:

<HierarchicalDataTemplate xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" ItemsSource="{Binding XPath=Division}">

然后您可以为 Division 节点内嵌包含一个数据模板,如下所示或在其他地方定义它:

      <HierarchicalDataTemplate.ItemTemplate>
    <DataTemplate>
      <TextBlock Text="{Binding XPath=DivisionCommanderName}" />
    </DataTemplate>
  </HierarchicalDataTemplate.ItemTemplate>

如果您有更多子节点,此模板本身可以是 HierarchicalDataTemplate。

编辑:

在 C# 代码中,模板层次结构可能存在误解:

  //This is for dynamically building a treeview with templates from an XML file
  XmlTextReader xmlReader1 = new XmlTextReader(@"E:\Temp\HierarchicalDataTemplate1.xml");
  HierarchicalDataTemplate hierarchicalDataTemplate1 = XamlReader.Load(xmlReader1) as HierarchicalDataTemplate;

  XmlTextReader xmlReader2 = new XmlTextReader("HierarchicalDataTemplate2.xml");
  HierarchicalDataTemplate hierarchicalDataTemplate2 = XamlReader.Load(xmlReader2) as HierarchicalDataTemplate;
  // Original: hierarchicalDataTemplate2.ItemTemplate = hierarchicalDataTemplate2;
  hierarchicalDataTemplate1.ItemTemplate = hierarchicalDataTemplate2;

  XmlTextReader xmlReader3 = new XmlTextReader("HierarchicalDataTemplate3.xml");
  HierarchicalDataTemplate hierarchicalDataTemplate3 = XamlReader.Load(xmlReader3) as HierarchicalDataTemplate;
  // Oridignal: hierarchicalDataTemplate3.ItemTemplate = hierarchicalDataTemplate3;
  hierarchicalDataTemplate2.ItemTemplate = hierarchicalDataTemplate3;

此外:模板必须反映其相应级别的节点。