136
|
1 |
/* EventCalendar. Copyright (C) 2005-2007, Alex Tingle. $Revision: 284 $ |
|
2 |
* This file is licensed under the GNU GPL. See LICENSE file for details. |
|
3 |
*/ |
|
4 |
|
|
5 |
// Set in HTML file: |
|
6 |
// var ec3.start_of_week |
|
7 |
// var ec3.month_of_year |
|
8 |
// var ec3.month_abbrev |
|
9 |
// var ec3.myfiles |
|
10 |
// var ec3.home |
|
11 |
// var ec3.hide_logo |
|
12 |
// var ec3.viewpostsfor |
|
13 |
|
|
14 |
/** Register an onload function. */ |
|
15 |
function WindowOnload(f) |
|
16 |
{ |
|
17 |
var prev=window.onload; |
|
18 |
window.onload=function(){ if(prev)prev(); f(); } |
|
19 |
} |
|
20 |
|
|
21 |
// namespace |
|
22 |
function ec3() |
|
23 |
{ |
|
24 |
WindowOnload( function() |
|
25 |
{ |
|
26 |
// Overwrite the href links in ec3_prev & ec3_next to activate EC3. |
|
27 |
var prev=document.getElementById('ec3_prev'); |
|
28 |
var next=document.getElementById('ec3_next'); |
|
29 |
if(prev && next) |
|
30 |
{ |
|
31 |
// Check for cat limit in month link |
|
32 |
var xCat=new RegExp('&cat=[0-9]+$'); |
|
33 |
var match=xCat.exec(prev.href); |
|
34 |
if(match) |
|
35 |
ec3.catClause=match[0]; |
|
36 |
// Replace links |
|
37 |
prev.href='javascript:ec3.go_prev()'; |
|
38 |
next.href='javascript:ec3.go_next()'; |
|
39 |
// Pre-load image. |
|
40 |
ec3.imgwait=new Image(14,14); |
|
41 |
ec3.imgwait.src=ec3.myfiles+'/ec_load.gif'; |
|
42 |
// Convert strings from PHP into Unicode |
|
43 |
ec3.viewpostsfor=unencode(ec3.viewpostsfor); |
|
44 |
for(var i=0; i<ec3.month_of_year.length; i++) |
|
45 |
ec3.month_of_year[i]=unencode(ec3.month_of_year[i]); |
|
46 |
for(var j=0; j<ec3.month_abbrev.length; j++) |
|
47 |
ec3.month_abbrev[j]=unencode(ec3.month_abbrev[j]); |
|
48 |
} |
|
49 |
} ); |
|
50 |
|
|
51 |
/** Converts HTML encoded text (e.g. "© Copyright") into Unicode. */ |
|
52 |
function unencode(text) |
|
53 |
{ |
|
54 |
if(!ec3.unencodeDiv) |
|
55 |
ec3.unencodeDiv=document.createElement('div'); |
|
56 |
ec3.unencodeDiv.innerHTML=text; |
|
57 |
return (ec3.unencodeDiv.innerText || ec3.unencodeDiv.firstChild.nodeValue); |
|
58 |
} |
|
59 |
|
|
60 |
function get_child_by_tag_name(element,tag_name) |
|
61 |
{ |
|
62 |
var results=element.getElementsByTagName(tag_name); |
|
63 |
if(results) |
|
64 |
for(var i=0; i<results.length; i++) |
|
65 |
if(results[i].parentNode==element) |
|
66 |
return results[i]; |
|
67 |
return 0; |
|
68 |
} |
|
69 |
ec3.get_child_by_tag_name=get_child_by_tag_name; |
|
70 |
|
|
71 |
|
|
72 |
function calc_day_id(day_num,month_num,year_num) |
|
73 |
{ |
|
74 |
if(ec3.today_day_num==day_num && |
|
75 |
ec3.today_month_num==month_num && |
|
76 |
ec3.today_year_num==year_num) |
|
77 |
{ |
|
78 |
return 'today'; |
|
79 |
} |
|
80 |
else |
|
81 |
{ |
|
82 |
return 'ec3_'+year_num+'_'+month_num+'_'+day_num; |
|
83 |
} |
|
84 |
} |
|
85 |
|
|
86 |
|
|
87 |
/** Replaces the caption and tbody in table to be the specified year/month. */ |
|
88 |
function create_calendar(table_cal,month_num,year_num) |
|
89 |
{ |
|
90 |
// Take a deep copy of the current calendar. |
|
91 |
var table=table_cal.cloneNode(1); |
|
92 |
|
|
93 |
// Calculate the zero-based month_num |
|
94 |
var month_num0=month_num-1; |
|
95 |
|
|
96 |
// Set the new caption |
|
97 |
var caption=get_child_by_tag_name(table,'caption'); |
|
98 |
if(caption) |
|
99 |
{ |
|
100 |
var c=get_child_by_tag_name(caption,'a'); |
|
101 |
var caption_text=ec3.month_of_year[month_num0] + ' ' + year_num; |
|
102 |
if(c && c.firstChild && c.firstChild.nodeType==ec3.TEXT_NODE ) |
|
103 |
{ |
|
104 |
if(month_num<10) |
|
105 |
{ |
|
106 |
c.href=ec3.home+'/?m='+year_num+'0'+month_num; |
|
107 |
} |
|
108 |
else |
|
109 |
{ |
|
110 |
c.href=ec3.home+'/?m='+year_num+month_num; |
|
111 |
} |
|
112 |
if(ec3.catClause) |
|
113 |
c.href+=ec3.catClause; // Copy cat' limit from original month link. |
|
114 |
c.title=ec3.viewpostsfor; |
|
115 |
c.title=c.title.replace(/%1\$s/,ec3.month_of_year[month_num0]); |
|
116 |
c.title=c.title.replace(/%2\$s/,year_num); |
|
117 |
c.firstChild.data=caption_text; |
|
118 |
} |
|
119 |
} |
|
120 |
|
|
121 |
if(caption && caption.firstChild && caption.firstChild.nodeType==ec3.TEXT_NODE) |
|
122 |
caption.firstChild.data=ec3.month_of_year[month_num0] + ' ' + year_num; |
|
123 |
|
|
124 |
var tbody=get_child_by_tag_name(table,'tbody'); |
|
125 |
|
|
126 |
// Remove all children from the table body |
|
127 |
while(tbody.lastChild) |
|
128 |
tbody.removeChild(tbody.lastChild); |
|
129 |
|
|
130 |
// Make a new calendar. |
|
131 |
var date=new Date(year_num,month_num0,1, 12,00,00); |
|
132 |
|
|
133 |
var tr=document.createElement('tr'); |
|
134 |
var td,div; |
|
135 |
tbody.appendChild(tr); |
|
136 |
var day_count=0 |
|
137 |
var col=0; |
|
138 |
while(date.getMonth()==month_num0 && day_count<40) |
|
139 |
{ |
|
140 |
var day=(date.getDay()+7-ec3.start_of_week)%7; |
|
141 |
if(col>6) |
|
142 |
{ |
|
143 |
tr=document.createElement('tr'); |
|
144 |
tbody.appendChild(tr); |
|
145 |
col=0; |
|
146 |
} |
|
147 |
if(col<day) |
|
148 |
{ |
|
149 |
// insert padding |
|
150 |
td=document.createElement('td'); |
|
151 |
td.colSpan=day-col; |
|
152 |
td.className='pad'; |
|
153 |
tr.appendChild(td); |
|
154 |
col=day; |
|
155 |
} |
|
156 |
// insert day |
|
157 |
td=document.createElement('td'); |
|
158 |
td.appendChild(document.createTextNode(date.getDate())); |
|
159 |
td.id=calc_day_id(date.getDate(),month_num,year_num); |
|
160 |
tr.appendChild(td); |
|
161 |
col++; |
|
162 |
day_count++; |
|
163 |
date.setDate(date.getDate()+1); |
|
164 |
} |
|
165 |
// insert padding |
|
166 |
if(col<7) |
|
167 |
{ |
|
168 |
td=document.createElement('td'); |
|
169 |
td.colSpan=7-col; |
|
170 |
td.className='pad'; |
|
171 |
tr.appendChild(td); |
|
172 |
} |
|
173 |
|
|
174 |
// add the 'dog' |
|
175 |
if((7-col)>1 && !ec3.hide_logo) |
|
176 |
{ |
|
177 |
a=document.createElement('a'); |
|
178 |
a.href='http://blog.firetree.net/?ec3_version='+ec3.version; |
|
179 |
a.title='Event Calendar '+ec3.version; |
|
180 |
td.style.verticalAlign='bottom'; |
|
181 |
td.appendChild(a); |
|
182 |
div=document.createElement('div'); |
|
183 |
div.className='ec3_ec'; |
|
184 |
div.align='right'; // keeps IE happy |
|
185 |
a.appendChild(div); |
|
186 |
} |
|
187 |
|
|
188 |
// set table's element id |
|
189 |
table.id='ec3_'+year_num+'_'+month_num; |
|
190 |
|
|
191 |
return table; |
|
192 |
} // end create_calendar() |
|
193 |
|
|
194 |
|
|
195 |
/** Dispatch an XMLHttpRequest for a month of calendar entries. */ |
|
196 |
function loadDates(month_num,year_num) |
|
197 |
{ |
|
198 |
var req=new XMLHttpRequest(); |
|
199 |
if(req) |
|
200 |
{ |
|
201 |
ec3.reqs.push(req); |
|
202 |
req.onreadystatechange=process_xml; |
|
203 |
req.open("GET", |
|
204 |
ec3.home+'/?ec3_xml='+year_num+'_'+month_num,true); |
|
205 |
set_spinner(1); |
|
206 |
req.send(null); |
|
207 |
} |
|
208 |
} |
|
209 |
|
|
210 |
|
|
211 |
/** Obtain an array of all the calendar tables. */ |
|
212 |
function get_calendars() |
|
213 |
{ |
|
214 |
var div=document.getElementById('wp-calendar'); |
|
215 |
var result=new Array(); |
|
216 |
for(var i=0; i<div.childNodes.length; i++) |
|
217 |
{ |
|
218 |
var c=div.childNodes[i]; |
|
219 |
if(c.id && c.id.search('ec3_[0-9]')==0 && c.style.display!='none') |
|
220 |
result.push(div.childNodes[i]); |
|
221 |
} |
|
222 |
if(result.length>0) |
|
223 |
return result; |
|
224 |
else |
|
225 |
return 0; |
|
226 |
} |
|
227 |
ec3.get_calendars=get_calendars; |
|
228 |
|
|
229 |
|
|
230 |
/** Changes the link text in the forward and backwards buttons. |
|
231 |
* Parameters are the 0-based month numbers. */ |
|
232 |
function rewrite_controls(prev_month0,next_month0) |
|
233 |
{ |
|
234 |
var prev=document.getElementById('ec3_prev'); |
|
235 |
if(prev && prev.firstChild && prev.firstChild.nodeType==ec3.TEXT_NODE) |
|
236 |
prev.firstChild.data='\u00ab\u00a0'+ec3.month_abbrev[prev_month0%12]; |
|
237 |
var next=document.getElementById('ec3_next'); |
|
238 |
if(next && next.firstChild && next.firstChild.nodeType==ec3.TEXT_NODE) |
|
239 |
next.firstChild.data=ec3.month_abbrev[next_month0%12]+'\u00a0\u00bb'; |
|
240 |
} |
|
241 |
|
|
242 |
|
|
243 |
/** Turn the busy spinner on or off. */ |
|
244 |
function set_spinner(on) |
|
245 |
{ |
|
246 |
var spinner=document.getElementById('ec3_spinner'); |
|
247 |
var publish=document.getElementById('ec3_publish'); |
|
248 |
if(spinner) |
|
249 |
{ |
|
250 |
if(on) |
|
251 |
{ |
|
252 |
spinner.style.display='inline'; |
|
253 |
if(publish) |
|
254 |
publish.style.display='none'; |
|
255 |
} |
|
256 |
else |
|
257 |
{ |
|
258 |
spinner.style.display='none'; |
|
259 |
if(publish) |
|
260 |
publish.style.display='inline'; |
|
261 |
} |
|
262 |
} |
|
263 |
} |
|
264 |
|
|
265 |
|
|
266 |
/** Called when the user clicks the 'previous month' button. */ |
|
267 |
function go_prev() |
|
268 |
{ |
|
269 |
var calendars=get_calendars(); |
|
270 |
if(!calendars) |
|
271 |
return; |
|
272 |
var pn=calendars[0].parentNode; |
|
273 |
|
|
274 |
// calculate date of new calendar |
|
275 |
var id_array=calendars[0].id.split('_'); |
|
276 |
if(id_array.length<3) |
|
277 |
return; |
|
278 |
var year_num=parseInt(id_array[1]); |
|
279 |
var month_num=parseInt(id_array[2])-1; |
|
280 |
if(month_num==0) |
|
281 |
{ |
|
282 |
month_num=12; |
|
283 |
year_num--; |
|
284 |
} |
|
285 |
// Get new calendar |
|
286 |
var newcal=document.getElementById('ec3_'+year_num+'_'+month_num); |
|
287 |
if(newcal) |
|
288 |
{ |
|
289 |
// Add in the new first calendar |
|
290 |
newcal.style.display=ec3.calendar_display; |
|
291 |
} |
|
292 |
else |
|
293 |
{ |
|
294 |
newcal=create_calendar(calendars[0],month_num,year_num); |
|
295 |
pn.insertBefore( newcal, calendars[0] ); |
|
296 |
loadDates(month_num,year_num); |
|
297 |
} |
|
298 |
// Hide the last calendar |
|
299 |
ec3.calendar_display=calendars[calendars.length-1].style.display; |
|
300 |
calendars[calendars.length-1].style.display='none'; |
|
301 |
|
|
302 |
// Re-write the forward & back buttons. |
|
303 |
rewrite_controls(month_num+10,month_num+calendars.length-1); |
|
304 |
} |
|
305 |
ec3.go_prev=go_prev; |
|
306 |
|
|
307 |
|
|
308 |
/** Called when the user clicks the 'next month' button. */ |
|
309 |
function go_next() |
|
310 |
{ |
|
311 |
var calendars=get_calendars(); |
|
312 |
if(!calendars) |
|
313 |
return; |
|
314 |
var pn=calendars[0].parentNode; |
|
315 |
var last_cal=calendars[calendars.length-1]; |
|
316 |
|
|
317 |
// calculate date of new calendar |
|
318 |
var id_array=last_cal.id.split('_'); |
|
319 |
if(id_array.length<3) |
|
320 |
return; |
|
321 |
var year_num=parseInt(id_array[1]); |
|
322 |
var month_num=1+parseInt(id_array[2]); |
|
323 |
if(month_num==13) |
|
324 |
{ |
|
325 |
month_num=1; |
|
326 |
year_num++; |
|
327 |
} |
|
328 |
// Get new calendar |
|
329 |
var newcal=document.getElementById('ec3_'+year_num+'_'+month_num); |
|
330 |
if(newcal) |
|
331 |
{ |
|
332 |
// Add in the new last calendar |
|
333 |
newcal.style.display=ec3.calendar_display; |
|
334 |
} |
|
335 |
else |
|
336 |
{ |
|
337 |
newcal=create_calendar(calendars[0],month_num,year_num); |
|
338 |
if(last_cal.nextSibling) |
|
339 |
pn.insertBefore(newcal,last_cal.nextSibling); |
|
340 |
else |
|
341 |
pn.appendChild(newcal); |
|
342 |
loadDates(month_num,year_num); |
|
343 |
} |
|
344 |
// Hide the first calendar |
|
345 |
ec3.calendar_display=calendars[0].style.display; |
|
346 |
calendars[0].style.display='none'; |
|
347 |
|
|
348 |
// Re-write the forward & back buttons. |
|
349 |
rewrite_controls(month_num-calendars.length+11,month_num); |
|
350 |
} |
|
351 |
ec3.go_next=go_next; |
|
352 |
|
|
353 |
|
|
354 |
/** Triggered when the XML load is complete. Checks that load is OK, and then |
|
355 |
* updates calendar days. */ |
|
356 |
function process_xml() |
|
357 |
{ |
|
358 |
var busy=0; |
|
359 |
for(var i=0; i<ec3.reqs.length; i++) |
|
360 |
{ |
|
361 |
var req=ec3.reqs[i]; |
|
362 |
if(req) |
|
363 |
{ |
|
364 |
if(req.readyState==4) |
|
365 |
{ |
|
366 |
ec3.reqs[i]=0; |
|
367 |
if(req.status==200) |
|
368 |
update_days(req.responseXML.documentElement); |
|
369 |
} |
|
370 |
else |
|
371 |
busy=1; |
|
372 |
} |
|
373 |
} |
|
374 |
if(!busy) |
|
375 |
{ |
|
376 |
// Remove old requests. |
|
377 |
while(ec3.reqs.shift && ec3.reqs.length && !ec3.reqs[0]) |
|
378 |
ec3.reqs.shift(); |
|
379 |
set_spinner(0); |
|
380 |
} |
|
381 |
} |
|
382 |
|
|
383 |
|
|
384 |
/** Adds links to the calendar for each day listed in the XML. */ |
|
385 |
function update_days(month_xml) |
|
386 |
{ |
|
387 |
var days=month_xml.getElementsByTagName('day'); |
|
388 |
if(!days) |
|
389 |
return; |
|
390 |
for(var i=0; i<days.length; i++) |
|
391 |
{ |
|
392 |
var td=document.getElementById(days[i].getAttribute('id')); |
|
393 |
if(td && td.firstChild && td.firstChild.nodeType==ec3.TEXT_NODE) |
|
394 |
{ |
|
395 |
td.className='ec3_postday'; |
|
396 |
var txt=td.removeChild(td.firstChild); |
|
397 |
var a=document.createElement('a'); |
|
398 |
a.href=days[i].getAttribute('link'); |
|
399 |
a.title=days[i].getAttribute('titles'); |
|
400 |
if(days[i].getAttribute('is_event')) |
|
401 |
{ |
|
402 |
td.className+=' ec3_eventday'; |
|
403 |
a.className='eventday'; |
|
404 |
} |
|
405 |
a.appendChild(txt); |
|
406 |
td.appendChild(a); |
|
407 |
} |
|
408 |
} |
|
409 |
if(typeof ec3_Popup != 'undefined') |
|
410 |
{ |
|
411 |
var month= |
|
412 |
document.getElementById(month_xml.childNodes[0].getAttribute('id')); |
|
413 |
if(month) |
|
414 |
ec3_Popup.add_tbody( get_child_by_tag_name(month,'tbody') ); |
|
415 |
} |
|
416 |
} |
|
417 |
|
|
418 |
|
|
419 |
} // end namespace ec3 |
|
420 |
|
|
421 |
// Export public functions from ec3 namespace. |
|
422 |
ec3(); |
|
423 |
|
|
424 |
// Set up static variables in namespace 'ec3'. |
|
425 |
|
|
426 |
// Get today's date. |
|
427 |
// Note - DO THIS ONCE, so that the value of today never changes! |
|
428 |
ec3.today=new Date(); |
|
429 |
ec3.today_day_num=ec3.today.getDate(); |
|
430 |
ec3.today_month_num=1+ec3.today.getMonth(); |
|
431 |
ec3.today_year_num=ec3.today.getFullYear(); |
|
432 |
|
|
433 |
// Holds ongoing XmlHttp requests. |
|
434 |
ec3.reqs=new Array(); |
|
435 |
|
|
436 |
ec3.ELEMENT_NODE=1; |
|
437 |
ec3.TEXT_NODE=3; |
|
438 |
|
|
439 |
ec3.version='3.1.4'; |