<!-- Original:  Doug Lawson (dlawson@clark.net) -->
<!-- Modified:  Korey Mercier (korey@wolfspring.com) -->

<!-- 2001.05 KSM: Modified to utilize the overLIB 3.10 library  -->
<!-- 2001.05 KSM: Added events and rewrote event/holiday diplay -->
<!-- 2001.09 KSM: Added layer support for nav. in both browsers -->

<!-- This script and many more are available free online at -->
<!-- The JavaScript Source!! http://javascript.internet.com -->


//////////////////////////////////////////////////////////////////////////////
// CODE TO BE INCLUDED ON PAGE
//
// <div id="overDiv" style="position:absolute; visibility:hide; z-index:1;"></div>
// <SCRIPT LANGUAGE="JavaScript" SRC="/include/overlib.js"></SCRIPT>
// <SCRIPT LANGUAGE="JavaScript" SRC="/include/calendar.js"></SCRIPT>
// <SCRIPT LANGUAGE="JavaScript">
// <!--
// 	addEvent(2001,"May",15,"This is a test event.");
// 	addHoliday(2001,"Apr",23,"This is a test holiday.");
// 	layerCalendars();
// //-->
// </SCRIPT>


///////////////////////////////////////////////
// EVENTS AND HOLIDAYS
var events = new Array();
// add events using addEvent()
var holidays = new Array();
holidays["2 Feb"] 		= "Imbolc/Candlemas";
holidays["20 Mar 2001"] = "Ostara/Spring Equinox";
holidays["1 May"] 		= "Beltane";
holidays["21 Jun 2001"] = "Midsummer/Summer Solstice";
holidays["1 Aug"] 		= "Lammas/Lughnassadh";
holidays["22 Sep 2001"] = "Mabon/Fall Equinox";
holidays["22 Sep 2002"] = "Mabon/Fall Equinox";
holidays["26 Sep 2001"] = "Coven of the Burning Waters' 5yr Anniversary";
holidays["26 Sep 2002"] = "Coven of the Burning Waters' 6yr Anniversary";
holidays["26 Sep 2003"] = "Coven of the Burning Waters' 7yr Anniversary";
holidays["31 Oct"] 		= "Samhain";
holidays["21 Dec 2001"] = "Winter Solstice/Yule";
holidays["21 Dec 2002"] = "Winter Solstice/Yule";
// replacement pattern for making the value strings safe to display
var re  = /'/g;
var rpl = "\\'";

///////////////////////////////////////////////
// COLORS
// changing colors here is a lot easier than slogging through the code 
//
// actually, it would be better to do all this with classes and style sheets 
// but we want to support some older browsers 
var colorWhite 		= "#FFFFFF"; 
var colorOffWhite	= "#F8F8F8"; 
var colorLightRed 	= "#FF4444"; 
var colorMedRed 	= "#AA0000"; 
var colorDarkRed	= "#660000";
var colorLightBlue	= "#E0E0FF"; 
var colorShadBlue   = "#BBBBFF";
var colorMedBlue	= "#CCCCFF";
var colorDarkBlue	= "#000066";
// colors for various parts of the calendars
var wkdBGColor    	= colorMedBlue;		// bg color for weekends
var wkdFGColor    	= colorMedRed;		// fg color for weekends
var holBGColor    	= colorShadBlue;	// bg color for holidays 
var holFGColor    	= colorDarkRed;		// fg color for holidays 
var eventBGColor  	= colorMedRed;		// bg color for events
var eventFGColor  	= colorOffWhite;	// fg color for events
var dowBGColor    	= colorLightBlue;	// bg for days of week
var dowFGColor    	= colorDarkBlue;	// fg for days of week 
var calHdrBGColor 	= colorDarkBlue;	// bg for month and year
var calHdrFGColor 	= colorOffWhite;	// fg for month and year

// style tags for holiday and event links
document.writeln("<STYLE TYPE=\"text/css\"><!-- ");
document.writeln("	a.calHoliday {text-decoration:none; color:" + holFGColor + "}");
document.writeln("	td.calHoliday {border-style:solid; border-width:1pt; border-color:" + holBGColor + "}");
document.writeln("	a.calEvent {text-decoration:none; color:" + eventFGColor + "}");
document.writeln(" --></STYLE>");


////////////////////////////////////////////////
// ABBREVIATED MONTH NAMES
// months[] is used internally for (among other things) compatibility with 
// javascript Date.parse() methods.  You should only have to change it if 
// your language variable changes. 
var months = new Array( "Jan","Feb","Mar", "Apr","May","Jun", "Jul","Aug","Sep","Oct", "Nov", "Dec");
///////////////////////////////////////////////
// LONG MONTH NAMES
// longmonths is used for calendar titles. They don't have to be long, 
// just whatever you would like to display 
// 
var longmonths = new Array( "January", "February", "March",
			    "April", "May", "June",
			    "July", "August", "September",
			    "October", "November", "December" ); 

var leapdays = new Array(31,29,31, 30,31,30, 31,31,30, 31,30,31); 
var yeardays = new Array(31,28,31, 30,31,30, 31,31,30, 31,30,31); 
//////////////////////////////////////////////// 
// the symbols to use at the top of the calendars
var dow = new Array("S","M","T","W","T","F","S"); 
// globalCalWidth is the default width for calendar tables
var globalCalWidth = "100%"; 

//////////////////////////////////////////////////////////////////
// a global date object to speed things up a little, since 
// there are lots of places where we need today's date
var calStartDOW = 0;
var myDate = new Date(); 
////////////////////////////////////////////////////////////////
// thisMonth and thisYear are used as static vars for 
// newCalendars() (for persistence between calls, which may 
// or may not involve reloading the document) 
// 
// whether these are important or not depends on how you
// handle the PREVIOUS and NEXT buttons. If you reload the 
// script from the server using GET, you won't use these variables. 
// 
// if you want to cahnge the target so that going backward or 
// forward does not require a reload, then you will be setting these
// from the buttons, probably best done with a handler for onClick()
var thisMonth = myDate.getMonth(); 
var thisYear  = myDate.getFullYear(); 
// Now, figure out the arguments the page was loaded with 
// and what they mean
//
// you won't need the next four lines if you don't use GET for
// the PREVIOUS and NEXT features. Comment them out 
// if that is the case 
var URLargs = getURLArgs(true); 
if (URLargs.year)    { thisYear = parseInt(URLargs.year);            } 
if (URLargs.month)   { thisMonth = (parseInt(URLargs.month)%12);     } 
if (URLargs.starton) { calStartDOW = (parseInt(URLargs.starton)%7);  }

function fullDate(year,mon,mday)
{
  return (longmonths[months.toString().indexOf(mon)/4] + " " + mday + ", " + year);
}
function isLeapYear( year )
{
  // is it leap year ? returns a boolean
  return ( (0 == (year%4)) && ( (0 != (year%100)) || (0 == (year%400)))); 
  // ie, if the year divides by 4, but not by 100 except when it divides by
  // 400, it is leap year
} 
function isValidDayOfMonth( day, month, year) 
{ 
  // determines whether a day is valid 
  // (ie, prevents Feb 30 from being processed) 
  // ( not used but left here for other pages that use 
  // this calendar, like the time-off request form ) 
  // 
  if (day <= 0) { return false; }
  if (isLeapYear(year)) { return (day <= leapdays[month])}
  return ( day <= yeardays[month]); 
} 
function canonicalDate(day, month, year) 
{ 
  // return the number of days since the Jan 0 2000 (ie, 1/1/2K returns 1, 31/12/1999 returns 0) 
  // for days before Jan 1 2000, returns negative numbers
  var canonDate = 0;
  // if the function had no arguments, use today's date; 
  var mday = myDate.getDate(); 
  var mmon = myDate.getMonth(); 
  var myr  = myDate.getFullYear(); 
  if( arguments.length > 0 ) 	 { mday = arguments[0];	 } 
  if( arguments.length > 1 ) 	 { mmon = arguments[1];	 } 
  if( arguments.length > 2 ) 	 { myr  = arguments[2];	 } 
 if(myr >= 2000) 
	{ canonDate += mday; 
	  while(mmon > 0)  { canonDate += isLeapYear(myr) ? leapdays[mmon]: yeardays[mmon]; mmon--;} 
	  while(myr > 2000){ canonDate += isLeapYear(myr) ? 366: 365; myr--;  } 
	} 
 else
	{ canonDate -= isLeapYear(myr) ? leapdays[mmon] - mday: yeardays[mmon] - mday; 
	  while(mmon < 11)  { mmon++; canonDate -= isLeapYear(myr) ? leapdays[mmon]: yeardays[mmon];} 
	  while(myr < 1999){ myr++; canonDate -= isLeapYear(myr) ? 366: 365;} 
	} 
 return canonDate; 
} 
function dateAdd(firstDate, numAdd) 
{ 
  // returns the date after adding the requested number of days to the firstDate.
  // Result is a date type.

	var myDay = firstDate.getDate();
	var myMonth= firstDate.getMonth();
	var myYear= firstDate.getYear();
	for(var i=0; i < numAdd; i++) {
		// increment date variables
		myDay++;
		if (myDay > (isLeapYear(myYear) ? leapdays[myMonth]: yeardays[myMonth])) {
			myDay = 1;
			myYear = (myMonth + 1 > 12) ? myYear + 1 : myYear;
			myMonth = (myMonth % 12) + 1;
		}
	}
	var lastDate = new Date(myYear,myMonth,myDay,firstDate.getHours(),firstDate.getMinutes(),firstDate.getSeconds()); 
	return lastDate; 
} 
function dateDiff(firstDate, secondDate) 
{ 
  // returns the result in days of subtracting firstDate from secondDate. Result is 
  // negative if secondDate came before firstDate. 
  var days= ( canonicalDate(secondDate.getDate(), secondDate.getMonth(), secondDate.getFullYear()) -  
				  canonicalDate(firstDate.getDate(), firstDate.getMonth(), firstDate.getFullYear())); 
  return days; 
} 
function lastMonth (myear, mmonth)
{
  var myYear = thisYear
  var myMonth = thisMonth
  if(arguments.length >= 1) { myYear = myear; } 
  if(arguments.length >= 2) { myMonth = mmonth; } 
  return (myMonth + 11) % 12; 
}
function lastYear (myear, mmonth)
{
  var myYear = thisYear
  var myMonth = thisMonth
  if(arguments.length >= 1) { myYear = myear; } 
  if(arguments.length >= 2) { myMonth = mmonth; } 
  return (myMonth == 0)? myYear -1: myYear; 
}
function nextMonth (myear, mmonth)
{
  var myYear = thisYear
  var myMonth = thisMonth
  if(arguments.length >= 1) { myYear = myear; } 
  if(arguments.length >= 2) { myMonth = mmonth; } 
  return (myMonth +1) % 12; 
}
function nextYear (myear, mmonth)
{
  var myYear = thisYear
  var myMonth = thisMonth
  if(arguments.length >= 1) { myYear = myear; } 
  if(arguments.length >= 2) { myMonth = mmonth; } 
  return (myMonth == 11)? myYear + 1: myYear;
}
function shiftArray(myArray) 
{ 
  // since Array.shift() is missing or broken on some versions of MSIE
  // we fake it here. 
  if(-1 != navigator.appVersion.indexOf("MSIE")) 		{ 
	 var myVal = myArray[0];
	 for(i=0; i<(myArray.length -1); i++)
		{ myArray[i] = myArray[i+1];}
	 myArray.length = myArray.length -1; 
	 return myVal; 		} 
	 else return myArray.shift(); 
} 
function dispEvent(year,mon,mday)
{
  // finds the event string associated with
  // the date specified by the parameters
  // and writes the information into a 
  // pop-up window called winEvent
  // More or less defunct since we added
  // the overLIB library.
  var title = fullDate(year,mon,mday);
  var content = getEvent(year,mon,mday);
  winEvent = window.open('','winEvent','height=200,width=400,menubar=no,resizable=yes,scrollbars=yes,statusbar=no');
  winEvent.document.writeln('<HTML><HEAD><TITLE>', title, '</TITLE><BODY BGCOLOR="', colorMedBlue, '">');
  winEvent.document.writeln('<FONT SIZE=4 FACE="Arial"><B>', title, '</B><BR>', content);
  winEvent.document.writeln('<FORM><INPUT TYPE=BUTTON VALUE="Close Window" onClick="window.close()"></FORM>');
  winEvent.document.writeln('</FONT></BODY></HTML>');
  winEvent.document.close();
  winEvent.focus();
}
function addEvent(year,mon,mday,event)
{
  // generates a date string based on the
  // parameters and assigned that date to
  // the value 'event' in the events array
  // the format is a little sensitive, you
  // have to make sure that 'mon' is
  // something that Date.parse() can understand 
  if( year > "" ) { var dStr = mday + " " + mon + " " + year; }
  else { var dStr = mday + " " + mon; }
  if( events[dStr] > "" ) { events[dStr] = events[dStr] + "<hr>" + event; }
  else { events[dStr] = event; }
}
function isEvent(year,mon,mday)
{
  // if the event is found, return
  // the value of the element
  var dStr = mday + " " + mon + " " + year; 
  if(events[dStr] > "") { return events[dStr].replace(re,rpl); } 
  // check for recurring dates (any year)
  dStr = mday + " " + mon; 
  if(events[dStr] > "") { return events[dStr].replace(re,rpl); } 
  return "";
}
function addHoliday(year,mon,mday,holiday)
{
  // generates a date string based on the
  // parameters and assigned that date to
  // the value 'holiday' in the holidays array
  // the format is a little sensitive, you
  // have to make sure that 'mon' is
  // something that Date.parse() can understand 
  if( year > "" ) { var dStr = mday + " " + mon + " " + year; }
  else { var dStr = mday + " " + mon; }
  if( holidays[dStr] > "" ) { holidays[dStr] = holidays[dStr] + "<hr>" + holiday; }
  else { holidays[dStr] = holiday; }
}
function isHoliday(year,mon,mday)
{ 
  // it the date on the list? 
  // the format is a little sensitive, you
  // have to make sure that 'mon' is
  // something that Date.parse() can understand 
  var dStr = mday + " " + mon + " " + year; 
  if(holidays[dStr]) { return holidays[dStr].replace(re,rpl); } 
  // check for recurring dates (any year)
  dStr = mday + " " + mon; 
  if(holidays[dStr]) { return holidays[dStr].replace(re,rpl); } 
  return false;
} 
function isWeekend( year, mon, mday) 
{ 
  var mDate = new Date(mday + " " + mon + " " + year); 
  return ( ( 0 == mDate.getDay())  ||  ( 6 == mDate.getDay()  )); 
} 
function calculateWorkDays( startDate, endDate) 
{ 
  // called with 2 Date Objects as arguments. 
  // calculates the number of workdays between two dates by adding up the 
  // number of days and subtracting weekends and holidays. 
  var myEndDate = canonicalDate(endDate.getDate(), endDate.getMonth(), endDate.getFullYear()); 
  var counter = 0; 
  var mDay = startDate.getDate(); 
  var mMonth = startDate.getMonth(); 
  var mYear  = startDate.getFullYear(); 
  while  (canonicalDate(mDay, mMonth, mYear) <= myEndDate)
    { 
		if(! ( isHoliday(mYear,months[mMonth],mDay) ||	 isWeekend(mYear,months[mMonth],mDay)) ) 
		{ counter++; } 

      // increment the date
      // are we at the end of a month ? 
      var omDay = mDay;
      var omMonth = mMonth; 
      var omYear = mYear; 
      mDay = isLeapYear(mYear) ? 
		  ((mDay >= leapdays[mMonth]) ? 1 : mDay+1):
		  ((mDay >= yeardays[mMonth]) ? 1 : mDay+1);
      // do we need to increment the month ? 
      mMonth = (mDay == 1) ?  (mMonth +1) % 12: mMonth; 
      // do we need to increment the year? 
      mYear = ( (mDay == 1) && (mMonth == 0)) ? mYear + 1: mYear;
      // startDate = new Date(mDay, mMonth, mYear); 
    }
  return counter; 
} 

