如何在Android中以编程方式获取API 23及更高版本中的位置(lat,lng)?

时间:2016-03-22 10:55:52

标签: android android-6.0-marshmallow android-location android-gps

我正在开发一个启用GPS并获取当前位置的应用程序。我的代码在所有Android版本中都运行良好,期望API 23即Marshmallows。我正在测试Nexus 5(API 23),Galaxy Note 3(API 22)。

这是我的代码

    public void program()
{
     locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
    locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, MINIMUM_TIME_BETWEEN_UPDATES, MINIMUM_DISTANCE_CHANGE_FOR_UPDATES, new MyLocationListener());

    if (!locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER)) {

        AlertDialog.Builder builder = new AlertDialog.Builder(NearBy.this);
        builder.setTitle("Location Service is Not Active");
        builder.setMessage("Please Enable your location services").setCancelable(false)
                .setPositiveButton("OK", new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int id) {

                        Intent intent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
                        startActivity(intent);

                    }
                });
        AlertDialog alert = builder.create();
        alert.show();
    } else if (locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER)) {
        Location location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
        Geocoder geocoder = new Geocoder(this, Locale.getDefault());
        List<Address> addresses = null;
        try {
            addresses = geocoder.getFromLocation(location.getLatitude(), location.getLongitude(), 1);

            final String cityName = addresses.get(0).getAddressLine(0) + " ";
            String stateName = addresses.get(0).getAddressLine(1) + " ";
            String countryName = addresses.get(0).getAddressLine(2) + " ";
            String country = addresses.get(0).getCountryName() + " ";
            String Area = addresses.get(0).getSubAdminArea() + " ";
            String Area1 = addresses.get(0).getAdminArea() + " ";
            String Area2 = addresses.get(0).getLocality() + " ";
            String Area3 = addresses.get(0).getSubLocality();
            Log.e("Locaton", cityName + stateName + countryName + country + Area + Area1 + Area2 + Area3);
        } catch (IOException e) {
            e.printStackTrace();
        } catch (NullPointerException e) {
            e.printStackTrace();
        }
    }
}

我在

收到NullpointerException
         addresses = geocoder.getFromLocation(location.getLatitude(), location.getLongitude(), 1);

仅适用于Nexus 5(API 23)。我还在Mainfest和运行时都授予了权限(ACCESS_FINE_LOCATION和ACCESS_COARSE_LOCATION)。

请为此提供解决方案。

已更新

我已经改变了我的代码。我创建了一个GPSTracker类,我得到了lat,Lng为0

GPSTracker.java

  public class GPSTracker extends Activity implements LocationListener {
private final Context mContext;
// flag for GPS status
boolean isGPSEnabled = false;
// flag for network status
boolean isNetworkEnabled = false;
// flag for GPS status
boolean canGetLocation = false;
Location location; // location
double latitude; // latitude
double longitude; // longitude

private static final long MIN_DISTANCE_CHANGE_FOR_UPDATES = 10; // 10 meters

private static final long MIN_TIME_BW_UPDATES = 1000 * 60 * 1; // 1 minute

protected LocationManager locationManager;

public GPSTracker(Context context) {
    this.mContext = context;
    getLocation();
}

public Location getLocation() {
    try {
        locationManager = (LocationManager) mContext
                .getSystemService(LOCATION_SERVICE);


        isGPSEnabled = locationManager
                .isProviderEnabled(LocationManager.GPS_PROVIDER);

        isNetworkEnabled = locationManager
                .isProviderEnabled(LocationManager.NETWORK_PROVIDER);
        if (!isGPSEnabled && !isNetworkEnabled) {

        } else {
            this.canGetLocation = true;
            if (isNetworkEnabled) {
                locationManager.requestLocationUpdates(
                        LocationManager.NETWORK_PROVIDER,
                        MIN_TIME_BW_UPDATES,
                        MIN_DISTANCE_CHANGE_FOR_UPDATES, this);
                Log.d("Network", "Network");
                if (locationManager != null) {
                    location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
                    if (location != null) {
                        latitude = location.getLatitude();
                        longitude = location.getLongitude();
                    }
                }
            }

            if (isGPSEnabled) {
                if (location == null) {
                    locationManager.requestLocationUpdates(
                            LocationManager.GPS_PROVIDER,
                            MIN_TIME_BW_UPDATES,
                            MIN_DISTANCE_CHANGE_FOR_UPDATES, this);
                    Log.d("GPS Enabled", "GPS Enabled");
                    if (locationManager != null) {
                        location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
                        if (location != null) {
                            latitude = location.getLatitude();
                            longitude = location.getLongitude();
                        }
                    }
                }
            }
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
    return location;
}
@TargetApi(Build.VERSION_CODES.M)
public void stopUsingGPS() {
    if (locationManager != null) {
        if (checkSelfPermission(Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && checkSelfPermission(Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {

            return;
        }
        locationManager.removeUpdates(GPSTracker.this);
    }
}


public double getLatitude() {
    if (location != null) {
        latitude = location.getLatitude();
    }

    return latitude;
}

public double getLongitude() {
    if (location != null) {
        longitude = location.getLongitude();
    }

    return longitude;
}


public boolean canGetLocation() {
    return this.canGetLocation;
}


public void showSettingsAlert() {
    AlertDialog.Builder alertDialog = new AlertDialog.Builder(mContext);

    alertDialog.setTitle("GPS is settings");

    alertDialog.setMessage("GPS is not enabled. Do you want to go to settings menu?");

    alertDialog.setPositiveButton("Settings", new DialogInterface.OnClickListener() {
        public void onClick(DialogInterface dialog, int which) {
            Intent intent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
            mContext.startActivity(intent);
        }
    });

    alertDialog.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        public void onClick(DialogInterface dialog, int which) {
            dialog.cancel();
        }
    });

    alertDialog.show();
}

@Override
public void onLocationChanged(Location currentLocation) {

    this.location = currentLocation;
    getLatitude();
    getLongitude();

}

@Override
public void onProviderDisabled(String provider) {

}

@Override
public void onProviderEnabled(String provider) {


}

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

}
}

2 个答案:

答案 0 :(得分:2)

<强>问题

The location obtained may be null if the last know location could not be found due to various reasons. Read about it in the docs [here][2]

原因/我如何调试

  1. getFromLocation根据文档不会抛出nullpointer,因此问题出在您的位置对象中。

    Read here about this method

  2. <强>解决方法

    Location location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
    

    检查上述步骤中获得的位置是否为NULL,然后继续使用地理编码器。

    代码段

    ...
    else if (locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER)) {
        Location location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
        if(location == null) {
           log.d("TAG", "The location could not be found");
           return; 
        }
        //else, proceed with geocoding.
        Geocoder geocoder = new Geocoder(this, Locale.getDefault());
    

    获取位置 - 示例

    Read here

    完整代码

    View it here

答案 1 :(得分:0)

首先在marshmallow中添加运行时的所有权限。否则请重新启动手机,然后重新检查。