使用Java中的JDOM在KML中的元素之间插入一个新元素

时间:2015-07-14 10:59:02

标签: java xml kml jdom jdom-2

我正在使用JDOM来创建和修改KML文件。每隔5秒钟,我会从客户端应用程序收到纬度,经度和时间的新值。我需要修改现有文件并添加纬度,经度和时间的最新值。

XML文件如下所示

<?xml version="1.0" encoding="UTF-8"?>
    <kml xmlns="http://www.opengis.net/kml/2.2"
     xmlns:gx="http://www.google.com/kml/ext/2.2">
     <Document>
      <Folder>
       <Placemark>
       <name>deviceA</name>
        <gx:Track>
          <when>2015-06-28T17:02:09Z</when>
          <when>2015-06-28T17:02:35Z</when>
          <gx:coord>3.404258 50.605892 100.000000</gx:coord>
          <gx:coord>3.416446 50.604040 100.000000</gx:coord>
        </gx:Track>
       </Placemark>
       <Placemark>
        <name>deviceB</name>
         <gx:Track>
          <when>2015-06-28T17:02:09Z</when>
          <when>2015-06-28T17:02:35Z</when>
          <gx:coord>3.403133 50.601702 100.000000</gx:coord>
          <gx:coord>3.410171 50.597344 100.000000</gx:coord>
         </gx:Track>
       </Placemark>
      </Folder>
     </Document>
    </kml>

我使用以下代码插入值

SAXBuilder builder = new SAXBuilder();
File xmlFile = new File(outputFile);
try {

        Document doc = (Document) builder.build(xmlFile);
        Element rootNode = doc.getRootElement();
        Element docNode = rootNode.getChild("Document",ns);
        Element folNode = docNode.getChild("Folder",ns);

        List list = folNode.getChildren("Placemark",ns);

        if(list.size()>0)
        {
            Element node = (Element) list.get(deviceid);
            Element tracknode = node.getChild("Track",ns2);
            List wlist = tracknode.getChildren("when",ns);

            Element newWhen = new Element("when",ns);
            newWhen.setText(whentext);

            Element newCoord = new Element("coord",ns2);
            newCoord.setText(coordtext);

            System.out.println("When size:"+wlist.size());

            int index =0;
            if(wlist.size()==0) index =0;
            else index= wlist.size()+1;

            tracknode.addContent(index, newWhen);
            tracknode.addContent(newCoord);                 
        }

        XMLOutputter outputter = new XMLOutputter(Format.getPrettyFormat());
        FileOutputStream writer = new FileOutputStream(outputFile);
        outputter.output(doc, writer);
        writer.flush();
        writer.close();

} catch (IOException io) {
  System.out.println(io.getMessage());
} catch (JDOMException jdomex) {
  System.out.println(jdomex.getMessage());
}

&#39; gx:coord&#39; part正确插入元素的末尾,但是当元素需要插入元素的末尾时,&#39;当&#39;时。所以我得到带有标签的孩子列表&#39;当&#39;。获取元素列表的大小并在最后一个元素后面的索引处插入。前两次插入是好的,第三次插入我面临一个奇怪的问题。新元素&#39;当&#39;正在插入现有的when元素之间,而不是插入元素列表的末尾。 例如

<gx:Track>
  <when>2015-06-28T17:02:09Z</when>
  <when>2015-06-28T17:02:44Z</when>
  <when>2015-06-28T17:02:35Z</when>
  <gx:coord>3.404258 50.605892 100.000000</gx:coord>
  <gx:coord>3.416446 50.604040 100.000000</gx:coord>
  <gx:coord>3.429492 50.602078 100.000000</gx:coord>
</gx:Track>

我想插入新的&#39;当&#39;所有元素存在后的元素。无论如何在java中使用JDOM吗?

感谢任何帮助

1 个答案:

答案 0 :(得分:1)

在JDOM中,列表是实时的,甚至是过滤的内容列表,其中只包含父项中的一部分项目。

例如,您创建元素节点的代码很好:

        Element newWhen = new Element("when",ns);
        newWhen.setText(whentext);

        Element newCoord = new Element("coord",ns2);
        newCoord.setText(coordtext);

但是,添加它们如何:

        Element firstcoord = tracknode.getChild("coord",ns2);
        tracknode.addContent(tracknode.indexOf(firstcoord), newWhen);
        tracknode.addContent(newCoord);
  • 在第一个坐标之前添加时间。
  • 添加最后的位置。

如果曲目是空的,您将需要一个不同的解决方案。

请注意,您应该在代码中使用泛型。来自JDOM的List值都是泛型的,并且很有用。这是我用来测试上述内容的完整(修改)代码:

    Document doc = new SAXBuilder().build("locations.kml");

    Namespace ns = Namespace.getNamespace("http://www.opengis.net/kml/2.2");
    Namespace ns2 = Namespace.getNamespace("gx", "http://www.google.com/kml/ext/2.2");

    Element rootNode = doc.getRootElement();
    Element docNode = rootNode.getChild("Document",ns);
    Element folNode = docNode.getChild("Folder",ns);

    List<Element> list = folNode.getChildren("Placemark",ns);

    if(!list.isEmpty())
    {
        Element node = list.get(0);
        Element tracknode = node.getChild("Track",ns2);

        Element newWhen = new Element("when",ns);
        newWhen.setText("WHEN");

        Element newCoord = new Element("coord",ns2);
        newCoord.setText("WHERE");

        Element firstcoord = tracknode.getChild("coord",ns2);
        tracknode.addContent(tracknode.indexOf(firstcoord), newWhen);
        tracknode.addContent(newCoord);

    }

    XMLOutputter outputter = new XMLOutputter(Format.getPrettyFormat());
    outputter.output(doc, System.out);