summaryrefslogtreecommitdiff
path: root/utilities/data2kml/data2kml.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'utilities/data2kml/data2kml.cpp')
-rw-r--r--utilities/data2kml/data2kml.cpp162
1 files changed, 119 insertions, 43 deletions
diff --git a/utilities/data2kml/data2kml.cpp b/utilities/data2kml/data2kml.cpp
index 86c805d..704111b 100644
--- a/utilities/data2kml/data2kml.cpp
+++ b/utilities/data2kml/data2kml.cpp
@@ -15,7 +15,7 @@
typedef struct {
uint32_t timestamp;
float lat;
- float lon;
+ float lng;
uint16_t speed;
uint16_t speedgps;
uint16_t rpm;
@@ -37,23 +37,46 @@ typedef struct {
DATASET* dataset;
int datacount;
float startLat;
- float startLon;
+ float startLng;
uint32_t curDate;
uint32_t curTime;
uint32_t ts;
uint32_t lastts;
float lastLat;
- float lastLon;
+ float lastLng;
uint32_t lastTime;
DATASET datas;
} KML_DATA;
-void WriteKMLData(KML_DATA* kd, uint32_t timestamp, uint16_t pid, float value[])
+uint16_t hex2uint16(const char *p)
+{
+ char c = *p;
+ uint16_t i = 0;
+ for (char n = 0; c && n < 4; c = *(++p)) {
+ if (c >= 'A' && c <= 'F') {
+ c -= 7;
+ }
+ else if (c >= 'a' && c <= 'f') {
+ c -= 39;
+ }
+ else if (c == ' ') {
+ continue;
+ }
+ else if (c < '0' || c > '9') {
+ break;
+ }
+ i = (i << 4) | (c & 0xF);
+ n++;
+ }
+ return i;
+}
+
+void WriteKMLData(KML_DATA* kd, uint32_t timestamp, uint16_t pid, int value[])
{
kd->ts = timestamp;
switch (pid) {
case PID_GPS_LATITUDE:
- kd->datas.lat = value[0] / 100000;
+ kd->datas.lat = (float)value[0] / 1000000;
if (!kd->startLat) {
kd->startLat = kd->datas.lat;
}
@@ -64,18 +87,18 @@ void WriteKMLData(KML_DATA* kd, uint32_t timestamp, uint16_t pid, float value[])
}
break;
case PID_GPS_LONGITUDE:
- kd->datas.lon = value[0] / 100000;
- if (!kd->startLon) {
- kd->startLon = kd->datas.lon;
+ kd->datas.lng = (float)value[0] / 1000000;
+ if (!kd->startLng) {
+ kd->startLng = kd->datas.lng;
}
if (kd->datacount > 0) {
- float diff = kd->datas.lon - kd->dataset[kd->datacount - 1].lon;
+ float diff = kd->datas.lng - kd->dataset[kd->datacount - 1].lng;
if (diff > 0.1 || diff < -0.1)
- kd->datas.lon = 0;
+ kd->datas.lng = 0;
}
break;
case PID_GPS_ALTITUDE:
- kd->datas.alt = (uint16_t)value[0];
+ kd->datas.alt = value[0];
break;
case PID_SPEED:
kd->datas.speed = (uint16_t)value[0];
@@ -113,7 +136,7 @@ void WriteKMLData(KML_DATA* kd, uint32_t timestamp, uint16_t pid, float value[])
kd->curTime = (uint32_t)value[0];
break;
}
- if (kd->curTime != kd->lastTime && kd->datas.lat && kd->datas.lon) {
+ if (kd->curTime != kd->lastTime && kd->datas.lat && kd->datas.lng) {
fprintf(kd->fp, "<when>");
if (kd->curDate) {
fprintf(kd->fp, "%04u-%02u-%02u", 2000 + (kd->curDate % 100), (kd->curDate / 100) % 100, kd->curDate / 10000);
@@ -127,7 +150,7 @@ void WriteKMLData(KML_DATA* kd, uint32_t timestamp, uint16_t pid, float value[])
fprintf(kd->fp, "T%02u:%02u:%02u.%03uZ", kd->curTime / 1000000, (kd->curTime / 10000) % 100, (kd->curTime / 100) % 100, (kd->curTime % 100) * 10);
}
fprintf(kd->fp, "</when>");
- fprintf(kd->fp, "<gx:coord>%f %f %d</gx:coord>", kd->datas.lon, kd->datas.lat, kd->datas.alt);
+ fprintf(kd->fp, "<gx:coord>%f %f %d</gx:coord>", kd->datas.lng, kd->datas.lat, kd->datas.alt);
kd->datas.timestamp = timestamp;
kd->dataset = (DATASET*)realloc(kd->dataset, sizeof(DATASET) * (kd->datacount + 1));
@@ -135,7 +158,7 @@ void WriteKMLData(KML_DATA* kd, uint32_t timestamp, uint16_t pid, float value[])
kd->datacount++;
kd->lastLat = kd->datas.lat;
- kd->lastLon = kd->datas.lon;
+ kd->lastLng = kd->datas.lng;
kd->lastTime = kd->curTime;
}
}
@@ -263,7 +286,7 @@ void WriteKMLTail(KML_DATA* kd)
if (g <= -0.15f) {
n++;
fprintf(kd->fp, "<Placemark><name>#%d %u:%02u</name>", n, kd->dataset[i].timestamp / 60000, (kd->dataset[i].timestamp / 1000) % 60);
- fprintf(kd->fp, "<styleUrl>#brakepoint</styleUrl><Point><coordinates>%f,%f</coordinates></Point>", kd->dataset[i].lon, kd->dataset[i].lat);
+ fprintf(kd->fp, "<styleUrl>#brakepoint</styleUrl><Point><coordinates>%f,%f</coordinates></Point>", kd->dataset[i].lng, kd->dataset[i].lat);
fprintf(kd->fp, "<ExtendedData>");
fprintf(kd->fp, "<Data name=\"Speed\"><value>%d</value></Data>", kd->dataset[i].speed);
fprintf(kd->fp, "<Data name=\"RPM\"><value>%d</value></Data>", kd->dataset[i].rpm);
@@ -285,6 +308,26 @@ void Cleanup(KML_DATA* kd)
free(kd);
}
+int ReadLine(FILE* fp, char* buf, int bufsize)
+{
+ int c;
+ int n = 0;
+ for (;;) {
+ c = fgetc(fp);
+ if (c == -1) break;
+ if (c == '\r' || c == '\n') {
+ if (n == 0)
+ continue;
+ else
+ break;
+ }
+ if (n == bufsize - 1) break;
+ buf[n++] = c;
+ }
+ buf[n] = 0;
+ return n;
+}
+
int ConvertToKML(const char* logfile, const char* kmlfile, uint32_t startpos, uint32_t endpos)
{
FILE* fp = fopen(logfile, "r");
@@ -303,37 +346,70 @@ int ConvertToKML(const char* logfile, const char* kmlfile, uint32_t startpos, ui
int elapsed;
int pid;
- while (fscanf(fp, "%d,%X,", &elapsed, &pid) > 0) {
- char c;
- char data[64];
- int i = 0;
- int index = 0;
- float value[3] = {0};
- while ((c = fgetc(fp)) != '\r') {
- if (i == sizeof(data)) continue;
- data[i++] = c;
- if (c == ' ') {
- if (index < 2) {
- data[i] = 0;
- value[index++] = atof(data);
- i = 0;
- }
- }
+ char buf[1024];
+ while (ReadLine(fp, buf, sizeof(buf)) > 0) {
+ if (buf[0] == '#') {
+ // absolute timestamp
+ ts = atoi(buf + 1);
}
- data[i] = 0;
- value[index] = atof(data);
- ts += elapsed;
- if (ts < startpos)
- continue;
+ else {
+ ts += atoi(buf);
+ }
+ char *p = strchr(buf, ',');
+ if (!p++) continue;
+ pid = 0;
+ if (*(p + 3) == ',') {
+ if (!memcmp(p, "DTE", 3))
+ pid = PID_GPS_DATE;
+ else if (!memcmp(p, "UTC", 3))
+ pid = PID_GPS_TIME;
+ else if (!memcmp(p, "UTC", 3))
+ pid = PID_GPS_TIME;
+ else if (!memcmp(p, "LAT", 3))
+ pid = PID_GPS_LATITUDE;
+ else if (!memcmp(p, "LNG", 3))
+ pid = PID_GPS_LONGITUDE;
+ else if (!memcmp(p, "ALT", 3))
+ pid = PID_GPS_ALTITUDE;
+ else if (!memcmp(p, "SPD", 3))
+ pid = PID_GPS_SPEED;
+ else if (!memcmp(p, "CRS", 3))
+ pid = PID_GPS_HEADING;
+ else if (!memcmp(p, "SAT", 3))
+ pid = PID_GPS_SAT_COUNT;
+ else if (!memcmp(p, "ACC", 3))
+ pid = PID_ACC;
+ else if (!memcmp(p, "GYR", 3))
+ pid = PID_GYRO;
+ else if (!memcmp(p, "MAG", 3))
+ pid = PID_COMPASS;
+ else if (!memcmp(p, "BAT", 3))
+ pid = PID_BATTERY_VOLTAGE;
+ }
+ if (pid == 0)
+ pid = hex2uint16(p);
- printf("Time=%.1f PID=%X", (float)ts / 1000, pid);
- for (int n = 0; n <= index; n++) {
- if (value[n] == (int)value[n])
- printf(" D%d=%d", n, (int)value[n]);
- else
- printf(" D%d=%f", n, value[n]);
+ p = strchr(p, ',');
+ if (!p++) continue;
+
+ int value[3] = {0};
+ int i = 0;
+ int total = 0;
+ do {
+ value[i] = atoi(p);
+ p = strchr(p, ',');
+ if (!p++) break;
+ total = ++i;
+ } while (i < 3);
+
+ printf("Time=%.2f ", (float)ts / 1000);
+ if (total == 1) {
+ printf("%X=%d", pid, value[0]);
+ }
+ else {
+ printf("%X=%d,%d,%d", pid, value[0], value[1], value[2]);
}
- putchar('\n');
+ printf("\n");
WriteKMLData(kd, ts, pid, value);
if (endpos && ts > endpos)