如何在Moment.js中设置默认偏移量?

时间:2015-02-05 14:07:20

标签: javascript momentjs

我目前正在使用Moment.js来操纵日期和时间。

如果用户手动更改设备上的时间,我会尝试避免问题。

所以我得到服务器时间,用浏览器时间检查偏移量。

var offset = moment(browserTime).diff(moment(serverTime));

但我不想存储该偏移量,并且每当我创建一个新时刻时都必须应用它:

var foo = moment().add('milliseconds', offset);

那么有没有办法在Moment中设置该偏移量,以便每个新时刻都应用该偏移量?类似的东西:

moment.setOffset(offset);

var foo = moment();
var bar = moment(new Date()).add('milliseconds', offset);

if (foo.isSame(bar)) {
    // success
}

如果没有,将该功能添加到Moment.js可能是个好主意(请注意)。

感谢。

P.S。:我知道这个问题与Moment.js set the base time from the server密切相关,但提出的答案并没有解决我的问题。

1 个答案:

答案 0 :(得分:2)

我可能会这样做:

var offsetMoment = (function(){
    var globalOffset = moment.duration(); // Defaults to no offset
    var offsetMoments = []; // Stores all moments that have a global offset
    var throwIfNotOffsetMoment = function(moment){ // Regular moment objects can't use offset methods
        if(! moment.isOffsetMoment){
            throw "- Moment is not an offsetMoment.";
        }
    };

    // Sets an the globalOffset and applies it to all offsetMoments
    // Offset is not relative to the current offset, example:
    //     now.setGlobalOffset(1,'day') //tommorrow
    //     now.setGlobalOffset(-1,'day') //yesterday, not today
    // Same arguments accepted as moment.duration
    moment.fn.setGlobalOffset = function(){
        var offset = moment.duration.apply(this,arguments);
        throwIfNotOffsetMoment(this);
        for(i in offsetMoments){
            offsetMoments[i].subtract(globalOffset).add(offset); // Subtract the old offset and add the new one
        }
        globalOffset = offset;
        return this;
    }

    // Return a new moment object without the offset
    moment.fn.baseTime = function(){ 
        throwIfNotOffsetMoment(this);
        return this.clone().subtract(globalOffset);
    };

    // Return a factory function to offsetMoment that creates offset moments
    // Makes it work exactly like the momentjs's constructor
    return function(){
        offsetMoments.push(moment.apply(this,arguments));
        offsetMoments[offsetMoments.length-1].isOffsetMoment = true;
        offsetMoments[offsetMoments.length-1].add(globalOffset);
        return offsetMoments[offsetMoments.length-1];
    }
})();

// Usage
var offsetA = offsetMoment("2012-10-05");
offsetA.setGlobalOffset(5,'minutes'); // 2012-10-05 00:05
offsetA.baseTime(); // return new moment object = 2012-10-05 00:00

var offsetB = offsetMoment(moment()); // five minutes from now

JSFiddle 以及一些基本测试用例。

可以通过扩展原型来完成,但这种方法效果很好。

基本上,您将moment.js包裹在offsetMoment中并为其提供一些共享变量。然后扩展moment.fn,以便您可以轻松访问/操作共享变量。

它仅限于一个全局偏移(但常规时刻仍可在没有偏移的情况下工作)。

它根本不影响时刻的常规功能。 offsetMoment对象应与moment个对象配合使用。

应该很容易将其调整到准确的规格。