JavaScriptでもうすぐ何の日をつくってみる

らら
らら

はじめに

なんか案件で、「もうすぐ何の日」って日付がでて・・2025/2/1 もうすぐ節分の日ですとか・・って

感じらしい・・

聞いて・・・祝日じゃないのね・・・って思いつつ・・JavaScriptでテストしてみようと・・

プログラム?

JavaScriptで祝日は以前、ブログでも紹介した・・・japanese-holidays.min.jsでいいでしょ。。

https://github.com/osamutake/japanese-holidays-js

関連

Movabletype8で営業日カレンダーをつくる
https://www.omakase.net/blog/2024/05/movabletype8-calender.html

FullCalendarについて
https://www.omakase.net/blog/2023/03/fullcalendar.html

祝日と行事になるのか・・・?

祝日

japanese-holidays.min.jsでは下記が判定してくれる。


元日
成人の日
建国記念の日
春分の日
天皇誕生日
みどりの日
昭和の日
憲法記念日
みどりの日
こどもの日
海の日
山の日
敬老の日
秋分の日
体育の日
文化の日
勤労感謝の日

行事?

とりあえず、有名どこで・・

ありゃ。。母の日・父の日って・・面倒なのね・・・


節分の日	2/3
バレンタイン	2/14
ひなまつり	3/3
ホワイトデー	3/14
エイプリルフール	4/1
母の日	5月 第2週 日曜日
父の日	6月 第3週 日曜日
七夕	7/7
ハロウィン	10/31
七五三	11/15
クリスマスイブ	12/24
クリスマス	12/25

うーむ。。月・日をハードコーディングでいいやって思ってたけど・・・

面倒そう・・

あとは・・もうすぐって・・・どれぐらい?

ぐぐってもでてこん・・・まぁ10日ぐらいにするか・・

第XX週のX曜日って何日?を・・

まぁCとかでライブラリないころやってた下記で・・・

今どきは・・ライブラリがあったりで。どのアルゴリズムつかうなって考えなくていいよね・・

ツェラーの公式


year	年
mon	月
day	日

(year + year / 4 - year / 100 + year / 400 + (13 * mon + 8) / 5 + day) % 7
戻り値は下記・・ 曜日 0:日 1:月 2:火 3:水 4:木 5:金 6:土 JavaScriptで書くと・・ まぁ。getDay()でもいいけど・・

	function getDayOfWeek(year,mon,day)
	{
		if(mon == 1 || mon == 2) {
			year--;
			mon += 12;
		}
		return( Math.floor(year +  Math.floor(year/4) -  Math.floor(year/100) +  Math.floor(year/400) +  Math.floor((13*mon+8)/5) + day) % 7);
	}

第XX週のX曜日って何日?

year 年

month 月

num 第何週

w 曜日 0:日 1:月 2:火 3:水 4:木 5:金 6:土

戻りは何日


	function whatweekday(year,month,num,w)
	{
		var rescue = [5,4,3,2,1,0,6,5,4,3,2,1,0];
		var wday	= getDayOfWeek(year,month,1);
		return(num * 7 - rescue[(w - wday)+6]);
	}

祝日が優先されます・・


<!DOCTYPE html>
<html lang="ja">
<head>
	<meta charset="UTF-8">
	<title>もうすぐ何の日</title>
	<meta name="viewport" content="width=device-width,initial-scale=1,minimum-scale=1">
	<meta name="format-detection" content="telephone=no">
	<meta name="keywords" content=",,,,">
	<meta name="description" content="">
	<meta name="author" content="">
	<meta name="google-site-verification" content="">
