Support altitude correction via Android's native AltitudeConverter (API34+).

Fixes #1492.
This commit is contained in:
Dennis Guse
2023-06-22 22:50:34 +02:00
parent 0c5c49cd92
commit 8c364ba7e2
4 changed files with 77 additions and 39 deletions
@@ -39,7 +39,7 @@ import de.dennisguse.opentracks.data.tables.TrackPointsColumns;
import de.dennisguse.opentracks.data.tables.TracksColumns;
import de.dennisguse.opentracks.services.RecordingStatus;
import de.dennisguse.opentracks.services.TrackRecordingService;
import de.dennisguse.opentracks.services.handlers.EGM2008CorrectionManager;
import de.dennisguse.opentracks.services.handlers.AltitudeCorrectionManager;
import de.dennisguse.opentracks.stats.TrackStatistics;
import de.dennisguse.opentracks.stats.TrackStatisticsUpdater;
@@ -73,7 +73,7 @@ public class TrackDataHub {
private final ContentProviderUtils contentProviderUtils;
private final int targetNumPoints;
private final EGM2008CorrectionManager egm2008Correction = new EGM2008CorrectionManager();
private final AltitudeCorrectionManager egm2008Correction = new AltitudeCorrectionManager();
//TODO Check if this is needed.
private HandlerThread handlerThread;
@@ -36,7 +36,7 @@ import de.dennisguse.opentracks.data.models.Track;
import de.dennisguse.opentracks.data.models.TrackPoint;
import de.dennisguse.opentracks.sensors.sensorData.SensorDataSet;
import de.dennisguse.opentracks.services.announcement.VoiceAnnouncementManager;
import de.dennisguse.opentracks.services.handlers.EGM2008CorrectionManager;
import de.dennisguse.opentracks.services.handlers.AltitudeCorrectionManager;
import de.dennisguse.opentracks.services.handlers.GpsStatusValue;
import de.dennisguse.opentracks.services.handlers.TrackPointCreator;
import de.dennisguse.opentracks.util.SystemUtils;
@@ -95,7 +95,7 @@ public class TrackRecordingService extends Service implements TrackPointCreator.
private VoiceAnnouncementManager voiceAnnouncementManager;
private TrackRecordingServiceNotificationManager notificationManager;
private EGM2008CorrectionManager egm2008CorrectionManager;
private AltitudeCorrectionManager egm2008CorrectionManager;
@Override
public void onCreate() {
@@ -108,7 +108,7 @@ public class TrackRecordingService extends Service implements TrackPointCreator.
gpsStatusObservable = new MutableLiveData<>(STATUS_GPS_DEFAULT);
recordingDataObservable = new MutableLiveData<>(NOT_RECORDING);
egm2008CorrectionManager = new EGM2008CorrectionManager();
egm2008CorrectionManager = new AltitudeCorrectionManager();
trackRecordingManager = new TrackRecordingManager(this);
trackRecordingManager.start();
trackPointCreator = new TrackPointCreator(this, this, handler);
@@ -0,0 +1,72 @@
package de.dennisguse.opentracks.services.handlers;
import android.content.Context;
import android.location.Location;
import android.location.altitude.AltitudeConverter;
import android.os.Build;
import android.util.Log;
import java.io.IOException;
import de.dennisguse.opentracks.data.models.Altitude;
import de.dennisguse.opentracks.data.models.TrackPoint;
import de.dennisguse.opentracks.util.EGM2008Utils;
/**
* More infos regarding Android 34's <a href="https://issuetracker.google.com/issues/195660815#comment1">AltitudeConverter</a>.
*/
public class AltitudeCorrectionManager {
private static final String TAG = AltitudeCorrectionManager.class.getSimpleName();
private AltitudeConverter altitudeConverter;
private final EGM2008Internal altitudeConverterFallback;
public AltitudeCorrectionManager() {
this.altitudeConverterFallback = new EGM2008Internal();
this.altitudeConverter = Build.VERSION.SDK_INT >= 34 ? new AltitudeConverter() : null;
}
public void correctAltitude(Context context, TrackPoint trackPoint) {
if (Build.VERSION.SDK_INT >= 34 && altitudeConverter != null) {
try {
Location loc = trackPoint.getLocation();
altitudeConverter.addMslAltitudeToLocation(context, loc);
trackPoint.setAltitude(Altitude.EGM2008.of(loc.getMslAltitudeMeters()));
return;
} catch (IOException e) {
Log.w(TAG, "Android's AltitudeConverter crashed; falling back to internal.");
altitudeConverter = null;
// Should we fallback
}
}
altitudeConverterFallback.correctAltitude(context, trackPoint);
}
private static class EGM2008Internal {
private static final String TAG = EGM2008Internal.class.getSimpleName();
private EGM2008Utils.EGM2008Correction egm2008Correction;
public void correctAltitude(Context context, TrackPoint trackPoint) {
if (!trackPoint.hasLocation() || !trackPoint.hasAltitude()) {
Log.d(TAG, "No altitude correction necessary.");
return;
}
if (egm2008Correction == null || !egm2008Correction.canCorrect(trackPoint.getLocation())) {
try {
egm2008Correction = EGM2008Utils.createCorrection(context, trackPoint.getLocation());
} catch (IOException e) {
Log.e(TAG, "Could not load altitude correction for " + trackPoint, e);
return;
}
}
trackPoint.setAltitude(egm2008Correction.correctAltitude(trackPoint.getLocation()));
}
}
}
@@ -1,34 +0,0 @@
package de.dennisguse.opentracks.services.handlers;
import android.content.Context;
import android.util.Log;
import java.io.IOException;
import de.dennisguse.opentracks.data.models.TrackPoint;
import de.dennisguse.opentracks.util.EGM2008Utils;
public class EGM2008CorrectionManager {
private static final String TAG = EGM2008CorrectionManager.class.getSimpleName();
private EGM2008Utils.EGM2008Correction egm2008Correction;
public void correctAltitude(Context context, TrackPoint trackPoint) {
if (!trackPoint.hasLocation() || !trackPoint.hasAltitude()) {
Log.d(TAG, "No altitude correction necessary.");
return;
}
if (egm2008Correction == null || !egm2008Correction.canCorrect(trackPoint.getLocation())) {
try {
egm2008Correction = EGM2008Utils.createCorrection(context, trackPoint.getLocation());
} catch (IOException e) {
Log.e(TAG, "Could not load altitude correction for " + trackPoint, e);
return;
}
}
trackPoint.setAltitude(egm2008Correction.correctAltitude(trackPoint.getLocation()));
}
}