【PHP】営業日カレンダー表示用PHPクラスを作ってみた

Contents

営業日カレンダー

営業日カレンダーを作ることになりそうだったのでサンプルを作ってみた。

まだまだ改善の余地はある。ってか動かなかったらごめんなさい。

ソースコード

Gistに上げました。

好きに使ってください(MITライセンス)。

動作するかどうかは保証しません、動作によって色んなことが起きても自己責任でどうぞ。


<?php
class business_calendar {
const WEEK = 7; // 1 week is 7 days
// holiday_of_week flag index
const IDX_SUNDAY = 0;
const IDX_MONDAY = 1;
const IDX_TUESDAY = 2;
const IDX_WEDNESDAY = 3;
const IDX_THURSDAY = 4;
const IDX_FRIDAY = 5;
const IDX_SATURDAY = 6;
protected $year = "";
protected $month = "";
protected $calendar = array();
protected $holiday_of_week = array();
protected $exception_holidays = array();
protected $exception_business_days = array();
function __construct($year, $month) {
$this->year = $year;
$this->month = $month;
$this->set_holiday_of_week();
$this->clear_exception_holidays();
$this->clear_exception_business_days();
}
function __destruct() {
}
/**
* 毎週の曜日休みを設定する
*/
public function set_holiday_of_week($sunday = false , $monday = false , $tuesday = false , $wednesday = false , $thursday = false , $friday = false , $saturday = false ) {
$holiday_of_week = array();
$holiday_of_week[self::IDX_SUNDAY] = $sunday;
$holiday_of_week[self::IDX_MONDAY] = $monday;
$holiday_of_week[self::IDX_TUESDAY] = $tuesday;
$holiday_of_week[self::IDX_WEDNESDAY] = $wednesday;
$holiday_of_week[self::IDX_THURSDAY] = $thursday;
$holiday_of_week[self::IDX_FRIDAY] = $friday;
$holiday_of_week[self::IDX_SATURDAY] = $saturday;
$this->holiday_of_week = $holiday_of_week;
}
/**
* 休日・稼働日の定義をクリアする
*/
protected function clear_days(&$array_target) {
$array_target = array();
}
public function clear_exception_holidays() {
$this->clear_days($this->exception_holidays);
}
public function clear_exception_business_days() {
$this->clear_days($this->exception_business_days);
}
/**
* 休日・稼働日の定義を追加する
*/
protected function add_day($year,$month,$day,&$array_target) {
$date = date('Ymd', mktime(0,0,0,$month,$day,$year));
if(!in_array($date,$array_target)) {
$array_target[] = $date;
}
}
public function add_exception_holiday($year,$month,$day) {
$this->add_day($year, $month, $day, $this->exception_holidays);
}
public function add_exception_business_day($year,$month,$day) {
$this->add_day($year, $month, $day, $this->exception_business_days);
}
/**
* 休日・稼働日の定義を削除する
*/
protected function remove_day($year,$month,$day,&$array_target) {
$date = date('Ymd', mktime(0,0,0,$month,$day,$year));
$key = array_search($date,$array_target);
if( $key !== false ) {
array_splice($array_target, $key+1, 1);
}
}
public function remove_exception_holidays($year,$month,$day) {
$this->remove_day($year, $month, $day, $this->exception_holidays);
}
public function remove_exception_business_days($year,$month,$day) {
$this->remove_day($year, $month, $day, $this->exception_business_days);
}
/**
* 稼働日チェック
*/
protected function is_businesday_day($day) {
$time = mktime(0,0,0,$this->month,$day,$this->year);
$week_day = (int)date("w",$time);
$date = date("Ymd",$time);
if( in_array( $date, $this->exception_business_days ) ) {
return true;
}
if( in_array( $date, $this->exception_holidays ) ) {
return true;
}
if( isset($this->holiday_of_week[$week_day]) && $this->holiday_of_week[$week_day]) {
return false;
}
return true;
}
/**
* 休日チェック
*/
protected function is_holiday($day) {
$time = mktime(0,0,0,$this->month,$day,$this->year);
$week_day = (int)date("w",$time);
$date = date("Ymd",$time);
if( in_array( $date, $this->exception_business_days ) ) {
return false;
}
if( in_array( $date, $this->exception_holidays ) ) {
return true;
}
if( isset($this->holiday_of_week[$week_day]) && $this->holiday_of_week[$week_day]) {
return true;
}
return false;
}
/**
* カレンダーの値を計算
*/
protected function calc_calendar() {
$first_day = mktime(0,0,0,$this->month,1,$this->year);
$start_offset = (int)date("w",$first_day);
$month_days = (int)date("t",$first_day);
$calendar = array();
$day = 1;
while($day < $month_days):
$row = array();
for($i = 0; $i < self::WEEK; $i++) {
if( ( $day == 1 && $i < $start_offset ) || $day > $month_days) {
$row[] = array("day" => "", "is_holiday" => false);
continue;
}
$holiday_flag = $this->is_holiday($day);
$date = date("Y年m月d日", mktime(0,0,0,$this->month,$day,$this->year));
$day_data = array(
"day" => $day,
"is_holiday" => $holiday_flag,
"value" => $date
);
$row[] = $day_data;
$day++;
}
$calendar[] = $row;
endwhile;
// var_dump($calendar);
$this->calendar = $calendar;
}
/**
* カレンダー出力
*/
public function render() {
$this->calc_calendar();
echo $this->get_table_header();
echo $this->get_table_body();
echo $this->get_table_footer();
}
protected function get_table_header() {
$date = date("Y年m月", mktime(0,0,0,$this->month,1,$this->year));
$html = '<table class="calendar">
<caption>' . $date . '</caption>
<thead>
<tr>
<th class="calendar-day-sunday">日</th>
<th class="calendar-day-monday">月</th>
<th class="calendar-day-tuesday">火</th>
<th class="calendar-day-wednesday">水</th>
<th class="calendar-day-thursday">木</th>
<th class="calendar-day-friday">金</th>
<th class="calendar-day-saturday">土</th>
</tr>
</thead>
<tbody>';
return $html;
}
protected function get_table_body() {
$html = "";
foreach ($this->calendar as $row ) {
$html .= "<tr>";
foreach ($row as $day) {
$html .= $this->get_table_cell($day);
}
$html .= "</tr>";
}
return $html;
}
protected function get_table_cell($day) {
if(empty($day["day"])) {
return "<td class='calendar-cell-empty'></td>";
}
$html = "";
$td_class = 'calendar-cell';
$td_class .= $day["is_holiday"] ? ' calendar-cell-holiday ' : ' calendar-cell-business-day ';
$html .= "<td class='{$td_class}'>";
$html .= '<div>' . $day["day"] . '</div>';
if( $day["is_holiday"] ) {
// 休日
$html .= "休";
} else {
// 営業日
$html .= "営業";
}
$html .= "</td>";
return $html;
}
protected function get_table_footer() {
return '</tbody>
</table>';
}
}

ライセンス

MIT license

使い方

ソースコードをダウンロードしてインクルード頂いた後、こんな感じで使って頂ければと思います。

まとめ

プログラム作るの面白かった。

仕事では未だ使っていないので、動かなかったらごめんなさい。



「【PHP】営業日カレンダー表示用PHPクラスを作ってみた」への1件のフィードバック

  1. 完璧でソースも読みやすくて、とても勉強になりました!
    ところで、このままだと「2019年6月」のカレンダーで30日が表示されないです。
    以下のように書き換えると問題なく表示されました。

    152行目
    while($day <= $month_days):

コメントを残す