I am using the google docs pdf embedded viewer in my android app to display my pdfs. Sometimes the viewer doesn't load my file even though most of the time it does and it's pretty random when it doesn't.
I generate the url with "https://docs.google.com/viewer?embedded=true&url=" + myUrl.
And after that I load the webview :
showLoader()
web_view.settings.javaScriptEnabled = true
web_view.clearCache(true)
web_view.webViewClient = object : WebViewClient() {
override fun onPageFinished(view: WebView?, url: String?) {
hideLoader()
}
override fun shouldOverrideUrlLoading(view: WebView?, request: WebResourceRequest?): Boolean {
web_view.loadUrl(url)
return true
}
override fun onReceivedSslError(view: WebView, handler: SslErrorHandler, error: SslError) {
println("before handler")
handler.proceed()
println("after handler")
}
}
web_view.loadUrl(url)
I tried to proceed if I encounter any sslError, to override urlLoading but none of this resolved my problem.
To test here is one of the url which doesn't always load :
http://docdif.fr.grpleg.com/general/MEDIAGRP/NP-FT-GT/LE10061AA.pdf
One thing I tried too is show the url when display on my app and when it doesn't load on my viewer it blocks too on my navigator. But if I reload the page it does charge.
Any idea what the bug might be?
Try this:
public void onPageFinished(WebView view, String url) {
if (view.getTitle().equals(""))
view.reload();
}
I hope that it can help you!
Related
I have to display website in my WebView inside my app which will ask user to upload photos into the website. Its working flawlessly if I open website outside of the app via Chrome browser, dialog pops up that web is asking for storage permission and after accepting it will open storage to upload content. If I display same website inside webView (inside my app) clicking on upload button won't do anything.
Is there some sort of PermissionListener which has to be implemented for my webview to handle this?
Code:
#SuppressLint("SetJavaScriptEnabled")
private fun initWebview(url: String){
val ws = webView.settings
ws.javaScriptEnabled = true
webView.webViewClient = object: WebViewClient(){
#Suppress("OverridingDeprecatedMember")
override fun shouldOverrideUrlLoading(view: WebView, url: String): Boolean {
view.loadUrl(url)
return false
}
}
webView.webChromeClient = object : WebChromeClient() {
override fun onConsoleMessage(consoleMessage: ConsoleMessage): Boolean {
App.log("WebViewLog: ${consoleMessage.message()}")
return true
}
}
webView.loadUrl(url)
}
I have added internet-permissions and I also used the WebViewClient.onPageFinished method to check whether the page has loaded which turns out it did. JavaScript is also enabled for my WebView.
The code I use to set up my web view
webView.webChromeClient = KeplerWebChromeClient(progressBar)
webView.webViewClient = keplerWebViewClient
webView.settings.javaScriptEnabled = true
webView.settings.useWideViewPort = true
webView.settings.loadWithOverviewMode = true
webView.settings.setSupportZoom(true)
webView.settings.setSupportMultipleWindows(true)
webView.scrollBarStyle = View.SCROLLBARS_INSIDE_OVERLAY
webView.setBackgroundColor(Color.WHITE)
I am using KeplerWebChromeClient to display web page loading progress.
keplerWebViewClient is an object of WebViewClient class which I use to load webpages and to track for whether the webpage has finished loading or not.
And I must mention that this issue doesn't always arise. Sometimes when I run my app, the WebView does work and it does load and display the web page correctly and other times it doesn't. I have found the below stated logcat entries to be unique to when the web page isn't displayed.
E/chromium: [ERROR:tile_manager.cc(778)] WARNING: tile memory limits exceeded, some content may not draw
[ERROR:tile_manager.cc(778)] WARNING: tile memory limits exceeded, some content may not draw
E/chromium: [ERROR:tile_manager.cc(778)] WARNING: tile memory limits exceeded, some content may not draw
E/chromium: [ERROR:tile_manager.cc(778)] WARNING: tile memory limits exceeded, some content may not draw
What is the issue here and how do I fix it? Thanks in advance.
Edit:
I cleared all the app data from my phone and then I restarted my app. After doing so, everything was working just fine. I was able to browse using the WebView but after using the app a few more times i.e. closing and opening it, the problem reappeared. Clearing all data solves the problem temporarily. What aid can this be in solving the problem?
I have to try and it's working fine for me.
private fun setupWebView(url: String) {
webView.settings.javaScriptEnabled = true
webView.settings.domStorageEnabled = true
webView.settings.setPluginState(WebSettings.PluginState.ON);
webView.settings.allowFileAccess = true;
webView.webViewClient = WebClient()
webView.webChromeClient = CustomWebChromeClient()
webView.loadUrl(url)
}
private inner class WebClient : WebViewClient() {
override fun onPageStarted(view: WebView, url: String, favicon: Bitmap?) {
super.onPageStarted(view, url, favicon)
}
override fun onPageCommitVisible(view: WebView, url: String) {
super.onPageCommitVisible(view, url)
}
override fun shouldOverrideUrlLoading(
view: WebView,
url: String
): Boolean {
view.loadUrl(url)
return true
}
override fun onPageFinished(view: WebView, url: String) {
super.onPageFinished(view, url)
}
}
private inner class CustomWebChromeClient : WebChromeClient() {
override fun onJsAlert(
view: WebView,
url: String,
message: String,
result: JsResult
): Boolean {
return false
}
}
I hope it's work for you!
I am trying to override the download Listener for a WebView so it gets to open websites not belonging to us in an external browser instead of loading them in the webview. Thing is, I'd like to simplify the code into something like this
webView?.setDownloadListener { url, userAgent, contentDisposition, mimetype, contentLength ->
if (!url.contains("mydomain")) {
CLog.v("InternalWebviewFragment.configWebView().setDownloadListener() isNOTmydomain url: $url")
val i = Intent(Intent.ACTION_VIEW, Uri.parse(url))
i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
activity?.startActivity(i)
}else{
super(url, userAgent, contentDisposition, mimetype, contentLength)
}
}
However, that call to super there, which I intend to have for urls that do belong to our domain, says that can only be used on the left hand of a dot. When I try to type
super.onDownloadStart
it gives an unresolved reference error.
How could I get the webview Listener to go on business as usual when the url is part of our domain? Is the super call only available in non-lambda methods?
After many tests, #Demigod's approach turned out to be the right one. It just needed the bit of having both deprecated and current methods of shouldOverrideUrlLoading as found here
// APIs up to 23 need this method
override fun shouldOverrideUrlLoading(view: WebView, url: String): Boolean {
if (!url.contains("mydomain")) {
// InternalWebviewFragment external (non mydomain) urls will be dispatched to an external browser
CLog.v("InternalWebviewFragment.getSimpleWebViewClientUrlLoading().shouldOverrideUrlLoadingOLD() isNotmydomain url: $url")
val i = Intent(Intent.ACTION_VIEW, Uri.parse(url))
activity?.startActivity(i)
CLog.v("InternalWebviewFragment.getSimpleWebViewClientUrlLoading().shouldOverrideUrlLoadingOLD() isNotmydomain After Intent")
return true //InternalWebviewFragment this avoids the webview to load the url we've just sent to the browser
}
CLog.v("InternalWebviewFragment.getSimpleWebViewClientUrlLoading().shouldOverrideUrlLoadingOLD() ismydomain url: $url")
// mydomain urls should load fine in the webview
view?.loadUrl(url)
return super.shouldOverrideUrlLoading(view, url)
}
// for APIs 24+
override fun shouldOverrideUrlLoading(
view: WebView?,
request: WebResourceRequest?
): Boolean {
if (!request?.url.toString().contains("mydomain")) {
// InternalWebviewFragment external (non mydomain) urls will be dispatched to an external browser
CLog.v("InternalWebviewFragment.getSimpleWebViewClientUrlLoading().shouldOverrideUrlLoading2() isNotmydomain url: ${request?.url.toString()}")
val i = Intent(Intent.ACTION_VIEW, Uri.parse(request?.url.toString()))
activity?.startActivity(i)
CLog.v("InternalWebviewFragment.getSimpleWebViewClientUrlLoading().shouldOverrideUrlLoading2() isNotmydomain After Intent")
return true //InternalWebviewFragment this avoids the webview to load the url we've just sent to the browser
}
CLog.v("InternalWebviewFragment.getSimpleWebViewClientUrlLoading().shouldOverrideUrlLoading() ismydomain url: $url")
// mydomain urls should load fine in the webview
view?.loadUrl(request?.url.toString())
return super.shouldOverrideUrlLoading(view, request)
}
I want processHTML to be triggered after the webpage is done loading. I think I need:
document.load =
for this. But I don't know the correct syntax for how to put it in loadUrl:
class JavaScriptTokenSubstractInterface {
#JavascriptInterface
#SuppressWarnings("unused")
fun processHTML(html: String) {
Log.d("","html shown is loading and not the result.")
}
}
val webView: WebView = findViewById(R.id.webView)
webView.settings.javaScriptEnabled = true
webView.settings.useWideViewPort = true
webView.requestFocus(View.FOCUS_DOWN)
webView.addJavascriptInterface(JavaScriptTokenSubstractInterface(), "HTMLOUT")
webView.webViewClient = object : WebViewClient() {
override fun onPageFinished(webView: WebView?, url: String?) {
super.onPageFinished(webView, url)
Thread.sleep(3000)
webView?.loadUrl("javascript:window.HTMLOUT.processHTML('<html>'+document.getElementsByTagName('html')[0].innerHTML+'</html>');")
}
}
webView.loadUrl("www.someWebPageThatIsLoading.nl")
What happens:
1. The loading of the page is shown
2. processHTML is triggered and it shows the HTML of the loading page
3. A few seconds go by and the page is done loading
processHTML should be triggered after the loading is done.
Getting error **html exposed beyond app through Intent.getData()** when trying to call another HTML file through html link inside web view from local assets folder in android studio.
Below Code might resolve your issue
webView.settings.javaScriptEnabled = true
webView.webViewClient = object : WebViewClient()
{
override fun shouldOverrideUrlLoading(view: WebView, url: String): Boolean {
view.loadUrl(url)
return true
}
// From api level 24
override fun shouldOverrideUrlLoading(view: WebView, request: WebResourceRequest): Boolean {
// Get the mailto url
val url = request.url.toString()
view.loadUrl(url)
// Return true means, leave the current web view and handle the url itself
return true
}
}
webView.loadUrl("file:///android_asset/sample.html")