Merge heads

This commit is contained in:
youtaol
2012-05-15 16:58:38 +08:00
parent f1573a550a
commit 37bfefaa3d
29 changed files with 379 additions and 499 deletions
+2 -2
View File
@@ -16,8 +16,8 @@ limitations under the License.
-->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
android:installLocation="auto"
android:versionCode="39"
android:versionName="1.1.16"
android:versionCode="40"
android:versionName="2.0"
package="com.google.android.maps.mytracks" >
<!-- Permission to initialize services -->
+42 -30
View File
@@ -19,41 +19,53 @@ limitations under the License.
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:minHeight="?android:attr/listPreferredItemHeight"
android:orientation="vertical"
android:orientation="horizontal"
android:padding="8dp" >
<ImageView
android:contentDescription="@string/icon_track"
android:id="@+id/list_item_icon"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:src="@drawable/track" />
<LinearLayout
android:layout_height="wrap_content"
android:layout_marginLeft="8dp"
android:layout_width="fill_parent"
android:orientation="horizontal" >
android:orientation="vertical" >
<LinearLayout
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:orientation="horizontal" >
<TextView
android:id="@+id/list_item_name"
android:singleLine="true"
style="@style/TextLarge" />
<TextView
android:id="@+id/list_item_category"
android:layout_marginLeft="8dp"
android:singleLine="true"
style="@style/TextSmall" />
</LinearLayout>
<LinearLayout
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:orientation="horizontal" >
<TextView
android:id="@+id/list_item_total_time"
android:layout_marginRight="8dp"
style="@style/ListItemStats" />
<TextView
android:id="@+id/list_item_total_distance"
android:layout_marginRight="8dp"
style="@style/ListItemStats" />
<TextView
android:id="@+id/list_item_start_time"
style="@style/ListItemStats" />
</LinearLayout>
<TextView
android:id="@+id/list_item_name"
android:singleLine="true"
style="@style/TextLarge.WithIcon" />
<TextView
android:id="@+id/list_item_category"
android:layout_marginLeft="8dp"
android:singleLine="true"
android:id="@+id/list_item_description"
android:singleLine="false"
android:textColor="@android:color/secondary_text_dark"
style="@style/TextSmall" />
</LinearLayout>
<LinearLayout
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:orientation="horizontal" >
<TextView
android:id="@+id/list_item_total_time"
android:layout_marginRight="8dp"
style="@style/ListItemStats" />
<TextView
android:id="@+id/list_item_total_distance"
android:layout_marginRight="8dp"
style="@style/ListItemStats" />
<TextView
android:id="@+id/list_item_start_time"
style="@style/ListItemStats" />
</LinearLayout>
<TextView
android:id="@+id/list_item_description"
android:singleLine="false"
android:textColor="@android:color/secondary_text_dark"
style="@style/TextSmall" />
</LinearLayout>
+1 -1
View File
@@ -28,7 +28,7 @@ limitations under the License.
android:layout_width="fill_parent" />
<ImageButton
android:background="@drawable/my_location"
android:contentDescription="@string/my_location"
android:contentDescription="@string/icon_my_location"
android:id="@+id/map_my_location"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
-46
View File
@@ -1,46 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright 2012 Google Inc.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
style="@style/ScrollView" >
<RelativeLayout
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:padding="8dp" >
<RadioGroup
android:id="@+id/marker_add_type"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:layout_height="wrap_content"
android:layout_width="wrap_content" >
<RadioButton
android:id="@+id/marker_add_statistics"
android:text="@string/marker_statistics"
style="@style/TextMedium" />
<RadioButton
android:id="@+id/marker_add_waypoint"
android:text="@string/marker_waypoint"
style="@style/TextMedium" />
</RadioGroup>
<Button
android:id="@+id/marker_add_more_options"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/generic_more_options" />
</RelativeLayout>
</ScrollView>
+16 -8
View File
@@ -31,19 +31,27 @@ limitations under the License.
android:orientation="vertical" >
<TextView
android:id="@+id/marker_detail_waypoint_marker_type"
style="@style/TextLarge" />
style="@style/TextLarge.WithTopMargin" />
<TextView
android:id="@+id/marker_detail_waypoint_description"
style="@style/TextLarge" />
style="@style/TextLarge.WithTopMargin" />
</LinearLayout>
<TableLayout
<LinearLayout
android:id="@+id/marker_detail_statistics_section"
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:paddingTop="8dp"
android:shrinkColumns="0,2"
android:stretchColumns="0,2" >
<include layout="@layout/stats_core" />
</TableLayout>
android:orientation="vertical" >
<TextView
android:text="@string/marker_detail_statistics_title"
style="@style/TextLarge.WithTopMargin" />
<TableLayout
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:paddingTop="8dp"
android:shrinkColumns="0,2"
android:stretchColumns="0,2" >
<include layout="@layout/stats_core" />
</TableLayout>
</LinearLayout>
</LinearLayout>
</ScrollView>
+2 -24
View File
@@ -24,28 +24,6 @@ limitations under the License.
android:layout_width="fill_parent"
android:orientation="vertical"
android:padding="8dp" >
<LinearLayout
android:id="@+id/marker_edit_type_section"
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:orientation="vertical" >
<TextView
android:text="@string/marker_type"
style="@style/EditLabel" />
<RadioGroup
android:id="@+id/marker_edit_type"
android:layout_height="wrap_content"
android:layout_width="wrap_content" >
<RadioButton
android:id="@+id/marker_edit_statistics"
android:text="@string/marker_statistics"
style="@style/TextMedium" />
<RadioButton
android:id="@+id/marker_edit_waypoint"
android:text="@string/marker_waypoint"
style="@style/TextMedium" />
</RadioGroup>
</LinearLayout>
<TextView
android:text="@string/generic_name"
style="@style/EditLabel" />
@@ -73,10 +51,10 @@ limitations under the License.
android:imeOptions="actionNext"
style="@style/EditName" />
<TextView
android:text="@string/marker_edit_waypoint_marker_type"
android:text="@string/marker_edit_marker_type"
style="@style/EditLabel.WithPaddingTop" />
<AutoCompleteTextView
android:hint="@string/marker_edit_waypoint_marker_type_hint"
android:hint="@string/marker_edit_marker_type_hint"
android:id="@+id/marker_edit_waypoint_marker_type"
android:imeOptions="actionNext"
style="@style/EditCategory" />
-1
View File
@@ -39,7 +39,6 @@ limitations under the License.
<string name="min_recording_interval_key">minRecordingInterval</string>
<string name="min_required_accuracy_key">minRequiredAccuracy</string>
<string name="pick_existing_map_key">pickExistingMap</string>
<string name="pick_statistics_marker_key">pickStatisticsMarker</string>
<string name="preferred_account_key">preferredAccount</string>
<string name="recording_track_id_key">recordingTrackId</string>
<string name="report_speed_key">reportSpeed</string>
+41 -43
View File
@@ -634,10 +634,6 @@ limitations under the License.
translation_description="The title on an alert dialog indicating error.">
Error
</string>
<string name="generic_more_options"
translation_description="The text on a button to say more options.">
More options
</string>
<string name="generic_name"
translation_description="The text label for entering a name.">
Name
@@ -825,6 +821,24 @@ limitations under the License.
What are waypoint markers?
</string>
<!-- Icon -->
<string name="icon_marker"
translation_description="The accessibility description for the 'Marker' icon.">
Marker
</string>
<string name="icon_my_location"
translation_description="The accessibility description for the 'My Location' icon.">
My Location
</string>
<string name="icon_recording"
translation_description="The accessibility description for the 'Recording' icon.">
Recording
</string>
<string name="icon_track"
translation_description="The accessibility description for the 'Track' icon.">
Track
</string>
<!-- Import -->
<string name="import_error"
translation_description="When importing all the tracks, a toast message indicating import error
@@ -920,8 +934,9 @@ limitations under the License.
<!-- Marker -->
<string name="marker_add_error"
translation_description="When adding a marker, the message indicating error.">
Unable to insert a marker. Try again.
translation_description="When adding a marker, the message indicating error due to no GPS
signal.">
Unable to insert a marker. No GPS signal. Try again.
</string>
<string name="marker_add_success"
translation_description="When adding a marker, the message indicating success.">
@@ -935,29 +950,34 @@ limitations under the License.
<string name="marker_detail_name"
translation_description="In the marker detail page, the label for the marker name.
%1$s marker name. E.g., 'Waypoint 1'.">
%1$s marker name. E.g., 'Marker 1'.">
Name: %1$s
</string>
<string name="marker_detail_waypoint_description"
translation_description="In the marker detail page, the label for the waypoint description.
<string name="marker_detail_description"
translation_description="In the marker detail page, the label for the description.
%1$s marker description. E.g., 'At the top'.">
Description: %1$s
</string>
<string name="marker_detail_waypoint_marker_type"
translation_description="In the marker detail page, the label for the waypoint marker type.
<string name="marker_detail_marker_type"
translation_description="In the marker detail page, the label for the marker type.
%1$s marker type. E.g., 'building'.">
Marker type: %1$s
</string>
<string name="marker_edit_waypoint_marker_type"
translation_description="In the marker edit page, the label for the waypoint marker type,
including some exmaples.">
<string name="marker_detail_statistics_title"
translation_description="In the marker detail page, the title for the statistics section
indicating that the data below are since the last Statistics marker.">
Since last Statistics marker:
</string>
<string name="marker_edit_marker_type"
translation_description="In the marker edit page, the label for the marker type, including some
exmaples.">
Marker type (e.g. building, pothole...)
</string>
<string name="marker_edit_waypoint_marker_type_hint"
translation_description="In the marker edit page, the hint in the waypoint marker type text
field when it is empty.">
<string name="marker_edit_marker_type_hint"
translation_description="In the marker edit page, the hint in the marker type text field when it
is empty.">
Marker type
</string>
<string name="marker_label_end"
@@ -978,10 +998,6 @@ limitations under the License.
translation_description="The message when the marker list is empty.">
You don\'t have any markers.
</string>
<string name="marker_statistics"
translation_description="The label to add a statistics marker.">
Statistics
</string>
<string name="marker_statistics_name_format"
translation_description="When adding a statistics marker, the string format for the default
name.
@@ -989,20 +1005,11 @@ limitations under the License.
%1$d: number. E.g., '1'.">
Statistics %1$d
</string>
<string name="marker_type"
translation_description="When adding a marker, the label to select a type, statistics or
waypoint.">
Type
</string>
<string name="marker_waypoint"
translation_description="The label to add a waypoint marker.">
Waypoint
</string>
<string name="marker_waypoint_name_format"
translation_description="When adding a waypoint marker, the string format for the default name.
<string name="marker_name_format"
translation_description="When adding a marker, the string format for the default name.
%1$d: number. E.g., '1'.">
Waypoint %1$d
Marker %1$d
</string>
<!-- Menu Items -->
@@ -1072,7 +1079,7 @@ limitations under the License.
Save as %1$s
</string>
<string name="menu_search"
translation_description="In the menu, to start a textual search for tracks or waypoints.">
translation_description="In the menu, to start a textual search for tracks or markers.">
Search
</string>
<string name="menu_send_google"
@@ -1119,11 +1126,6 @@ limitations under the License.
</string>
<!-- My Location -->
<string name="my_location"
translation_description="The accessibility description for the My Location button on the map
view.">
My Location
</string>
<string name="my_location_approximate_location"
translation_description="When displaying the user's current location, a status message
indicating that GPS is not available and an approximate location is used instead.">
@@ -2127,10 +2129,6 @@ limitations under the License.
translation_description="In the track detail page, the title when recording.">
Recording...
</string>
<string name="track_icon_description"
translation_description="The accessibility description for the track icon.">
Track
</string>
<string name="track_edit_activity_type"
translation_description="In the page to edit a track, the label for the text field to edit the
activity type, including some examples of activity types.">
+3 -4
View File
@@ -122,10 +122,9 @@ limitations under the License.
<item name="android:layout_width">wrap_content</item>
<item name="android:textSize">22sp</item>
</style>
<!-- The style for large size text with an icon on the left -->
<style name="TextLarge.WithIcon">
<item name="android:drawablePadding">8dp</item>
<item name="android:gravity">center_vertical</item>
<!-- The style for large size text with top margin -->
<style name="TextLarge.WithTopMargin">
<item name="android:layout_marginTop">8dp</item>
</style>
<!-- The style for medium size text -->
<style name="TextMedium">
@@ -44,6 +44,10 @@ public class MarkerDetailActivity extends AbstractMyTracksActivity {
private long markerId;
private Waypoint waypoint;
private TextView name;
private View waypointSection;
private View statisticsSection;
@Override
protected void onCreate(Bundle bundle) {
super.onCreate(bundle);
@@ -55,29 +59,29 @@ public class MarkerDetailActivity extends AbstractMyTracksActivity {
finish();
return;
}
name = (TextView) findViewById(R.id.marker_detail_name);
waypointSection = findViewById(R.id.marker_detail_waypoint_section);
statisticsSection = findViewById(R.id.marker_detail_statistics_section);
}
@Override
protected void onResume() {
super.onResume();
waypoint = MyTracksProviderUtils.Factory.get(this).getWaypoint(markerId);
if (waypoint == null) {
Log.d(TAG, "waypoint is null");
finish();
return;
}
TextView name = (TextView) findViewById(R.id.marker_detail_name);
name.setText(getString(R.string.marker_detail_name, waypoint.getName()));
View waypointSection = findViewById(R.id.marker_detail_waypoint_section);
View statisticsSection = findViewById(R.id.marker_detail_statistics_section);
if (waypoint.getType() == Waypoint.TYPE_WAYPOINT) {
waypointSection.setVisibility(View.VISIBLE);
statisticsSection.setVisibility(View.GONE);
TextView markerType = (TextView) findViewById(R.id.marker_detail_waypoint_marker_type);
markerType.setText(getString(
R.string.marker_detail_waypoint_marker_type, waypoint.getCategory()));
markerType.setText(getString(R.string.marker_detail_marker_type, waypoint.getCategory()));
TextView description = (TextView) findViewById(R.id.marker_detail_waypoint_description);
description.setText(getString(
R.string.marker_detail_waypoint_description, waypoint.getDescription()));
description.setText(getString(R.string.marker_detail_description, waypoint.getDescription()));
} else {
waypointSection.setVisibility(View.GONE);
statisticsSection.setVisibility(View.VISIBLE);
@@ -85,7 +89,7 @@ public class MarkerDetailActivity extends AbstractMyTracksActivity {
StatsUtils.setLocationValues(this, waypoint.getLocation(), false);
}
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.marker_detail, menu);
@@ -21,7 +21,6 @@ import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.content.WaypointCreationRequest;
import com.google.android.apps.mytracks.content.WaypointCreationRequest.WaypointType;
import com.google.android.apps.mytracks.services.TrackRecordingServiceConnection;
import com.google.android.apps.mytracks.util.PreferencesUtils;
import com.google.android.apps.mytracks.util.TrackRecordingServiceConnectionUtils;
import com.google.android.maps.mytracks.R;
@@ -33,7 +32,6 @@ import android.widget.ArrayAdapter;
import android.widget.AutoCompleteTextView;
import android.widget.Button;
import android.widget.EditText;
import android.widget.RadioGroup;
/**
* An activity to add/edit a marker.
@@ -46,17 +44,13 @@ public class MarkerEditActivity extends AbstractMyTracksActivity {
public static final String EXTRA_TRACK_ID = "track_id";
public static final String EXTRA_MARKER_ID = "marker_id";
public static final String EXTRA_STATISTICS_MARKER = "statistics_marker";
private long trackId;
private long markerId;
private boolean statisticsMarker;
private TrackRecordingServiceConnection trackRecordingServiceConnection;
private Waypoint waypoint;
// UI elements
private View typeSection;
private RadioGroup type;
private View statisticsSection;
private EditText statisticsName;
private View waypointSection;
@@ -72,36 +66,9 @@ public class MarkerEditActivity extends AbstractMyTracksActivity {
trackId = getIntent().getLongExtra(EXTRA_TRACK_ID, -1L);
markerId = getIntent().getLongExtra(EXTRA_MARKER_ID, -1L);
statisticsMarker = getIntent().getBooleanExtra(EXTRA_STATISTICS_MARKER, true);
trackRecordingServiceConnection = new TrackRecordingServiceConnection(this, null);
trackRecordingServiceConnection = new TrackRecordingServiceConnection(this, null);
// Setup UI elements
typeSection = findViewById(R.id.marker_edit_type_section);
type = (RadioGroup) findViewById(R.id.marker_edit_type);
type.setOnCheckedChangeListener(new RadioGroup.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(RadioGroup group, int checkedId) {
boolean statistics = checkedId == R.id.marker_edit_statistics;
statisticsSection.setVisibility(statistics ? View.VISIBLE : View.GONE);
waypointSection.setVisibility(statistics ? View.GONE : View.VISIBLE);
int nextMarkerNumber = trackId == -1L ? -1
: MyTracksProviderUtils.Factory.get(MarkerEditActivity.this)
.getNextMarkerNumber(trackId, statistics);
if (statistics) {
String name = nextMarkerNumber == -1 ? getString(R.string.marker_type_statistics)
: getString(R.string.marker_statistics_name_format, nextMarkerNumber);
statisticsName.setText(name);
statisticsName.selectAll();
} else {
String name = nextMarkerNumber == -1 ? getString(R.string.marker_type_waypoint)
: getString(R.string.marker_waypoint_name_format, nextMarkerNumber);
waypointName.setText(name);
waypointName.selectAll();
waypointMarkerType.setText("");
waypointDescription.setText("");
}
}
});
statisticsSection = findViewById(R.id.marker_edit_statistics_section);
statisticsName = (EditText) findViewById(R.id.marker_edit_statistics_name);
@@ -131,7 +98,6 @@ public class MarkerEditActivity extends AbstractMyTracksActivity {
final boolean newMarker = markerId == -1L;
setTitle(newMarker ? R.string.menu_insert_marker : R.string.menu_edit);
typeSection.setVisibility(newMarker ? View.VISIBLE : View.GONE);
done.setText(newMarker ? R.string.generic_add : R.string.generic_save);
done.setOnClickListener(new View.OnClickListener() {
@Override
@@ -146,7 +112,16 @@ public class MarkerEditActivity extends AbstractMyTracksActivity {
});
if (newMarker) {
type.check(statisticsMarker ? R.id.marker_edit_statistics : R.id.marker_edit_waypoint);
statisticsSection.setVisibility(View.GONE);
waypointSection.setVisibility(View.VISIBLE);
int nextMarkerNumber = trackId == -1L ? -1
: MyTracksProviderUtils.Factory.get(this).getNextMarkerNumber(trackId, false);
String name = nextMarkerNumber == -1 ? getString(R.string.marker_type_waypoint)
: getString(R.string.marker_name_format, nextMarkerNumber);
waypointName.setText(name);
waypointName.selectAll();
waypointMarkerType.setText("");
waypointDescription.setText("");
} else {
waypoint = MyTracksProviderUtils.Factory.get(this).getWaypoint(markerId);
if (waypoint == null) {
@@ -183,18 +158,13 @@ public class MarkerEditActivity extends AbstractMyTracksActivity {
* Adds a marker.
*/
private void addMarker() {
boolean statistics = type.getCheckedRadioButtonId() == R.id.marker_edit_statistics;
PreferencesUtils.setBoolean(this, R.string.pick_statistics_marker_key, statistics);
WaypointType waypointType = statistics ? WaypointType.STATISTICS : WaypointType.WAYPOINT;
String markerName = statistics ? statisticsName.getText().toString()
: waypointName.getText().toString();
String markerCategory = statistics ? null : waypointMarkerType.getText().toString();
String markerDescription = statistics ? null : waypointDescription.getText().toString();
String markerIconUrl = getString(statistics ? R.string.marker_statistics_icon_url
: R.string.marker_waypoint_icon_url);
WaypointCreationRequest waypointCreationRequest = new WaypointCreationRequest(
waypointType, markerName, markerCategory, markerDescription, markerIconUrl);
WaypointType.WAYPOINT,
false,
waypointName.getText().toString(),
waypointMarkerType.getText().toString(),
waypointDescription.getText().toString(),
getString(R.string.marker_waypoint_icon_url));
TrackRecordingServiceConnectionUtils.addMarker(
this, trackRecordingServiceConnection, waypointCreationRequest);
}
@@ -20,12 +20,10 @@ import com.google.android.apps.mytracks.content.MyTracksProviderUtils;
import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.content.WaypointsColumns;
import com.google.android.apps.mytracks.fragments.DeleteOneMarkerDialogFragment;
import com.google.android.apps.mytracks.fragments.MarkerAddDialogFragment;
import com.google.android.apps.mytracks.util.ApiAdapterFactory;
import com.google.android.apps.mytracks.util.IntentUtils;
import com.google.android.apps.mytracks.util.ListItemUtils;
import com.google.android.apps.mytracks.util.PreferencesUtils;
import com.google.android.apps.mytracks.util.StringUtils;
import com.google.android.maps.mytracks.R;
import android.content.Context;
@@ -139,12 +137,12 @@ public class MarkerListActivity extends AbstractMyTracksActivity {
boolean statistics = cursor.getInt(typeIndex) == Waypoint.TYPE_STATISTICS;
String name = cursor.getString(nameIndex);
int iconId = statistics ? R.drawable.yellow_pushpin : R.drawable.blue_pushpin;
String contentDescription = getString(R.string.icon_marker);
String category = statistics ? null : cursor.getString(categoryIndex);
long time = cursor.getLong(timeIndex);
String startTime = time == 0
? null : StringUtils.formatDateTime(MarkerListActivity.this, time);
String description = statistics ? null : cursor.getString(descriptionIndex);
ListItemUtils.setListItem(view, name, iconId, category, null, null, startTime, description);
ListItemUtils.setListItem(MarkerListActivity.this,
view, name, iconId, contentDescription, category, null, null, time, description);
}
};
listView.setAdapter(resourceCursorAdapter);
@@ -197,8 +195,9 @@ public class MarkerListActivity extends AbstractMyTracksActivity {
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.marker_list_insert_marker:
MarkerAddDialogFragment.newInstance(trackId)
.show(getSupportFragmentManager(), MarkerAddDialogFragment.MARKER_ADD_DIALOG_TAG);
Intent intent = IntentUtils.newIntent(this, MarkerEditActivity.class)
.putExtra(MarkerEditActivity.EXTRA_TRACK_ID, trackId);
startActivity(intent);
return true;
case R.id.marker_list_search:
return ApiAdapterFactory.getApiAdapter().handleSearchMenuSelection(this);
@@ -25,12 +25,15 @@ import com.google.android.apps.mytracks.content.Track;
import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.fragments.DeleteOneMarkerDialogFragment;
import com.google.android.apps.mytracks.fragments.DeleteOneTrackDialogFragment;
import com.google.android.apps.mytracks.fragments.DeleteOneTrackDialogFragment.DeleteOneTrackCaller;
import com.google.android.apps.mytracks.services.TrackRecordingServiceConnection;
import com.google.android.apps.mytracks.stats.TripStatistics;
import com.google.android.apps.mytracks.util.ApiAdapterFactory;
import com.google.android.apps.mytracks.util.IntentUtils;
import com.google.android.apps.mytracks.util.ListItemUtils;
import com.google.android.apps.mytracks.util.PreferencesUtils;
import com.google.android.apps.mytracks.util.StringUtils;
import com.google.android.apps.mytracks.util.TrackRecordingServiceConnectionUtils;
import com.google.android.maps.mytracks.R;
import android.app.SearchManager;
@@ -67,12 +70,13 @@ import java.util.SortedSet;
*
* @author Rodrigo Damazio
*/
public class SearchListActivity extends AbstractMyTracksActivity {
public class SearchListActivity extends AbstractMyTracksActivity implements DeleteOneTrackCaller {
private static final String TAG = SearchListActivity.class.getSimpleName();
private static final String NAME_FIELD = "name";
private static final String ICON_FIELD = "icon";
private static final String ICON_CONTENT_DESCRIPTION_FIELD = "iconContentDescription";
private static final String CATEGORY_FIELD = "category";
private static final String TOTAL_TIME_FIELD = "totalTime";
private static final String TOTAL_DISTANCE_FIELD = "totalDistance";
@@ -103,6 +107,7 @@ public class SearchListActivity extends AbstractMyTracksActivity {
}
};
private TrackRecordingServiceConnection trackRecordingServiceConnection;
private MyTracksProviderUtils myTracksProviderUtils;
private SearchEngine searchEngine;
private SearchRecentSuggestions searchRecentSuggestions;
@@ -121,6 +126,7 @@ public class SearchListActivity extends AbstractMyTracksActivity {
setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
setContentView(R.layout.search_list);
trackRecordingServiceConnection = new TrackRecordingServiceConnection(this, null);
myTracksProviderUtils = MyTracksProviderUtils.Factory.get(this);
searchEngine = new SearchEngine(myTracksProviderUtils);
searchRecentSuggestions = SearchEngineProvider.newHelper(this);
@@ -161,14 +167,17 @@ public class SearchListActivity extends AbstractMyTracksActivity {
Map<String, Object> resultMap = getItem(position);
String name = (String) resultMap.get(NAME_FIELD);
int iconId = (Integer) resultMap.get(ICON_FIELD);
String iconContentDescription = (String) resultMap.get(ICON_CONTENT_DESCRIPTION_FIELD);
String category = (String) resultMap.get(CATEGORY_FIELD);
String totalTime = (String) resultMap.get(TOTAL_TIME_FIELD);
String totalDistance = (String) resultMap.get(TOTAL_DISTANCE_FIELD);
String startTime = (String) resultMap.get(START_TIME_FIELD);
long startTime = (Long) resultMap.get(START_TIME_FIELD);
String description = (String) resultMap.get(DESCRIPTION_FIELD);
ListItemUtils.setListItem(view,
ListItemUtils.setListItem(SearchListActivity.this,
view,
name,
iconId,
iconContentDescription,
category,
totalTime,
totalDistance,
@@ -186,10 +195,17 @@ public class SearchListActivity extends AbstractMyTracksActivity {
@Override
protected void onResume() {
super.onResume();
TrackRecordingServiceConnectionUtils.resume(this, trackRecordingServiceConnection);
metricUnits = PreferencesUtils.getBoolean(
this, R.string.metric_units_key, PreferencesUtils.METRIC_UNITS_DEFAULT);
}
@Override
protected void onDestroy() {
super.onDestroy();
trackRecordingServiceConnection.unbind();
}
@Override
public void onNewIntent(Intent intent) {
setIntent(intent);
@@ -382,11 +398,9 @@ public class SearchListActivity extends AbstractMyTracksActivity {
boolean statistics = waypoint.getType() == Waypoint.TYPE_STATISTICS;
resultMap.put(NAME_FIELD, waypoint.getName());
resultMap.put(ICON_FIELD, statistics ? R.drawable.yellow_pushpin : R.drawable.blue_pushpin);
resultMap.put(ICON_CONTENT_DESCRIPTION_FIELD, getString(R.string.icon_marker));
resultMap.put(CATEGORY_FIELD, statistics ? null : waypoint.getCategory());
long time = waypoint.getLocation().getTime();
String startTime = StringUtils.formatDateTime(this, time);
resultMap.put(START_TIME_FIELD, time == 0 || startTime.equals(trackName) ? null : startTime);
resultMap.put(START_TIME_FIELD, waypoint.getLocation().getTime());
// Display the marker's track name in the total time field
resultMap.put(TOTAL_TIME_FIELD, trackName == null ? null
@@ -408,18 +422,21 @@ public class SearchListActivity extends AbstractMyTracksActivity {
TripStatistics tripStatitics = track.getStatistics();
resultMap.put(NAME_FIELD, track.getName());
resultMap.put(ICON_FIELD, isRecording ? R.drawable.menu_record_track : R.drawable.track);
resultMap.put(ICON_CONTENT_DESCRIPTION_FIELD, getString(isRecording ? R.string.icon_recording
: R.string.icon_track));
resultMap.put(CATEGORY_FIELD, track.getCategory());
resultMap.put(TOTAL_TIME_FIELD, isRecording ? null : StringUtils.formatElapsedTime(
tripStatitics.getTotalTime()));
resultMap.put(TOTAL_DISTANCE_FIELD, isRecording ? null : StringUtils.formatDistance(
this, tripStatitics.getTotalDistance(), metricUnits));
String startTime = StringUtils.formatDateTime(this, tripStatitics.getStartTime());
if (startTime.equals(track.getName())) {
startTime = null;
}
resultMap.put(START_TIME_FIELD, startTime);
resultMap.put(START_TIME_FIELD, tripStatitics.getStartTime());
resultMap.put(DESCRIPTION_FIELD, track.getDescription());
resultMap.put(TRACK_ID_FIELD, track.getId());
resultMap.put(MARKER_ID_FIELD, null);
}
@Override
public TrackRecordingServiceConnection getTrackRecordingServiceConnection() {
return trackRecordingServiceConnection;
}
}
@@ -22,13 +22,13 @@ import com.google.android.apps.mytracks.services.TrackRecordingServiceConnection
import com.google.android.apps.mytracks.services.sensors.SensorManager;
import com.google.android.apps.mytracks.services.sensors.SensorManagerFactory;
import com.google.android.apps.mytracks.services.sensors.SensorUtils;
import com.google.android.apps.mytracks.util.StringUtils;
import com.google.android.apps.mytracks.util.TrackRecordingServiceConnectionUtils;
import com.google.android.maps.mytracks.R;
import com.google.protobuf.InvalidProtocolBufferException;
import android.os.Bundle;
import android.os.RemoteException;
import android.text.format.DateFormat;
import android.util.Log;
import android.widget.TextView;
@@ -221,7 +221,7 @@ public class SensorStateActivity extends AbstractMyTracksActivity {
* @param sensorDataSet sensor data set
*/
private String getLastSensorTime(Sensor.SensorDataSet sensorDataSet) {
return StringUtils.formatTime(this, sensorDataSet.getCreationTime());
return DateFormat.format("h:mm:ss aa", sensorDataSet.getCreationTime()).toString();
}
/**
@@ -23,9 +23,9 @@ import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.content.WaypointCreationRequest;
import com.google.android.apps.mytracks.fragments.ChartFragment;
import com.google.android.apps.mytracks.fragments.DeleteOneTrackDialogFragment;
import com.google.android.apps.mytracks.fragments.DeleteOneTrackDialogFragment.DeleteOneTrackCaller;
import com.google.android.apps.mytracks.fragments.InstallEarthDialogFragment;
import com.google.android.apps.mytracks.fragments.MapFragment;
import com.google.android.apps.mytracks.fragments.MarkerAddDialogFragment;
import com.google.android.apps.mytracks.fragments.StatsFragment;
import com.google.android.apps.mytracks.io.file.SaveActivity;
import com.google.android.apps.mytracks.io.file.TrackWriterFactory.TrackFileFormat;
@@ -64,7 +64,7 @@ import java.util.List;
* @author Leif Hendrik Wilden
* @author Rodrigo Damazio
*/
public class TrackDetailActivity extends AbstractMyTracksActivity {
public class TrackDetailActivity extends AbstractMyTracksActivity implements DeleteOneTrackCaller {
public static final String EXTRA_TRACK_ID = "track_id";
public static final String EXTRA_MARKER_ID = "marker_id";
@@ -85,8 +85,6 @@ public class TrackDetailActivity extends AbstractMyTracksActivity {
private MenuItem shareMenuItem;
private MenuItem sendGoogleMenuItem;
private MenuItem saveMenuItem;
private MenuItem editMenuItem;
private MenuItem deleteMenuItem;
private View mapViewContainer;
@@ -226,8 +224,6 @@ public class TrackDetailActivity extends AbstractMyTracksActivity {
shareMenuItem = menu.findItem(R.id.track_detail_share);
sendGoogleMenuItem = menu.findItem(R.id.track_detail_send_google);
saveMenuItem = menu.findItem(R.id.track_detail_save);
editMenuItem = menu.findItem(R.id.track_detail_edit);
deleteMenuItem = menu.findItem(R.id.track_detail_delete);
updateMenu();
return true;
@@ -255,11 +251,12 @@ public class TrackDetailActivity extends AbstractMyTracksActivity {
case R.id.track_detail_stop_recording:
updateMenuItems(false);
setTitle(false);
TrackRecordingServiceConnectionUtils.stop(this, trackRecordingServiceConnection);
TrackRecordingServiceConnectionUtils.stop(this, trackRecordingServiceConnection, true);
return true;
case R.id.track_detail_insert_marker:
MarkerAddDialogFragment.newInstance(trackId)
.show(getSupportFragmentManager(), MarkerAddDialogFragment.MARKER_ADD_DIALOG_TAG);
intent = IntentUtils.newIntent(this, MarkerEditActivity.class)
.putExtra(MarkerEditActivity.EXTRA_TRACK_ID, trackId);
startActivity(intent);
return true;
case R.id.track_detail_play:
if (isEarthInstalled()) {
@@ -349,7 +346,7 @@ public class TrackDetailActivity extends AbstractMyTracksActivity {
if (event.getAction() == MotionEvent.ACTION_DOWN) {
if (TrackRecordingServiceConnectionUtils.isRecording(this, trackRecordingServiceConnection)) {
TrackRecordingServiceConnectionUtils.addMarker(
this, trackRecordingServiceConnection, WaypointCreationRequest.DEFAULT_STATISTICS);
this, trackRecordingServiceConnection, WaypointCreationRequest.DEFAULT_WAYPOINT);
return true;
}
}
@@ -455,12 +452,6 @@ public class TrackDetailActivity extends AbstractMyTracksActivity {
if (saveMenuItem != null) {
saveMenuItem.setVisible(!isRecording);
}
if (editMenuItem != null) {
editMenuItem.setVisible(!isRecording);
}
if (deleteMenuItem != null) {
deleteMenuItem.setVisible(!isRecording);
}
}
/**
@@ -492,4 +483,9 @@ public class TrackDetailActivity extends AbstractMyTracksActivity {
}
return false;
}
@Override
public TrackRecordingServiceConnection getTrackRecordingServiceConnection() {
return trackRecordingServiceConnection;
}
}
@@ -89,7 +89,7 @@ public class TrackEditActivity extends AbstractMyTracksActivity {
track.setCategory(activityType.getText().toString());
track.setDescription(description.getText().toString());
myTracksProviderUtils.updateTrack(track);
finish();
finish();
}
});
@@ -102,7 +102,7 @@ public class TrackEditActivity extends AbstractMyTracksActivity {
cancel.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
finish();
finish();
}
});
cancel.setVisibility(View.VISIBLE);
@@ -20,6 +20,7 @@ import com.google.android.apps.mytracks.content.TracksColumns;
import com.google.android.apps.mytracks.fragments.CheckUnitsDialogFragment;
import com.google.android.apps.mytracks.fragments.DeleteAllTrackDialogFragment;
import com.google.android.apps.mytracks.fragments.DeleteOneTrackDialogFragment;
import com.google.android.apps.mytracks.fragments.DeleteOneTrackDialogFragment.DeleteOneTrackCaller;
import com.google.android.apps.mytracks.fragments.EulaDialogFragment;
import com.google.android.apps.mytracks.fragments.WelcomeDialogFragment;
import com.google.android.apps.mytracks.io.file.TrackWriterFactory.TrackFileFormat;
@@ -68,7 +69,7 @@ import android.widget.Toast;
*
* @author Leif Hendrik Wilden
*/
public class TrackListActivity extends FragmentActivity {
public class TrackListActivity extends FragmentActivity implements DeleteOneTrackCaller {
private static final String TAG = TrackListActivity.class.getSimpleName();
@@ -217,20 +218,20 @@ public class TrackListActivity extends FragmentActivity {
boolean isRecording = cursor.getLong(idIndex) == recordingTrackId;
String name = cursor.getString(nameIndex);
int iconId = isRecording ? R.drawable.menu_record_track : R.drawable.track;
String iconContentDescription = getString(isRecording ? R.string.icon_recording
: R.string.icon_track);
String category = cursor.getString(categoryIndex);
String totalTime = isRecording
? null : StringUtils.formatElapsedTime(cursor.getLong(timeIndex));
String totalDistance = isRecording ? null : StringUtils.formatDistance(
TrackListActivity.this, cursor.getDouble(distanceIndex), metricUnits);
String startTime =
StringUtils.formatDateTime(TrackListActivity.this, cursor.getLong(startIndex));
if (startTime.equals(name)) {
startTime = null;
}
long startTime = cursor.getLong(startIndex);
String description = cursor.getString(descriptionIndex);
ListItemUtils.setListItem(view,
ListItemUtils.setListItem(TrackListActivity.this,
view,
name,
iconId,
iconContentDescription,
category,
totalTime,
totalDistance,
@@ -388,7 +389,7 @@ public class TrackListActivity extends FragmentActivity {
return true;
case R.id.track_list_stop_recording:
updateMenuItems(false);
TrackRecordingServiceConnectionUtils.stop(this, trackRecordingServiceConnection);
TrackRecordingServiceConnectionUtils.stop(this, trackRecordingServiceConnection, true);
return true;
case R.id.track_list_search:
return ApiAdapterFactory.getApiAdapter().handleSearchMenuSelection(this);
@@ -506,4 +507,9 @@ public class TrackListActivity extends FragmentActivity {
}
return super.onKeyUp(keyCode, event);
}
@Override
public TrackRecordingServiceConnection getTrackRecordingServiceConnection() {
return trackRecordingServiceConnection;
}
}
@@ -18,11 +18,16 @@ package com.google.android.apps.mytracks.fragments;
import com.google.android.apps.mytracks.TrackListActivity;
import com.google.android.apps.mytracks.content.MyTracksProviderUtils;
import com.google.android.apps.mytracks.services.TrackRecordingServiceConnection;
import com.google.android.apps.mytracks.util.DialogUtils;
import com.google.android.apps.mytracks.util.IntentUtils;
import com.google.android.apps.mytracks.util.PreferencesUtils;
import com.google.android.apps.mytracks.util.TrackRecordingServiceConnectionUtils;
import com.google.android.maps.mytracks.R;
import android.app.Activity;
import android.app.Dialog;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.os.Bundle;
@@ -30,7 +35,7 @@ import android.support.v4.app.DialogFragment;
/**
* A DialogFragment to delete one track.
*
*
* @author Jimmy Shih
*/
public class DeleteOneTrackDialogFragment extends DialogFragment {
@@ -38,6 +43,17 @@ public class DeleteOneTrackDialogFragment extends DialogFragment {
public static final String DELETE_ONE_TRACK_DIALOG_TAG = "deleteOneTrackDialog";
private static final String KEY_TRACK_ID = "trackId";
/**
* Interface for caller of this dialog fragment.
*
* @author Jimmy Shih
*/
public interface DeleteOneTrackCaller {
public TrackRecordingServiceConnection getTrackRecordingServiceConnection();
}
private DeleteOneTrackCaller caller;
public static DeleteOneTrackDialogFragment newInstance(long trackId) {
Bundle bundle = new Bundle();
bundle.putLong(KEY_TRACK_ID, trackId);
@@ -47,17 +63,32 @@ public class DeleteOneTrackDialogFragment extends DialogFragment {
return deleteOneTrackDialogFragment;
}
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);
try {
caller = (DeleteOneTrackCaller) activity;
} catch (ClassCastException e) {
throw new ClassCastException(activity.toString() + " must implement DeleteOneTrackCaller");
}
}
@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
return DialogUtils.createConfirmationDialog(getActivity(),
R.string.track_detail_delete_confirm_message, new DialogInterface.OnClickListener() {
@Override
@Override
public void onClick(DialogInterface dialog, int which) {
MyTracksProviderUtils.Factory.get(getActivity())
.deleteTrack(getArguments().getLong(KEY_TRACK_ID));
Intent intent = IntentUtils.newIntent(getActivity(), TrackListActivity.class);
long trackId = getArguments().getLong(KEY_TRACK_ID);
Context context = getActivity();
if (trackId == PreferencesUtils.getLong(context, R.string.recording_track_id_key)) {
TrackRecordingServiceConnectionUtils.stop(
context, caller.getTrackRecordingServiceConnection(), false);
}
MyTracksProviderUtils.Factory.get(context).deleteTrack(trackId);
Intent intent = IntentUtils.newIntent(context, TrackListActivity.class);
startActivity(intent);
// Close the activity since its content can change after delete.
// Close the activity since its content can change after delete
getActivity().finish();
}
});
@@ -1,122 +0,0 @@
/*
* Copyright 2012 Google Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License"); you may not
* use this file except in compliance with the License. You may obtain a copy of
* the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations under
* the License.
*/
package com.google.android.apps.mytracks.fragments;
import com.google.android.apps.mytracks.MarkerEditActivity;
import com.google.android.apps.mytracks.content.WaypointCreationRequest;
import com.google.android.apps.mytracks.services.TrackRecordingServiceConnection;
import com.google.android.apps.mytracks.util.IntentUtils;
import com.google.android.apps.mytracks.util.PreferencesUtils;
import com.google.android.apps.mytracks.util.TrackRecordingServiceConnectionUtils;
import com.google.android.maps.mytracks.R;
import android.app.AlertDialog;
import android.app.Dialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.os.Bundle;
import android.support.v4.app.DialogFragment;
import android.view.View;
import android.widget.Button;
import android.widget.RadioGroup;
/**
* A DialogFragment to add a marker.
*
* @author Jimmy Shih
*/
public class MarkerAddDialogFragment extends DialogFragment {
public static final String MARKER_ADD_DIALOG_TAG = "markerAddDialog";
private static final String KEY_TRACK_ID = "trackId";
private TrackRecordingServiceConnection trackRecordingServiceConnection;
private RadioGroup radioGroup;
private Button moreOptions;
/**
* Creates a new instance of {@link MarkerAddDialogFragment}.
*
* @param trackId the track id
*/
public static MarkerAddDialogFragment newInstance(long trackId) {
Bundle bundle = new Bundle();
bundle.putLong(KEY_TRACK_ID, trackId);
MarkerAddDialogFragment markerAddDialogFragment = new MarkerAddDialogFragment();
markerAddDialogFragment.setArguments(bundle);
return markerAddDialogFragment;
}
@Override
public void onCreate(Bundle arg0) {
super.onCreate(arg0);
trackRecordingServiceConnection = new TrackRecordingServiceConnection(getActivity(), null);
}
@Override
public void onResume() {
super.onResume();
TrackRecordingServiceConnectionUtils.resume(getActivity(), trackRecordingServiceConnection);
}
@Override
public void onDestroy() {
super.onDestroy();
trackRecordingServiceConnection.unbind();
}
@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
View view = getActivity().getLayoutInflater().inflate(R.layout.marker_add, null);
radioGroup = (RadioGroup) view.findViewById(R.id.marker_add_type);
moreOptions = (Button) view.findViewById(R.id.marker_add_more_options);
moreOptions.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
boolean statisticsMarker = radioGroup.getCheckedRadioButtonId()
== R.id.marker_add_statistics;
Intent intent = IntentUtils.newIntent(getActivity(), MarkerEditActivity.class);
intent.putExtra(MarkerEditActivity.EXTRA_TRACK_ID, getArguments().getLong(KEY_TRACK_ID));
intent.putExtra(MarkerEditActivity.EXTRA_STATISTICS_MARKER, statisticsMarker);
startActivity(intent);
dismiss();
}
});
boolean pickStatisticsMarker = PreferencesUtils.getBoolean(getActivity(),
R.string.pick_statistics_marker_key, PreferencesUtils.PICK_STATISTICS_MARKER_DEFAULT);
radioGroup.check(pickStatisticsMarker ? R.id.marker_add_statistics : R.id.marker_add_waypoint);
return new AlertDialog.Builder(getActivity())
.setNegativeButton(R.string.generic_cancel, null)
.setPositiveButton(R.string.generic_add, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
boolean statisticsMarker = radioGroup.getCheckedRadioButtonId()
== R.id.marker_add_statistics;
PreferencesUtils.setBoolean(
getActivity(), R.string.pick_statistics_marker_key, statisticsMarker);
TrackRecordingServiceConnectionUtils.addMarker(getActivity(),
trackRecordingServiceConnection,
statisticsMarker ? WaypointCreationRequest.DEFAULT_STATISTICS
: WaypointCreationRequest.DEFAULT_WAYPOINT);
}
})
.setTitle(R.string.menu_insert_marker)
.setView(view)
.create();
}
}
@@ -102,7 +102,7 @@ public class CsvTrackWriter implements TrackFormatWriter {
@Override
public void writeBeginWaypoints() {
writeCommaSeparatedLine(context.getString(R.string.generic_name),
context.getString(R.string.marker_edit_waypoint_marker_type_hint),
context.getString(R.string.marker_edit_marker_type_hint),
context.getString(R.string.generic_description),
context.getString(R.string.description_location_latitude),
context.getString(R.string.description_location_longitude),
@@ -30,6 +30,7 @@ import com.google.android.apps.mytracks.content.Track;
import com.google.android.apps.mytracks.content.TracksColumns;
import com.google.android.apps.mytracks.content.Waypoint;
import com.google.android.apps.mytracks.content.WaypointCreationRequest;
import com.google.android.apps.mytracks.content.WaypointCreationRequest.WaypointType;
import com.google.android.apps.mytracks.content.WaypointsColumns;
import com.google.android.apps.mytracks.services.sensors.SensorManager;
import com.google.android.apps.mytracks.services.sensors.SensorManagerFactory;
@@ -589,7 +590,7 @@ public class TrackRecordingService extends Service {
statsBuilder.setMinRecordingDistance(minRecordingDistance);
waypointStatsBuilder = new TripStatisticsBuilder(startTime);
waypointStatsBuilder.setMinRecordingDistance(minRecordingDistance);
currentWaypointId = insertWaypoint(WaypointCreationRequest.DEFAULT_STATISTICS);
currentWaypointId = insertWaypoint(WaypointCreationRequest.DEFAULT_START_TRACK);
length = 0;
showNotification();
registerLocationListener();
@@ -916,37 +917,33 @@ public class TrackRecordingService extends Service {
public long insertWaypoint(WaypointCreationRequest request) {
if (!isRecording()) {
throw new IllegalStateException(
"Unable to insert waypoint marker while not recording!");
throw new IllegalStateException("Unable to insert marker while not recording!");
}
if (request == null) {
request = WaypointCreationRequest.DEFAULT_WAYPOINT;
}
Waypoint wpt = new Waypoint();
switch (request.getType()) {
case WAYPOINT:
buildWaypointMarker(wpt, request);
break;
case STATISTICS:
buildStatisticsMarker(wpt, request);
break;
}
wpt.setTrackId(recordingTrackId);
wpt.setLength(length);
if (lastLocation == null
|| statsBuilder == null || statsBuilder.getStatistics() == null) {
// A null location is ok, and expected on track start.
// Make it an impossible location.
Location l = new Location("");
l.setLatitude(100);
l.setLongitude(180);
wpt.setLocation(l);
Waypoint waypoint = new Waypoint();
if (request.getType() == WaypointType.WAYPOINT) {
buildWaypointMarker(waypoint, request);
} else {
wpt.setLocation(lastLocation);
wpt.setDuration(lastLocation.getTime()
- statsBuilder.getStatistics().getStartTime());
buildStatisticsMarker(waypoint, request);
}
Uri uri = providerUtils.insertWaypoint(wpt);
waypoint.setTrackId(recordingTrackId);
waypoint.setLength(length);
if (lastLocation == null || statsBuilder == null || statsBuilder.getStatistics() == null) {
if (!request.isTrackStatistics()) {
return -1L;
}
/*
* For track statistics, a null location is OK. Make it an impossible
* location.
*/
Location location = new Location("");
location.setLatitude(100);
location.setLongitude(180);
waypoint.setLocation(location);
} else {
waypoint.setLocation(lastLocation);
waypoint.setDuration(lastLocation.getTime() - statsBuilder.getStatistics().getStartTime());
}
Uri uri = providerUtils.insertWaypoint(waypoint);
return Long.parseLong(uri.getLastPathSegment());
}
@@ -963,7 +960,7 @@ public class TrackRecordingService extends Service {
} else {
int nextMarkerNumber = providerUtils.getNextMarkerNumber(recordingTrackId, false);
name = nextMarkerNumber == -1 ? getString(R.string.marker_type_waypoint)
: getString(R.string.marker_waypoint_name_format, nextMarkerNumber);
: getString(R.string.marker_name_format, nextMarkerNumber);
}
wpt.setName(name);
if (request.getCategory() != null) {
@@ -18,7 +18,9 @@ package com.google.android.apps.mytracks.util;
import com.google.android.maps.mytracks.R;
import android.content.Context;
import android.view.View;
import android.widget.ImageView;
import android.widget.TextView;
/**
@@ -33,26 +35,32 @@ public class ListItemUtils {
/**
* Sets a list item.
*
* @param context the context
* @param view the list item view
* @param name the name value
* @param iconId the icon id
* @param iconContentDescription the icon content description
* @param category the category value
* @param totalTime the total time value
* @param totalDistance the total distance value
* @param startTime the start time value
* @param description the description value
*/
public static void setListItem(View view,
public static void setListItem(Context context, View view,
String name,
int iconId,
String iconContentDescription,
String category,
String totalTime,
String totalDistance,
String startTime,
long startTime,
String description) {
ImageView iconImageView = (ImageView) view.findViewById(R.id.list_item_icon);
iconImageView.setImageResource(iconId);
iconImageView.setContentDescription(iconContentDescription);
TextView nameTextView = (TextView) view.findViewById(R.id.list_item_name);
nameTextView.setText(name);
nameTextView.setCompoundDrawablesWithIntrinsicBounds(iconId, 0, 0, 0);
TextView categoryTextView = (TextView) view.findViewById(R.id.list_item_category);
setTextView(categoryTextView, category);
@@ -63,8 +71,11 @@ public class ListItemUtils {
TextView totalDistanceTextView = (TextView) view.findViewById(R.id.list_item_total_distance);
setTextView(totalDistanceTextView, totalDistance);
String startTimeDisplay = startTime == 0L
|| StringUtils.formatDateTime(context, startTime).equals(name) ? null
: StringUtils.formatRelativeDateTime(context, startTime);
TextView startTimeTextView = (TextView) view.findViewById(R.id.list_item_start_time);
setTextView(startTimeTextView, startTime);
setTextView(startTimeTextView, startTimeDisplay);
TextView descriptionTextView = (TextView) view.findViewById(R.id.list_item_description);
setTextView(descriptionTextView, description);
@@ -66,7 +66,6 @@ public class PreferencesUtils {
public static final int PERIODIC_TASK_OFF = 0;
public static final boolean PICK_EXISTING_MAP_DEFAULT = false;
public static final boolean PICK_STATISTICS_MARKER_DEFAULT = true;
public static final String PREFERRED_ACCOUNT_DEFAULT = "";
public static final long RECORDING_TRACK_ID_DEFAULT = -1L;
public static final boolean REPORT_SPEED_DEFAULT = true;
@@ -23,6 +23,7 @@ import android.text.format.DateUtils;
import java.text.ParsePosition;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.TimeZone;
import java.util.regex.Matcher;
@@ -42,7 +43,6 @@ public class StringUtils {
"yyyy-MM-dd'T'HH:mm:ss");
private static final Pattern ISO_8601_EXTRAS = Pattern.compile(
"^(\\.\\d+)?(?:Z|([+-])(\\d{2}):(\\d{2}))?$");
static {
ISO_8601_DATE_TIME_FORMAT.setTimeZone(TimeZone.getTimeZone("UTC"));
ISO_8601_BASE.setTimeZone(TimeZone.getTimeZone("UTC"));
@@ -50,25 +50,31 @@ public class StringUtils {
private StringUtils() {}
/**
* Formats the time based on user's phone date/time preferences.
*
* @param context the context
* @param time the time in milliseconds
*/
public static String formatTime(Context context, long time) {
return android.text.format.DateFormat.getTimeFormat(context).format(time);
}
/**
* Formats the date and time based on user's phone date/time preferences.
*
*
* @param context the context
* @param time the time in milliseconds
*/
public static String formatDateTime(Context context, long time) {
return android.text.format.DateFormat.getDateFormat(context).format(time) + " "
+ formatTime(context, time);
+ DateUtils.formatDateTime(context, time, DateUtils.FORMAT_SHOW_TIME).toString();
}
/**
* Formats the relative date and time based on user's phone date/time preferences.
*
* @param context the context
* @param time the time in milliseconds
*/
public static String formatRelativeDateTime(Context context, long time) {
long now = Calendar.getInstance().getTimeInMillis();
if (now - time > DateUtils.WEEK_IN_MILLIS) {
return formatDateTime(context, time);
} else {
return DateUtils.getRelativeTimeSpanString(time, now, DateUtils.MINUTE_IN_MILLIS,
DateUtils.FORMAT_ABBREV_RELATIVE).toString();
}
}
/**
@@ -96,24 +96,30 @@ public class TrackRecordingServiceConnectionUtils {
* @param context the context
* @param trackRecordingServiceConnection the track recording service
* connection
* @param showEditor true to show the editor
*/
public static void stop(
Context context, TrackRecordingServiceConnection trackRecordingServiceConnection) {
public static void stop(Context context,
TrackRecordingServiceConnection trackRecordingServiceConnection, boolean showEditor) {
ITrackRecordingService trackRecordingService = trackRecordingServiceConnection
.getServiceIfBound();
if (trackRecordingService != null) {
try {
/*
* Need to remember the recordingTrackId before calling endCurrentTrack.
* endCurrentTrack sets the value to -1L.
*/
long recordingTrackId = PreferencesUtils.getLong(context, R.string.recording_track_id_key);
trackRecordingService.endCurrentTrack();
if (recordingTrackId != PreferencesUtils.RECORDING_TRACK_ID_DEFAULT) {
Intent intent = IntentUtils.newIntent(context, TrackEditActivity.class)
.putExtra(TrackEditActivity.EXTRA_TRACK_ID, recordingTrackId)
.putExtra(TrackEditActivity.EXTRA_NEW_TRACK, true);
context.startActivity(intent);
if (showEditor) {
/*
* Need to remember the recordingTrackId before calling
* endCurrentTrack. endCurrentTrack sets the value to -1L.
*/
long recordingTrackId = PreferencesUtils.getLong(
context, R.string.recording_track_id_key);
trackRecordingService.endCurrentTrack();
if (recordingTrackId != PreferencesUtils.RECORDING_TRACK_ID_DEFAULT) {
Intent intent = IntentUtils.newIntent(context, TrackEditActivity.class)
.putExtra(TrackEditActivity.EXTRA_TRACK_ID, recordingTrackId)
.putExtra(TrackEditActivity.EXTRA_NEW_TRACK, true);
context.startActivity(intent);
}
} else {
trackRecordingService.endCurrentTrack();
}
} catch (Exception e) {
Log.e(TAG, "Unable to stop recording.", e);
@@ -20,34 +20,38 @@ import android.os.Parcelable;
/**
* A request for the service to create a waypoint at the current location.
*
*
* @author Sandor Dornbush
*/
public class WaypointCreationRequest implements Parcelable {
public static enum WaypointType {
WAYPOINT,
STATISTICS;
WAYPOINT, STATISTICS;
}
private WaypointType type;
// true if this marker contains the track statistics
private boolean isTrackStatistics;
private String name;
private String category;
private String description;
private String iconUrl;
public final static WaypointCreationRequest DEFAULT_WAYPOINT =
new WaypointCreationRequest(WaypointType.WAYPOINT);
public final static WaypointCreationRequest DEFAULT_STATISTICS =
new WaypointCreationRequest(WaypointType.STATISTICS);
private WaypointCreationRequest(WaypointType type) {
this.type = type;
public final static WaypointCreationRequest DEFAULT_WAYPOINT = new WaypointCreationRequest(
WaypointType.WAYPOINT, false);
public final static WaypointCreationRequest DEFAULT_STATISTICS = new WaypointCreationRequest(
WaypointType.STATISTICS, false);
public final static WaypointCreationRequest DEFAULT_START_TRACK = new WaypointCreationRequest(
WaypointType.STATISTICS, true);
private WaypointCreationRequest(WaypointType type, boolean isTrackStatistics) {
this(type, isTrackStatistics, null, null, null, null);
}
public WaypointCreationRequest(WaypointType type, String name, String category,
String description, String iconUrl) {
public WaypointCreationRequest(WaypointType type, boolean isTrackStatistics, String name,
String category, String description, String iconUrl) {
this.type = type;
this.isTrackStatistics = isTrackStatistics;
this.name = name;
this.category = category;
this.description = description;
@@ -58,15 +62,13 @@ public class WaypointCreationRequest implements Parcelable {
@Override
public WaypointCreationRequest createFromParcel(Parcel source) {
int i = source.readInt();
if (i > WaypointType.values().length) {
throw new IllegalArgumentException("Could not find waypoint type: " + i);
}
WaypointCreationRequest request = new WaypointCreationRequest(WaypointType.values()[i]);
request.name = source.readString();
request.category = source.readString();
request.description = source.readString();
request.iconUrl = source.readString();
WaypointCreationRequest request = new WaypointCreationRequest(
WaypointType.values()[source.readInt()],
source.readByte() == 1,
source.readString(),
source.readString(),
source.readString(),
source.readString());
return request;
}
@@ -76,7 +78,7 @@ public class WaypointCreationRequest implements Parcelable {
}
public static final Creator CREATOR = new Creator();
@Override
public int describeContents() {
return 0;
@@ -85,16 +87,21 @@ public class WaypointCreationRequest implements Parcelable {
@Override
public void writeToParcel(Parcel parcel, int arg1) {
parcel.writeInt(type.ordinal());
parcel.writeByte((byte) (isTrackStatistics ? 1 : 0));
parcel.writeString(name);
parcel.writeString(category);
parcel.writeString(description);
parcel.writeString(iconUrl);
}
public WaypointType getType() {
return type;
}
public boolean isTrackStatistics() {
return isTrackStatistics;
}
public String getName() {
return name;
}
@@ -102,7 +109,7 @@ public class WaypointCreationRequest implements Parcelable {
public String getCategory() {
return category;
}
public String getDescription() {
return description;
}
@@ -35,19 +35,21 @@ public class WaypointCreationRequestTest extends AndroidTestCase {
p.setDataPosition(0);
WaypointCreationRequest copy = WaypointCreationRequest.CREATOR.createFromParcel(p);
assertEquals(original.getType(), copy.getType());
assertFalse(copy.isTrackStatistics());
assertNull(copy.getName());
assertNull(copy.getDescription());
assertNull(copy.getIconUrl());
}
public void testAllAttributesParceling() {
WaypointCreationRequest original =
new WaypointCreationRequest(WaypointType.WAYPOINT, "name", "category", "description", "img.png");
WaypointCreationRequest original = new WaypointCreationRequest(
WaypointType.WAYPOINT, false, "name", "category", "description", "img.png");
Parcel p = Parcel.obtain();
original.writeToParcel(p, 0);
p.setDataPosition(0);
WaypointCreationRequest copy = WaypointCreationRequest.CREATOR.createFromParcel(p);
assertEquals(original.getType(), copy.getType());
assertFalse(copy.isTrackStatistics());
assertEquals("name", copy.getName());
assertEquals("category", copy.getCategory());
assertEquals("description", copy.getDescription());
@@ -39,6 +39,7 @@ import android.location.Location;
import android.net.Uri;
import android.os.Bundle;
import android.os.IBinder;
import android.os.RemoteException;
import android.provider.Settings;
import android.test.RenamingDelegatingContext;
import android.test.ServiceTestCase;
@@ -494,6 +495,7 @@ public class TrackRecordingServiceTest extends ServiceTestCase<TestRecordingServ
ITrackRecordingService service = bindAndGetService(createStartIntent());
assertTrue(service.isRecording());
insertLocation(service);
assertEquals(1, service.insertWaypoint(WaypointCreationRequest.DEFAULT_STATISTICS));
assertEquals(2, service.insertWaypoint(WaypointCreationRequest.DEFAULT_STATISTICS));
@@ -530,12 +532,13 @@ public class TrackRecordingServiceTest extends ServiceTestCase<TestRecordingServ
ITrackRecordingService service = bindAndGetService(createStartIntent());
assertTrue(service.isRecording());
insertLocation(service);
assertEquals(1, service.insertWaypoint(WaypointCreationRequest.DEFAULT_WAYPOINT));
Waypoint wpt = providerUtils.getWaypoint(1);
assertEquals(getContext().getString(R.string.marker_waypoint_icon_url),
wpt.getIcon());
assertEquals(getContext().getString(R.string.marker_waypoint_name_format, 1), wpt.getName());
assertEquals(getContext().getString(R.string.marker_name_format, 1), wpt.getName());
assertEquals(Waypoint.TYPE_WAYPOINT, wpt.getType());
assertEquals(123L, wpt.getTrackId());
assertEquals(0.0, wpt.getLength());
@@ -742,4 +745,22 @@ public class TrackRecordingServiceTest extends ServiceTestCase<TestRecordingServ
assertTrue(tripStatistics.getStartTime() > 0);
assertTrue(tripStatistics.getStopTime() >= tripStatistics.getStartTime());
}
/**
* Inserts a location and waits for 100ms.
*
* @param trackRecordingService the track recording service
*/
private void insertLocation(ITrackRecordingService trackRecordingService)
throws RemoteException, InterruptedException {
Location location = new Location("gps");
location.setLongitude(35.0f);
location.setLatitude(45.0f);
location.setAccuracy(5);
location.setSpeed(10);
location.setTime(System.currentTimeMillis());
location.setBearing(3.0f);
trackRecordingService.recordLocation(location);
Thread.sleep(100);
}
}
@@ -17,7 +17,6 @@
package com.google.android.apps.mytracks.util;
import android.test.AndroidTestCase;
import android.text.format.DateFormat;
import java.util.GregorianCalendar;
import java.util.TimeZone;
@@ -29,23 +28,6 @@ import java.util.TimeZone;
*/
public class StringUtilsTest extends AndroidTestCase {
/**
* Tests {@link StringUtils#formatDateTime(android.content.Context, long)}.
*/
public void testFormatTime() {
assertEquals(DateFormat.getTimeFormat(getContext()).format(0L),
StringUtils.formatTime(getContext(), 0L));
}
/**
* Tests {@link StringUtils#formatDateTime(android.content.Context, long)}.
*/
public void testFormatDateTime() {
String expected = DateFormat.getDateFormat(getContext()).format(0L) + " "
+ DateFormat.getTimeFormat(getContext()).format(0L);
assertEquals(expected, StringUtils.formatDateTime(getContext(), 0L));
}
/**
* Tests {@link StringUtils#formatDateTimeIso8601(long)}.
*/