/*
	Copyright 2009 Itamar Arjuan
	jsDatePick is distributed under the terms of the GNU General Public License.
*/
/*
	Configuration settings documentation:
	
	useMode (Integer) – Possible values are 1 and 2 as follows:
		1 – The calendar's HTML will be directly appended to the field supplied by target
		2 – The calendar will appear as a popup when the field with the id supplied in target is clicked.
	
	target (String) – The id of the field to attach the calendar to , usually a text input field when using useMode 2.
    
    targetButton (string) - The id of the button which should be used to display the calender when using useMode2.
	
	isStripped (Boolean) – When set to true the calendar appears without the visual design - usually used with useMode 1
	
	selectedDate (Object) – When supplied , this object tells the calendar to open up with this date selected already.
	
	yearsRange (Array) – When supplied , this array sets the limits for the years enabled in the calendar.
    
    disabledDates (Array) - When supplied, this array contains Date objects sets dates which cannot be selected by click. 
	
	limitToToday (Boolean) – Enables you to limit the possible picking days to today's date.
	
	cellColorScheme (String) – Enables you to swap the colors of the date's cells from a wide range of colors.
		Available color schemes: torqoise,purple,pink,orange,peppermint,aqua,armygreen,bananasplit,beige,
		deepblue,greenish,lightgreen,  ocean_blue <-default
	
	dateFormat (String) - Enables you to easily switch the date format without any hassle at all! 
		Should you not supply anything this field will default to: "%m-%d-%Y"
		
		Possible values to use in the date format:
		
		%d - Day of the month, 2 digits with leading zeros
		%j - Day of the month without leading zeros
		
		%m - Numeric representation of a month, with leading zeros
		%M - A short textual representation of a month, three letters
		%n - Numeric representation of a month, without leading zeros
		%F - A full textual representation of a month, such as January or March
		
		%Y - A full numeric representation of a year, 4 digits
		%y - A two digit representation of a year
		
		You can of course put whatever divider you want between them.
		
	weekStartDay (Integer) : Enables you to change the day that the week starts on.
		Possible values 0 (Sunday) through 6 (Saturday)
		Default value is 1 (Monday)
        
    multiselect (Boolean) - Enables the multiselection of the dates
		
	Note: We have implemented a way to change the image path of the img folder should you decide you want to move it somewhere else.
	Please read through the instructions on how to carefully accomplish that just in the next comment!
	
	Thanks for using my calendar !
	Itamar :-)
	
	itamar.arjuan@gmail.com
	
*/

