Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

webview shouldinterceptrequest example

I need to know how does the shouldinterceptrequest work. I don't know how to create and handle this method to read and replace the CSS link. Thank you!

like image 889
androdio Avatar asked Nov 25 '11 20:11

androdio


People also ask

What is the use of WebViewClient in Android?

Android WebView is used to display HTML in an android app. We can use android WebView to load HTML page into android app.

What is a WebViewClient?

WebViewClient is the object responsible for most the actions inside a WebView. JavaScript enabled, security, routing, etc. You can make a custom one, as well as use a Chrome one.

What is shouldOverrideUrlLoading?

shouldOverrideUrlLoading is called when a new page is about to be opened whereas shouldInterceptRequest is called each time a resource is loaded like a css file, a js file etc.


2 Answers

Well, the short answer is that it works quite similar to shouldOverrideUrlLoading(WebView view, String url), as illustrated in the WebView tutorial.

To get you started, see the code below. You simply override the shouldInterceptRequest(WebView view, String url) method of your WebViewClient. Obviously you don't have to do that inline, but for the sake of compactness that's what I did:

    WebView webview = (WebView) findViewById(R.id.webview);     webview.setWebViewClient(new WebViewClient() {         @Override         public WebResourceResponse shouldInterceptRequest (final WebView view, String url) {             if (url.contains(".css")) {                 return getCssWebResourceResponseFromAsset();             } else {                 return super.shouldInterceptRequest(view, url);             }         }          /**          * Return WebResourceResponse with CSS markup from a String.           */         @SuppressWarnings("deprecation")         private WebResourceResponse getCssWebResourceResponseFromString() {             return getUtf8EncodedCssWebResourceResponse(new ByteArrayInputStream("body { background-color: #F781F3; }".getBytes()));         }          /**          * Return WebResourceResponse with CSS markup from an asset (e.g. "assets/style.css").           */         private WebResourceResponse getCssWebResourceResponseFromAsset() {             try {                 return getUtf8EncodedCssWebResourceResponse(getAssets().open("style.css"));             } catch (IOException e) {                 return null;             }         }          /**          * Return WebResourceResponse with CSS markup from a raw resource (e.g. "raw/style.css").           */         private WebResourceResponse getCssWebResourceResponseFromRawResource() {             return getUtf8EncodedCssWebResourceResponse(getResources().openRawResource(R.raw.style));         }          private WebResourceResponse getUtf8EncodedCssWebResourceResponse(InputStream data) {             return new WebResourceResponse("text/css", "UTF-8", data);         }      });      webview.loadUrl("http://stackoverflow.com"); 

Catch the loading of the css file and return your own WebResourceResponse containing the data you want to load in stead.

Do note that this method requires API level 11.

If you want to do something similar for Android 2.x, you might want to try using the earlier mentioned shouldOverrideUrlLoading(WebView view, String url) to avoid loading the page, fetch it manually, replace the reference to the css file with your own, and finally call loadData(String data, String mimeType, String encoding) (or loadDataWithBaseURL(String baseUrl, String data, String mimeType, String encoding, String historyUrl)) on the WebView, passing in the manipulated html content as a string.

Before:

Before

After:

After

like image 114
MH. Avatar answered Sep 19 '22 04:09

MH.


this might be also interesting for you. It reads files from specific folders and if a request is incoming with this filename it uses the file from the asset folder and not that from web.

    //get list of files of specific asset folder     private ArrayList listAssetFiles(String path) {          List myArrayList = new ArrayList();         String [] list;         try {             list = getAssets().list(path);             for(String f1 : list){                 myArrayList.add(f1);             }         } catch (IOException e) {             e.printStackTrace();         }         return (ArrayList) myArrayList;     }      //get mime type by url     public String getMimeType(String url) {         String type = null;         String extension = MimeTypeMap.getFileExtensionFromUrl(url);         if (extension != null) {             if (extension.equals("js")) {                 return "text/javascript";             }             else if (extension.equals("woff")) {                 return "application/font-woff";             }             else if (extension.equals("woff2")) {                 return "application/font-woff2";             }             else if (extension.equals("ttf")) {                 return "application/x-font-ttf";             }             else if (extension.equals("eot")) {                 return "application/vnd.ms-fontobject";             }             else if (extension.equals("svg")) {                 return "image/svg+xml";             }             type = MimeTypeMap.getSingleton().getMimeTypeFromExtension(extension);         }         return type;     }      //return webresourceresponse     public WebResourceResponse loadFilesFromAssetFolder (String folder, String url) {         List myArrayList = listAssetFiles(folder);         for (Object str : myArrayList) {             if (url.contains((CharSequence) str)) {                 try {                     Log.i(TAG2, "File:" + str);                     Log.i(TAG2, "MIME:" + getMimeType(url));                     return new WebResourceResponse(getMimeType(url), "UTF-8", getAssets().open(String.valueOf(folder+"/" + str)));                 } catch (IOException e) {                     e.printStackTrace();                 }             }         }         return null;     }      //@TargetApi(Build.VERSION_CODES.LOLLIPOP)     @SuppressLint("NewApi")     @Override     public WebResourceResponse shouldInterceptRequest(final WebView view, String url) {         //Log.i(TAG2, "SHOULD OVERRIDE INIT");         //String url = webResourceRequest.getUrl().toString();         String extension = MimeTypeMap.getFileExtensionFromUrl(url);         //I have some folders for files with the same extension         if (extension.equals("css") || extension.equals("js") || extension.equals("img")) {             return loadFilesFromAssetFolder(extension, url);         }         //more possible extensions for font folder         if (extension.equals("woff") || extension.equals("woff2") || extension.equals("ttf") || extension.equals("svg") || extension.equals("eot")) {             return loadFilesFromAssetFolder("font", url);         }          return null;     } 
like image 43
EscapeNetscape Avatar answered Sep 21 '22 04:09

EscapeNetscape