I have an Android app which has a webview. When there\'s no internet connection, webview will display page not available. I want to make this look like an app as much as pos
You can check device is connect to internet through data or wifi by following code
ConnectivityManager manager = (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo i = manager.getActiveNetworkInfo();
boolean hasConnect = (i!= null && i.isConnected() && i.isAvailable());
if(hasConnect)
{
// show the webview
}
else
{
// do what ever you need when when no internet connection
}
After user go to webview , then if the connect is lost you can capture that event from following code
webView.setWebViewClient(new Callback());
public class Callback extends WebViewClient{
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl){
Toast.makeText(getApplicationContext(), "Failed loading app!, No Internet Connection found.", Toast.LENGTH_SHORT).show();
}
}
following permissions need to give
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
You can use my CustomWebViewClient
it -
All you need to do is attach it to your webView
webView.setWebViewClient(new CustomWebViewClient ());
CustomWebViewClient class
/**
* WebViewClient subclass loads all hyperlinks in the existing WebView
*/
public class CustomWebViewClient 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;
}
Dialog loadingDialog = new Dialog(WebViewActivity.this);
@Override
public void onPageStarted(WebView view, String url, Bitmap favicon) {
super.onPageStarted(view, url, favicon);
webViewPreviousState = PAGE_STARTED;
if (loadingDialog == null || !loadingDialog.isShowing())
loadingDialog = ProgressDialog.show(WebViewActivity.this, "",
"Loading Please Wait", true, true,
new DialogInterface.OnCancelListener() {
@Override
public void onCancel(DialogInterface dialog) {
// do something
}
});
loadingDialog.setCancelable(false);
}
@RequiresApi(api = Build.VERSION_CODES.M)
@Override
public void onReceivedError(WebView view, WebResourceRequest request,
WebResourceError error) {
if (isConnected()) {
final Snackbar snackBar = Snackbar.make(rootView, "onReceivedError : " + error.getDescription(), Snackbar.LENGTH_INDEFINITE);
snackBar.setAction("Reload", new View.OnClickListener() {
@Override
public void onClick(View view) {
webView.loadUrl("javascript:window.location.reload( true )");
}
});
snackBar.show();
} else {
final Snackbar snackBar = Snackbar.make(rootView, "No Internet Connection ", Snackbar.LENGTH_INDEFINITE);
snackBar.setAction("Enable Data", new View.OnClickListener() {
@Override
public void onClick(View view) {
startActivityForResult(new Intent(Settings.ACTION_WIRELESS_SETTINGS), 0);
webView.loadUrl("javascript:window.location.reload( true )");
snackBar.dismiss();
}
});
snackBar.show();
}
super.onReceivedError(view, request, error);
}
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
@Override
public void onReceivedHttpError(WebView view,
WebResourceRequest request, WebResourceResponse errorResponse) {
if (isConnected()) {
final Snackbar snackBar = Snackbar.make(rootView, "HttpError : " + errorResponse.getReasonPhrase(), Snackbar.LENGTH_INDEFINITE);
snackBar.setAction("Reload", new View.OnClickListener() {
@Override
public void onClick(View view) {
webView.loadUrl("javascript:window.location.reload( true )");
}
});
snackBar.show();
} else {
final Snackbar snackBar = Snackbar.make(rootView, "No Internet Connection ", Snackbar.LENGTH_INDEFINITE);
snackBar.setAction("Enable Data", new View.OnClickListener() {
@Override
public void onClick(View view) {
startActivityForResult(new Intent(Settings.ACTION_WIRELESS_SETTINGS), 0);
webView.loadUrl("javascript:window.location.reload( true )");
snackBar.dismiss();
}
});
snackBar.show();
}
super.onReceivedHttpError(view, request, errorResponse);
}
@Override
public void onPageFinished(WebView view, String url) {
if (webViewPreviousState == PAGE_STARTED) {
if (null != loadingDialog) {
loadingDialog.dismiss();
loadingDialog = null;
}
}
}
}
Check Connectivity Method
/**
* Check if there is any connectivity
*
* @return is Device Connected
*/
public boolean isConnected() {
ConnectivityManager cm = (ConnectivityManager)
this.getSystemService(Context.CONNECTIVITY_SERVICE);
if (null != cm) {
NetworkInfo info = cm.getActiveNetworkInfo();
return (info != null && info.isConnected());
}
return false;
}
webView.setWebViewClient(new WebViewClient() {
int errorCode = 0;
@SuppressWarnings("deprecation")
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
return handleUri(view, url);
}
@TargetApi(Build.VERSION_CODES.N)
@Override
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
return handleUri(view, request.getUrl().toString());
}
private boolean handleUri(WebView view, final String url) {
view.loadUrl(url);
return true;
}
@Override
public void onPageFinished(WebView view, String url) {
if(errorCode == 0) {
//CHECK IS PAGE I NEED AND DO STUFF
} else {
errorCode = 0;
//delay and try again
}
}
@SuppressWarnings("deprecation")
@Override
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
handleError(errorCode);
}
@TargetApi(Build.VERSION_CODES.N)
@Override
public void onReceivedError(WebView view, WebResourceRequest request, WebResourceError error) {
handleError(error.getErrorCode());
}
private void handleError(int errorCode) {
this.errorCode = errorCode;
}
});
You'll want to override the shouldOverrideUrlLoading method of a WebViewClient to catch URL clicks.
To check the Wifi status, you'll want to use the ConnectivityManager
Try this:
WebView mWebView;
NetworkInfo networkInfoWifi = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE).getNetworkInfo(ConnectivityManager.TYPE_WIFI);
mWebView.setWebViewClient(mWebClient);
WebViewClient mWebClient = new WebViewClient(){
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url){
return true;
}
@Override
public void onLoadResource(WebView view, String url){
if (networkInfoWifi.isConnected()) {
//Take action
}
}
}
I'd recommend breaking your problem into two smaller steps - Click Interception and Connection Status Checking, and searching for them. This yields plenty of results, and I was able to use these two existing answers to put together the code:
Intercept Webview Click
Check Wifi Connection
I have used the following in my projects:
DetectConnection.Java
import android.content.Context;
import android.net.ConnectivityManager;
public class DetectConnection {
public static boolean checkInternetConnection(Context context) {
ConnectivityManager con_manager = (ConnectivityManager)
context.getSystemService(Context.CONNECTIVITY_SERVICE);
return (con_manager.getActiveNetworkInfo() != null
&& con_manager.getActiveNetworkInfo().isAvailable()
&& con_manager.getActiveNetworkInfo().isConnected());
}
}
Main code:
if (!DetectConnection.checkInternetConnection(this)) {
Toast.makeText(getApplicationContext(), "No Internet!", Toast.LENGTH_SHORT).show();
} else {
wv = (WebView) findViewById(R.id.donate_webView1);
c = new CustomWebViewClient();
wv.setWebViewClient(c);
wv.clearCache(true);
wv.clearHistory();
wv.getSettings().setJavaScriptEnabled(true);
wv.getSettings().setJavaScriptCanOpenWindowsAutomatically(true);
wv.getSettings().setBuiltInZoomControls(true);
wv.loadUrl("http://www.google.com");
}
// Function to load all URLs in same webview
private class CustomWebViewClient extends WebViewClient {
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (!DetectConnection.checkInternetConnection(this)) {
Toast.makeText(getApplicationContext(), "No Internet!", Toast.LENGTH_SHORT).show();
} else {
view.loadUrl(url);
}
return true;
}
}
Update the Manifest:
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />