将两个客户端JavaScript计时器与服务器同步

时间:2013-03-05 19:34:32

标签: php javascript jquery mysql ajax

我有两个JavaScript倒计时器(用于游戏),以及一个MySQL表,用于从任何一个AJAX调用接收数据。

该过程如下:

  1. 客户端启动计时器,将其写入data1 MySQL列 它启动了计时器,并带有当前的time1列 时间戳(精度为.01s,来自PHP调用,因为MySQL没有 那样做)

  2. 另一个客户端(以2秒的间隔轮询服务器)检测到更改并启动计时器,但会立即减去(它是倒数计时器)ctime - time1其中ctime是时间戳第二个客户端调用(也由PHP提供)和time1是第一个客户端在启动计时器时写入的时间戳。

  3. 这种方法应该消除由轮询的2s间隔引起的延迟,但不管它是否存在(我真的不确定),定时器之间的同步会有所不同。有时它们确实是死的,有时它们最多可以消失3秒钟。 (这是不可靠的。)

    以下是我正在使用的一些相关代码:

    var timerRunning, timeRemaining, responseTime;
    
    function restartLocalTimer() {
        var d = new Date();
        responseTime = d.getTime()/1000;
        timerRunning = true;
        timerTick();
    }
    
    function restartSyncTimer(resp) { // resp is the AJAX response passed
        var d = new Date();
        responseTime = d.getTime()/1000 - parseFloat(resp["ctime"]) + parseFloat(resp["time"]);
        timerRunning = true;
        timerTick();
    }
    
    function timerTick() {
        d = new Date();
        timeRemaining = 20 - d.getTime()/1000 + responseTime;
        if (timerRunning) setTimeout("timerTick()",25);
    }
    

    所有时间值都以秒为单位。 (由于数据库,以后可能会更改为ms。)

    我的问题是:是否还有其他(重大)延迟我没有考虑到?有没有更好的方法呢?

    另请注意:我对jQuery开放(使用它已经用于AJAX调用),但不想使用websockets。

2 个答案:

答案 0 :(得分:1)

我会采用与桌面网络多人游戏相同的方法。即使在连接中断的短暂时刻(例如“滞后”),客户端也会在该时间内投射预期的轨迹。在这种情况下,您依赖于本地间隔,并在获得异步心跳响应时使用确切的服务器时间进行更新。

答案 1 :(得分:-1)

已知

setTimeout及其兄弟不可靠。还有另外一篇文章:Is there a more accurate way to create a Javascript timer than setTimeout?给出了一些指示。