Bugfix: export now really includes sensor data (as double) and import is done as float.

This commit is contained in:
Dennis Guse
2019-10-21 21:58:41 +02:00
parent 75ef8d99d4
commit 1719d21a5b
4 changed files with 57 additions and 38 deletions
@@ -49,9 +49,10 @@ public class KmlTrackWriter implements TrackWriter {
private static final String END_STYLE = "end";
private static final String TRACK_STYLE = "track";
private static final String SCHEMA_ID = "schema";
private static final String CADENCE = "cadence";
private static final String HEART_RATE = "heart_rate";
private static final String POWER = "power";
private static final String SENSOR_TYPE_CADENCE = "cadence";
private static final String SENSOR_TYPE_HEART_RATE = "heart_rate";
private static final String SENSOR_TYPE_POWER = "power";
private static final String WAYPOINT_ICON = "http://maps.google.com/mapfiles/kml/pushpin/blue-pushpin.png";
private static final String STATISTICS_ICON = "http://maps.google.com/mapfiles/kml/pushpin/ylw-pushpin.png";
@@ -129,9 +130,9 @@ public class KmlTrackWriter implements TrackWriter {
printWriter.println("<Schema id=\"" + SCHEMA_ID + "\">");
if (exportSensorData) {
writeSensorStyle(POWER, context.getString(R.string.description_sensor_power));
writeSensorStyle(CADENCE, context.getString(R.string.description_sensor_cadence));
writeSensorStyle(HEART_RATE, context.getString(R.string.description_sensor_heart_rate));
writeSensorStyle(SENSOR_TYPE_POWER, context.getString(R.string.description_sensor_power));
writeSensorStyle(SENSOR_TYPE_CADENCE, context.getString(R.string.description_sensor_cadence));
writeSensorStyle(SENSOR_TYPE_HEART_RATE, context.getString(R.string.description_sensor_heart_rate));
}
printWriter.println("</Schema>");
}
@@ -245,13 +246,13 @@ public class KmlTrackWriter implements TrackWriter {
printWriter.println("<SchemaData schemaUrl=\"#" + SCHEMA_ID + "\">");
if (exportSensorData) {
if (powerList.size() > 0) {
writeSensorData(powerList, POWER);
writeSensorData(powerList, SENSOR_TYPE_POWER);
}
if (cadenceList.size() > 0) {
writeSensorData(cadenceList, CADENCE);
writeSensorData(cadenceList, SENSOR_TYPE_CADENCE);
}
if (heartRateList.size() > 0) {
writeSensorData(heartRateList, HEART_RATE);
writeSensorData(heartRateList, SENSOR_TYPE_HEART_RATE);
}
}
printWriter.println("</SchemaData>");
@@ -460,11 +461,11 @@ public class KmlTrackWriter implements TrackWriter {
* Writes a sensor style.
*
* @param name the name of the sesnor
* @param displayName the sensor display name
* @param sensorType the sensor display name
*/
private void writeSensorStyle(String name, String displayName) {
printWriter.println("<gx:SimpleArrayField name=\"" + name + "\" type=\"int\">");
printWriter.println("<displayName>" + StringUtils.formatCData(displayName) + "</displayName>");
private void writeSensorStyle(String name, String sensorType) {
printWriter.println("<gx:SimpleArrayField name=\"" + name + "\" type=\"float\">");
printWriter.println("<displayName>" + StringUtils.formatCData(sensorType) + "</displayName>");
printWriter.println("</gx:SimpleArrayField>");
}
}
@@ -384,8 +384,7 @@ abstract class AbstractFileTrackImporter extends DefaultHandler implements Track
* @param message the message
*/
protected String createErrorMessage(String message) {
return String.format(Locale.US, "Parsing error at line: %d column: %d. %s",
locator.getLineNumber(), locator.getColumnNumber(), message);
return String.format(Locale.US, "Parsing error at line: %d column: %d. %s", locator.getLineNumber(), locator.getColumnNumber(), message);
}
/**
@@ -19,6 +19,7 @@ package de.dennisguse.opentracks.io.file.importer;
import android.content.Context;
import android.location.Location;
import android.net.Uri;
import android.util.Log;
import androidx.annotation.VisibleForTesting;
@@ -39,6 +40,8 @@ import de.dennisguse.opentracks.content.sensor.SensorDataSet;
*/
public class KmlFileTrackImporter extends AbstractFileTrackImporter {
private static final String TAG = KmlFileTrackImporter.class.getSimpleName();
private static final String CADENCE = "cadence";
private static final String HEART_RATE = "heart_rate";
private static final String POWER = "power";
@@ -65,11 +68,11 @@ public class KmlFileTrackImporter extends AbstractFileTrackImporter {
private static final String ATTRIBUTE_NAME = "name";
private boolean trackStarted = false;
private String sensorName;
private String sensorType;
private ArrayList<Location> locationList;
private ArrayList<Integer> cadenceList;
private ArrayList<Integer> heartRateList;
private ArrayList<Integer> powerList;
private ArrayList<Float> cadenceList;
private ArrayList<Float> heartRateList;
private ArrayList<Float> powerList;
/**
* Constructor.
@@ -229,20 +232,30 @@ public class KmlFileTrackImporter extends AbstractFileTrackImporter {
*/
private void onTrackSegmentEnd() {
// Close a track segment by inserting the segment locations
boolean hasHeartRate = heartRateList.size() == locationList.size();
boolean hasCadence = cadenceList.size() == locationList.size();
boolean hasPower = powerList.size() == locationList.size();
for (int i = 0; i < locationList.size(); i++) {
Location location = locationList.get(i);
if (!hasPower && !hasCadence && !hasHeartRate) {
boolean hasSensorData = false;
float heartrate = SensorDataSet.DATA_UNAVAILABLE;
float cadence = SensorDataSet.DATA_UNAVAILABLE;
float power = SensorDataSet.DATA_UNAVAILABLE;
if (i < heartRateList.size()) {
heartrate = heartRateList.get(i);
hasSensorData = true;
}
if (i < cadenceList.size()) {
cadence = cadenceList.get(i);
hasSensorData = true;
}
if (i < powerList.size()) {
power = powerList.get(i);
hasSensorData = true;
}
if (!hasSensorData) {
insertTrackPoint(location);
} else {
float heartrate = hasHeartRate ? heartRateList.get(i) : SensorDataSet.DATA_UNAVAILABLE;
float cadence = hasHeartRate ? cadenceList.get(i) : SensorDataSet.DATA_UNAVAILABLE;
float power = hasHeartRate ? powerList.get(i) : SensorDataSet.DATA_UNAVAILABLE;
SensorDataSetLocation sensorDataSetLocation = new SensorDataSetLocation(location, new SensorDataSet(heartrate, cadence, power, SensorDataSet.DATA_UNAVAILABLE, location.getTime()));
insertTrackPoint(sensorDataSetLocation);
}
@@ -277,7 +290,7 @@ public class KmlFileTrackImporter extends AbstractFileTrackImporter {
* On sensor data start. gx:SimpleArrayData start tag.
*/
private void onSensorDataStart(Attributes attributes) {
sensorName = attributes.getValue(ATTRIBUTE_NAME);
sensorType = attributes.getValue(ATTRIBUTE_NAME);
}
/**
@@ -291,18 +304,24 @@ public class KmlFileTrackImporter extends AbstractFileTrackImporter {
if (content.equals("")) {
return;
}
int value;
float value;
try {
value = Integer.parseInt(content);
value = Float.valueOf(content);
} catch (NumberFormatException e) {
throw new SAXException(createErrorMessage("Unable to parse gx:value:" + content), e);
}
if (POWER.equals(sensorName)) {
powerList.add(value);
} else if (HEART_RATE.equals(sensorName)) {
heartRateList.add(value);
} else if (CADENCE.equals(sensorName)) {
cadenceList.add(value);
switch (sensorType) {
case POWER:
powerList.add(value);
break;
case HEART_RATE:
heartRateList.add(value);
break;
case CADENCE:
cadenceList.add(value);
break;
default:
Log.w(TAG, "Data from sensor " + sensorType + " is not (yet) supported.");
}
}
}
@@ -853,7 +853,7 @@ public class TrackRecordingService extends Service {
*/
private void insertLocation(Track track, Location location, Location lastValidTrackPoint) {
if (location == null) {
Log.w(TAG, "Ignore insertLocation. loation is null.");
Log.w(TAG, "Ignore insertLocation. location is null.");
return;
}
// Do not insert if inserted already