在最后一次迭代的 each() 函数中更改变量值 - jQuery

change variable value in each() function last iteration - jQuery

这是我的 fiddle link.

所以我会有多个步骤,应该一个一个地制作动画。为了让它们一个接一个地动画化,我使用了一些 flag 变量。根据它的值,相应的步骤应该是动画的。

但是有一个问题 - 它的值在第一步中没有被改变,这就是为什么当你点击 2(从时间轴)时只有第一步被动画化。当我在 each() 函数中一个一个地动画每个箭头并且 flag 变量值在箭头的最后一次迭代中被更改时,问题出在下面的部分:

var flag = 0;
function step_1(){
    jQuery(".step_1_nav").addClass('active_bullet_point');
    jQuery(".step_1 .label").addClass('active_label_text');

    var delay = 0;
    jQuery('.step_1 .arrows span').each(function(index) {
        var $this = $(this);
        var total = $('.step_1 .arrows span').length;
        $this.delay(delay).animate({opacity:1}, 100, function(){
            $this.addClass('white_animated_arrow');
            if (index === (total - 1)) {
                jQuery(".step_1 .bullet_point").addClass('active_bullet_point');
                flag = 1;
            }
        });
        delay += 100;
    });
}

jQuery(".step_2_nav").click(function(){
    step_1();
    console.log(flag); /* here flag returns 0 instead of 1 */
    step_2();
});

当我放这部分的时候

if (index === (total - 1)) {
    jQuery(".step_1 .bullet_point").addClass('active_bullet_point');
    flag = 1;
}

out of animate 回调函数标志的值被更改为 1,但它立即发生而不等待最后一个箭头的迭代并且所有 2 个步骤都立即被动画化。

我在这里缺少什么?有什么想法吗?

不确定我是否理解得很好。当第 2 步时,您想要的是反向 运行 的动画,对吗?

您可以使用 jQuery reverse() 来实现此目的,如下所示:

jQuery(jQuery('.step_2 .arrows span').get().reverse()).each();

var flag = 0;
function step_1(){    
    jQuery(".step_1_nav").addClass('active_bullet_point');
    jQuery(".step_1 .label").addClass('active_label_text');

    var delay = 0;
    jQuery('.step_1 .arrows span').each(function(index) {
        var $this = $(this);
        var total = $('.step_1 .arrows span').length;
        $this.delay(delay).animate({opacity:1}, 100, function(){
            $this.addClass('white_animated_arrow');
            if (index === (total - 1)) {
                jQuery(".step_1 .bullet_point").addClass('active_bullet_point');
                flag = 1;
            }
        });
        delay += 100;
    });
}

function step_2(){
    if(flag == 1){
        jQuery(".step_2_nav").addClass('active_bullet_point');
        jQuery(".step_2 .label").addClass('active_label_text');

        var delay = 0;
        jQuery('.step_2 .arrows span').each(function(index) {
            var $this = $(this);
            var total = $('.step_2 .arrows span').length;
            $this.delay(delay).animate({opacity:1}, 100, function(){
                $this.addClass('white_animated_arrow');
                if (index === (total - 1)) {
                    jQuery(".step_2 .bullet_point").addClass('active_bullet_point');
                    flag = 1;
                }
            });
            delay += 100;
        });
    }
}

jQuery(".step_1_nav").click(function(){
    step_1();
});