function writeCalendar(myYear, myMonth, sday, eday)
{ 
  // writes a calendar and returns HTML for myMonth myYear. 
  // sday and eday are optional values indicating the range of dates 
  // to be set in bold. 
  // get a new date for the first day of the month the user is looking at
  var calDate = new Date( myYear,  myMonth, 1, 0,0,0,0 ); 
  // how many days are in the month ? 
  var mDays = isLeapYear(myYear) ? leapdays[myMonth]: yeardays[myMonth]; 
  var i = 0; 
  // what day of the week does the month start on? 
  var wkDay = calDate.getDay(); 
  var dateBgAtt = ""; 
  var dateFontTag = "";
  var fontCloseTag = ""; 
  var dateLinkTag = "";
  var linkCloseTag = "";
  var boldTag = "";
  var unBoldTag = "";
  var tHoliday = "";
  var tEvent = "";
  // if the function was called with the sday and eday arguments, then the 
  // caller wants a range of dates written in bold 
  var useBold = arguments.length >= 4 ? true: false; 
  // text to return
  var txt = "";
  
  // write the header for the calendar ( month and year ) 
  txt = txt + "<CENTER>\n<TABLE STYLE='border: 1 solid " + calHdrBGColor + "' BORDER=0 CELLPADDING=6 CELLSPACING=0 WIDTH=\"80%\">\n";
  // set the background color in the TR tag
  txt = txt + "<TR BGCOLOR=\"" + calHdrBGColor + "\">";
  // set the FG color using a FONT tag, better would be style sheets 
  txt = txt + 
		"<TD COLSPAN=5><FONT COLOR=\"" + calHdrFGColor + "\"><STRONG>" +
		longmonths[myMonth] +
		"</STRONG></FONT></TD>" + "<TD COLSPAN=2><FONT COLOR=\"" + calHdrFGColor + "\"><STRONG>" +
		myYear + 
		"</STRONG></FONT></TD></TR>\n"; 
  // write the abbreviations for days of the week into the top line of the calendar
  txt = txt + "<TR BGCOLOR=\"" + dowBGColor + "\">"; 
  for(i=0; i< 7; i++) 
	 { txt = txt + "<TD ALIGN=CENTER><FONT COLOR=\"" + dowFGColor +
						 "\">" + dow[((i+calStartDOW)%7)] + 
						 "</FONT></TD>";}
  txt = txt + "</TR>\n";
  // start the first line with blank spaces until we get to the first day of the month
  txt = txt + "<TR ALIGN='RIGHT'>"; 
  for(i=0 ; i < ((7 - calStartDOW + wkDay)%7); i++) 
	 { txt = txt + "<TD>&nbsp\;&nbsp\;&nbsp\;</TD>";	 }
  // since javascript doesn't do modulus on negative numbers, 
  // add 7 to anything that might be negative
  var cmdate = i - ((7 - calStartDOW + wkDay)%7); 
  // write the weekdays
  for( i=i; cmdate < mDays ; i++) 
	 {  
		// what is the date ? 
		cmdate++; 
		// if we have reached the end of a week, start another one
		if(0 == (i%7)){ txt = txt + "</TR>\n<TR ALIGN='RIGHT'>"; } 

		// reset all parameters
		dateBgAtt = ""; 
		dateFontTag = "";
		fontCloseTag = "";
		dateLinkTag = "";
		linkCloseTag = "";
		boldTag = ""; 
		unBoldTag = "";

		// if the date is a weekend, set it in color
		if( isWeekend(calDate.getFullYear(),months[calDate.getMonth()],cmdate) )
		  { 	 
			 dateBgAtt = "BGCOLOR=\"" + wkdBGColor + "\""; 
			 dateFontTag = "<FONT COLOR=\"" +  wkdFGColor +  "\">";
			 fontCloseTag = "</FONT>";
		  }

		// get holiday/event values
		tHoliday = isHoliday(calDate.getFullYear(),months[calDate.getMonth()],cmdate)
		tEvent = isEvent(calDate.getFullYear(),months[calDate.getMonth()],cmdate)

		// if the date is a holiday, use the overLIB codes
		if(tHoliday)
		  { 	 
			 dateBgAtt = "BGCOLOR=\"" + holBGColor + "\""; 
			 dateFontTag = "<FONT COLOR=\"" +  holFGColor +  "\">";
			 fontCloseTag = "</FONT>";
			 dateLinkTag = "<A CLASS=\"calHoliday\" HREF=\"javascript:void(0)\" onMouseOver=\"overlib('" +
			 	tHoliday + "', WIDTH,-1, CAPTION, '<NOBR>" +
			 	fullDate(calDate.getFullYear(),months[calDate.getMonth()],cmdate) + "</NOBR>')\" onMouseOut=\"nd()\"> ";
			 linkCloseTag = "</A>";
		  }

		// check for events on this day
		if(tEvent)
		  {
			 dateBgAtt = "BGCOLOR=\"" + eventBGColor + "\"" + (tHoliday ? " CLASS=\"calHoliday\"" : "")
			 dateFontTag = "<FONT COLOR=\"" +  eventFGColor +  "\">";
			 fontCloseTag = "</FONT>";
			 dateLinkTag = "<A CLASS=\"calEvent\" HREF=\"javascript:void(0)\" onMouseOver=\"overlib('" +
			 	(tHoliday ? tHoliday + "<hr>" : "") + tEvent + "', CAPTION, '<NOBR>" +
			 	fullDate(calDate.getFullYear(),months[calDate.getMonth()],cmdate) + "</NOBR>')\" onMouseOut=\"nd()\"> ";
			 linkCloseTag = "</A>";
			////////////////////////////////////////////////////////////
			// Replaced the dispEvent method of opening an external
			// window with the overLIB library floating captions.
			//
			// dateLinkTag = "<A HREF=\"javascript:dispEvent(" + calDate.getFullYear() + 
			//   ",'" + months[calDate.getMonth()] + "'," + cmdate + ")\" CLASS=\"calEvent\">";
			// linkCloseTag = "</A>";
			//
		  }

		// set the days off in bold
		if( ( useBold )  && (cmdate >= sday) && (cmdate <= eday))
		  {
			 boldTag = "<STRONG><EM>"; 
			 unBoldTag = "</EM></STRONG>";
		  } 

		// write the day number
		txt = txt + "<TD " + dateBgAtt + " >" + dateFontTag + boldTag + dateLinkTag + (cmdate < 10 ? "&nbsp\;":"") + cmdate + linkCloseTag + unBoldTag + fontCloseTag + "</TD>";
	 }
  while(0 != (i%7)) { txt = txt + "<TD>&nbsp\;&nbsp\;&nbsp\;</TD>"; i++; }
  txt = txt + "</TR>"; 
  txt = txt + "</TABLE></CENTER>\n"; 

  return txt;
} 
function drawCalendar( ourTarget, ourYear, ourMonth, startDay, endDay)
{
  // serves as a wrapper for writeCalendar() 
  // if you want to do anything special, such as changing the colors, 
  // or opening a special window, you can do it here before calling writeCalendar(). 
  // sday and eday are optional values indicating the range of dates 
  // to be set in bold. 
  // arguments: 
  // ourTarget - document to write to 
  // ourYear, ourMonth - integers, typically returned by Date.getMonth() and Date.getDate()
  // startDay, endDay  - optional start and end days for bolding 
  var myMonth = myDate.getMonth(); 
  var myYear  = myDate.getFullYear(); 
  var target = document; 
  // strictly speaking, all the arguments are optional. 
  // if you only want this month's calendar, called drawCalendar() with no args. 
  if(arguments.length >= 1) { target = ourTarget; }
  if(arguments.length >= 2) { myYear = ourYear; } 
  if(arguments.length >= 3) { myMonth = ourMonth; } 
	 { target.write(writeCalendar(myYear, myMonth, startDay, endDay)); }
} 
function getURLArgs(caseBool) 
{ 
  // gets the arguments the page was loaded with - that is, 
  // everything after the first '?' 
  // parameters:
  // caseBool - set to true or positive integer to force lowercase 
  // for parameter values 
  // 
  // values are ALWAYS case sensitive 
  // 
  var casefree = ( (true == caseBool) || (caseBool >= 1)) ? true: false; 
  var args  = new Object(); 
  var query = location.search.substring(1); 
  //  alert(query); 
  var pairs = query.split("&"); 
  for(var i = 0; i< pairs.length; i++) 
	 { 
		pairs[i]= unescape(pairs[i]); 
		var pos=pairs[i].indexOf('='); 
		if(-1 == pos) continue; 
		var argname; 
		if(true != casefree) { argname = pairs[i].substring(0,pos); } 
		else { argname = pairs[i].substring(0,pos).toLowerCase(); } 
		var value = pairs[i].substring(pos+1); 
		args[argname] = value; 
	 } 
  return args; 
} 



