We have web application which sends REST API request and change the DOM after request is completed. It is all done in jQuery with AJAX calls. But the problem is, all of the dynamic parts of a page has a slight delay to get updated on page refresh. It's like you first see the static elements and then immediately it gets updated. It is noticeable quite a lot.
We wait for $(document).ready so I think that is the issue. Is there a better way of updating HTML before it gets rendered so the user won't notice the change?
Not to mention, most of the data are cached in sessionStorage so it could be read without REST call.
I searched a little bit but I'm not quite sure, do I need a client-side template engine for this? Like Mustache.js?
I don't think it it possible to completely avoid delays caused by ajax requests. You could possibly put some request out of $(document).ready and place it in a head section:
<head>
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript">
// some javascipt here, $.getJSON etc.
</script>
</head>
In this case you have to look out for selecting elements that are not rendered yet (this could cause some unpleasent errors).
Finally I would recommend you to use some loading gif and animations of loaded elements in order to increase user experience. Take a look for example at AngularJS and its animation features here: https://docs.angularjs.org/tutorial/step_12
If all you're worried about is the noticeable change when the page updates, you could put everything inside your body tag inside a container div and give it display:none;. Display a loading image on page load then show the container div when the Ajax request is complete.
Related
I have those lines that should be blocked for some of pages.
So we don't have to use them.
<script src="/Scripts/jquery.validate.js"></script>
<script src="/Scripts/jquery.validate.unobtrusive.js"></script>
Is it possible to do somehow? I mean I don't have access to the Layout page and core code.
Can we do it using JavaScript/jQuery somehow?
Check this reference.
Removing a script element does not do anything. If you can somehow access a script element, it was executed a long time ago and removing it will have no effect.
Following will totally remove them from DOM only but not effect to code at all because already they are executed before. So be sure you don't need them at all to that page. Apply them before that script loads and after jquery load. like:
<script>
$('script[src="/Scripts/jquery.validate.js"],
script[src="/Scripts/jquery.validate.unobtrusive.js"]').remove();
</script>
<script src="/Scripts/jquery.validate.js"></script>
<script src="/Scripts/jquery.validate.unobtrusive.js"></script>
But I would prefer not to remove them, because they will harm other I believe.
Since you do not have access to the Layout, you really can't remove them before they're loaded and parsed by the user's browser.
If you need them for some pages and not others, there is no harm loading them for all pages since the browser should cache them on the first request and use the cache on each additional request. A little overhead on initial page load, but should be insignificant for future page loads
I see that Javascript code is normally in heading part of HTML code.
<head>
<script type="text/javascript" language="javascript" src="core.js"></script>
...
</head>
Is it OK to put the Javascript code in a body part of HTML code? I tested it, but it seems to work.
<body>
<script type="text/javascript" language="javascript" src="core.js"></script>
...
</body>
If so, why the examples of Javascript books put the javascript code in heading part?
If not, what's the difference between putting the javascript code in body/heading part?
Not only is it OK, it's actually better, since it lets the content come first.
If your viewers have a slow (eg, mobile) connection, it's better to send the actual content first, so that they can read it while the browser downloads the Javascript.
All the people saying it is better only applies if you are talking about at the bottom of the page (and that is an up for debate thing) from a code quality point of view, it is NOT ok to sprinkle script tags through your html. All references to javascript should be in a single place on the page, either the head (where they should be), or the very bottom (as a perf optimization)
Edit:
Basically, a web page is made up of 3 pieces; style (css), structure (html), and behavior (javascript). These pieces are all very distinct, so it makes sense to keep them as separate as possible. That way if you need to change some javascript, it is all in one place. If it is sprinkled through the file, it becomes much more difficult to find the code you are looking for, and that code basically becomes noise when you are just looking at structure.
It is the same arguments as why not sprinkle db access code all over your page. It has nothing to do with technical reasons, purely an architectural/design decision. Code that does different things should be kept separate for readability, maintainability, and by extension, refactorability (not sure if that last one is actually a word...)
You can do it, and people often do.
For example, people like to put their script tags just before the closing </body> to make web pages render quicker.
Also, if you do a script block after an element is created, you don't need to wait for DOM ready.
Be warned though, don't add, or remove an element from an unclosed ancestor in the markup tree (not including the script block's immediate parent element), or you will get the dreaded Operation Aborted error in IE.
Just something to add on:
I have preference of putting Javascript file right before </body>. My reasons being that:
Content can load and be shown first. If you load huge Javascript files first, which most are meaningless until the page is loaded, the user won't be able to see anything until the JS files are loaded.
Most Javascript code require to work with the UI can only run after the UI has been loaded. Placing the codes at the end of the html file reduces the need to use the onload event handler.
It is very bad habit to place Javascript snippets all over the HTML file. Placing all at the back of the HTML file allows you to manage your Javascript more efficiently.
It is legal according to the spec.
Most examples use them in the header as the headers come first and the browser will be able to parse the reference and download the JS files faster.
Additionally, these are links and are not part of the display, so traditionally, put in the header.
It is perfectly legal but there seem to be some differing opinions about it. Those who say to put all the javascript references in the head argue that the script is downloaded before the rest of the page become visible and dependent on it. So your user will not see an object on screen, attempt to interact with it and get an error because the javascript code is not yet loaded.
On the other hand, the argument goes that it takes longer to load all the script before the user sees the page and that can have a negative impact on perceived speed of your site.
JavaScripts inside body will be executed immediately while the page loads into the browser
Placing javascript at the end of the body will defer javascript load (ie: the page will render faster), but remember that any javascript function used for an event should be loaded before the event declaration, it is mainly because users may be able to fire an event before the page is completely loaded (so before the function is loaded)!
I used to put it in the head, then I've heard that it takes longer for the page to load so I started placing the scripts at the very bottom. However, I found out the most 'clean' way to do it is to place it in the head BUT you place the script inside a document.ready function. This way you have the best of both worlds. It is cleaner because it is in the head and it is not loaded before the content has been loaded, so there aren't any problems performance wise either.
With jQuery for instance, you can do it like this:
$(document).ready(function() {
alert('test');
});
The alert will only popup when the page has been fully loaded, even though the script is in the head.
The problem is simple, but can't figure out a solution. Many thanks for those who helps.
I want to modify a web page (DOM tree) before it is displayed on screen.
I understand that the DOM tree is fully loaded in memory before being processed.
Do any of you knows a way to process this fully loaded DOM tree while it is on memory
and then let it be displayed with its new structure ?
The reason i want to do that, is because i'm working on an addon that is adding content to an existing web site.
added-> Just need to mention that the existing web site is not mine, so i can't use php to modify the website content is not mine.
But right now, the web site is displayed without the addon content
and you see the content coming after 1 second (because i append the content after website is already displayed), so you see the website content moving.
Thanks for helping.
It's not very difficult. Just hide the body using CSS and on the onload-event of the document do your manipulation and show the body.
Short example:
<html>
<head>
<title>example</title>
<style type="text/css">
<!--
html.scripted body{display:none;}
-->
</style>
<script type="text/javascript">
<!--
//set class for html-element, so the css-rule above will be applied to the body
document.getElementsByTagName('html')[0].className='scripted';
//on page load
window.onload=function()
{
//do the manipulation
document.body.appendChild(document.createElement('em')).appendChild(document.createTextNode('dynamic content'));
alert('manipulation done');
//show the body
document.body.style.display='block';
}
//-->
</script>
</head>
<body>
static content
</body>
</html>
In regard to Brad's comment below you may consider if there may be other ways. As the real issue seems to be the moving content, it could be possible to place a static placeholder where the dynamic content will appear later.
You mention PHP in your tags, so why not build your document server-side? Then, it doesn't matter.
If you must do this client side, then I also wouldn't worry about this. Web pages are rendered progressively anyway. Maybe you have a fast computer and a quick connection to your servers, but I guarantee you that most of your users do not.
Just add some code to the bit where the DOM is ready to make your page enhancements. Relevant: Javascript DOM ready without an entire framework
The only way to manipulate the DOM before it's loaded is by using a pre-processor like php.
Javascript can only manipulate the DOM after it's loaded.
For any further help beyond that you would have to provide a more specific example :-)
I finally found a solution.
I make the addon looking at web page navigation. In fact, it looks at url changes so that I know the user is moving to a different location (therefore I know I have to do something before I even got the 'Load' event of the web page).
Then I just try to access an element (that I know will be in the DOM, like the header) using a loop. Then when the element appears (before the 'Load' event) I insert the code and stop looping/listening.
If anyone need more details of how it is all done, I'll gladly answer your question.
Thanks.
Im experiencing strange behavior with Firefox and Dojo. I have a html page with these lines in the <head> section:
...
<script type="text/javascript" src="dojo.js" djconfig="parseOnLoad: true, locale: 'de'"></script>
<script type="text/javascript">
dojo.require("dojo.number");
</script>
...
Sometimes the page loads normally. But sometimes it won't. Firefox will fetch the whole html page but not render it. I see only a gray window.
After some experiments I figured out that the rendering problem has something to do with the load time of the html. Firefox starts evaluating the html page while loading it. If the page takes too long to load the above javascript will be executed BEFORE the html finishes loading.
If this happens I'll get the gray window. Advising Firefox to show me the source code of the page will display the correct complete html code. BUT: if I save the page to disk (File->Save Page As...) the html code will be truncated and the above part will look like this:
...
<script type="text/javascript" src="dojo.js" djconfig="parseOnLoad: true, locale: 'de'"></script>
<script type="text/javascript">
dojo.require("dojo.number");
</script></head><body></body></html>
This explains why I get to see a gray area. But why does this code appear there? I assume the require() method of Dojo does something "evil". But I can't figure out what. There is no write.document("</head><body></body></html>"); in the Dojo code. I checked for it.
The problem would be fixed, if I'd place the dojo.require("dojo.number"); statement in the window.load event:
<script type="text/javascript">
window.load=function() {
dojo.require("dojo.number");
}
</script>
But I'm curious why this happens. Is there a Javasctript function which forces Firefox to stop evaluating the page? Does Dojo do somethig "bad"? Can anyone explain this behavior to me?
EDIT: Dojo 1.3.1, no JS errors or warnings.
What does the rest of the page look like? What elements should be rendering that aren't? What other Javascript do you have?
What you have looks fine, but you will not be able to use methods in dojo.number or anything else loaded via dojo.require until after the page loads -- you must wait for window.onload to fire, or use the dojo.addOnLoad() method to trigger a callback. The latter is actually a bit quicker than onload.
dojo.require uses synch xhr to load which does block the browser, so if the load is unusually slow, you will notice a delay in the rendering of the page.
I think this is a rendering bug in Firefox that I've seen in a number of contexts where the one common factor is the amount of time the browser takes to load all the resources loaded in the of the page. The more scripts you have in the head that take a long time to request over the network or eval, the higher your chances are of running into this. Hitting the page with a warm cache notably reduces the possibility of running into the paint bug as well. Another way to mitigate it is to put the javascript at the end of the which is also a best practice since it doesn't block the browser from previewing markup immediately as it gets it.
Regarding the specifics of using dojo, common use cases include running things onload like creating and starting up widgets. If you have code in an onload handler that uses a dojo module like a widget, then stick the dojo.require statement inside the onload handler as well instead of before the onload handler. There's no point in suffering the performance penalty or blocking the initial UI rendering if you don't need it until later. Then build custom dojo layers to include the minimal core (possibly a custom base to make it even smaller) and the other 90% of what you need in a separate layer. Load the minimal core layer in the head (to get dojo.addOnLoad, etc) and then the other layer at the end of the body. If you live in a modular application framework where apps come and go in the page content area depending on the page you're on, each app should put the dojo.require statements for the respective dojo module it uses immediately before the module is actually referenced.
This won't work obviously if you need a module immediately in an inline script, but if that's the case then a custom dojo build will also help mitigate that case also.
I'm unaware of a reported issue with Mozilla, but I have also seen this much less often on other browsers some time ago.
I'd like to embed a number from another page. The remote call is small (only returns a number) but I would like the page to keep loading while the request is out. How should I do it? I'm currently doing
<span id="target">Loading ...</span>
<script>
var cb = function(data) {
document.getElementById("target").innerHTML = data;
}
</script>
<script src="http://webnumbr.com/webnumbrs.latest.json(callback=cb)"></script>
I'm open to client side or server side changes. Just the least code for the client embed the better
The "official" recommendation (see rules) is to put all JavaScript at the very bottom of the HTML file. The contents of every tag will be evaluated before rendering continues, as the outcome of the script might affect further rendering (think of document.write()).
Honestly,
I think the best way may be to simply put it in an onLoad() instruction so it doesn't load until the document has fully rendered. It's similar to Tom's answer but in this case you will eliminate the majority of the DOM issues you're experiencing.
I believe you are using AJAX to load the content from other page on loading the current page, make sure that your AJAX call is asynchronous, and update the "webNumbr_webnumbrs" control only after successfull completion.