2 Probleme mit TreeView - XML auslesen

  • VB.NET

Es gibt 9 Antworten in diesem Thema. Der letzte Beitrag () ist von ErfinderDesRades.

    2 Probleme mit TreeView - XML auslesen

    Ich will für ein paar Kollegen ein kleines "Hilfsprogramm" schreiben.
    Hier sollen bestimmte Programme geöffnet werden können.
    Um den Pfade zu diesen Programmen zu aktualisieren oder weitere Programme hinzuzufügen, lade ich es per XML in einen TreeView. So weit so gut.
    Nun habe ich jedoch 2 kleine Probleme, für welche ich noch keine Lösung gefunden habe.

    1. in meinem Beispiel ist als erstes "Visual Studio" angegeben. Hier ist ein Leerzeichen im Namen. Wenn ich dies auch so in der XML angebe, wird die XML nicht geladen, weil er nicht mit dem Leerzeichen zwischen "Visual" und "Studio" klar kommt. Ohne Leerzeichen sieht es aber auch irgendwie blöd aus im Treeview. Wie kann ich also ein Leerzeichen in der XML speichern oder besser gesagt es so laden, dass das Leerzeichen dann da ist?

    2. Ich würde gerne den Pfad und Startdatei (Bsp. "C:\Program Files (x86)\Microsoft Visual Studio 12.0\Common7\IDE\devenv.exe" von Visual Studio) mit in der XML speichern und diese dann über mein Programm ausführen beim drauf klicken. Jedoch weiss ich absolut nicht, wo ich den Pfad usw. in der XML dann speichern muss und wie ich aus dem "Select Case" (siehe Code) auf diesen Pfad in der XML dann zugreifen soll!?

    die XML sieht wie folgt aus :

    XML-Quellcode

    1. <Nodes>
    2. <Programme>
    3. <Test>
    4. <VisualStudio />
    5. <Excel />
    6. </Test>
    7. <andere>
    8. <VB.NET />
    9. </andere>
    10. </Programme>
    11. <Test1>
    12. <bla />
    13. <blup />
    14. </Test1>
    15. </Nodes>


    Mein Code :

    VB.NET-Quellcode

    1. Option Strict On
    2. Option Explicit On
    3. Imports System.Xml
    4. Public Class XmlTreeView
    5. Public Shared Sub LoadFromXml(ByVal FileName As String, ByVal TheTreeView As TreeView)
    6. Dim xDoc As New XmlDocument
    7. xDoc.Load(FileName)
    8. FillTreeView(TheTreeView.Nodes, xDoc.DocumentElement)
    9. End Sub
    10. Private Shared Sub FillTreeView(ByVal CurrentNodes As TreeNodeCollection, _
    11. ByVal xNode As XmlNode)
    12. For Each xChild As XmlNode In xNode.ChildNodes
    13. FillTreeView(CurrentNodes.Add(xChild.Name).Nodes, xChild)
    14. Next
    15. End Sub
    16. Public Shared Sub SaveToXml(ByVal FileName As String, ByVal TheTreeView As TreeView)
    17. Dim xDoc As New XmlDocument
    18. xDoc.LoadXml("<Nodes></Nodes>")
    19. SaveNodes(xDoc.DocumentElement, TheTreeView.Nodes)
    20. xDoc.Save(FileName)
    21. End Sub
    22. Private Shared Sub SaveNodes(ByVal xNode As XmlNode, ByVal CurrentNodes As TreeNodeCollection)
    23. For Each tn As TreeNode In CurrentNodes
    24. Debug.WriteLine(tn.Text)
    25. SaveNodes(xNode.AppendChild(xNode.OwnerDocument.CreateElement(tn.Text)), tn.Nodes)
    26. Next
    27. End Sub
    28. Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As _
    29. System.EventArgs) Handles Button1.Click
    30. 'zum theoretischen speichern der XML - vielleicht später mal...
    31. End Sub
    32. Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As _
    33. System.EventArgs) Handles Button2.Click
    34. XmlTreeView.SaveToXml("Nodes2.xml", Me.TreeView1)
    35. End Sub
    36. Sub treeView1_NodeMouseDoubleClick(ByVal sender As Object, ByVal e As TreeNodeMouseClickEventArgs) Handles TreeView1.NodeMouseDoubleClick
    37. Select Case TreeView1.SelectedNode.Text
    38. Case Is = "Visual Studio"
    39. MsgBox("Visual Studio")
    40. Case Is = "Excel"
    41. MsgBox("Excel")
    42. End Select
    43. End Sub
    44. Private Sub XmlTreeView_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    45. Me.TreeView1.Nodes.Clear()
    46. XmlTreeView.LoadFromXml("Nodes.xml", Me.TreeView1)
    47. End Sub
    48. End Class


    Ich hoffe ihr könnt meine Problematik nachvollziehen und mir helfen ;)
    die xml ist falsch strukturiert.
    Um Nodes gleicher Art auszulesen müssen sie auch denselben TagNamen haben.
    Unterschiede werden in den XmlAttributen niedergelegt.
    Das löst dann auch das Problem mit dem Space - In Xml-Attributen ist solch nämlich zulässig.

    vlt guuge auch Xml-Tutorial für tieferes Verständnis von Xml
    @zauber777 Wie soll denn der befüllte TreeView hinterher aussehen?
    Ich hab hier mal ne Minimalversion gemacht:

    VB.NET-Quellcode

    1. Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
    2. Me.TreeView1.Nodes.Clear()
    3. Using reader = XmlReader.Create("c:\Temp\xxx.xml")
    4. While reader.Read()
    5. Me.TreeView1.Nodes.Add(reader.Name)
    6. End While
    7. End Using
    8. End Sub
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    wie gesagt: Dein Xml-Code widerspricht allen Standards, und ist grad für den Aufbau einer Baum-Struktur ganz ungeeignet.
    Dein Kardinalfehler ist, dass du die Auszeichnungs-Tags als Daten missbrauchst - dafür sind sie nicht vorgesehen.
    Xml ist eine sog. "Auszeichnungssprache", die Tags sind "Auszeichnungen" der Daten - sie sind aber selbst keine Daten.

    Aber das steht auch im Tut, und wie verarbeitbares Xml aussehen kann, ja auch, inklusive downloadables Beispiel.

    Einfacher als im Tut kann mans glaub kaum erklären - ich zumindest nicht, sonst hätte ichs ja gemacht.
    Erklärungen sind wohl prinzipiiell nicht einfacher als das Erklärte (sollten sie zumindest ;) ).

    Nichtsdestotrotz musst du das verstehen, sonst wird dat nix.

    Ein gangbarer Weg wäre allerdings, nachzufragen bei Punkten, die du nicht verstehst.
    @zauber777 MAch es vielleicht mal anders herum.
    Nimm Deinen designten TreeView und versuche, ihn in eine XML-Datei zu schreiben. Parallel dazu machst Du die Einleseroutine.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    @RoadFromGermany ich habe es schon versucht in eine XML-Datei zu speichern. Jedoch kommt genau dann schon der erster Fehler, dass Leerzeichen dabei sind...null
    "Das ' '-Zeichen, hexidezimaler Wert 0x20, darf nicht in einem Namen enthalten sein."

    Zum Auslesen/Speichern habe ich folgenden Code genommen :

    VB.NET-Quellcode

    1. Private Shared Sub FillTreeView(ByVal CurrentNodes As TreeNodeCollection, _
    2. ByVal xNode As XmlNode)
    3. For Each xChild As XmlNode In xNode.ChildNodes
    4. FillTreeView(CurrentNodes.Add(xChild.Name).Nodes, xChild)
    5. Next
    6. End Sub
    7. ' TreeView-Inhalt (Nodes-Objekte) als XML-Datei speichern
    8. Public Shared Sub SaveToXml(ByVal FileName As String, ByVal TheTreeView As TreeView)
    9. Dim xDoc As New XmlDocument
    10. xDoc.LoadXml("<Nodes></Nodes>")
    11. SaveNodes(xDoc.DocumentElement, TheTreeView.Nodes)
    12. xDoc.Save(FileName)
    13. End Sub
    14. Private Shared Sub SaveNodes(ByVal xNode As XmlNode, ByVal CurrentNodes As TreeNodeCollection)
    15. For Each tn As TreeNode In CurrentNodes
    16. Debug.WriteLine(tn.Text)
    17. SaveNodes(xNode.AppendChild(xNode.OwnerDocument.CreateElement(tn.Text)), tn.Nodes)
    18. Next
    19. End Sub
    Bin nun ein ganzes Stück weiter...
    Nun hänge ich jedoch noch an meinem 2. Problem: Wie kann ich das Attribut in welchen ich den Pfad und Datei angebe in der XML im TreeView als Doppelklick nutzen?
    Normalerweise müsste es ja im Bereich "'Sub treeView1_NodeMouseDoubleClick..." bei "Case Is = " sein. Wie ich dem TreeView aber sagen soll, dass es dann den zugehörigen Attribut aus der XML nehmen und ausführen soll, versteh ich leider absolut nicht...

    XML-Quellcode

    1. <?xml version="1.0" encoding="utf-8" ?>
    2. <Nodes>
    3. <Programme>
    4. <Test>
    5. <Programm Pfad="C:\Program Files (x86)\Microsoft Visual Studio 12.0\Common7\IDE\devenv.exe">Visual Studio</Programm>
    6. <Programm Pfad="C:\Program Files\Microsoft Office 15\root\office15\EXCEL.EXE">Excel</Programm>
    7. </Test>
    8. <andere>
    9. <Programm Pfad="C:\Program Files\Notepad++\notepad++.exe">Notepad ++</Programm>
    10. </andere>
    11. </Programme>
    12. <Test1>
    13. <Programm>bla</Programm>
    14. <Programm>blup</Programm>
    15. </Test1>
    16. </Nodes>

    VB.NET-Quellcode

    1. ​Option Strict On
    2. Option Explicit On
    3. Imports System.Xml
    4. Public Class XmlTreeView
    5. Public Shared Sub LoadFromXml(ByVal FileName As String, ByVal TheTreeView As TreeView)
    6. Dim xDoc As New XmlDocument
    7. xDoc.Load(FileName)
    8. FillTreeView(TheTreeView.Nodes, xDoc.DocumentElement)
    9. End Sub
    10. Private Shared Sub FillTreeView(ByVal CurrentNodes As TreeNodeCollection, ByVal xNode As XmlNode)
    11. For Each xChild As XmlNode In xNode.ChildNodes
    12. If xChild.Name <> "Programm" Then
    13. FillTreeView(CurrentNodes.Add(xChild.Name).Nodes, xChild)
    14. Else
    15. CurrentNodes.Add(xChild.InnerText)
    16. End If
    17. Next
    18. End Sub
    19. Public Shared Sub SaveToXml(ByVal FileName As String, ByVal TheTreeView As TreeView)
    20. Dim xDoc As New XmlDocument
    21. xDoc.LoadXml("<Nodes></Nodes>")
    22. SaveNodes(xDoc.DocumentElement, TheTreeView.Nodes)
    23. xDoc.Save(FileName)
    24. End Sub
    25. Private Shared Sub SaveNodes(ByVal xNode As XmlNode, ByVal CurrentNodes As TreeNodeCollection)
    26. For Each tn As TreeNode In CurrentNodes
    27. Debug.WriteLine(tn.Text)
    28. SaveNodes(xNode.AppendChild(xNode.OwnerDocument.CreateElement(tn.Text)), tn.Nodes)
    29. Next
    30. End Sub
    31. 'Sub treeView1_NodeMouseDoubleClick(ByVal sender As Object, ByVal e As TreeNodeMouseClickEventArgs) Handles TreeView1.NodeMouseDoubleClick
    32. ' Select Case TreeView1.SelectedNode.Text
    33. ' Case Is = "Visual Studio"
    34. ' Process.Start("C:\Program Files (x86)\Microsoft Visual Studio 12.0\Common7\IDE\devenv.exe")
    35. ' Case Is = "Excel"
    36. ' Process.Start("C:\Program Files\Microsoft Office 15\root\office15\EXCEL.EXE")
    37. 'End Select
    38. 'End Sub