DurationFormatで期間をlocaleに基づいて表現する
Intl.DurationFormatはlocaleに応じた形式で期間を表現するIntlの新機能で、Baseline 2025で利用可能です。formatメソッドで文字列として期間を取得でき、formatToPartsメソッドでは各部分をオブジェクトの配列として取得できます。言語による期間の表現の違いを標準に従って簡単扱いましょう。
はじめに
Firefox 136.0のリリースでIntl
のDurationFormat
が2025年のBaselineに追加されました。
Intl.DurationFormat
はlocale
に基づいた書式設定で期間を表現するものです。
const duration = {
years: 1,
months: 2,
weeks: 3,
days: 3,
hours: 4,
minutes: 5,
seconds: 6,
};
new Intl.DurationFormat('ja').format(duration);
// 1 年 2 か月 3 週間 3 日 4 時間 5 分 6 秒
GitHub - tc39/proposal-intl-duration-format
Contribute to tc39/proposal-intl-duration-format development by creating an account on GitHub.
github.com
Intl.DurationFormat
Intl.DurationFormat
はlocale
に応じた書式の期間を表示するためのオブジェクトです。
他のIntl
オブジェクトと同じように静的メソッドとしてsupportedLocalesOf()
やインスタンスメソッドresolvedOptions()
を持っています。
locale
に応じた期間の出力はIntlDurationFormat
オブジェクトを作成して、format
及びにformatToParts
メソッドで行います。
locale
や書式設定はIntl.DurationFormat
オブジェクトを作成するタイミングで設定します。
new Intl.DurationFormat('ja-JP', {
style: 'long',
});
第一引数にlocale
を文字列や配列で渡し、第二引数でその他のオプションをオブジェクト形式で渡します。
オプションの全ては説明しませんが、style
で表示する期間の長さ、years
・months
等で個別のstyle
を決定、yearsDisplay
・monthsDisplay
などで0の時の表示を決めます。
style
にはlong
とshort
とnarrow
とdigital
の4つがあります。locale
がja
の場合、以下のような表示になります。
// long 1 年 2 か月 3 週間 3 日 4 時間 5 分 6 秒 7 ミリ秒 8 マイクロ秒 9 ナノ秒
// short 1 年 2 か月 3 週間 3 日 4 時間 5 分 6 秒 7 ms 8 μs 9 ns
// narrow 1y2m3w3d4h5m6s7ms8μs9ns
// digital 1 年 2 か月 3 週間 3 日 4:05:06.007008009
format
作成したIntl.DurationFormat
オブジェクトに対してformat
メソッドを呼び出すことで期間を表示します。
format
は対応している期間をオブジェクト形式で受け取ります。
const duration = {
years: 1,
months: 2,
hours: 4,
seconds: 6,
};
new Intl.DurationFormat('ja').format(duration);
// 1 年 2 か月 4 時間 6 秒
全ての期間を含める必要はありません。
言い忘れましたが、期間はyears
、months
、weeks
、days
、hours
、minutes
、seconds
、milliseconds
、microseconds
、nanoseconds
の9つに対応しています。これらをformat
に渡すオブジェクトのキーとして利用できます。
formatToParts
formatToParts
メソッドはformat
メソッドと同じように期間を表示しますが、format
メソッドが文字列を返すのに対して、formatToParts
メソッドはオブジェクトの配列を返します。
const duration = {
years: 1,
months: 2,
hours: 4,
seconds: 6,
};
new Intl.DurationFormat('ja').formatToParts(duration);
// [
// {
// "type": "integer",
// "value": "1",
// "unit": "year"
// },
// {
// "type": "literal",
// "value": " ",
// "unit": "year"
// },
// {
// "type": "unit",
// "value": "年",
// "unit": "year"
// },
// {
// "type": "literal",
// "value": " "
// },
// {
// "type": "integer",
// "value": "2",
// "unit": "month"
// },
// {
// "type": "literal",
// "value": " ",
// "unit": "month"
// },
// {
// "type": "unit",
// "value": "か月",
// "unit": "month"
// },
// {
// "type": "literal",
// "value": " "
// },
// {
// "type": "integer",
// "value": "4",
// "unit": "hour"
// },
// {
// "type": "literal",
// "value": " ",
// "unit": "hour"
// },
// {
// "type": "unit",
// "value": "時間",
// "unit": "hour"
// },
// {
// "type": "literal",
// "value": " "
// },
// {
// "type": "integer",
// "value": "6",
// "unit": "second"
// },
// {
// "type": "literal",
// "value": " ",
// "unit": "second"
// },
// {
// "type": "unit",
// "value": "秒",
// "unit": "second"
// }
// ]
期間を元に自分なりの表示を作成する場合はこちらが便利です。
日本語でformat
した場合スペースが気になるので、こちらを利用した方が見栄えが良いかもしれません。