forked from upstream-mirrors/OpenTracks
Cutting service binding and preferences dependencies to the MyTracks singleton.
This commit is contained in:
@@ -23,26 +23,23 @@ import com.google.android.apps.mytracks.content.TracksColumns;
|
|||||||
import com.google.android.apps.mytracks.content.WaypointCreationRequest;
|
import com.google.android.apps.mytracks.content.WaypointCreationRequest;
|
||||||
import com.google.android.apps.mytracks.io.file.TempFileCleaner;
|
import com.google.android.apps.mytracks.io.file.TempFileCleaner;
|
||||||
import com.google.android.apps.mytracks.services.ITrackRecordingService;
|
import com.google.android.apps.mytracks.services.ITrackRecordingService;
|
||||||
import com.google.android.apps.mytracks.services.TrackRecordingService;
|
import com.google.android.apps.mytracks.services.TrackRecordingServiceBinder;
|
||||||
import com.google.android.apps.mytracks.services.tasks.StatusAnnouncerFactory;
|
import com.google.android.apps.mytracks.services.tasks.StatusAnnouncerFactory;
|
||||||
import com.google.android.apps.mytracks.util.ApiFeatures;
|
import com.google.android.apps.mytracks.util.ApiFeatures;
|
||||||
import com.google.android.apps.mytracks.util.UriUtils;
|
|
||||||
import com.google.android.apps.mytracks.util.SystemUtils;
|
import com.google.android.apps.mytracks.util.SystemUtils;
|
||||||
|
import com.google.android.apps.mytracks.util.UriUtils;
|
||||||
import com.google.android.maps.mytracks.R;
|
import com.google.android.maps.mytracks.R;
|
||||||
|
|
||||||
import android.app.Activity;
|
import android.app.Activity;
|
||||||
import android.app.AlertDialog;
|
import android.app.AlertDialog;
|
||||||
import android.app.TabActivity;
|
import android.app.TabActivity;
|
||||||
import android.content.ComponentName;
|
|
||||||
import android.content.ContentUris;
|
import android.content.ContentUris;
|
||||||
import android.content.DialogInterface;
|
import android.content.DialogInterface;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.content.ServiceConnection;
|
|
||||||
import android.content.SharedPreferences;
|
import android.content.SharedPreferences;
|
||||||
import android.content.res.Resources;
|
import android.content.res.Resources;
|
||||||
import android.net.Uri;
|
import android.net.Uri;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.os.IBinder;
|
|
||||||
import android.os.RemoteException;
|
import android.os.RemoteException;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
import android.view.Menu;
|
import android.view.Menu;
|
||||||
@@ -60,6 +57,7 @@ import android.widget.Toast;
|
|||||||
* The super activity that embeds our sub activities.
|
* The super activity that embeds our sub activities.
|
||||||
*
|
*
|
||||||
* @author Leif Hendrik Wilden
|
* @author Leif Hendrik Wilden
|
||||||
|
* @author Rodrigo Damazio
|
||||||
*/
|
*/
|
||||||
public class MyTracks extends TabActivity implements OnTouchListener {
|
public class MyTracks extends TabActivity implements OnTouchListener {
|
||||||
private TrackDataHub dataHub;
|
private TrackDataHub dataHub;
|
||||||
@@ -80,48 +78,12 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
*/
|
*/
|
||||||
private boolean startNewTrackRequested = false;
|
private boolean startNewTrackRequested = false;
|
||||||
|
|
||||||
private ITrackRecordingService trackRecordingService;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Utilities to deal with the database.
|
* Utilities to deal with the database.
|
||||||
*/
|
*/
|
||||||
private MyTracksProviderUtils providerUtils;
|
private MyTracksProviderUtils providerUtils;
|
||||||
|
|
||||||
private SharedPreferences sharedPreferences;
|
private TrackRecordingServiceBinder serviceBinder;
|
||||||
|
|
||||||
/**
|
|
||||||
* The connection to the track recording service.
|
|
||||||
*/
|
|
||||||
private final ServiceConnection serviceConnection = new ServiceConnection() {
|
|
||||||
@Override
|
|
||||||
public void onServiceConnected(ComponentName className, IBinder service) {
|
|
||||||
Log.d(Constants.TAG, "MyTracks: Service now connected.");
|
|
||||||
// Delay setting the service until we are done with initialization.
|
|
||||||
ITrackRecordingService trackRecordingService =
|
|
||||||
ITrackRecordingService.Stub.asInterface(service);
|
|
||||||
try {
|
|
||||||
// TODO: Send a start service intent and broadcast service started
|
|
||||||
// message to avoid the hack below and a race condition.
|
|
||||||
if (startNewTrackRequested) {
|
|
||||||
startNewTrackRequested = false;
|
|
||||||
startRecordingNewTrack(trackRecordingService);
|
|
||||||
}
|
|
||||||
} finally {
|
|
||||||
MyTracks.this.trackRecordingService = trackRecordingService;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onServiceDisconnected(ComponentName className) {
|
|
||||||
Log.d(TAG, "MyTracks: Service now disconnected.");
|
|
||||||
trackRecordingService = null;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Whether {@link #serviceConnection} is bound or not.
|
|
||||||
*/
|
|
||||||
private boolean isBound = false;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Tabs/View navigation:
|
* Tabs/View navigation:
|
||||||
@@ -135,6 +97,18 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
private final Runnable serviceBindCallback = new Runnable() {
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
synchronized (serviceBinder) {
|
||||||
|
ITrackRecordingService service = serviceBinder.getServiceIfBound();
|
||||||
|
if (startNewTrackRequested && service != null) {
|
||||||
|
startRecordingNewTrack(service);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Checks whether we have a track recording session in progress.
|
* Checks whether we have a track recording session in progress.
|
||||||
* In some cases, when the service has crashed or has been restarted
|
* In some cases, when the service has crashed or has been restarted
|
||||||
@@ -145,6 +119,7 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
* based on settings from the shared preferences.
|
* based on settings from the shared preferences.
|
||||||
*/
|
*/
|
||||||
public boolean isRecording() {
|
public boolean isRecording() {
|
||||||
|
ITrackRecordingService trackRecordingService = serviceBinder.getServiceIfBound();
|
||||||
if (trackRecordingService == null) {
|
if (trackRecordingService == null) {
|
||||||
// Fall back to alternative check method.
|
// Fall back to alternative check method.
|
||||||
return dataHub.isRecording();
|
return dataHub.isRecording();
|
||||||
@@ -177,10 +152,10 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
providerUtils = MyTracksProviderUtils.Factory.get(this);
|
providerUtils = MyTracksProviderUtils.Factory.get(this);
|
||||||
sharedPreferences = getSharedPreferences(Constants.SETTINGS_NAME, 0);
|
dataHub = new TrackDataHub(this, providerUtils);
|
||||||
dataHub = new TrackDataHub(this, sharedPreferences, providerUtils);
|
|
||||||
menuManager = new MenuManager(this);
|
menuManager = new MenuManager(this);
|
||||||
dialogManager = new DialogManager(this);
|
dialogManager = new DialogManager(this);
|
||||||
|
serviceBinder = TrackRecordingServiceBinder.getInstance(this);
|
||||||
|
|
||||||
// The volume we want to control is the Text-To-Speech volume
|
// The volume we want to control is the Text-To-Speech volume
|
||||||
int volumeStream =
|
int volumeStream =
|
||||||
@@ -230,7 +205,6 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
|
|
||||||
dataHub.destroy();
|
dataHub.destroy();
|
||||||
|
|
||||||
tryUnbindTrackRecordingService();
|
|
||||||
super.onDestroy();
|
super.onDestroy();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -250,7 +224,7 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
// 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
|
||||||
// killed. Shouldn't block longer than approx. 2 seconds.
|
// killed. Shouldn't block longer than approx. 2 seconds.
|
||||||
Log.d(TAG, "MyTracks.onPause");
|
Log.d(TAG, "MyTracks.onPause");
|
||||||
tryUnbindTrackRecordingService();
|
serviceBinder.unbindService();
|
||||||
super.onPause();
|
super.onPause();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -259,7 +233,7 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
// Called when the current activity is being displayed or re-displayed
|
// Called when the current activity is being displayed or re-displayed
|
||||||
// to the user.
|
// to the user.
|
||||||
Log.d(TAG, "MyTracks.onResume");
|
Log.d(TAG, "MyTracks.onResume");
|
||||||
tryBindTrackRecordingService();
|
serviceBinder.bindService(serviceBindCallback);
|
||||||
super.onResume();
|
super.onResume();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -271,8 +245,7 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
|
|
||||||
// Ensure that service is running if we're supposed to be recording
|
// Ensure that service is running if we're supposed to be recording
|
||||||
if (dataHub.isRecording()) {
|
if (dataHub.isRecording()) {
|
||||||
Intent startIntent = new Intent(this, TrackRecordingService.class);
|
serviceBinder.startService();
|
||||||
startService(startIntent);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Intent intent = getIntent();
|
Intent intent = getIntent();
|
||||||
@@ -445,6 +418,7 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
* @throws RemoteException If the call on the service failed.
|
* @throws RemoteException If the call on the service failed.
|
||||||
*/
|
*/
|
||||||
public long insertWaypoint(WaypointCreationRequest request) throws RemoteException {
|
public long insertWaypoint(WaypointCreationRequest request) throws RemoteException {
|
||||||
|
ITrackRecordingService trackRecordingService = serviceBinder.getServiceIfBound();
|
||||||
if (trackRecordingService == null) {
|
if (trackRecordingService == null) {
|
||||||
throw new IllegalStateException("The recording service is not bound.");
|
throw new IllegalStateException("The recording service is not bound.");
|
||||||
}
|
}
|
||||||
@@ -485,14 +459,16 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
* Starts the track recording service (if not already running) and binds to
|
* Starts the track recording service (if not already running) and binds to
|
||||||
* it. Starts recording a new track.
|
* it. Starts recording a new track.
|
||||||
*/
|
*/
|
||||||
public void startRecording() {
|
void startRecording() {
|
||||||
if (trackRecordingService == null) {
|
synchronized (serviceBinder) {
|
||||||
startNewTrackRequested = true;
|
startNewTrackRequested = true;
|
||||||
Intent startIntent = new Intent(this, TrackRecordingService.class);
|
serviceBinder.startService();
|
||||||
startService(startIntent);
|
|
||||||
tryBindTrackRecordingService();
|
// Binding was already requested before, it either already happened
|
||||||
} else {
|
// (in which case running the callback manually triggers the actual recording start)
|
||||||
startRecordingNewTrack(trackRecordingService);
|
// or it will happen in the future
|
||||||
|
// (in which case running the callback now will have no effect).
|
||||||
|
serviceBindCallback.run();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -501,8 +477,10 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
* "Stopped recording" and pop up the Track Details activity.
|
* "Stopped recording" and pop up the Track Details activity.
|
||||||
*/
|
*/
|
||||||
public void stopRecording() {
|
public void stopRecording() {
|
||||||
|
ITrackRecordingService trackRecordingService = serviceBinder.getServiceIfBound();
|
||||||
if (trackRecordingService != null) {
|
if (trackRecordingService != null) {
|
||||||
// Save the track id as the shared preference will overwrite the recording track id.
|
// Save the track id as the shared preference will overwrite the recording track id.
|
||||||
|
SharedPreferences sharedPreferences = getSharedPreferences(Constants.SETTINGS_NAME, 0);
|
||||||
long currentTrackId = sharedPreferences.getLong(getString(R.string.recording_track_key), -1);
|
long currentTrackId = sharedPreferences.getLong(getString(R.string.recording_track_key), -1);
|
||||||
try {
|
try {
|
||||||
trackRecordingService.endCurrentTrack();
|
trackRecordingService.endCurrentTrack();
|
||||||
@@ -519,14 +497,10 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
startActivity(intent);
|
startActivity(intent);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
tryUnbindTrackRecordingService();
|
|
||||||
try {
|
serviceBinder.stopService();
|
||||||
stopService(new Intent(MyTracks.this, TrackRecordingService.class));
|
|
||||||
} catch (SecurityException e) {
|
|
||||||
Log.e(TAG, "Encountered a security exception when trying to stop service.", e);
|
|
||||||
}
|
|
||||||
trackRecordingService = null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void clearSelectedTrack() {
|
void clearSelectedTrack() {
|
||||||
dataHub.unloadCurrentTrack();
|
dataHub.unloadCurrentTrack();
|
||||||
}
|
}
|
||||||
@@ -535,54 +509,10 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
return dataHub.getSelectedTrackId();
|
return dataHub.getSelectedTrackId();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Binds to track recording service if it is running.
|
|
||||||
*/
|
|
||||||
private void tryBindTrackRecordingService() {
|
|
||||||
Log.d(TAG,
|
|
||||||
"MyTracks: Trying to bind to track recording service...");
|
|
||||||
bindService(new Intent(this, TrackRecordingService.class),
|
|
||||||
serviceConnection, 0);
|
|
||||||
Log.d(TAG, "MyTracks: ...bind finished!");
|
|
||||||
isBound = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Tries to unbind the track recording service. Catches exception silently in
|
|
||||||
* case service is not registered anymore.
|
|
||||||
*/
|
|
||||||
private void tryUnbindTrackRecordingService() {
|
|
||||||
if (isBound) {
|
|
||||||
Log.d(TAG, "MyTracks: Trying to unbind from track recording service...");
|
|
||||||
try {
|
|
||||||
unbindService(serviceConnection);
|
|
||||||
Log.d(TAG, "MyTracks: ...unbind finished!");
|
|
||||||
} catch (IllegalArgumentException e) {
|
|
||||||
Log.d(TAG, "MyTracks: Tried unbinding, but service was not registered.", e);
|
|
||||||
}
|
|
||||||
isBound = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public DialogManager getDialogManager() {
|
public DialogManager getDialogManager() {
|
||||||
return dialogManager;
|
return dialogManager;
|
||||||
}
|
}
|
||||||
|
|
||||||
// @VisibleForTesting
|
|
||||||
long getRecordingTrackId() {
|
|
||||||
return sharedPreferences.getLong(getString(R.string.recording_track_key), -1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// @VisibleForTesting
|
|
||||||
SharedPreferences getSharedPreferences() {
|
|
||||||
return sharedPreferences;
|
|
||||||
}
|
|
||||||
|
|
||||||
// @VisibleForTesting
|
|
||||||
ITrackRecordingService getTrackRecordingService() {
|
|
||||||
return trackRecordingService;
|
|
||||||
}
|
|
||||||
|
|
||||||
public TrackDataHub getDataHub() {
|
public TrackDataHub getDataHub() {
|
||||||
return dataHub;
|
return dataHub;
|
||||||
}
|
}
|
||||||
@@ -593,8 +523,4 @@ public class MyTracks extends TabActivity implements OnTouchListener {
|
|||||||
public static MyTracks getInstance() {
|
public static MyTracks getInstance() {
|
||||||
return instance;
|
return instance;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void clearInstance() {
|
|
||||||
instance = null;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,6 +18,7 @@ package com.google.android.apps.mytracks;
|
|||||||
import static com.google.android.apps.mytracks.Constants.TAG;
|
import static com.google.android.apps.mytracks.Constants.TAG;
|
||||||
import com.google.android.apps.mytracks.content.Sensor;
|
import com.google.android.apps.mytracks.content.Sensor;
|
||||||
import com.google.android.apps.mytracks.services.ITrackRecordingService;
|
import com.google.android.apps.mytracks.services.ITrackRecordingService;
|
||||||
|
import com.google.android.apps.mytracks.services.TrackRecordingServiceBinder;
|
||||||
import com.google.android.apps.mytracks.services.sensors.SensorUtils;
|
import com.google.android.apps.mytracks.services.sensors.SensorUtils;
|
||||||
import com.google.android.maps.mytracks.R;
|
import com.google.android.maps.mytracks.R;
|
||||||
import com.google.protobuf.InvalidProtocolBufferException;
|
import com.google.protobuf.InvalidProtocolBufferException;
|
||||||
@@ -45,6 +46,7 @@ public class SensorStateActivity extends Activity {
|
|||||||
private static final long REFRESH_PERIOD_MS = 250;
|
private static final long REFRESH_PERIOD_MS = 250;
|
||||||
|
|
||||||
private final StatsUtilities utils;
|
private final StatsUtilities utils;
|
||||||
|
private TrackRecordingServiceBinder serviceBinder;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This timer periodically invokes the refresh timer task.
|
* This timer periodically invokes the refresh timer task.
|
||||||
@@ -79,6 +81,8 @@ public class SensorStateActivity extends Activity {
|
|||||||
|
|
||||||
setContentView(R.layout.sensor_state);
|
setContentView(R.layout.sensor_state);
|
||||||
|
|
||||||
|
serviceBinder = TrackRecordingServiceBinder.getInstance(this);
|
||||||
|
serviceBinder.bindService(stateUpdater);
|
||||||
updateState();
|
updateState();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -97,11 +101,13 @@ public class SensorStateActivity extends Activity {
|
|||||||
timer = null;
|
timer = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void updateState() {
|
@Override
|
||||||
MyTracks mt = MyTracks.getInstance();
|
protected void onDestroy() {
|
||||||
|
serviceBinder.unbindService();
|
||||||
|
}
|
||||||
|
|
||||||
ITrackRecordingService service =
|
protected void updateState() {
|
||||||
mt == null ? null : mt.getTrackRecordingService();
|
ITrackRecordingService service = serviceBinder.getServiceIfBound();
|
||||||
if (service == null) {
|
if (service == null) {
|
||||||
Log.d(Constants.TAG, "Could not get track recording service.");
|
Log.d(Constants.TAG, "Could not get track recording service.");
|
||||||
updateSensorState(Sensor.SensorState.NONE);
|
updateSensorState(Sensor.SensorState.NONE);
|
||||||
|
|||||||
@@ -22,6 +22,7 @@ import static com.google.android.apps.mytracks.Constants.MAX_LOCATION_AGE_MS;
|
|||||||
import static com.google.android.apps.mytracks.Constants.MAX_NETWORK_AGE_MS;
|
import static com.google.android.apps.mytracks.Constants.MAX_NETWORK_AGE_MS;
|
||||||
import static com.google.android.apps.mytracks.Constants.TAG;
|
import static com.google.android.apps.mytracks.Constants.TAG;
|
||||||
|
|
||||||
|
import com.google.android.apps.mytracks.Constants;
|
||||||
import com.google.android.apps.mytracks.content.DataSourceManager.DataSourceListener;
|
import com.google.android.apps.mytracks.content.DataSourceManager.DataSourceListener;
|
||||||
import com.google.android.apps.mytracks.content.MyTracksProviderUtils.DoubleBufferedLocationFactory;
|
import com.google.android.apps.mytracks.content.MyTracksProviderUtils.DoubleBufferedLocationFactory;
|
||||||
import com.google.android.apps.mytracks.content.MyTracksProviderUtils.LocationIterator;
|
import com.google.android.apps.mytracks.content.MyTracksProviderUtils.LocationIterator;
|
||||||
@@ -195,10 +196,17 @@ public class TrackDataHub {
|
|||||||
/**
|
/**
|
||||||
* Default constructor.
|
* Default constructor.
|
||||||
*/
|
*/
|
||||||
public TrackDataHub(Context ctx, SharedPreferences preferences,
|
public TrackDataHub(Context ctx, MyTracksProviderUtils providerUtils) {
|
||||||
|
this(ctx, ctx.getSharedPreferences(Constants.SETTINGS_NAME, 0), providerUtils);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Intermediate constructor, used only for passing preferences into arguments.
|
||||||
|
*/
|
||||||
|
private TrackDataHub(Context ctx, SharedPreferences preferences,
|
||||||
MyTracksProviderUtils providerUtils) {
|
MyTracksProviderUtils providerUtils) {
|
||||||
this(ctx, new DataSourcesWrapperImpl(ctx, preferences), new TrackDataListeners(),
|
this(ctx, new DataSourcesWrapperImpl(ctx, preferences), new TrackDataListeners(),
|
||||||
preferences, providerUtils, TARGET_DISPLAYED_TRACK_POINTS);
|
preferences, providerUtils, TARGET_DISPLAYED_TRACK_POINTS);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -785,7 +785,7 @@ public class TrackRecordingService extends Service implements LocationListener {
|
|||||||
if (intent != null &&
|
if (intent != null &&
|
||||||
intent.getBooleanExtra(RESUME_TRACK_EXTRA_NAME, false)) {
|
intent.getBooleanExtra(RESUME_TRACK_EXTRA_NAME, false)) {
|
||||||
Log.d(TAG, "TrackRecordingService: requested resume");
|
Log.d(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.
|
||||||
if (recordingTrack == null || !shouldResumeTrack(recordingTrack)) {
|
if (recordingTrack == null || !shouldResumeTrack(recordingTrack)) {
|
||||||
Log.i(TAG,
|
Log.i(TAG,
|
||||||
@@ -796,7 +796,7 @@ public class TrackRecordingService extends Service implements LocationListener {
|
|||||||
stopSelfResult(startId);
|
stopSelfResult(startId);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Log.i(TAG, "TrackRecordingService: resuming");
|
Log.i(TAG, "TrackRecordingService: resuming");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+203
@@ -0,0 +1,203 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2011 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.services;
|
||||||
|
|
||||||
|
import static com.google.android.apps.mytracks.Constants.TAG;
|
||||||
|
|
||||||
|
import com.google.android.apps.mytracks.Constants;
|
||||||
|
import com.google.android.apps.mytracks.util.SystemUtils;
|
||||||
|
|
||||||
|
import android.content.ComponentName;
|
||||||
|
import android.content.Context;
|
||||||
|
import android.content.Intent;
|
||||||
|
import android.content.ServiceConnection;
|
||||||
|
import android.os.IBinder;
|
||||||
|
import android.util.Log;
|
||||||
|
|
||||||
|
import java.util.WeakHashMap;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A helper for managing the binding to the track recording service.
|
||||||
|
* This uses reference counting so multiple callers can share a binding.
|
||||||
|
*
|
||||||
|
* @author Rodrigo Damazio
|
||||||
|
*/
|
||||||
|
public class TrackRecordingServiceBinder {
|
||||||
|
/** Singleton instance. */
|
||||||
|
private static TrackRecordingServiceBinder instance;
|
||||||
|
|
||||||
|
private final ServiceConnection serviceConnection = new ServiceConnection() {
|
||||||
|
@Override
|
||||||
|
public void onServiceConnected(ComponentName className, IBinder service) {
|
||||||
|
Log.d(Constants.TAG, "Service now connected.");
|
||||||
|
|
||||||
|
// Delay setting the service until we are done with initialization.
|
||||||
|
ITrackRecordingService trackRecordingService =
|
||||||
|
ITrackRecordingService.Stub.asInterface(service);
|
||||||
|
synchronized (TrackRecordingServiceBinder.this) {
|
||||||
|
try {
|
||||||
|
for (Runnable callback : pendingBindCallbacks.keySet()) {
|
||||||
|
if (callback != null) {
|
||||||
|
callback.run();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} finally {
|
||||||
|
pendingBindCallbacks.clear();
|
||||||
|
TrackRecordingServiceBinder.this.trackRecordingService = trackRecordingService;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onServiceDisconnected(ComponentName className) {
|
||||||
|
Log.d(TAG, "Service now disconnected.");
|
||||||
|
synchronized (TrackRecordingServiceBinder.this) {
|
||||||
|
trackRecordingService = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
/** Pointer to the service, if bound. */
|
||||||
|
private ITrackRecordingService trackRecordingService;
|
||||||
|
|
||||||
|
/** Count of bindings to the service. */
|
||||||
|
private int bindCount = 0;
|
||||||
|
|
||||||
|
/** Set of callbacks to execute when the service connects. */
|
||||||
|
private final WeakHashMap<Runnable, Object> pendingBindCallbacks =
|
||||||
|
new WeakHashMap<Runnable, Object>();
|
||||||
|
|
||||||
|
/** Application context. */
|
||||||
|
private final Context applicationContext;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Starts the service with the default intent.
|
||||||
|
*
|
||||||
|
* This should only be called when the service will be put in recording mode,
|
||||||
|
* as the service being started means it'll be listening to the GPS.
|
||||||
|
* Notice that it is perfectly fine to call {@link #bindService} without calling
|
||||||
|
* this at all.
|
||||||
|
*/
|
||||||
|
public void startService() {
|
||||||
|
Intent intent = new Intent(applicationContext, TrackRecordingService.class);
|
||||||
|
applicationContext.startService(intent);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Binds to the service, and calls the given callback afterwards.
|
||||||
|
* Calls to this method should be balanced with calls to {@link #unbindService}.
|
||||||
|
*
|
||||||
|
* @param onBindCallback the callback for when the service is connected
|
||||||
|
*/
|
||||||
|
public void bindService(Runnable onBindCallback) {
|
||||||
|
synchronized (this) {
|
||||||
|
bindCount++;
|
||||||
|
if (trackRecordingService != null) {
|
||||||
|
if (onBindCallback != null) {
|
||||||
|
onBindCallback.run();
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (onBindCallback != null) {
|
||||||
|
pendingBindCallbacks.put(onBindCallback, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (bindCount == 1) {
|
||||||
|
Intent intent = new Intent(applicationContext, TrackRecordingService.class);
|
||||||
|
int flags = SystemUtils.isRelease(applicationContext) ? 0 : Context.BIND_DEBUG_UNBIND;
|
||||||
|
applicationContext.bindService(intent, serviceConnection, flags);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Unbinds from the service.
|
||||||
|
*
|
||||||
|
* This will unbind from the service, unless another caller is still bound to it.
|
||||||
|
* Calls to this method should be balanced with calls to {@link #bindService}.
|
||||||
|
*/
|
||||||
|
public void unbindService() {
|
||||||
|
synchronized (this) {
|
||||||
|
bindCount--;
|
||||||
|
if (bindCount > 0) {
|
||||||
|
// Someone else may still be using it.
|
||||||
|
return;
|
||||||
|
} else if (bindCount < 0) {
|
||||||
|
Log.e(TAG, "Unbalanced binding calls.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
applicationContext.unbindService(serviceConnection);
|
||||||
|
} catch (IllegalArgumentException e) {
|
||||||
|
Log.d(TAG, "Tried unbinding, but service was not registered.", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Stops the service, and consequently its GPS listening.
|
||||||
|
*/
|
||||||
|
public void stopService() {
|
||||||
|
try {
|
||||||
|
applicationContext.stopService(new Intent(applicationContext, TrackRecordingService.class));
|
||||||
|
} catch (SecurityException e) {
|
||||||
|
Log.e(TAG, "Encountered a security exception when trying to stop service.", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void finalize() throws Throwable {
|
||||||
|
if (bindCount > 0) {
|
||||||
|
Log.e(TAG, "Leaked bindings: " + bindCount + " bindings left on finalize.");
|
||||||
|
}
|
||||||
|
|
||||||
|
super.finalize();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the connected service instance, or null if not connected.
|
||||||
|
*/
|
||||||
|
public ITrackRecordingService getServiceIfBound() {
|
||||||
|
return trackRecordingService;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the singleton instance of this class.
|
||||||
|
* Notice that although a context is required, it is safe to call this from
|
||||||
|
* multiple different contexts to obtain the same instance.
|
||||||
|
*
|
||||||
|
* @param context the current context
|
||||||
|
* @return the singleton instance
|
||||||
|
*/
|
||||||
|
public synchronized static TrackRecordingServiceBinder getInstance(Context context) {
|
||||||
|
if (instance == null) {
|
||||||
|
Context applicationContext = context.getApplicationContext();
|
||||||
|
instance = new TrackRecordingServiceBinder(applicationContext);
|
||||||
|
}
|
||||||
|
return instance;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Internal constructor.
|
||||||
|
*
|
||||||
|
* @param applicationContext the current application (not activity) context
|
||||||
|
*/
|
||||||
|
private TrackRecordingServiceBinder(Context applicationContext) {
|
||||||
|
this.applicationContext = applicationContext;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -36,56 +36,48 @@ import java.util.concurrent.atomic.AtomicBoolean;
|
|||||||
* @author Bartlomiej Niechwiej
|
* @author Bartlomiej Niechwiej
|
||||||
*/
|
*/
|
||||||
public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
||||||
|
private SharedPreferences sharedPreferences;
|
||||||
|
|
||||||
public MyTracksTest() {
|
public MyTracksTest() {
|
||||||
super(MyTracks.class);
|
super(MyTracks.class);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void setUp() throws Exception {
|
|
||||||
super.setUp();
|
|
||||||
MyTracks.clearInstance();
|
|
||||||
assertNull(MyTracks.getInstance());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void tearDown() throws Exception {
|
protected void tearDown() throws Exception {
|
||||||
clearSelectedAndRecordingTracks();
|
clearSelectedAndRecordingTracks();
|
||||||
waitForIdle();
|
waitForIdle();
|
||||||
|
|
||||||
super.tearDown();
|
super.tearDown();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testInitialization_mainAction() {
|
public void testInitialization_mainAction() {
|
||||||
// Make sure we can start MyTracks and the activity doesn't start recording.
|
// Make sure we can start MyTracks and the activity doesn't start recording.
|
||||||
assertNotNull(getActivity());
|
assertInitialized();
|
||||||
assertNotNull(MyTracks.getInstance());
|
|
||||||
assertNotNull(getActivity().getSharedPreferences());
|
|
||||||
|
|
||||||
// Check if not recording.
|
// Check if not recording.
|
||||||
assertFalse(getActivity().isRecording());
|
assertFalse(getActivity().isRecording());
|
||||||
assertEquals(-1, getActivity().getRecordingTrackId());
|
assertEquals(-1, getRecordingTrackId());
|
||||||
long selectedTrackId = getActivity().getSharedPreferences().getLong(
|
long selectedTrackId = getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.selected_track_key), -1);
|
getActivity().getString(R.string.selected_track_key), -1);
|
||||||
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testInitialization_viewActionWithNoData() {
|
public void testInitialization_viewActionWithNoData() {
|
||||||
// Simulate start with ACTION_VIEW intent.
|
// Simulate start with ACTION_VIEW intent.
|
||||||
Intent startIntent = new Intent();
|
Intent startIntent = new Intent();
|
||||||
startIntent.setAction(Intent.ACTION_VIEW);
|
startIntent.setAction(Intent.ACTION_VIEW);
|
||||||
setActivityIntent(startIntent);
|
setActivityIntent(startIntent);
|
||||||
|
|
||||||
assertNotNull(getActivity());
|
assertInitialized();
|
||||||
assertNotNull(MyTracks.getInstance());
|
|
||||||
assertNotNull(getActivity().getSharedPreferences());
|
|
||||||
|
|
||||||
// Check if not recording.
|
// Check if not recording.
|
||||||
assertFalse(getActivity().isRecording());
|
assertFalse(getActivity().isRecording());
|
||||||
assertEquals(-1, getActivity().getRecordingTrackId());
|
assertEquals(-1, getRecordingTrackId());
|
||||||
long selectedTrackId = getActivity().getSharedPreferences().getLong(
|
long selectedTrackId = getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.selected_track_key), -1);
|
getActivity().getString(R.string.selected_track_key), -1);
|
||||||
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testInitialization_viewActionWithValidData() throws Exception {
|
public void testInitialization_viewActionWithValidData() throws Exception {
|
||||||
// Simulate start with ACTION_VIEW intent.
|
// Simulate start with ACTION_VIEW intent.
|
||||||
Intent startIntent = new Intent();
|
Intent startIntent = new Intent();
|
||||||
@@ -93,24 +85,22 @@ public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
|||||||
Uri uri = Uri.fromFile(File.createTempFile("valid", ".gpx"));
|
Uri uri = Uri.fromFile(File.createTempFile("valid", ".gpx"));
|
||||||
|
|
||||||
// TODO: Add a valid GPX.
|
// TODO: Add a valid GPX.
|
||||||
|
|
||||||
startIntent.setData(uri);
|
startIntent.setData(uri);
|
||||||
setActivityIntent(startIntent);
|
setActivityIntent(startIntent);
|
||||||
|
|
||||||
assertNotNull(getActivity());
|
assertInitialized();
|
||||||
assertNotNull(MyTracks.getInstance());
|
|
||||||
assertNotNull(getActivity().getSharedPreferences());
|
|
||||||
|
|
||||||
// Check if not recording.
|
// Check if not recording.
|
||||||
assertFalse(getActivity().isRecording());
|
assertFalse(getActivity().isRecording());
|
||||||
assertEquals(-1, getActivity().getRecordingTrackId());
|
assertEquals(-1, getRecordingTrackId());
|
||||||
long selectedTrackId = getActivity().getSharedPreferences().getLong(
|
long selectedTrackId = getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.selected_track_key), -1);
|
getActivity().getString(R.string.selected_track_key), -1);
|
||||||
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
||||||
|
|
||||||
// TODO: Finish this test.
|
// TODO: Finish this test.
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testInitialization_viewActionWithInvalidData() throws Exception {
|
public void testInitialization_viewActionWithInvalidData() throws Exception {
|
||||||
// Simulate start with ACTION_VIEW intent.
|
// Simulate start with ACTION_VIEW intent.
|
||||||
Intent startIntent = new Intent();
|
Intent startIntent = new Intent();
|
||||||
@@ -118,34 +108,29 @@ public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
|||||||
Uri uri = Uri.fromFile(File.createTempFile("invalid", ".gpx"));
|
Uri uri = Uri.fromFile(File.createTempFile("invalid", ".gpx"));
|
||||||
startIntent.setData(uri);
|
startIntent.setData(uri);
|
||||||
setActivityIntent(startIntent);
|
setActivityIntent(startIntent);
|
||||||
|
|
||||||
assertNotNull(getActivity());
|
assertInitialized();
|
||||||
assertNotNull(MyTracks.getInstance());
|
|
||||||
assertNotNull(getActivity().getSharedPreferences());
|
|
||||||
|
|
||||||
// Check if not recording.
|
// Check if not recording.
|
||||||
assertFalse(getActivity().isRecording());
|
assertFalse(getActivity().isRecording());
|
||||||
assertEquals(-1, getActivity().getRecordingTrackId());
|
assertEquals(-1, getRecordingTrackId());
|
||||||
long selectedTrackId = getActivity().getSharedPreferences().getLong(
|
long selectedTrackId = getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.selected_track_key), -1);
|
getActivity().getString(R.string.selected_track_key), -1);
|
||||||
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
||||||
|
|
||||||
// TODO: Finish this test.
|
// TODO: Finish this test.
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testRecording_startAndStop() throws Exception {
|
public void testRecording_startAndStop() throws Exception {
|
||||||
// Make sure we can start MyTracks and the activity doesn't start recording.
|
assertInitialized();
|
||||||
assertNotNull(getActivity());
|
|
||||||
assertNotNull(MyTracks.getInstance());
|
|
||||||
assertNotNull(getActivity().getSharedPreferences());
|
|
||||||
|
|
||||||
// Check if not recording.
|
// Check if not recording.
|
||||||
clearSelectedAndRecordingTracks();
|
clearSelectedAndRecordingTracks();
|
||||||
waitForIdle();
|
waitForIdle();
|
||||||
|
|
||||||
assertFalse(getActivity().isRecording());
|
assertFalse(getActivity().isRecording());
|
||||||
assertEquals(-1, getActivity().getRecordingTrackId());
|
assertEquals(-1, getRecordingTrackId());
|
||||||
long selectedTrackId = getActivity().getSharedPreferences().getLong(
|
long selectedTrackId = getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.selected_track_key), -1);
|
getActivity().getString(R.string.selected_track_key), -1);
|
||||||
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
||||||
|
|
||||||
@@ -153,16 +138,16 @@ public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
|||||||
getActivity().startRecording();
|
getActivity().startRecording();
|
||||||
long recordingTrackId = awaitRecordingStatus(5000, true);
|
long recordingTrackId = awaitRecordingStatus(5000, true);
|
||||||
assertTrue(recordingTrackId >= 0);
|
assertTrue(recordingTrackId >= 0);
|
||||||
|
|
||||||
// Wait until we are done and make sure that selectedTrack = recordingTrack.
|
// Wait until we are done and make sure that selectedTrack = recordingTrack.
|
||||||
waitForIdle();
|
waitForIdle();
|
||||||
assertEquals(recordingTrackId, getActivity().getSharedPreferences().getLong(
|
assertEquals(recordingTrackId, getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.recording_track_key), -1));
|
getActivity().getString(R.string.recording_track_key), -1));
|
||||||
selectedTrackId = getActivity().getSharedPreferences().getLong(
|
selectedTrackId = getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.selected_track_key), -1);
|
getActivity().getString(R.string.selected_track_key), -1);
|
||||||
assertEquals(recordingTrackId, selectedTrackId);
|
assertEquals(recordingTrackId, selectedTrackId);
|
||||||
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
||||||
|
|
||||||
// Watch for MyTracksDetails activity.
|
// Watch for MyTracksDetails activity.
|
||||||
ActivityMonitor monitor = getInstrumentation().addMonitor(
|
ActivityMonitor monitor = getInstrumentation().addMonitor(
|
||||||
TrackDetails.class.getName(), null, false);
|
TrackDetails.class.getName(), null, false);
|
||||||
@@ -170,14 +155,14 @@ public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
|||||||
// Now, stop the track and make sure that it is still selected, but
|
// Now, stop the track and make sure that it is still selected, but
|
||||||
// no longer recording.
|
// no longer recording.
|
||||||
getActivity().stopRecording();
|
getActivity().stopRecording();
|
||||||
|
|
||||||
// Check if we got back MyTracksDetails activity.
|
// Check if we got back MyTracksDetails activity.
|
||||||
Activity activity = getInstrumentation().waitForMonitor(monitor);
|
Activity activity = getInstrumentation().waitForMonitor(monitor);
|
||||||
assertTrue(activity instanceof TrackDetails);
|
assertTrue(activity instanceof TrackDetails);
|
||||||
|
|
||||||
// TODO: Update track name and other properties and test if they were
|
// TODO: Update track name and other properties and test if they were
|
||||||
// properly saved.
|
// properly saved.
|
||||||
|
|
||||||
// Simulate a click on Save button.
|
// Simulate a click on Save button.
|
||||||
Button save = (Button) activity.findViewById(R.id.trackdetails_save);
|
Button save = (Button) activity.findViewById(R.id.trackdetails_save);
|
||||||
save.performClick();
|
save.performClick();
|
||||||
@@ -185,13 +170,18 @@ public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
|||||||
// Check the remaining properties.
|
// Check the remaining properties.
|
||||||
recordingTrackId = awaitRecordingStatus(5000, false);
|
recordingTrackId = awaitRecordingStatus(5000, false);
|
||||||
assertEquals(-1, recordingTrackId);
|
assertEquals(-1, recordingTrackId);
|
||||||
assertEquals(recordingTrackId, getActivity().getRecordingTrackId());
|
assertEquals(recordingTrackId, getRecordingTrackId());
|
||||||
assertEquals(recordingTrackId, getActivity().getSharedPreferences().getLong(
|
assertEquals(recordingTrackId, getSharedPreferences().getLong(
|
||||||
getActivity().getString(R.string.recording_track_key), -1));
|
getActivity().getString(R.string.recording_track_key), -1));
|
||||||
// Make sure this is the same track as the last recording track ID.
|
// Make sure this is the same track as the last recording track ID.
|
||||||
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
assertEquals(selectedTrackId, getActivity().getSelectedTrackId());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void assertInitialized() {
|
||||||
|
assertNotNull(getActivity());
|
||||||
|
assertNotNull(MyTracks.getInstance());
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Waits until the UI thread becomes idle.
|
* Waits until the UI thread becomes idle.
|
||||||
*/
|
*/
|
||||||
@@ -216,13 +206,13 @@ public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Clears {selected,recording}TrackId in the {@link SharedPreferences}.
|
* Clears {selected,recording}TrackId in the {@link getSharedPreferences()}.
|
||||||
*/
|
*/
|
||||||
private void clearSelectedAndRecordingTracks() {
|
private void clearSelectedAndRecordingTracks() {
|
||||||
Editor editor = getActivity().getSharedPreferences().edit();
|
Editor editor = getSharedPreferences().edit();
|
||||||
editor.putLong(getActivity().getString(R.string.selected_track_key), -1);
|
editor.putLong(getActivity().getString(R.string.selected_track_key), -1);
|
||||||
editor.putLong(getActivity().getString(R.string.recording_track_key), -1);
|
editor.putLong(getActivity().getString(R.string.recording_track_key), -1);
|
||||||
|
|
||||||
editor.clear();
|
editor.clear();
|
||||||
editor.commit();
|
editor.commit();
|
||||||
}
|
}
|
||||||
@@ -245,6 +235,17 @@ public class MyTracksTest extends ActivityInstrumentationTestCase2<MyTracks>{
|
|||||||
}
|
}
|
||||||
waitForIdle();
|
waitForIdle();
|
||||||
assertEquals(isRecording, getActivity().isRecording());
|
assertEquals(isRecording, getActivity().isRecording());
|
||||||
return getActivity().getRecordingTrackId();
|
return getRecordingTrackId();
|
||||||
|
}
|
||||||
|
|
||||||
|
private long getRecordingTrackId() {
|
||||||
|
return getSharedPreferences().getLong(getActivity().getString(R.string.recording_track_key), -1);
|
||||||
|
}
|
||||||
|
|
||||||
|
private SharedPreferences getSharedPreferences() {
|
||||||
|
if (sharedPreferences == null) {
|
||||||
|
sharedPreferences = getActivity().getSharedPreferences(Constants.SETTINGS_NAME, 0);
|
||||||
|
}
|
||||||
|
return sharedPreferences;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user