6

This is XML file

 <Root>
 <RootNode name="CurrentDbName" value="DeltaTest Backup" DesiPath="E:\BuildBackups">
 <ChildNode name="Application" value="App">
  <LeafNode name="Source" value="Source" SourcePath="E:\Alertv2" /> 
  <LeafNode name="Publish" value="Publish" SourcePath="C:\Alert_Source" /> 
  </ChildNode>
 <ChildNode name="Database" value="DB">
  <LeafNode name="Dev" value="Dev" SourcePath="C:\Kiran3" /> 
  <LeafNode name="Build" value="Build" SourcePath="C:\Kiran4" /> 
  </ChildNode>
  </RootNode>  </Root>

From this, I want to create a treeview in WPF and looks like

-Root
 --DeltaTestBaclup
  ---App
    ----Source
    ----Publish
  ---Db
    ----Dev
    ----Build

So please help me to create this treeview.

5 Answers 5

3

Here is a way to do it programmatically. This is based on this website's solution

public YourWindow()
{
    InitializeComponent();
    BuildTree(treeView, XDocument.Load(System.IO.Path.Combine(System.IO.Directory.GetCurrentDirectory(), @"testxml.xml")));
}

private void BuildTree(TreeView treeView, XDocument doc)
{
    TreeViewItem treeNode = new TreeViewItem 
    {  
        //Should be Root
        Header = doc.Root.Name.LocalName,
        IsExpanded = true
    };
    treeView.Items.Add(treeNode);
    BuildNodes(treeNode, doc.Root);
}

private void BuildNodes(TreeViewItem treeNode, XElement element)
{
    foreach (XNode child in element.Nodes())
    {
        switch (child.NodeType)
        {
            case XmlNodeType.Element:
                XElement childElement = child as XElement;
                TreeViewItem childTreeNode = new TreeViewItem
                {
                    //Get First attribute where it is equal to value
                    Header = childElement.Attributes().First(s => s.Name == "value").Value ,
                    //Automatically expand elements
                    IsExpanded = true
                };
                treeNode.Items.Add(childTreeNode);
                BuildNodes(childTreeNode, childElement);
                break;
            case XmlNodeType.Text:
                XText childText = child as XText;
                treeNode.Items.Add(new TreeViewItem { Header = childText.Value, });
                break;
        }
    }
}

That code behind will build the tree to your spec. This is the XAML

<Grid>
    <TreeView Margin="20" Background="LightGray" x:Name="treeView" />
</Grid>
Sign up to request clarification or add additional context in comments.

1 Comment

Hey, you missed a semicolon at "BuildNodes(childTreeNode, childElement)". :)
1
    class Mapper
{
    private string sourceXmlFile;
    private XDocument xmlData;

    public Mapper(string xmlFilePath)
    {            
        sourceXmlFile = xmlFilePath;           
    }

    private void BuildNodes(TreeViewItem treeNode, XElement element)
    {

        string attributes = "";
        if (element.HasAttributes)
        {
            foreach (var att in element.Attributes())
            {
                attributes += " " + att.Name + " = " + att.Value;
            }
        }

        TreeViewItem childTreeNode = new TreeViewItem
        {
            Header = element.Name.LocalName + attributes,
            IsExpanded = true
        };
        if (element.HasElements)
        {
            foreach (XElement childElement in element.Elements())
            {
                BuildNodes(childTreeNode, childElement);
            }
        }
        else
        {
            TreeViewItem childTreeNodeText = new TreeViewItem
            {
                Header = element.Value,
                IsExpanded = true
            };
            childTreeNode.Items.Add(childTreeNodeText);                    
        }

        treeNode.Items.Add(childTreeNode);
    }



    public void LoadXml(TreeView treeview)
    {
        try
        {
            if (sourceXmlFile != null)
            {
                xmlData = XDocument.Load(sourceXmlFile, LoadOptions.None);
                if (xmlData == null)
                {
                    throw new XmlException("Cannot load Xml document from file : " + sourceXmlFile);
                }
                else
                {
                    TreeViewItem treeNode = new TreeViewItem
                    {
                        Header = sourceXmlFile,
                        IsExpanded = true
                    };


                    BuildNodes(treeNode, xmlData.Root);
                    treeview.Items.Add(treeNode);
                }
            }
            else
            {
                throw new IOException("Xml file is not set correctly.");
            }
        }
        catch (IOException ioex)
        {
            //log
        }
        catch (XmlException xmlex) 
        {
            //log
        }
        catch (Exception ex)
        {
            //log
        }
    }

}

This is the most generic version for every xml structure. For example :

    <Catalog>
  <Book id="bk101">
        <Author>Garcia, Debra</Author>
    <Title id="33">XML Developer's Guide</Title>
    <Genre>Computer</Genre>
    <Price>44.95</Price>
    <PublishDate>2000-10-01</PublishDate>
    <Description>An in-depth look at creating applications 
      with XML.</Description>
  </Book>
  <Book id="bk102">
    <Author>Garcia, Debra</Author>
    <Title>Midnight Rain</Title>
    <Genre>Fantasy</Genre>
    <Price>5.95</Price>
    <PublishDate>2000-12-16</PublishDate>
    <Description>A former architect battles corporate zombies, 
      an evil sorceress, and her own childhood to become queen 
      of the world.</Description>
  </Book>
