DataSourceManager now always registers for all changes.

This commit is contained in:
Dennis Guse
2020-04-02 18:44:23 +02:00
parent 2ef74eb908
commit 5581b404f7
2 changed files with 16 additions and 102 deletions
@@ -20,10 +20,6 @@ import android.content.ContentResolver;
import android.content.Context; import android.content.Context;
import android.database.ContentObserver; import android.database.ContentObserver;
import android.os.Handler; import android.os.Handler;
import android.util.Log;
import java.util.EnumSet;
import java.util.Set;
import de.dennisguse.opentracks.content.data.TrackPointsColumns; import de.dennisguse.opentracks.content.data.TrackPointsColumns;
import de.dennisguse.opentracks.content.data.TracksColumns; import de.dennisguse.opentracks.content.data.TracksColumns;
@@ -42,7 +38,6 @@ class DataSourceManager {
private final ContentResolver contentResolver; private final ContentResolver contentResolver;
// Registered listeners // Registered listeners
private final Set<TrackDataType> registeredListeners = EnumSet.noneOf(TrackDataType.class);
private final ContentObserver tracksTableObserver; private final ContentObserver tracksTableObserver;
private final ContentObserver waypointsTableObserver; private final ContentObserver waypointsTableObserver;
private final ContentObserver trackPointsTableObserver; private final ContentObserver trackPointsTableObserver;
@@ -72,99 +67,21 @@ class DataSourceManager {
} }
/** /**
* Updates listeners with data source. * Registers for content changes.
*
* @param listeners the listeners
*/ */
void updateListeners(EnumSet<TrackDataType> listeners) { public void start() {
EnumSet<TrackDataType> neededListeners = EnumSet.copyOf(listeners); contentResolver.registerContentObserver(TracksColumns.CONTENT_URI, false, tracksTableObserver);
contentResolver.registerContentObserver(WaypointsColumns.CONTENT_URI, false, waypointsTableObserver);
// Map SAMPLED_OUT_POINT_UPDATES to POINT_UPDATES since they correspond to the same internal listener contentResolver.registerContentObserver(TrackPointsColumns.CONTENT_URI_BY_ID, false, trackPointsTableObserver);
if (neededListeners.contains(TrackDataType.SAMPLED_OUT_TRACK_POINTS_TABLE)) {
neededListeners.remove(TrackDataType.SAMPLED_OUT_TRACK_POINTS_TABLE);
neededListeners.add(TrackDataType.SAMPLED_IN_TRACK_POINTS_TABLE);
}
Log.d(TAG, "Updating listeners " + neededListeners);
// Unnecessary = registered - needed
Set<TrackDataType> unnecessaryListeners = EnumSet.copyOf(registeredListeners);
unnecessaryListeners.removeAll(neededListeners);
// Missing = needed - registered
Set<TrackDataType> missingListeners = EnumSet.copyOf(neededListeners);
missingListeners.removeAll(registeredListeners);
// Remove unnecessary listeners
for (TrackDataType trackDataType : unnecessaryListeners) {
unregisterListener(trackDataType);
}
// Add missing listeners
for (TrackDataType trackDataType : missingListeners) {
registerListener(trackDataType);
}
// Update registered listeners
registeredListeners.clear();
registeredListeners.addAll(neededListeners);
} }
/** /**
* Registers a listener with data source. * Unregisters from content changes.
*
* @param trackDataType the listener data type
*/ */
private void registerListener(TrackDataType trackDataType) { public void stop() {
switch (trackDataType) { contentResolver.unregisterContentObserver(tracksTableObserver);
case TRACKS_TABLE: contentResolver.unregisterContentObserver(waypointsTableObserver);
contentResolver.registerContentObserver(TracksColumns.CONTENT_URI, false, tracksTableObserver); contentResolver.unregisterContentObserver(trackPointsTableObserver);
break;
case WAYPOINTS_TABLE:
contentResolver.registerContentObserver(WaypointsColumns.CONTENT_URI, false, waypointsTableObserver);
break;
case SAMPLED_IN_TRACK_POINTS_TABLE:
contentResolver.registerContentObserver(TrackPointsColumns.CONTENT_URI_BY_ID, false, trackPointsTableObserver);
break;
case SAMPLED_OUT_TRACK_POINTS_TABLE:
// Do nothing. SAMPLED_OUT_POINT_UPDATES is mapped to POINT_UPDATES.
break;
default:
break;
}
}
/**
* Unregisters a listener with data source.
*
* @param trackDataType listener data type
*/
private void unregisterListener(TrackDataType trackDataType) {
switch (trackDataType) {
case TRACKS_TABLE:
contentResolver.unregisterContentObserver(tracksTableObserver);
break;
case WAYPOINTS_TABLE:
contentResolver.unregisterContentObserver(waypointsTableObserver);
break;
case SAMPLED_IN_TRACK_POINTS_TABLE:
contentResolver.unregisterContentObserver(trackPointsTableObserver);
break;
case SAMPLED_OUT_TRACK_POINTS_TABLE:
// Do nothing. SAMPLED_OUT_POINT_UPDATES is mapped to POINT_UPDATES.
break;
default:
break;
}
}
/**
* Unregisters all listeners with data source.
*/
void unregisterAllListeners() {
for (TrackDataType trackDataType : TrackDataType.values()) {
unregisterListener(trackDataType);
}
} }
/** /**
@@ -172,7 +89,7 @@ class DataSourceManager {
* *
* @author Jimmy Shih * @author Jimmy Shih
*/ */
public interface DataSourceListener { interface DataSourceListener {
/** /**
* Notifies when the tracks table is updated. * Notifies when the tracks table is updated.
@@ -39,7 +39,7 @@ import de.dennisguse.opentracks.util.LocationUtils;
import de.dennisguse.opentracks.util.PreferencesUtils; import de.dennisguse.opentracks.util.PreferencesUtils;
/** /**
* Track data hub. Receives data from {@link de.dennisguse.opentracks.content.DataSourceManager.DataSource} and distributes it to {@link TrackDataListener} after some processing. * Track data hub. Receives data from {@link de.dennisguse.opentracks.content.DataSourceManager} and distributes it to {@link TrackDataListener} after some processing.
* *
* @author Rodrigo Damazio * @author Rodrigo Damazio
*/ */
@@ -100,7 +100,7 @@ public class TrackDataHub implements DataSourceManager.DataSourceListener, Share
return; return;
} }
started = true; started = true;
handlerThread = new HandlerThread("TrackDataHubHandlerThread"); handlerThread = new HandlerThread(TAG);
handlerThread.start(); handlerThread.start();
handler = new Handler(handlerThread.getLooper()); handler = new Handler(handlerThread.getLooper());
dataSourceManager = new DataSourceManager(context, this); dataSourceManager = new DataSourceManager(context, this);
@@ -111,7 +111,7 @@ public class TrackDataHub implements DataSourceManager.DataSourceListener, Share
@Override @Override
public void run() { public void run() {
if (dataSourceManager != null) { if (dataSourceManager != null) {
dataSourceManager.updateListeners(trackDataManager.getRegisteredTrackDataTypes()); dataSourceManager.start();
loadDataForAll(); loadDataForAll();
} }
} }
@@ -128,7 +128,7 @@ public class TrackDataHub implements DataSourceManager.DataSourceListener, Share
started = false; started = false;
dataSourceManager.unregisterAllListeners(); dataSourceManager.stop();
if (handlerThread != null) { if (handlerThread != null) {
handlerThread.getLooper().quit(); handlerThread.getLooper().quit();
handlerThread = null; handlerThread = null;
@@ -163,7 +163,6 @@ public class TrackDataHub implements DataSourceManager.DataSourceListener, Share
public void run() { public void run() {
trackDataManager.registerListener(trackDataListener, trackDataTypes); trackDataManager.registerListener(trackDataListener, trackDataTypes);
if (dataSourceManager != null) { if (dataSourceManager != null) {
dataSourceManager.updateListeners(trackDataManager.getRegisteredTrackDataTypes());
loadDataForListener(trackDataListener); loadDataForListener(trackDataListener);
} }
} }
@@ -180,9 +179,6 @@ public class TrackDataHub implements DataSourceManager.DataSourceListener, Share
@Override @Override
public void run() { public void run() {
trackDataManager.unregisterListener(trackDataListener); trackDataManager.unregisterListener(trackDataListener);
if (dataSourceManager != null) {
dataSourceManager.updateListeners(trackDataManager.getRegisteredTrackDataTypes());
}
} }
}); });
} }
@@ -454,6 +450,7 @@ public class TrackDataHub implements DataSourceManager.DataSourceListener, Share
* *
* @param runnable the runnable * @param runnable the runnable
*/ */
@Deprecated //TODO: Why actually catch this problem: I guess it would be better to fail hard.
@VisibleForTesting @VisibleForTesting
private void runInHandlerThread(Runnable runnable) { private void runInHandlerThread(Runnable runnable) {
if (handler == null) { if (handler == null) {