///////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////
// LAYER CODE
//
var calendarScript = '';	// Used when updating layers


function layerCalendars(myear, mmonth)
{ 
  // puts three calendars on the page from which it 
  // was called. (last month, this month, next month) 
  // Params:
  // myear  -  the year for the center calendar
  // mmonth -  the month for the center calendar
  var myMonth = thisMonth; 
  var myYear  = thisYear; 
  if(arguments.length >= 1) { myYear = myear; } 
  if(arguments.length >= 2) { myMonth = mmonth; } 

  // text to display
  var txt = formatCalendars(myYear,myMonth);

  // Define browser-specific layer for Calendar
  if (document.layers) {                     // NS4+
	document.write('<table border=0 cellpadding=0 cellspacing=0 width="100%"><tr><td>');
	document.write('<ilayer id="calDiv" above="overDiv"><layer id="cal2Div">' + txt + '&nbsp;</layer></ilayer>');
	document.write('</td></tr></table>');
	calendarScript = 'document.calDiv.document.cal2Div.document.write(txt);' +
	                 'document.calDiv.document.cal2Div.document.close();';

  } else if (document.all) {                   // IE4+
	document.write('<div id="calDiv">' + txt + '</div>');
	calendarScript = 'calDiv.innerHTML = txt;';
  }
} 

