forked from upstream-mirrors/OpenTracks
Forward multiple tracks to dashboard
This commit is contained in:
committed by
Dennis Guse
parent
db3eef0104
commit
ad990e8cd7
+3
-3
@@ -14,15 +14,15 @@ For the time being, the OpenTracks Data API can be used to implement mainly cust
|
|||||||
|
|
||||||
## Implementation
|
## Implementation
|
||||||
OpenTracks by default does not expose any data to 3rd-party applications.
|
OpenTracks by default does not expose any data to 3rd-party applications.
|
||||||
On the request of the user (i.e., pressing a button), an Intent is created that exposes the `Track` data (it's summary) as well as the `TrackPoint`s.
|
On the request of the user (i.e., pressing a button), an Intent is created that exposes the `Track` data (it's summary) as well as the `TrackPoint`s of one or more selected tracks.
|
||||||
For each, one URI is provided.
|
For each, one URI is provided.
|
||||||
These URIs notify observers if on content changes (e.g., a new `TrackPoint` was added).
|
These URIs notify observers if on content changes (e.g., a new `TrackPoint` was added).
|
||||||
|
|
||||||
Limitations:
|
Limitations:
|
||||||
* only tracks selected by the user is exposed,
|
* only tracks selected by the user are exposed,
|
||||||
* `Waypoints` are not exposed,
|
* `Waypoints` are not exposed,
|
||||||
* access is only granted temporarily and automatically revoked (see `FLAG_GRANT_READ_URI_PERMISSION`),
|
* access is only granted temporarily and automatically revoked (see `FLAG_GRANT_READ_URI_PERMISSION`),
|
||||||
* no write access is impossible, and
|
* no write access is possible, and
|
||||||
* neither track recordings can be started, paused, or stopped.
|
* neither track recordings can be started, paused, or stopped.
|
||||||
|
|
||||||
All required information can be found in `IntentDashboardUtils.java`.
|
All required information can be found in `IntentDashboardUtils.java`.
|
||||||
|
|||||||
+8
@@ -766,4 +766,12 @@ public class CustomContentProviderUtilsTest {
|
|||||||
contentProviderUtils.insertTrack(track);
|
contentProviderUtils.insertTrack(track);
|
||||||
contentProviderUtils.bulkInsertTrackPoint(track.getLocations().toArray(new Location[0]), track.getLocations().size(), track.getId());
|
contentProviderUtils.bulkInsertTrackPoint(track.getLocations().toArray(new Location[0]), track.getLocations().size(), track.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testFormatIdListForUri() {
|
||||||
|
Assert.assertEquals("", ContentProviderUtils.formatIdListForUri(new long[]{}));
|
||||||
|
Assert.assertEquals("12", ContentProviderUtils.formatIdListForUri(new long[]{12}));
|
||||||
|
Assert.assertEquals("42,43,44", ContentProviderUtils.formatIdListForUri(new long[]{42, 43, 44}));
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -22,6 +22,7 @@ import android.content.Context;
|
|||||||
import android.database.Cursor;
|
import android.database.Cursor;
|
||||||
import android.location.Location;
|
import android.location.Location;
|
||||||
import android.net.Uri;
|
import android.net.Uri;
|
||||||
|
import android.text.TextUtils;
|
||||||
|
|
||||||
import androidx.annotation.VisibleForTesting;
|
import androidx.annotation.VisibleForTesting;
|
||||||
|
|
||||||
@@ -68,6 +69,7 @@ public class ContentProviderUtils {
|
|||||||
* Maximum number of waypoints that will be loaded at one time.
|
* Maximum number of waypoints that will be loaded at one time.
|
||||||
*/
|
*/
|
||||||
public static final int MAX_LOADED_WAYPOINTS_POINTS = 10000;
|
public static final int MAX_LOADED_WAYPOINTS_POINTS = 10000;
|
||||||
|
public static final String ID_SEPARATOR = ",";
|
||||||
|
|
||||||
private final IContentResolver contentResolver;
|
private final IContentResolver contentResolver;
|
||||||
private int defaultCursorBatchSize = 2000;
|
private int defaultCursorBatchSize = 2000;
|
||||||
@@ -942,4 +944,26 @@ public class ContentProviderUtils {
|
|||||||
void setDefaultCursorBatchSize(int defaultCursorBatchSize) {
|
void setDefaultCursorBatchSize(int defaultCursorBatchSize) {
|
||||||
this.defaultCursorBatchSize = defaultCursorBatchSize;
|
this.defaultCursorBatchSize = defaultCursorBatchSize;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Formats an array of IDs as comma separated string value
|
||||||
|
*
|
||||||
|
* @param ids array with IDs
|
||||||
|
* @return comma separated list of ids
|
||||||
|
*/
|
||||||
|
public static String formatIdListForUri(long[] ids) {
|
||||||
|
StringBuilder idsPathSegment = new StringBuilder();
|
||||||
|
for (long id : ids) {
|
||||||
|
if (idsPathSegment.length() > 0) {
|
||||||
|
idsPathSegment.append(ID_SEPARATOR);
|
||||||
|
}
|
||||||
|
idsPathSegment.append(id);
|
||||||
|
}
|
||||||
|
return idsPathSegment.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static String[] parseTrackIdsFromUri(Uri url) {
|
||||||
|
return TextUtils.split(url.getLastPathSegment(), ID_SEPARATOR);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -53,6 +53,8 @@ public abstract class CustomContentProvider extends ContentProvider {
|
|||||||
|
|
||||||
private static final String TAG = CustomContentProvider.class.getSimpleName();
|
private static final String TAG = CustomContentProvider.class.getSimpleName();
|
||||||
|
|
||||||
|
private static final String SQL_LIST_DELIMITER = ",";
|
||||||
|
|
||||||
private final UriMatcher uriMatcher;
|
private final UriMatcher uriMatcher;
|
||||||
|
|
||||||
private SQLiteDatabase db;
|
private SQLiteDatabase db;
|
||||||
@@ -61,10 +63,10 @@ public abstract class CustomContentProvider extends ContentProvider {
|
|||||||
uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
|
uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TrackPointsColumns.CONTENT_URI_BY_ID.getPath(), UrlType.TRACKPOINTS.ordinal());
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TrackPointsColumns.CONTENT_URI_BY_ID.getPath(), UrlType.TRACKPOINTS.ordinal());
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TrackPointsColumns.CONTENT_URI_BY_ID.getPath() + "/#", UrlType.TRACKPOINTS_BY_ID.ordinal());
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TrackPointsColumns.CONTENT_URI_BY_ID.getPath() + "/#", UrlType.TRACKPOINTS_BY_ID.ordinal());
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TrackPointsColumns.CONTENT_URI_BY_TRACKID.getPath() + "/#", UrlType.TRACKPOINTS_BY_TRACKID.ordinal());
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TrackPointsColumns.CONTENT_URI_BY_TRACKID.getPath() + "/*", UrlType.TRACKPOINTS_BY_TRACKID.ordinal());
|
||||||
|
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.CONTENT_URI.getPath(), UrlType.TRACKS.ordinal());
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.CONTENT_URI.getPath(), UrlType.TRACKS.ordinal());
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.CONTENT_URI.getPath() + "/#", UrlType.TRACKS_BY_ID.ordinal());
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.CONTENT_URI.getPath() + "/*", UrlType.TRACKS_BY_ID.ordinal());
|
||||||
|
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, WaypointsColumns.CONTENT_URI.getPath(), UrlType.WAYPOINTS.ordinal());
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, WaypointsColumns.CONTENT_URI.getPath(), UrlType.WAYPOINTS.ordinal());
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, WaypointsColumns.CONTENT_URI.getPath() + "/#", UrlType.WAYPOINTS_BY_ID.ordinal());
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, WaypointsColumns.CONTENT_URI.getPath() + "/#", UrlType.WAYPOINTS_BY_ID.ordinal());
|
||||||
@@ -202,12 +204,11 @@ public abstract class CustomContentProvider extends ContentProvider {
|
|||||||
break;
|
break;
|
||||||
case TRACKPOINTS_BY_ID:
|
case TRACKPOINTS_BY_ID:
|
||||||
queryBuilder.setTables(TrackPointsColumns.TABLE_NAME);
|
queryBuilder.setTables(TrackPointsColumns.TABLE_NAME);
|
||||||
|
|
||||||
queryBuilder.appendWhere(TrackPointsColumns._ID + "=" + ContentUris.parseId(url));
|
queryBuilder.appendWhere(TrackPointsColumns._ID + "=" + ContentUris.parseId(url));
|
||||||
break;
|
break;
|
||||||
case TRACKPOINTS_BY_TRACKID:
|
case TRACKPOINTS_BY_TRACKID:
|
||||||
queryBuilder.setTables(TrackPointsColumns.TABLE_NAME);
|
queryBuilder.setTables(TrackPointsColumns.TABLE_NAME);
|
||||||
queryBuilder.appendWhere(TrackPointsColumns.TRACKID + "=" + ContentUris.parseId(url));
|
queryBuilder.appendWhere(TrackPointsColumns.TRACKID + " IN (" + TextUtils.join(SQL_LIST_DELIMITER, ContentProviderUtils.parseTrackIdsFromUri(url)) + ")");
|
||||||
break;
|
break;
|
||||||
case TRACKS:
|
case TRACKS:
|
||||||
queryBuilder.setTables(TracksColumns.TABLE_NAME);
|
queryBuilder.setTables(TracksColumns.TABLE_NAME);
|
||||||
@@ -215,7 +216,7 @@ public abstract class CustomContentProvider extends ContentProvider {
|
|||||||
break;
|
break;
|
||||||
case TRACKS_BY_ID:
|
case TRACKS_BY_ID:
|
||||||
queryBuilder.setTables(TracksColumns.TABLE_NAME);
|
queryBuilder.setTables(TracksColumns.TABLE_NAME);
|
||||||
queryBuilder.appendWhere(TracksColumns._ID + "=" + ContentUris.parseId(url));
|
queryBuilder.appendWhere(TracksColumns._ID + " IN (" + TextUtils.join(SQL_LIST_DELIMITER, ContentProviderUtils.parseTrackIdsFromUri(url)) + ")");
|
||||||
break;
|
break;
|
||||||
case WAYPOINTS:
|
case WAYPOINTS:
|
||||||
queryBuilder.setTables(WaypointsColumns.TABLE_NAME);
|
queryBuilder.setTables(WaypointsColumns.TABLE_NAME);
|
||||||
@@ -417,4 +418,4 @@ public abstract class CustomContentProvider extends ContentProvider {
|
|||||||
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
|
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,7 +1,6 @@
|
|||||||
package de.dennisguse.opentracks.util;
|
package de.dennisguse.opentracks.util;
|
||||||
|
|
||||||
import android.content.ClipData;
|
import android.content.ClipData;
|
||||||
import android.content.ContentUris;
|
|
||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.net.Uri;
|
import android.net.Uri;
|
||||||
@@ -10,6 +9,7 @@ import java.util.ArrayList;
|
|||||||
|
|
||||||
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;
|
||||||
|
import de.dennisguse.opentracks.content.provider.ContentProviderUtils;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create an {@link Intent} to request showing a Dashboard.
|
* Create an {@link Intent} to request showing a Dashboard.
|
||||||
@@ -24,11 +24,12 @@ public class IntentDashboardUtils {
|
|||||||
private IntentDashboardUtils() {
|
private IntentDashboardUtils() {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static boolean startDashboard(Context context, long trackId) {
|
public static boolean startDashboard(Context context, long[] trackIds) {
|
||||||
ArrayList<Uri> uris = new ArrayList<>();
|
ArrayList<Uri> uris = new ArrayList<>();
|
||||||
|
String trackIdList = ContentProviderUtils.formatIdListForUri(trackIds);
|
||||||
|
|
||||||
uris.add(0, ContentUris.withAppendedId(TracksColumns.CONTENT_URI, trackId));
|
uris.add(0, Uri.withAppendedPath(TracksColumns.CONTENT_URI, trackIdList));
|
||||||
uris.add(1, ContentUris.withAppendedId(TrackPointsColumns.CONTENT_URI_BY_TRACKID, trackId));
|
uris.add(1, Uri.withAppendedPath(TrackPointsColumns.CONTENT_URI_BY_TRACKID, trackIdList));
|
||||||
|
|
||||||
Intent intent = new Intent(ACTION_DASHBOARD);
|
Intent intent = new Intent(ACTION_DASHBOARD);
|
||||||
intent.putParcelableArrayListExtra(ACTION_DASHBOARD_PAYLOAD, uris);
|
intent.putParcelableArrayListExtra(ACTION_DASHBOARD_PAYLOAD, uris);
|
||||||
@@ -47,4 +48,5 @@ public class IntentDashboardUtils {
|
|||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -140,7 +140,7 @@ public class IntentUtils {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (IntentDashboardUtils.startDashboard(context, trackIds[0])) {
|
if (IntentDashboardUtils.startDashboard(context, trackIds)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user