JTree:如何将节点的属性添加为自己的叶子?

时间:2015-05-22 20:34:22

标签: java xml swing tree jtree

我用javax.swing.JTree可视化XML文件。使用了来自thisthis问题的代码后,我不得不在节点中添加属性作为其中的内容。

这个简单的XML:

<?xml version="1.0" encoding="utf-8"?>
<!-- comment -->
<MYXML xmlns="">
    <Header id=""></Header>
    <Product id="" name="">
        <Description>Some text</Description>
        <Ref id=""></Ref>
        <Data id="">
            <Ref id=""></Ref>
        </Data>
        <Form id=""></Form>
    </Product>
</MYXML>

被解析为org.w3c.dom.Document并以org.w3c.dom.Node传递以递归构建JTree:

private DefaultMutableTreeNode buildTreeNode(Node rootNode) {
    DefaultMutableTreeNode treeNode = new DefaultMutableTreeNode(
            rootNode.getNodeName());
    NodeList children = rootNode.getChildNodes();

    for (int i = 0; i < children.getLength(); i++) {
        Node node = children.item(i);
        short nodeType = node.getNodeType();

        if (nodeType == Node.ELEMENT_NODE) {
            treeNode.add(buildTreeNode(node));

            // FIXME attributes should be leaves of their nodes
            if (node.hasAttributes()) {
                NamedNodeMap attributes = node.getAttributes();
                for (int j = 0; j < attributes.getLength(); j++) {
                    Node attr = attributes.item(j);
                    treeNode.add(new DefaultMutableTreeNode("@" + attr));
                }
            }
        } else if (nodeType == Node.TEXT_NODE) {
            String text = node.getTextContent().trim();
            if (!text.equals("")) {
                treeNode.add(new DefaultMutableTreeNode(text));
            }
        } else if (nodeType == Node.COMMENT_NODE) {
            String comment = node.getNodeValue().trim();
            treeNode.add(new DefaultMutableTreeNode("#" + comment));
        }
    }
    return treeNode;
}

结果不是我想要的:

result

叶子“Header”,“Ref”和“Form”应该是节点,所有属性(标记为@)应该是节点的叶子。如何通过递归方法实现这一目标?

以下是Gist上的工作示例。

编辑:我想出来并在下面回答了我的问题。

2 个答案:

答案 0 :(得分:1)

TreeNode中有一个方法isLeaf,你需要实现它,因为,当这个节点没有子节点(childrenCount == 0)时,它通常返回true,否则返回false。您希望将其标记为节点元素,而不管它们的子计数如何,因此您需要实现/覆盖此方法,它将返回您需要的内容。

您的算法也存在问题:

您需要检查您的节点是否具有节点子节点,或者只是具有叶子的终端节点。您需要区分这两者,并实现适当的逻辑来处理它,由您决定如何在代码中解释此xml。

答案 1 :(得分:0)

好吧,由于Krzysztof的暗示,我终于把它整理出来了。现在,正确处理带子节点的节点,属性叶子应该是:

Sub Main()

    Dim i As Decimal = 2

    For x As Integer = 1 To 5
        i = i + 0.2
    Next
    MsgBox(i) '3
    MsgBox(i > 3) 'False >> No problem

End Sub

产生我想要的东西:

enter image description here

完成后,Gist上的更正示例。