31. var $list = $("#list");
for(var i = 0; i < 1000; i++) {
$list.append("<li>"+i+"</li>");
}
Appending the same element many
times to the DOM
jQuery DOM Manipulation
32. var array = [];
for(var i = 0; i < 1000; i++){
array[i] = "<li>"+i+"</li>";
}
$list.append(array.join(""));
Using string concatenation or
array.join() before appending
jQuery DOM Manipulation
34. var $noSuchElement = $("#element-not-found");
if ($noSuchElement.length) {
$noSuchElement.slideUp();
}
Verifying objects exist before using
them
jQuery DOM Manipulation
35. var $list = $("#list-container > ul");
// Complicated DOM manipulation methods
Performing lots of DOM manipulation
inline
jQuery DOM Manipulation
36. var $list = $("#list-container > ul").detach();
// Complicated DOM manipulation
$list.appendTo("#list-container");
Detaching elements before DOM
manipulation and adding them back
jQuery DOM Manipulation
According to builtwith.com jQuery’s core library is used by about 70% of the top 100,000 web sites, up 10% from last year.
Several projects use jQuery including Bootstrap, Backbone.js, jQuery Mobile and many plugins have been developed to support jQuery.
How many of you are currently developing web sites with jQuery?
When used correctly, jQuery can make it easier to build interesting and interactive web sites.
Today I am going to share some good and bad ideas when developing web sites using the jQuery framework.
If developers follow best practices and standards it makes code easier to read and comprehend.
Code bases should appear as if it were written by a single programmer, rather than a group of competing coders.
I have consolidated several examples of how to improve maintainability and performance using best practices and standards.
I have collected these from several web sites and blog posts I have perused throughout my career as a developer.
I wish I had known about jQuery coding standards and best practices when I first started developing with jQuery.
Although back when I first started developing with jQuery they probably didn’t exist.
I would get frustrated when I would find three or four different ways to write the same bit of logic and I wish I had some guidelines to follow.
With this presentation I hope to help you avoid the frustration I went through when I started developing with jQuery.
I will cover best practices and standards related to the following topics...
Loading jQuery from a local server can be slow.
Loading jQuery from a CDN is much faster because
CDNs use very powerful, geographically distributed servers to deliver jQuery to your users.
Since many web sites use CDNs the jQuery library will most likely have already been cached by the browser and may not even need to be downloaded at all.
In this code snippet you can see that jQuery is loaded from Google’s CDN which hosts many frameworks along with jQuery.
It is a bad idea to assume the CDN is going to be up 100% of the time.
In the unlikely event that jQuery fails to load from the CDN your web site is probably going to look pretty bad.
This code example demonstrates how to verify if jQuery has been loaded.
And if jQuery fails to load a script tag is written out to load jQuery from your local server
Explain the code.
Protocol dependent URLs are URLs that contain the http: or https: portion of the URL.
If your web page is loaded using the https: protocol and jQuery is loaded using http: protocol.
Your users will get a nasty error message similar to the one displayed here.
Leave off the http: or https: portion off the URL
The browser will use the same protocol that was used to load the html
No more ugly error message
This is less of an issue with modern browsers, but unfortunately not all of our users are using modern browsers.
If the script is loaded at the top of the page the browser will download it before it downloads other resources such as the HTML and CSS.
The user will be starring at a blank page while they are waiting for jQuery to downloaded and run.
When jQuery is loaded at the bottom of the page the browser will download the HTML and CSS before it downloads the JavaScript.
The page will render faster allowing the user to view the page more quickly because the HTML and CSS will load and draw the page before the JavaScript code is downloaded.
In order to make jQuery more efficient for sites that don’t support IE8 and below the that code has been removed in version 2.x
Your code will NOT run as expected on browsers less than IE9.
The jQuery foundation was nice enough to produce a version of the framework with support for IE 8 and below.
Use jQuery 1.x if you intend to support IE 6, 7 and 8.
In this example the big container variable is difficult to read
And it is not clear that it is a jQuery object
It is much easier to read the big container variable because it is written using camel case.
A common jQuery standard is to preface jQuery object variable names with a $.
This makes it easy to identify that this variable is a jQuery object.
Searching the DOM is slow therefore you want to do it less often.
In this code example jQuery will search the DOM for an element with an id of container 50 times.
In this example jQuery searches the DOM once for the element
The jQuery object is saved to a variable in the first line of code
Then inside the for loop the variable is referenced instead of searching the DOM for the element each time.
In this code example jQuery will search the DOM three times for the same object.
Once when the addClass method is called.
Then again when the fadeIn method is used.
And one more time for the removeClass method.
jQuery methods return the object that it references
This allows you to chain jQuery methods.
In this example jQuery will search the DOM for an element with an ID of link.
Then it will run the addClass method, pass the jQuery object to the fadeIn method and finally to the removeClass method.
The DOM is searched one time before calling the three methods instead of three times.
If only one element on the page contains the class product this is not the most efficient way to find the element.
jQuery will search the entire DOM for the class even after it finds the element.
Searching the DOM by ID is faster because jQuery will call the native JavaScript method document.getElementById().
It is also faster because IDs are unique and jQuery will stop searching the DOM once the element is found.
Testing performance using JSPerf.com showed that searching by id is 54% faster than search for a class name.
This is slow since jQuery must search for multiple elements to find what it is looking for.
In the first code example jQuery will search for an element with an id of container.
And when that is found it will search for a table with a class of attendees and finally a td with a class of column.
As you can see there are several elements that need to be found before finding what you are really looking for which is slow.
In the first line of code jQuery will only search for one element and quit searching when it is found.
In the second line of code jQuery will search for an element with an ID of product-container and then search for all child elements with a class of products.
This is faster than searching the whole DOM for the element with the class of products.
Especially if you have several elements in the product container you need to search for.
The last line of code is similar to writing the find method and functions similar to it.
According to a test on JSPerf.com using the find method is 56% faster than using a child selector.
Searching using universal selectors such as * or pseudo classes such as radio or checkbox is very slow.
In the last two lines of code jQuery will search all elements in the DOM to see if they have a type attribute of radio or checkbox.
The first line of code will run faster because the children method has been substituted for the * universal selector.
jQuery will first search for the element with the class container and then find all the children in that element.
In the last two lines of code the input element has been specified.
jQuery will search for input tags on the page first and then check if the input tag has a attribute of type radio or checkbox.
Rather than searching all the elements for the attributes.
According to a test on JSPerf.com searching for :checkbox is 92% slower than input[type=checkbox] and 68% slower than input:checkbox.
In this example, each time the append method is called,
In this case 50 times in the for loop the browser must resize and/or reposition elements.
As you can imagine this can be very slow
In this code an array is built containing the list of elements and they are all added to the DOM at the same time.
This is faster because the browser only has resize and/or reposition elements once.
In this example jQuery will run three functions before it realizes the element doesn’t exist.
In this example the jQuery object is saved to a variable.
On the next line of code we verify the element exists first by checking the length of the selector.
This is faster because only one jQuery method is called and the slideUp method is never called.
For example we have a list with many items and run many DOM manipulation methods on it.
DOM manipulation is slow.
jQuery provide a nice method to make this much more efficient.
Detaching an element from the DOM before manipulating it is faster.
Because the browser doesn’t have to refresh the page with each change.
The page is refreshed once when the element is added back to the page.
It is difficult to update or remove event handlers,
And debug JavaScript if it is embedded in the HTML code.
Updating or removing event handlers is easier if the code is in a JavaScript file.
And debugging the JavaScript code is easier if it is all in one place.
If there is one thing you take away from this presentation it is this: Please don’t use anonymous functions.
You would think this is a best practice by how many code samples and documentation pages contain anonymous function.
They are difficult to debug, maintain, test and are not reusable and Please avoid using them.
As you can see here the click handler references the linkClickHandler function instead of using an anonymous function.
Named functions are much easier to debug, maintain and test.
As well as the linkClickHandler method in this example can be reused by a hover or keyboard event.
Again anonymous functions are difficult to debug, maintain, test and are not reusable.
It is difficult to determine where the document ready event hander ends when your code is contained in a huge anonymous function.
Yet I see this all over the Internet.
The document ready event handler can be written with a named function.
This will make it easier to break your code up into smaller pieces that are more manageable.
I usually start all my jQuery projects with this code.
In this example an event handler is attached to each link within the element with the ID of list.
If the list contains 10 items 10 click handlers will be created for this list.
This is redundant and can be slow.
In this code snippet a single event handler is added to the list element,
And when a user clicks on a link within the list the event will bubble up to the parent list element.
This will reduces the number of event handlers on the page,
And will be more efficient especially if the list contains many elements.
This click handler functions the same except only one click hander is created on the list instead of one for each item in the list.
.getJson and .get are short cuts for $.ajax.
$.ajax is what is actually called, therefore, you might as well use it.
As you can see in this example,
It is difficult to read the parameters when they are added as part of the ajax URL.
Parameters are much easier to read in this code snippet because it is added using the data object.
If error handling is not added the ajax will fail silently.
404, 500 and failure handlers are all implemented here.
A friendly message should be added to the error handlers to display to the user,
As well as some method to notifying developers of the error.
The error could be saved to a log or emailed to the developer.
It is difficult to debug and update your CSS code if it integrated with the JavaScript code.
Create classes in your CSS style sheets,
And add them using the jQuery addClass method.
In this example the attr method is called three times.
This is inefficient and there is a better way to write this code.
Instead of calling the attr method three times you can pass in an object literal.
When you use object literals the attr method is only called once.
Hopefully I have demonstrated how following standards and best practices can make your code more maintainable and efficient.
You now should see how your code can be easier to read and comprehend.
Now go out there and start writing more efficient code and write it as if it were written by a single programmer, rather than a group of coders.