jQuery(".step_2_nav").click(function(){
    step_1();
    flag = 1;
    console.log(flag);
    step_2();
});
.step {
  margin-right:30px;
  display:inline-block;
  vertical-align:top;
  text-align:center;
  margin-top:20px;
  margin-left:20px;
}
.arrows {
  width:10px;
  display:inline-block;
  vertical-align:top;
}
.arrows_up {
}
.arrows span {
    border: solid #000;
    border-width: 0 2px 2px 0;
    display: block;
    padding: 4px;
    margin-bottom: 4px;
    width: 0;
    height: 0;
    -webkit-transition: border-color 0.4s;
    -moz-transition: border-color 0.4s;
    transition: border-color 0.4s;
}
.arrows_down span {
    transform: rotate(135deg);
    -webkit-transform: rotate(45deg);
    -moz-transform: rotate(45deg);
    -ms-transform: rotate(45deg);
}
.arrows_up span {
    transform: rotate(-135deg);
    -webkit-transform: rotate(-135deg);
    -moz-transform: rotate(-135deg);
    -ms-transform: rotate(-135deg);
}
.label {
  color:#000;
  margin-bottom:10px;
  font-weight:bold;
  display:block;
  font-family:'Arial';
}
.bullet_point span {
    font-family:'Arial';
    width: 12px;
    height: 12px;
    border-radius: 50%;
    background: #000;
    display: inline-block;
    vertical-align: middle;
    -webkit-transition: all 0.4s;
    -moz-transition: all 0.4s;
    transition: all 0.4s;
}
.step_2 .bullet_point {
  margin-bottom:15px;
}
.step_2 .label {
  margin-top:5px;
}
.active_label_text {
  color:red;
}
span.white_animated_arrow {
    border-color: red;
}
.timer_nav {
  margin-top:20px;
  margin-left:0px;
}
.timer_nav  span.timeline {
  color:#000 !important;
  cursor:text;
}
.timer_nav span {
  color:#000;
  font-size:20px;
  cursor:pointer;
  font-family:'Arial';
  font-weight:bold;
  margin:0px 10px;
  -webkit-transition: all 0.4s;
    -moz-transition: all 0.4s;
    transition: all 0.4s;
}
.timer_nav span:hover {
  color:red;
}
.active_bullet_point {
  color:red;
}
.timer_nav span.active_bullet_point {
  color:red;
}
.active_bullet_point span {
  background:red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="step step_1">
  <span class="label">STEP 1</span>
  <div class="arrows arrows_down">
    <span></span>
    <span></span>
    <span></span>
    <span></span>
  </div>
  <div class="bullet_point"><span></span></div>
</div>

<div class="step step_2">
  <div class="bullet_point"><span></span></div> 
  <div class="arrows arrows_up">
    <span></span>
    <span></span>
    <span></span>
    <span></span>
  </div>
  <span class="label">STEP 2</span>
</div>

<div class="timer_nav">
  <span class="timeline">Timeline</span>
  <span class="step_1_nav">1</span>
  <span class="step_2_nav">2</span>
</div>

指定一个匿名回调,并让step_1接受它:

function step_1(callback){
    if(!callback) callback =function(){};
    jQuery(".step_1_nav").addClass('active_bullet_point');
    jQuery(".step_1 .label").addClass('active_label_text');

    var delay = 0;
    jQuery('.step_1 .arrows span').each(function(index) {
        var $this = $(this);
        var total = $('.step_1 .arrows span').length;
        $this.delay(delay).animate({opacity:1}, 100, function(){
            $this.addClass('white_animated_arrow');
            if (index === (total - 1)) {
                jQuery(".step_1 .bullet_point").addClass('active_bullet_point');
                callback();
            }
        });
        delay += 100;
    });
}

并称它为:

jQuery(".step_2_nav").click(function(){
    step_1(step_2);
});

这是fiddle

这有点像不同步动画,你可以在step1完成后调用你的step2,意思是把它放在你第一步的回调函数里。
我设置 setTimeout 是因为您似乎使用了额外的转换,这会使您的 step1 调用时间更长。

    function step_1(child) {
        jQuery(".step_1_nav").addClass('active_bullet_point');
        jQuery(".step_1 .label").addClass('active_label_text');

        var delay = 0;
        jQuery('.step_1 .arrows span').each(function(index) {
            var $this = $(this);
            var total = $('.step_1 .arrows span').length;
            $this.animate({
                opacity: 1
            }, delay, function() {
                $this.addClass('white_animated_arrow');
                if (index === (total - 1)) {
                    jQuery(".step_1 .bullet_point").addClass('active_bullet_point');
                    if(child) setTimeout(()=> step_2(), 300);
                }
            });
            delay += 100;
        });
    }

    function step_2() {
        // if (flag == 1) {
            jQuery(".step_2_nav").addClass('active_bullet_point');
            jQuery(".step_2 .label").addClass('active_label_text');

            var delay = 0;
            jQuery('.step_2 .arrows span').each(function(index) {
                var $this = $(this);
                var total = $('.step_2 .arrows span').length;
                $this.delay(delay).animate({
                    opacity: 1
                }, 100, function() {
                    $this.addClass('white_animated_arrow');
                    if (index === (total - 1)) {
                        jQuery(".step_2 .bullet_point").addClass('active_bullet_point');
                    }
                });
                delay += 100;
            });
        // }
    }

    jQuery(".step_1_nav").click(function() {
        step_1();
    });

    jQuery(".step_2_nav").click(function() {
        step_1(true);
    });
.step {
        margin-right: 30px;
        display: inline-block;
        vertical-align: top;
        text-align: center;
        margin-top: 20px;
        margin-left: 20px;
    }
    
    .arrows {
        width: 10px;
        display: inline-block;
        vertical-align: top;
    }
    
    .arrows_up {}
    
    .arrows span {
        border: solid #000;
        border-width: 0 2px 2px 0;
        display: block;
        padding: 4px;
        margin-bottom: 4px;
        width: 0;
        height: 0;
        -webkit-transition: border-color 0.4s;
        -moz-transition: border-color 0.4s;
        transition: border-color 0.4s;
    }
    
    .arrows_down span {
        transform: rotate(135deg);
        -webkit-transform: rotate(45deg);
        -moz-transform: rotate(45deg);
        -ms-transform: rotate(45deg);
    }
    
    .arrows_up span {
        transform: rotate(-135deg);
        -webkit-transform: rotate(-135deg);
        -moz-transform: rotate(-135deg);
        -ms-transform: rotate(-135deg);
    }
    
    .label {
        color: #000;
        margin-bottom: 10px;
        font-weight: bold;
        display: block;
        font-family: 'Arial';
    }
    
    .bullet_point span {
        font-family: 'Arial';
        width: 12px;
        height: 12px;
        border-radius: 50%;
        background: #000;
        display: inline-block;
        vertical-align: middle;
        -webkit-transition: all 0.4s;
        -moz-transition: all 0.4s;
        transition: all 0.4s;
    }
    
    .step_2 .bullet_point {
        margin-bottom: 15px;
    }
    
    .step_2 .label {
        margin-top: 5px;
    }
    
    .active_label_text {
        color: red;
    }
    
    span.white_animated_arrow {
        border-color: red;
    }
    
    .timer_nav {
        margin-top: 20px;
        margin-left: 0px;
    }
    
    .timer_nav span.timeline {
        color: #000 !important;
        cursor: text;
    }
    
    .timer_nav span {
        color: #000;
        font-size: 20px;
        cursor: pointer;
        font-family: 'Arial';
        font-weight: bold;
        margin: 0px 10px;
        -webkit-transition: all 0.4s;
        -moz-transition: all 0.4s;
        transition: all 0.4s;
    }
    
    .timer_nav span:hover {
        color: red;
    }
    
    .active_bullet_point {
        color: red;
    }
    
    .timer_nav span.active_bullet_point {
        color: red;
    }
    
    .active_bullet_point span {
        background: red;
    }
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="step step_1">
        <span class="label">STEP 1</span>
        <div class="arrows arrows_down">
            <span></span>
            <span></span>
            <span></span>
            <span></span>
        </div>
        <div class="bullet_point"><span></span></div>
    </div>
    <div class="step step_2">
        <div class="bullet_point"><span></span></div>
        <div class="arrows arrows_up">
            <span></span>
            <span></span>
            <span></span>
            <span></span>
        </div>
        <span class="label">STEP 2</span>
    </div>
    <div class="timer_nav">
        <span class="timeline">Timeline</span>
        <span class="step_1_nav">1</span>
        <span class="step_2_nav">2</span>
    </div>
    </div>

我使用 setInterval()

JS FIDDLE DEMO

var counter_step1 = 0;
var counter_step2 = 0;
var step1Completed = false;
var timeDelay = 400; // set delay time accordingly

function step1() {

  $(".step_1 .label").addClass("active_label_text");
  var arrowCount = $(".arrows_down span").size();
  var myFisrt = setInterval(function() {
    if (counter_step1 < arrowCount) {
      counter_step1++
      $(".arrows_down span:nth-child(" + counter_step1 + ")").addClass("white_animated_arrow");
    } else {
      $(".step_1 .bullet_point").addClass("active_bullet_point");
      step1Completed = true;
      clearInterval(myFisrt);
    }
  }, timeDelay);
}


function step2() {
  var arrowCount = $(".arrows_up span").size();
  var mySecond = setInterval(function() {
    if (step1Completed) {
      $(".step_2 .label").addClass("active_label_text");
      if (arrowCount > counter_step2) {
        $(".arrows_up span:nth-child(" + arrowCount + ")").addClass("white_animated_arrow");
        arrowCount--
      } else {
        $(".step_2 .bullet_point").addClass("active_bullet_point");
        clearInterval(mySecond);
      }
    }
  }, timeDelay);
}

function setAnimation(myVALUE) {
  step1();
  if (myVALUE == "STEP2") { step2();  }
}

$(".step_1_nav").on('click', function() {
  setAnimation("STEP1");
});

$(".step_2_nav").on('click', function() {
  setAnimation("STEP2");
});

我已经完成了下面的工作,但不是解决问题的正确方法。

这是因为 JS 在 step_1() 结束之前不会停止。它不是在等待 step_1() 中的 'delay' 循环并调用 step_2()。如果你把 alert() 放在两个函数中你就会知道。

jQuery(".step_2_nav").click(function(){`enter code here`
      step_1();
      flag=1;
      step_2();
})

你也可以尝试使用 https://api.jquery.com/category/deferred-object/

希望对你有所帮助