Sup*_*ngs 15 android webview android-webview
问题很简单.在应用程序中,我们希望跟踪显示的当前URL.为此,我们使用shouldOverrideUrlLoading
回调来WebViewClient
保存url到每个更新的类字段.这是相关代码:
mWebView.getSettings().setJavaScriptEnabled(true);
mWebView.getSettings().setDomStorageEnabled(true);
mWebView.setWebViewClient(new WebViewClient() {
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
mCurrentUrl = url;
// If we don't return false then any redirect (like redirecting to the mobile
// version of the page) or any link click will open the web browser (like an
// implicit intent).
return false;
}
@Override
public void onPageFinished(WebView view, String url) {
super.onPageFinished(view, url);
...
}
});
mWebView.loadUrl(mInitialUrl);
Run Code Online (Sandbox Code Playgroud)
但是,至少有一种情况,即回调永远不会被触发,并且mCurrentUrl字段不会更新.
网址:https://m.pandora.net/es-es/products/bracelets/556000
上次更新的URL(在单击产品时永远不会调用shouldOverrideUrlLoading):https://m.pandora.net/es-es/products/bracelets
我尝试过像onPageStarted()这样的回调,但是url也被过滤了,因为它的受保护代码似乎没有可访问的上游.
阅读有关WebView的android文档我发现了这个:
https://developer.android.com/guide/webapps/migrating.html#URLs
在请求资源和解析使用自定义URL方案的链接时,新WebView会应用其他限制.例如,如果实现了诸如shouldOverrideUrlLoading()或shouldInterceptRequest()之类的回调,则WebView仅针对有效URL调用它们.
但仍然没有意义,因为上面的网址是通用的,应该符合标准.
任何替代或解决方案?
Leo*_*ilä 21
当您单击该网页上的产品时,它会使用JavaScript加载新内容,并使用HTML5历史记录API更新地址栏中的可见URL .
从上面的MDN文章:
这将导致URL栏显示http://mozilla.org/bar.html,但不会导致浏览器加载bar.html甚至检查bar.html是否存在.
这些有时被称为单页面应用程序.由于实际加载的页面不会更改,因此不会调用页面加载的WebView回调.
如果您确切地知道要拦截哪种HTTP请求,则可以使用shouldInterceptRequest
为每个请求调用的回调.Web应用程序可能会从API加载一些数据,例如,当显示产品时,您可以检测到该数据.
如果无法检测到这一点,但您可以控制Web应用程序,则可以使用Android JavaScript界面直接从Web页面调用Android应用程序中的方法.
如果您无法控制加载的页面,您仍然可以尝试将本地JavaScript文件注入网页并观察何时使用历史API,然后通过JS接口调用Android应用程序中的方法.我尝试使用上一个链接中描述的方法在Chrome中观察这些事件,它似乎工作正常.
也许这对某人有帮助,虽然问题中的签名是正确的,但 Android Studio 建议使用以下方法签名:
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
Run Code Online (Sandbox Code Playgroud)
然后就再也没有打电话过来。我花了一段时间才注意到正确的签名是:
public boolean shouldOverrideUrlLoading(WebView view, String url) {
Run Code Online (Sandbox Code Playgroud)
抱歉,如果这不是 100% 符合问题,但我相信这可能会对处于相同情况的人有所帮助。注意到第二个参数不同并不总是容易的。
请省略 mWebView.getSettings().setDomStorageEnabled(true);
然后再试一次,如果发现一个新的url会调用 shouldOverrideUrl()
小智 7
在偶然发现这个问题并寻找解决方案之后,我找到了最适合我的解决方案
override fun doUpdateVisitedHistory(view: WebView?, url: String?, isReload: Boolean) {
// your code here
super.doUpdateVisitedHistory(view, url, isReload)
}
Run Code Online (Sandbox Code Playgroud)
您可以尝试的另一种方法:通过 javascript side 捕获 url。使用以下命令初始化您的 webView:
webView.addJavascriptInterface(new WebAppInterface(getActivity()), "Android");
Run Code Online (Sandbox Code Playgroud)
页面完全加载后(您可以使用算法来检查,如下/sf/answers/433989811/),然后:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
webView.evaluateJavascript("(function() {return window.location.href;})", new ValueCallback<String>() {
@Override
public void onReceiveValue(String url) {
//do your scheme with variable "url"
}
});
} else {
webView.loadUrl("javascript:Android.getURL(window.location.href);");
}
Run Code Online (Sandbox Code Playgroud)
并声明你的WebAppInterface
:
public class WebAppInterface {
Activity mContext;
public WebAppInterface(Activity c) {
mContext = c;
}
@JavascriptInterface
public void getURL(final String url) {
mContext.runOnUiThread(new Runnable() {
@Override
public void run() {
//do your scheme with variable "url" in UIThread side. Over here you can call any method inside your activity/fragment
}
});
}
}
Run Code Online (Sandbox Code Playgroud)
您可以执行类似的操作来获取 url 或页面内的其他任何内容。
我遇到了与您相同的问题,并且完成了通过侦听回调到WebViewChromeClient的扩展
public void onReceivedTitle(WebView view, String title)
mWebView.setWebChromeClient(mSWWebChromeClient);
private WebChromeClient mSWWebChromeClient = new WebChromeClient() {
@Override
public void onReceivedTitle(WebView view, String title) {
super.onReceivedTitle(view, title);
if (!view.getUrl().equals(mCurrentUrl)) {
mCurrentUrl = view.getUrl();
//make something
}
}
};
Run Code Online (Sandbox Code Playgroud)
对我来说,问题出在下面——
mWebView.getSettings().setSupportMultipleWindows(true);
Run Code Online (Sandbox Code Playgroud)
删除它后,shouldOverrideUrlLoading 被调用。
归档时间: |
|
查看次数: |
18013 次 |
最近记录: |