function updateCalendars(myear, mmonth)
{ 
  var myMonth = thisMonth; 
  var myYear  = thisYear; 
  if(arguments.length >= 1) { myYear = myear; } 
  if(arguments.length >= 2) { myMonth = mmonth; } 
  // text to display
  var txt = formatCalendars(myYear,myMonth);
  eval(calendarScript);
} 

function formatCalendars(myYear, myMonth)
{
  // text to display
  var txt = ''
  
  // setup next/previous buttons
  var previousString = '<A CLASS="calHoliday" HREF="javascript:void(0)" onClick="return moveBack()"><FONT FACE="Arial Bold" SIZE=4><B>[&lt\;&lt\;]</B></FONT></A>';
  var nextString =     '<A CLASS="calHoliday" HREF="javascript:void(0)" onClick="return moveForward()"><FONT FACE="Arial" SIZE=4><B>[&gt\;&gt\;]</B></FONT></A>';

  // header and previous button
  txt = txt + '<P><CENTER>\n';
  txt = txt + '<TABLE WIDTH="' + globalCalWidth + '"><TR VALIGN=TOP>\n<TD>';
  txt = txt + previousString;
  txt = txt + '</TD>\n<TD WIDTH="30%">'; 

  // calendar #1
  var isThisMonth = ((lastMonth() == myDate.getMonth()) && (lastYear() == myDate.getFullYear())); 
  txt = txt + writeCalendar(lastYear(), lastMonth(), (isThisMonth ? myDate.getDate():0), (isThisMonth ? myDate.getDate():0)); 
  txt = txt + '</TD>\n<TD WIDTH="30%">';

  // calendar #2
  isThisMonth = ((myMonth == myDate.getMonth()) && (myYear == myDate.getFullYear())); 
  txt = txt + writeCalendar(myYear, myMonth, (isThisMonth ? myDate.getDate():0), (isThisMonth ? myDate.getDate():0)); 
  txt = txt + '</TD>\n<TD WIDTH="30%">';

  // calendar #3
  isThisMonth = ((nextMonth() == myDate.getMonth()) && (nextYear() == myDate.getFullYear())); 
  txt = txt + writeCalendar(nextYear(), nextMonth(), (isThisMonth ? myDate.getDate():0), (isThisMonth ? myDate.getDate():0)); 
  txt = txt + '</TD>\n<TD>';

  // footer and next button
  txt = txt + nextString;
  txt = txt + '</TD></TR></TABLE>\n';
  txt = txt + '</CENTER>\n';

  return txt;
}

