/**
* File: MASCalendar.js
* Author: 2005 Gerhard Schaber, MakeArtChange webdesign
*/

/**
* Global variables
*/
MASCalendar_imagePath       = "images/";
MASCalendar_calendars       = new Array();
MASCalendar_isMouseOver     = false;
MASCalendar_mouseX          = 0;
MASCalendar_mouseY          = 0;
supportedByBrowser          = true;

/**
* The calendar constructor
*
* @access public
* @param string objName      Name of the object that you create
* @param string callbackFunc Name of the callback function
* @param string ctrl         Input control name which holds the date
* @param string pickertitle  Title for the date picker button
* @param string dateformat   date format
*/
	function MASCalendar(objName, callbackFunc, ctrl, pickertitle, dateformat)
	{
		/**
        * Properties
        */
		this.today            = new Date();
		this.seldate          = new Date();

		this.objName          = objName;
		this.callbackFunc     = callbackFunc;
		this.ctrl             = ctrl;
		this.pickertitle      = pickertitle;
		this.dateformat       = dateformat;
		this.layerID          = "MASCalendar_Calendar_" + MASCalendar_calendars.length;

		this.offsetX          = -100;
		this.offsetY          = -50;

		this.useMonthCombo    = true;
		this.useYearCombo     = true;
		this.yearComboRange   = 5;

		this.currentMonth     = this.today.getMonth();
		this.currentYear      = this.today.getFullYear();

        // main
		this.show             = MASCalendar_show;

        // set calendar properties
		this.setOffset        = MASCalendar_setOffset;
		this.getCalendar      = MASCalendar_getCalendar;
		this.hideCalendar     = MASCalendar_hideCalendar;
		this.showCalendar     = MASCalendar_showCalendar;

		this.getDaysInMonth   = MASCalendar_getDaysInMonth;
		this.onMouseOver      = MASCalendar_onMouseOver;
		this.parseDate        = MASCalendar_parseDate;

		/**
        * Constructor type code
        */
		MASCalendar_calendars[MASCalendar_calendars.length] = this;
		if (supportedByBrowser) {
			document.write('<a href="javascript: ' + this.objName + '.show()"><img src="' + MASCalendar_imagePath + 'MASCalendar.gif" border="0" title="' + this.pickertitle + '" align="middle"/></a>');
			document.write('<div class="MASCalendar" id="' + this.layerID + '" onmouseover="' + this.objName + '.onMouseOver(true)" onmouseout="' + this.objName + '.onMouseOver(false)"></div>');
		}
	}

