网上我看见有人想用InsertNodeBefore来实现这个想法。代码如下:
Sub HowDoesInsertNodeBeforeWork()
Dim oCXPart As CustomXMLPart
Dim oCXNode As CustomXMLNode
Dim strXML As String
strXML = "<?xml version='1.0' ?><invoice xmlns='http://abc...xyz'>" _
& "<items>" _
& "<item ><name supplier='Home Depot'>Hammer</name><price>12</price></item>" _
& "<item ><name supplier='Lowes'>Hammer</name><price>12</price></item>" _
& "<item ><name supplier='Contoso'>Hammer</name><price>11</price></item>" _
& "</items>" _
& "</invoice>"
On Error Resume Next
ActiveDocument.CustomXMLParts(4).Delete
On Error GoTo 0
'Add the part.
Set oCXPart = ActiveDocument.CustomXMLParts.Add
'Load the XML
oCXPart.LoadXML strXML
'Define a node.
Set oCXNode = oCXPart.SelectSingleNode("//*[@supplier='Contoso']")
Debug.Print oCXNode.BaseName
'Attempt to insert a node before the defined node.
oCXNode.InsertNodeBefore "Test", , msoCustomXMLNodeElement, "Test Node Text"
Debug.Print oCXNode.ParentNode.XML
'Seems the XML should look like this:
Debug.Print "<item xmlns=""http://abc...xyz""><Test xmlns="""">Test Node Text</Test><name supplier=""Contoso"">Hammer</name><price>11</price></item>"
'With the new node "Test" inserted before the defined node "name"
'What am I missing?
End Sub
可是结果是错误的。原因有2:
1. 所先的结点不对,上面代码所先的节点是要插入节点的兄弟节点。实际上应该选这个节点的父节点。
2. 方法不对InsertNodeBefore会将要插入的内容插入到所选节点的未尾。 http://msdn.microsoft.com/en-us/library/office/microsoft.office.core.customxmlnode.insertnodebefore(v=office.14).aspx
解决方案是用InsertSubtreeBefore代码如下:
Sub HowDoesInsertNodeBeforeWork()
Dim oCXPart As CustomXMLPart
Dim oCXNode As CustomXMLNode
Dim strXML As String
strXML = "<?xml version='1.0' ?><invoice xmlns='http://abc...xyz'>" _
& "<items>" _
& "<item ><name supplier='Home Depot'>Hammer</name><price>12</price></item>" _
& "<item ><name supplier='Lowes'>Hammer</name><price>12</price></item>" _
& "<item ><name supplier='Contoso'>Hammer</name><price>11</price></item>" _
& "</items>" _
& "</invoice>"
On Error Resume Next
ActiveDocument.CustomXMLParts(4).Delete
On Error GoTo 0
'Add the part.
Set oCXPart = ActiveDocument.CustomXMLParts.Add
'Load the XML
oCXPart.LoadXML strXML
'Define a node.
Set oCXNode = oCXPart.SelectSingleNode("/ns0:invoice[1]/ns0:items[1]/ns0:item[3][ns0:name[@supplier='Contoso']]")
Set xt = oCXPart.SelectSingleNode("/ns0:invoice[1]/ns0:items[1]/ns0:item[3]/ns0:name[@supplier='Contoso']")
Debug.Print oCXNode.BaseName
Debug.Print oCXNode.XPath
'Attempt to insert a node before the defined node.
'oCXNode.InsertNodeBefore "Test", , msoCustomXMLNodeElement, "Test Node Text"
oCXNode.InsertSubtreeBefore "<test>Test Node Text</test>", xt
Debug.Print oCXPart.SelectSingleNode("/ns0:invoice[1]/ns0:items[1]/ns0:item[3][ns0:name[@supplier='Contoso']]").XML
'Seems the XML should look like this:
Debug.Print "<item xmlns=""http://abc...xyz""><Test xmlns="""">Test Node Text</Test><name supplier=""Contoso"">Hammer</name><price>11</price></item>"
'With the new node "Test" inserted before the defined node "name"
'What am I missing?
End Sub