function moveBack()
{
  var myMonth = thisMonth;
  var myYear = thisYear;
  thisMonth = lastMonth(myYear,myMonth);
  thisYear = lastYear(myYear,myMonth);
  updateCalendars();
  return false;
}
function moveForward()
{
  var myMonth = thisMonth;
  var myYear = thisYear;
  thisMonth = nextMonth(myYear,myMonth);
  thisYear = nextYear(myYear,myMonth);
  updateCalendars();
  return false;
}



///////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////
// OUTDATED CODE
//
// This code consists of old function manifestations that shouldn't be used
//

function newCalendars(myear, mmonth)
{ 
  // puts three calendars on the page from which it 
  // was called. (last month, this month, next month) 
  // Params
  // 
  // when called with 2 arguments
  // myear  -  the year for the center calendar
  // mmonth -  the month for the center calendar
  var myMonth = thisMonth; 
  var myYear  = thisYear; 
  if(arguments.length == 2) { myMonth = mmonth; myYear = myear; } 
  // it's surprising how many coders don't use modular arithmetic to 
  // do date and time. Javascript doesn't understand negative numbers in
  // positive modulus, so we add 11 instead of subtracting 1. 
  var lastMonth = (myMonth + 11) % 12; 
  var lmYear    = (myMonth == 0)? myYear -1: myYear; 
  var nextMonth = (myMonth +1) % 12; 
  var nmYear    = (myMonth == 11)? myYear + 1: myYear;

  //////////////////////////////////////////////////////////////////////////////
  // SETUP the NEXT and PREVIOUS buttons
  // 
  // note that we create a form and use the document URL as the target,
  // with the METHOD of GET. 
  // 
  // if we were writing the calendars into a separate window or frame, 
  // we wouldn't need to reload; we could just change the global values 
  // for thisYear, thisMonth, and calStartDOW, and refresh that window
  // by calling newCalendars() with that window as target. 
  // 
  var docName = location.pathname; 
  var previousString = "<INPUT TYPE=\"BUTTON\" VALUE=\"&lt;&lt;\"" +
	 " onClick='document.newCal.month.value=\"" + lastMonth+  "\"; " + 
	 "document.newCal.year.value=" + lmYear + "; " + 
	 "submit();' > "; 
  var nextString = "<INPUT TYPE=\"BUTTON\" VALUE=\"&gt;&gt;\"" +
	 " onClick='document.newCal.month.value=" + nextMonth+  "; " + 
	 "document.newCal.year.value=" + nmYear + "; " + 
	 "submit();' > "; 

  document.write("<FORM NAME=\"newCal\" METHOD=\"GET\" ACTION=\"" + docName + "\">");
  document.write("<INPUT TYPE=\"hidden\" NAME=\"month\" VALUE=\"" + myMonth +"\">");
  document.write("<INPUT TYPE=\"hidden\" NAME=\"year\" VALUE=\"" + myYear +"\">");
  document.write("<CENTER>"); 

  ///////////////////////////////////////////////////////////////////////////
  // WRITE CALENDAR #1
  // 
  document.write("<TABLE ALIGN=\"TOP\" WIDTH=\"" + globalCalWidth + "\"><TR VALIGN=\"TOP\"><TD>");
  document.write(previousString + "</TD><TD>"); 
  var isThisMonth = ((lastMonth == myDate.getMonth())&& (lmYear==myDate.getFullYear())); 
  document.write(writeCalendar(lmYear, lastMonth,
					(isThisMonth ? myDate.getDate():0), 
					(isThisMonth ? myDate.getDate():0)
					)); 
  isThisMonth = ((myMonth == myDate.getMonth())&& (myYear==myDate.getFullYear())); 
  document.write("</TD>\n<TD>");
  ///////////////////////////////////////////////////////////////////////////
  // WRITE CALENDAR #2
  // 
  document.write(writeCalendar(myYear, myMonth, 
					(isThisMonth? myDate.getDate():0), 
					(isThisMonth? myDate.getDate():0))); 
  document.write("</TD>\n<TD>");
  ///////////////////////////////////////////////////////////////////////////
  // WRITE CALENDAR #3
  // 
  isThisMonth = ((nextMonth == myDate.getMonth())&& (nmYear==myDate.getFullYear())); 
  document.write(writeCalendar(nmYear, nextMonth,
					(isThisMonth ? myDate.getDate():0), 
					(isThisMonth ? myDate.getDate():0))); 
  document.write("</TD><TD>" + nextString); 
  document.write("</TD></TR></TABLE>\n");

  //  Uncomment this to display the US/Euro style radio buttons 
  //  document.write("<INPUT TYPE=\"hidden\" NAME=\"startOn\" VALUE=\"" + calStartDOW +"\">");  
  //  var calStyleString = "" + 
  //	 "<SMALL>calendar style: US" + 
  //	 "<INPUT TYPE='radio' NAME='calStyle' VALUE='us'" +
  //	 ((calStartDOW == 0)? " CHECKED " : " ") + 
  //	 " onClick='document.newCal.startOn.value=\"0\"; " +  
  //	 "document.newCal.submit();'>  " +
  //	 "" + 
  //	 "Euro <INPUT TYPE='radio' NAME='calStyle' VALUE='euro'" +
  //	 ((calStartDOW == 1)? " CHECKED " : " ") + 
  //	 " onClick='document.newCal.startOn.value=\"1\"; " +  
  //	 "submit();'></SMALL>"; 
  // document.write(calStyleString); 

  document.write("</CENTER><P>\n"); 
  document.write("</FORM>"); 

} 