</Catalog>

Will produce this : This how it looks

Comments

0

Welcome to stackoverflow, if you could post some sample xml - it would help to visualise what your working towards. I think you need to use 1 or more HierarchicalDataTemplate.

Assuming an xml file called data.xml:

<?xml version="1.0" encoding="utf-8" ?>
<root>
     <item>
      <DeltaTestBaclup>aaa</DeltaTestBaclup>
      <App>bbb</App>
      <Source>ccc</Source>
      <Publish>ddd</Publish>
    </item>
    <item>
      <DeltaTestBaclup>aaa</DeltaTestBaclup>
      <App>bbb</App>
      <Source>ccc</Source>
      <Publish>ddd</Publish>
    </item>
</root>

You could use xaml something similar to:

 <Grid>
        <Grid.DataContext>
            <XmlDataProvider Source="data.xml"></XmlDataProvider>
        </Grid.DataContext>
        <Grid.Resources>
            <HierarchicalDataTemplate x:Key="ItemTemplate" DataType="item">
                <TextBlock>
                    <TextBlock Text="{Binding XPath=DeltaTestBaclup}" />
                    <LineBreak></LineBreak>
                    <TextBlock Text="{Binding XPath=App}" />
                    <LineBreak></LineBreak>
                    <TextBlock Text="{Binding XPath=Source}" />
                    <LineBreak></LineBreak>
                    <TextBlock Text="{Binding XPath=Publish}" />                    
                </TextBlock>
            </HierarchicalDataTemplate>
        </Grid.Resources>

        <TreeView  Name="treeView" 
                   ItemsSource="{Binding Path=.,XPath=/root/item}" 
                   ItemTemplate="{StaticResource ItemTemplate}">      
        </TreeView>
    </Grid>

Comments

0

I know this question was asked a few months ago but I don't think it was answered accurately as I ran into the same problem and none of these suggestions helped me solve it.

Here's a link that explains how to populate a treeview from an .xml using winforms:

http://www.codeproject.com/Articles/12606/Loading-and-Saving-XML-to-and-from-a-TreeView-Cont

I managed to adapt it to wpf so to populate a TreeView using the info in an .xml:

//First, we'll load the Xml document
XmlDocument xDoc = new XmlDocument();
xDoc.Load(filename);

//Now, clear out the treeview, 
treeView.Items.Clear();

//and add the first (root) node
TreeViewItem treeviewItemRoot   = new TreeViewItem();
treeviewItemRoot.Header         = "Root";

treeView.Items.Add(treeviewItemRoot);

TreeViewItem tNode = new TreeViewItem();
tNode = (TreeViewItem)treeView.Items[0];

//We make a call to addTreeNode, 
//where we'll add all of our nodes
addTreeNode(xDoc.DocumentElement, tNode);



//This function is called recursively until all nodes are loaded
private void addTreeNode(XmlNode xmlNode, TreeViewItem treeNode)
{
    XmlNode xNode;
    TreeViewItem tNode;
    XmlNodeList xNodeList;
    if (xmlNode.HasChildNodes) //The current node has children
    {
        xNodeList = xmlNode.ChildNodes;
        for (int x = 0; x <= xNodeList.Count - 1; x++)
        //Loop through the child nodes
        {
            xNode = xmlNode.ChildNodes[x];

            treeNode.Items.Add(new TreeViewItem());
            tNode = treeNode.Items[x] as TreeViewItem;
            addTreeNode(xNode, tNode);
        }
    }
    else //No children, so add the outer xml (trimming off whitespace)
        treeNode.Header = xmlNode.OuterXml.Trim(); 
}

1 Comment

How do you link it to you xaml page?
-2

You can read about that here, an example from that site:

<TreeView Margin="10,10,0,13" Name="TreeView1" HorizontalAlignment="Left"
 VerticalAlignment="Top" Width="194" Height="200">
    <TreeViewItem Header="Cold Drinks">
        <TreeViewItem Header="Coke"></TreeViewItem>
        <TreeViewItem Header="Pepsi"></TreeViewItem>
        <TreeViewItem Header="Orange Juice"></TreeViewItem>
        <TreeViewItem Header="Milk"></TreeViewItem>
        <TreeViewItem Header="Iced Tea"></TreeViewItem>
        <TreeViewItem Header="Mango Shake"></TreeViewItem>
    </TreeViewItem>
</TreeView>

That would result in this

alt text
(source: c-sharpcorner.com)

So in your case you need to add some more TreeViewItems and nest them up a bit, play with the above code to get the result you want!

1 Comment

Question was "How to create treeview from XML file" not nesting manually in xaml

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.