/**
* Shows the calendar
*
* @access public
* @param integer month Optional month number (0-11)
* @param integer year  Optional year (YYYY format)
*/
	function MASCalendar_show()
	{
		var monthnames, numdays, thisMonth, firstOfMonth, cseldate;
		var ret, row, i, cssClass, linkHTML, previousMonth, previousYear;
		var nextMonth, nextYear, pprevImgHTML, pprevLinkHTML, prevImgHTML, prevLinkHTML, nextImgHTML, nextLinkHTML, nnextImgHTML, nnextLinkHTML;
		var monthComboOptions, monthCombo, yearComboOptions, yearCombo, html;

   		weekdays = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];

        if ( arguments[0] != null )
        {
            this.currentMonth = arguments[0];
        }
        if ( arguments[0] != null )
        {
            this.currentYear = arguments[1];
        }

        cseldate = document.getElementsByName(this.ctrl)[0].value;
        if (cseldate != null && cseldate != "")
        {
            this.seldate = this.parseDate( cseldate, this.dateformat );
        }

		monthnames = new Array("January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December");
		numdays    = this.getDaysInMonth(this.currentMonth, this.currentYear);

		thisMonth    = new Date(this.currentYear, this.currentMonth, 1);
		firstOfMonth = thisMonth.getDay();

		// First few blanks up to first day
		ret = new Array(new Array());
		for(i=0; i<firstOfMonth; i++){
			cssClass = "MASCalendar_day";
			if (ret[0].length==0 || ret[0].length==6)
			{
    			cssClass += "_we";
            }
			ret[0][ret[0].length] = '<td class="' + cssClass + '">&nbsp;</td>';
		}

		// Main body of calendar
		row = 0;
		i   = 1;
		while(i <= numdays){
			if(ret[row].length == 7){
				ret[++row] = new Array();
			}

			/**
            * Generate this cells' HTML
            */
			cssClass = "MASCalendar_day";
            if (i == this.seldate.getDate() && this.currentMonth == this.seldate.getMonth() && this.currentYear == this.seldate.getFullYear())
            {
                cssClass = "MASCalendar_selected";
            }
			if (ret[row].length==0 || ret[row].length==6)
			{
    			cssClass += "_we";
            }

			cssLinkClass = "MASCalendar_cell_normal";
            if (i == this.today.getDate() && this.currentMonth == this.today.getMonth() && this.currentYear == this.today.getFullYear())
            {
                cssLinkClass = "MASCalendar_cell_today";
            }

			ctrl = "'" + this.ctrl + "'";
			linkHTML = '<a href="javascript: ' + this.callbackFunc + '(' + i + ', ' + (Number(this.currentMonth) + 1) + ', ' + this.currentYear + ', ' + ctrl + '); ' + this.objName + '.hideCalendar()" class="' + cssLinkClass + '">' + (i++) + '</a>';
			ret[row][ret[row].length] = '<td align="center" class="' + cssClass + '">' + linkHTML + '</td>';
		}

		// Format the HTML
		for(i=0; i<ret.length; i++){
			ret[i] = ret[i].join("\n") + "\n";
		}

		ppreviousYear  = thisMonth.getFullYear() - 1;
		previousYear  = thisMonth.getFullYear();
		previousMonth = thisMonth.getMonth() - 1;
		if(previousMonth < 0){
			previousMonth = 11;
			previousYear--;
		}
		
		nnextYear  = thisMonth.getFullYear() + 1;
		nextYear  = thisMonth.getFullYear();
		nextMonth = thisMonth.getMonth() + 1;
		if(nextMonth > 11){
			nextMonth = 0;
			nextYear++;
		}

		pprevImgHTML  = '<img src="' + MASCalendar_imagePath + '/pprev.jpg" alt="<<" border="0" />';
		pprevLinkHTML = '<a href="javascript: ' + this.objName + '.show(' + thisMonth.getMonth() + ', ' + ppreviousYear + ')">' + pprevImgHTML + '</a>';
		prevImgHTML  = '<img src="' + MASCalendar_imagePath + '/prev.jpg" alt="<<" border="0" />';
		prevLinkHTML = '<a href="javascript: ' + this.objName + '.show(' + previousMonth + ', ' + previousYear + ')">' + prevImgHTML + '</a>';
		nextImgHTML  = '<img src="' + MASCalendar_imagePath + '/next.jpg" alt="<<" border="0" />';
		nextLinkHTML = '<a href="javascript: ' + this.objName + '.show(' + nextMonth + ', ' + nextYear + ')">' + nextImgHTML + '</a>';
		nnextImgHTML  = '<img src="' + MASCalendar_imagePath + '/nnext.jpg" alt="<<" border="0" />';
		nnextLinkHTML = '<a href="javascript: ' + this.objName + '.show(' + thisMonth.getMonth() + ', ' + nnextYear + ')">' + nnextImgHTML + '</a>';

		// Create month combobox
		if (this.useMonthCombo) {
			monthComboOptions = "";
			for (i=0; i<12; i++) {
				selected = (i == thisMonth.getMonth() ? 'selected="selected"' : '');
				monthComboOptions += '<option value="' + i + '" ' + selected + '>' + monthnames[i] + '</option>';
			}
			monthCombo = '<select name="months" onchange="' + this.objName + '.show(this.options[this.selectedIndex].value, ' + this.objName + '.currentYear)">' + monthComboOptions + '</select>';
		} else {
			monthCombo = monthnames[thisMonth.getMonth()];
		}
		
        // Create year combobox
		if (this.useYearCombo) {
			yearComboOptions = '';
			for (i = thisMonth.getFullYear() - this.yearComboRange; i <= (thisMonth.getFullYear() + this.yearComboRange); i++) {
				selected = (i == thisMonth.getFullYear() ? 'selected="selected"' : '');
				yearComboOptions += '<option value="' + i + '" ' + selected + '>' + i + '</option>';
			}
			yearCombo = '<select name="years" onchange="' + this.objName + '.show(' + this.objName + '.currentMonth, this.options[this.selectedIndex].value)">' + yearComboOptions + '</select>';
		} else {
			yearCombo = thisMonth.getFullYear();
		}

		html = '<table border="0" bgcolor="#eeeeee">';
		html += '<tr><td class="MASCalendar_header">' + pprevLinkHTML + prevLinkHTML + '</td><td nowrap colspan="5" align="center" class="MASCalendar_header">' + monthCombo + ' ' + yearCombo + '</td><td align="right" class="MASCalendar_header">' + nextLinkHTML + nnextLinkHTML + '</td></tr>';
		html += '<tr>';
		for (i=0; i<weekdays.length; i++)
		{
    		html += '<td class="MASCalendar_dayname">' + weekdays[i] + '</td>';
        }
		html += '</tr>';
		html += '<tr>' + ret.join('</tr>\n<tr>') + '</tr>';
		html += '</table>';

		this.getCalendar().innerHTML = html;
		if (!arguments[0] && !arguments[1]) {
			this.showCalendar();
    		this.getCalendar().style.top  = (MASCalendar_mouseY + this.offsetY) + 'px';
    		this.getCalendar().style.left = (MASCalendar_mouseX + this.offsetX) + 'px';
		}
	}