function writeCalendar_OLD(target, myYear, myMonth, sday, eday)
{ 
  // writes a calendar to target  for myMonth myYear. 
  // sday and eday are optional values indicating the range of dates 
  // to be set in bold. 
  // get a new date for the first day of the month the user is looking at
  var calDate = new Date( myYear,  myMonth, 1, 0,0,0,0 ); 
  // how many days are in the month ? 
  var mDays = isLeapYear(myYear) ? leapdays[myMonth]: yeardays[myMonth]; 
  var i = 0; 
  // what day of the week does the month start on? 
  var wkDay = calDate.getDay(); 
  var dateBgAtt = ""; 
  var dateFontTag = "";
  var fontCloseTag = ""; 
  var dateLinkTag = "";
  var linkCloseTag = "";
  var boldTag = "";
  var unBoldTag = ""; 
  // if the function was called with the sday and eday arguments, then the 
  // caller wants a range of dates written in bold 
  var useBold = arguments.length >= 5 ? true: false; 
  // write the header for the calendar ( month and year ) 
  target.write("<CENTER>\n<TABLE BORDER=0 CELLPADDING=6 CELLSPACING=0 WIDTH=\"80%\">\n");
  // set the background color in the TR tag
  target.write("<TR BGCOLOR=\"", calHdrBGColor,  "\">");
  // set the FG color using a FONT tag, better would be style sheets 
  target.write(
		"<TD COLSPAN=5><FONT COLOR=\"", calHdrFGColor,  "\"><STRONG>",
		longmonths[myMonth],
		"</STRONG></FONT></TD>","<TD COLSPAN=2><FONT COLOR=\"", calHdrFGColor, "\"><STRONG>", 	
		myYear, 
		"</STRONG></FONT></TD></TR>\n"
		); 
  // write the abbreviations for days of the week into the top line of the calendar
  target.write("<TR BGCOLOR=\"", dowBGColor, "\">"); 
  for(i=0; i< 7; i++) 
	 { target.write("<TD ALIGN=CENTER><FONT COLOR=\"", dowFGColor,   
						 "\">", dow[((i+calStartDOW)%7)], 
						 "</FONT></TD>");}
  target.write("</TR>\n");
  // start the first line with blank spaces until we get to the first day of the month
  target.write("<TR ALIGN='RIGHT'>"); 
  for(i=0 ; i < ((7 - calStartDOW + wkDay)%7); i++) 
	 { target.write("<TD>&nbsp\;&nbsp\;&nbsp\;</TD>");	 }
  // since javascript doesn't do modulus on negative numbers, 
  // add 7 to anything that might be negative
  var cmdate = i - ((7 - calStartDOW + wkDay)%7); 
  // write the weekdays
  for( i=i; cmdate < mDays ; i++) 
	 {  
		// what is the date ? 
		cmdate++; 
		// if we have reached the end of a week, start another one
		if(0 == (i%7)){ target.write("</TR>\n<TR ALIGN='RIGHT'>"); } 

		// reset all parameters
		dateBgAtt = ""; 
		dateFontTag = "";
		fontCloseTag = "";
		dateLinkTag = "";
		linkCloseTag = "";
		boldTag = ""; 
		unBoldTag = "";

		// if the date is a weekend, set it in color
		if( isWeekend(calDate.getFullYear(),months[calDate.getMonth()],cmdate) )
		  { 	 
			 dateBgAtt = "BGCOLOR=\"" + wkdBGColor + "\""; 
			 dateFontTag = "<FONT COLOR=\"" +  wkdFGColor +  "\">";
			 fontCloseTag = "</FONT>";
		  }

		// if the date is a holiday, use the overLIB codes
		if( isHoliday(calDate.getFullYear(),months[calDate.getMonth()],cmdate) )
		  { 	 
			 dateBgAtt = "BGCOLOR=\"" + holBGColor + "\""; 
			 dateFontTag = "<FONT COLOR=\"" +  holFGColor +  "\">";
			 fontCloseTag = "</FONT>";
			 dateLinkTag = "<A CLASS=\"calHoliday\" HREF=\"javascript:void(0)\" onMouseOver=\"overlib('" +
			 	isHoliday(calDate.getFullYear(),months[calDate.getMonth()],cmdate) + "', WIDTH,-1, CAPTION, '<NOBR>" +
			 	fullDate(calDate.getFullYear(),months[calDate.getMonth()],cmdate) + "</NOBR>')\" onMouseOut=\"nd()\">";
			 linkCloseTag = "</A>";
		  }

		// check for events on this day
		if( isEvent(calDate.getFullYear(),months[calDate.getMonth()],cmdate) )
		  {
			 dateBgAtt = "BGCOLOR=\"" + eventBGColor + "\""; 
			 dateFontTag = "<FONT COLOR=\"" +  eventFGColor +  "\">";
			 fontCloseTag = "</FONT>";
			 dateLinkTag = "<A CLASS=\"calEvent\" HREF=\"javascript:void(0)\" onMouseOver=\"overlib('" +
			 	isEvent(calDate.getFullYear(),months[calDate.getMonth()],cmdate) + "', CAPTION, '<NOBR>" +
			 	fullDate(calDate.getFullYear(),months[calDate.getMonth()],cmdate) + "</NOBR>')\" onMouseOut=\"nd()\">";
			 linkCloseTag = "</A>";
			////////////////////////////////////////////////////////////
			// Replaced the dispEvent method of opening an external
			// window with the overLIB library floating captions.
			//
			// dateLinkTag = "<A HREF=\"javascript:dispEvent(" + calDate.getFullYear() + 
			//   ",'" + months[calDate.getMonth()] + "'," + cmdate + ")\" CLASS=\"calEvent\">";
			// linkCloseTag = "</A>";
			//
		  }

		// set the days off in bold
		if( ( useBold )  && (cmdate >= sday) && (cmdate <= eday))
		  {
			 boldTag = "<STRONG><EM>"; 
			 unBoldTag = "</EM></STRONG>";
		  } 

		// write the day number
		target.write("<TD ", dateBgAtt, " >", dateFontTag, boldTag, dateLinkTag, cmdate, linkCloseTag, unBoldTag, fontCloseTag, "</TD>");
	 }
  while(0 != (i%7)) { 	target.write("<TD>&nbsp\;&nbsp\;&nbsp\;</TD>"); i++; }
  target.write("</TR>"); 
  target.write("</TABLE></CENTER>\n"); 
} 

function drawCalendar_OLD( ourTarget, ourYear, ourMonth, startDay, endDay)
{
  // serves as a wrapper for writeCalendar() 
  // if you want to do anything special, such as changing the colors, 
  // or opening a special window, you can do it here before calling writeCalendar(). 
  // sday and eday are optional values indicating the range of dates 
  // to be set in bold. 
  // arguments: 
  // ourTarget - document to write to 
  // ourYear, ourMonth - integers, typically returned by Date.getMonth() and Date.getDate()
  // startDay, endDay  - optional start and end days for bolding 
  var myMonth = myDate.getMonth(); 
  var myYear  = myDate.getFullYear(); 
  var target = document; 
  // strictly speaking, all the arguments are optional. 
  // if you only want this month's calendar, called drawCalendar() with no args. 
  if(arguments.length >= 1) { target = ourTarget; }
  if(arguments.length >= 2) { myYear = ourYear; } 
  if(arguments.length >= 3) { myMonth = ourMonth; } 
	 { writeCalendar(target, myYear, myMonth, startDay, endDay); }
}


