我试图使用纬度和经度向用户显示两个位置之间的持续时间。我的权限有问题,我不知道如何处理它。
这是我的doInBackground代码:
protected String[] doInBackground(String... params) {
try {
LocationManager locationManager = (LocationManager) MyCustomHomeActivity.this
.getSystemService(LOCATION_SERVICE);
// getting GPS status
boolean isGPSEnabled = locationManager
.isProviderEnabled(LocationManager.GPS_PROVIDER);
// getting network status
boolean isNetworkEnabled = locationManager
.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
if (!isGPSEnabled && !isNetworkEnabled) {
// no network provider is enabled
} else {
// if GPS Enabled get lat/long using GPS Services
if (isGPSEnabled) {
if (locationManager != null) {
location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
if (location != null) {
latitude = location.getLatitude();
longitude = location.getLongitude();
}
}
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
String shuLat = "41.2207188";
String shuLong = "-73.24168179999999";
String forecastJsonStr = null;
String myUrlSetup = "https://maps.googleapis.com/maps/api/directions/json?origin="+latitude + "," + longitude +"&destination="+shuLat +"," + shuLong + "&departure_time=now&traffic_model=best_guess&key=AIzaSyB6l8vrnspw2-1Q_cnzO03JlAsIOMl-7bs";
HttpURLConnection urlConnection = null;
BufferedReader reader = null;
try {
URL url;
url = new URL(myUrlSetup);
// Create the request to GoogleMapAPI, and open the connection
urlConnection = (HttpURLConnection) url.openConnection();
urlConnection.setRequestMethod("GET");
urlConnection.connect();
// Read the input stream into a String
InputStream inputStream = urlConnection.getInputStream();
StringBuffer buffer = new StringBuffer();
if (inputStream == null) {
// Nothing to do.
return null;
}
System.out.println("I am in doInBackground step3");
reader = new BufferedReader(new InputStreamReader(inputStream));
String line;
while ((line = reader.readLine()) != null) {
// Since it's JSON, adding a newline isn't necessary (it won't affect parsing)
// But it does make debugging a *lot* easier if you print out the completed
// buffer for debugging.
buffer.append(line + "\n");
}
if (buffer.length() == 0) {
// Stream was empty. No point in parsing.
return null;
}
forecastJsonStr = buffer.toString();
Log.v(LOG_TAG, "Forecast string: " + forecastJsonStr);
} catch (IOException e) {
Log.e(LOG_TAG, "Error ", e);
// If the code didn't successfully get the weather data, there's no point in attemping
// to parse it.
return null;
} finally {
if (urlConnection != null) {
urlConnection.disconnect();
}
if (reader != null) {
try {
reader.close();
} catch (final IOException e) {
Log.e(LOG_TAG, "Error closing stream", e);
}
}
}
try {
System.out.println("I am just in front of calling getDurationDataFromJson");
return getDurationDataFromJson(forecastJsonStr);
} catch (JSONException e) {
Log.e(LOG_TAG, e.getMessage(), e);
e.printStackTrace();
}
return new String[0];
}//end doInBackground
这是我的getDurationDataFromJSON代码:
private String[] getDurationDataFromJson(String forecastJsonStr)
throws JSONException {
// These are the names of the JSON objects that need to be extracted.
final String OWM_ROUTES = "routes";
final String OWM_LEGS = "legs";
final String OWM_DURATION = "duration";
final String OWM_TEXT = "text";
String[] resultStrs = new String[0];
String duration;
JSONObject durationJson = new JSONObject(forecastJsonStr);
JSONArray routeArray = durationJson.getJSONArray(OWM_ROUTES);
JSONArray legArray = routeArray.getJSONObject(0).getJSONArray(OWM_LEGS);
//Duration
JSONObject durationObj = legArray.getJSONObject(0).getJSONObject(OWM_DURATION);
duration = durationObj.getString(OWM_TEXT);
resultStrs[0] = duration;
System.out.println("Duration is: " + duration);
for (String s : resultStrs) {
System.out.println("Duration entry: " + s);
Log.v(LOG_TAG, "Duration entry: " + s);
}
return resultStrs;
}
我面临的麻烦是doInBackGround代码中的以下部分:
location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
错误是:
Call requires permission which may be rejected by user: code should explicitly check to see if permission is available(with `check permission`) or explicitly handle a potential `SecurityException`.
我不确定我是否朝着正确的方向前进。请指导我完成这个。
答案 0 :(得分:1)
使用Android API级别(23),在运行时请求权限,这里有官方文档:
https://developer.android.com/training/permissions/requesting.html
基本上,您需要检查设备Android API级别是否> = 23,如果是,请求所需的权限。尝试这样的事情:
if ( Build.VERSION.SDK_INT >= 23)
//Ask for needed permissions following the docs mentioned above
}
我希望这有帮助!
答案 1 :(得分:0)
我建议你使用FusedLocationProviderApi 获得最后的已知位置。
但在使用位置做任何事情之前,您需要确保已提供
。
现在我来到了你的观点。从API Level-23开始,android会出现明确的权限搜索功能。为此,您需要执行一些步骤。
我特此附上一些代码块供您使用 -
检查所需的权限状态和设备位置服务
public boolean isLocationEnabled() {
int locationMode = 0;
String locationProviders;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
try {
locationMode = Settings.Secure.getInt(context.getContentResolver(), Settings.Secure.LOCATION_MODE);
} catch (Settings.SettingNotFoundException e) {
e.printStackTrace();
}
return locationMode != Settings.Secure.LOCATION_MODE_OFF;
} else {
locationProviders = Settings.Secure.getString(context.getContentResolver(), Settings.Secure.LOCATION_PROVIDERS_ALLOWED);
return !TextUtils.isEmpty(locationProviders);
}
}
public boolean hasCoarseLocationPermission() {
return ContextCompat.checkSelfPermission(activity, Manifest.permission.ACCESS_COARSE_LOCATION) == PackageManager.PERMISSION_GRANTED;
}
public boolean hasFineLocationPermission() {
return ContextCompat.checkSelfPermission(activity, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED;
}

现在,在检查并提供expicit权限后启动您的活动/片段
private void initiateYourActivityCallAfterCheckingPermission() {
if (hasCoarseLocationPermission() && hasFineLocationPermission()) {
if (locationUtil.isLocationEnabled()) {
startYourLocationActivity();
}
} else if (!hasFineLocationPermission() && hasCoarseLocationPermission()) {
requestBothLocationPermission();
} else if (hasFineLocationPermission() && hasCoarseLocationPermission()) {
requestFineLocationPermission();
} else if (hasFineLocationPermission() && !hasCoarseLocationPermission()) {
requestCoarseLocationPermission();
}
}
private void requestBothLocationPermission() {
if (ActivityCompat.shouldShowRequestPermissionRationale(SplashActivity.this, Manifest.permission.ACCESS_COARSE_LOCATION)
&& ActivityCompat.shouldShowRequestPermissionRationale(SplashActivity.this, Manifest.permission.ACCESS_FINE_LOCATION)) {
} else {
ActivityCompat.requestPermissions(SplashActivity.this,
new String[]{Manifest.permission.ACCESS_COARSE_LOCATION, Manifest.permission.ACCESS_FINE_LOCATION},
REQUEST_BOTH_LOCATION);
}
}
private void requestCoarseLocationPermission() {
if (ActivityCompat.shouldShowRequestPermissionRationale(SplashActivity.this,
Manifest.permission.ACCESS_COARSE_LOCATION)) {
} else {
ActivityCompat.requestPermissions(SplashActivity.this,
new String[]{Manifest.permission.ACCESS_COARSE_LOCATION}, REQUEST_COARSE_LOCATION);
}
}
private void requestFineLocationPermission() {
if (ActivityCompat.shouldShowRequestPermissionRationale(SplashActivity.this,
Manifest.permission.ACCESS_FINE_LOCATION)) {
} else {
ActivityCompat.requestPermissions(SplashActivity.this,
new String[]{Manifest.permission.ACCESS_FINE_LOCATION}, REQUEST_FINE_LOCATION);
}
}
/**
* to process permission result
*/
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
switch (requestCode) {
case General.REQUEST_BOTH_LOCATION:
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED && grantResults[1] == PackageManager.PERMISSION_GRANTED) {
startYourLocationActivity();
}
break;
case General.REQUEST_COARSE_LOCATION:
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
startYourLocationActivity();
}
break;
case General.REQUEST_FINE_LOCATION:
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
startYourLocationActivity();
}
break;
}
}

希望这会有所帮助。