/**
* Sets the offset to the mouse position where the calendar appears at
*
* @param integer offsetX horizontal offset
* @param integer offsetY vertical offset
*/
	function MASCalendar_setOffset( offsetX, offsetY )
	{
        this.setOffsetX( offsetX );
		this.setOffsetY( offsetY );
	}

/**
* Returns the layer object
*/
	function MASCalendar_getCalendar()
	{
		var layerID = this.layerID;

		if ( document.getElementById( layerID ) ) {
			return document.getElementById( layerID );
		} else if ( document.all( layerID )) {
			return document.all( layerID );
		}
	}

/**
* Hides the calendar
*/
	function MASCalendar_hideCalendar()
	{
		this.getCalendar().style.visibility = "hidden";
	}

/**
* Shows the calendar
*/
	function MASCalendar_showCalendar()
	{
		this.getCalendar().style.visibility = "visible";
	}

/**
* Returns the number of days of a month
*
* @param integer month the month to get number of days of
* @param integer year  the year
*/
	function MASCalendar_getDaysInMonth( month, year )
	{
		monthdays = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];
		leapmonth = ( (month == 1) &&
                      ( (year % 4 == 0 && year % 100 != 0) || ( year % 400 == 0 ) ) );
		if ( leapmonth ) {
			return 29;
		} else {
			return ( monthdays[month] );
		}
	}

/**
* Save mouse over info
*
* @param boolean isMouseover true if mouse is over calendar; false otherwise
*/
	function MASCalendar_onMouseOver( isMouseover )
	{
		MASCalendar_isMouseOver = isMouseover;
		return true;
	}

/**
* Save mouse position
*/
    MASCalendar_oldOnMousemoveHandler = null;
    if ( document.onmousemove != null )
    {
        MASCalendar_oldOnMousemoveHandler = document.onmousemove;
    }

    function MASCalendar_onMouseMove( eventarg )
	{
		if ( supportedByBrowser ) {
			/* if ( eventarg != null ) {
                eventarg = event;
            } */
			if ( eventarg != null ) {
    			MASCalendar_mouseX = eventarg.pageX;
    			MASCalendar_mouseY = eventarg.pageY;
            }
            else
            {
    			MASCalendar_mouseX = event.clientX + document.body.scrollLeft;
    			MASCalendar_mouseY = event.clientY + document.body.scrollTop;
            }
		}
		if ( MASCalendar_oldOnMousemoveHandler != null )
		{
		  MASCalendar_oldOnmousemove( eventarg );
        }
	}

	document.onmousemove = MASCalendar_onMouseMove;

/**
* Hide calendars when clicking into another control
*/
    MASCalendar_oldOnclickHandler = null;
    if ( document.onclick != null )
    {
        MASCalendar_oldOnclickHandler = document.onclick;
    }

    function MASCalendar_onClick( eventarg )
	{
		if ( supportedByBrowser ) {
			/* if ( eventarg != null ) {
                eventarg = event;
            } */
			if( !MASCalendar_isMouseOver ){
				for( i=0; i<MASCalendar_calendars.length; ++i ){
					MASCalendar_calendars[i].hideCalendar();
				}
			}

		}
		if (MASCalendar_oldOnclickHandler != null)
		{
            MASCalendar_oldOnclickHandler( eventarg );
        }
	}

	document.onclick = MASCalendar_onClick;

/**
* Parse date
*/
function MASCalendar_parseDate( datestring, dateformat )
{
    var dtstring = datestring.replace(/\s/gi, "");
    var dtformat = dateformat.replace(/\s/gi, "").toLowerCase();
    var dateArray = dtstring.split(/[\.\-\/]/);
    var formatArray = dtformat.split(/[\.\-\/]/);
    var day = 0;
    var month = 0;
    var year = 0;
    var i;
    for (i=0; i<formatArray.length && i<dateArray.length; i++)
    {
        if (formatArray[i] == "d")
        {
            day = parseInt(dateArray[i]);
        }
        else if (formatArray[i] == "m")
        {
            month = parseInt(dateArray[i])-1;
        }
        else if (formatArray[i] == "y")
        {
            year = parseInt(dateArray[i]);
        }
    }
    var date = new Date( year, month, day );
    return date;
}



