[英]WebChromeClient doesn't ask for location permission anymore
我有一個 Android 應用程序,它使用 WebView 在 Open Street Map 上顯示 map,幾周后停止正常工作。
幾周前,當用戶在 web 頁面上點擊顯示我的位置時,Android 會提示允許應用加載當前的 position,但此時只顯示一個錯誤: Geolocation error: user denied Geolocation
。
我在 SO 和 Google 上查看了這里,看看我的代碼的某些部分是否已被棄用或被阻止,但我沒有發現任何有用的東西。 我發現的唯一信息是關於ActionBarActivity
但也使用AppCompatActivity
問題是一樣的。
MainActivity 的 MVP 版本如下(我刪除了此示例中其他無用的行):
package com.vinaysomawat.careerhigh;
import android.Manifest;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.net.Uri;
import android.os.Build;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.webkit.WebSettings;
import android.webkit.WebView;
import android.webkit.WebViewClient;
import android.webkit.GeolocationPermissions;
import android.webkit.WebChromeClient;
public class MainActivity extends ActionBarActivity {
public String mGeolocationOrigin;
public GeolocationPermissions.Callback mGeolocationCallback;
private static final int REQUEST_FINE_LOCATION=0;
public class GeoWebViewClient extends WebViewClient {
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
// When user clicks a hyperlink, load in the existing WebView
view.loadUrl(url);
return true;
}
}
public class GeoWebChromeClient extends WebChromeClient {
@Override
public void onGeolocationPermissionsShowPrompt(String origin,
GeolocationPermissions.Callback callback) {
String perm = Manifest.permission.ACCESS_FINE_LOCATION;
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M ||
ContextCompat.checkSelfPermission(MainActivity.this, perm) == PackageManager.PERMISSION_GRANTED) {
// we're on SDK < 23 OR user has already granted permission
callback.invoke(origin, true, false);
} else {
if (!ActivityCompat.shouldShowRequestPermissionRationale(MainActivity.this, perm)) {
// ask the user for permission
ActivityCompat.requestPermissions(MainActivity.this, new String[] {perm}, REQUEST_FINE_LOCATION);
// we will use these when user responds
mGeolocationOrigin = origin;
mGeolocationCallback = callback;
}
}}
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
switch (requestCode) {
case REQUEST_FINE_LOCATION:
boolean allow = false;
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// user has allowed this permission
allow = true;
}
if (mGeolocationCallback != null) {
// call back to web chrome client
mGeolocationCallback.invoke(mGeolocationOrigin, allow, false);
}
break;
}
}
WebView mywebview;
@Override
protected void onCreate(Bundle savedInstanceState) {
//Hide TopBar
getSupportActionBar().hide();
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mywebview = (WebView)findViewById(R.id.webView);
WebSettings webSettings = mywebview.getSettings();
// Empty Cache
mywebview.clearCache(true);
// Hide Zoom buttons
mywebview.getSettings().setDisplayZoomControls(false);
mywebview.getSettings().setJavaScriptCanOpenWindowsAutomatically(true);
mywebview.getSettings().setBuiltInZoomControls(true);
mywebview.setWebViewClient(new GeoWebViewClient());
// Below required for geolocation
mywebview.getSettings().setJavaScriptEnabled(true);
mywebview.getSettings().setGeolocationEnabled(true);
mywebview.setWebChromeClient(new GeoWebChromeClient());
mywebview.setWebChromeClient(new WebChromeClient() {
@Override
public boolean onCreateWindow(WebView view, boolean dialog, boolean userGesture, android.os.Message resultMsg)
{
WebView.HitTestResult result = view.getHitTestResult();
String data = result.getExtra();
Context context = view.getContext();
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(data));
context.startActivity(browserIntent);
return false;
}
});
mywebview.loadUrl("https://mycurrentlocation.net/");
}
@Override
public void onBackPressed(){
if(mywebview.canGoBack()) {
mywebview.goBack();
} else
{
super.onBackPressed();
}
}
@Override
public boolean onCreateOptionsMenu(Menu menu){
getMenuInflater().inflate(R.menu.menu_main, menu);
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item){
int id = item.getItemId();
if(id == R.id.action_settings){
return true;
}
return super.onOptionsItemSelected(item);
}
}
當我單擊按鈕顯示我當前的 position 時,在 Android Studio 中我得到以下日志:
E/Resource: printErrorResource,可能不是錯誤,因為模塊對 =android.content.res.HwResourcesImpl.printErrorResource:2634 android.content.res.ResourcesImpl.openRawResource:444 android.content.res.Resources 調用的資源具有實體訪問權限。 openRawResource:1418 android.content.res.Resources.openRawResource:1362 android.support.v4.graphics.TypefaceCompatBaseImpl.createFromResourcesFontFile:304 android.support.v4.graphics.TypefaceCompat.createFromResourcesFontFile:232 I/ResourcesImplEx: The apk asset path = ApkAssets {path=/system/framework/framework-res.apk} apk資源路徑=ApkAssets{path=/system/framework/framework-res-hwext.apk} apk資源路徑=ApkAssets{path=/preas/oversea/ overlay/GmsConfigOverlay.apk} apk資源路徑 = ApkAssets{path=/preas/oversea/overlay/GmsGsaConfigOverlay.apk} apk資源路徑 = ApkAssets{path=/preas/oversea/overlay/GoogleExtServicesConfigOverlay.apk} apk資源路徑= ApkAssets{path=/preas/oversea/o verlay/GoogleModuleMetadataConfigOverlay.apk} apk資產路徑=ApkAssets{path=/preas/oversea/overlay/GooglePermissionControllerConfigOverlay.apk} apk資產路徑=ApkAssets{path=/hw_product/overlay/frameworkResOverlay.apk} apk資產路徑=ApkAssets {path=/odm/overlay/frameworkResOverlay.apk} apk 資產路徑 = ApkAssets{path=/data/app/com.vinaysomawat.careerhigh-3JvsuNOhaJTzUZrEdMaQnA==/base.apk} I/ResourcesImplEx: apk 資產路徑 = ApkAssets {path=/data/app/com.google.android.webview-Lw6x1ElnmD4d1UEVSG95iA==/base.apk} apk資產路徑=ApkAssets{path=/data/app/com.google.android.webview-Lw6x1ElnmD4d1UEVSG95iA==/ split_config.it.apk} apk資源路徑=ApkAssets{path=/data/app/com.google.android.webview-Lw6x1ElnmD4d1UEVSG95iA==/split_weblayer.apk} apk資源路徑=ApkAssets{path=/data/app/ com.google.android.trichromelibrary_489608833-ndmJcgRaxXQPmZ7r_KqT-w==/base.apk}
然后顯示此日志(我認為這是表示無法加載位置的錯誤橫幅):
D/HiTouch_PressGestureDetector: onAttached, package=com.vinaysomawat.careerhigh, windowType=2, mHiTouchRestricted=false D/mali_winsys: EGLint new_window_surface(egl_winsys_display *, void *, EGLSurface, EGLConfig, egl_winsys_surface **, EGLBoolean) 返回 0x3000
是的。 我有一個類似的問題。 android webview 和地理位置的位置權限不再由 webChromeClient 處理。 現在,它們的處理方式與 Android 原生應用程序相同。 我使用以下內容作為指南,效果很好。
使用這個庫而不是擁有適用於 Android 的 WebView 組件
https://github.com/delight-im/Android-AdvancedWebView
在這個庫中,權限處理得很好
我希望這對你有幫助
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.