jQuery Load SlideToggle Jumping

jqueryscrolltoggle

When I began blogging, I envisioned that the majority of my posts would be similar to this one – documenting interesting quirks and bug fixes. Of course, nearly every quirk or fix I’ve come across has already been documented on various blogs across the internet – until now!

 

The Problem

When working on the taxonomic browser for PNW Moths, I had an issue with the jQuery slidetoggle command jumping when displaying AJAX loaded content for the first time. The root problem whenever you have  a jumpy/jerky slidetoggle is that jQuery has calculated the wrong height for your container. The most common fix for this problem, setting a static width, has a good writeup at jQuery for Designers. Even after applying this fix, the problem still persisted on the server.

 

The Diagnosis

On one test, I happened to notice the image content flash in while the div was sliding in – this, coupled with the fact that the problem didn’t occur on localhost made me realize something about the jQuery.load() completion callback. jQuery fires the callback when the HTML content has loaded, but not necessarily the image resources that the HTML refers to. In my case, scrolltoggle was calculating the hidden div’s height when a majority of the images hadn’t fully loaded, giving the animation an inaccurate height and causing a jump.

 

The Solution

The solution is to wait to call scrolltoggle until after the images have loaded, which I did with the help of Alexander Dickson’s waitForImages plugin (waiting for images is a surprisingly tricky thing to do cross-browser).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// Toggle on click
jQuery(this).find('.toggle_item').click(function() {
  if (jQuery(this).parent().siblings('.ajax').html().length) {
    // If we've loaded the content before, just show it
    jQuery(this).parent().siblings('.ajax').slideToggle('slow');
  } else {
    // Otherwise, load it via AJAX
    jQuery(this).parent().siblings('.ajax').load(url + ' .browse_item', function() {
        jQuery(this).waitForImages(function() {
            jQuery(this).slideToggle('slow');
        });
        return false;
    });
  }
});

 

If this post ever saves you an hour, please drop a comment below!

On another note, I apologize to my readers for the lack of posts recently; school and work has been extremely hectic this quarter. However, that doesn’t mean I haven’t been programming interesting things… I have another exciting post in the works detailing a simple Ant AI I wrote and a preview of a mobile application I’m working on.

P.S. Code readability has been improved with a new jQuery effect (Try mousing over).