如何在moment.js持续时间上使用format()函数?

271

我是否能够在持续时间对象上使用 moment.jsformat 方法?我在文档中没有找到它的任何信息,并且似乎也不是持续时间对象的属性。

我想要做这样的事情:

var diff = moment(end).unix() - moment(start).unix();
moment.duration(diff).format('hh:mm:ss')

另外,如果有其他能够轻松实现此类功能的库,我会对推荐很感兴趣。

谢谢!


9
moment.utc(duration.asMilliseconds()).format('hh:mm:ss'); “duration”是一个向量。将其尾部放在原点上,您可以使用日期格式化来得到“hh:mm:ss”。 - Paul Williams
1
moment.utc(moment.duration(23, 'seconds').asMilliseconds()).format('hh:mm:ss') => "12:00:23" 不太好用 - goldenratio
2
啊,我找到问题了,在我的先前示例中,HH:mm:ss会给出00:00:23。所以只是小时部分的大小写错误。 - goldenratio
1
对于那些想以可读的方式显示持续时间的人,请使用:moment.duration(diff_ms).humanize(); - Rafe
31个回答

5
如果diff是一个瞬间
var diff = moment(20111031) - moment(20111010);
var formated1 = moment(diff).format("hh:mm:ss");
console.log("format 1: "+formated1);

在考虑到时区等因素的情况下,这似乎不太可靠。你在生产中使用它吗? - Keith
问题没有提到时区。 - Kieran
3
每个人都生活在一个时区。在每个时区中,零点时刻(moment(0))是否总是显示为凌晨12点? - Keith
我只是想问一下你回答中的代码是否有效,因为我持怀疑态度。我已经写了很多处理日期的代码,使用了许多编程语言。根据我的经验,你的代码似乎只能在某些时区中运行 - 但我还是要问一下,因为也许有关于Javascript如何表示Unix纪元附近的日期的知识我不知道。 - Keith
1
第二行代码将从时间起点(1970年)创建一个时刻。这样做是不正确的。 - kumarharsh
正如@Harsh所指出的那样,moment()构造函数需要一个Unix时间戳,因此无论您传递什么参数,它都将被假定为距离1970年1月1日的特定时间间隔。 - ken

5

如果需要显示超过24小时的所有时间,并且不需要在小时前添加‘0’,则可以使用一行简短的代码进行格式化:

Math.floor(duration.as('h')) + moment.utc(duration.as('ms')).format(':mm:ss')

这是最好的h:mm答案,但我认为最好的显示方式只是 moment.duration(val,'seconds').humanize() - user1944491
1
对于我的使用情况来说,仅显示所有带有 mmss 的小时是最好的方式,因为它紧凑且类似于逗号分隔值,因此非常适合进行视觉比较。 - o.v

5

简短版本(一行版):

moment.duration(durationInMs).asHours()|0||"00" + ":" + moment.utc(durationInMs).format("mm:ss")

扩展版本:

export const formatDuration = (durationInMs) => {
    const hours = Math.floor(moment.duration(durationInMs).asHours()) || "00"
    return hours + ":" + moment.utc(durationInMs).format("mm:ss")
}

示例案例:

Example cases


5
如果你愿意使用不同的javascript库,numeral.js可以将秒数格式化为以下形式(以下为1000秒的示例):
var string = numeral(1000).format('00:00');
// '00:16:40'

肯定是正确的方法。正如预期的那样。 - Piotr Kula

5

基于ni-ko-o-kin的回答

meassurements = ["years", "months", "weeks", "days", "hours", "minutes", "seconds"];
withPadding = (duration) => {
    var step = null;
    return meassurements.map((m) => duration[m]()).filter((n,i,a) => {
        var nonEmpty = Boolean(n);
        if (nonEmpty || step || i >= a.length - 2) {
            step = true;
        }
        return step;
    }).map((n) => ('0' + n).slice(-2)).join(':')
}

duration1 = moment.duration(1, 'seconds');
duration2 = moment.duration(7200, 'seconds');
duration3 = moment.duration(604800, 'seconds');

withPadding(duration1); // 00:01
withPadding(duration2); // 02:00:00
withPadding(duration3); // 01:07:00:00:00

我认为这不太易读。你想解决什么问题?你的用例是什么? - ni-ko-o-kin
我再次更新了我的答案,以处理超过一天的情况。对于我的使用情况,它运行良好。 - ni-ko-o-kin
2
问题在于,在大多数情况下,您的解决方案并不理想,因为它包含太多前导零。谁想要返回“00:00:00:00:01”呢?我的解决方案是“可扩展的”,只添加所需数量的前导零。 - shaedrich
完美运行。非常简单的输出。如果没有天数,将不会显示任何零天等。 - Hasan Sefa Ozalp

4

在这些情况下,我使用经典的格式化函数:

var diff = moment(end).unix() - moment(start).unix();

//use unix function instead of difference
moment.unix(diff).format('hh:mm:ss')

这是一个技巧,因为时间差被处理为标准的日期时间,早期的纪元日期时间,但这对我们的目标并不重要,也不需要任何插件。

3

将moment持续时间格式化为字符串

var duration = moment.duration(86400000); //value in milliseconds
var hours = duration.hours();
var minutes = duration.minutes();
var seconds = duration.seconds();
var milliseconds = duration.milliseconds();

var date = moment().hours(hours).minutes(minutes).seconds(seconds).millisecond(milliseconds);
if (is12hr){
    return date.format("hh:mm:ss a");
}else{
    return date.format("HH:mm:ss");
}

3

如何正确使用moment.js时间间隔(durations)? | 在代码中使用moment.duration()

首先,您需要导入momentmoment-duration-format

import moment from 'moment';
import 'moment-duration-format';

接下来,使用时间长度函数。让我们运用上面的例子:28800 = 上午8点。

moment.duration(28800, "seconds").format("h:mm a");

好的,你没有上述类型错误。你得到了一个正确的值 8:00 am 吗?不是... 你得到的值是 8:00 a。Moment.js 格式化没有像预期的那样工作。

解决方案是将秒转换为毫秒并使用 UTC 时间。

moment.utc(moment.duration(value, 'seconds').asMilliseconds()).format('h:mm a')

现在是早上8点。如果您想使用“8”而不是“8:00 am”表示整点时间,我们需要使用正则表达式。

const time = moment.utc(moment.duration(value, 'seconds').asMilliseconds()).format('h:mm a');
time.replace(/:00/g, '')

3

我的解决方案不涉及任何其他库,而且它适用于时间差大于24小时的情况。

var momentInSeconds = moment.duration(n,'seconds')
console.log(("0" + Math.floor(momentInSeconds.asHours())).slice(-2) + ':' + ("0" + momentInSeconds.minutes()).slice(-2) + ':' + ("0" + momentInSeconds.seconds()).slice(-2))

3

如果您使用 Angular,请将以下内容添加到您的过滤器中:

.filter('durationFormat', function () {
    return function (value) {
        var days = Math.floor(value/86400000);
        value = value%86400000;
        var hours = Math.floor(value/3600000);
        value = value%3600000;
        var minutes = Math.floor(value/60000);
        value = value%60000;
        var seconds = Math.floor(value/1000);
        return (days? days + ' days ': '') + (hours? hours + ' hours ': '') + (minutes? minutes + ' minutes ': '') + (seconds? seconds + ' seconds ': '')
    }
})

使用示例

<div> {{diff | durationFormat}} </div>

非常好,确实如此。我正在寻找像这样的“漂亮格式”。谢谢! - riketscience

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接