forked from upstream-mirrors/OpenTracks
Merge Matthew's changes.
This commit is contained in:
@@ -30,12 +30,13 @@ import com.google.android.apps.mytracks.util.StringUtils;
|
||||
import com.google.android.apps.mytracks.util.UnitConversions;
|
||||
import com.google.android.maps.mytracks.R;
|
||||
import com.google.api.client.googleapis.GoogleHeaders;
|
||||
import com.google.api.client.googleapis.GoogleTransport;
|
||||
import com.google.api.client.googleapis.MethodOverrideIntercepter;
|
||||
import com.google.api.client.http.GenericUrl;
|
||||
import com.google.api.client.http.HttpRequest;
|
||||
import com.google.api.client.http.HttpResponse;
|
||||
import com.google.api.client.http.HttpTransport;
|
||||
import com.google.api.client.http.InputStreamContent;
|
||||
import com.google.api.client.javanet.NetHttpTransport;
|
||||
import com.google.api.client.util.Strings;
|
||||
|
||||
import android.app.Activity;
|
||||
@@ -82,6 +83,21 @@ public class SendToFusionTables implements Runnable {
|
||||
private static final int MAX_POINTS_PER_UPLOAD = 2048;
|
||||
|
||||
private static final String GDATA_VERSION = "2";
|
||||
|
||||
// This class reports upload status to the user as a completion percentage
|
||||
// using a progress bar. Progress is defined as follows:
|
||||
//
|
||||
// 0% Getting track metadata
|
||||
// 5% Creating Fusion Table (GData to FT server)
|
||||
// 10%-90% Uploading the track data to Fusion Tables
|
||||
// 95% Uploading waypoints
|
||||
// 100% Done
|
||||
private static final int PROGRESS_INITIALIZATION = 0;
|
||||
private static final int PROGRESS_FUSION_TABLE_CREATE = 5;
|
||||
private static final int PROGRESS_UPLOAD_DATA_MIN = 10;
|
||||
private static final int PROGRESS_UPLOAD_DATA_MAX = 90;
|
||||
private static final int PROGRESS_UPLOAD_WAYPOINTS = 95;
|
||||
private static final int PROGRESS_COMPLETE = 100;
|
||||
|
||||
private final Activity context;
|
||||
private final AuthManager auth;
|
||||
@@ -105,6 +121,12 @@ public class SendToFusionTables implements Runnable {
|
||||
private static String MARKER_TYPE_END = "large_red";
|
||||
private static String MARKER_TYPE_WAYPOINT = "large_yellow";
|
||||
|
||||
static {
|
||||
// We manually assign the transport to avoid having HttpTransport try to
|
||||
// load it via reflection (which breaks due to ProGuard).
|
||||
HttpTransport.setLowLevelHttpTransport(new NetHttpTransport());
|
||||
}
|
||||
|
||||
public SendToFusionTables(Activity context, AuthManager auth,
|
||||
long trackId, ProgressIndicator progressIndicator,
|
||||
OnSendCompletedListener onCompletion) {
|
||||
@@ -115,10 +137,14 @@ public class SendToFusionTables implements Runnable {
|
||||
this.onCompletion = onCompletion;
|
||||
this.stringUtils = new StringUtils(context);
|
||||
this.providerUtils = MyTracksProviderUtils.Factory.get(context);
|
||||
transport = GoogleTransport.create();
|
||||
GoogleHeaders headers = (GoogleHeaders) transport.defaultHeaders;
|
||||
|
||||
GoogleHeaders headers = new GoogleHeaders();
|
||||
headers.setApplicationName("Google-MyTracks-" + MyTracksUtils.getMyTracksVersion(context));
|
||||
headers.gdataVersion = GDATA_VERSION;
|
||||
|
||||
transport = new HttpTransport();
|
||||
MethodOverrideIntercepter.setAsFirstFor(transport);
|
||||
transport.defaultHeaders = headers;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -141,7 +167,7 @@ public class SendToFusionTables implements Runnable {
|
||||
int statusMessageId = R.string.error_sending_to_fusiontables;
|
||||
boolean success = true;
|
||||
try {
|
||||
progressIndicator.setProgressValue(1);
|
||||
progressIndicator.setProgressValue(PROGRESS_INITIALIZATION);
|
||||
progressIndicator.setProgressMessage(R.string.progress_message_reading_track);
|
||||
|
||||
// Get the track meta-data
|
||||
@@ -149,25 +175,30 @@ public class SendToFusionTables implements Runnable {
|
||||
String originalDescription = track.getDescription();
|
||||
|
||||
// Create a new table:
|
||||
progressIndicator.setProgressValue(PROGRESS_FUSION_TABLE_CREATE);
|
||||
progressIndicator.setProgressMessage(R.string.progress_message_creating_fusiontable);
|
||||
success = createNewTable(track);
|
||||
|
||||
if (success) {
|
||||
success = makeTableUnlisted(tableId);
|
||||
if (!createNewTable(track) || !makeTableUnlisted(tableId)) {
|
||||
return;
|
||||
}
|
||||
|
||||
progressIndicator.setProgressValue(PROGRESS_UPLOAD_DATA_MIN);
|
||||
progressIndicator.setProgressMessage(R.string.progress_message_sending_fusiontables);
|
||||
|
||||
// Upload all of the segments of the track plus start/end markers
|
||||
if (success) {
|
||||
success = uploadAllTrackPoints(track, originalDescription);
|
||||
if (!uploadAllTrackPoints(track, originalDescription)) {
|
||||
return;
|
||||
}
|
||||
|
||||
progressIndicator.setProgressValue(PROGRESS_UPLOAD_WAYPOINTS);
|
||||
|
||||
// Upload all the waypoints.
|
||||
if (success) {
|
||||
success = uploadWaypoints(track);
|
||||
statusMessageId = R.string.status_new_fusiontable_has_been_created;
|
||||
if (!uploadWaypoints(track)) {
|
||||
return;
|
||||
}
|
||||
|
||||
statusMessageId = R.string.status_new_fusiontable_has_been_created;
|
||||
Log.d(MyTracksConstants.TAG, "SendToFusionTables: Done: " + success);
|
||||
progressIndicator.setProgressValue(100);
|
||||
progressIndicator.setProgressValue(PROGRESS_COMPLETE);
|
||||
} finally {
|
||||
|
||||
final boolean finalSuccess = success;
|
||||
@@ -198,7 +229,7 @@ public class SendToFusionTables implements Runnable {
|
||||
|
||||
private boolean makeTableUnlisted(String tableId) {
|
||||
Log.d(MyTracksConstants.TAG, "Setting visibility to unlisted.");
|
||||
String query = "UPDATE TABLE " + tableId + " SET VISIBILITY = unlisted";
|
||||
String query = "UPDATE TABLE " + tableId + " SET VISIBILITY = UNLISTED";
|
||||
return runUpdate(query);
|
||||
}
|
||||
|
||||
@@ -290,11 +321,10 @@ public class SendToFusionTables implements Runnable {
|
||||
DoubleBuffer elevationBuffer = new DoubleBuffer(MyTracksConstants.ELEVATION_SMOOTHING_FACTOR);
|
||||
|
||||
List<Location> locations = new ArrayList<Location>(MAX_POINTS_PER_UPLOAD);
|
||||
progressIndicator.setProgressMessage(R.string.progress_message_reading_track);
|
||||
Location lastLocation = null;
|
||||
do {
|
||||
if (totalLocationsRead % 100 == 0) {
|
||||
updateProgress();
|
||||
updateTrackDataUploadProgress();
|
||||
}
|
||||
|
||||
Location loc = providerUtils.createLocation(locationsCursor);
|
||||
@@ -406,8 +436,7 @@ public class SendToFusionTables implements Runnable {
|
||||
}
|
||||
|
||||
private boolean prepareAndUploadPoints(Track track, List<Location> locations) {
|
||||
progressIndicator.setProgressMessage(R.string.progress_message_preparing_track);
|
||||
updateProgress();
|
||||
updateTrackDataUploadProgress();
|
||||
|
||||
int numLocations = locations.size();
|
||||
if (numLocations < 2) {
|
||||
@@ -420,7 +449,6 @@ public class SendToFusionTables implements Runnable {
|
||||
ArrayList<Track> splitTracks = prepareLocations(track, locations);
|
||||
|
||||
// Start uploading them
|
||||
progressIndicator.setProgressMessage(R.string.progress_message_sending_fusiontables);
|
||||
for (Track splitTrack : splitTracks) {
|
||||
if (totalSegmentsUploaded > 1) {
|
||||
splitTrack.setName(splitTrack.getName() + " "
|
||||
@@ -444,7 +472,7 @@ public class SendToFusionTables implements Runnable {
|
||||
|
||||
locations.clear();
|
||||
totalLocationsUploaded += numLocations;
|
||||
updateProgress();
|
||||
updateTrackDataUploadProgress();
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -473,7 +501,7 @@ public class SendToFusionTables implements Runnable {
|
||||
boolean startNewTrackSegment = false;
|
||||
for (Location loc : locations) {
|
||||
if (totalLocationsPrepared % 100 == 0) {
|
||||
updateProgress();
|
||||
updateTrackDataUploadProgress();
|
||||
}
|
||||
if (loc.getLatitude() > 90) {
|
||||
startNewTrackSegment = true;
|
||||
@@ -596,17 +624,18 @@ public class SendToFusionTables implements Runnable {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the current upload progress.
|
||||
*/
|
||||
private void updateProgress() {
|
||||
private void updateTrackDataUploadProgress() {
|
||||
// The percent of the total that represents the completed part of this
|
||||
// segment.
|
||||
int totalPercentage =
|
||||
// segment. We calculate it as an absolute percentage, and then scale it
|
||||
// to fit the completion percentage range alloted to track data upload.
|
||||
double totalPercentage =
|
||||
(totalLocationsRead + totalLocationsPrepared + totalLocationsUploaded)
|
||||
/ (totalLocations * 3);
|
||||
totalPercentage = Math.min(99, totalPercentage);
|
||||
progressIndicator.setProgressValue(totalPercentage);
|
||||
|
||||
double scaledPercentage = totalPercentage
|
||||
* (PROGRESS_UPLOAD_DATA_MAX - PROGRESS_UPLOAD_DATA_MIN) + PROGRESS_UPLOAD_DATA_MIN;
|
||||
|
||||
progressIndicator.setProgressValue((int) scaledPercentage);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -33,12 +33,7 @@ public class ApiFeatures {
|
||||
*/
|
||||
public static final int ANDROID_API_LEVEL = Integer.parseInt(
|
||||
Build.VERSION.SDK);
|
||||
|
||||
private static final String PLATFORM_ADAPTER_GINGERBREAD =
|
||||
"com.google.android.apps.mytracks.util.GingerbreadPlatformAdapter";
|
||||
private static final String PLATFORM_ADAPTER_ECLAIR =
|
||||
"com.google.android.apps.mytracks.util.EclairPlatformAdapter";
|
||||
|
||||
|
||||
private static ApiFeatures instance;
|
||||
|
||||
/**
|
||||
@@ -67,30 +62,18 @@ public class ApiFeatures {
|
||||
* Allow subclasses for mocking, but no direct instantiation.
|
||||
*/
|
||||
protected ApiFeatures() {
|
||||
// It is safe to import unsupported classes as long as we only actually
|
||||
// load the class when supported.
|
||||
if (getApiLevel() >= 9) {
|
||||
apiPlatformAdapter = createPlatformAdapter(PLATFORM_ADAPTER_GINGERBREAD);
|
||||
apiPlatformAdapter = new GingerbreadPlatformAdapter();
|
||||
} else if (getApiLevel() >= 5) {
|
||||
apiPlatformAdapter = createPlatformAdapter(PLATFORM_ADAPTER_ECLAIR);
|
||||
apiPlatformAdapter = new EclairPlatformAdapter();
|
||||
} else {
|
||||
// Cupcake adapter is always supported, so it's safe to do static linkage.
|
||||
apiPlatformAdapter = new CupcakePlatformAdapter();
|
||||
}
|
||||
|
||||
|
||||
Log.i(MyTracksConstants.TAG, "Using platform adapter " + apiPlatformAdapter.getClass());
|
||||
}
|
||||
|
||||
private static ApiPlatformAdapter createPlatformAdapter(String className) {
|
||||
try {
|
||||
Class<?> clazz = Class.forName(className);
|
||||
return (ApiPlatformAdapter) clazz.newInstance();
|
||||
} catch (ClassNotFoundException e) {
|
||||
throw new RuntimeException("ApiFeatures: Unable to find " + className, e);
|
||||
} catch (InstantiationException e) {
|
||||
throw new RuntimeException("ApiFeatures: Unable to instantiate " + className, e);
|
||||
} catch (IllegalAccessException e) {
|
||||
throw new RuntimeException("ApiFeatures: Unable to access " + className, e);
|
||||
}
|
||||
}
|
||||
|
||||
public ApiPlatformAdapter getApiPlatformAdapter() {
|
||||
return apiPlatformAdapter;
|
||||
|
||||
Reference in New Issue
Block a user