forked from upstream-mirrors/OpenTracks
Share multiple tracks from TrackListActivity.
This commit is contained in:
@@ -298,7 +298,7 @@ public class TrackDetailActivity extends AbstractListActivity implements ChooseA
|
|||||||
|
|
||||||
shareMenuItem = menu.findItem(R.id.track_detail_share);
|
shareMenuItem = menu.findItem(R.id.track_detail_share);
|
||||||
ShareActionProvider shareActionProvider = (ShareActionProvider) shareMenuItem.getActionProvider();
|
ShareActionProvider shareActionProvider = (ShareActionProvider) shareMenuItem.getActionProvider();
|
||||||
shareActionProvider.setShareIntent(IntentUtils.newShareFileIntent(this, trackId));
|
shareActionProvider.setShareIntent(IntentUtils.newShareFileIntent(this, new long[]{trackId}));
|
||||||
|
|
||||||
voiceFrequencyMenuItem = menu.findItem(R.id.track_detail_voice_frequency);
|
voiceFrequencyMenuItem = menu.findItem(R.id.track_detail_voice_frequency);
|
||||||
splitFrequencyMenuItem = menu.findItem(R.id.track_detail_split_frequency);
|
splitFrequencyMenuItem = menu.findItem(R.id.track_detail_split_frequency);
|
||||||
|
|||||||
@@ -110,17 +110,12 @@ public class TrackListActivity extends AbstractListActivity implements ConfirmDe
|
|||||||
private final ContextualActionModeCallback contextualActionModeCallback = new ContextualActionModeCallback() {
|
private final ContextualActionModeCallback contextualActionModeCallback = new ContextualActionModeCallback() {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onPrepare(Menu menu, int[] positions, long[] ids, boolean showSelectAll) {
|
public void onPrepare(Menu menu, int[] positions, long[] trackIds, boolean showSelectAll) {
|
||||||
boolean isRecording = recordingTrackId != PreferencesUtils.RECORDING_TRACK_ID_DEFAULT;
|
boolean isSingleSelection = trackIds.length == 1;
|
||||||
boolean isSingleSelection = ids.length == 1;
|
|
||||||
|
|
||||||
menu.findItem(R.id.list_context_menu_share).setVisible(!isRecording && isSingleSelection);
|
MenuItem shareMenuItem = menu.findItem(R.id.list_context_menu_share);
|
||||||
Intent shareIntent = null;
|
ShareActionProvider shareActionProvider = (ShareActionProvider) shareMenuItem.getActionProvider();
|
||||||
if (isSingleSelection) {
|
shareActionProvider.setShareIntent(trackIds.length == 0 ? null : IntentUtils.newShareFileIntent(TrackListActivity.this, trackIds));
|
||||||
shareIntent = IntentUtils.newShareFileIntent(TrackListActivity.this, ids[0]);
|
|
||||||
}
|
|
||||||
ShareActionProvider shareActionProvider = (ShareActionProvider) menu.findItem(R.id.list_context_menu_share).getActionProvider();
|
|
||||||
shareActionProvider.setShareIntent(shareIntent);
|
|
||||||
|
|
||||||
menu.findItem(R.id.list_context_menu_edit).setVisible(isSingleSelection);
|
menu.findItem(R.id.list_context_menu_edit).setVisible(isSingleSelection);
|
||||||
menu.findItem(R.id.list_context_menu_select_all).setVisible(showSelectAll);
|
menu.findItem(R.id.list_context_menu_select_all).setVisible(showSelectAll);
|
||||||
|
|||||||
@@ -11,7 +11,6 @@ import android.os.ParcelFileDescriptor;
|
|||||||
import android.provider.OpenableColumns;
|
import android.provider.OpenableColumns;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
import android.util.Pair;
|
import android.util.Pair;
|
||||||
import android.widget.Toast;
|
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
import androidx.annotation.NonNull;
|
||||||
import androidx.annotation.Nullable;
|
import androidx.annotation.Nullable;
|
||||||
@@ -45,28 +44,50 @@ public class ShareContentProvider extends CustomContentProvider implements ICont
|
|||||||
public static final String TAG = ShareContentProvider.class.getCanonicalName();
|
public static final String TAG = ShareContentProvider.class.getCanonicalName();
|
||||||
|
|
||||||
private static final int URI_KML = 1;
|
private static final int URI_KML = 1;
|
||||||
|
private static final int URI_KMZ = 2;
|
||||||
|
private static final int URI_GPX = 3;
|
||||||
|
|
||||||
private static final UriMatcher uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
|
private static final UriMatcher uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
|
||||||
|
private static final String TRACKID_DELIMITER = "_";
|
||||||
|
|
||||||
static {
|
static {
|
||||||
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.TABLE_NAME + "/kml/*", URI_KML);
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.TABLE_NAME + "/kml/*", URI_KML);
|
||||||
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.TABLE_NAME + "/kmz/*", URI_KMZ);
|
||||||
|
uriMatcher.addURI(ContentProviderUtils.AUTHORITY_PACKAGE, TracksColumns.TABLE_NAME + "/gpx/*", URI_GPX);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Pair<Uri, String> createURI(long[] trackIds) {
|
public static Pair<Uri, String> createURI(long[] trackIds, @NonNull TrackFileFormat trackFileFormat) {
|
||||||
if (trackIds.length == 0) {
|
if (trackIds.length == 0) {
|
||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
}
|
}
|
||||||
|
|
||||||
StringBuilder builder = new StringBuilder();
|
StringBuilder builder = new StringBuilder();
|
||||||
for (long trackId : trackIds) {
|
for (long trackId : trackIds) {
|
||||||
builder.append(trackId).append(",");
|
builder.append(trackId).append(TRACKID_DELIMITER);
|
||||||
}
|
}
|
||||||
builder.deleteCharAt(builder.lastIndexOf(","));
|
builder.deleteCharAt(builder.lastIndexOf(TRACKID_DELIMITER));
|
||||||
|
|
||||||
Uri uri = Uri.parse(ContentProviderUtils.CONTENT_BASE_URI + "/" + TracksColumns.TABLE_NAME + "/kml/" + builder + ".kml");
|
Uri uri = Uri.parse(ContentProviderUtils.CONTENT_BASE_URI + "/" + TracksColumns.TABLE_NAME + "/" + trackFileFormat.getExtension() + "/" + builder + "." + trackFileFormat.getExtension());
|
||||||
String mime = getTypeMime(uri);
|
String mime = getTypeMime(uri);
|
||||||
return new Pair<>(uri, mime);
|
return new Pair<>(uri, mime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static long[] parseURI(Uri uri) {
|
||||||
|
String lastPathSegment = uri.getLastPathSegment();
|
||||||
|
if (lastPathSegment == null) {
|
||||||
|
return new long[]{};
|
||||||
|
}
|
||||||
|
|
||||||
|
String fileExtension = "." + getTrackFileFormat(uri).getExtension();
|
||||||
|
String[] lastPathSegmentSplit = lastPathSegment.replace(fileExtension, "").split(TRACKID_DELIMITER);
|
||||||
|
|
||||||
|
long[] trackIds = new long[lastPathSegmentSplit.length];
|
||||||
|
for (int i = 0; i < trackIds.length; i++) {
|
||||||
|
trackIds[i] = Long.valueOf(lastPathSegmentSplit[i]);
|
||||||
|
}
|
||||||
|
return trackIds;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Do not allow to be exported via AndroidManifest.
|
* Do not allow to be exported via AndroidManifest.
|
||||||
* Check that caller has permissions to access {@link CustomContentProvider}.
|
* Check that caller has permissions to access {@link CustomContentProvider}.
|
||||||
@@ -85,20 +106,6 @@ public class ShareContentProvider extends CustomContentProvider implements ICont
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static long[] parseURI(Uri uri) {
|
|
||||||
String lastPathSegment = uri.getLastPathSegment();
|
|
||||||
if (lastPathSegment == null) {
|
|
||||||
return new long[]{};
|
|
||||||
}
|
|
||||||
|
|
||||||
String[] lastPathSegmentSplit = lastPathSegment.replace(".kml", "").split(",");
|
|
||||||
long[] trackIds = new long[lastPathSegmentSplit.length];
|
|
||||||
for (int i = 0; i < trackIds.length; i++) {
|
|
||||||
trackIds[i] = Long.valueOf(lastPathSegmentSplit[i]);
|
|
||||||
}
|
|
||||||
return trackIds;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Cursor query(@NonNull Uri uri, @Nullable String[] projection, @Nullable String selection, @Nullable String[] selectionArgs, @Nullable String sortOrder) {
|
public Cursor query(@NonNull Uri uri, @Nullable String[] projection, @Nullable String selection, @Nullable String[] selectionArgs, @Nullable String sortOrder) {
|
||||||
if (uriMatcher.match(uri) != URI_KML) {
|
if (uriMatcher.match(uri) != URI_KML) {
|
||||||
@@ -133,12 +140,18 @@ public class ShareContentProvider extends CustomContentProvider implements ICont
|
|||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
public static String getTypeMime(@NonNull Uri uri) {
|
public static String getTypeMime(@NonNull Uri uri) {
|
||||||
switch (uriMatcher.match(uri)) {
|
return getTrackFileFormat(uri).getMimeType();
|
||||||
case URI_KML:
|
}
|
||||||
return TrackFileFormat.KML.getMimeType();
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
private static TrackFileFormat getTrackFileFormat(@NonNull Uri uri) {
|
||||||
|
switch (uriMatcher.match(uri)) {
|
||||||
|
case URI_KMZ:
|
||||||
|
return TrackFileFormat.KMZ;
|
||||||
|
case URI_GPX:
|
||||||
|
return TrackFileFormat.GPX;
|
||||||
|
default: //URI_KML
|
||||||
|
return TrackFileFormat.KML;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
@@ -172,8 +185,7 @@ public class ShareContentProvider extends CustomContentProvider implements ICont
|
|||||||
try (FileOutputStream fileOutputStream = new FileOutputStream(output.getFileDescriptor())) {
|
try (FileOutputStream fileOutputStream = new FileOutputStream(output.getFileDescriptor())) {
|
||||||
fileTrackExporter.writeTrack(fileOutputStream);
|
fileTrackExporter.writeTrack(fileOutputStream);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
Log.w(TAG, "Oops closing " + e);
|
Log.w(TAG, "there occurred an error while sharing a file: " + e);
|
||||||
Toast.makeText(getContext(), "", Toast.LENGTH_SHORT).show();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -37,6 +37,7 @@ import de.dennisguse.opentracks.content.DescriptionGeneratorImpl;
|
|||||||
import de.dennisguse.opentracks.content.ShareContentProvider;
|
import de.dennisguse.opentracks.content.ShareContentProvider;
|
||||||
import de.dennisguse.opentracks.content.Track;
|
import de.dennisguse.opentracks.content.Track;
|
||||||
import de.dennisguse.opentracks.content.Waypoint;
|
import de.dennisguse.opentracks.content.Waypoint;
|
||||||
|
import de.dennisguse.opentracks.io.file.TrackFileFormat;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Utilities for creating intents.
|
* Utilities for creating intents.
|
||||||
@@ -71,13 +72,15 @@ public class IntentUtils {
|
|||||||
* Creates an intent to share a track file with an app.
|
* Creates an intent to share a track file with an app.
|
||||||
*
|
*
|
||||||
* @param context the context
|
* @param context the context
|
||||||
* @param trackId the track id
|
* @param trackIds the track ids
|
||||||
*/
|
*/
|
||||||
public static Intent newShareFileIntent(Context context, long trackId) {
|
public static Intent newShareFileIntent(Context context, long[] trackIds) {
|
||||||
Track track = ContentProviderUtils.Factory.get(context).getTrack(trackId);
|
String trackDescription = "";
|
||||||
String trackDescription = track == null ? "" : new DescriptionGeneratorImpl(context).generateTrackDescription(track, false);
|
if (trackIds.length == 1) {
|
||||||
|
Track track = ContentProviderUtils.Factory.get(context).getTrack(trackIds[0]);
|
||||||
Pair<Uri, String> uriAndMime = ShareContentProvider.createURI(new long[]{trackId});
|
trackDescription = track == null ? "" : new DescriptionGeneratorImpl(context).generateTrackDescription(track, false);
|
||||||
|
}
|
||||||
|
Pair<Uri, String> uriAndMime = ShareContentProvider.createURI(trackIds, TrackFileFormat.KML);
|
||||||
|
|
||||||
return new Intent(Intent.ACTION_SEND)
|
return new Intent(Intent.ACTION_SEND)
|
||||||
.putExtra(Intent.EXTRA_STREAM, uriAndMime.first)
|
.putExtra(Intent.EXTRA_STREAM, uriAndMime.first)
|
||||||
@@ -109,7 +112,7 @@ public class IntentUtils {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Pair<Uri, String> uriAndMime = ShareContentProvider.createURI(trackIds);
|
Pair<Uri, String> uriAndMime = ShareContentProvider.createURI(trackIds, TrackFileFormat.KML);
|
||||||
Intent intent = new Intent();
|
Intent intent = new Intent();
|
||||||
intent.setAction(android.content.Intent.ACTION_VIEW);
|
intent.setAction(android.content.Intent.ACTION_VIEW);
|
||||||
intent.setDataAndType(uriAndMime.first, uriAndMime.second);
|
intent.setDataAndType(uriAndMime.first, uriAndMime.second);
|
||||||
|
|||||||
Reference in New Issue
Block a user