Fixed an exception in MyTracks (added isBound), moved resumeState from onStart to onCreate in TrackRecordingService and some minor refactoring.

This commit is contained in:
Bartlomiej Niechwiej
2010-10-03 23:28:12 -07:00
parent beee6af79d
commit dfe947f54d
3 changed files with 46 additions and 31 deletions
@@ -208,6 +208,11 @@ public class MyTracks extends TabActivity implements OnTouchListener,
} }
}; };
/**
* Whether {@link #serviceConnection} is bound or not.
*/
private boolean isBound = false;
/* /*
* Tabs/View navigation: * Tabs/View navigation:
*/ */
@@ -348,6 +353,13 @@ public class MyTracks extends TabActivity implements OnTouchListener,
} }
} }
@Override
protected void onDestroy() {
Log.d(MyTracksConstants.TAG, "MyTracks.onDestroy");
tryUnbindTrackRecordingService();
super.onDestroy();
}
@Override @Override
protected void onPause() { protected void onPause() {
// Called when activity is going into the background, but has not (yet) been // Called when activity is going into the background, but has not (yet) been
@@ -370,6 +382,7 @@ public class MyTracks extends TabActivity implements OnTouchListener,
@Override @Override
protected void onStop() { protected void onStop() {
Log.d(MyTracksConstants.TAG, "MyTracks.onStop");
super.onStop(); super.onStop();
// Clean up any temporary GPX and KML files. // Clean up any temporary GPX and KML files.
cleanTmpDirectory("gpx"); cleanTmpDirectory("gpx");
@@ -1383,6 +1396,7 @@ public class MyTracks extends TabActivity implements OnTouchListener,
bindService(new Intent(this, TrackRecordingService.class), bindService(new Intent(this, TrackRecordingService.class),
serviceConnection, 0); serviceConnection, 0);
Log.d(MyTracksConstants.TAG, "MyTracks: ...bind finished!"); Log.d(MyTracksConstants.TAG, "MyTracks: ...bind finished!");
isBound = true;
} }
/** /**
@@ -1390,10 +1404,9 @@ public class MyTracks extends TabActivity implements OnTouchListener,
* case service is not registered anymore. * case service is not registered anymore.
*/ */
private void tryUnbindTrackRecordingService() { private void tryUnbindTrackRecordingService() {
// Do not attempt to unbind if there is already a pending unbind operation. if (isBound) {
if (trackRecordingService != null) {
Log.d(MyTracksConstants.TAG, Log.d(MyTracksConstants.TAG,
"MyTracks: Trying to unbind from track recording service..."); "MyTracks: Trying to unbind from track recording service...");
try { try {
unbindService(serviceConnection); unbindService(serviceConnection);
Log.d(MyTracksConstants.TAG, "MyTracks: ...unbind finished!"); Log.d(MyTracksConstants.TAG, "MyTracks: ...unbind finished!");
@@ -1401,6 +1414,7 @@ public class MyTracks extends TabActivity implements OnTouchListener,
Log.d(MyTracksConstants.TAG, Log.d(MyTracksConstants.TAG,
"MyTracks: Tried unbinding, but service was not registered.", e); "MyTracks: Tried unbinding, but service was not registered.", e);
} }
isBound = false;
} }
} }
@@ -19,7 +19,7 @@ package com.google.android.apps.mytracks.services;
import android.content.Context; import android.content.Context;
/** /**
* This class will periodically announce the user's trip statitics. This class * This class will periodically announce the user's trip statistics. This class
* is a wrapper for cupcake devices. * is a wrapper for cupcake devices.
* *
* @author Sandor Dornbush * @author Sandor Dornbush
@@ -153,6 +153,11 @@ public class TrackRecordingService extends Service implements LocationListener {
*/ */
private boolean isMoving = true; private boolean isMoving = true;
/**
* The most recent recording track.
*/
private Track recordingTrack;
/** /**
* Is the service currently recording a track? * Is the service currently recording a track?
*/ */
@@ -396,7 +401,7 @@ public class TrackRecordingService extends Service implements LocationListener {
TripStatistics stats = track.getStatistics(); TripStatistics stats = track.getStatistics();
statsBuilder = new TripStatisticsBuilder(); statsBuilder = new TripStatisticsBuilder();
statsBuilder.resumeAt(stats.getStartTime()); statsBuilder.resumeAt(stats.getStartTime());
setUpScheduler(false, true); setUpAnnouncer();
signalManager.restore(); signalManager.restore();
splitManager.restore(); splitManager.restore();
@@ -481,7 +486,7 @@ public class TrackRecordingService extends Service implements LocationListener {
} }
// At least one track must be available for appending points: // At least one track must be available for appending points:
Track recordingTrack = providerUtils.getTrack(recordingTrackId); recordingTrack = getRecordingTrack();
if (recordingTrack == null) { if (recordingTrack == null) {
Log.d(MyTracksConstants.TAG, Log.d(MyTracksConstants.TAG,
"Not recording. No track to append to available."); "Not recording. No track to append to available.");
@@ -496,8 +501,8 @@ public class TrackRecordingService extends Service implements LocationListener {
// Update the idle time if needed. // Update the idle time if needed.
locationListenerPolicy.updateIdleTime(statsBuilder.getIdleTime()); locationListenerPolicy.updateIdleTime(statsBuilder.getIdleTime());
if (currentRecordingInterval if (currentRecordingInterval !=
!= locationListenerPolicy.getDesiredPollingInterval()) { locationListenerPolicy.getDesiredPollingInterval()) {
registerLocationListener(); registerLocationListener();
} }
@@ -657,24 +662,29 @@ public class TrackRecordingService extends Service implements LocationListener {
* registered and spit out additional debugging info to the logs: * registered and spit out additional debugging info to the logs:
*/ */
timer.schedule(checkLocationListener, 1000 * 60 * 5, 1000 * 60); timer.schedule(checkLocationListener, 1000 * 60 * 5, 1000 * 60);
setUpScheduler(true, false);
// Try to restore previous recording state in case this service has been
// restarted by the system, which can sometimes happen.
recordingTrack = getRecordingTrack();
if (recordingTrack != null) {
restoreStats(recordingTrack);
isRecording = true;
showNotification();
}
} }
/** /**
* Creates an {@link Executer} and optionally schedules a periodic task. * Creates an {@link Executer} and schedules {@class SafeStatusAnnouncerTask}.
* @param createIfNecessary whether to create {@link #executer}, * The announcer requires a TTS service and user should have enabled
* if {@code null}. * the announcements, otherwise this method is no-op.
* @param scheduleTask whether to schedule a new task.
*/ */
private void setUpScheduler(boolean createIfNecessary, boolean scheduleTask) { private void setUpAnnouncer() {
if (mTTSAvailable && announcementFrequency != -1) { if (mTTSAvailable && announcementFrequency != -1) {
if (executer == null && createIfNecessary) { if (executer == null) {
SafeStatusAnnouncerTask announcer = new SafeStatusAnnouncerTask(this); SafeStatusAnnouncerTask announcer = new SafeStatusAnnouncerTask(this);
executer = new PeriodicTaskExecuter(announcer, this); executer = new PeriodicTaskExecuter(announcer, this);
} }
if (scheduleTask && executer != null) { executer.scheduleTask(announcementFrequency * 60000);
executer.scheduleTask(announcementFrequency * 60000);
}
} }
} }
@@ -730,16 +740,13 @@ public class TrackRecordingService extends Service implements LocationListener {
Log.d(MyTracksConstants.TAG, Log.d(MyTracksConstants.TAG,
"TrackRecordingService.handleStartCommand: " + startId); "TrackRecordingService.handleStartCommand: " + startId);
// Load previous track.
Track track = getRecordingTrack();
// Check if called on phone reboot with resume intent. // Check if called on phone reboot with resume intent.
if (intent != null && if (intent != null &&
intent.getBooleanExtra(RESUME_TRACK_EXTRA_NAME, false)) { intent.getBooleanExtra(RESUME_TRACK_EXTRA_NAME, false)) {
Log.d(MyTracksConstants.TAG, "TrackRecordingService: requested resume"); Log.d(MyTracksConstants.TAG, "TrackRecordingService: requested resume");
// Make sure that the current track exists and is fresh enough. // Make sure that the current track exists and is fresh enough.
// Note: Sometimes we may get null intent, so avoid a NPE. // Note: Sometimes we may get null intent, so avoid a NPE.
if (track == null || !maybeResumeTrack(track)) { if (recordingTrack == null || !shouldResumeTrack(recordingTrack)) {
Log.i(MyTracksConstants.TAG, Log.i(MyTracksConstants.TAG,
"TrackRecordingService: Not resuming because the previous track " "TrackRecordingService: Not resuming because the previous track "
+ "doesn't exist or is too old"); + "doesn't exist or is too old");
@@ -748,15 +755,9 @@ public class TrackRecordingService extends Service implements LocationListener {
} }
Log.i(MyTracksConstants.TAG, "TrackRecordingService: resuming"); Log.i(MyTracksConstants.TAG, "TrackRecordingService: resuming");
} }
if (track != null) {
restoreStats(track);
isRecording = true;
showNotification();
}
} }
private boolean maybeResumeTrack(Track track) { private boolean shouldResumeTrack(Track track) {
Log.d(MyTracksConstants.TAG, Log.d(MyTracksConstants.TAG,
"maybeResumeTrack: autoResumeTrackTimeout = " + autoResumeTrackTimeout); "maybeResumeTrack: autoResumeTrackTimeout = " + autoResumeTrackTimeout);
@@ -873,7 +874,7 @@ public class TrackRecordingService extends Service implements LocationListener {
isMoving = true; isMoving = true;
statsBuilder = new TripStatisticsBuilder(); statsBuilder = new TripStatisticsBuilder();
statsBuilder.resumeAt(startTime); statsBuilder.resumeAt(startTime);
setUpScheduler(false, true); setUpAnnouncer();
length = 0; length = 0;
showNotification(); showNotification();
registerLocationListener(); registerLocationListener();
@@ -979,7 +980,7 @@ public class TrackRecordingService extends Service implements LocationListener {
executer = null; executer = null;
} }
} else { } else {
setUpScheduler(true, true); setUpAnnouncer();
} }
} }
} }