up until now, when using the LocationClient in order to obtain the user's last known location, I had no problems, testing on Jelly Bean for example.
I got a KitKat phone to test on, and I found that there is a DEFAULT setting in Settings -> Location, that is called "Device only" and it solely relies on GPS to start, connect and obtain location. This takes A WHILE. Also, when Im indoors it might get no location whatsoever.
If I go to Settings, and switch to "High accuracy" I go back to my app and BAM location is right there.
Question is:
How do I detect which of those three location settings is set on KitKat and ask the user to change it (or directly change it myself)
The three settings are:
-device only
-battery save mode
-high accuracy
As far as I know, you can individually determine which of the services are enabled/disabled using the LocationManager class.
locationManager = (LocationManager) getApplicationContext().getSystemService(LOCATION_SERVICE);
isGPSEnabled = locationManager
.isProviderEnabled(LocationManager.GPS_PROVIDER);
isNetworkEnabled = locationManager
.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
So all you have to do would be to determine which of them are enabled, and act accordingly. If either of them are disabled, you could ask the user to turn them on.
if(!isGPSEnabled) {
startActivity(new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS));
}
if(!isNetworkEnabled) {
startActivity(new Intent(Settings.ACTION_WIRELESS_SETTINGS));
}
EDIT :
You could use the LocationManager class to just get your settings right and then use LocationClient to actually gather location information.
Related
I've been playing around with FusedLocationProvider and I found that if your phone's Location Mode is set to "Device Only" (changed in Settings - it means only GPS is enabled for location. Wifi networks and cell towers aren't used to improve accuracy), then I couldn't find a way for FusedLocationProvider to get you a location without asking the user to change it to High Accuracy (onResolutionRequired is always called).
All four LocationRequest priorities did not work:
PRIORITY_HIGH_ACCURACY - asked to switch to Location Mode "High
Accuracy"
PRIORITY_BALANCED_POWER_ACCURACY - same as above
PRIORITY_LOW_POWER - same as above
PRIORITY_NO_POWER - just didn't work
Is there no way to get location through FusedLocationProvider if the device is in this mode? I am pretty sure you can get it through the android.location.LocationManager. That seems like a huge design flaw if this is meant to be better abstraction on top of it..
You do need to use LocationManager to detect this, and I agree that it's really dumb. Use the following code:
LocationManager locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
if (locationManager != null && locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER)) {
requestLocationUpdates();
} else {
//Location request code
}
Here's a sample project I've made that incorporates this technique:
https://github.com/gavingt/basic_location_improved
I am writing an services which suggest near by facilities
I am using fuseAPI and asking for last known location so that i can suggest at least something. If I am asking user to on GPS he is uninstalling app.
I have used standard code of google to get last known location I thought it will give last known location even if user off GPS.
Google API let you choose location provider, GPS or Network (Access Point, if supported).
The way to do this it using LocationManager.NETWORK_PROVIDER
In additional, You can check if the provider is enabled (if your AP support location) with isProvideEnabled method:
boolean isNetworkEnabled = locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
boolean isGPSEnabled = locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
boolean isNetworkEnabled = locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
The first one returns true when I have the GPS on, but the second one returns false even though im connected to my wifi. On the location settings i have enabled both gps and wifi for location determinations.
We need more information like api level.
Check this thread, this must solve your problem. And if you want to get location, just use the google_play_service locatioClient.
Network Connection is closed but location provider is NetworkProvider
After some thorough search on the phone's settings, my Network Location app was disabled for some unknown reason. Wifi was turned on, and both gps and network were chosen for location settings. So after turning it back on and a phone restart, I was finally asked to allow the droid to store my location on the phone
I am using the Criteria object to get the best provider like so
final boolean isGpsEnabled = locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
if(isGpsEnabled) {
Criteria crit = new Criteria();
crit.setAccuracy(Criteria.ACCURACY_FINE);
crit.setCostAllowed(true);
crit.setPowerRequirement(Criteria.NO_REQUIREMENT);
crit.setSpeedRequirement(false);
String provider = locationManager.getBestProvider(criteria, true);
locationManager.requestLocationUpdates(provider, 600000, 0, new myLocationListener());
}
On my phone (Android 4.1) I have both "Use GPS Satellites" and "Use Wireless Networks" options enabled. Now, the above code works great when I am outdoors and it gives me the GPS location.
But, when I am indoors it does not revert to the "network" provider. It just keeps trying to get the location via GPS and never get its (I wait 1 minute or so)
When I change the code of Criteria to use Criteria.ACCURACY_COARSE then it uses "network" provider.
How do I get it to first try the GPS (because it is enabled) and because we are indoor it will not be able to connect to a satellite to then fall back to using the "network". I can't get that working easily. I state again, GPS is enabled but no access to satellites so want it to get network location instead.
Thanks.
The solution was create the location manager and attach 2 listeners to receive updates. One for GPS and another for NETWORK. You set it to receive updates fairly quickly (or depending on your own case, I just needed to get the location) You then create a method that compares the location of the GPS and Network and find which one is more accurate. You do this at most 3 times to get on average which one is returning the most accurate position and then you stop the location updates.
I'm working on an application which uses location.
My problem:
When I'm looking for the best provider, I only get the "network".
I know why but I don't know how to improve this.
In the locations settings, when I check "parameter -> location" and "security settings -> Use wireless network", the LocationManager.getBestProvider() returns only network. When it is not checked, and the GPS is active, getBestProvider returns the GPS.
What I want to do is:
When both options are checked, how to use / detect the GPS, instead of the network, as the location provider.
You have to first check whether GPS is on or not. If it is on then get the location from GPS, if not get the location from network.
To check the gps status use :
manager = (LocationManager) getSystemService(Context.LOCATION_SERVICE );
boolean statusOfGPS = manager.isProviderEnabled(LocationManager.GPS_PROVIDER);