Texture and JavaScript Performance

Jun 28, 2010
Episode 30
This week, Nick explores the design element of texture and Jim shows you how to optimize your JavaScript performance.
Spotlight

Thanks to those who make Doctype possible!

Texture in Web Design

Texture

When designing websites, texture is one of the most useful elements of design, because it can add a lot of nice variation into your design.

You’ve probably heard of the “grunge” look, which usually features ink splatters, drips, torn up paper, and other more organic elements. The grunge look tends to come and go over the years, even before the web existed. Although this particular style is a great example of how texture can be incorporated into a web design, your site doesn’t have to go for the grunge look in order to leverage texture.

For example, you could make a very elegant background that looks like wood paneling or stone, you could create a more sleek and futuristic look with brushed or sandblasted metal.

Using Textures

When looking for ways to use texture, you might use premade textures or you might try creating your own.

You can use texture in your site’s background, in the header, or anywhere that you feel like you need to add a bit more variation and visual interest. Just be careful not to add so much texture that you distract from the important parts of your site.

You can get a lot of textural elements by just searching around the web for images, following tutorials, or playing around in Photoshop. A great way to pick up some rich and original textures though, is to use a scanner. You can scan in all sorts of interesting things, like crumples pieces of paper, a woven sweater, or a tablecloth. Another great source of texture is a digital camera. You can look in your own photo library, or go outside for the day and take pictures of interesting brick walls, the bark of a tree, or the crazy carpet in a hotel lobby.

Once you’ve gathered your source material, you’ll probably have to massage it a bit in Photoshop to fit your website. For example, you may want to turn a picture into a repeating texture to use it for your site background.

JavaScript Performance

When working with JavaScript in the browser, sometimes it’s important to make sure your code is running as efficiently as it can. Today we are going to to be taking a look at JavaScript Performance.

Loops

One obvious place to optimize performance is in loops.

When working with loops, you want to look at the work that is being done over and over again and try to minimize it. Now this really depends on what’s in your code, but take a good hard look inside your loop and see if there are any calculations of functions that will always return the same value. These really only need calculated once, so put them before your loop so you don’t have to calculate them again and again.

for(var i=0; i < array.length; i++){
  var seconds = 1000 * 24 * 60 * 60 * 60;
  var listOfWords = "some words here".split(' ');
  doSomething(i, seconds, listOfWords);
}

Also if your loop is comparing it’s iterator variable to the lenght of the array, you need to realize there is a cost to looking up the length of the array, and since it generally doesn’t change in most loops, you can store the length into a variable before the loop, and compare to that instead.

var seconds = 1000 * 24 * 60 * 60 * 60;
var listOfWords = "some words here".split(' ');
var len = array.length;
for(var i=0; i < len; i++){
  doSomething(i, seconds, listOfWords);
}

DOM manipulations, string manipulations, and function calls are the biggest things to watch out for, so try to minimize their use inside loops and you will likely see an increase in speed.

Variable lookups

Resolving variables in JavaScript does take time. Several factors influence the resolution times of variables, but you can’t beat a local variable for speed.

One slowdown is if your variable is defined several scopes higher than your current scope.

jQuery = (...)
(function(){
  ...
  (function(){
    ...
    (function(){

      jQuery(...)
      jQuery(...)
      jQuery()
    })()
  })()
})

In this example, jQuery is defined at the global scope. Inside a deeply nested scope, we are using the jQuery variable several times, and each time the browser needs to find what it references. This involves searching several scopes for the variable, and each of these may be fairly large.

You can speed this up by redefining jQuery in your local scope, so you can resolve it without having to search through the whole scope chain.

jQuery = (...)
(function(){
  ...
  (function(){
    ...
    (function(){
      var jQuery = jQuery;

      jQuery(...)
      jQuery(...)
      jQuery()
    })()
  })()
})

Obviously you only want to do this if your variable is referenced several times. If it is only used once in the first place, this extra piece of code will actually be more work.

Another slowdown can happen when looking up properties. For instance YAHOO’s YUI2 library has a lot of deeply nested functions and properties, to keep it organized.

YAHOO.util.Dom.get('.test');
YAHOO.util.Dom.get('.another');
YAHOO.util.Dom.get('.again');

Here, if we are using this deep YAHOO.util.Dom.get function, we can make it faster, and easier to type by assigning it to a local variable

var Domget = YAHOO.util.Dom.get;
Domget('.test');
Domget('.another');
Domget('.again');
DOM Changes and Styles

Often you want to change styles of your elements using JavaScript. For instance jQuery’s css function makes it easy to set several styles at once.

$('div#intro').css({
  color: '#F00',
  width: '500px',
  float: 'left',
  padding: '30px'
})

But this is costly. Each property you set requires the browser to reflow, or recalculate the position and dimensions of elements on the page. This is very costly.

Instead, you should try to utilize css classes, and apply or remove them. Doing this allows the browser to do a much more efficient reflow, instead of several small ones.

/* CSS */
.crazyStyle {
  color: #F00;
  width: 500px;
  float: left;
  padding: 30px;
}

/* JavaScript */
$('div#intro').addClass('crazyStyle')

Creating elements in JavaScript can be costly as well. If you want to create an ordered list with hundreds of elements, it’s much more efficient to create the html for the list items, the use innerHTML on the list to add them then it is to individually create elements and append them.

// Faster
var html = "";
for(var i=0; i < 1000; i++){
  html += "<li>#" + i + "</li>";
}
myList.innerHTML = html;

// Slower
for(var i=0; i < 1000; i++){
  var li = document.createElement('LI');
  var text = document.createTextNode('#' + i);
  li.appendChild(text);
  myList.appendChild('text');
}

And when you are creating string from little pieces, it is more efficient to create an array of small strings and add to the array, and then join them all together, than it is to constantly append to one string over and over again.

// Faster
var html = [];
for(var i=0; i < 1000; i++){
  html.push("<li>#" + i + "</li>");
}
myList.innerHTML = html.join('');

// Slower
var html = "";
for(var i=0; i < 1000; i++){
  html += "<li>#" + i + "</li>";
}
myList.innerHTML = html;