+
+
+
diff --git a/MyTracks/src/com/google/android/apps/mytracks/AutoCompleteTextPreference.java b/MyTracks/src/com/google/android/apps/mytracks/AutoCompleteTextPreference.java
new file mode 100644
index 000000000..0096b1815
--- /dev/null
+++ b/MyTracks/src/com/google/android/apps/mytracks/AutoCompleteTextPreference.java
@@ -0,0 +1,64 @@
+package com.google.android.apps.mytracks;
+
+import com.google.android.maps.mytracks.R;
+
+import android.content.Context;
+import android.preference.EditTextPreference;
+import android.util.AttributeSet;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewParent;
+import android.widget.ArrayAdapter;
+import android.widget.AutoCompleteTextView;
+
+/**
+ * The {@link AutoCompleteTextPreference} class is a preference that allows for
+ * string input using auto complete . It is a subclass of
+ * {@link EditTextPreference} and shows the {@link AutoCompleteTextView} in a
+ * dialog.
+ *
+ * This preference will store a string into the SharedPreferences.
+ *
+ * @author Rimas Trumpa (with Matt Levan)
+ */
+public class AutoCompleteTextPreference extends EditTextPreference {
+
+ private AutoCompleteTextView mEditText = null;
+
+ public AutoCompleteTextPreference(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ mEditText = new AutoCompleteTextView(context, attrs);
+ mEditText.setThreshold(0);
+
+ // Gets autocomplete values for 'Default Activity' preference
+ if (getKey().equals(context.getString(R.string.default_category_key))) {
+ ArrayAdapter adapter = ArrayAdapter.createFromResource(context,
+ R.array.activity_types, android.R.layout.simple_dropdown_item_1line);
+ mEditText.setAdapter(adapter);
+ }
+ }
+
+ @Override
+ protected void onBindDialogView(View view) {
+ AutoCompleteTextView editText = mEditText;
+ editText.setText(getText());
+
+ ViewParent oldParent = editText.getParent();
+ if (oldParent != view) {
+ if (oldParent != null) {
+ ((ViewGroup) oldParent).removeView(editText);
+ }
+ onAddEditTextToDialogView(view, editText);
+ }
+ }
+
+ @Override
+ protected void onDialogClosed(boolean positiveResult) {
+ if (positiveResult) {
+ String value = mEditText.getText().toString();
+ if (callChangeListener(value)) {
+ setText(value);
+ }
+ }
+ }
+}
diff --git a/MyTracks/src/com/google/android/apps/mytracks/CheckUnits.java b/MyTracks/src/com/google/android/apps/mytracks/CheckUnits.java
index 104242f75..a35f4409d 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/CheckUnits.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/CheckUnits.java
@@ -23,73 +23,63 @@ import android.app.Activity;
import android.app.AlertDialog;
import android.content.Context;
import android.content.DialogInterface;
-import android.content.Intent;
import android.content.SharedPreferences;
-import java.util.Locale;
-
/**
- * Check to see if the units are the default for the locale.
- * This comes down to warning Americans that the default is metric.
+ * Checks with the user if he prefers the metric units or the imperial units.
*
* @author Sandor Dornbush
*/
class CheckUnits {
- private static final String PREFERENCE_UNITS_CHECKED = "checkunits.checked";
- private static final String PREFERENCES_CHECK_UNITS = "checkunits";
+ private static final String CHECK_UNITS_PREFERENCE_FILE = "checkunits";
+ private static final String CHECK_UNITS_PREFERENCE_KEY = "checkunits.checked";
+ private static boolean metric = true;
- static void check(final Context context) {
- final SharedPreferences preferences =
- context.getSharedPreferences(PREFERENCES_CHECK_UNITS, Activity.MODE_PRIVATE);
-
- // Has the user already warned about the default units?
- if (preferences.getBoolean(PREFERENCE_UNITS_CHECKED, false)) {
+ public static void check(final Context context) {
+ final SharedPreferences checkUnitsSharedPreferences = context.getSharedPreferences(
+ CHECK_UNITS_PREFERENCE_FILE, Activity.MODE_PRIVATE);
+ if (checkUnitsSharedPreferences.getBoolean(CHECK_UNITS_PREFERENCE_KEY, false)) {
return;
}
- // Is the user in the US?
- Locale current = Locale.getDefault();
- Locale enUs = new Locale(Locale.ENGLISH.getLanguage(),
- Locale.US.getCountry());
- if (!current.equals(enUs)) {
- return;
- }
-
- final AlertDialog.Builder builder = new AlertDialog.Builder(context);
- builder.setTitle(R.string.check_units_title);
- builder.setCancelable(true);
- builder.setPositiveButton(R.string.yes, new DialogInterface.OnClickListener() {
+ AlertDialog.Builder builder = new AlertDialog.Builder(context);
+ builder.setTitle(context.getString(R.string.preferred_units_title));
+ CharSequence[] items = { context.getString(R.string.preferred_units_metric),
+ context.getString(R.string.preferred_units_imperial) };
+ builder.setSingleChoiceItems(items, 0, new DialogInterface.OnClickListener() {
+ @Override
public void onClick(DialogInterface dialog, int which) {
- recordCheckPerformed(preferences);
+ if (which == 0) {
+ metric = true;
+ } else {
+ metric = false;
+ }
}
});
- builder.setNegativeButton(R.string.no, new DialogInterface.OnClickListener() {
+ builder.setCancelable(true);
+ builder.setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
- changeDefaultUnits(context, preferences);
+ recordCheckPerformed(checkUnitsSharedPreferences);
+ SharedPreferences useMetricPreferences = context.getSharedPreferences(
+ Constants.SETTINGS_NAME, Activity.MODE_PRIVATE);
+ SharedPreferences.Editor editor = useMetricPreferences.edit();
+ String key = context.getString(R.string.metric_units_key);
+ ApiFeatures.getInstance().getApiAdapter().applyPreferenceChanges(
+ editor.putBoolean(key, metric));
}
});
builder.setOnCancelListener(new DialogInterface.OnCancelListener() {
public void onCancel(DialogInterface dialog) {
- recordCheckPerformed(preferences);
+ recordCheckPerformed(checkUnitsSharedPreferences);
}
});
- builder.setMessage(R.string.check_units_message);
builder.show();
}
- private static void changeDefaultUnits(Context context, SharedPreferences preferences) {
- recordCheckPerformed(preferences);
- Intent startIntent = new Intent(context, SettingsActivity.class);
- startIntent.putExtra(context.getString(R.string.open_settings_screen),
- context.getString(R.string.display_settings_screen_key));
- context.startActivity(startIntent);
- }
-
private static void recordCheckPerformed(SharedPreferences preferences) {
ApiFeatures.getInstance().getApiAdapter().applyPreferenceChanges(
- preferences.edit().putBoolean(PREFERENCE_UNITS_CHECKED, true));
+ preferences.edit().putBoolean(CHECK_UNITS_PREFERENCE_KEY, true));
}
- private CheckUnits() {
- }
+ private CheckUnits() {}
}
diff --git a/MyTracks/src/com/google/android/apps/mytracks/ImportAllTracks.java b/MyTracks/src/com/google/android/apps/mytracks/ImportAllTracks.java
index dfea7d5d5..248899c65 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/ImportAllTracks.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/ImportAllTracks.java
@@ -16,6 +16,7 @@
package com.google.android.apps.mytracks;
import com.google.android.apps.mytracks.content.MyTracksProviderUtils;
+import com.google.android.apps.mytracks.content.TracksColumns;
import com.google.android.apps.mytracks.io.file.GpxImporter;
import com.google.android.apps.mytracks.util.FileUtils;
import com.google.android.apps.mytracks.util.SystemUtils;
@@ -24,7 +25,11 @@ import com.google.android.maps.mytracks.R;
import android.app.Activity;
import android.app.AlertDialog;
import android.app.ProgressDialog;
+import android.content.ContentUris;
+import android.content.DialogInterface;
+import android.content.Intent;
import android.content.SharedPreferences;
+import android.net.Uri;
import android.os.PowerManager.WakeLock;
import android.util.Log;
import android.widget.Toast;
@@ -49,22 +54,36 @@ import org.xml.sax.SAXException;
public class ImportAllTracks {
private final Activity activity;
+ private FileUtils fileUtils;
+ private boolean singleTrackSelected;
+ private String gpxPath;
private WakeLock wakeLock;
private ProgressDialog progress;
- private FileUtils fileUtils;
- private String gpxPath;
private int gpxFileCount;
private int importSuccessCount;
-
+ private long importedTrackIds[];
+
public ImportAllTracks(Activity activity) {
- this.activity = activity;
- Log.i(Constants.TAG, "ImportAllTracks: Starting");
- fileUtils = new FileUtils();
- gpxPath = fileUtils.buildExternalDirectoryPath("gpx");
-
- new Thread(runner).start();
+ this(activity, null);
}
+ /**
+ * Constructor to import tracks.
+ *
+ * @param activity the activity
+ * @param path path of the gpx file to import and display. If null, then just
+ * import all the gpx files under MyTracks/gpx and do not display any
+ * track.
+ */
+ public ImportAllTracks(Activity activity, String path) {
+ Log.i(Constants.TAG, "ImportAllTracks: Starting");
+ this.activity = activity;
+ fileUtils = new FileUtils();
+ singleTrackSelected = path != null;
+ gpxPath = path == null ? fileUtils.buildExternalDirectoryPath("gpx") : path;
+ new Thread(runner).start();
+ }
+
private final Runnable runner = new Runnable() {
public void run() {
aquireLocksAndImport();
@@ -81,7 +100,7 @@ public class ImportAllTracks {
if (prefs != null) {
recordingTrackId = prefs.getLong(activity.getString(R.string.recording_track_key), -1);
}
- if (recordingTrackId != -1) {
+ if (recordingTrackId == -1) {
wakeLock = SystemUtils.acquireWakeLock(activity, wakeLock);
}
@@ -107,12 +126,26 @@ public class ImportAllTracks {
Log.i(Constants.TAG, "ImportAllTracks: Done");
AlertDialog.Builder builder = new AlertDialog.Builder(activity);
if (gpxFileCount == 0) {
- builder.setMessage(activity.getString(R.string.import_multi_empty, gpxPath + "/"));
+ builder.setMessage(activity.getString(R.string.import_multi_empty, gpxPath));
} else {
builder.setMessage(activity.getString(R.string.import_multi_done, importSuccessCount, gpxFileCount,
- gpxPath + "/"));
+ gpxPath));
}
- builder.setPositiveButton(R.string.ok, null);
+ builder.setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
+ @Override
+ public void onClick(DialogInterface dialog, int which) {
+ if (singleTrackSelected) {
+ long lastTrackId = importedTrackIds[importedTrackIds.length - 1];
+ Uri trackUri = ContentUris.withAppendedId(TracksColumns.CONTENT_URI, lastTrackId);
+
+ Intent intent = new Intent(Intent.ACTION_VIEW);
+ intent.setDataAndType(trackUri, TracksColumns.CONTENT_ITEMTYPE);
+ intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
+ activity.startActivity(intent);
+ activity.finish();
+ }
+ }
+ });
builder.show();
}
@@ -185,7 +218,7 @@ public class ImportAllTracks {
private boolean importFile(File gpxFile, MyTracksProviderUtils providerUtils) {
Log.i(Constants.TAG, "ImportAllTracks: importing: " + gpxFile.getName());
try {
- GpxImporter.importGPXFile(new FileInputStream(gpxFile), providerUtils);
+ importedTrackIds = GpxImporter.importGPXFile(new FileInputStream(gpxFile), providerUtils);
return true;
} catch (FileNotFoundException e) {
Log.w(Constants.TAG, "GPX file wasn't found/went missing: "
@@ -203,15 +236,22 @@ public class ImportAllTracks {
}
/**
- * Returns a list of the GPX Files found in the GPX directory.
+ * Gets a list of the GPX files. If singleTrackSelected is true, returns a
+ * list containing just the gpxPath file. If singleTrackSelected is false,
+ * returns a list of GPX files under the gpxPath directory.
*/
private List getGpxFiles() {
- List gpxFiles = new LinkedList();
- File[] gpxFileCandidates = new File(gpxPath).listFiles();
- if (gpxFileCandidates != null) {
- for (File file : gpxFileCandidates) {
- if (!file.isDirectory() && file.getName().endsWith(".gpx")) {
- gpxFiles.add(file);
+ List gpxFiles = new LinkedList();
+ File file = new File(gpxPath);
+ if (singleTrackSelected) {
+ gpxFiles.add(file);
+ } else {
+ File[] gpxFileCandidates = file.listFiles();
+ if (gpxFileCandidates != null) {
+ for (File candidate : gpxFileCandidates) {
+ if (!candidate.isDirectory() && candidate.getName().endsWith(".gpx")) {
+ gpxFiles.add(candidate);
+ }
}
}
}
diff --git a/MyTracks/src/com/google/android/apps/mytracks/SettingsActivity.java b/MyTracks/src/com/google/android/apps/mytracks/SettingsActivity.java
index c659a4c87..6bf1a5547 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/SettingsActivity.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/SettingsActivity.java
@@ -54,10 +54,6 @@ import java.util.Set;
/**
* An activity that let's the user see and edit the settings.
*
- * This activity has two entry points, "root" and "display" preference screen.
- * If bundle.getString("open_settings_screen") is set to "display_settings_screen_key", then
- * the "display" preference screen is shown, otherwise, the "root" display preference is shown.
- *
* @author Leif Hendrik Wilden
* @author Rodrigo Damazio
*/
@@ -104,16 +100,6 @@ public class SettingsActivity extends PreferenceActivity {
protected void onCreate(Bundle icicle) {
super.onCreate(icicle);
- initActivityCommons();
-
- // If we only need the display setting screen nothing else needs to load.
- if (processIntent())
- return;
-
- initActivitySpecifics();
- }
-
- private void initActivityCommons() {
// The volume we want to control is the Text-To-Speech volume
ApiFeatures apiFeatures = ApiFeatures.getInstance();
int volumeStream =
@@ -146,9 +132,7 @@ public class SettingsActivity extends PreferenceActivity {
setRecordingIntervalOptions();
setAutoResumeTimeoutOptions();
- }
-
- private void initActivitySpecifics() {
+
// Hook up switching of displayed list entries between metric and imperial
// units
CheckBoxPreference metricUnitsPreference =
@@ -259,23 +243,6 @@ public class SettingsActivity extends PreferenceActivity {
list.setEntries(options);
}
- private boolean processIntent() {
- boolean showDisplaySettings = false;
- Bundle bundle = getIntent().getExtras();
- PreferenceScreen preferenceScreen;
- String intentString = getString(R.string.open_settings_screen);
-
- if (bundle != null) {
- preferenceScreen = (PreferenceScreen) findPreference(bundle.getString(intentString));
- if (preferenceScreen != null) {
- showDisplaySettings = true;
- setPreferenceScreen(preferenceScreen);
- }
- }
-
- return showDisplaySettings;
- }
-
private void customizeSensorOptionsPreferences() {
ListPreference sensorTypePreference =
(ListPreference) findPreference(getString(R.string.sensor_type_key));
@@ -352,10 +319,6 @@ public class SettingsActivity extends PreferenceActivity {
protected void onResume() {
super.onResume();
- // If we only need the display setting screen nothing else needs to load.
- if (processIntent())
- return;
-
configureBluetoothPreferences();
Preference backupNowPreference =
findPreference(getString(R.string.backup_to_sd_key));
diff --git a/MyTracks/src/com/google/android/apps/mytracks/io/SendToDocs.java b/MyTracks/src/com/google/android/apps/mytracks/io/SendToDocs.java
index 472d1db0c..2ba84887f 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/io/SendToDocs.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/io/SendToDocs.java
@@ -22,6 +22,7 @@ import com.google.android.apps.mytracks.content.Track;
import com.google.android.apps.mytracks.io.docs.DocsHelper;
import com.google.android.apps.mytracks.io.gdata.GDataClientFactory;
import com.google.android.apps.mytracks.io.gdata.GDataWrapper;
+import com.google.android.apps.mytracks.io.sendtogoogle.SendType;
import com.google.android.common.gdata.AndroidXmlParserFactory;
import com.google.android.maps.mytracks.R;
import com.google.wireless.gdata.client.GDataClient;
@@ -115,13 +116,11 @@ public class SendToDocs {
Log.d(Constants.TAG, "SendToDocs: Uploading to spreadsheet");
success = uploadToDocs(track);
if (success) {
- if (createdNewSpreadSheet) {
- statusMessage = activity.getString(
- R.string.sending_to_docs_success_new_doc);
- } else {
- statusMessage = activity.getString(
- R.string.sending_to_docs_success_existing_doc);
- }
+ String format = createdNewSpreadSheet
+ ? activity.getString(R.string.send_google_docs_new_doc_success)
+ : activity.getString(R.string.send_google_docs_existing_doc_success);
+ String url = activity.getString(SendType.DOCS.getServiceUrl());
+ statusMessage = String.format(format, url);
} else {
statusMessage = activity.getString(R.string.error_sending_to_docs);
}
diff --git a/MyTracks/src/com/google/android/apps/mytracks/io/SendToFusionTables.java b/MyTracks/src/com/google/android/apps/mytracks/io/SendToFusionTables.java
index 8b6e83be1..571ee6dfd 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/io/SendToFusionTables.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/io/SendToFusionTables.java
@@ -24,6 +24,7 @@ import com.google.android.apps.mytracks.content.Track;
import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.io.gdata.GDataWrapper;
import com.google.android.apps.mytracks.io.gdata.GDataWrapper.QueryFunction;
+import com.google.android.apps.mytracks.io.sendtogoogle.SendType;
import com.google.android.apps.mytracks.stats.DoubleBuffer;
import com.google.android.apps.mytracks.stats.TripStatistics;
import com.google.android.apps.mytracks.util.ApiFeatures;
@@ -71,7 +72,7 @@ public class SendToFusionTables implements Runnable {
* Listener invoked when sending to fusion tables completes.
*/
public interface OnSendCompletedListener {
- void onSendCompleted(String tableId, boolean success, int statusMessage);
+ void onSendCompleted(String tableId, boolean success, String statusMessage);
}
/** The GData service id for Fusion Tables. */
@@ -168,7 +169,7 @@ public class SendToFusionTables implements Runnable {
}
private void doUpload() {
- int statusMessageId = R.string.error_sending_to_fusion_tables;
+ String statusMessage = context.getString(R.string.error_sending_to_fusion_tables);
boolean success = true;
try {
progressIndicator.setProgressValue(PROGRESS_INITIALIZATION);
@@ -205,17 +206,18 @@ public class SendToFusionTables implements Runnable {
return;
}
- statusMessageId = R.string.sending_to_fusion_tables_success;
+ String format = context.getString(R.string.send_google_fusion_tables_success);
+ String url = context.getString(SendType.FUSION_TABLES.getServiceUrl());
+ statusMessage = String.format(format, url);
Log.d(Constants.TAG, "SendToFusionTables: Done: " + success);
progressIndicator.setProgressValue(PROGRESS_COMPLETE);
} finally {
final boolean finalSuccess = success;
- final int finalStatusMessageId = statusMessageId;
+ final String finalStatusMessage = statusMessage;
context.runOnUiThread(new Runnable() {
public void run() {
if (onCompletion != null) {
- onCompletion.onSendCompleted(
- tableId, finalSuccess, finalStatusMessageId);
+ onCompletion.onSendCompleted(tableId, finalSuccess, finalStatusMessage);
}
}
});
diff --git a/MyTracks/src/com/google/android/apps/mytracks/io/SendToMyMaps.java b/MyTracks/src/com/google/android/apps/mytracks/io/SendToMyMaps.java
index 84a6cb0de..9c38d9b8a 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/io/SendToMyMaps.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/io/SendToMyMaps.java
@@ -23,6 +23,7 @@ import com.google.android.apps.mytracks.content.MyTracksProviderUtils;
import com.google.android.apps.mytracks.content.Track;
import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.io.mymaps.MapsFacade;
+import com.google.android.apps.mytracks.io.sendtogoogle.SendType;
import com.google.android.apps.mytracks.stats.DoubleBuffer;
import com.google.android.apps.mytracks.stats.TripStatistics;
import com.google.android.apps.mytracks.util.LocationUtils;
@@ -75,7 +76,7 @@ public class SendToMyMaps implements Runnable {
private int totalSegmentsUploaded;
public interface OnSendCompletedListener {
- void onSendCompleted(String mapId, boolean success, int statusMessage);
+ void onSendCompleted(String mapId, boolean success, String statusMessage);
}
public SendToMyMaps(Activity context, String mapId, AuthManager auth,
@@ -98,7 +99,7 @@ public class SendToMyMaps implements Runnable {
}
private void doUpload() {
- int statusMessageId = R.string.error_sending_to_my_maps;
+ String statusMessage = context.getString(R.string.error_sending_to_my_maps);
boolean success = true;
try {
progressIndicator.setProgressMessage(
@@ -173,9 +174,11 @@ public class SendToMyMaps implements Runnable {
}
if (success) {
- statusMessageId = isNewMap
- ? R.string.sending_to_my_maps_success_new_map
- : R.string.sending_to_my_maps_success_existing_map;
+ String format = isNewMap
+ ? context.getString(R.string.send_google_my_maps_new_map_success)
+ : context.getString(R.string.send_google_my_maps_existing_map_success);
+ String url = context.getString(SendType.MYMAPS.getServiceUrl());
+ statusMessage = String.format(format, url);
}
Log.d(TAG, "SendToMyMaps: Done: " + success);
progressIndicator.setProgressValue(100);
@@ -185,12 +188,11 @@ public class SendToMyMaps implements Runnable {
}
final boolean finalSuccess = success;
- final int finalStatusMessageId = statusMessageId;
+ final String finalStatusMessage = statusMessage;
context.runOnUiThread(new Runnable() {
public void run() {
if (onCompletion != null) {
- onCompletion.onSendCompleted(
- mapId, finalSuccess, finalStatusMessageId);
+ onCompletion.onSendCompleted(mapId, finalSuccess, finalStatusMessage);
}
}
});
diff --git a/MyTracks/src/com/google/android/apps/mytracks/io/file/ImportActivity.java b/MyTracks/src/com/google/android/apps/mytracks/io/file/ImportActivity.java
index f6323aba3..027e35002 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/io/file/ImportActivity.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/io/file/ImportActivity.java
@@ -17,56 +17,21 @@ package com.google.android.apps.mytracks.io.file;
import static com.google.android.apps.mytracks.Constants.TAG;
-import com.google.android.apps.mytracks.content.MyTracksProviderUtils;
-import com.google.android.apps.mytracks.content.TracksColumns;
+import com.google.android.apps.mytracks.ImportAllTracks;
import com.google.android.apps.mytracks.util.UriUtils;
-import com.google.android.maps.mytracks.R;
import android.app.Activity;
-import android.app.AlertDialog;
-import android.app.AlertDialog.Builder;
-import android.app.Dialog;
-import android.app.ProgressDialog;
-import android.content.ContentUris;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnClickListener;
import android.content.Intent;
import android.net.Uri;
-import android.os.Bundle;
import android.util.Log;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-
-import javax.xml.parsers.ParserConfigurationException;
-
-import org.xml.sax.SAXException;
-
/**
- * Helper activity which imports tracks from a file.
+ * An activity that imports a track from a file and displays the track in My Tracks.
*
* @author Rodrigo Damazio
*/
public class ImportActivity extends Activity {
- private static final int PROGRESS_DIALOG = 1;
- private static final int SUCCESS_DIALOG = 2;
- private static final int FAILURE_DIALOG = 3;
-
- private MyTracksProviderUtils providerUtils;
-
- private ProgressDialog progressDialog;
- private int resultMessage;
- private long importedTrackIds[];
-
- @Override
- public void onCreate(Bundle savedState) {
- super.onCreate(savedState);
-
- providerUtils = MyTracksProviderUtils.Factory.get(this);
- }
-
@Override
public void onStart() {
super.onStart();
@@ -74,143 +39,20 @@ public class ImportActivity extends Activity {
Intent intent = getIntent();
String action = intent.getAction();
Uri data = intent.getData();
- if (!(Intent.ACTION_VIEW.equals(action) || Intent.ACTION_ATTACH_DATA.equals(action))
- || !UriUtils.isFileUri(data)) {
- Log.e(TAG, "Received an intent with unsupported action or data: " + intent);
+ if (!(Intent.ACTION_VIEW.equals(action) || Intent.ACTION_ATTACH_DATA.equals(action))) {
+ Log.e(TAG, "Received an intent with unsupported action: " + intent);
finish();
return;
}
-
- Log.i(TAG, "Importing GPX file at " + data);
- startTrackImport(data.getPath());
- }
-
- @Override
- protected Dialog onCreateDialog(int id) {
- switch (id) {
- case PROGRESS_DIALOG:
- progressDialog = new ProgressDialog(this);
- progressDialog.setIcon(android.R.drawable.ic_dialog_info);
- progressDialog.setTitle(R.string.progress_title);
- progressDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
- progressDialog.setMessage(getString(R.string.progress_message_import));
- return progressDialog;
- case SUCCESS_DIALOG:
- final Builder dialogBuilder = new AlertDialog.Builder(this);
- dialogBuilder.setCancelable(true);
- dialogBuilder.setPositiveButton(android.R.string.ok, new OnClickListener() {
- @Override
- public void onClick(DialogInterface arg0, int arg1) {
- finish();
- }
- });
- dialogBuilder.setNegativeButton(R.string.import_show_track, new OnClickListener() {
- @Override
- public void onClick(DialogInterface arg0, int arg1) {
- showImportedTrack();
- finish();
- }
- });
- return dialogBuilder.create();
- case FAILURE_DIALOG:
- AlertDialog.Builder builder = new AlertDialog.Builder(this);
- builder.setPositiveButton(R.string.ok, new OnClickListener() {
- @Override
- public void onClick(DialogInterface arg0, int arg1) {
- finish();
- }
- });
- builder.setIcon(android.R.drawable.ic_dialog_alert);
- builder.setTitle(R.string.error);
- return builder.create();
-
+
+ if (!UriUtils.isFileUri(data)) {
+ Log.e(TAG, "Received an intent with unsupported data: " + intent);
+ finish();
+ return;
}
-
- return null;
- }
-
- @Override
- protected void onPrepareDialog(int id, Dialog dialog) {
- super.onPrepareDialog(id, dialog);
-
- switch (id) {
- case SUCCESS_DIALOG:
- AlertDialog successDialog = (AlertDialog) dialog;
- successDialog.setMessage(getString(R.string.import_success, importedTrackIds.length));
- break;
- case FAILURE_DIALOG:
- AlertDialog failureDialog = (AlertDialog) dialog;
- failureDialog.setMessage(getString(resultMessage));
- break;
- }
- }
-
- protected void showImportedTrack() {
- long lastTrackId = importedTrackIds[importedTrackIds.length - 1];
- Uri trackUri = ContentUris.withAppendedId(TracksColumns.CONTENT_URI, lastTrackId);
-
- Intent intent = new Intent(Intent.ACTION_VIEW);
- intent.setDataAndType(trackUri, TracksColumns.CONTENT_ITEMTYPE);
- intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
- startActivity(intent);
- finish();
- }
-
- private void startTrackImport(final String fileName) {
- showDialog(PROGRESS_DIALOG);
-
- Thread t = new Thread() {
- @Override
- public void run() {
- resultMessage = R.string.success;
-
- importedTrackIds = null;
-
- try {
- try {
- InputStream is = new FileInputStream(fileName);
- importedTrackIds = GpxImporter.importGPXFile(is, providerUtils);
- } catch (SAXException e) {
- Log.e(TAG, "Caught an unexpected exception.", e);
- resultMessage = R.string.error_generic;
- } catch (ParserConfigurationException e) {
- Log.e(TAG, "Caught an unexpected exception.", e);
- resultMessage = R.string.error_generic;
- } catch (IOException e) {
- Log.e(TAG, "Caught an unexpected exception.", e);
- resultMessage = R.string.error_import_unable_to_read_file;
- } catch (NullPointerException e) {
- Log.e(TAG, "Caught an unexpected exception.", e);
- resultMessage = R.string.error_import_invalid_gpx_format;
- } catch (OutOfMemoryError e) {
- Log.e(TAG, "Caught an unexpected exception.", e);
- resultMessage = R.string.error_import_out_of_memory;
- }
-
- boolean success = (importedTrackIds != null && importedTrackIds.length > 0);
- showImportResult(success);
- } finally {
- runOnUiThread(new Runnable() {
- public void run() {
- dismissDialog(PROGRESS_DIALOG);
- }
- });
- }
- }
- };
- t.start();
- }
-
- private void showImportResult(boolean success) {
- final int dialogToShow = success ? SUCCESS_DIALOG : FAILURE_DIALOG;
-
- // Show a dialog telling the user about the import, and asking if he wishes
- // to open the track right away.
- runOnUiThread(new Runnable() {
- @Override
- public void run() {
- showDialog(dialogToShow);
- }
- });
+
+ String path = data.getPath();
+ Log.i(TAG, "Importing GPX file at " + path);
+ new ImportAllTracks(this, path);
}
}
diff --git a/MyTracks/src/com/google/android/apps/mytracks/io/mymaps/MapsFacade.java b/MyTracks/src/com/google/android/apps/mytracks/io/mymaps/MapsFacade.java
index a5b817dc1..722f614c1 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/io/mymaps/MapsFacade.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/io/mymaps/MapsFacade.java
@@ -3,6 +3,7 @@ package com.google.android.apps.mytracks.io.mymaps;
import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.io.AuthManager;
+import com.google.android.apps.mytracks.util.StringUtils;
import com.google.android.maps.GeoPoint;
import com.google.android.maps.mytracks.R;
import com.google.wireless.gdata.client.HttpException;
@@ -119,7 +120,7 @@ public class MapsFacade {
MyMapsMapMetadata metaData = new MyMapsMapMetadata();
metaData.setTitle(title);
metaData.setDescription(description + " - "
- + category + " - " + context.getString(R.string.send_to_google_by_mytracks));
+ + category + " - " + StringUtils.getCreatedByMyTracks(context, false));
metaData.setSearchable(isPublic);
Entry entry = MyMapsGDataConverter.getMapEntryForMetadata(metaData);
Log.d(MyMapsConstants.TAG, "Title: " + entry.getTitle());
diff --git a/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendActivity.java b/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendActivity.java
index 573e95765..395688c92 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendActivity.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendActivity.java
@@ -429,9 +429,9 @@ public class SendActivity extends Activity implements ProgressIndicator {
SendToMyMaps.OnSendCompletedListener onCompletion = new SendToMyMaps.OnSendCompletedListener() {
@Override
- public void onSendCompleted(String mapId, boolean success, int statusMessage) {
+ public void onSendCompleted(String mapId, boolean success, String statusMessage) {
// TODO: Use this message
- sendToMyMapsMessage = getString(statusMessage);
+ sendToMyMapsMessage = statusMessage;
sendToMyMapsSuccess = success;
if (sendToMyMapsSuccess) {
sendToMyMapsMapId = mapId;
@@ -491,10 +491,9 @@ public class SendActivity extends Activity implements ProgressIndicator {
OnSendCompletedListener onCompletion = new OnSendCompletedListener() {
@Override
- public void onSendCompleted(String tableId, boolean success,
- int statusMessage) {
+ public void onSendCompleted(String tableId, boolean success, String statusMessage) {
// TODO: Use this message
- sendToFusionTablesMessage = getString(statusMessage);
+ sendToFusionTablesMessage = statusMessage;
sendToFusionTablesSuccess = success;
if (sendToFusionTablesSuccess) {
sendToFusionTablesTableId = tableId;
diff --git a/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendType.java b/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendType.java
index 66feccf41..37d382a63 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendType.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/io/sendtogoogle/SendType.java
@@ -24,11 +24,11 @@ import com.google.android.maps.mytracks.R;
*/
public enum SendType {
MYMAPS(R.string.sendtogoogle_google_mymaps,
- R.string.sendtogoogle_google_mymaps_url),
+ R.string.send_google_my_maps_url),
FUSION_TABLES(R.string.sendtogoogle_google_fusiontables,
- R.string.sendtogoogle_google_fusiontables_url),
+ R.string.send_google_fusion_tables_url),
DOCS(R.string.sendtogoogle_google_docs,
- R.string.sendtogoogle_google_docs_url);
+ R.string.send_google_docs_url);
private int serviceName;
private int serviceUrl;
diff --git a/MyTracks/src/com/google/android/apps/mytracks/services/TrackRecordingService.java b/MyTracks/src/com/google/android/apps/mytracks/services/TrackRecordingService.java
index c32f88c10..c266cf26b 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/services/TrackRecordingService.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/services/TrackRecordingService.java
@@ -559,6 +559,11 @@ public class TrackRecordingService extends Service {
Log.d(TAG,
"Location listener now unregistered w/ TrackRecordingService.");
}
+
+ private String getDefaultActivityType(Context context) {
+ SharedPreferences prefs = context.getSharedPreferences(Constants.SETTINGS_NAME, 0);
+ return prefs.getString(context.getString(R.string.default_category_key), "");
+ }
/*
* Recording lifecycle.
@@ -582,6 +587,7 @@ public class TrackRecordingService extends Service {
track.setId(recordingTrackId);
track.setName(new DefaultTrackNameFactory(this).newTrackName(
recordingTrackId, startTime));
+ track.setCategory(getDefaultActivityType(this));
isRecording = true;
isMoving = true;
diff --git a/MyTracks/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTask.java b/MyTracks/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTask.java
index a1dbaba2f..9e66f8d37 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTask.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTask.java
@@ -24,6 +24,7 @@ import com.google.android.apps.mytracks.stats.TripStatistics;
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.common.annotations.VisibleForTesting;
import android.content.Context;
import android.content.SharedPreferences;
@@ -327,7 +328,8 @@ public class StatusAnnouncerTask implements PeriodicTask {
*
* @param time the time
*/
- private String getAnnounceTime(long time) {
+ @VisibleForTesting
+ String getAnnounceTime(long time) {
int[] parts = StringUtils.getTimeParts(time);
String secLabel =
context.getString(parts[0] == 1 ? R.string.voice_second : R.string.voice_seconds);
@@ -343,6 +345,7 @@ public class StatusAnnouncerTask implements PeriodicTask {
sb.append(hourLabel);
sb.append(" ");
sb.append(parts[1]);
+ sb.append(" ");
sb.append(minLabel);
} else {
sb.append(parts[1]);
@@ -350,6 +353,7 @@ public class StatusAnnouncerTask implements PeriodicTask {
sb.append(minLabel);
sb.append(" ");
sb.append(parts[0]);
+ sb.append(" ");
sb.append(secLabel);
}
return sb.toString();
diff --git a/MyTracks/src/com/google/android/apps/mytracks/util/StringUtils.java b/MyTracks/src/com/google/android/apps/mytracks/util/StringUtils.java
index 308905fdc..b86ca9162 100644
--- a/MyTracks/src/com/google/android/apps/mytracks/util/StringUtils.java
+++ b/MyTracks/src/com/google/android/apps/mytracks/util/StringUtils.java
@@ -303,7 +303,7 @@ public class StringUtils implements DescriptionGenerator {
+ "
",
// Line 1
- context.getString(R.string.send_to_google_by_mytracks),
+ getCreatedByMyTracks(context, true),
// Line 2
context.getString(R.string.total_distance_label),
@@ -353,6 +353,22 @@ public class StringUtils implements DescriptionGenerator {
ChartURLGenerator.getChartUrl(distances, elevations, track, context));
}
+ /**
+ * Returns the 'Created by My Tracks on Android' string.
+ *
+ * @param context the context
+ * @param addLink true to add a link to the My Tracks web site
+ */
+ public static String getCreatedByMyTracks(Context context, boolean addLink) {
+ String format = context.getString(R.string.send_google_by_my_tracks);
+ if (addLink) {
+ String url = context.getString(R.string.my_tracks_web_url);
+ return String.format(format, "", "");
+ } else {
+ return String.format(format, "", "");
+ }
+ }
+
private String getSpeedString(double speed, int speedLabel, int paceLabel,
boolean displaySpeed) {
double speedInKph = speed * 3.6;
diff --git a/MyTracksTest/src/com/google/android/apps/mytracks/services/TrackRecordingServiceTest.java b/MyTracksTest/src/com/google/android/apps/mytracks/services/TrackRecordingServiceTest.java
index 16b7af12a..71fe422d1 100644
--- a/MyTracksTest/src/com/google/android/apps/mytracks/services/TrackRecordingServiceTest.java
+++ b/MyTracksTest/src/com/google/android/apps/mytracks/services/TrackRecordingServiceTest.java
@@ -382,6 +382,8 @@ public class TrackRecordingServiceTest
Track track = providerUtils.getTrack(id);
assertNotNull(track);
assertEquals(id, track.getId());
+ assertEquals(sharedPreferences.getString(context.getString(R.string.default_category_key), ""),
+ track.getCategory());
assertEquals(id, sharedPreferences.getLong(
context.getString(R.string.recording_track_key), -1));
assertEquals(id, service.getRecordingTrackId());
diff --git a/MyTracksTest/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTaskTest.java b/MyTracksTest/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTaskTest.java
index 4f7c2e600..48d52bc5b 100644
--- a/MyTracksTest/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTaskTest.java
+++ b/MyTracksTest/src/com/google/android/apps/mytracks/services/tasks/StatusAnnouncerTaskTest.java
@@ -478,7 +478,59 @@ public class StatusAnnouncerTaskTest extends AndroidTestCase {
task.runWithStatistics(null);
AndroidMock.verify(mockTask, tts);
}
+
+ /**
+ * Tests {@link StatusAnnouncerTask#getAnnounceTime(long)} with time zero.
+ */
+ public void testGetAnnounceTime_time_zero() {
+ long time = 0; // 0 seconds
+ assertEquals("0 minutes 0 seconds", task.getAnnounceTime(time));
+ }
+ /**
+ * Tests {@link StatusAnnouncerTask#getAnnounceTime(long)} with time one.
+ */
+ public void testGetAnnounceTime_time_one() {
+ long time = 1 * 1000; // 1 second
+ assertEquals("0 minutes 1 second", task.getAnnounceTime(time));
+ }
+
+ /**
+ * Tests {@link StatusAnnouncerTask#getAnnounceTime(long)} with singular
+ * numbers with the hour unit.
+ */
+ public void testGetAnnounceTime_singular_has_hour() {
+ long time = (1 * 60 * 60 * 1000) + (1 * 60 * 1000) + (1 * 1000); // 1 hour 1 minute 1 second
+ assertEquals("1 hour 1 minute", task.getAnnounceTime(time));
+ }
+
+ /**
+ * Tests {@link StatusAnnouncerTask#getAnnounceTime(long)} with plural numbers
+ * with the hour unit.
+ */
+ public void testGetAnnounceTime_plural_has_hour() {
+ long time = (2 * 60 * 60 * 1000) + (2 * 60 * 1000) + (2 * 1000); // 2 hours 2 minutes 2 seconds
+ assertEquals("2 hours 2 minutes", task.getAnnounceTime(time));
+ }
+
+ /**
+ * Tests {@link StatusAnnouncerTask#getAnnounceTime(long)} with singular
+ * numbers without the hour unit.
+ */
+ public void testGetAnnounceTime_singular_no_hour() {
+ long time = (1 * 60 * 1000) + (1 * 1000); // 1 minute 1 second
+ assertEquals("1 minute 1 second", task.getAnnounceTime(time));
+ }
+
+ /**
+ * Tests {@link StatusAnnouncerTask#getAnnounceTime(long)} with plural numbers
+ * without the hour unit.
+ */
+ public void testGetAnnounceTime_plural_no_hour() {
+ long time = (2 * 60 * 1000) + (2 * 1000); // 2 minutes 2 seconds
+ assertEquals("2 minutes 2 seconds", task.getAnnounceTime(time));
+ }
+
private void startTask(int state) {
AndroidMock.resetToNice(tts);
AndroidMock.replay(tts);