mirror of
https://codeberg.org/Freeyourgadget/Gadgetbridge.git
synced 2026-07-31 07:44:24 +02:00
GPX: add support for importing older GPX version 1.0 files
Also takes care of slightly quirky GPX 1.1 files that contain extra spaces, XML comments or use floats instead of integers for cadence and heart rate.
This commit is contained in:
committed by
José Rebelo
parent
3bb686a106
commit
6fcb07ea98
@@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2023-2025 José Rebelo, Thomas Kuehne
|
||||
/* Copyright (C) 2023-2026 José Rebelo, Thomas Kuehne
|
||||
|
||||
This file is part of Gadgetbridge.
|
||||
|
||||
@@ -168,7 +168,9 @@ public class GpxParser {
|
||||
if (text == null || text.length() < 1) {
|
||||
return defaultDouble;
|
||||
}
|
||||
return Double.parseDouble(text);
|
||||
// some GPX generators write NaN instead of an empty value
|
||||
final double value = Double.parseDouble(text);
|
||||
return Double.isNaN(value) ? defaultDouble : value;
|
||||
}
|
||||
|
||||
private float getFloat(String attribute, float defaultFloat) {
|
||||
@@ -176,7 +178,9 @@ public class GpxParser {
|
||||
if (text == null || text.length() < 1) {
|
||||
return defaultFloat;
|
||||
}
|
||||
return Float.parseFloat(text);
|
||||
// some GPX generators write NaN instead of an empty value
|
||||
final float value = Float.parseFloat(text);
|
||||
return Float.isNaN(value) ? defaultFloat : value;
|
||||
}
|
||||
|
||||
private int getInt(String attribute, int defaultInt) {
|
||||
@@ -184,7 +188,13 @@ public class GpxParser {
|
||||
if (text == null || text.length() < 1) {
|
||||
return defaultInt;
|
||||
}
|
||||
return Integer.parseInt(text);
|
||||
|
||||
try {
|
||||
return Integer.parseInt(text);
|
||||
} catch (NumberFormatException e) {
|
||||
// some GPX generators write malformed cadence and HR values: "6.0" instead of "6"
|
||||
return Math.round(getFloat(attribute, defaultInt));
|
||||
}
|
||||
}
|
||||
|
||||
private void parseGpx() throws Exception {
|
||||
|
||||
@@ -3,12 +3,17 @@
|
||||
xmlns:ax="http://www.garmin.com/xmlschemas/ActivityExtension/v1"
|
||||
xmlns:g3="http://www.garmin.com/xmlschemas/GpxExtensions/v3"
|
||||
xmlns:gpx="http://www.topografix.com/GPX/1/1"
|
||||
xmlns:gpxOld="http://www.topografix.com/GPX/1/0"
|
||||
xmlns:tx="http://www.garmin.com/xmlschemas/TrackPointExtension/v1"
|
||||
xmlns:tx2="http://www.garmin.com/xmlschemas/TrackPointExtension/v2"
|
||||
xmlns:w1="http://www.garmin.com/xmlschemas/WaypointExtension/v1"
|
||||
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
|
||||
exclude-result-prefixes="ax g3 gpx tx tx2 w1"
|
||||
exclude-result-prefixes="ax g3 gpx tx tx2 w1 gpxOld"
|
||||
version="1.0">
|
||||
<!--
|
||||
This pre-processes GPX v1.0 and v1.1 and common extension for import by
|
||||
Gadgedbridge's nodomain.freeyourgadget.gadgetbridge.util.gpx.GPXParser
|
||||
-->
|
||||
<xsl:output
|
||||
encoding="UTF-8"
|
||||
indent="yes"
|
||||
@@ -16,122 +21,169 @@
|
||||
version="1.0" />
|
||||
<xsl:strip-space elements="*" />
|
||||
|
||||
<xsl:template match="/gpx:gpx">
|
||||
<xsl:template match="/gpx:gpx | /gpxOld:gpx">
|
||||
<gpx>
|
||||
<xsl:if test="gpx:metadata/gpx:name"><xsl:attribute name="name"><xsl:value-of select="gpx:metadata/gpx:name" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:metadata/gpx:author/gpx:name"><xsl:attribute name="author"><xsl:value-of select="gpx:metadata/gpx:author/gpx:name" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:metadata/gpx:time"><xsl:attribute name="time"><xsl:value-of select="gpx:metadata/gpx:time" /></xsl:attribute></xsl:if>
|
||||
<xsl:apply-templates select="gpx:wpt" />
|
||||
<xsl:apply-templates select="gpx:trk" />
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:metadata/gpx:name"><xsl:attribute name="name"><xsl:value-of select="gpx:metadata/gpx:name" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:name"><xsl:attribute name="name"><xsl:value-of select="gpxOld:name" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:metadata/gpx:author/gpx:name"><xsl:attribute name="author"><xsl:value-of select="gpx:metadata/gpx:author/gpx:name" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:name"><xsl:attribute name="author"><xsl:value-of select="gpxOld:author" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:metadata/gpx:time"><xsl:attribute name="time"><xsl:value-of select="normalize-space(gpx:metadata/gpx:time)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:time"><xsl:attribute name="time"><xsl:value-of select="normalize-space(gpxOld:time)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
|
||||
<xsl:apply-templates select="gpx:wpt | gpxOld:wpt" />
|
||||
<xsl:apply-templates select="gpx:trk | gpxOld:trk" />
|
||||
</gpx>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="gpx:wpt">
|
||||
<xsl:template match="gpx:wpt | gpxOld:wpt">
|
||||
<wpt>
|
||||
<xsl:call-template name="point" />
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:extensions/g3:WaypointExtension/g3:Temperature">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="gpx:extensions/g3:WaypointExtension/g3:Temperature" /></xsl:attribute>
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="normalize-space(gpx:extensions/g3:WaypointExtension/g3:Temperature)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/w1:WaypointExtension/w1:Temperature">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="gpx:extensions/w1:WaypointExtension/w1:Temperature" /></xsl:attribute>
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="normalize-space(gpx:extensions/w1:WaypointExtension/w1:Temperature)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:extensions/g3:WaypointExtension/g3:Depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="gpx:extensions/g3:WaypointExtension/g3:Depth" /></xsl:attribute>
|
||||
<xsl:attribute name="depth"><xsl:value-of select="normalize-space(gpx:extensions/g3:WaypointExtension/g3:Depth)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/w1:WaypointExtension/w1:Depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="gpx:extensions/w1:WaypointExtension/w1:Depth" /></xsl:attribute>
|
||||
<xsl:attribute name="depth"><xsl:value-of select="normalize-space(gpx:extensions/w1:WaypointExtension/w1:Depth)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
</wpt>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="gpx:trk">
|
||||
<xsl:template match="gpx:trk |gpxOld:trk">
|
||||
<trk>
|
||||
<xsl:attribute name="name"><xsl:value-of select="gpx:name" /></xsl:attribute>
|
||||
<xsl:if test="gpx:type"><xsl:attribute name="type"><xsl:value-of select="gpx:type" /></xsl:attribute></xsl:if>
|
||||
<xsl:apply-templates select="gpx:trkseg" />
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:name"><xsl:attribute name="name"><xsl:value-of select="gpx:name" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:name"><xsl:attribute name="name"><xsl:value-of select="gpxOld:name" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:type"><xsl:attribute name="type"><xsl:value-of select="normalize-space(gpx:type)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:type"><xsl:attribute name="type"><xsl:value-of select="normalize-space(gpxOld:type)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:apply-templates select="gpx:trkseg | gpxOld:trkseg" />
|
||||
</trk>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="gpx:trkseg">
|
||||
<xsl:template match="gpx:trkseg | gpxOld:trkseg">
|
||||
<trkseg>
|
||||
<xsl:apply-templates select="gpx:trkpt" />
|
||||
<xsl:apply-templates select="gpx:trkpt | gpxOld:trkpt" />
|
||||
</trkseg>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="gpx:trkpt">
|
||||
<xsl:template match="gpx:trkpt | gpxOld:trkpt">
|
||||
<trkpt>
|
||||
<xsl:call-template name="point" />
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:extensions/tx2:TrackPointExtension/tx2:atemp">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="gpx:extensions/tx2:TrackPointExtension/tx2:atemp" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/tx:TrackPointExtension/tx:atemp">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="gpx:extensions/tx:TrackPointExtension/tx:atemp" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/g3:TrackPointExtension/g3:Temperature">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="gpx:extensions/g3:TrackPointExtension/g3:Temperature" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:extensions/tx2:TrackPointExtension/tx2:depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="gpx:extensions/tx2:TrackPointExtension/tx2:depth" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/tx:TrackPointExtension/tx:depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="gpx:extensions/tx:TrackPointExtension/tx:depth" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/g3:TrackPointExtension/g3:Depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="gpx:extensions/g3:TrackPointExtension/g3:Depth" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:extensions/tx2:TrackPointExtension/tx2:hr">
|
||||
<xsl:attribute name="hr"><xsl:value-of select="gpx:extensions/tx2:TrackPointExtension/tx2:hr" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/tx:TrackPointExtension/tx:hr">
|
||||
<xsl:attribute name="hr"><xsl:value-of select="gpx:extensions/tx:TrackPointExtension/tx:hr" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:extensions/tx2:TrackPointExtension/tx2:cad">
|
||||
<xsl:attribute name="cad"><xsl:value-of select="gpx:extensions/tx2:TrackPointExtension/tx2:cad" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/tx:TrackPointExtension/tx:cad">
|
||||
<xsl:attribute name="cad"><xsl:value-of select="gpx:extensions/tx:TrackPointExtension/tx:cad" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:extensions/tx2:TrackPointExtension/tx2:speed">
|
||||
<xsl:attribute name="speed"><xsl:value-of select="gpx:extensions/tx2:TrackPointExtension/tx2:speed" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:extensions/ax:TrackPointExtension/ax:speed">
|
||||
<xsl:attribute name="speed"><xsl:value-of select="gpx:extensions/ax:TrackPointExtension/ax:speed" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:apply-templates select="gpx:extensions | gpxOld:extensions" />
|
||||
<xsl:if test="gpxOld:speed">
|
||||
<xsl:attribute name="speed"><xsl:value-of select="normalize-space(gpxOld:speed)" /></xsl:attribute>
|
||||
</xsl:if>
|
||||
</trkpt>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="gpx:extensions | gpxOld:extensions">
|
||||
<xsl:choose>
|
||||
<xsl:when test="tx2:TrackPointExtension/tx2:atemp">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="normalize-space(tx2:TrackPointExtension/tx2:atemp)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="tx:TrackPointExtension/tx:atemp">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="normalize-space(tx:TrackPointExtension/tx:atemp)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="g3:TrackPointExtension/g3:Temperature">
|
||||
<xsl:attribute name="temperature"><xsl:value-of select="normalize-space(g3:TrackPointExtension/g3:Temperature)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="tx2:TrackPointExtension/tx2:depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="normalize-space(tx2:TrackPointExtension/tx2:depth)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="tx:TrackPointExtension/tx:depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="normalize-space(tx:TrackPointExtension/tx:depth)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="g3:TrackPointExtension/g3:Depth">
|
||||
<xsl:attribute name="depth"><xsl:value-of select="normalize-space(g3:TrackPointExtension/g3:Depth)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="tx2:TrackPointExtension/tx2:hr">
|
||||
<xsl:attribute name="hr"><xsl:value-of select="normalize-space(tx2:TrackPointExtension/tx2:hr)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="tx:TrackPointExtension/tx:hr">
|
||||
<xsl:attribute name="hr"><xsl:value-of select="normalize-space(tx:TrackPointExtension/tx:hr)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="tx2:TrackPointExtension/tx2:cad">
|
||||
<xsl:attribute name="cad"><xsl:value-of select="normalize-space(tx2:TrackPointExtension/tx2:cad)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="tx:TrackPointExtension/tx:cad">
|
||||
<xsl:attribute name="cad"><xsl:value-of select="normalize-space(tx:TrackPointExtension/tx:cad)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="tx2:TrackPointExtension/tx2:speed">
|
||||
<xsl:attribute name="speed"><xsl:value-of select="normalize-space(tx2:TrackPointExtension/tx2:speed)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="tx:TrackPointExtension/tx:speed">
|
||||
<xsl:attribute name="speed"><xsl:value-of select="normalize-space(tx:TrackPointExtension/tx:speed)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="ax:TrackPointExtension/ax:speed">
|
||||
<xsl:attribute name="speed"><xsl:value-of select="normalize-space(ax:TrackPointExtension/ax:speed)" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template name="point">
|
||||
<xsl:attribute name="lat"><xsl:value-of select="@lat" /></xsl:attribute>
|
||||
<xsl:attribute name="lon"><xsl:value-of select="@lon" /></xsl:attribute>
|
||||
<xsl:if test="gpx:ele"><xsl:attribute name="ele"><xsl:value-of select="gpx:ele" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:time"><xsl:attribute name="time"><xsl:value-of select="gpx:time" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:name"><xsl:attribute name="name"><xsl:value-of select="gpx:name" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:desc"><xsl:attribute name="desc"><xsl:value-of select="gpx:desc" /></xsl:attribute></xsl:if>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:desc">
|
||||
<xsl:attribute name="desc"><xsl:value-of select="gpx:desc" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:cmt">
|
||||
<xsl:attribute name="desc"><xsl:value-of select="gpx:cmt" /></xsl:attribute>
|
||||
</xsl:when>
|
||||
<xsl:when test="gpx:ele"><xsl:attribute name="ele"><xsl:value-of select="normalize-space(gpx:ele)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:ele"><xsl:attribute name="ele"><xsl:value-of select="normalize-space(gpxOld:ele)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:time"><xsl:attribute name="time"><xsl:value-of select="normalize-space(gpx:time)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:time"><xsl:attribute name="time"><xsl:value-of select="normalize-space(gpxOld:time)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:name"><xsl:attribute name="name"><xsl:value-of select="gpx:name" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:name"><xsl:attribute name="name"><xsl:value-of select="gpxOld:name" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:desc"><xsl:attribute name="desc"><xsl:value-of select="gpx:desc" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpx:cmt"><xsl:attribute name="desc"><xsl:value-of select="gpx:cmt" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:desc"><xsl:attribute name="desc"><xsl:value-of select="gpxOld:desc" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:cmt"><xsl:attribute name="desc"><xsl:value-of select="gpxOld:cmt" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:sym"><xsl:attribute name="sym"><xsl:value-of select="normalize-space(gpx:sym)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:sym"><xsl:attribute name="sym"><xsl:value-of select="normalize-space(gpxOld:sym)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:hdop"><xsl:attribute name="hdop"><xsl:value-of select="normalize-space(gpx:hdop)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:hdop"><xsl:attribute name="hdop"><xsl:value-of select="normalize-space(gpxOld:hdop)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:vdop"><xsl:attribute name="vdop"><xsl:value-of select="normalize-space(gpx:vdop)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:vdop"><xsl:attribute name="vdop"><xsl:value-of select="normalize-space(gpxOld:vdop)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:choose>
|
||||
<xsl:when test="gpx:pdop"><xsl:attribute name="pdop"><xsl:value-of select="normalize-space(gpx:pdop)" /></xsl:attribute></xsl:when>
|
||||
<xsl:when test="gpxOld:pdop"><xsl:attribute name="pdop"><xsl:value-of select="normalize-space(gpxOld:pdop)" /></xsl:attribute></xsl:when>
|
||||
</xsl:choose>
|
||||
<xsl:if test="gpx:sym"><xsl:attribute name="sym"><xsl:value-of select="gpx:sym" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:hdop"><xsl:attribute name="hdop"><xsl:value-of select="gpx:hdop" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:vdop"><xsl:attribute name="vdop"><xsl:value-of select="gpx:vdop" /></xsl:attribute></xsl:if>
|
||||
<xsl:if test="gpx:pdop"><xsl:attribute name="pdop"><xsl:value-of select="gpx:pdop" /></xsl:attribute></xsl:if>
|
||||
</xsl:template>
|
||||
</xsl:stylesheet>
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2023-2025 José Rebelo, Thomas Kuehne
|
||||
/* Copyright (C) 2023-2026 José Rebelo, Thomas Kuehne
|
||||
|
||||
This file is part of Gadgetbridge.
|
||||
|
||||
@@ -200,4 +200,22 @@ public class GPXParserTest extends TestBase {
|
||||
Assert.assertEquals(trackpoint.getTime(), activityPoint.getTime());
|
||||
Assert.assertEquals(trackpoint.getVdop(), activityPoint.getLocation().getVdop(), 0.0);
|
||||
}
|
||||
|
||||
// test import of old GPX v1.0
|
||||
@Test
|
||||
public void TestGpxImportOld() throws Exception {
|
||||
final byte[] actual;
|
||||
try (final InputStream gpx = getClass().getResourceAsStream("/TestGpxImportOld.gpx")) {
|
||||
actual = GpxParser.transformGpx(gpx);
|
||||
}
|
||||
|
||||
byte[] expected = readBinaryResource("/TestGpxImportOld.xml");
|
||||
Assert.assertArrayEquals(expected, actual);
|
||||
|
||||
final GpxFile file1;
|
||||
try (final InputStream gpx = getClass().getResourceAsStream("/TestGpxImportOld.gpx")) {
|
||||
file1 = new GpxParser(gpx).getGpxFile();
|
||||
}
|
||||
Assert.assertNotNull(file1);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,18 +17,18 @@
|
||||
</metadata>
|
||||
|
||||
<wpt lat="47.5048828125" lon="9.7393798828125">
|
||||
<ele>-470.1</ele>
|
||||
<time>2025-10-03T14:10:59Z</time>
|
||||
<ele>-470.1 <!-- comment --></ele>
|
||||
<time>2025-10-03T14:10:59Z <!-- comment --></time>
|
||||
<name>Bregenz</name>
|
||||
<desc>city in Österreich</desc>
|
||||
<sym>Airport</sym>
|
||||
<hdop>1.4</hdop>
|
||||
<vdop>3.2</vdop>
|
||||
<pdop>1.5</pdop>
|
||||
<hdop>1.4 <!-- comment --></hdop>
|
||||
<vdop>3.2 <!-- comment --></vdop>
|
||||
<pdop>1.5 <!-- comment --></pdop>
|
||||
<extensions>
|
||||
<wpx:WaypointExtension>
|
||||
<wpx:Temperature>9.1</wpx:Temperature>
|
||||
<wpx:Depth>6.1</wpx:Depth>
|
||||
<wpx:Temperature>9.1 <!-- comment --></wpx:Temperature>
|
||||
<wpx:Depth>6.1 <!-- comment --></wpx:Depth>
|
||||
</wpx:WaypointExtension>
|
||||
</extensions>
|
||||
</wpt>
|
||||
@@ -41,8 +41,8 @@
|
||||
<sym>Anchor</sym>
|
||||
<extensions>
|
||||
<ge:WaypointExtension>
|
||||
<ge:Temperature>19.2</ge:Temperature>
|
||||
<ge:Depth>16.2</ge:Depth>
|
||||
<ge:Temperature>19.2 <!-- comment --></ge:Temperature>
|
||||
<ge:Depth>16.2 <!-- comment --></ge:Depth>
|
||||
</ge:WaypointExtension>
|
||||
</extensions>
|
||||
</wpt>
|
||||
@@ -74,23 +74,23 @@
|
||||
<name>Gadgetbridge import test track</name>
|
||||
<trkseg>
|
||||
<trkpt lat="47.5048828125" lon="9.7393798828125">
|
||||
<ele>-440.2</ele>
|
||||
<time>2025-10-03T15:10:59Z</time>
|
||||
<ele>-440.2 <!-- comment --></ele>
|
||||
<time>2025-10-03T15:10:59Z <!-- comment --></time>
|
||||
<name>Tp1</name>
|
||||
<desc>a description</desc>
|
||||
<sym>Summit</sym>
|
||||
<hdop>1.4</hdop>
|
||||
<vdop>3.2</vdop>
|
||||
<pdop>1.5</pdop>
|
||||
<hdop>1.4 <!-- comment --></hdop>
|
||||
<vdop>3.2 <!-- comment --></vdop>
|
||||
<pdop>1.5 <!-- comment --></pdop>
|
||||
<extensions>
|
||||
<t1:TrackPointExtension>
|
||||
<t1:atemp>28.3</t1:atemp>
|
||||
<t1:depth>26.3</t1:depth>
|
||||
<t1:hr>123</t1:hr>
|
||||
<t1:cad>22</t1:cad>
|
||||
<t1:atemp>28.3 <!-- comment --></t1:atemp>
|
||||
<t1:depth>26.3 <!-- comment --></t1:depth>
|
||||
<t1:hr>123 <!-- comment --></t1:hr>
|
||||
<t1:cad>22 <!-- comment --></t1:cad>
|
||||
</t1:TrackPointExtension>
|
||||
<ax:TrackPointExtension>
|
||||
<ax:speed>23.3</ax:speed>
|
||||
<ax:speed>23.3 <!-- comment --></ax:speed>
|
||||
</ax:TrackPointExtension>
|
||||
</extensions>
|
||||
</trkpt>
|
||||
@@ -102,8 +102,8 @@
|
||||
<sym>Water</sym>
|
||||
<extensions>
|
||||
<ge:TrackPointExtension>
|
||||
<ge:Temperature>34.3</ge:Temperature>
|
||||
<ge:Depth>10345</ge:Depth>
|
||||
<ge:Temperature>34.3 <!-- comment --></ge:Temperature>
|
||||
<ge:Depth>10345 <!-- comment --></ge:Depth>
|
||||
</ge:TrackPointExtension>
|
||||
</extensions>
|
||||
</trkpt>
|
||||
@@ -111,11 +111,11 @@
|
||||
<time>2025-10-03T03:30:00-12:00</time>
|
||||
<extensions>
|
||||
<t2:TrackPointExtension>
|
||||
<t2:atemp>40.4</t2:atemp>
|
||||
<t2:depth>41.4</t2:depth>
|
||||
<t2:hr>42</t2:hr>
|
||||
<t2:cad>43</t2:cad>
|
||||
<t2:speed>44.4</t2:speed>
|
||||
<t2:atemp>40.4 <!-- comment --></t2:atemp>
|
||||
<t2:depth>41.4 <!-- comment --></t2:depth>
|
||||
<t2:hr>42 <!-- comment --></t2:hr>
|
||||
<t2:cad>43 <!-- comment --></t2:cad>
|
||||
<t2:speed>44.4 <!-- comment --></t2:speed>
|
||||
</t2:TrackPointExtension>
|
||||
</extensions>
|
||||
</trkpt>
|
||||
|
||||
@@ -0,0 +1,98 @@
|
||||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<gpx xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0"
|
||||
creator="GPSLogger 79 - http://gpslogger.mendhak.com/"
|
||||
xmlns="http://www.topografix.com/GPX/1/0"
|
||||
xsi:schemaLocation="http://www.topografix.com/GPX/1/0 http://www.topografix.com/GPX/1/0/gpx.xsd"
|
||||
xmlns:ns3="http://www.garmin.com/xmlschemas/TrackPointExtension/v1">
|
||||
|
||||
<name>Five Hikes in the White Mountains</name>
|
||||
<desc>Five Hikes in the White Mountains!!</desc>
|
||||
<author>Franz Wilhelmstötter</author>
|
||||
<email>franz.wilhelmstoetter@gmail.com</email>
|
||||
<url>https://github.com/jenetics/jpx</url>
|
||||
<urlname>Visit my New Hampshire hiking website!</urlname>
|
||||
<time>2016-08-21T12:24:27Z</time>
|
||||
<keywords>Hiking, NH, Presidential Range</keywords>
|
||||
|
||||
|
||||
<wpt lat="48.2033471" lon="16.3608048">
|
||||
<time>2016-08-21T12:51:30Z <!-- comment -->
|
||||
</time>
|
||||
<name>khm</name>
|
||||
<src>network</src>
|
||||
<extensions><foo>asdf</foo><foo>asdf</foo></extensions>
|
||||
</wpt>
|
||||
<wpt lat="48.34067" lon="16.71754">
|
||||
<ele>164.0 <!-- comment -->
|
||||
</ele>
|
||||
<name>Gänserndorf</name>
|
||||
</wpt>
|
||||
<trk>
|
||||
<name>March 21</name>
|
||||
<trkseg>
|
||||
<trkpt lat="48.19949341" lon="16.40377444">
|
||||
<ele>212.0 <!--comment-->
|
||||
</ele>
|
||||
<time>2016-08-21T12:24:27Z <!--comment-->
|
||||
</time>
|
||||
<course>341.6 <!--comment-->
|
||||
</course>
|
||||
<speed>0.67052215 <!--comment-->
|
||||
</speed>
|
||||
<src>gps <!--comment-->
|
||||
</src>
|
||||
<sat>14 <!--comment-->
|
||||
</sat>
|
||||
</trkpt>
|
||||
<trkpt lat="-48.19948359" lon="16.40371021">
|
||||
<ele>212.0 <ignoreBrokenXml /></ele>
|
||||
<time>2016-08-21T12:24:31Z <!-- comment -->
|
||||
</time>
|
||||
<course>298.6 <!-- comment -->
|
||||
</course>
|
||||
<speed>0.7424285 <!-- comment -->
|
||||
</speed>
|
||||
<geoidheight>43.0 <!-- comment -->
|
||||
</geoidheight>
|
||||
<src>gps</src>
|
||||
<sat>2</sat>
|
||||
<hdop>0.7 <!-- comment -->
|
||||
</hdop>
|
||||
<vdop>0.8 <!-- comment -->
|
||||
</vdop>
|
||||
<pdop>1.1 <!-- comment -->
|
||||
</pdop>
|
||||
</trkpt>
|
||||
<trkpt lat="45.589817" lon="-73.67511">
|
||||
<ele>42.05 <!-- comment -->
|
||||
</ele>
|
||||
<time>2023-05-07T18:34:59Z <!-- comment -->
|
||||
</time>
|
||||
<name>Position 1</name>
|
||||
<extensions>
|
||||
<ns3:TrackPointExtension>
|
||||
<ns3:speed>2.3255813 <!-- comment -->
|
||||
</ns3:speed> <!-- comment -->
|
||||
<ns3:cad>0.0 <!-- comment -->
|
||||
</ns3:cad>
|
||||
<ns3:hr>72 <!-- comment -->
|
||||
</ns3:hr>
|
||||
</ns3:TrackPointExtension>
|
||||
</extensions>
|
||||
</trkpt>
|
||||
<trkpt lat="52.52543" lon="0.07307"><speed>NaN</speed></trkpt>
|
||||
<trkpt lat="52.52483" lon="0.07329" />
|
||||
</trkseg>
|
||||
</trk>
|
||||
<trk>
|
||||
<trkseg>
|
||||
<trkpt lat="52.53395" lon="0.07863">
|
||||
<extensions />
|
||||
</trkpt>
|
||||
</trkseg>
|
||||
<trkseg>
|
||||
<trkpt lat="52.53667" lon="0.09328"></trkpt>
|
||||
<trkpt lat="52.5367" lon="0.09352"></trkpt>
|
||||
</trkseg>
|
||||
</trk>
|
||||
</gpx>
|
||||
@@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><gpx name="Five Hikes in the White Mountains" author="Franz Wilhelmstötter" time="2016-08-21T12:24:27Z">
|
||||
<wpt lat="48.2033471" lon="16.3608048" time="2016-08-21T12:51:30Z" name="khm"/>
|
||||
<wpt lat="48.34067" lon="16.71754" ele="164.0" name="Gänserndorf"/>
|
||||
<trk name="March 21">
|
||||
<trkseg>
|
||||
<trkpt lat="48.19949341" lon="16.40377444" ele="212.0" time="2016-08-21T12:24:27Z" speed="0.67052215"/>
|
||||
<trkpt lat="-48.19948359" lon="16.40371021" ele="212.0" time="2016-08-21T12:24:31Z" hdop="0.7" vdop="0.8" pdop="1.1" speed="0.7424285"/>
|
||||
<trkpt lat="45.589817" lon="-73.67511" ele="42.05" time="2023-05-07T18:34:59Z" name="Position 1" hr="72" cad="0.0" speed="2.3255813"/>
|
||||
<trkpt lat="52.52543" lon="0.07307" speed="NaN"/>
|
||||
<trkpt lat="52.52483" lon="0.07329"/>
|
||||
</trkseg>
|
||||
</trk>
|
||||
<trk>
|
||||
<trkseg>
|
||||
<trkpt lat="52.53395" lon="0.07863"/>
|
||||
</trkseg>
|
||||
<trkseg>
|
||||
<trkpt lat="52.53667" lon="0.09328"/>
|
||||
<trkpt lat="52.5367" lon="0.09352"/>
|
||||
</trkseg>
|
||||
</trk>
|
||||
</gpx>
|
||||
Reference in New Issue
Block a user