paged.csci
paged.csci

Reputation: 37

jQuery Animations don't wait before starting their Complete

I've been working on fading divs in and out on clicks in a navigation bar, but I was having trouble getting the 'complete' input of an animation function to work properly. My solution was adding in delays (I've supplied code and a JSFiddle), but this seems like a bad solution to me. I was wondering if someone could explain the 'complete' input of things like .fadeIn() and .fadeOut() to me?

I used the following example, and found that the fade in would start before the fadeout had been completed, causing jumps in the divs, which I was trying to avoid.

$(function () {
    $('#tabCarts').click(function () {
        $('div[id^="body"]').fadeOut(140, function () {
            $('#bodyCarts').fadeIn(140);
        });
    });
    $('#tabSearch').click(function () {
        $('div[id^="body"]').fadeOut(140, function () {
            $('#bodySearch').fadeIn(140);
        });
    });
    $('#tabRequests').click(function () {
        $('div[id^="body"]').fadeOut(140, function () {
            $('#bodyRequests').fadeIn(140);
        });
    });
});

Here is the basic markup that I did to demonstrate.

<ul>
    <li><a href="#" id="tabCarts"> Carts</a>

    </li>
    <li><a href="#" id="tabSearch"> Search</a>

    </li>
    <li><a href="#" id="tabRequests"> Requests</a>

    </li>
</ul>
<div id="bodyCarts" class="bodyTab">Carts</div>
<div id="bodySearch" class="bodyTab">Search</div>
<div id="bodyRequests" class="bodyTab">Requests</div>

And here is my JSFiddle Entry so you can see what I'm talking about.

My solution involved putting delays in before the fadeIn started, and having them both run simultaneously, but this feels like a bad answer to me.

Thanks for the answers!

Upvotes: 2

Views: 160

Answers (1)

Frizi
Frizi

Reputation: 2940

The cause of firing the callback too early is that you are binding the hiding animation to already hidden elements. It is immediately completed on some of them.

To fix this, you need to select only visible element by $('div[id^="body"]:visible') selector.

One more gotcha here. As you are now selecting only visible elements, at least one of them need to be visible in the first place. That's why I put the additional fadeIn at the beginning.

http://jsfiddle.net/RdwUS/5/

$(function () {
    $('#bodyCarts').fadeIn(140);
    $('#tabCarts').click(function () {
        $('div[id^="body"]:visible').fadeOut(140, function () {
            $('#bodyCarts').fadeIn(140);
        });
    });
    $('#tabSearch').click(function () {
        $('div[id^="body"]:visible').fadeOut(140, function () {
            $('#bodySearch').fadeIn(140);
        });
    });
    $('#tabRequests').click(function () {
        $('div[id^="body"]:visible').fadeOut(140, function () {
            $('#bodyRequests').fadeIn(140);
        });
    });
});

Upvotes: 2

Related Questions