Javascript倒数计时器 - 客户端时间与mySQL时间

时间:2015-03-11 22:30:26

标签: javascript mysql

以下代码是倒数计时器。它从mySQL中提取结束日期时间戳并使用它来计算。问题是mysql时间可能与使用计时器查看页面的客户端位于不同的时区。

我还使用NOW()从mySQL中提取当前时间戳,认为这将允许计时器计算为创建它的用户。

如果我将NOW()值放在此代码段

var timeDiff = target - (new Date()); 

喜欢这样

var nt='2015-03-11 05:12:15'.split(/[- :]/);
var timeDiff = target - (new Date(nt[0],nt[1]-1,nt[2],nt[3],nt[4],nt[5]));

计数器显示页面加载时剩余的正确时间,但不再以交互方式计算。我想我需要在客户端本地时间和mySQL NOW()之间获得数小时的差异,并调整此行中的日期以使交互式计时器运行。

var timeDiff = target - (new Date());  

我尝试的任何东西似乎都无法运作。

如果客户端碰巧在同一时区内,则这是工作脚本。

 <script language="javaScript">              
  document.write(hrs);
  function timeDiff(target) {
    function z(n) {return (n<10? '0' : '') + n;}
    var timeDiff = target - (new Date()); 
    var hours    = timeDiff / 3.6e6 | 0;
    var minutes  = timeDiff % 3.6e6 / 6e4 | 0;
    var seconds  = timeDiff % 6e4 / 1e3 | 0;
    if (hours<0 || minutes<0 || seconds<0) {
      document.getElementById('divBody').style.display='none';
      document.getElementById('divExpired').style.display='';    
      return '<b>EXPIRED</b>';
      }
    else {
      return '<b>' + z(hours) + '</b> Hours, <b>' + z(minutes) + '</b>  Mins, <b>' + z(seconds) + '</b> Secs';
      }
    }
  function doCountDown(target) {
    document.getElementById('timer').innerHTML = '<img src=\"/backhaul/images/my/al-active.png\" class=\"vm2\" /> <span style=\"color:#c40000\"><b>EXPIRES IN</b></span>: ' + timeDiff(target);
    var lag = 1020 - (new Date() % 100);
    setTimeout(function(){doCountDown(target);}, lag);
    }
  window.onload = function() {
    //Insert Expiratin Date from mySQL into t var
    var t='2015-03-12 00:00:00'.split(/[- :]/);
    doCountDown(new Date(t[0],t[1]-1,t[2],t[3],t[4],t[5]));
  }
</script>

2 个答案:

答案 0 :(得分:6)

有很多方法可以做到这一点,但我会详细说明两种方式。

方法1:调整客户端的时间

您尝试做的一种方法是获取服务器的当前时间并找出与客户当前时间的差异。您只需将服务器目标时间调整到客户端即可。这可以通过

完成
var serverDifference=Date.parse(mysql_data.now)-Date.now()
var target=Date.parse(mysql_data.server_time_in_two_hours)-serverDifference

然后你可以毫无问题地将它输入你的功能。

方法2:计算剩余的时间,服务器端

由于您只需要一个倒数计时器,我认为仅发送秒左侧服务器端更合适。这可以使用SQL

完成
 select timestampdiff(SECOND,now(),end_time) seconds_left from timers;

然后你只需制作一个根据剩余秒数而不是目标日期倒计时的计时器。您可以通过从服务器收到的时间减去javascript运行的时间来计算剩余的秒数。像

这样的东西
var client_start=Date.now()
function timeDiff_fromseconds(target) {
    function z(n) {return (n<10? '0' : '') + n;}
    var timeDiff =target-(Date.now()-client_start)
    var hours    = timeDiff / 3.6e6 | 0;
    var minutes  = timeDiff % 3.6e6 / 6e4 | 0;
    var seconds  = timeDiff % 6e4 / 1e3 | 0;
    if (hours<0 || minutes<0 || seconds<0) {   
      return '<b>EXPIRED</b>';
      }
    else {
      return '<b>' + z(hours) + '</b> Hours, <b>' + z(minutes) + '</b>  Mins, <b>' + z(seconds) + '</b> Secs';
      }
}

performance.now()建议@dandavis。这将返回自打开选项卡以来的毫秒数,精确到1/1000毫秒。即使客户端浏览器的系统时钟发生变化,这也不会改变。要获得完全支持,您应该使用polyfillAs of the time of this writing, iOS Safari doesn't support it)。在这种情况下,我们可以用它替换Date.now()

JSFiddle演示:

http://jsfiddle.net/3o3u5r5j/1/

答案 1 :(得分:0)

如果可以从数据库获得剩余的秒数而不是到期时间(意味着在服务器上计算它并发送到客户端)。然后您可以使用以下代码(示例)。 Fiddle

var countDownId;
var timer;
function countDown(){
    console.log(timer--);
    if(timer<=0){
        clearInterval(countDownId);
        alert('time expired');
    }
}

function startCountDown(secondsToExpire){
    var milliseconds = 1 * 1000 ;// 1 second
    timer = secondsToExpire;

    countDownId = setInterval(function() { countDown();},milliseconds);
}

  window.onload = function() {
    //Insert remaining time from expiration
    var timeRemaining = 5;
    startCountDown(timeRemaining);
  }

您可以调整它以满足您的需求。