A calendar code


This class can be used to display month calendars in HTML tables.

It takes a given month and year and generates an HTML table with the days of that month. The calendar start week day may be set to Sunday or Monday.

Special event days may exhibit the title of the event in the respective calendar table cell.

The class also shows links to pages that display the next and previous months.

The calendar presentation details can be configured with CSS styles.

The class generates XHTML compliant HTML.

Download Source code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
< ?php
 
class calendar {
 
	// Events array
	private $events = array();
	// Defaults for day and month names
	private $dayNames = array ( 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun');
	private $monthNames = array ( 'January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December' );
	// Defaults for prev and next links
	private $prevMonthNavTxt = '&laquo';
	private $nextMonthNavTxt = '&raquo';
	private $calendarName;
 
	public function __construct($name='cal') {
		// Assign name to calendar
		if (strpos($name, ' ') || strpos($name, '_') || is_numeric(substr($name, 0, 1)))
			throw new exception('Calendar name must be a valid CSS name');
		$this->calendarName = $name;
 
		// Names for special cases
		$this->markup = array('current_day' => 'current-day',
									'last_day_of_week' =>'last-day-of-week',
									'prev_month' => 'prev-month-day',
									'next_month' => 'next-month-day',
									'event' => 'event',
									'header' => 'header',
									'nav' => 'nav',
									'days_of_week' => 'days-of-week'
									);
	}
 
	// Get calendar name
	public function getCalendarName(){
		return $this->calendarName;
	}
 
	// Set text for previous and next calendar links
	public function setNavigationText($prev, $next) {
		$this->prevMonthNavTxt = $prev;
		$this->nextMonthNavTxt = $next;
	}
	// Get text for previous and next calendar links
	public function getNavigationText() {
		return array(	'prev' => $this->prevMonthNavTxt,
						'next' => $this->nextMonthNavTxt
					);
	}
 
	// Set inner border width. Would be too annoying to do this with CSS
	public function setInnerBorder($size) {
		$this->innerBorder = intval($size);
	}
	// Set inner border width. Would be too annoying to do this with CSS
	public function getInnerBorder($size) {
		return $this->innerBorder;
	}
 
	// Set the names of the days
	public function setDayNames($array) {
		if (count($array) == 7)
			$this->dayNames = $array;
		else
			throw new exception ('Invalid value for setDayNames()');
	}
	// Get the names of the days
	public function getDayNames($array) {
		return $this->dayNames;
	}
 
	// Set the names of the months
	public function setMonthNames($array) {
		if (count($array) == 12)
			$this->monthNames = $array;
		else
			throw new exception ('Invalid value for setMonthNames()');
	}
	// Set the names of the months
	public function getMonthNames($array) {
		return $this->monthNames;
	}
 
	// Sets the calendar start day 0=monday, 1=sunday, 2=saturday etc...
	public function setStartDay($day) {
		if (is_int($day) && $day >= 0 && $day < =6) {
			$this->startDay=$day;
			for ($i=0;$i< $day;$i++)
			array_unshift($this->dayNames, array_pop($this->dayNames));
		}
		else
			throw new exception('Invalid value for setStartDay()');
	}
	// Gets the calendar start day
	public function getStartDay($day) {
		return $this->startDay=$day;
	}
 
	// Enables prev and next month links
	public function enableNavigation() {
		$this->enableNav = true;
	}
	// Disables prev and next month links
	public function disableNavigation() {
		$this->enableNav = false;
	}
 
	// Gets the long name of the current month
	private function getMonthName() {
		return ucwords($this->monthNames[$this->month-1]);
	}
	// Get calendars month 1-12
	private function getMonth() {
		return $this->month;
	}
	// Get calendar year ####
	private function getYear() {
		return $this->year;
	}
 
	// Enables nicely formatted html instead of just one big line
	public function enablePrettyHTML() {
		$this->prettyHTML = true;
	}
	// Disables nicely formatted html instead of just one big line
	public function disablePrettyHTML() {
		$this->prettyHTML = false;
	}
 
	// Display the year along side the month
	public function enableYear() {
		$this->displayYear = true;
	}
	// Do not display year near the month
	public function disableYear() {
		$this->displayYear = false;
	}
 
	// Enables the displaying of prev and next month's days on the calendar
	public function enableNonMonthDays() {
		$this->displayNonMonthDays = true;
	}
	// Disables the displaying of previous and next month's days on the calendar
	public function disableNonMonthDays() {
		$this->displayNonMonthDays = false;
	}
 
	// get an event on a given date
	public function getEventByDate($year, $month, $day) {
		if (isset($this->events[$year][$month][$day]))
			return $this->events[$year][$month][$day];
		return FALSE;
	}
 
	// Add an event
	public function addEvent($eventTitle, $eventYear, $eventMonth, $eventDay, $eventLink) {
		$this->events[$eventYear][$eventMonth][$eventDay] = array(	'event_title' => $eventTitle, 'event_link' => $eventLink);
	}
	public function removeEvent($eventYear, $eventMonth, $eventDay) {
		unset($this->events[$eventYear][$eventMonth][$eventDay]);
	}
 
	// Offsets timestamp according to offset and returns the day month or year
	private function timeTravel($offset, $dmy, $timeStamp) {
		$dateVals = array (	'd' => 'j',
							'm' => 'n',
							'y' => 'Y'
							);
		return date($dateVals[$dmy], strtotime($offset, $timeSTamp));
	}
 
	// Display calendar.true Supply month and year to override default value of current month
	public function display($month='', $year='') {
 
		// Remove whitespaces
		$year = trim($year);
		$month = trim($month);
 
		// Set day, month and year of calendar
		$this->day = 1;
		$this->month = ($month == '') ?	date('n') : $month;
		$this->year = ($year == '') ? date('Y') : $year;
 
		// Check for valid input	
		if (!preg_match('~[0-9]{4}~', $this->year))
			throw new exception('Invalid value for year');
		if (!is_numeric($this->month) || $this->month < 0 || $this->month > 13)
			throw new exception('Invalid value for month');
 
		// Set the current timestamp
		$this->timeStamp = mktime(1,1,1,$this->month, $this->day, $this->year);
		// Set the number of days in teh current month
		$this->daysInMonth = date('t',$this->timeStamp);
 
		// Start table
		$calHTML = sprintf("<table id=\"%s\" cellpadding=\"0\" cellspacing=\"%d\"><thead><tr>", $this->calendarName, $this->innerBorder);
 
		// Display previous month navigation
		if ($this->enableNav) {
			$pM = explode('-', date('n-Y', strtotime('-1 month', $this->timeStamp)));
			$calHTML .= sprintf("<td class=\"%s-%s\"><a href=\"?%smonth=%d&amp;year=%d\">%s</a></td>", $this->calendarName, $this->markup['nav'], $this->queryString, $pM[0], $pM[1],$this->prevMonthNavTxt);
		}
 
		// Month name and optional year
		$calHTML .= sprintf("<td colspan=\"%d\" id=\"%s-%s\">%s%s</td>", ($this->enableNav ? 5 : 7), $this->calendarName, $this->markup['header'], $this->getMonthName(), ($this->displayYear ? ' ' .$this->year : ''));
 
		// Display next month navigation
		if ($this->enableNav) {
			$nM = explode('-', date('n-Y', strtotime('+1 month', $this->timeStamp)));
			$calHTML .= sprintf("<td class=\"%s-%s\"><a href=\"?%smonth=%d&amp;year=%d\">%s</a></td>", $this->calendarName, $this->markup['nav'], $this->queryString, $nM[0], $nM[1],$this->nextMonthNavTxt);
		}
 
		$calHTML .= sprintf("</tr></thead><tbody><tr id=\"%s\">", $this->markup['days_of_week']);
 
		// Display day headers
		foreach($this->dayNames as $k => $dayName)
			$calHTML .= sprintf("<td>%s</td>", $dayName);
 
		$calHTML .= "</tr><tr>";
 
		/// What the heck is this
		$sDay = date('N', $this->timeStamp) + $this->startDay - 1;
 
		// Print previous months days
			for ($e=1;$e< =$sDay;$e++)
				$calHTML .= sprintf("<td class=\"%s-%s\">%s", $this->calendarName, $this->markup['prev_month'],  (($this->displayNonMonthDays) ? $this->timeTravel("-" . ($sDay -$e) . " days", 'd', $this->timeStamp) : ''));
 
		// Print days
		for ($i=1;$i< =$this->daysInMonth;$i++) {
			// Set current day and timestamp
			$this->day = $i;
			$this->timeStamp = mktime(1,1,1,$this->month, $this->day, $this->year);
 
			// Set day as either plain text or event link
			if (isset($this->events[$this->year][$this->month][$this->day]))
				$this->htmlDay = sprintf("<a href=\"%s\" title=\"%s\">%s</a>", $this->events[$this->year][$this->month][$this->day]['event_link'], $this->events[$this->year][$this->month][$this->day]['event_title'], $this->day);
			else
				$this->htmlDay = $this->day;			
 
			// Display calendar cell
			$calHTML .= sprintf("<td %s%s>%s</td>", ($this->timeStamp == mktime(1,1,1,date('n'),date('j'),date('Y')) ? 'id="' . $this->calendarName . '-' . $this->markup['current_day'] . '" ' : ''), ((($sDay + $this->day) % 7 == 0) ? 'class="' . $this->calendarName . '-' . $this->markup['last_day_of_week'] . '"' : ''), $this->htmlDay);				
 
			// End row if necessary			
			if (($sDay + $this->day) % 7 == 0)
				$calHTML .= "</tr><tr>";
		}
 
		// Print next months days
		for ($e2=1;$e2 < (7 - (($sDay + $this->daysInMonth -1) % 7)); $e2++)
			$calHTML .= sprintf("<td class=\"%s-next-month-day%s\">%s</td>", $this->calendarName, ((($sDay + $this->day + $e2) % 7 == 0) ? ' ' . $this->calendarName . '-' . $this->markup['last_day_of_week'] : ''), (($this->displayNonMonthDays) ? $this->timeTravel("+$e2 days", 'd', $this->timeStamp) : ''));
 
		$calHTML .= "</tr></tbody></table>";
 
		// Tidy up html
		if ($this->prettyHTML) {
			$replaceWhat = array('<tr ', '<td', '</tr>', '', '<thead>', '</thead>', '<tbody>', '</tbody>');
			$replaceWith = array("\n\t\t</tr><tr ", "\n\t\t\t<td", "\n\t\t</tr>", "\n", "\n\t<thead>", "\n\t</thead>", "\n\t<tbody>", "\n\t</tbody>");
			$calHTML = str_replace($replaceWhat, $replaceWith, $calHTML);
		}
 
		// Print calendar
		echo $calHTML;
	}
 
}
?>
</tr>

If you enjoyed this post, please consider to leave a comment or subscribe to the feed and get future articles delivered to your feed reader.

Comments

It is not passing validation. It breaks validation when you have emty tags with no tags

$calHTML .= “”;
}

// Print next months days
for ($e2=1;$e2 daysInMonth -1) % 7)); $e2++)
$calHTML .= sprintf(”%s”, $this->calendarName, ((($sDay + $this->day + $e2) % 7 == 0) ? ‘ ‘ . $this->calendarName . ‘-’ . $this->markup['last_day_of_week'] : ”), (($this->displayNonMonthDays) ? $this->timeTravel(”+$e2 days”, ‘d’, $this->timeStamp) : ”));

$calHTML .= “”;

Hello,

How change the first day to Sunday?

I try and change many options, but does’t work.

Thanks and greetings from Costa Rica

Leave a comment

(required)

(required)