Skip to content

Commit

Permalink
Idle: TrackRecordingManager creates IDLE TrackPoints.
Browse files Browse the repository at this point in the history
Fixes of #1187.
  • Loading branch information
dennisguse committed Jul 31, 2023
1 parent 88db8d0 commit 723a21e
Show file tree
Hide file tree
Showing 6 changed files with 59 additions and 64 deletions.
Original file line number Diff line number Diff line change
@@ -1,33 +1,16 @@
package de.dennisguse.opentracks.data.model;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;

import org.junit.Test;

import java.time.Instant;
import java.time.temporal.ChronoUnit;

import de.dennisguse.opentracks.data.models.Distance;
import de.dennisguse.opentracks.data.models.TrackPoint;

public class TrackPointTest {

@Test
public void isRecent_true() {
TrackPoint tp = new TrackPoint(TrackPoint.Type.SEGMENT_END_MANUAL, Instant.now());

assertTrue(tp.isRecent());
}

@Test
public void isRecent_false() {
TrackPoint tp = new TrackPoint(TrackPoint.Type.SEGMENT_END_MANUAL, Instant.now().minus(2, ChronoUnit.MINUTES));

assertFalse(tp.isRecent());
}

@Test
public void distanceToPrevious() {
TrackPoint tp1 = new TrackPoint(TrackPoint.Type.TRACKPOINT, Instant.ofEpochMilli(0))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -284,11 +284,6 @@ public TrackPoint setSpeed(Speed speed) {
this.speed = speed;
return this;
}

public boolean isMoving() {
return hasSpeed() && getSpeed().isMoving();
}

public boolean hasBearing() {
return bearing != null;
}
Expand Down Expand Up @@ -349,9 +344,8 @@ public boolean fulfillsAccuracy(Distance thresholdHorizontalAccuracy) {
return hasHorizontalAccuracy() && horizontalAccuracy.lessThan(thresholdHorizontalAccuracy);
}

//TODO Bearing requires a location; what do we do if we don't have any?
public float bearingTo(@NonNull TrackPoint dest) {
return getLocation().bearingTo(dest.getLocation());
return bearingTo(dest.getLocation());
}

//TODO Bearing requires a location; what do we do if we don't have any?
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
import android.content.SharedPreferences;
import android.database.sqlite.SQLiteException;
import android.net.Uri;
import android.os.Handler;
import android.util.Log;
import android.util.Pair;

Expand Down Expand Up @@ -32,11 +33,17 @@ class TrackRecordingManager implements SharedPreferences.OnSharedPreferenceChang

private static final String TAG = TrackRecordingManager.class.getSimpleName();

private static final Duration IDLE_TIMEOUT = Duration.ofSeconds(30);

private static final AltitudeCorrectionManager ALTITUDE_CORRECTION_MANAGER = new AltitudeCorrectionManager();

private final Runnable ON_IDLE = this::onIdle;

private final ContentProviderUtils contentProviderUtils;
private final Context context;

private final Handler handler;

private final TrackPointCreator trackPointCreator;

private Distance recordingDistanceInterval;
Expand All @@ -52,9 +59,10 @@ class TrackRecordingManager implements SharedPreferences.OnSharedPreferenceChang
private TrackPoint lastStoredTrackPoint;
private TrackPoint lastStoredTrackPointWithLocation;

TrackRecordingManager(Context context, TrackPointCreator trackPointCreator) {
TrackRecordingManager(Context context, TrackPointCreator trackPointCreator, Handler handler) {
this.context = context;
this.trackPointCreator = trackPointCreator;
this.handler = handler;
contentProviderUtils = new ContentProviderUtils(context);
}

Expand Down Expand Up @@ -162,16 +170,27 @@ public Marker.Id insertMarker(String name, String category, String description,
return new Marker.Id(ContentUris.parseId(uri));
}

void onIdle() {
Log.d(TAG, "Becoming idle");
onNewTrackPoint(trackPointCreator.createIdle());
handler.removeCallbacks(this::onIdle);
}

/**
* @return TrackPoint was stored?
*/
boolean onNewTrackPoint(@NonNull TrackPoint trackPoint) {
synchronized boolean onNewTrackPoint(@NonNull TrackPoint trackPoint) {
if (trackPoint.hasSpeed()) {
lastTrackPointUIWithSpeed = trackPoint;
}
if (trackPoint.hasAltitude()) {
lastTrackPointUIWithAltitude = trackPoint;
}

if (trackPoint.getType() == TrackPoint.Type.IDLE) {
insertTrackPoint(trackPoint, true);
return true;
}
//Storing trackPoint

// Always insert the first segment location
Expand All @@ -192,10 +211,10 @@ boolean onNewTrackPoint(@NonNull TrackPoint trackPoint) {
if (!shouldStore) {
Log.d(TAG, "Ignoring TrackPoint as it has no distance (and sensor data is not new enough).");
return false;
} else {
insertTrackPoint(trackPoint, true);
return true;
}

insertTrackPoint(trackPoint, true);
return true;
}

Distance distanceToLastStoredTrackPoint;
Expand All @@ -208,18 +227,17 @@ boolean onNewTrackPoint(@NonNull TrackPoint trackPoint) {
if (distanceToLastStoredTrackPoint.greaterThan(maxRecordingDistance)) {
trackPoint.setType(TrackPoint.Type.SEGMENT_START_AUTOMATIC);
insertTrackPoint(trackPoint, true);

handler.removeCallbacks(ON_IDLE);
handler.postDelayed(ON_IDLE, IDLE_TIMEOUT.toMillis());
return true;
}

if (distanceToLastStoredTrackPoint.greaterOrEqualThan(recordingDistanceInterval)
&& trackPoint.isMoving()) {
if (distanceToLastStoredTrackPoint.greaterOrEqualThan(recordingDistanceInterval)) {
insertTrackPoint(trackPoint, false);
return true;
}

if (trackPoint.isMoving() != lastStoredTrackPoint.isMoving()) {
// Moving from non-moving to moving or vice versa; required to compute moving time correctly.
insertTrackPoint(trackPoint, true);
handler.removeCallbacks(ON_IDLE);
handler.postDelayed(this::onIdle, IDLE_TIMEOUT.toMillis());
return true;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -99,8 +99,8 @@ public void onCreate() {
gpsStatusObservable = new MutableLiveData<>(STATUS_GPS_DEFAULT);
recordingDataObservable = new MutableLiveData<>(NOT_RECORDING);

trackPointCreator = new TrackPointCreator(this, this, handler);
trackRecordingManager = new TrackRecordingManager(this, trackPointCreator);
trackPointCreator = new TrackPointCreator(this);
trackRecordingManager = new TrackRecordingManager(this, trackPointCreator, handler);
trackRecordingManager.start();

voiceAnnouncementManager = new VoiceAnnouncementManager(this);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,16 +35,11 @@ public class TrackPointCreator {
private Clock clock = new MonotonicClock();
private SensorManager sensorManager;

public TrackPointCreator(Callback service, Context context, Handler handler) {
public TrackPointCreator(Callback service) {
this.service = service;
this.sensorManager = new SensorManager(this);
}

@VisibleForTesting
TrackPointCreator(Callback service) {
this.service = service;
}

public synchronized void start(@NonNull Context context, @NonNull Handler handler) {
this.context = context;

Expand Down Expand Up @@ -105,6 +100,13 @@ public synchronized TrackPoint createSegmentEnd() {
return segmentEnd;
}

public synchronized TrackPoint createIdle() {
TrackPoint idle = new TrackPoint(TrackPoint.Type.IDLE, createNow());
addSensorData(idle);
reset();
return idle;
}

public Pair<TrackPoint, SensorDataSet> createCurrentTrackPoint(@Nullable TrackPoint lastTrackPointUISpeed, @Nullable TrackPoint lastTrackPointUIAltitude, @Nullable TrackPoint lastStoredTrackPointWithLocation) {
TrackPoint currentTrackPoint = new TrackPoint(TrackPoint.Type.TRACKPOINT, createNow());

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -132,26 +132,24 @@ public void addTrackPoint(TrackPoint trackPoint) {
currentSegment.setAverageHeartRate(HeartRate.of(averageHeartRateBPM));
}

// Update total distance
if (trackPoint.hasSensorDistance()) {
// Sensor-based distance/speed
currentSegment.addTotalDistance(trackPoint.getSensorDistance());
} else if (lastTrackPoint != null
&& lastTrackPoint.hasLocation()
&& trackPoint.hasLocation() && trackPoint.isMoving()) {
// GPS-based distance/speed
// Assumption: we ignore TrackPoints that are not moving as those are likely imprecise GPS measurements
Distance movingDistance = trackPoint.distanceToPrevious(lastTrackPoint);
currentSegment.addTotalDistance(movingDistance);
}


// Update moving time
if (trackPoint.isMoving() && lastTrackPoint != null && lastTrackPoint.isMoving()) {
currentSegment.addMovingTime(trackPoint, lastTrackPoint);

// Update max speed
updateSpeed(trackPoint, lastTrackPoint);
{
// Update total distance
Distance movingDistance = null;
if (trackPoint.hasSensorDistance()) {
movingDistance = trackPoint.getSensorDistance();
} else if (lastTrackPoint != null
&& lastTrackPoint.hasLocation()
&& trackPoint.hasLocation()) {
// GPS-based distance/speed
movingDistance = trackPoint.distanceToPrevious(lastTrackPoint);
}
if (movingDistance != null) {
currentSegment.addTotalDistance(movingDistance);
if (lastTrackPoint != null) {
currentSegment.addMovingTime(trackPoint, lastTrackPoint);
updateSpeed(trackPoint, lastTrackPoint);
}
}
}

if (trackPoint.isSegmentManualEnd()) {
Expand Down

0 comments on commit 723a21e

Please sign in to comment.