FullCalendarライブラリで日付の移動をするときに、2/31や4/31などカレンダー上存在しない日付であるかチェックをする関数をどうやって実装するか調べました。
参考:
■背景
・カレンダーの操作は、年・月・日がそれぞれ独立して操作できる状態。
・1/31の状態から月を1月進めて2/31へ移動したりすると、カレンダーの表示が3月になったりした。
・カレンダーのプログラムへ引数(年・月・日)を渡す前に、その値がカレンダーとして妥当性があるか判別をしたい。
■関数サンプル
// 引数は、年・月・日の3つ
// 戻り値は、true:カレンダー日付として存在、false:カレンダー日付として存在しない
const isValidDate = (year: string | number, month: string | number, day: string | number) => {
let result = false
const checkDate = new Date(year + '/' + ('0' + month).slice(-2) + '/' + ('0' + day).slice(-2))
// カレンダーの日付として妥当であるか確認
if (('0' + (checkDate.getMonth() + 1).toString()).slice(-2) == ('0' + month).slice(-2)){
result = true
} else {
result = false
}
return result
}
Dateオブジェクトを生成した場合、カレンダーに存在しないデータとならないことを利用しています。
例えば、Date('2023/02/29')で生成した場合、2月に29日が存在しないため、Dateオブジェクトとしては、3月1日(Wed Mar 01 2023 00:00:00 GMT+0900 (日本標準時))のデータとなります。
引数で渡した月の値とDateオブジェクトの月データが異なっていればカレンダーに存在しない月として判定しています。
■改善点
Dateオブジェクトを生成するときに「new Date('1/01/41')」とすると、2041/1/1(Tue Jan 01 2041 00:00:00 GMT+0900 (日本標準時))で生成されます。
1年1月41日と解釈すると、カレンダーの日付として存在しないため、関数の結果としては正しくありません。
それぞれの引数を正規表現で判定する方法も別途試してみたいと思いました。