How can I check the current status of the GPS receiver? I already checked the LocationListener
onStatusChanged method but somehow it seems that is not working,
The GPS icon seems to change its state according to received broadcast intents. You can change its state yourself with the following code samples:
Notify that the GPS has been enabled:
Intent intent = new Intent("android.location.GPS_ENABLED_CHANGE");
intent.putExtra("enabled", true);
sendBroadcast(intent);
Notify that the GPS is receiving fixes:
Intent intent = new Intent("android.location.GPS_FIX_CHANGE");
intent.putExtra("enabled", true);
sendBroadcast(intent);
Notify that the GPS is no longer receiving fixes:
Intent intent = new Intent("android.location.GPS_FIX_CHANGE");
intent.putExtra("enabled", false);
sendBroadcast(intent);
Notify that the GPS has been disabled:
Intent intent = new Intent("android.location.GPS_ENABLED_CHANGE");
intent.putExtra("enabled", false);
sendBroadcast(intent);
Example code to register receiver to the intents:
// MyReceiver must extend BroadcastReceiver
MyReceiver receiver = new MyReceiver();
IntentFilter filter = new IntentFilter("android.location.GPS_ENABLED_CHANGE");
filter.addAction("android.location.GPS_FIX_CHANGE");
registerReceiver(receiver, filter);
By receiving these broadcast intents you can notice the changes in GPS status. However, you will be notified only when the state changes. Thus it is not possible to determine the current state using these intents.
Ok, so let's try a combination of all the answers and updates so far and do something like this:
LocationManager
LocationManager
with addGpsStatusListenerThe GPS listener could be something like this:
GpsStatus.Listener listener = new GpsStatus.Listener() {
void onGpsStatusChanged(int event) {
if (event == GPS_EVENT_SATELLITE_STATUS) {
GpsStatus status = mLocManager.getGpsStatus(null);
Iterable<GpsSatellite> sats = status.getSatellites();
// Check number of satellites in list to determine fix state
}
}
}
The APIs are a bit unclear about when and what GPS and satellite information is given, but I think an idea would be to look at how many satellites are available. If it's below three, then you can't have a fix. If it's more, then you should have a fix.
Trial and error is probably the way to go to determine how often Android reports satellite info, and what info each GpsSatellite
object contains.
If you just need to know if there's a fix, then check for the last known location provided by the GPS receiver and check the .getTime() value to know how old is that. If it's recent enough (like... a few seconds) you have a fix.
LocationManager lm = (LocationManager)context.getSystemService(LOCATION_SERVICE);
Location loc = lm.getLastKnownLocation(LocationManager.GPS_PROVIDER);
// Get the time of the last fix
long lastFixTimeMillis = loc.getTime();
... and finally compare that to current date time (In UTC!). If it's recent enough you have a fix.
I do that in my app and so far so good.
I may be wrong but it seems people seem to be going way off-topic for
i just need to know if the gps icon at the top of the screen is blinking (no actual fix)
That is easily done with
LocationManager lm = (LocationManager) getSystemService(LOCATION_SERVICE);
boolean gps_on = lm.isProviderEnabled(LocationManager.GPS_PROVIDER);
To see if you have a solid fix, things get a little trickier:
public class whatever extends Activity {
LocationManager lm;
Location loc;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
lm = (LocationManager) getSystemService(LOCATION_SERVICE);
loc = null;
request_updates();
}
private void request_updates() {
if (lm.isProviderEnabled(LocationManager.GPS_PROVIDER)) {
// GPS is enabled on device so lets add a loopback for this locationmanager
lm.requestLocationUpdates(LocationManager.GPS_PROVIDER,0, 0, locationListener);
}
}
LocationListener locationListener = new LocationListener() {
public void onLocationChanged(Location location) {
// Each time the location is changed we assign loc
loc = location;
}
// Need these even if they do nothing. Can't remember why.
public void onProviderDisabled(String arg0) {}
public void onProviderEnabled(String provider) {}
public void onStatusChanged(String provider, int status, Bundle extras) {}
};
Now whenever you want to see if you have fix?
if (loc != null){
// Our location has changed at least once
blah.....
}
If you want to be fancy you can always have a timeout using System.currentTimeMillis() and loc.getTime()
Works reliably, at least on an N1 since 2.1.
Maybe it's the best possiblity to create a TimerTask that sets the received Location to a certain value (null?) regularly. If a new value is received by the GPSListener it will update the location with the current data.
I think that would be a working solution.
With LocationManager you can getLastKnownLocation() after you getBestProvider(). This gives you a Location object, which has the methods getAccuracy() in meters and getTime() in UTC milliseconds
Does this give you enough info?
Or perhaps you could iterate over the LocationProviders and find out if each one meetsCriteria( ACCURACY_COARSE )