var mariaFormCalenderStrings = {

    "en": {
        "MONTHS": ["January","February","March","April","May","June","July","August","September","October","November","December"],
        "DAYS_3": ["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],
        "MONTH_FWD": "Move a month forward",
        "MONTH_BCK": "Move a month backward",
        "YEAR_FWD": "Move a year forward",
        "YEAR_BCK": "Move a year backward",
        "CLOSE": "Close the calendar",
        "ERROR_2": "Internal Error, sorry.",
        "ERROR_4": "Internal Error, sorry."
    },
    "de": {
        "MONTHS": ["Januar","Februar","März","April","Mai","Juni","Juli","August","September","Oktober","November","Dezember"],
        "DAYS_3": ["So","Mo","Di","Mi","Do","Fr","Sa"],
        "MONTH_FWD": "Einen Monat weiter",
        "MONTH_BCK": "Einen Monat zurück",
        "YEAR_FWD": "Ein Jahr weiter",
        "YEAR_BCK": "Ein Jahr zurück",
        "CLOSE": "Kalender schliessen",
        "ERROR_2": "Interner Fehler, sorry.",
        "ERROR_4": "Interner Fehler, sorry."
    }

};

// The language array - change these values to your language to better fit your needs!
g_l = [];

/* Changing the image path: WARNING! */
/*
	The image path can be changed easily , however a few important
	safety steps must take place!
	
	CSS as a rule-of-thumb is always looking for relative image paths to where the CSS
	file resides. Meaning , if we place the css document of JsDatePick somewhere else
	Since some of the elements inside the CSS have  background:url(img/someimage.png);
	
	The system will try to look for a file under the same folder where the CSS file is.
	So pay careful attention when moving the CSS file somewhere else as the images folder
	must be relative to it. If you want to put the CSS document somewhere else and the images somewhere
	else - you HAVE to look and replace each background:url(img/someimage.png); to the new path you desire.
	
	That way you ensure risk free operation of images.
	For any further questions or support about this issue - please consider the feedback form
	at javascriptcalendar.org
	Thank you!
*/
g_jsDatePickImagePath = "img/";
g_jsDatePickDirectionality = "ltr";

g_arrayOfUsedJsDatePickCalsGlobalNumbers = [];
g_arrayOfUsedJsDatePickCals = [];
g_currentDateObject = {};
g_currentDateObject.dateObject = new Date();

g_currentDateObject.day = g_currentDateObject.dateObject.getDate();
g_currentDateObject.month = g_currentDateObject.dateObject.getMonth() + 1;
g_currentDateObject.year = g_currentDateObject.dateObject.getFullYear();

JsgetElem = function(id){ return document.getElementById(id); };

String.prototype.trim = function() {
	return this.replace(/^\s+|\s+$/g,"");
};
String.prototype.ltrim = function() {
	return this.replace(/^\s+/,"");
};
String.prototype.rtrim = function() {
	return this.replace(/\s+$/,"");
};
String.prototype.strpad=function(){
	return (!isNaN(this) && this.toString().length==1)?"0"+this:this;
};

JsDatePick = function(configurationObject){
	if (document.all){
		this.isie = true;
		this.iever = JsDatePick.getInternetExplorerVersion();
	} else {
		this.isie = false;
	}
	
	this.oConfiguration = {};
	this.oCurrentDay = g_currentDateObject;
    
    this.setConfiguration(configurationObject);
	
    this.monthsTextualRepresentation = g_l["MONTHS"];
	
	this.lastPostedDay = null;
	
	this.initialZIndex = 2;
	
	this.globalNumber = this.getUnUsedGlobalNumber();
	g_arrayOfUsedJsDatePickCals[this.globalNumber] = this;
	
	this.makeCalendar();
    
};

JsDatePick.getCalInstanceById=function(id){ return g_arrayOfUsedJsDatePickCals[parseInt(id,10)]; };

JsDatePick.getInternetExplorerVersion=function(){
	var rv = -1, ua, re;
	if (navigator.appName == 'Microsoft Internet Explorer'){
		ua = navigator.userAgent;
		re = new RegExp("MSIE ([0-9]{1,}[\.0-9]{0,})");
		if (re.exec(ua) != null){
		  rv = parseFloat( RegExp.$1 );
		}
		return rv;
	}
};

JsDatePick.prototype.setC = function(obj, aClassName){
	if (this.isie && this.iever > 7){
		obj.setAttribute("class", aClassName);
	} else {
		obj.className = aClassName;
	}
};

JsDatePick.prototype.setExclusiveClass = function (elem,myClass) {
    $.each(['imgDayNormal','imgDayDown', 'imgDayDisabled', 'imgDayOver'], function (i,val) {
        $(elem).removeClass(val);
    });
    $(elem).addClass(myClass);
}

JsDatePick.prototype.getUnUsedGlobalNumber = function(){
	
	var aNum = Math.floor(Math.random()*1000);
	
	while ( ! this.isUnique_GlobalNumber(aNum) ){
		aNum = Math.floor(Math.random()*1000);
	}
	
	return aNum;
};

JsDatePick.prototype.isUnique_GlobalNumber = function(aNum){
	var i;
	for (i=0; i<g_arrayOfUsedJsDatePickCalsGlobalNumbers.length; i++){
		if (g_arrayOfUsedJsDatePickCalsGlobalNumbers[i] == aNum){
			return false;
		}
	}
	return true;
};

JsDatePick.prototype.addOnSelectedDelegate = function(aDelegatedFunction){
	if (typeof(aDelegatedFunction) == "function"){
		this.addonSelectedDelegate = aDelegatedFunction;
	}
	return false;
};

JsDatePick.prototype.setOnSelectedDelegate = function(aDelegatedFunction){
	if (typeof(aDelegatedFunction) == "function"){
		this.onSelectedDelegate = aDelegatedFunction;
		return true;
	}
	return false;
};

JsDatePick.prototype.executeOnSelectedDelegateIfExists = function(){
	if (typeof(this.onSelectedDelegate) == "function"){
		this.onSelectedDelegate();
	}
	if (typeof(this.addonSelectedDelegate) == "function"){
		this.addonSelectedDelegate();
	}
};

JsDatePick.prototype.setRepopulationDelegate = function(aDelegatedFunction){
	if (typeof(aDelegatedFunction) == "function"){
		this.repopulationDelegate = aDelegatedFunction;
		return true;
	}
	return false;
};

//check if a date is disabled
JsDatePick.prototype.isDateIdealDisabled = function(aDate){
    var thisDate = new Date(this.currentYear,this.currentMonth - 1,parseInt(aDate));
        
    for (var i=0;i<this.oConfiguration.disabledDates.length;i++) {
        
        if (thisDate.getTime() == this.oConfiguration.disabledDates[i].getTime())
            return true;
    }
    
    return false;
};

//Add disabled dates
JsDatePick.prototype.addDisabledDates = function(dates){
   
    this.oConfiguration.disabledDates = this.oConfiguration.disabledDates.concat(this.clearDates(dates));
    
    //update the current dates
    this.writeDates(this.getDates());
}

//overwrite existing disabled dates with the passed array
JsDatePick.prototype.setDisabledDates = function(dates) {

    this.oConfiguration.disabledDates = this.clearDates(dates);
    
    //update the current dates
    this.writeDates(this.getDates());

}

//sets the passed dates to 00:00:00 hours
JsDatePick.prototype.clearDates = function(dates)
{
    var tempDates = new Array();
    for(var i = 0; i < dates.length; i++)
    {
        var temp = new Date(dates[i].getFullYear(), dates[i].getMonth(), dates[i].getDate());
        tempDates[i] = temp;
    }
    return tempDates;
}

//is for remove the selection from text
JsDatePick.prototype.clearSelection = function createSelection() {

    
    var txt = '';
     if (window.getSelection)
    {
        txt = window.getSelection();
             }
    else if (document.getSelection)
    {
        txt = document.getSelection();
            }
    else if (document.selection)
    {
        txt = document.selection.createRange().text;
            }
    
    if(txt.removeAllRanges)
        txt.removeAllRanges();
}


JsDatePick.prototype.setConfiguration = function(aConf){
	this.oConfiguration.isStripped 		= (aConf["isStripped"] != null) ? aConf["isStripped"] : false;
	this.oConfiguration.useMode    		= (aConf["useMode"] != null) ? aConf["useMode"] : 1;
	this.oConfiguration.selectedDate   	= (aConf["selectedDate"] != null) ? aConf["selectedDate"] : null;
	this.oConfiguration.target			= (aConf["target"] != null) ? aConf["target"] : null;
	this.oConfiguration.yearsRange		= (aConf["yearsRange"] != null) ? aConf["yearsRange"] : [1971,2100];
	this.oConfiguration.limitToToday	= (aConf["limitToToday"] != null) ? aConf["limitToToday"] : false;
	this.oConfiguration.field			= (aConf["field"] != null) ? aConf["field"] : false;
	this.oConfiguration.cellColorScheme = (aConf["cellColorScheme"] != null) ? aConf["cellColorScheme"] : "ocean_blue";
	this.oConfiguration.dateFormat		= (aConf["dateFormat"] != null) ? aConf["dateFormat"] : "%m-%d-%Y";
	this.oConfiguration.imgPath			= (aConf["imgPath"].length != null) ? aConf["imgPath"] : "img/";
	this.oConfiguration.weekStartDay   	= (aConf["weekStartDay"] != null) ? aConf["weekStartDay"] : 1;
    this.oConfiguration.multiselect     = (aConf["multiselect"] != null) ? aConf["multiselect"] : false;
    this.oConfiguration.targetButton    = (aConf["targetButton"] != null) ? aConf["targetButton"] : null;
    this.oConfiguration.disabledDates   = (aConf["disabledDates"] != null) ? this.clearDates(aConf["disabledDates"]) : null;
    this.oConfiguration.language   = (aConf["language"] != null) ? aConf["language"] : 'en';
    
    //choose the right language strings
    g_l = mariaFormCalenderStrings[this.oConfiguration.language];
    g_l["ERROR_1"] = g_l["ERROR_2"];
    g_l["ERROR_3"] = g_l["ERROR_4"];
	
	this.selectedDayObject = {};
	this.flag_DayMarkedBeforeRepopulation = false;
	this.flag_aDayWasSelected = false;
	this.lastMarkedDayObject = null;
	
	if (!this.oConfiguration.selectedDate){
		this.currentYear 	= this.oCurrentDay.year;
		this.currentMonth	= this.oCurrentDay.month;
		this.currentDay		= this.oCurrentDay.day;
	}
};

JsDatePick.prototype.resizeCalendar = function(){
	this.leftWallStrechedElement.style.height = "0px";
	this.rightWallStrechedElement.style.height = "0px";
	
	var totalHeight = this.JsDatePickBox.offsetHeight, newStrechedHeight = totalHeight-16;	
	
	if (newStrechedHeight < 0){
		return;
	}
	
	this.leftWallStrechedElement.style.height = newStrechedHeight+"px";
	this.rightWallStrechedElement.style.height = newStrechedHeight+"px";
	return true;
};

JsDatePick.prototype.closeCalendar = function(calendar){

    var globalCalNumber;
    
    if(calendar == undefined)
    {
        this.JsDatePickBox.style.display = "none";
        globalCalNumber = $(this.JsDatePickBox).attr("globalCalNumber");
    }
    else
    {
        calendar.JsDatePickBox.style.display = "none";
        globalCalNumber = $(calendar.JsDatePickBox).attr("globalCalNumber");
    }
	$(document).unbind('click',this.tmpCloseCal);
};

JsDatePick.prototype.populateFieldWithSelectedDate = function(){
    

    if(this.oConfiguration.multiselect == false)
    {
        
        JsgetElem(this.oConfiguration.target).value = this.getSelectedDayFormatted();
        if (this.lastPickedDateObject){
            delete(this.lastPickedDateObject);
        }
        this.lastPickedDateObject = {};
        this.lastPickedDateObject.day = this.selectedDayObject.day;
        this.lastPickedDateObject.month = this.selectedDayObject.month;
        this.lastPickedDateObject.year = this.selectedDayObject.year;
        
        this.closeCalendar();
    }
    else
    {
        if(JsgetElem(this.oConfiguration.target).value == "")
            JsgetElem(this.oConfiguration.target).value = this.getSelectedDayFormatted();
        else
            JsgetElem(this.oConfiguration.target).value += ", " + this.getSelectedDayFormatted();
            
        
    }
};

JsDatePick.prototype.makeCalendar = function(){
	var d = document, JsDatePickBox, clearfix, closeButton, inputElement, aSpan, aFunc;
	
	JsDatePickBox = d.createElement("div");
	clearfix		= d.createElement("div");
	closeButton		= d.createElement("div");
	
	this.setC(JsDatePickBox, "JsDatePickBox");
	this.setC(clearfix, "clearfix");
	this.setC(closeButton, "jsDatePickCloseButton");
	closeButton.setAttribute("globalNumber",this.globalNumber);


	$(closeButton).mouseup(function(){
        var gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText('');
        gRef.closeCalendar();
    });

	
	this.JsDatePickBox = JsDatePickBox;
	leftWall  	= d.createElement("div");
	rightWall 	= d.createElement("div");
	topWall		= d.createElement("div");
	bottomWall	= d.createElement("div");
	topCorner	 = d.createElement("div");
	bottomCorner = d.createElement("div");
	wall		 = d.createElement("div");

	this.setC(topCorner, "leftTopCorner");
	this.setC(bottomCorner, "leftBottomCorner");
	this.setC(wall, "leftWall");

	this.leftWallStrechedElement = wall;
	this.leftWall  = leftWall;
	this.rightWall = rightWall;



	topCorner	 = d.createElement("div");
	bottomCorner = d.createElement("div");
	wall		 = d.createElement("div");

	this.setC(topCorner, "rightTopCorner");
	this.setC(bottomCorner, "rightBottomCorner");
	this.setC(wall, "rightWall");

	this.rightWallStrechedElement = wall;



	if (this.oConfiguration.isStripped){
		this.setC(leftWall, "hiddenBoxLeftWall");
		this.setC(rightWall, "hiddenBoxRightWall");
	} else {
		this.setC(leftWall, "boxLeftWall");
		this.setC(rightWall, "boxRightWall");
	}


	JsDatePickBox.appendChild(this.getDOMCalendarStripped());


	if (!this.oConfiguration.isStripped){
		JsDatePickBox.appendChild(closeButton);
		JsDatePickBox.appendChild(topWall);
		JsDatePickBox.appendChild(bottomWall);
	}
	
	if (this.oConfiguration.useMode == 2){
		if (this.oConfiguration.target != false){
			if (typeof(JsgetElem(this.oConfiguration.target)) != null){
				inputElement = JsgetElem(this.oConfiguration.target);
		
				aSpan = document.createElement("span");
				inputElement.parentNode.replaceChild(aSpan,inputElement);
				aSpan.appendChild(inputElement);
		
				inputElement.setAttribute("globalNumber",this.globalNumber);
                
                if(this.oConfiguration.targetButton != null)
                {   
                    
                    var button = document.getElementById(this.oConfiguration.targetButton);
                    if(button != null)
                    {
                        $(button).click(function(){  JsDatePick.getCalInstanceById(inputElement.getAttribute("globalNumber")).showCalendar(); });
                    }
                }
                else
                {
                    $(inputElement).click(function(){ JsDatePick.getCalInstanceById(this.getAttribute("globalNumber")).showCalendar(); });
                    $(inputElement).focus(function(){ JsDatePick.getCalInstanceById(this.getAttribute("globalNumber")).showCalendar(); });
                }
				
				aSpan.style.position = "relative";
				this.initialZIndex++;
				
				JsDatePickBox.style.zIndex = this.initialZIndex.toString();
				JsDatePickBox.style.position = "absolute";
				JsDatePickBox.style.top = "18px";
				JsDatePickBox.style.left = "0px";
				JsDatePickBox.style.display = "none";
				aSpan.appendChild(JsDatePickBox);
				
				aFunc = new Function("g_arrayOfUsedJsDatePickCals["+this.globalNumber+"].populateFieldWithSelectedDate();");
				
				this.setOnSelectedDelegate(aFunc);
			} else {
				alert(g_l["ERROR_3"]);
			}
		}
        
	} else {
		if (this.oConfiguration.target != null){
			JsgetElem(this.oConfiguration.target).appendChild(JsDatePickBox);
			JsgetElem(this.oConfiguration.target).style.position = "relative";
			JsDatePickBox.style.position = "absolute";
			JsDatePickBox.style.top = "0px";
			JsDatePickBox.style.left = "0px";
			this.resizeCalendar();
			this.executePopulationDelegateIfExists();
		} else {
			alert(g_l["ERROR_4"]);
		}
	}
    
    //append the esc key press close function
    var object = this;
    $(d).keydown(function(e){
        if(e.keyCode == 27)
            object.closeCalendar();
    });
};

JsDatePick.prototype.determineFieldDate = function(){
	var aField,divider,dateMold,array,array2,i,dI,yI,mI,tflag=false,fflag=false;
	
	if (this.lastPickedDateObject){
		this.setSelectedDay({
			year:parseInt(this.lastPickedDateObject.year),
			month:parseInt(this.lastPickedDateObject.month,10),
			day:parseInt(this.lastPickedDateObject.day,10)
		});
	} else {
		aField = JsgetElem(this.oConfiguration.target);
		
		if (aField.value.trim().length == 0){
			this.unsetSelection();
			
			if (typeof(this.oConfiguration.selectedDate) == "object" && this.oConfiguration.selectedDate){
				this.setSelectedDay({
					year:parseInt(this.oConfiguration.selectedDate.year),
					month:parseInt(this.oConfiguration.selectedDate.month,10),
					day:parseInt(this.oConfiguration.selectedDate.day,10)
				});
			}
			
		} else {
			if (aField.value.trim().length > 5){
				divider = this.senseDivider(this.oConfiguration.dateFormat);
				dateMold = this.oConfiguration.dateFormat;
				array 	= aField.value.trim().split(divider);
				array2 	= dateMold.trim().split(divider);
				i=dI=yI=mI=0;
				
				for (i=0; i<array2.length; i++){
					switch (array2[i]){
						case "%d": case "%j": dI = i; break;
						case "%m": case "%n": mI = i; break;
						case "%M": mI = i; tflag=true; break;
						case "%F": mI = i; fflag=true; break;
						case "%Y": case "%y": yI = i;
					}
				}
				
				if (tflag){
					for (i=0; i<12; i++){
						if (g_l["MONTHS"][i].substr(0,3).toUpperCase() == array[mI].toUpperCase()){
							mI = i+1; break;
						}
					}
				} else if (fflag){
					for (i=0; i<12; i++){
						if (g_l["MONTHS"][i].toLowerCase() == array[mI].toLowerCase()){
							mI = i+1; break;
						}
					}
				} else {
					mI = parseInt(array[mI],10);
				}
				
				this.setSelectedDay({
					year:parseInt(array[yI],10),
					month:mI,
					day:parseInt(array[dI],10)
				});
			} else {
				this.unsetSelection();
				return;
			}
		}
	}
};

JsDatePick.prototype.senseDivider=function(aStr){return aStr.replace("%d","").replace("%j","").replace("%m","").replace("%M","").replace("%n","").replace("%F","").replace("%Y","").replace("%y","").substr(0,1);};

JsDatePick.prototype.sortDatesArray = function(dates){

}

/*quicksort functions*/
JsDatePick.prototype.quicksort = function (array) {
    function quick_sort(array)
    {
        qsort(array, 0, array.length);
    }

    function qsort(array, begin, end)
    {
        if(end-1>begin) {
            var pivot=begin+Math.floor(Math.random()*(end-begin));

            pivot=partition(array, begin, end, pivot);

            qsort(array, begin, pivot);
            qsort(array, pivot+1, end);
        }
    }

    var swap=function(array, a, b)
    {
        var tmp=array[a];
        array[a]=array[b];
        array[b]=tmp;
    }

    function partition(array, begin, end, pivot)
    {
        var piv=array[pivot];
        swap(array, pivot, end-1);
        var store=begin;
        var ix;
        for(ix=begin; ix<end-1; ++ix) {
            if(array[ix]<=piv) {
                swap(array, store, ix);
                ++store;
            }
        }
        swap(array, end-1, store);

        return store;
    }

    return quick_sort(array);
}


JsDatePick.prototype.parseSingleDate = function (dateString) {
    var tmp = dateString.trim().split(".");
    tmp[1] -=1;
    var tmpDate = new Date(tmp[2], tmp[1], tmp[0]);
    if (
        tmp[0]*1 == tmpDate.getDate() &&
        tmp[1]*1 == tmpDate.getMonth() &&
        tmp[2]*1 == tmpDate.getFullYear()
    ) {
        /*for (var i=0;i<this.oConfiguration.disabledDates.length;i++) {
            if (tmpDate.getTime() == this.oConfiguration.disabledDates[i].getTime()) {
                return null;
            }
        }*/
        return tmpDate;
    }
    return null;
}

//get dates from the textfield
JsDatePick.prototype.getDates = function(){

    //get the dates/date from textinput

    //get the string
    var dateString = JsgetElem(this.oConfiguration.target).value;
    
    
    
    var oldDates = [];
    if (dateString.indexOf(',') < 0 && dateString.trim() != "") {
    
        //if no interval
        if(this.intervalToDatesArray(dateString.trim()) == null)
        {
            var res = this.parseSingleDate(dateString);
            if (res !== null)
                oldDates[oldDates.length] = res;
        }
        else
        {
            var temp = this.intervalToDatesArray(dateString.trim());
            
            for(var i = 0; i < temp.length; i++)
            {
                oldDates.push(temp[i]);
            }
        }
        
    } else if (dateString.indexOf(',') >= 0 && dateString.trim() != "") {
        var tmp2 = dateString.trim().split(',');
        for (var i=0;i<tmp2.length;i++) {
            
            if(this.intervalToDatesArray(tmp2[i].trim()) == null)
            {
                var res = this.parseSingleDate(tmp2[i]);
                if (res !== null)
                    oldDates[oldDates.length] = res;
            }
            else
            {
                var temp = this.intervalToDatesArray(tmp2[i].trim());
            
                for(var k = 0; k < temp.length; k++)
                {
                    oldDates.push(temp[k]);
                }
            }
        }
     
    }
    
    
    var tempOldDates = new Array();
    //remove disabled dates from array
    if(this.oConfiguration.disabledDates != null)
    {
        for(var i = 0; i < oldDates.length; i++)
        {
            if(!this.isDateInArray(oldDates[i], this.oConfiguration.disabledDates))
                tempOldDates[tempOldDates.length] = oldDates[i];
        }
    }
    oldDates = tempOldDates;

    //sort dates
    this.quicksort(oldDates);
    
    if (!this.oConfiguration.multiselect) {
        oldDates.splice(1, oldDates.length - 1);
    }
    
    return oldDates;
}

//check if the passed date is in the passed array
JsDatePick.prototype.isDateInArray = function(date, array)
{
    for(var i = 0; i < array.length; i++)
    {
        if(date.getTime() == array[i].getTime())
            return true;
    }
    return false;
}

//update the input values
JsDatePick.prototype.updateInput = function(){

    this.writeDates(this.currentDates);
}

JsDatePick.prototype.writeDates = function(dates){


    //
    JsgetElem(this.oConfiguration.target).value = "";
    
    var firstDate = null;
    var endDate = null;
    
    var currentDate = null;
    
    for(var i = 0; i < dates.length; i++)
    {
        currentDate = dates[i];
        if(firstDate == null)
            firstDate = dates[i];

        else
        {
            var compareDate = endDate == null ? firstDate : endDate;
            if(dates[i].getTime() - 86400000 == compareDate.getTime())
            {
                endDate = dates[i];
            }
            else
            {
                if(endDate != null)
                {
                    JsgetElem(this.oConfiguration.target).value += this.dateToString(firstDate) + "-" + this.dateToString(endDate) + ", ";
                }
                else
                {
                    JsgetElem(this.oConfiguration.target).value += this.dateToString(firstDate) + ", ";
                }
                firstDate = dates[i];
                endDate = null;
            }   
        }

        //write the last interval
        if(i + 1 == dates.length)
        {
            if(endDate != null)
            {
                JsgetElem(this.oConfiguration.target).value += this.dateToString(firstDate) + "-" + this.dateToString(endDate);
            }
            else
            {
                JsgetElem(this.oConfiguration.target).value += this.dateToString(firstDate);
            }
        }
    }
    
    $(JsgetElem(this.oConfiguration.target)).trigger('change');
}

//converts a interval to an date array which contains all days within the interval
JsDatePick.prototype.intervalToDatesArray = function(intervalString){

    
    var dates = intervalString.trim().split('-');
    
    if(dates.length != 2)
        return null;
        
    var dateArray = new Array();
    
    var startDate = this.parseSingleDate(dates[0]);
    if (startDate === null)
        return null;
   
    var endDate = this.parseSingleDate(dates[1]);
    if (endDate === null)
        return null;
    
    //error if startdate == enddate
    if(startDate.getTime() == endDate.getTime())
        return null;
        
    //switch order if startdate is later than enddate
    if(startDate.getTime() > endDate.getTime())
    {
        var temp = startDate;
        starDate = endDate;
        endDate = temp;
    }
    
    
    for(var i = 0; i <= endDate.getDate() - startDate.getDate(); i++)
    {
        var tempDate = new Date(startDate.getFullYear(), startDate.getMonth(), startDate.getDate() + i);
        dateArray.push(tempDate);
    }
    
    
    return dateArray;
}

//remove a date from textfield when multiselect is on and the user clicks on a selected date
JsDatePick.prototype.removeDate = function(date){


    //remove the current dates from array
    for(var i = 0; i < this.currentDates.length; i++)
    {
        if(date.getTime() == this.currentDates[i].getTime())
        {
            this.currentDates.splice(i, 1);
        }
    }
    
    //sort array and update the input field
    this.quicksort(this.currentDates);
    this.updateInput();
}

JsDatePick.prototype.tmpCloseCal = null;

JsDatePick.prototype.showCalendar = function(){
	if (this.JsDatePickBox.style.display == "none"){
    
        //this.updateCalendar();
        
        if (this.tmpCloseCal === null) {
            var tmpCloseCal = new Function("g_arrayOfUsedJsDatePickCals["+this.globalNumber+"].closeCalendar();");
            this.tmpCloseCal = tmpCloseCal;
        } else {
            var tmpCloseCal = this.tmpCloseCal;
        }
        
		this.determineFieldDate();
        $(document).unbind('click',tmpCloseCal);
        
		this.JsDatePickBox.style.display = "block";
       
		this.resizeCalendar();
		this.executePopulationDelegateIfExists();
		$(this.JsDatePickBox).mouseover (function(){
            $(document).unbind('click',tmpCloseCal);
        });
		
		this.JsDatePickBox.setAttribute("globalCalNumber", this.globalNumber);
        var globalNumber = this.globalNumber;
                   
        $(this.JsDatePickBox).mouseout (function(){
            $(document).click(tmpCloseCal);
        });
        
        var inputField = document.getElementById(this.oConfiguration.target);
        $(inputField).keydown(function (e) {
            if (e.keyCode != 16) {
                tmpCloseCal();
            }
        });
		
	} else {
        
        
        if(this.oConfiguration.targetButton == null)
            return;
        else
        {

            this.JsDatePickBox.style.display = "none";
        }
	}
    
    this.currentDates = this.getDates();
    
    this.updateInput();
};


//adds a array or single date to the currentdates and sorts the array
JsDatePick.prototype.addToCurrentDates = function(dates){

    if(dates == undefined || dates == null || dates.length == 0)
        return;
    if(dates.length)
    {
        if (this.oConfiguration.multiselect) {
        
            for(var i = 0; i < dates.length; i++)
            {
                this.currentDates.push(dates[i]);
            }
        
        } else {
            this.currentDates[0] = dates[0];
        }
    }
    else
    {
        if (this.oConfiguration.multiselect) {
            this.currentDates.push(dates);
        } else {
            this.currentDates[0] = dates;
        }
    }
    
    this.quicksort(this.currentDates);
    
}


JsDatePick.prototype.isAvailable = function(y, m, d){
	if (y > this.oCurrentDay.year){
		return false;
	}
	
	if (m > this.oCurrentDay.month && y == this.oCurrentDay.year){
		return false;
	}
	
	if (d > this.oCurrentDay.day && m == this.oCurrentDay.month && y == this.oCurrentDay.year ){
		return false;
	}
	
	return true;
};

JsDatePick.prototype.getDOMCalendarStripped = function(){
	var d = document,boxMain,boxMainInner,clearfix,boxMainCellsContainer,tooltip,weekDaysRow,clearfix2;
	
	boxMain = d.createElement("div");
	if (this.oConfiguration.isStripped){
		this.setC(boxMain, "boxMainStripped");
	} else {
		this.setC(boxMain, "boxMain");
	}
	
	this.boxMain = boxMain;
	
	boxMainInner 			= d.createElement("div");
	clearfix	 			= d.createElement("div");
	boxMainCellsContainer 	= d.createElement("div");
	tooltip					= d.createElement("div");
	weekDaysRow				= d.createElement("div");
	clearfix2				= d.createElement("div");
	
	this.setC(clearfix, "clearfix");
	this.setC(clearfix2, "clearfix");
	this.setC(boxMainInner, "boxMainInner");
	this.setC(boxMainCellsContainer, "boxMainCellsContainer");
	this.setC(tooltip, "tooltip");
	this.setC(weekDaysRow, "weekDaysRow");
	
	this.tooltip = tooltip;
	
	boxMain.appendChild(boxMainInner);
	
	this.controlsBar = this.getDOMControlBar();
	this.makeDOMWeekDays(weekDaysRow);
	
	boxMainInner.appendChild(this.controlsBar);
	boxMainInner.appendChild(clearfix);
	boxMainInner.appendChild(tooltip);
	boxMainInner.appendChild(weekDaysRow);
	boxMainInner.appendChild(boxMainCellsContainer);
	boxMainInner.appendChild(clearfix2);
	
	this.boxMainCellsContainer = boxMainCellsContainer;
	this.populateMainBox(boxMainCellsContainer);
	
	return boxMain;
};

JsDatePick.prototype.makeDOMWeekDays = function(aWeekDaysRow){
	var i=0,d = document,weekDaysArray = g_l["DAYS_3"],textNode,weekDay;	
	
	for (i=this.oConfiguration.weekStartDay; i<7; i++){
		weekDay 	= d.createElement("div");
		textNode 	= d.createTextNode(weekDaysArray[i]);
		this.setC(weekDay, "weekDay");
		
		weekDay.appendChild(textNode);
		aWeekDaysRow.appendChild(weekDay);
	}
	
	if (this.oConfiguration.weekStartDay > 0){
		for (i=0; i<this.oConfiguration.weekStartDay; i++){
			weekDay 	= d.createElement("div");
			textNode 	= d.createTextNode(weekDaysArray[i]);
			this.setC(weekDay, "weekDay");
			
			weekDay.appendChild(textNode);
			aWeekDaysRow.appendChild(weekDay);
		}
	}
	weekDay.style.marginRight = "0px";
};

JsDatePick.prototype.repopulateMainBox = function(){
	while (this.boxMainCellsContainer.firstChild){
		this.boxMainCellsContainer.removeChild(this.boxMainCellsContainer.firstChild);
	}
	
	this.populateMainBox(this.boxMainCellsContainer);
	this.resizeCalendar();
	this.executePopulationDelegateIfExists();
};

JsDatePick.prototype.executePopulationDelegateIfExists = function(){
	if (typeof(this.repopulationDelegate) == "function"){
		this.repopulationDelegate();
	}
};

//if the dates were marked but not confirmed, set the cell status to original
JsDatePick.prototype.clearMarked = function(){
   
    
    //get the cells
    var children = this.boxMainCellsContainer.childNodes;

    for(var i = 0; i < children.length; i++)
    {
        var child = children[i];
        
        //if is marked
        if(parseInt(child.getAttribute("isMarked")) == 1)
        {
            //remove the temp attribute
            child.removeAttribute("isMarked");
        
            //change the style to origin
            if (parseInt(child.getAttribute("isToday")) == 1){
                this.setC(child, "dayNormalToday");
                this.setExclusiveClass(child,'imgDayNormal');
            } else {
                this.setC(child, "dayNormal");
                this.setExclusiveClass(child,'imgDayNormal');
            }
        }
    }
}

//confirm the selection of dates which were selected with the shift key
JsDatePick.prototype.saveMarked = function(){
    
    //get the cells
    var children = this.boxMainCellsContainer.childNodes;
    
    var newDates = new Array();
    
    //foreach
    for(var i = 0; i < children.length; i++)
    {
        var child = children[i];
        
        //if is marked
        if(parseInt(child.getAttribute("isMarked")) == 1)
        {
            //remove the temp attribute
            child.removeAttribute("isMarked");
            
            //set status to isSelected
            child.setAttribute("isSelected", 1);
            
            //change style to as isSelected
            if (parseInt(child.getAttribute("isToday")) == 1){
                this.setC(child, "dayDownToday");
                this.setExclusiveClass(child,'imgDayDown');
            } else {
                this.setC(child, "dayDown");
                this.setExclusiveClass(child,'imgDayDown');
            }
          
            //save the new date to array
            var day = child.textContent || child.innerText;
            var tempDate = new Date(this.currentYear, this.currentMonth - 1, parseInt(day));
            newDates.push(tempDate);
        }        
    }
    this.addToCurrentDates(newDates);
}

//make a date string with form dd.mm.yyyy
JsDatePick.prototype.dateToString = function(date)
{
    return date.getDate() + "." + (date.getMonth() + 1) + "." + date.getFullYear();
}


JsDatePick.prototype.populateMainBox = function(aMainBox){
	var d = document,aDayDiv,aTextNode,columnNumber = 1,disabledDayFlag = false,cmpMonth = this.currentMonth-1,oDay,iStamp,skipDays,i,currentColorScheme;
    
    //init the date array
    this.currentDates = this.getDates();
	
	oDay = new Date(this.currentYear, cmpMonth, 1, 1, 0, 0);
	iStamp = oDay.getTime();
	
	this.flag_DayMarkedBeforeRepopulation = false;
	this.setControlBarText(this.monthsTextualRepresentation[cmpMonth] + ", " + this.currentYear);
	
	skipDays = parseInt(oDay.getDay())-this.oConfiguration.weekStartDay;
	if (skipDays < 0){
		skipDays = skipDays + 7;
	}
	
	i=0;
	for (i=0; i<skipDays; i++){
		aDayDiv = d.createElement("div");
		this.setC(aDayDiv, "skipDay");
		aMainBox.appendChild(aDayDiv);
		if (columnNumber == 7){
			columnNumber = 1;
		} else {
			columnNumber++;
		}
	}
	
	while (oDay.getMonth() == cmpMonth){
		disabledDayFlag = false;
		aDayDiv 	= d.createElement("div");
		
		if (this.lastPostedDay){
			if (this.lastPostedDay == oDay.getDate()){
				aTextNode	= parseInt(this.lastPostedDay,10)+1;
			} else {
				aTextNode	= d.createTextNode(oDay.getDate());
			}
		} else {
			aTextNode	= d.createTextNode(oDay.getDate());
		}
		
		aDayDiv.appendChild(aTextNode);
		aMainBox.appendChild(aDayDiv);
		
		aDayDiv.setAttribute("globalNumber",this.globalNumber);
		
		if (columnNumber == 7){
			if (g_jsDatePickDirectionality == "ltr"){
				aDayDiv.style.marginRight = "0px";
			} else {
				aDayDiv.style.marginLeft = "0px";
			}
		}
		
		if (this.isToday(oDay)){
			aDayDiv.setAttribute("isToday",1);
		}
		
		if (this.oConfiguration.limitToToday){
			if ( ! this.isAvailable(this.currentYear, this.currentMonth, parseInt(oDay.getDate()) ) ){
				disabledDayFlag = true;
				aDayDiv.setAttribute("isJsDatePickDisabled",1);
			}
		}

		$(aDayDiv).mouseover(function(){
            var gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber")),currentColorScheme;
            currentColorScheme = gRef.getCurrentColorScheme();

            if (parseInt(this.getAttribute("isDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isSelected")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isToday")) == 1){

            } else {

            }
            
            if(gRef.shiftKey == true && gRef.oConfiguration.multiselect)
            {
                //mark the day and all days between the start and the current day
                for(var i = 0; i < this.parentNode.childNodes.length; i++)
                {

                    var child = this.parentNode.childNodes[i];
                    var childText = child.textContent || child.innerText;
                    
                    if( ((parseInt(childText) >= gRef.shiftPressedBegin && parseInt(childText) <= parseInt(this.innerText || this.textContent)) || 
                    ( parseInt(childText) <= gRef.shiftPressedBegin && parseInt(childText) >= parseInt(this.innerText || this.textContent) ))
                    && 
                    parseInt(child.getAttribute("isDisabled")) != 1 &&
                    parseInt(child.getAttribute("isSelected")) != 1)
                    {
                       
                        child.setAttribute("isMarked", 1);
                        if (parseInt(child.getAttribute("isToday")) == 1){
                            gRef.setC(child, "dayDownToday");
                            gRef.setExclusiveClass(child,'imgDayDown');
                        } else {
                            gRef.setC(child, "dayDown");
                            gRef.setExclusiveClass(child,'imgDayDown');
                        }
                    }
                    else 
                    {                        
                        if(parseInt(child.getAttribute("isMarked")) == 1)
                        {
                            
                            child.removeAttribute("isMarked");
                        
                            if (parseInt(child.getAttribute("isToday")) == 1){
                                
                                gRef.setC(child, "dayNormalToday");
                                gRef.setExclusiveClass(child,'imgDayNormal');
                            } else {
                                gRef.setC(child, "dayNormal");
                                gRef.setExclusiveClass(child,'imgDayNormal');
                            }
                        }
                    }
                } 
            }
        });
		
		$(aDayDiv).mouseout (function(){
            var gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber")),currentColorScheme;
            currentColorScheme = gRef.getCurrentColorScheme();
            

            
            if (parseInt(this.getAttribute("isDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isSelected")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isToday")) == 1){
                gRef.setC(this, "dayNormalToday");
                gRef.setExclusiveClass(this,'imgDayNormal');
            } else {
                gRef.setC(this, "dayNormal");
                gRef.setExclusiveClass(this,'imgDayNormal');
            }

        });
        
        $(aDayDiv).mousemove(function(event)
        {
            //fix fuck IE bug, fuck IE
            event = window.event || event;
                
            var gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber")),currentColorScheme;
            gRef.clearSelection();
            if(event.shiftKey == false && gRef.oConfiguration.multiselect)
            {
                gRef.shiftKey = false;
                //clear selected fields
                gRef.clearMarked();
            }
        });
		
		$(aDayDiv).mousedown(function(event){
            var gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber")),currentColorScheme;
            currentColorScheme = gRef.getCurrentColorScheme();
            
            //fix fuck IE bug, fuck IE
            event = window.event || event;
            
            if (parseInt(this.getAttribute("isDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isSelected")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isToday")) == 1){
                gRef.setC(this, "dayDownToday");
                gRef.setExclusiveClass(this,'imgDayDown');
            } else {
                gRef.setC(this, "dayDown");
                gRef.setExclusiveClass(this,'imgDayDown');
            }
            
            
            
            
        });
		
		$(aDayDiv).mouseup(function(event){
            var gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber")),currentColorScheme;
            currentColorScheme = gRef.getCurrentColorScheme();
            
            //fix fuck IE bug, **** IE
            event = window.event || event;
            
            if (parseInt(this.getAttribute("isDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
                return;
            }
            if (parseInt(this.getAttribute("isToday")) == 1){
                gRef.setC(this, "dayNormalToday");
                gRef.setExclusiveClass(this,'imgDayNormal');
            } else {
                gRef.setC(this, "dayNormal");
                gRef.setExclusiveClass(this,'imgDayNormal');
            }
            
            //check if already in the list
            if(parseInt(this.getAttribute("isSelected")) == 1 && event.shiftKey == false && gRef.oConfiguration.multiselect){
                
                
                //remove selection
                this.setAttribute("isSelected", 0);
               
            
                if (parseInt(this.getAttribute("isToday")) == 1){
                    gRef.setC(this, "dayNormalToday");
                    gRef.setExclusiveClass(this,'imgDayNormal');
                } else {
                    gRef.setC(this, "dayNormal");
                    gRef.setExclusiveClass(this,'imgDayNormal');
                }
                
                //remove the date from textfield
                var day = this.textContent || this.innerText;
                gRef.removeDate(new Date(gRef.currentYear, gRef.currentMonth - 1, parseInt(day)));
            }
            else if(event.shiftKey == true && gRef.shiftKey == false && gRef.oConfiguration.multiselect)
            {
                gRef.shiftKey = true;
                gRef.shiftPressedBegin = parseInt(this.textContent || this.innerText);
                
                this.setAttribute("isMarked", 1);
                if (parseInt(this.getAttribute("isToday")) == 1){
                    gRef.setC(this, "dayDownToday");
                    gRef.setExclusiveClass(this,'imgDayDown');
                } else {
                    gRef.setC(this, "dayDown");
                    gRef.setExclusiveClass(this,'imgDayDown');
                }
            }
            else if(event.shiftKey == true && gRef.shiftKey == true && gRef.oConfiguration.multiselect){
                
                gRef.shiftKey = false;
                gRef.saveMarked();
            }
            else
            {
                //get the day browser crossed
                var day = this.textContent || this.innerText;
               
                gRef.setDaySelection(this, event.shiftKey);
                gRef.addToCurrentDates(new Date(gRef.currentYear, gRef.currentMonth - 1, day));
                //gRef.executeOnSelectedDelegateIfExists();
            }
            
            
           
            gRef.updateInput();
           
        });
	
		if (this.isSelectedDay(oDay.getDate())){
			aDayDiv.setAttribute("isSelected",1);
			this.flag_DayMarkedBeforeRepopulation = true;
			this.lastMarkedDayObject = aDayDiv;
			
			if (parseInt(aDayDiv.getAttribute("isToday")) == 1){
				this.setC(aDayDiv, "dayDownToday");
				this.setExclusiveClass(aDayDiv,'imgDayDown');
			} else {
				this.setC(aDayDiv, "dayDown");
				this.setExclusiveClass(aDayDiv,'imgDayDown');
			}	
			
		} else if (this.isDateIdealDisabled(oDay.getDate())) {
            aDayDiv.setAttribute("isDisabled",1);
            aDayDiv.setAttribute("class", aDayDiv.getAttribute("class") + " disabled");
            
            currentColorScheme = this.getCurrentColorScheme();
            
            if (parseInt(aDayDiv.getAttribute("isToday")) == 1){
                
                    this.setC(aDayDiv, "dayDisabled");
                    this.setExclusiveClass(aDayDiv,'imgDayDisabled');
                
            } else {
                
                    this.setC(aDayDiv, "dayDisabled");
                    this.setExclusiveClass(aDayDiv,'imgDayDisabled');
               
            }
		} else {
			currentColorScheme = this.getCurrentColorScheme();
			
			if (parseInt(aDayDiv.getAttribute("isToday")) == 1){
				if (disabledDayFlag){
					this.setC(aDayDiv, "dayDisabled");
					this.setExclusiveClass(aDayDiv,'imgDayNormal');
				} else {
					this.setC(aDayDiv, "dayNormalToday");
					this.setExclusiveClass(aDayDiv,'imgDayNormal');
				}
			} else {
				if (disabledDayFlag){
					this.setC(aDayDiv, "dayDisabled");
					this.setExclusiveClass(aDayDiv,'imgDayNormal');
				} else {
					this.setC(aDayDiv, "dayNormal");
					this.setExclusiveClass(aDayDiv,'imgDayNormal');
				}
			}
		}
		
		if (columnNumber == 7){
			columnNumber = 1;
		} else {
			columnNumber++;
		}
		iStamp += 86400000;
		oDay.setTime(iStamp);
	}
	
	this.lastPostedDay = null;
	
	return aMainBox;
};

JsDatePick.prototype.unsetSelection = function(){
	this.flag_aDayWasSelected = false;
	this.selectedDayObject = {};
	this.repopulateMainBox();
};

JsDatePick.prototype.setSelectedDay = function(dateObject){
	this.flag_aDayWasSelected = true;
    
    
	
	this.selectedDayObject.day = parseInt(dateObject.day,10);
	this.selectedDayObject.month = parseInt(dateObject.month,10);
	this.selectedDayObject.year = parseInt(dateObject.year);
    
    //if the date is wrong set the date to today
    if(isNaN(this.selectedDayObject.year) == true)
    {
        var today = new Date();
        
        this.selectedDayObject.day = today.getDate();
        this.selectedDayObject.month = today.getMonth() + 1;
        this.selectedDayObject.year = today.getFullYear();
    }
    
    this.currentMonth 	= this.selectedDayObject.month;
	this.currentYear	= this.selectedDayObject.year;
	
	//this.currentMonth 	= dateObject.month;
	//this.currentYear	= dateObject.year;
	
	this.repopulateMainBox();
};

JsDatePick.prototype.isSelectedDay = function(aDate){

    //get all dates
    var dates = this.currentDates;

    
    for(var i = 0; i < dates.length; i++)
    {
        //check if dates are equal
        if (parseInt(aDate) == dates[i].getDate() &&
			this.currentMonth == dates[i].getMonth() + 1 &&
			this.currentYear == dates[i].getFullYear()){
            
			return true;
		}
    }
    
	return false;
};

JsDatePick.prototype.getSelectedDay = function(){
	if (this.flag_aDayWasSelected){
		return this.selectedDayObject;
	} else {
		return false;
	}
};

JsDatePick.prototype.getSelectedDayFormatted = function(){
	if (this.flag_aDayWasSelected){
		
		var dateStr = this.oConfiguration.dateFormat;
		
		dateStr = dateStr.replace("%d", this.selectedDayObject.day.toString().strpad());
		dateStr = dateStr.replace("%j", this.selectedDayObject.day);
		
		dateStr = dateStr.replace("%m", this.selectedDayObject.month.toString().strpad());
		dateStr = dateStr.replace("%M", g_l["MONTHS"][this.selectedDayObject.month-1].substr(0,3).toUpperCase());
		dateStr = dateStr.replace("%n", this.selectedDayObject.month);
		dateStr = dateStr.replace("%F", g_l["MONTHS"][this.selectedDayObject.month-1]);
		
		dateStr = dateStr.replace("%Y", this.selectedDayObject.year);
		dateStr = dateStr.replace("%y", this.selectedDayObject.year.toString().substr(2,2));
		
		return dateStr;
	} else {
		return false;
	}
};

JsDatePick.prototype.setDaySelection = function(anElement, shiftKey){
	var currentColorScheme = this.getCurrentColorScheme();
	
	if  (this.flag_DayMarkedBeforeRepopulation){
		/* Un mark last selected day */
		
        if(this.oConfiguration.multiselect == false)
        {
            this.lastMarkedDayObject.setAttribute("isSelected",0);
            
            if (parseInt(this.lastMarkedDayObject.getAttribute("isToday")) == 1){
                this.setC(this.lastMarkedDayObject, "dayNormalToday");
                this.setExclusiveClass(this.lastMarkedDayObject,'imgDayNormal');
            } else {
                this.setC(this.lastMarkedDayObject, "dayNormal");
                this.setExclusiveClass(this.lastMarkedDayObject,'imgDayNormal');
            }
        }
	}
	
	this.flag_aDayWasSelected = true;
	this.selectedDayObject.year  = this.currentYear;
	this.selectedDayObject.month = this.currentMonth;
	this.selectedDayObject.day   = parseInt(anElement.innerHTML);
	
	this.flag_DayMarkedBeforeRepopulation = true;
	this.lastMarkedDayObject = anElement;
	
	anElement.setAttribute("isSelected",1);
	
	if (parseInt(anElement.getAttribute("isToday")) == 1){
		this.setC(anElement, "dayDownToday");
		this.setExclusiveClass(anElement,'imgDayDown');
	} else {
		this.setC(anElement, "dayDown");
		this.setExclusiveClass(anElement,'imgDayDown');
	}
};

JsDatePick.prototype.isToday = function(aDateObject){
	var cmpMonth = this.oCurrentDay.month-1;
	if (aDateObject.getDate() == this.oCurrentDay.day &&
		aDateObject.getMonth() == cmpMonth &&
		aDateObject.getFullYear() == this.oCurrentDay.year){
		return true;
	}
	return false;
};

JsDatePick.prototype.setControlBarText = function(aText){
	var aTextNode = document.createTextNode(aText);
	
	while (this.controlsBarTextCell.firstChild){
		this.controlsBarTextCell.removeChild(this.controlsBarTextCell.firstChild);
	}
	
	this.controlsBarTextCell.appendChild(aTextNode);
};

JsDatePick.prototype.setTooltipText = function(aText){
	while (this.tooltip.firstChild){
		this.tooltip.removeChild(this.tooltip.firstChild);
	}
	
	var aTextNode = document.createTextNode(aText);
	this.tooltip.appendChild(aTextNode);
};

JsDatePick.prototype.moveForwardOneYear = function(){
	var desiredYear = this.currentYear + 1;
	if (desiredYear < parseInt(this.oConfiguration.yearsRange[1])){
		this.currentYear++;
		this.repopulateMainBox();
		return true;
	} else {
		return false;
	}
};

JsDatePick.prototype.moveBackOneYear = function(){
	var desiredYear = this.currentYear - 1;
	
	if (desiredYear > parseInt(this.oConfiguration.yearsRange[0])){
		this.currentYear--;
		this.repopulateMainBox();
		return true;
	} else {
		return false;
	}
};

JsDatePick.prototype.moveForwardOneMonth = function(){
	
	if (this.currentMonth < 12){
		this.currentMonth++;
	} else {
		if (this.moveForwardOneYear()){
			this.currentMonth = 1;
		} else {
			this.currentMonth = 12;
		}
	}
	
	this.repopulateMainBox();
};

JsDatePick.prototype.moveBackOneMonth = function(){
	
	if (this.currentMonth > 1){
		this.currentMonth--;
	} else {
		if (this.moveBackOneYear()){
			this.currentMonth = 12;
		} else {
			this.currentMonth = 1;
		}
	}
	
	this.repopulateMainBox();
};

JsDatePick.prototype.getCurrentColorScheme = function(){
	return this.oConfiguration.cellColorScheme;
};

JsDatePick.prototype.getDOMControlBar = function(){
	var d = document, controlsBar,monthForwardButton,monthBackwardButton,yearForwardButton,yearBackwardButton,controlsBarText;
	
	controlsBar 			= d.createElement("div");
	monthForwardButton		= d.createElement("div");
	monthBackwardButton		= d.createElement("div");
	yearForwardButton		= d.createElement("div");
	yearBackwardButton		= d.createElement("div");
	controlsBarText			= d.createElement("div");
	
	this.setC(controlsBar, "controlsBar");
	this.setC(monthForwardButton, "monthForwardButton");
	this.setC(monthBackwardButton, "monthBackwardButton");
	this.setC(yearForwardButton, "yearForwardButton");
	this.setC(yearBackwardButton, "yearBackwardButton");
	this.setC(controlsBarText, "controlsBarText");
		
	controlsBar.setAttribute("globalNumber",this.globalNumber);
	monthForwardButton.setAttribute("globalNumber",this.globalNumber);
	monthBackwardButton.setAttribute("globalNumber",this.globalNumber);
	yearBackwardButton.setAttribute("globalNumber",this.globalNumber);
	yearForwardButton.setAttribute("globalNumber",this.globalNumber);
	
	this.controlsBarTextCell = controlsBarText;
	
	controlsBar.appendChild(monthForwardButton);
	controlsBar.appendChild(monthBackwardButton);
	controlsBar.appendChild(yearForwardButton);
	controlsBar.appendChild(yearBackwardButton);
	controlsBar.appendChild(controlsBarText);
	
	$(monthForwardButton).mouseover (function(){
        var gRef,parentElement;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["MONTH_FWD"]);
    });

	$(monthForwardButton).mouseout(function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText('');
    });

	$(monthForwardButton).mousedown(function(){
        var gRef,parentElement;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["MONTH_FWD"]);
    });

	$(monthForwardButton).mouseup (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["MONTH_FWD"]);
        gRef.moveForwardOneMonth();
    });

	/* Month backward button event handlers */

	$(monthBackwardButton).mouseover (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["MONTH_BCK"]);

    });

	$(monthBackwardButton).mouseout(function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText('');

    });

	$(monthBackwardButton).mousedown (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["MONTH_BCK"]);

    });

	$(monthBackwardButton).mouseup (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["MONTH_BCK"]);
        gRef.moveBackOneMonth();
    });

	/* Year forward button */

	$(yearForwardButton).mouseover (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["YEAR_FWD"]);
    });

	$(yearForwardButton).mouseout (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText('');
    });

	$(yearForwardButton).mousedown (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["YEAR_FWD"]);
    });

	$(yearForwardButton).mouseup (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["YEAR_FWD"]);
        gRef.moveForwardOneYear();
    });

	/* Year backward button */

	$(yearBackwardButton).mouseover (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["YEAR_BCK"]);
    });

	$(yearBackwardButton).mouseout (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText('');
    });

	$(yearBackwardButton).mousedown (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["YEAR_BCK"]);
    });

	$(yearBackwardButton).mouseup (function(){
        var parentElement,gRef;
        if (parseInt(this.getAttribute("isJsDatePickDisabled")) == 1){
            return;
        }
        parentElement = this.parentNode;
        while (parentElement.className != "controlsBar"){
            parentElement = parentElement.parentNode;
        }
        gRef = JsDatePick.getCalInstanceById(this.getAttribute("globalNumber"));
        gRef.setTooltipText(g_l["YEAR_BCK"]);
        gRef.moveBackOneYear();
    });
	
	return controlsBar;
};
