Making a standard, static website more fun with AJAX!

Written on

You have a website. It has links. Clicking on a link tells the browser to drop everything it has and get a completely new set of data. That data can include headers, menus, footers, essentially things that the old page and the new page share. That isn’t very bandwidth efficient. Or exciting.

I had a website just like that, but I wanted more. I wanted everything to use AJAX where applicable. I didn’t want to see the screen flicker between pages. And I also didn’t want to invest too much time in this. And I did it! And you can do it too!

What I propose to you is animations! Content flying off the screen (and back)! Also, transforming your existing website almost instantly from non-AJAX to AJAX.

How hard is it to implement? Surprisingly easy with the help of jQuery. If you want a live example, just browse this very website.

Step 1: have a function that allows you to download a piece of content via AJAX.

function getURLViaAJAX(url) {
    $.ajax({
        url: url,
        cache: false,
        type: "GET",
        data: { AJAX : 1 }
    })
    .done(function( html ) {
        $("#maincontent").html( html );
    });
}

This gives us a function that replaces the #maincontent with the content of a page we’re retrieving. It’s a start! But we’re not using that function anywhere. No worries!

Step 2: make all links use our function instead!

function updateLinks(contentOnly)
{
    if(contentOnly == 0)
    {
        $('a').click(function() {
            getURLViaAJAX(this.href)
            window.history.pushState("", "Went to new page", this.href);
            return false;
        });
    } else {
        $('#maincontent a').click(function() {
            getURLViaAJAX(this.href)
            window.history.pushState("", "Went to new page", this.href);
            return false;
        });
    }
}

$(document).ready(function() {
    updateLinks(0);
});

This makes ALL the links on the page attempt to use AJAX to get their content. It also makes use of HTML5’s State History feature, to allow going back and forth between pages. And don’t worry, if the user doesn’t have JavaScript enabled, it just reverts to the plain old behaviour of yore. If you want to fine-tune what links should use AJAX, just change $('a') to $('a[class=ajax_link]') to only allow anchors with class=”ajax_link”, or, alternatively, use $('a').not('.not_ajax') to ignore anchors with class=”not_ajax”.

You could use this method to replace the onClick behaviour of all anchors on a page with whatever else you want!

You’ll now ask yourself: but doesn’t this just download the whole page anyway? And I answer: yes, it currently still does. But we fix everything!

Step 3: notice how in the getURLViaAJAX function we have data: { AJAX : 1 }. This is the key to doing some trickier stuff. You have to edit any files that control how you receive data and have any useless data not processed when $_GET['AJAX'] is 1.

An example for PHP:

<?php if(!(isset($_GET['AJAX']) && $_GET['AJAX'] == 1)) { ?>
    //LOTS OF CODE WE DON'T WANT
<?php } ?>

When a page is retrieved without the AJAX=1 query string, it renders normally. When it does get that query string, it omits any headers, scripts, menus, etc.

What about animations? Glad you asked! We can handle those however way we want in the .done function of the getURLViaAJAX block of code. Here’s my example:

.done(function( html ) {
    $("#maincontent").animate(
    {
        left: $(window).width()
    }, 500, function() {
        $( "#maincontent" ).html( html );
        updateLinks(1);
    });
    $("#maincontent").animate(
    {
        left: 0
    }, 500);
});

Oh, and yes, you do need to call updateLinks(1) to change the behaviour of any new links that might be created once we retrieve a new page. The “1” parameter tells it to update only the new page elements (the ones in #maincontent). You don’t want to update ALL the links again, trust me.

Step 4: We’re done! Your particular website will likely need some tweaks to make it work, but these instructions should prove to be a good start for most people!

Step 5: Still here? Well, good. Because I didn’t tell you of some of the problems that might arise from doing this. First off, Facebook social bits (the Like button, comments, etc) that might exist on the page you’re retrieving will not work. How do we solve this? Add FB.XFBML.parse() after updateLinks(1) in the .done function. For LinkedIn buttons, the call to add is IN.parse(). And that’s it.

Good luck!

Disclaimer: I am certain there are ways to improve on this solution. I am also certain I may have missed some very important issue that could cause problems. But practice has shown this works well enough and I truly hope it stays that way.