Gracefully Degrading Javascript

In the early days of web development, before the W3C became a real heavyweight influence, and in the thick of the browser wars of yesteryear many bad habits were formed around the methods of writing JavaScript. Waves of free 'cut-n-paste' solutions appeared on the scene, often bulging with dodgy code and browser-sniffing techniques. Such things were common place for one reason; there were no standards. Today, in 2006, things are very different indeed. The push for standardisation over the internet has never been stronger and finally after years of tearing our hair out we web developers have a set of guidelines to work to. This is becoming very evident with the likes of HTML in the form of its standardised cousin XHTML. However old habits die hard and the transition from non-standard, inaccessible JavaScript is appearing to take place at a much slower pace.

In this article I will introduce you to a few basic methods which you can employ, should you decide to pick up your JavaScript paintbrush anytime soon. I'll try and keep them as simple as possible and stick only to three important points, however some entry-level knowledge of JavaScript will be necessary. Here we go.

  1. Flexible Links - Many JavaScript actions activate through the click of an element. For the most part inactive JavaScript will not adversely affect that element. This is not the case however with links if not handled correctly. A badly written link will almost certainly be a dead link should JavaScript be turned off. Many developers use the JavaScript pseudo command as a value to the href attribute:
    <a href="javascript:myFunction();" title="My Link">
    Due to some support issues this method is not recommended, even if JavaScript was guaranteed to be active. Another method is to use a combination of the onclick attribute and a null href attribute:
    <a href="#" onclick="myFunction();" title="My Link">
    Perhaps a small improvement over the previous version, but this still does not degrade gracefully. If JavaScript is not active, nether is the link. What we need is something that will work regardless of whether JS is on or off:
    <a href="example.html" onclick="myFunction(); return false;" title="My Link">
    That's better! If JavaScript is active the myFunction(); is executed correctly. Furthermore the following return false; statement ensures that the link's href attribute is not followed by the browser. Should JavaScript not be active however, the link is followed as normal to a page which typically will present the same content that the myFunction(); function would have provided.
  2. Avoid Browser Sniffing - Browser sniffing is the technique of identifying a client's browser by extracting information from it. This technique is somewhat risky and not recommended for several good reasons:
    • Browsers lie - they are under the control of the visitor and can therefore be tampered with. Additionally for historical reasons browsers also sometimes provide incorrect information.
    • Convoluted Code - There are a lot of browser types out there, many of which both you and I will not have heard of. Catering for all of them will be a heavy task to say the least and can leave your code difficult to read and maintain.
    • Future Maintenance - A new browser is released and all browser sniffing software will have to be updated in order to cater correctly.
    Foundationally the technique of browser sniffing is to ensure graceful degradation. To remove such a feature without a replacement would be foolish. However there is a much better method of ensuring your software handles well on non-standard JavaScript supporting browsers.
  3. Using Object Detection - Why identify browsers to determine the extent of JavaScript support when you can go directly to the source? An object in JavaScript is a construct with properties that are either variables or other objects. Functions associated with an object are known as the object's methods. An example would be the document object using the getElementById method:
    document.getElementById('id');
    By testing for the presence of this object prior to any other commands we can effectively determine in just one line of code whether the client's browser supports the JavaScript specification we require. Take a look at the following statement:
    if (!document.getElementById) return false;
    In this statement we are saying "if the document method getElementById is not executing correctly then halt execution of the script". You can use this method on any object you like, but in many cases it is not necessary to use more than just the above, or it's sibling method getElementsByTagName.

We've only scratched the surface of accessible Javascript here, however, simple as they are the above points will notably improve the quality and accessibility of your code. I'll be writing more about this and similar subjects in future posts, so stay tuned!

Article Envelope

About the Author

Photo of Steve Tucker

Steve Tucker is a 23 year old web developer living in Huddersfield, England
Read more...



Comments

  1. Comment Envelope

    As for flexible links, it's also good practice to attach onclick event handlers with javascript itself instead of embedding it inside the link. For example:

    &lt;script language="javascript"&gt;
    linkage.onclick = "javascript:myFunction();
    &lt;/script&gt;

    &lt;a href="example.html">text&lt;/a&gt;

    Permilink
  2. Great point Oliver, and one which I had considered including this in the article. This falls more under seperation of structure from behaviour so I decided to omit it for a more specific post on the subject soon.

    Permilink
    • Dated: 08/05/2006
    • Author: Tilly
    • Website: none

    Object detection - something i never tried before but sounds useful man! thanx for the tips!

    Permilink
    • Dated: 11/05/2006
    • Author: Dan Wilson
    • Website: none

    I think its imporant that we make sure the quaility of our codes as high as possible. The difference that small additions make, such as the ones youve pointed out in this article, are huge from an accesiblility point of view. Good one!!

    Permilink
  3. Cheers for the comments all.

    Permilink
    • Dated: 12/05/2006
    • Author: Jeff
    • Website: none

    For a more in-depth look at this I suggest reading DOM Scripting by Jermy Keith. I just finished reading a chapter dedicated solely to making your links gracefully degrade and being as unobtrusive as possoble. An excellent read!

    Glad to see others headin in the right direction.

    Permilink
  4. If only JS was a language I could grasp. I was just trying to edit the delicious JSON script and couldn't get it working.

    Who know's maybe it will make sense to me someday...

    Permilink
  5. @Jen JavaScript aint that hard, but on a personal level I found that my prior knowledge and experience in PHP and a few other languages really helped.

    Permilink
    • Dated: 15/05/2006
    • Author: dreamer
    • Website: none

    The next step would be:

    <a href="example.html" onclick="return myFunction();" title="My Link">

    Thus the link execution is not only up to JavaScript being enabled but rather on the myFunction() return value. Which might still be "true" if the function didn't complete its task, for whatever reason that might be.

    Permilink
  6. Yeah, thats a good observation. Its just extra validation all the way, so every base is covered whatever the circumstaces

    Permilink

Leave a Comment

Please feel free to leave a comment about this article. You can enter HTML markup, though it will be encoded and appear as you type it.

Please keep your comments friendly and constructive. Offensive comments will be deleted and the author will no-doubt be subject to an eternity of torment in the fiery pits of hell. Cheers.

What is 40 + 6?