webpage takes a lot of time to load - java

In a webview in Android, I first load a webpage and then display only a part of it using some javascript commands. During the whole process a "loading" message is displayed.
Problem : It take s alot of time to load even if the internet speed is fast. (>60 sec always). How to reduce time ?
This is my WebViewClient class that I attach with the webview (and the class contains only 1 method):
#Override
public void onPageFinished(WebView view, String url){
view.loadUrl("javascript:document.getElementsByClassName('menu')[0].innerHTML=''");
view.loadUrl("javascript:document.getElementsByClassName('gbh')[0].innerHTML=''");
view.loadUrl("javascript:document.getElementsByClassName('input')[0].innerHTML=''");
view.loadUrl("javascript:document.getElementsByClassName('card_title')[0].innerHTML=''");
view.loadUrl("javascript:document.getElementsByClassName('cell_input')[0].innerHTML=''");
view.loadUrl("javascript:document.getElementsByName('pre')[0].innerHTML=''");
view.loadUrl("javascript:document.getElementById('footer').innerHTML=''");
view.loadUrl("javascript:document.getElementsByClassName('foot')[0].innerHTML=''");
}

Sir, You could use the YSlow or Google PageLoad plugins for your browser, to get specific tips on how to improve page load and speed up your page.
By default, a WebView provides no browser-like widgets, it does not enable JavaScript and also web page errors are ignored.

Related

Android Studio Webview (Java) - Is there a way to wait until a loading inside a web page is finished before loading url?

I'm trying to get some elements in a web page using webView.loadUrl(...);.
However, I found out that there is a loading that "creates" these elements after the page is already loaded. So, I didn't find a way to get these.
I tried to use onPageFinished but it doesn't look like it is called when the loading inside the web page finishes.
I also tried to put a button that triggers the webView.loadUrl(...);. This tip only works if the user doesn't click too fast on the button, because then the loading doesn't have the time to finish before.
Here is a video of the page booting up, hoping for you to better understand what I mean by a loading inside the page :
https://www.youtube.com/watch?v=q1267dcJai8&feature=youtu.be
If I haven't been clear enough, I'd be happy to clarify things further.
Thank you in advance!
Edit : To clarify something, I'm not exactly asking for a way to get these elements. A way to delay the webView.loadUrl(...); while the webpage is loading would also be perfect for me.
Try onProgressChanged() of WebChromeClient like below.
Documentation link:
https://developer.android.com/reference/android/webkit/WebChromeClient#onProgressChanged(android.webkit.WebView,%20int)
#Override
public void onProgressChanged(WebView view, final int newProgress) {
super.onProgressChanged(view, newProgress);
if (newProgress == 100) {
//Page load done
}
else
{
//Page is still loading wait...
}
}

YoutubeThumbnailLoader taking too long to show a thumbnail?

Relevant code:
YouTubeThumbnailView first_video = (YouTubeThumbnailView) findViewById(R.id.main_video);
first_video.initialize(Config.YOUTUBE_API, new YouTubeThumbnailView.OnInitializedListener() {
#Override
public void onInitializationSuccess(YouTubeThumbnailView youTubeThumbnailView, YouTubeThumbnailLoader youTubeThumbnailLoader) {
final String video = getResources().getString(R.string.principal_funcoes);
youTubeThumbnailLoader.setVideo(video);
}
The time it takes for the method 'youTubeThumbnailLoader.setVideo(String s)" to work is absurd.
It takes 30+ seconds for a thumbnail to show up, with full cabled connection (100mbps).
It's definitely impossible for a user to wait more than 2 seconds for the thumbnail to show up, and have a completely blank screen while he waits for that to happen.
What can I do to load the video thumbnail any faster, or at least make YouTubeThumbnailView show a loading image while it fetches the thumbnail?
You can use direct youtube api urls for getting youtube thumbnails and they are way to faster too. here are urls you can try.
Start:-- It is only give you default size thumbnails.
https://ytimg.googleusercontent.com/vi/<insert-youtube-video-id-here>/default.jpg
For the high quality version of the thumbnail use a url similar to this:
https://ytimg.googleusercontent.com/vi/<insert-youtube-video-id-here>/hqdefault.jpg
There is also a medium quality version of the thumbnail, using a url similar to the HQ:
https://ytimg.googleusercontent.com/vi/<insert-youtube-video-id-here>/mqdefault.jpg
For the standard definition version of the thumbnail, use a url similar to this:
https://ytimg.googleusercontent.com/vi/<insert-youtube-video-id-here>/sddefault.jpg
For the maximum resolution version of the thumbnail use a url similar to this:
https://ytimg.googleusercontent.com/vi/<insert-youtube-video-id-here>/maxresdefault.jpg
It helps me to develop youtube application, Hope it also help you.

Most efficient way to load a lot of images from URL Android

I'm making this netflix style app in which images are loaded into different categories. Let's say Dog videos (has 15 images), Cat videos (15 images), etc... All the images are loaded from a URL, it kind of takes a while for all to load. I was wondering if there was anything I could do to speed up the process? Or maybe show an empty container then fill it as the images load (that would be cool).
This is what I have done:
I have multiple async calls in one Activity, (1 async call per category)
JSONTask1 dogTask = new JSONTask1();
JSONTask2 catTask = new JSONTask2();
JSONTask3 pigTask = new JSONTask3();
JSONTask4 horseTask = new JSONTask4();
dogTask.execute("");
catTask.execute("");
pigTask.execute("");
horseTask.execute("");
I have all of those in a row in my actual code. Thanks.
I would use the "proxy pattern". Basically, you need to create a class that contains the minimal informations required for the display. In which, you have a preview image.
When ever you load everything you start by showing the preview content, ie : a loading gif for everypicture with the title of the movie or whatever. and basically the proxy would have a "loadImage" method that would make an ajax call or async call and the photos would load one by one. Plus, to make the loading easier, make sure the photos are not oversized.
You can see Picasso answers , in picasso i suggest you this way :
Picasso.with(getApplicationContext()).load("your url").placeholder(R.drawable.your_place_holder).error(R.drawable.showing_when_error_occured)
.into(imageView, new Callback() {
#Override
public void onSuccess() {
}
#Override
public void onError() {
}
});
Also another suggestion from me : convert your thumb images to base64 format in backend, then firstly retrieve your thumbs and show them. Then start an async task and change images when successfull.
Like whatsapp. In whatsapp you have thumb images they have so low resolution and super fast. When you click image if you have internet connection they load actual thumb images, and click again they load larger image.
Picasso website :http://square.github.io/picasso/
Load them asynchronously with Picasso, you can even show a placeholder image until the real one is loaded

Android Webview, working with Anchors

I am loading a webpage into a webview from the database with the loadDataWithBaseURL() function and am trying to subsequently jump to an Anchor point. When I place a button just below the webview that uses the loadUrl()-function, it jumps to the Anchor point just fine. But if I place the loadUrl() after the loadDataWithBaseURL() it says page not found.
webview.loadDataWithBaseURL("app:myhtml", data, "text/html", "UTF-8", null);
webview.loadUrl("app:myhtml#tips");
I assumed it was because the load had not completed, and thus it couldn't find the Anchor, but I tried a loop to wait for it to getProgress() to equal 100, and have verified it's reaching 100 before that command executes, but it still won't find the page unless it's associated with the button click.
Any Ideas out there on how I can load a page from the database and then jump to an anchor point at the same time. I'm working with the Android 2.1 SDK.
Thanks to your help I got it to load directly to my anchor by adding this little bit of code. However I can't scroll around on the page, it starts to move and then snaps back. I suspect because it is reloading the page to that anchor each time. I'm fairly new to Android, and Java even, so this may be the wrong implementation of your suggestion, but I'd certainly appreciate a little more direction. Here is the code I used:
webview.setWebViewClient(new WebViewClient() {
#Override
public void onPageFinished(WebView view, String url) {
super.onPageFinished(webview, "app://data");
webview.loadUrl("app://data#tips");
}
});
It seems this is making an infinite loop.
Try using valid URL as a base URL in loadDataWithBaseURL(), such as app://myhtml.
Also, to make sure the data was loaded implement WebViewCLient.onPageFinished().
It was getting in an infinite onPageFinished loop before. It had nothing to do with me scrolling, it was just continuously loading the same page. This code allows it to load without without getting stuck in a loop.
webview.setWebViewClient(new WebViewClient() {
#Override
public void onPageFinished(WebView view, String url) {
if(url.contains("#") != true){
webview.loadUrl("app://data#tips");
}
}
});

How to clear the (CSS) visited history of an Android WebView?

I try to reuse an existing WebView by clearing any private data the previous user left behind:
CookieManager.getInstance().removeAllCookie();
webview.clearHistory();
webview.clearFormData();
webview.clearCache(true);
clearHistory seems only to clear the back/forward list, accessible via API, but not the internal list used for coloring links inside the web content.
I even tried the following, suggested by another stackoverflow answer:
deleteDatabase("webview.db");
deleteDatabase("webviewCache.db");
I still have no luck: CSS :visited selectors still work after reloading the page.
An alternative would be to use the API level 11 private browsing feature (new constructor argument), but then I cannot benefit from visited links at all; and can no longer target older versions.
Maybe someone has a solution for this issue? Thanks for your help.
Summary of the answers I got so far:
I tried these two answers, but the first seems to clear HTML5 data storage and the latter seems to be specific to the built-in browser:
WebStorage.getInstance().deleteAllData();
Browser.clearHistory(getContentResolver());
WebChromeClient.getVisitedHistory(ValueCallback<String[]> callback) is only called after the first time I create a new WebView in a recently installed application.
I tried to remove the WebView from view hierachy and create a new one, but unfortunately the visited history seems to be stored for the whole application.
Override WebChromeClient and WebViewClient... Damn that was hidden.
I actually had to dig up a bit to find this out.
WebView webView = (WebView)findViewById(R.id.myWebView);
WebChromeClient myWebChromeClient = new WebChromeClient(){
#Override
public void getVisitedHistory(ValueCallback<String[]> callback) {
// called during webview initialization, original implementation does strictly nothing
// and defaults to the native method WebViewCore.nativeProvideVisitedHistory()
String[] myUserHistory = getVisitedUrlsFromMyOwnDatabase(userId);
callback.onReceiveValue(myUserHistory);
}
};
WebViewClient myWebViewClient = new WebViewClient(){
#Override
public void doUpdateVisitedHistory(WebView view, String url,
boolean isReload) {
// called whenever there is a new link being visited
insertIfNotExistVisitedUrlIntoMyOwnDatabaseForUser(userId);
super(view, url, isReload);
}
}
webView.setWebViewClient(myWebViewClient);
webView.setChromeClient(myWebChromeClient);
webView.getSettings().etc(whatever)...
I think I'm "almost there". Here's the part I managed: what it does so far is remove css history altogether, so we're halfway there. I can't get the browser to recognize the url format I'm providing in "myUserHistory", so in effect the only feature this code does is reset css history altogether, but it's only called once when the WebView is instanciated (or created, didn't check), so for a true multiuser experience you'd need to recreate the webview at each login.
My problem now is that I can't manage to load the urlHistory properly. My Honeycomb Xoom webview seems to ignore my data.
Ah well, I hope it works for you. For me just calling callback.onReceiveValue(new String[]{}); in getVisitedHistory() will be good enough.
EDIT:
I just put twenty more minutes into it because I'm curious. This method is what delegates to the WebChromeClient (mCallbackProxy = WebChromeClient).
protected void populateVisitedLinks() {
ValueCallback callback = new ValueCallback<String[]>() {
public void onReceiveValue(String[] value) {
sendMessage(EventHub.POPULATE_VISITED_LINKS, (Object)value);
}
};
mCallbackProxy.getVisitedHistory(callback);
}
It's protected in WebViewCore, which is a private attribute of WebView with no accessor. The sendMessage delegates to EventHub which is private, and WebViewCore is filled with private native methods, and one of these seems to be the one actually calling the populateVisitedLinks() method during the initialization.
Unless someone at Google adds a public method to WebView to trigger the repopulation, I'm afraid it's practically impossible to achieve your goal. Sorry :(
As a side note, all these native visited history handling really makes me wonder: why do hardware manufacturers care so much about which urls we visited? ;) <<< sarcasm
As an alternate solution, you could try adding your own CSS with the same base colors the default CSS has and switch the CSS by another one (with same color for both "types" of links) when you want to reset the visited links.
A:link{color: "#990000"; text-decoration: none;}
A:visited{color: "#990000"; text-decoration: none;}
A:hover{color: "#ff0000"; text-decoration: none;}
If you can obtain a Browser instance (maybe you can set a WebChromeClient to WebView) you can use its clearHistory() method.
Does WebStorage.clearAllData() have the desired effect? Unfortunately, the documentation on this class is very sparse compared to WebView and doesn't say whether it applies to WebViews.
The exact time you're calling clearHistory() may also have an effect. Clearing it and then navigating to a new page may still keep the first page in history, and you have to call the method after the new page has loaded.
Personally, if privacy is a real issue, I would create a new set of objects from scratch for this new session if possible.

Categories