/*
* Geopaparazzi - Digital field mapping on Android based devices
* Copyright (C) 2016 HydroloGIS (www.hydrologis.com)
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package eu.geopaparazzi.library.gps;
import android.Manifest;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.pm.PackageManager;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteFullException;
import android.location.GpsStatus;
import android.location.GpsStatus.Listener;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.os.Handler;
import android.os.IBinder;
import android.os.SystemClock;
import android.preference.PreferenceManager;
import android.support.v4.app.ActivityCompat;
import android.widget.Toast;
import eu.geopaparazzi.library.R;
import eu.geopaparazzi.library.database.GPLog;
import eu.geopaparazzi.library.database.IGpsLogDbHelper;
import eu.geopaparazzi.library.util.LibraryConstants;
import eu.geopaparazzi.library.util.PositionUtilities;
import eu.geopaparazzi.library.util.debug.TestMock;
import static eu.geopaparazzi.library.util.LibraryConstants.DEFAULT_LOG_WIDTH;
import static eu.geopaparazzi.library.util.LibraryConstants.GPS_LOGGING_DISTANCE;
import static eu.geopaparazzi.library.util.LibraryConstants.GPS_LOGGING_INTERVAL;
import static eu.geopaparazzi.library.util.LibraryConstants.PREFS_KEY_GPSLOGGINGDISTANCE;
import static eu.geopaparazzi.library.util.LibraryConstants.PREFS_KEY_GPSLOGGINGINTERVAL;
/**
* A service to handle the GPS data.
* <p/>
* <p/>
* use this to start and trigger a service</br>
* <code>Intent i= new Intent(context, GpsService.class)</code>;</br>
* add data to the intent</br>
* <code>i.putExtra("KEY1", "Value to be used by the service");</br>
* context.startService(i);</code>
*
* @author Andrea Antonello (www.hydrologis.com)
*/
@SuppressWarnings("nls")
public class GpsService extends Service implements LocationListener, Listener {
private static final boolean DOLOGPOSITION = GPLog.LOG_ABSURD;
private static final boolean DO_WHILE_LOOP_LOG = GPLog.LOG_ABSURD;
/**
* Intent key to pass the boolean to start gps database logging.
*/
public static final String START_GPS_LOGGING = "START_GPS_LOGGING";
/**
* Intent key to pass the boolean to stop gps database logging.
*/
public static final String STOP_GPS_LOGGING = "STOP_GPS_LOGGING";
/**
* Intent key to pass the string gps database log helper class.
*/
public static final String START_GPS_LOG_HELPER_CLASS = "START_GPS_LOG_HELPER_CLASS";
/**
* Intent key to pass the string gps log name.
*/
public static final String START_GPS_LOG_NAME = "START_GPS_LOG_NAME";
/**
* Intent key to pass the flag to continue log
*/
public static final String START_GPS_CONTINUE_LOG = "START_GPS_CONTINUE_LOG";
/**
* Intent key to use for broadcasts.
*/
public static final String GPS_SERVICE_BROADCAST_NOTIFICATION = "eu.geopaparazzi.library.gps.GpsService";
/**
* Intent key to use for int gps status.
* <p/>
* <p>Status can be:
* <ul>
* <li>gps off = 0</li>
* <li>gps on but not listening for updates = 1</li>
* <li>gps on and listening for updates but no fix= 2</li>
* <li>gps has fix = 3</li>
* </ul>
*/
public static final String GPS_SERVICE_STATUS = "GPS_SERVICE_STATUS";
/**
* Intent key to use for int gps logging status.
* <p/>
* <p>Status can be:
* <ul>
* <li>gps logging off = 0</li>
* <li>gps logging on = 1</li>
* </ul>
*/
public static final String GPS_LOGGING_STATUS = "GPS_LOGGING_STATUS";
/**
* Intent key to use for double array position data [lon, lat, elev].
*/
public static final String GPS_SERVICE_POSITION = "GPS_SERVICE_POSITION";
/**
* Intent key to use for double array position extra data [accuracy, speed, bearing].
*/
public static final String GPS_SERVICE_POSITION_EXTRAS = "GPS_SERVICE_POSITION_EXTRAS";
/**
* Intent key to use for long time.
*/
public static final String GPS_SERVICE_POSITION_TIME = "GPS_SERVICE_POSITION_TIME";
/**
* Intent key to use for current recorded log id.
*/
public static final String GPS_SERVICE_CURRENT_LOG_ID = "GPS_SERVICE_CURRENT_LOG_ID";
/**
* Intent key to use for int array gps extra data [maxSatellites, satCount, satUsedInFixCount].
*/
public static final String GPS_SERVICE_GPSSTATUS_EXTRAS = "GPS_SERVICE_GPSSTATUS_EXTRAS";
/**
* Intent key to use to trigger a broadcast.
*/
public static final String GPS_SERVICE_DO_BROADCAST = "GPS_SERVICE_DO_BROADCAST";
private SharedPreferences preferences;
private LocationManager locationManager;
private boolean useNetworkPositions = false;
private boolean isMockMode = false;
/**
* The last taken gps location.
*/
private GpsLocation lastGpsLocation = null;
/**
* The previous gps location or null if no gps location was taken yet.
* <p/>
* <p>This changes with every {@link #onLocationChanged(Location)}.</p>
*/
private Location previousLoc = null;
private long lastLocationupdateMillis;
private int currentPointsNum;
/**
* The current total distance of the track from start to the current point.
*/
private double currentDistance;
/**
* GPS time interval.
*/
private static int WAITSECONDS = 1;
private GpsStatus mStatus;
private long currentRecordedLogId = -1;
private volatile boolean gotFix;
private boolean isDatabaseLogging = false;
private boolean isListeningForUpdates = false;
private boolean isProviderEnabled;
private Handler toastHandler;
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
// GPLog.addLogEntry(this, "onStartCommand called with intent: " + intent);
/*
* If startService(intent) is called while the service is running,
* its onStartCommand() is also called. Therefore your service needs
* to be prepared that onStartCommand() can be called several times.
*/
if (preferences == null) {
preferences = PreferenceManager.getDefaultSharedPreferences(this);
useNetworkPositions = preferences.getBoolean(LibraryConstants.PREFS_KEY_GPS_USE_NETWORK_POSITION, false);
isMockMode = preferences.getBoolean(LibraryConstants.PREFS_KEY_MOCKMODE, false);
toastHandler = new Handler();
log("onStartCommand: Preferences created");
}
if (locationManager == null) {
locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
return Service.START_FLAG_RETRY;
}
locationManager.addGpsStatusListener(this);
isProviderEnabled = isGpsOn();
log("onStartCommand: LocationManager created + GpsService started");
}
if (!isListeningForUpdates) {
registerForLocationUpdates();
log("onStartCommand: Registered for location updates");
}
if (intent != null) {
/*
* START GPS logging
*/
if (intent.hasExtra(START_GPS_LOGGING)) {
boolean startGpsLogging = intent.getBooleanExtra(START_GPS_LOGGING, false);
if (startGpsLogging) {
log("onStartCommand: Start GPS logging called");
if (!isDatabaseLogging) {
String gpsLogName = intent.getStringExtra(START_GPS_LOG_NAME);
String gpsLogHelperClass = intent.getStringExtra(START_GPS_LOG_HELPER_CLASS);
boolean continueLastGpsLog = intent.getBooleanExtra(START_GPS_CONTINUE_LOG, false);
try {
Class<?> logHelper = Class.forName(gpsLogHelperClass);
IGpsLogDbHelper newInstance = (IGpsLogDbHelper) logHelper.newInstance();
startDatabaseLogging(gpsLogName, continueLastGpsLog, newInstance);
} catch (Exception e) {
GPLog.error(this, "Could not start logging", e);
}
}
}
}
if (intent.hasExtra(STOP_GPS_LOGGING)) {
boolean stopGpsLogging = intent.getBooleanExtra(STOP_GPS_LOGGING, false);
if (stopGpsLogging) {
log("onStartCommand: Stop GPS logging called");
if (isDatabaseLogging) {
stopDatabaseLogging();
}
}
}
if (intent.hasExtra(GPS_SERVICE_DO_BROADCAST)) {
log("onStartCommand: broadcast trigger");
boolean doBroadcast = intent.getBooleanExtra(GPS_SERVICE_DO_BROADCAST, false);
if (doBroadcast) {
broadcast("triggered by onStartCommand Intent");
}
}
}
return Service.START_REDELIVER_INTENT;
}
@Override
public void onDestroy() {
log("onDestroy Gpsservice.");
if (isDatabaseLogging) {
stopDatabaseLogging();
}
if (locationManager != null && isListeningForUpdates) {
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
throw new SecurityException();
}
locationManager.removeUpdates(this);
locationManager.removeGpsStatusListener(this);
isListeningForUpdates = false;
}
if (TestMock.isOn) {
TestMock.stopMocking(locationManager);
}
super.onDestroy();
}
/**
* Starts listening to the gps provider.
*/
private void registerForLocationUpdates() {
try {
if (isMockMode) {
log("Gps started using Mock locations");
TestMock.startMocking(locationManager, this);
isListeningForUpdates = true;
} else {
float minDistance = 0.2f;
long waitForSecs = WAITSECONDS;
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
throw new SecurityException();
}
if (useNetworkPositions) {
locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, waitForSecs * 1000l, minDistance, this);
} else {
locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, waitForSecs * 1000l, minDistance, this);
}
isListeningForUpdates = true;
log("registered for updates.");
}
broadcast("triggered by registerForLocationUpdates");
} catch (Exception e) {
GPLog.error(this, null, e);
isListeningForUpdates = false;
}
}
/**
* Starts logging into the database.
*
* @param logName a name for the new log or <code>null</code>.
* @param continueLastLog if true, the last previous log is continued.
* @param dbHelper the db helper.
*/
private void startDatabaseLogging(final String logName, final boolean continueLastLog, final IGpsLogDbHelper dbHelper) {
if (isDatabaseLogging) {
// we do not start twice
return;
}
isDatabaseLogging = true;
Thread t = new Thread() {
public void run() {
try {
SQLiteDatabase sqliteDatabase = dbHelper.getDatabase();
long gpsLogId = -1;
if (continueLastLog) {
try {
log("Continue from last log...");
gpsLogId = dbHelper.getLastLogId();
log("...with log id: " + gpsLogId);
} catch (Exception e) {
// ignore and create a new one
}
}
if (gpsLogId < 0) {
long now = System.currentTimeMillis();
gpsLogId = dbHelper.addGpsLog(now, now, 0, logName, DEFAULT_LOG_WIDTH, "red", true);
log("Beginning a new log with log id: " + gpsLogId);
}
currentRecordedLogId = gpsLogId;
log("GPS Start logging. Logid: " + gpsLogId);
// get preferences
String minDistanceStr = preferences.getString(PREFS_KEY_GPSLOGGINGDISTANCE,
String.valueOf(GPS_LOGGING_DISTANCE));
float minDistance = 1f;
try {
minDistance = Float.parseFloat(minDistanceStr);
} catch (Exception e) {
GPLog.error(this, null, e);
}
String intervalStr = preferences
.getString(PREFS_KEY_GPSLOGGINGINTERVAL, String.valueOf(GPS_LOGGING_INTERVAL));
int waitForSecs = 3;
try {
waitForSecs = Integer.parseInt(intervalStr);
} catch (Exception e) {
GPLog.error(this, null, e);
}
if (DO_WHILE_LOOP_LOG) {
GPLog.addLogEntry(GpsService.this, "GPS waiting interval: " + waitForSecs);
GPLog.addLogEntry(GpsService.this, "GPS min distance: " + minDistance);
}
long previousGpsLocationTime = -1;
currentPointsNum = 0;
currentDistance = 0;
while (isDatabaseLogging) {
if (gotFix || isMockMode) {
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this, "GPS DEBUG: loop while at: " + System.nanoTime());
if (lastGpsLocation == null) {
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this, "GPS JUMP POINT: lastGpsLocation == null");
if (!holdABitAndCheckLogging(waitForSecs)) {
break;
}
continue;
}
long time = lastGpsLocation.getTime();
if (previousGpsLocationTime == time) {
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this,
"GPS JUMP POINT: lastGpsLocation == previous (no new point incoming)");
if (!holdABitAndCheckLogging(waitForSecs)) {
break;
}
continue;
}
previousGpsLocationTime = time;
if (lastGpsLocation.getPreviousLoc() == null) {
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this,
"GPS JUMP POINT: waiting for second valid point to come in.");
if (!holdABitAndCheckLogging(waitForSecs)) {
break;
}
continue;
}
double recLon = lastGpsLocation.getLongitude();
double recLat = lastGpsLocation.getLatitude();
double recAlt = lastGpsLocation.getAltitude();
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this, "GPS DEBUG: loop while 1: " + System.nanoTime());
double lastDistance = lastGpsLocation.distanceToPrevious();
if (DO_WHILE_LOOP_LOG) {
StringBuilder sb = new StringBuilder();
sb.append("GPS\ngpsloc: ");
sb.append(lastGpsLocation.getLatitude());
sb.append("/");
sb.append(lastGpsLocation.getLongitude());
sb.append("\n");
if (lastGpsLocation.getPreviousLoc() != null) {
sb.append("previousLoc: ");
sb.append(lastGpsLocation.getPreviousLoc().getLatitude());
sb.append("/");
sb.append(lastGpsLocation.getPreviousLoc().getLongitude());
sb.append("\n");
}
sb.append("distance: ");
sb.append(lastDistance);
sb.append(" - mindistance: ");
sb.append(minDistance);
logABS(sb.toString());
}
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this, "GPS DEBUG: loop while 2: " + System.nanoTime());
// ignore near points
if (lastDistance < minDistance) {
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this, "GPS JUMP POINT: distance from previous");
if (!holdABitAndCheckLogging(waitForSecs)) {
break;
}
continue;
}
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this, "GPS DEBUG: loop while 3: " + System.nanoTime());
try {
if (isDatabaseLogging) {
dbHelper.addGpsLogDataPoint(sqliteDatabase, gpsLogId, recLon, recLat, recAlt,
lastGpsLocation.getTime());
}
} catch (Exception e) {
// we log the exception and try to go on
GPLog.error(this, "Point in db writing error!", e);
}
if (DO_WHILE_LOOP_LOG)
GPLog.addLogEntry(GpsService.this, "GPS DEBUG: loop while 4: " + System.nanoTime());
currentPointsNum++;
currentDistance = currentDistance + lastDistance;
}
if (!holdABitAndCheckLogging(waitForSecs)) {
break;
}
}
if (currentPointsNum < 4 && !continueLastLog) {
log("Removing gpslog, since too few points were added. Logid: " + gpsLogId);
dbHelper.deleteGpslog(gpsLogId);
} else {
// set the end time stamp and the total distance for the track
long end = System.currentTimeMillis();
dbHelper.setEndTs(gpsLogId, end);
dbHelper.setTrackLengthm(gpsLogId, currentDistance);
}
currentPointsNum = 0;
currentDistance = 0;
currentRecordedLogId = -1;
} catch (SQLiteFullException e) {
e.printStackTrace();
String msg = getResources().getString(R.string.error_disk_full);
GPLog.error(this, msg, e);
toastHandler.post(new ToastRunnable(msg));
} catch (Exception e) {
String msg = getResources().getString(R.string.cantwrite_gpslog);
GPLog.error(this, msg, e);
toastHandler.post(new ToastRunnable(msg));
} finally {
isDatabaseLogging = false;
}
log("GPS Exit logging...");
}
/**
* Waits a bit before next gps query.
*
* @param waitForSecs seconds to wait.
* @return <code>false</code> if the gps got interrupted, <code>true</code> else.
*/
private boolean holdABitAndCheckLogging(int waitForSecs) {
try {
for (int i = 0; i < waitForSecs; i++) {
Thread.sleep(1000L);
if (!isDatabaseLogging) {
return false;
}
}
return true;
} catch (InterruptedException e) {
String msg = getResources().getString(R.string.cantwrite_gpslog);
GPLog.error(this, msg, e);
return true;
}
}
};
t.start();
Toast.makeText(GpsService.this, R.string.gpsloggingon, Toast.LENGTH_SHORT).show();
}
private void stopDatabaseLogging() {
isDatabaseLogging = false;
}
private static void log(String msg) {
try {
if (GPLog.LOG_HEAVY)
GPLog.addLogEntry("GPSSERVICE", null, null, msg);
} catch (Exception e) {
e.printStackTrace();
}
}
private static void logABS(String msg) {
try {
if (GPLog.LOG_ABSURD)
GPLog.addLogEntry("GPSSERVICE", null, null, msg);
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* Checks if the GPS is switched on.
* <p/>
* <p>Does not say if the GPS is supplying valid data.</p>
*
* @return <code>true</code> if the GPS is switched on.
*/
private boolean isGpsOn() {
if (locationManager == null) {
return false;
}
boolean gpsIsEnabled;
if (useNetworkPositions) {
gpsIsEnabled = locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
} else {
gpsIsEnabled = locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
}
logABS("Gps is enabled: " + gpsIsEnabled);
return gpsIsEnabled;
}
public void onLocationChanged(Location loc) {
if (loc == null) {
lastGpsLocation = null;
return;
}
lastGpsLocation = new GpsLocation(loc);
synchronized (lastGpsLocation) {
lastLocationupdateMillis = SystemClock.elapsedRealtime();
lastGpsLocation.setPreviousLoc(previousLoc);
// save last known location
double recLon = lastGpsLocation.getLongitude();
double recLat = lastGpsLocation.getLatitude();
double recAlt = lastGpsLocation.getAltitude();
PositionUtilities.putGpsLocationInPreferences(preferences, recLon, recLat, recAlt);
previousLoc = loc;
broadcast("triggered by onLocationChanged");
}
}
public void onStatusChanged(String provider, int status, Bundle extras) {
// for( GpsManagerListener activity : listeners ) {
// activity.onStatusChanged(provider, status, extras);
// }
}
public void onProviderEnabled(String provider) {
isProviderEnabled = true;
if (!isListeningForUpdates) {
registerForLocationUpdates();
}
broadcast("triggered by onProviderEnabled");
}
public void onProviderDisabled(String provider) {
isProviderEnabled = false;
broadcast("triggered by onProviderDisabled");
}
public void onGpsStatusChanged(int event) {
mStatus = locationManager.getGpsStatus(mStatus);
// check fix
boolean tmpGotFix = GpsStatusInfo.checkFix(gotFix, lastLocationupdateMillis, event);
if (!tmpGotFix) {
// check if it is just standing still
GpsStatusInfo info = new GpsStatusInfo(mStatus);
int satForFixCount = info.getSatUsedInFixCount();
if (satForFixCount > 2) {
tmpGotFix = true;
// updating loc update, assuming the still filter is giving troubles
lastLocationupdateMillis = SystemClock.elapsedRealtime();
}
}
// if (DOLOGPOSITION) {
// StringBuilder sb = new StringBuilder();
// sb.append("gotFix: ").append(gotFix).append(" tmpGotFix: ").append(tmpGotFix).append("\n");
// GPLog.addLogEntry("GPSSERVICE", sb.toString());
// }
if (tmpGotFix != gotFix) {
gotFix = tmpGotFix;
broadcast("triggered by onGpsStatusChanged on fix change: " + gotFix);
} else {
gotFix = tmpGotFix;
if (!tmpGotFix && isProviderEnabled) {
broadcast("triggered by onGpsStatusChanged on fix change: " + gotFix);
}
}
if (!gotFix) {
lastGpsLocation = null;
}
}
/**
* @param message a message that can be used for logging.
*/
private void broadcast(String message) {
Intent intent = new Intent(GPS_SERVICE_BROADCAST_NOTIFICATION);
int status = 0; // gps off
if (isProviderEnabled) {
status = 1; // gps on
}
if (isProviderEnabled && isListeningForUpdates && !gotFix) {
status = 2; // listening for updates but has no fix
}
if ((isProviderEnabled && isListeningForUpdates && gotFix && lastGpsLocation != null) || isMockMode) {
status = 3; // listening for updates and has fix
}
intent.putExtra(GPS_SERVICE_STATUS, status);
if (isDatabaseLogging || (isDatabaseLogging && isMockMode)) {
intent.putExtra(GPS_SERVICE_CURRENT_LOG_ID, currentRecordedLogId);
intent.putExtra(GPS_LOGGING_STATUS, 1);
} else {
intent.putExtra(GPS_LOGGING_STATUS, 0);
}
double lon = -1;
double lat = -1;
double elev = -1;
float accuracy = -1;
float speed = -1;
float bearing = -1;
long time = -1;
if (lastGpsLocation != null) {
lon = lastGpsLocation.getLongitude();
lat = lastGpsLocation.getLatitude();
elev = lastGpsLocation.getAltitude();
double[] lastPositionArray = new double[]{lon, lat, elev};
intent.putExtra(GPS_SERVICE_POSITION, lastPositionArray);
accuracy = lastGpsLocation.getAccuracy();
speed = lastGpsLocation.getSpeed();
bearing = lastGpsLocation.getBearing();
float[] lastPositionExtrasArray = new float[]{accuracy, speed, bearing};
intent.putExtra(GPS_SERVICE_POSITION_EXTRAS, lastPositionExtrasArray);
time = lastGpsLocation.getTime();
intent.putExtra(GPS_SERVICE_POSITION_TIME, time);
}
int maxSatellites = -1;
int satCount = -1;
int satUsedInFixCount = -1;
if (mStatus != null) {
GpsStatusInfo info = new GpsStatusInfo(mStatus);
maxSatellites = info.getMaxSatellites();
satCount = info.getSatCount();
satUsedInFixCount = info.getSatUsedInFixCount();
intent.putExtra(GPS_SERVICE_GPSSTATUS_EXTRAS, new int[]{maxSatellites, satCount, satUsedInFixCount});
}
if (DOLOGPOSITION) {
StringBuilder sb = new StringBuilder();
sb.append("GPS SERVICE INFO: ").append(message).append("\n");
sb.append("---------------------------\n");
sb.append("gps status=").append(GpsServiceStatus.getStatusForCode(status)).append("(" + status).append(")\n");
sb.append("lon=").append(lon).append("\n");
sb.append("lat=").append(lat).append("\n");
sb.append("elev=").append(elev).append("\n");
sb.append("accuracy=").append(accuracy).append("\n");
sb.append("speed=").append(speed).append("\n");
sb.append("bearing=").append(bearing).append("\n");
sb.append("time=").append(time).append("\n");
sb.append("maxSatellites=").append(maxSatellites).append("\n");
sb.append("satCount=").append(satCount).append("\n");
sb.append("satUsedInFix=").append(satUsedInFixCount).append("\n");
GPLog.addLogEntry("GPSSERVICE", sb.toString());
}
sendBroadcast(intent);
}
private class ToastRunnable implements Runnable {
String mText;
public ToastRunnable(String text) {
mText = text;
}
@Override
public void run() {
Toast.makeText(getApplicationContext(), mText, Toast.LENGTH_LONG).show();
}
}
// /////////////////////////////////////////////
// UNUSET METHODS
// /////////////////////////////////////////////
// @Override
// public void onCreate() {
// super.onCreate();
// /*
// * If the startService(intent) method is called and the service is not
// * yet running, the service object is created and the onCreate()
// * method of the service is called.
// */
// }
//
// @Override
// public ComponentName startService( Intent service ) {
// /*
// * Once the service is started, the startService(intent) method in the
// * service is called. It passes in the Intent object from the
// * startService(intent) call.
// */
// return super.startService(service);
// }
//
@Override
public IBinder onBind(Intent intent) {
return null;
}
//
// @Override
// public boolean stopService( Intent name ) {
// /*
// * You stop a service via the stopService() method. No matter how
// * frequently you called the startService(intent) method, one call
// * to the stopService() method stops the service.
// *
// * A service can terminate itself by calling the stopSelf() method.
// * This is typically done if the service finishes its work.
// */
// return super.stopService(name);
// }
}