// Monthly Calendar
function monthlyCalendar(_instanceName, _htmlobjectId) 
{	
	
	// Constructor	
	this.instanceName = _instanceName;
	this.htmlobjectId = _htmlobjectId;	
	
	// Setup
	this.onClickClose = true;
	this.monthNames = new Array("jan","feb","mar","apr","may","jun","jul","aug","sep","oct","nov","dec"); 
	this.formInputObject = null;
	this.arguments = null;
	this.setFormInput = true;
	this.setEmptyInput = true;
	this.displayAllDays = false;
	this.availableDays = new Array();
	this.displayAvailableDays = false;
	this.excludeDays = new Array();
	this.hideExcludedDays = false;
	this.onSelected = null;
	this.appendHtml = '';
	this.availableDuration = 0;
	this.availableDurationType = 'month';
	
	// Display
	this.offsetX = 80;
	this.offsetY = 115;
	this.width = 400;
	this.height = 400;
	
	// Now date
	var nowDate = new Date();
	var nowWeekDay = nowDate.getDay()+1;
	var nowDay = nowDate.getDate();
	var nowMonth = nowDate.getUTCMonth() + 1;
	var nowYear = nowDate.getFullYear();	
	var nowMonthStartWeekDay = new Date(String(nowMonth)+"/1/"+String(nowYear)).getDay()+1;
	var nowMonthTotalDays = new Date(nowYear, nowMonth, 0).getDate();	
	
	// Until
	var untilDay = null;
	var untilMonth = null;
	var untilYear = null;
	
	// Selected date
	var selectedDate = new Date();
	var selectedDay = selectedDate.getDate();
	var selectedMonth = selectedDate.getUTCMonth() + 1;
	var selectedYear = selectedDate.getFullYear();	
	
	// Display date
	var displayDate = new Date();
	var displayWeekDay = displayDate.getDay()+1;
	var displayDay = displayDate.getDate();
	var displayMonth = displayDate.getUTCMonth() + 1;
	var displayYear = displayDate.getFullYear();	
	var displayMonthStartWeekDay = new Date(String(displayMonth)+"/1/"+String(displayYear)).getDay()+1;
	var displayMonthTotalDays = new Date(displayYear, displayMonth, 0).getDate();	
	
	
	// Get scrolling	
	getScrollingPosition = function() 
	{
		var position = new Array(0,0);
		if (typeof window.pageYOffset != 'undefined')
		{
			position = [
			window.pageXOffset,
			window.pageYOffset
			];
		}
		else if (typeof document.documentElement.scrollTop
		!= 'undefined' && document.documentElement.scrollTop > 0)
		{
			position = [
			document.documentElement.scrollLeft,
			document.documentElement.scrollTop
			];
		}
		else if (typeof document.body.scrollTop != 'undefined')
		{
			position = [
			document.body.scrollLeft,
			document.body.scrollTop
			];
		}
		return position;
	}	
	
	// Create holder Element
	this.createHTMLObject = function() 
	{
		if(!document.getElementById(this.htmlobjectId)) 
		{
			var htmlObject = document.createElement('div');
			htmlObject.id = this.htmlobjectId;
			document.getElementsByTagName('body')[0].appendChild(htmlObject);	
			
			// Calendar Object
			document.getElementById(this.htmlobjectId).innerHTML = '<div id="'+this.htmlobjectId+'_calendar"></div>'+this.appendHtml;
		}
	}
	
	// Popup
	this.popup = function (_mouseEvent,_formObject) 
	{		
		this.formInputObject = _formObject;
		
		// Arguments
		if(arguments.length == 3)
			this.arguments = arguments[2];
		else
			this.arguments = null;
		
		// Position
		_mouseEvent = (_mouseEvent) ? _mouseEvent : ((window.event) ? event : null);
				
		var scrollPostion = getScrollingPosition();		
		
		var posX = _mouseEvent.clientX-this.offsetX+scrollPostion[0];
		
		
		if(posX+this.width > document.getElementsByTagName('body')[0].clientWidth-5)
			posX = document.getElementsByTagName('body')[0].clientWidth-this.width-5;
		
		if(posX < 5)
			posX = 10;	
			
		var posY = _mouseEvent.clientY-this.offsetY+scrollPostion[1];		
		
		// Setup HTML Object
		this.createHTMLObject();		
		
		// Layout
		document.getElementById(this.htmlobjectId).style.top =  posY+"px";
		document.getElementById(this.htmlobjectId).style.left =  posX+"px";	
		document.getElementById(this.htmlobjectId).style.display = "block";		
		
		// Set form input date
		if(this.setFormInput && this.formInputObject.value.match(/[0-9]{1,2}\/[0-9]{1,2}\/[0-9]{2,4}/)) 
		{			
			// Parse
			var inputDate = this.formInputObject.value.split('/');
			
			// Set select
			selectedDate = new Date(inputDate[2], parseInt(inputDate[0])-1, inputDate[1]);
			selectedDay = selectedDate.getDate();
			selectedMonth = selectedDate.getUTCMonth() + 1;
			selectedYear = selectedDate.getFullYear();
			
			// Set display
			displayDate = new Date(inputDate[2], parseInt(inputDate[0])-1, inputDate[1]);
			displayWeekDay = displayDate.getDay()+1;
			displayDay = displayDate.getDate();
			displayMonth = displayDate.getUTCMonth() + 1;
			displayYear = displayDate.getFullYear();
			displayMonthStartWeekDay = new Date(String(displayMonth)+"/1/"+String(displayYear)).getDay()+1;			
			displayMonthTotalDays = new Date(displayYear, displayMonth, 0).getDate();
		}
		
		else if(this.setFormInput && !this.setEmptyInput)
			selectedYear = 0;	
			
		// Avilable duration		
		if(this.availableDuration > 0)
		{
			if(this.availableDurationType == 'year')
				var untilDate = new Date(nowYear+this.availableDuration,nowMonth-1,nowDay);
			else if(this.availableDurationType == 'day')
				var untilDate = new Date(nowYear,nowMonth-1,nowDay+this.availableDuration);
			else 
				var untilDate = new Date(nowYear,nowMonth-1+this.availableDuration,nowDay);			
			untilDay = untilDate.getDate();
			untilMonth = untilDate.getUTCMonth() + 1;
			untilYear = untilDate.getFullYear();	
		}
		
		// Insert
		if(this.hideExcludedDays)
			this.setExcludedDays(displayMonth, displayYear, this.arguments);
		else if(this.displayAvailableDays)
			this.setAvailableDays(displayMonth, displayYear, this.arguments);
		else 
			this.insertHTML();
			
		// On Popup	
		if(typeof this.onPopup == 'function')
			this.onPopup(_formObject);	
		
	}
	
	// Select day
	this.onDaySelect = function (_dayObject,_day, _month, _year) 
	{
		
		// Insert Input
		if(this.formInputObject != null)
			this.formInputObject.value = _month+'/'+_day+'/'+_year;	
		
		// On change function
		if (this.formInputObject != null && typeof this.formInputObject.onchange == "function") 
			this.formInputObject.onchange();		
		
		// Selected
		selectedDay = selectedDay;
		selectedMonth = displayMonth;
		selectedYear = displayYear;
		
		if(typeof this.onSelected == 'function')
			this.onSelected(_day, _month, _year, this.arguments);		
		
		if(this.onClickClose)
			document.getElementById(this.htmlobjectId).style.display = "none";
		else 
		{
			if(document.getElementById(this.htmlobjectId+'_selected'))
			{
				document.getElementById(this.htmlobjectId+'_selected').className = "day";
				document.getElementById(this.htmlobjectId+'_selected').id = null;
			}
			_dayObject.id = this.htmlobjectId+'_selected';
			_dayObject.className = _dayObject.className+' selected';			
		}
		
	}	
	
	// Is day available
	this.isDayAvailable = function (_day) 
	{	
		for (var i = 0; i < this.availableDays.length; i++) 
			if(_day == this.availableDays[i]) 
				return true;						
		return false;	
	}	
	
	// Available days
	this.setAvailableDays = function (_month, _year) 
	{
		this.displayAvailableDays = true;	
		this.availableDays = Array();		
	}
	
	// Is day not available
	this.isDayExclude = function (_day, _month, _year) 
	{	
		// Set days
		for (var i = 0; i < this.excludeDays.length; i++) 
			if(_day == this.excludeDays[i]) 
				return true;
		
		// Available duration
		if(this.availableDuration > 0 && (_day >= untilDay && _month >= untilMonth && _year >= untilYear) || (_month > untilMonth && _year >= untilYear) || _year > untilYear)
			return true;							
		
		return false;	
	}
	
	// Excluded days
	this.setExcludedDays = function (_month, _year) 
	{
		this.hideExcludedDays = true;	
		this.excludeDays = Array();		
	}
	
	// Insert HTML
	this.insertHTML = function () 
	{			
		var dayCount = 1;
		var writeHtml = '<div class="holder">';			
		writeHtml += '<div class="monthPrev" onclick="'+this.instanceName+'.changeMonth(\'prev\')"></div>';
		writeHtml += '<div class="monthNameYear">'+this.monthNames[displayMonth-1]+'&nbsp;&nbsp;'+displayYear+'</div>';
		writeHtml += '<div class="monthNext" onclick="'+this.instanceName+'.changeMonth(\'next\')"></div>';
		writeHtml += '<div style="clear:both"></div>';
		writeHtml += '<span class="weekDay">S</span><span class="weekDay">M</span><span class="weekDay" >T</span><span class="weekDay" >W</span><span class="weekDay">Th</span><span class="weekDay">F</span><span class="weekDay">S</span>';
			
			// Days
			for (var i = 1; i <= 42; i++) 
			{
				if ((i==1)|| (i==8)|| (i==15)|| (i==22)|| (i==29)|| (i==36)) 
				{
					writeHtml +=  '<br style="clear:both" />';			
				}
				if ((dayCount <= displayMonthTotalDays) && (i >= displayMonthStartWeekDay)) 
				{
					if(!this.displayAllDays && ( (nowDay > dayCount && nowMonth == displayMonth && nowYear == displayYear) || (nowMonth > displayMonth && nowYear == displayYear) || nowYear > displayYear))
						writeHtml += '<span class="day past" onfocus="if(this.blur)this.blur();" >'+dayCount+'</span>';	
					else if(this.hideExcludedDays && this.isDayExclude(dayCount,displayMonth,displayYear))
						writeHtml += '<span class="day off" onfocus="if(this.blur)this.blur();" >'+dayCount+'</span>';	
					else if(dayCount == selectedDay && selectedMonth == displayMonth && selectedYear == displayYear && (!this.displayAvailableDays || (this.displayAvailableDays && this.isDayAvailable(dayCount)) ) ) 	
						writeHtml += '<span class="day selected" id="'+this.htmlobjectId+'_selected" onclick="'+this.instanceName+'.onDaySelect(this,'+dayCount+', '+displayMonth+', '+displayYear+');" onfocus="if(this.blur)this.blur();" >'+dayCount+'</span>';						
					else if(this.displayAvailableDays && !this.isDayAvailable(dayCount))
						writeHtml += '<span class="day off" onfocus="if(this.blur)this.blur();" >'+dayCount+'</span>';		
					else 
						writeHtml += '<span class="day" onclick="'+this.instanceName+'.onDaySelect(this,'+dayCount+', '+displayMonth+', '+displayYear+');" onfocus="if(this.blur)this.blur();" >'+dayCount+'</span>';	
					
					dayCount++;					
				} 
				else 
				{ 
					writeHtml += '<span class="empty">&nbsp;</span>';
				}
			}
			
		// End
		writeHtml += '</div>';		
		
		// Insert
		document.getElementById(this.htmlobjectId+'_calendar').innerHTML = writeHtml;
	}
	
	// Change Month
	this.changeMonth = function(_action) 
	{
		// Action
		if (_action == "prev")
			displayMonth--;
		
		else if (_action == "next") 
			displayMonth++;
			
		else if (_action == "return") 
		{ 
			displayMonth = selectedMonth;
			displayYear = selectedYear;
		}
		
		// Correct
		if (displayMonth == 0) 
		{
			displayMonth = 12;
			displayYear--;
		} 
		
		else if (displayMonth == 13) 
		{
			displayMonth = 1;
			displayYear++
		}
		
		// Set
		displayDate = new Date(displayYear, displayMonth, 0);
		displayWeekDay = displayDate.getDay()+1;
		displayDay = displayDate.getDate();
		displayMonthStartWeekDay = new Date(String(displayMonth)+"/1/"+String(displayYear)).getDay()+1;
		displayMonthTotalDays = new Date(displayYear, displayMonth, 0).getDate();	
		
		// Reset
		this.excludeDays = new Array();
		
		// Insert
		if(this.hideExcludedDays)
			this.setExcludedDays(displayMonth, displayYear, this.arguments);
		else if(this.displayAvailableDays)
			this.setAvailableDays(displayMonth ,displayYear, this.arguments);
		else 
			this.insertHTML();	
	}
	
	// Update
	this.update = function() 
	{		
		// Reset
		this.excludeDays = new Array();
		
		// Insert
		if(this.hideExcludedDays)
			this.setExcludedDays(displayMonth, displayYear, this.arguments);
		else if(this.displayAvailableDays)
			this.setAvailableDays(displayMonth, displayYear, this.arguments);
		else 
			this.insertHTML();	
	}
	
}