<script src="https://code.jquery.com/jquery-3.5.1.min.js"></script>
<script src="https://cdn.rawgit.com/osamutake/japanese-holidays-js/v1.0.6/lib/japanese-holidays.min.js"></script>
<script>
$(function(){
	var now = new Date();
//	var now = new Date(2025, 1-1, 12);		デバック用
	var festival = [
		{
			'name': '節分の日',
			'date': '2/3',
		},
		{
			'name': 'バレンタイン',
			'date': '2/14',
		},
		{
			'name': 'ひなまつり',
			'date': '3/3',
		},
		{
			'name': 'ホワイトデー',
			'date': '3/14',
		},
		{
			'name': 'エイプリルフール',
			'date': '4/1',
		},
		{
			'name': '母の日',
			'date': '5/'+ whatweekday(now.getFullYear(),5,2,0),	//5月 第2週 日曜日
		},
		{
			'name': '父の日',
			'date': '6/'+ whatweekday(now.getFullYear(),6,3,0),	//6月 第3週 日曜日
		},
		{
			'name': '七夕',
			'date': '7/7',
		},
		{
			'name': 'ハロウィン',
			'date': '10/31',
		},
		{
			'name': '七五三',
			'date': '11/15',
		},
		{
			'name': 'クリスマスイブ',
			'date': '12/24',
		},
		{
			'name': 'クリスマス',
			'date': '12/25',
		},
	];
	var add_date = new Date();
	add_date.setDate(add_date.getDate() + 10);		//10日先を取得 もうすぐな日数を・・
	var save_date = new Date(add_date.getTime());
	var holiday
	var today_f = 0;
	for (var date = new Date(now.getTime());now <= save_date; date.setDate(date.getDate() + 1)) {
		holiday = JapaneseHolidays.isHoliday(date);
		if(holiday) {
			if(date.getMonth() == now.getMonth() &&  date.getDate() == now.getDate()) {
				today_f = 1;
			}
			break;
		}
		holiday = festival_chk(date);
		if(holiday) {
			if(date.getMonth() == now.getMonth() &&  date.getDate() == now.getDate()) {
				today_f = 1;
			}
			break;
		}
	}
	var today = new Date();
	var year = today.getFullYear();
	var month = today.getMonth() + 1;
	var day = today.getDate();
	view = year + '/' + month + '/' + day;
	if(holiday) {
		if(today_f == 0) {	
			$('#dateview').html(view+"<br>もうすぐ " + holiday + " です");
		} else {
			$('#dateview').html(view+"<br>今日は " + holiday + " です");
		}
	} else {
		$('#dateview').html(view+"<br>特になし");
	}
	function festival_chk(date)
	{
		var wmonth = date.getMonth() + 1;
		var wday = date.getDate();
		var cmpday = wmonth + "/" + wday;
		for (var i = 0; i < festival.length; i++) {
			if(festival[i]['date']  == cmpday) {
				return festival[i]['name'];
			}
		}
		return "";
	}
	// ex. whatweekday(西暦,月,週,曜日)	(曜日 0:日 1:月 2:火 3:水 4:木 5:金 6:土)
	//	何年,何月,の第何,何曜日が何日になるのか?
	//
	// Parameters
	//	$year	西暦
	//	$month	月
	//	$day	日
	//	$num	第何
	//	$w		何曜日	(曜日 0:日 1:月 2:火 3:水 4:木 5:金 6:土)
	// Returns
	//	何日
	// Memo
	function whatweekday(year,month,num,w)
	{
		var rescue = [5,4,3,2,1,0,6,5,4,3,2,1,0];
		var wday	= getDayOfWeek(year,month,1);
		return(num * 7 - rescue[(w - wday)+6]);
	}
	//	指定日の曜日を得る関数
	//
	// Parameters
	//	$year	西暦
	//	$mon	月
	//	$day	日
	// Returns
	//	  曜日 0:日 1:月 2:火 3:水 4:木 5:金 6:土
	// Memo
	//	ツェラーの公式より曜日を求める
	//	グレゴリウス暦(1582年10月15日(金)午後以後)で有効
	function getDayOfWeek(year,mon,day)
	{
		if(mon == 1 || mon == 2) {
			year--;
			mon += 12;
		}
		return( Math.floor(year +  Math.floor(year/4) -  Math.floor(year/100) +  Math.floor(year/400) +  Math.floor((13*mon+8)/5) + day) % 7);
	}
});
</script>
</head>
<body>
	<h1>日付</h1>
	<div id="dateview"></div>
</body>
</html>

さいごに・・

まぁ。。作ってて思ったけど・・いるのか・・これだけど・・

ECサイトとかの、記事かなんかと連動して、バレンタイン特集とか、記事書いて・・

その記事にリンクしないと意味なさそう・・・おい・・作っておいて・・

まぁMTとかで記事書いて、何の日にチェックしたものをJSで日付とURL吐き出せば。。

festival変数を下記に差し替えれば


2/14	バレンタイン	https://バレンタインの記事URL
3/14	ホワイトデー	https://ホワイトデーの記事URL

MTEntryFestivalTitleとかカスタムフィールドの名称です。

festival変数は、連想じゃないので上記ソースは直さないと・・だめです。


var  festival = [
<MTEntries lastn="0">
['<$MTEntryFestivalDate$>','<$MTEntryFestivalTitle$>','<$MTEntryPermalink encode_xml="1"$>'],
</MTEntries>
];

関連記事