Make an element unclickable while animated

2019-06-14 12:51发布

问题:

I am trying to make an element not clickable when it is animated. When the animation is done I want it to be clickable again. I have searched a long time for some help on how to achieve this, but I can't get it to work and I don't know why.

The HTML:

<p>
   <span class="red" id="a">A</span><span id="llright" class="hide">llright</span> B C D
</p>

When letter A is clicked, it moves to the left and then some text fades in next to it.

The jQuery:

(function() {

var letterA = $('#a'),
    llright = $('#llright');


$('#a:not(.open)').live('click', function() {
    letterA.animate({
    marginRight: "5.7in",
    }, 1300, function() {
        letterA.addClass('open');
        llright.fadeIn(1300); // Animation complete.
    });

});


$('#a.open').live('click', function() {
    llright.fadeOut(700);
    letterA.delay(700).animate({
    marginRight: "0.0in",
    }, 700, function() {
        letterA.removeClass('open');
    });

});


})();

The animation works great, but this doesn't:

if(letterA.is(':animated')) {
    letterA.unbind('click');
};

The last part doesn't work at all, even when I insert a simple alert() instead of unbind() it doesn't seem to figure out when A is moving and not.

I could really use some help here, I have tried everything I can think of.

Thx /Oscar

回答1:

Your check is only running on page load. Do the check inside of the click function:

$('#a:not(.open)').live('click', function() {
    if(!letterA.is(':animated')) {
        letterA.animate({
        marginRight: "5.7in",
        }, 1300, function() {
            letterA.addClass('open');
            llright.fadeIn(1300); // Animation complete.
        });
    }
});

Also, live() is deprecated; consider moving to on().



回答2:

It's more economical to attach just one click handler with internal branching to cater for the different circumstances; forward animation, reverse animation and to reject while animation is in progress.

You can also get away without addClass/removeClass('open') by testing the state of llright instead.

Something like this should do it:

$('#a').on('click', function() {
    var $this = $(this),
        llright = $this.next("span");
    if($this.is(":animated") || llright.is(":animated")) {
        return;//reject (no action)
    }
    if(llright.is(":visible")) { //reverse animation sequence
        llright.fadeOut(700, function(){
            $this.animate({
                marginRight: 0,
            }, 700);
        });
    }
    else {
        $this.animate({ //forward animation sequence
            marginRight: "5.7in",
        }, 1300, function() {
            llright.fadeIn(1300);
        });
    }
});

Note also that with this code it is not necessary to use .live().