In webview android I am trying to load a url and in order to check if the load of this url is done successfully (internet connection was available, the server was up etc) I was under the impression that webview.loadUrl would throw exceptions, but wrong! as it explicitly is stated in here "an exception will NOT be thrown".
在webview android中,我正在尝试加载一个url,为了检查这个url的加载是否成功(internet连接是可用的,服务器是打开的等等),我对webview的印象是。loadUrl将抛出异常,但错误!因为它在这里显式地声明了“一个异常不会被抛出”。
So how can I check to see if webview.loadUrl did not fail ?
我怎么检查webview。loadUrl没有失败?
3 个解决方案
#1
12
Unfortunately, currently there is no easy way in WebView to ensure that everything on the page has been loaded successfully. We are hoping for a better API to come up in future version. Let me explain what you can do now.
不幸的是,目前WebView中没有简单的方法来确保页面上的所有内容都已成功加载。我们希望在未来的版本中出现更好的API。让我解释一下你现在能做什么。
First of all, in order to detect any problems that prevent WebView from making a connection to the server for loading your main page (e.g. bad domain name, I/O error, etc.), you should use WebViewClient.onReceivedError
callback as other people correctly suggest:
首先,为了检测任何阻止WebView连接到服务器以加载您的主页的问题(例如,坏域名、I/O错误等),您应该使用WebViewClient。正如其他人正确建议的那样,onReceivedError回调:
public class MyWebViewClient extends WebViewClient {
@Override
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
// Make a note about the failed load.
}
}
myWebView.setWebViewClient(new MyWebViewClient());
If the server connection was successful, and the main page was retrieved and parsed, you will receive WebView.onPageFinished
callback, so you also need to have this in your WebViewClient
subclass:
如果服务器连接成功,主页面被检索和解析,您将收到WebView。onPageFinished回调,所以您还需要在WebViewClient子类中包含这个:
public class MyWebViewClient extends WebViewClient {
...
@Override
public void onPageFinished(WebView view, String url) {
// Make a note that the page has finished loading.
}
...
}
The caveat here is that if you have received an HTTP error from the server (e.g. a 404 or a 500 error), this callback will be called anyway, it's just the content that you will get in your WebView will be a server error page. People suggest different ways of how to deal with it, see the answers here: How can I check from Android WebView if a page is a "404 page not found"? Basically, it really depends on what you expect to be a "good" page and a "error" page. Unfortunately, there is currently no way for the app to get the HTTP response code from WebView.
这里需要注意的是,如果您从服务器接收到HTTP错误(例如404或500错误),这个回调将被调用,您在WebView中获得的内容将是一个服务器错误页面。人们建议用不同的方式来处理它,看看这里的答案:如果一个页面是一个“404页面没有找到”,我如何从Android WebView进行检查?基本上,它取决于你期望的“好”页面和“错误”页面。不幸的是,目前应用程序无法从WebView获取HTTP响应代码。
The callbacks WebViewClient.onPageStarted
and WebViewClient.onProgressChanged
are only useful if you want to draw a progress bar as you are loading the page.
WebViewClient回调。onPageStarted WebViewClient。onProgressChanged只有在加载页面时想要绘制进度条时才有用。
Also note that the way of overriding WebViewClient.shouldOverrideUrlLoading
that people usually suggest is not correct:
还要注意重写WebViewClient的方法。人们通常认为的应该是不正确的:
public class MyWebViewClient extends WebViewClient {
...
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
// !!! DO NOT DO THIS UNCONDITIONALLY !!!
view.loadUrl(url);
return true;
}
...
}
What few developers realize is that the callback is also called for subframes with non-https schemes. If you'll encounter something like <iframe src='tel:1234'>
, you will end up executing view.loadUrl('tel:1234')
and your app will show an error page, since WebView doesn't know how to load a tel:
URL. It is recommended to simply return false from the method, if you want WebView to do the loading:
很少有开发人员意识到的是,回调也用于非https模式的子帧。如果您遇到类似
public class MyWebViewClient extends WebViewClient {
...
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
// Returning 'false' unconditionally is fine.
return false;
}
...
}
This doesn’t mean you should not call WebView.loadUrl
from shouldOverrideUrlLoading
at all. The specific pattern to avoid is doing so unconditionally for all URLs.
这并不意味着你不应该调用WebView。loadUrl from shouldOverrideUrlLoading。要避免的特定模式是对所有url无条件地这样做。
#2
2
public class AppWebViewClient extends WebViewClient {
@Override
public void onPageStarted(WebView view, String url, Bitmap favicon) {
// TODO Auto-generated method stub
super.onPageStarted(view, url, favicon);
setProgressBar(true);
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
view.loadUrl(url);
return true;
}
@Override
public void onPageFinished(WebView view, String url) {
//Page load finished
super.onPageFinished(view, url);
setProgressBar(false);
}
}
and then you can do
然后你可以这么做
webView.setWebViewClient(new AppWebViewClient());
For the error part you can override the onReceivedError
method
对于错误部分,可以重写onReceivedError方法
@Override
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
// TODO Auto-generated method stub
super.onReceivedError(view, errorCode, description, failingUrl);
}
#3
-2
You can check if a URL is loaded successfully by using onProgressChanged()
可以使用onProgressChanged()检查URL是否成功加载
mWebView.setWebChromeClient(new WebChromeClient() {
public void onProgressChanged(WebView view, int progress) {
progressBar.setProgress(progress);
if (progress == 100) {
//your url is loaded successfully
}
}
});
#1
12
Unfortunately, currently there is no easy way in WebView to ensure that everything on the page has been loaded successfully. We are hoping for a better API to come up in future version. Let me explain what you can do now.
不幸的是,目前WebView中没有简单的方法来确保页面上的所有内容都已成功加载。我们希望在未来的版本中出现更好的API。让我解释一下你现在能做什么。
First of all, in order to detect any problems that prevent WebView from making a connection to the server for loading your main page (e.g. bad domain name, I/O error, etc.), you should use WebViewClient.onReceivedError
callback as other people correctly suggest:
首先,为了检测任何阻止WebView连接到服务器以加载您的主页的问题(例如,坏域名、I/O错误等),您应该使用WebViewClient。正如其他人正确建议的那样,onReceivedError回调:
public class MyWebViewClient extends WebViewClient {
@Override
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
// Make a note about the failed load.
}
}
myWebView.setWebViewClient(new MyWebViewClient());
If the server connection was successful, and the main page was retrieved and parsed, you will receive WebView.onPageFinished
callback, so you also need to have this in your WebViewClient
subclass:
如果服务器连接成功,主页面被检索和解析,您将收到WebView。onPageFinished回调,所以您还需要在WebViewClient子类中包含这个:
public class MyWebViewClient extends WebViewClient {
...
@Override
public void onPageFinished(WebView view, String url) {
// Make a note that the page has finished loading.
}
...
}
The caveat here is that if you have received an HTTP error from the server (e.g. a 404 or a 500 error), this callback will be called anyway, it's just the content that you will get in your WebView will be a server error page. People suggest different ways of how to deal with it, see the answers here: How can I check from Android WebView if a page is a "404 page not found"? Basically, it really depends on what you expect to be a "good" page and a "error" page. Unfortunately, there is currently no way for the app to get the HTTP response code from WebView.
这里需要注意的是,如果您从服务器接收到HTTP错误(例如404或500错误),这个回调将被调用,您在WebView中获得的内容将是一个服务器错误页面。人们建议用不同的方式来处理它,看看这里的答案:如果一个页面是一个“404页面没有找到”,我如何从Android WebView进行检查?基本上,它取决于你期望的“好”页面和“错误”页面。不幸的是,目前应用程序无法从WebView获取HTTP响应代码。
The callbacks WebViewClient.onPageStarted
and WebViewClient.onProgressChanged
are only useful if you want to draw a progress bar as you are loading the page.
WebViewClient回调。onPageStarted WebViewClient。onProgressChanged只有在加载页面时想要绘制进度条时才有用。
Also note that the way of overriding WebViewClient.shouldOverrideUrlLoading
that people usually suggest is not correct:
还要注意重写WebViewClient的方法。人们通常认为的应该是不正确的:
public class MyWebViewClient extends WebViewClient {
...
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
// !!! DO NOT DO THIS UNCONDITIONALLY !!!
view.loadUrl(url);
return true;
}
...
}
What few developers realize is that the callback is also called for subframes with non-https schemes. If you'll encounter something like <iframe src='tel:1234'>
, you will end up executing view.loadUrl('tel:1234')
and your app will show an error page, since WebView doesn't know how to load a tel:
URL. It is recommended to simply return false from the method, if you want WebView to do the loading:
很少有开发人员意识到的是,回调也用于非https模式的子帧。如果您遇到类似
public class MyWebViewClient extends WebViewClient {
...
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
// Returning 'false' unconditionally is fine.
return false;
}
...
}
This doesn’t mean you should not call WebView.loadUrl
from shouldOverrideUrlLoading
at all. The specific pattern to avoid is doing so unconditionally for all URLs.
这并不意味着你不应该调用WebView。loadUrl from shouldOverrideUrlLoading。要避免的特定模式是对所有url无条件地这样做。
#2
2
public class AppWebViewClient extends WebViewClient {
@Override
public void onPageStarted(WebView view, String url, Bitmap favicon) {
// TODO Auto-generated method stub
super.onPageStarted(view, url, favicon);
setProgressBar(true);
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
view.loadUrl(url);
return true;
}
@Override
public void onPageFinished(WebView view, String url) {
//Page load finished
super.onPageFinished(view, url);
setProgressBar(false);
}
}
and then you can do
然后你可以这么做
webView.setWebViewClient(new AppWebViewClient());
For the error part you can override the onReceivedError
method
对于错误部分,可以重写onReceivedError方法
@Override
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
// TODO Auto-generated method stub
super.onReceivedError(view, errorCode, description, failingUrl);
}
#3
-2
You can check if a URL is loaded successfully by using onProgressChanged()
可以使用onProgressChanged()检查URL是否成功加载
mWebView.setWebChromeClient(new WebChromeClient() {
public void onProgressChanged(WebView view, int progress) {
progressBar.setProgress(progress);
if (progress == 100) {
//your url is loaded successfully
}
}
});