简体   繁体   中英

Delaying slider animation and change effect to fade?

I am using a very simple JS for my slider, currently the images slide horizontally, left or right depending on which arrow you press. The problem I am experiencing is that there is no delay on the animation so if you click the direction arrows several times rapidly, it takes a while for the slides to catch up and there's a lot of strange overlapping.

I would like to change the animation effect to a fade and set up a delay so that you cannot advance to the next or previous slide until the current slide is done animating. Any help would be greatly appreciated!

var slideInProgress = false; 
var currentSlideIndex = 0,
slides;
function setTopSlider(){
  if (jQuery('#top_slider #container .slide').length != 0) {
    slides = jQuery('#top_slider #container > .slide');
    for(var i=0; i <= slides.length; i++){
      jQuery(slides[i]).css('left','100%');
    };
    jQuery(slides[currentSlideIndex]).css('left','0%');

    var el=jQuery('.dot:eq('+currentSlideIndex+')');
    src = el.css("background-image").replace("_off", "_over");
    el.css("background-image", src);
    el.addClass('active');
  };
};

function slide(dir) {
    var current, next, nextSlide;
    current = jQuery(slides[currentSlideIndex]);
    if(!isNaN(dir)){
        next = dir;
        if(next > currentSlideIndex )dir = 'left';
        else dir = 'right';
    };


      if(dir == 'left'){
        if(!next){
           next = currentSlideIndex + 1;
           if(next >= slides.length){
              next = 0;
           }
        }
if (slideInProgress) {
    return;
    }
    slideInProgress = true;
        nextSlide = jQuery(slides[next]);
        nextSlide.css('left','100%');
        nextSlide.css('z-index',parseInt(current.css('z-index'), 10)+1);
        nextSlide.animate({left: '0%'}, 1500);
        current.animate({left: '-100%'}, 1500);
      }else{
        console.log('moving right');
        if(!next){
             next = currentSlideIndex - 1;
            if(next < 0){
              next = slides.length-1;
            }
        }
        nextSlide = jQuery(slides[next]);
        nextSlide.css('left','-100%');
        nextSlide.css('z-index',parseInt(current.css('z-index'), 10)+1);
        nextSlide.animate({left: '0%'}, 1500);
        current.animate({left: '100%'}, 1500);
omplete: function(){
            slideInProgress = false;
            });
      };

    current.addClass('active');
    nextSlide.removeClass('active');


    var el=jQuery('.dot:eq('+currentSlideIndex+')');
    src = el.css("background-image").replace("_over", "_off");
    el.css("background-image", src);
    el.removeClass('active');


    el=jQuery('.dot:eq('+next+')');
    src = el.css("background-image").replace("_off", "_over");
    el.css("background-image", src);
    el.addClass('active');



    console.log('currentSlideIndex'+currentSlideIndex);
    console.log('next'+next);
    console.log('dir'+dir);
    currentSlideIndex = next;
};

I would just use some control variables.

Set some global (boolean) variable indicating that sliding is in progress and dont allow another sliding while previous is in progress.

UPDATE: I took your updated code, made some changes and marked changes I made in your code with // **** //. Hope, you will understand it :-). (I didnt test the code, but it should work).

// **** //
var slideInProgress = 0;
// **** //
var currentSlideIndex = 0,
        slides;
function setTopSlider() {
    if (jQuery('#top_slider #container .slide').length != 0) {
        slides = jQuery('#top_slider #container > .slide');
        for (var i = 0; i <= slides.length; i++) {
            jQuery(slides[i]).css('left', '100%');
        }
        ;
        jQuery(slides[currentSlideIndex]).css('left', '0%');
        var el = jQuery('.dot:eq(' + currentSlideIndex + ')');
        src = el.css("background-image").replace("_off", "_over");
        el.css("background-image", src);
        el.addClass('active');
    }
    ;
}
;
function slide(dir) {
    // **** //
    if (slideInProgress != 0) {
        return;
    }
    slideInProgress = 3;
    // **** //
    var current, next, nextSlide;
    current = jQuery(slides[currentSlideIndex]);
    if (!isNaN(dir)) {
        next = dir;
        if (next > currentSlideIndex)
            dir = 'left';
        else
            dir = 'right';
    }
    ;
    if (dir == 'left') {
        if (!next) {
            next = currentSlideIndex + 1;
            if (next >= slides.length) {
                next = 0;
            }
        }
        nextSlide = jQuery(slides[next]);
        nextSlide.css('left', '100%');
        nextSlide.css('z-index', parseInt(current.css('z-index'), 10) + 1);
        // **** //
        //nextSlide.animate({left: '0%'}, 1500);
        nextSlide.animate({
            left: '0%'
        }, {
            duration: 1500,
            complete: function() {
                slideInProgress--;
            }
        });
        //current.animate({left: '-100%'}, 1500);
        current.animate({
            left: '-100%'
        }, {
            duration: 1500,
            complete: function() {
                slideInProgress--;
            }
        });
        // **** //

    } else {
        console.log('moving right');
        if (!next) {
            next = currentSlideIndex - 1;
            if (next < 0) {
                next = slides.length - 1;
            }
        }
        nextSlide = jQuery(slides[next]);
        nextSlide.css('left', '-100%');
        nextSlide.css('z-index', parseInt(current.css('z-index'), 10) + 1);
        // **** //
        //nextSlide.animate({left: '0%'}, 1500);
        nextSlide.animate({
            left: '0%'
        }, {
            duration: 1500,
            complete: function() {
                slideInProgress--;
            }
        });
        //current.animate({left: '100%'}, 1500);
        current.animate({
            left: '100%'
        }, {
            duration: 1500,
            complete: function() {
                slideInProgress--;
            }
        });
        // **** //

    }
    current.addClass('active');
    nextSlide.removeClass('active');
    var el = jQuery('.dot:eq(' + currentSlideIndex + ')');
    src = el.css("background-image").replace("_over", "_off");
    el.css("background-image", src);
    el.removeClass('active');
    el = jQuery('.dot:eq(' + next + ')');
    src = el.css("background-image").replace("_off", "_over");
    el.css("background-image", src);
    el.addClass('active');
    console.log('currentSlideIndex' + currentSlideIndex);
    console.log('next' + next);
    console.log('dir' + dir);
    currentSlideIndex = next;
    // **** //
    slideInProgress--;
    // **** //
}

In jQuery animate I used complete callback function, which sets slideInPrgress to false after animation completes.

Optionally, you can set another variable indicating that someone pressed arrow while previous animation was in progress and do that slide after previous finished.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM