.fadeIn .fadeOut 会导致数组索引出现奇怪的行为

.fadeIn .fadeOut causes strange behaviour with array index

本文关键字:索引 fadeOut 数组 fadeIn      更新时间:2023-09-26

我有以下代码在特定索引处显示数组中的字符串。每次调用函数时,索引都会递增,并显示一个新字符串:

var questions = ["What is your name?","What is your favourite colour?","What is the air speed velocity of an unladen swallow?"];
var currentQuestionIndex = 0;
function showQuestion() {
    
    if (currentQuestionIndex <= questions.length-1) {
        
        var question = $('#question');
            console.log(questions[currentQuestionIndex]);
            question.text(questions[currentQuestionIndex]);
        
        currentQuestionIndex = currentQuestionIndex+1;
        questionTimer();
    } else {
        console.log("End question 1");
    }
}
function questionTimer() {
    setTimeout(function () {
        showQuestion();
    }, 3000);
}
showQuestion();
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="question"></div>

这工作正常,但是一旦我尝试在问题div中淡出/淡入淡出,代码就不再正常工作,并且显示索引1处的字符串而不是0。谁能解释为什么?

非工作版本:

var questions = ["What is your name?","What is your favourite colour?","What is the air speed velocity of an unladen swallow?"];
var currentQuestionIndex = 0;
function showQuestion() {
    
    if (currentQuestionIndex <= questions.length-1) {
        
        var question = $('#question');
        question.fadeOut(400, function () {
            question.text(questions[currentQuestionIndex]);
            question.fadeIn(400);
        });
        
        currentQuestionIndex = currentQuestionIndex+1;
        questionTimer();
    } else {
        console.log("End question 1");
    }
}
function questionTimer() {
    setTimeout(function () {
        showQuestion();
    }, 3000);
}
showQuestion();
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="question"></div>

当文本尚未淡出时,您正在执行 +1。要解决这个问题,请将所有内容都移到fadeOut()回调中:

var questions = ["Question 1","Question 2","Question 3","Question 4"];
var currentQuestionIndex = 0;
function showQuestion() {
    
    if (currentQuestionIndex <= questions.length-1) {
        
        var question = $('#question');
        question.fadeOut(400, function () {
            question.text(questions[currentQuestionIndex]);
            question.fadeIn(400);
            currentQuestionIndex = currentQuestionIndex+1;
            questionTimer();
        });
    } else {
        console.log("End question 1");
    }
}
function questionTimer() {
    setTimeout(function () {
        showQuestion();
    }, 3000);
}
showQuestion();
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="question"></div>

这是因为动画是异步的。增加变量的代码将在设置文本的代码之前运行。

改为在设置文本的代码中增加变量:

var question = $('#question');
question.fadeOut(400, function () {
    question.text(questions[currentQuestionIndex]);
    currentQuestionIndex = currentQuestionIndex+1;
    question.fadeIn(400);
});

演示:

    var questions = ["What is your name?","What is your favourite colour?","What is the air speed velocity of an unladen swallow?"];
    var currentQuestionIndex = 0;
    function showQuestion() {
        
        if (currentQuestionIndex <= questions.length-1) {
            
            var question = $('#question');
            question.fadeOut(400, function () {
                question.text(questions[currentQuestionIndex]);
                currentQuestionIndex = currentQuestionIndex+1;
                question.fadeIn(400);
            });
            questionTimer();
        } else {
            console.log("End question 1");
        }
    }
    function questionTimer() {
        setTimeout(function () {
            showQuestion();
        }, 3000);
    }
    showQuestion();
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
    <div id="question"></div>

问题是你假设线程将停止执行并等到效果完成再继续下一句。这是不正确的。效果是异步运行的,因此当它淡入时,您正在增加计数器,因此当它准备好淡出时,计数器已经增加了 1。

就像您等到淡出完成淡入才能执行淡入

一样,您必须等到淡入完成才能增加计数器的值。

轻松修复

var questions = ["Question 1","Question 2","Question 3","Question 4"];
var currentQuestionIndex = 0;
function showQuestion() {
    
    if (currentQuestionIndex <= questions.length-1) {
        
        var question = $('#question');
        question.fadeOut(400, function () {
            question.text(questions[currentQuestionIndex]);
            question.fadeIn(400,  function() {
              currentQuestionIndex = currentQuestionIndex+1;                       
              questionTimer();});
        });
       //move these two inside the callback for fadeIn
       //currentQuestionIndex = currentQuestionIndex+1;                       
       //questionTimer();
    } else {
        console.log("End question 1");
    }
}
function questionTimer() {
    setTimeout(function () {
        showQuestion();
    }, 3000);
}
showQuestion();
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="question"></div>