7

我正在显示关于给定结束时间的倒计时手表。

虽然它的工作完美,但我想知道哪个是最好的应用方法。

下面是我的倒计时功能。

  var timerId;
  var postData = {endDate : endDate, tz : tz};  
  var countdown = function()
    { 
      $.ajax({
               type : 'post',
               async : false,
               timeout : 1000,
               url : './ajax_countdown.php',
               data : $.param(postData),
               dataType : 'json',
               success : function (resp){
                  $('#currentTime').html(resp.remainingTime);
               }
            }); 
     }

我想要的是该函数(倒计时)应该在每 1 秒后自动调用一次,如果它没有在 1 秒内执行/完成,则取消当前的 ajax 并开始一个新的 ajax 调用。

现在我发现有4种工作方法

方法 1:将setInterval() 与窗口对象一起使用

window.setInterval(countdown, 1000);

方法 2:独立使用setInterval()

setInterval(function() {countdown()}, 1000);

方法3:在函数内部使用setTimeOut调用其他函数来初始化主函数

var countdown = function() { 
     $.ajax({ //ajax code });
     timerId = setTimeout(countdown, 5000); // assign to a variable
 }

function clockStart() {  
        if (timerId) return
        countdown();
}
clockStart(); // calling this function 

方法4:使用匿名函数调用

var countdown = function() { 
     $.ajax({ //ajax code });
     timerId = setTimeout(countdown, 5000);
 }
  (function(){
         if (timerId) return;
         countdown();
})();

请告诉我

  • 每种方法的优缺点是什么,哪一种是最好/正确的方法?
  • 我应该使用clearTimeOut()orclearInterval()吗?

参考

http://javascript.info/tutorial/settimeout-setinterval

每 60 秒调用一次函数

http://www.electrictoolbox.com/using-settimeout-javascript/

4

3 回答 3

8

我不会使用你的任何方法。原因是setTimeout并且setInterval 不保证您的代码将在指定的延迟后执行。这是因为 JavaScript 是单线程的。

如果我需要在指定的延迟后只调用一次函数,那么我使用setTimeout. 但是,如果我需要在固定的时间间隔后调用函数,那么我不使用setInterval. 相反,我使用delta timing。这是代码

使用增量计时的优点是您的代码将更接近您指定的固定时间间隔执行。它会自我纠正。创建和使用增量计时器很简单。例如,您的代码将编写如下:

var timer = new DeltaTimer(function (time) {
    $.ajax({
        // properties
    });

    if (time - start >= 5000) timer.stop();
}, 1000);

var start = timer.start();

上面的delta timer优于setInterval(方法1),利用了setTimeout(方法2)但也能自我修正,使用函数启动定时器(方法3),并且不使用特殊clockStart函数污染作用域(方法4) .

此外,您可以轻松获得在计时器启动后调用函数的确切时间,因为调用函数的时间作为参数传递给函数。定时器也有一个stop停止定时器的方法。要再次启动它再次调用start

编辑:

如果你想让它DeltaTimer看起来更像setInterval(自动启动计时器),你可以实现一个 spawn 函数,如下所示:

DeltaTimer.spawn = function (render, interval) {
    var timer = new DeltaTimer(render, interval);

    var start = timer.start = function (start) {
        return function () {
            render.start = start();
        };
    }(timer.start);

    start();

    return timer;
};

然后您可以自动创建并启动DeltaTimer如下:

var timer = DeltaTimer.spawn(function countdown(time) {
    $.ajax({
        // properties
    });

    if (time - countdown.start >= 5000) timer.stop();
}, 1000);

因此var timer = DeltaTimer.spawn(funct, delay);等价于var interval = setInterval(funct, delay);timer.stop();等价于clearInterval(interval);。我想这就是你可以自动化的程度。

于 2012-07-17T11:18:41.923 回答
6

使用 #1 而不是 #2 的好处是window引用消除了范围变量覆盖的机会setInterval

// When out of global scope...
function setInterval() {

}

window.setInterval(foo, 100); // still calls the "correct" setInterval

countdown将调用包装在函数中(#1、#2)没有区别。#2 为您提供了更大的灵活性,因为您还可以调用其他函数/传递参数等(尽管如果出现这种情况,从 #1 交换到 #2 显然是微不足道的)。

#4 省去了你必须声明一个函数clockStart,除此之外,它与 #3 相同。

clearTimeout如果您使用过,请使用setTimeoutclearInterval如果您使用过setInterval...

您还应该了解如何以不同setTimeout的方式setInterval工作。这里有一个惊人的答案,它解释了......

至于我会用什么?我会使用#2。

于 2012-07-17T10:51:59.353 回答
-1

如果您正在创建倒计时,那么为什么您不使用 jquery 插件并根据您的要求对其进行自定义?在这里结帐

http://www.tripwiremagazine.com/2012/05/jquery-countdown-scripts.html

于 2012-07-17T11:09:01.710 回答