GetLastKnownLocation 返回 null

我读过一些关于这个的问题,但是我没有找到我需要的答案。

现在,我已经设置好了我的地图,我想获取我当前的 GPS 位置。 我已经检查了我的变量不是 NULL,但是我的结果来自:

getLastKnownLocation(provider, false);

不过也没有,所以这就是我需要帮助的地方。 我已经为 COARSE + FINE 位置添加了权限。但是我的手机通常禁用各种网络数据,因为我不喜欢我的电话账单中不可预测的数据流费用。因此,我只有 WiFi 启用和连接到这个测试。

还有什么我需要启用,以便这是可能的?我认为 WiFi 应该足够了吧?

89671 次浏览

You are trying to get the cached location from the Network Provider. You have to wait for a few minutes till you get a valid fix. Since the Network Provider's cache is empty, you are obviously getting a null there..

Use this method to get the last known location:

LocationManager mLocationManager;
Location myLocation = getLastKnownLocation();


private Location getLastKnownLocation() {
mLocationManager = (LocationManager)getApplicationContext().getSystemService(LOCATION_SERVICE);
List<String> providers = mLocationManager.getProviders(true);
Location bestLocation = null;
for (String provider : providers) {
Location l = mLocationManager.getLastKnownLocation(provider);
if (l == null) {
continue;
}
if (bestLocation == null || l.getAccuracy() < bestLocation.getAccuracy()) {
// Found best last known location: %s", l);
bestLocation = l;
}
}
return bestLocation;
}

Add this code

if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
return;
}

before the function:

locationManagerObject.requestLocationUpdates(LocationManager.GPS_PROVIDER, MINIMUM_TIME_BETWEEN_UPDATES, MINIMUM_DISTANCE_CHANGE_FOR_UPDATES, new LocationListener()) as well as the function: locationManagerObject.getLastKnownLocation(LocationManager.GPS_PROVIDER)

Replace ur line with

Location location = LocationServices.FusedLocationApi.getLastLocation(googleApiClient);

you are mixing the new and the old location API's together when you shouldnt.

to get the last known location all your have to do is call

compile "com.google.android.gms:play-services-location:11.0.1"
mLocationClient.getLastLocation();

once the location service was connected.

read how to use the new location API

http://developer.android.com/training/location/retrieve-current.html#GetLocation

 private void getLastLocationNewMethod(){
FusedLocationProviderClient mFusedLocationClient = LocationServices.getFusedLocationProviderClient(this);
mFusedLocationClient.getLastLocation()
.addOnSuccessListener(new OnSuccessListener<Location>() {
@Override
public void onSuccess(Location location) {
// GPS location can be null if GPS is switched off
if (location != null) {
getAddress(location);
}
}
})
.addOnFailureListener(new OnFailureListener() {
@Override
public void onFailure(@NonNull Exception e) {
Log.d("MapDemoActivity", "Error trying to get last GPS location");
e.printStackTrace();
}
});
}

Try this it works good for me :-

LocationManager mLocationManager;
Location myLocation = getLastKnownLocation();


private Location getLastKnownLocation() {
Location oldLoc;
while (true){
oldLoc = mLocationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
if (oldLoc == null){
continue;
}
else {
break;
}
}
return oldLoc;
}

You can use NETWORK_PROVIDER in place of GPS_PROVIDER for faster results..

I had this problem in Xamarin.Android.

Location location = locationManager.GetLastKnownLocation(provider); was returning null value. I checked my code and got to know that I had just requested permission for ACCESS_COARSE_LOCATION. I added code to request permission for ACCESS_FINE_LOCATION and now it was not returning null. Here is my code:

void AskPermissions()
{
if (CheckSelfPermission(Manifest.Permission.AccessCoarseLocation) != (int)Permission.Granted ||
CheckSelfPermission(Manifest.Permission.AccessFineLocation) != (int)Permission.Granted)
RequestPermissions(new string[] { Manifest.Permission.AccessCoarseLocation, Manifest.Permission.AccessFineLocation }, 0);
else
GetLocation();
}


public override void OnRequestPermissionsResult(int requestCode, string[] permissions, [GeneratedEnum] Android.Content.PM.Permission[] grantResults)
{
if (CheckSelfPermission(Manifest.Permission.AccessCoarseLocation) == (int)Permission.Granted &&
CheckSelfPermission(Manifest.Permission.AccessFineLocation) == (int)Permission.Granted)
GetLocation();
else
Log.Info(tag, "Permission not Granted: Please enter desired Location manually.");
}


void GetLocation()
{
locationManager = (LocationManager)GetSystemService(LocationService);
provider = locationManager.GetBestProvider(new Criteria(), false);
Location location = locationManager.GetLastKnownLocation(provider);
if (location != null)
Log.Info(tag, "Location Lat: " + location.Latitude + " Lon: " + location.Longitude);
else
Log.Info(tag, "Location is null");
}

In case anyone coming from Xamarin.Android (C#) would find it useful. For Java or Android Studio the code would be similar withs some minor Syntax changes like GetLastKnownLocation() will be getLastKnownLocation() as method names in Java start with lowercase letters while in C# method names start with Uppercase letters.

I liked this solution to update location:

Update location

In resume, add the condition:

Location myLocation = getLastKnownLocation();
if (myLocation == null) {
locationManager.requestLocationUpdates(
LocationManager.PASSIVE_PROVIDER,
MIN_TIME_BW_UPDATES,
MIN_DISTANCE_CHANGE_FOR_UPDATES, this);
Log.d("GPS", "GPS Enabled");
}

And maybe is some basic, but check that GPS is ON.

private void getLastLocation()
{
LocationManager locationManager = (LocationManager) this.getSystemService(Context.LOCATION_SERVICE);




LocationListener locationListener = new LocationListener() {
public void onLocationChanged(Location location) {
Log.e("location",location.getLatitude()+"");


}


public void onStatusChanged(String provider, int status, Bundle extras) {}


public void onProviderEnabled(String provider) {}


public void onProviderDisabled(String provider) {}
};


locationManager.requestSingleUpdate(LocationManager.NETWORK_PROVIDER,locationListener,null);


}

// This will help you for fetching location after gps enable

locationManager.requestSingleUpdate(LocationManager.NETWORK_PROVIDER,locationListener,null);