 function Calendar(isSenderReciever, returnContainerId, returnDayId, returnYearId, returnHiddenFieldId, instancename, startday, startmonth, startyear) {
   //  methods
   //  ~~~
   this.getHowManyDays         = Calendar_getHowManyDays;
   this.setFullMonthsOnly      = Calendar_setFullMonthsOnly;
   this.setOneMonthOnly        = Calendar_setOneMonthOnly;
   this.setScrollable          = Calendar_setScrollable;
   this.nextMonth              = Calendar_nextMonth;
   this.prevMonth              = Calendar_prevMonth;
   this.draw                   = Calendar_draw;
   this.setDate                = Calendar_setDate;
   this.getStartDateFromString = Calendar_getStartDateFromString;
   //this.getStartDateFrom       = Calendar_getStartDateFrom;
   this.getEndDateFromString   = Calendar_getEndDateFromString;
   //this.getEndDateFrom         = Calendar_getEndDateFrom;
   this.parseUserDateInput     = Calendar_parseUserDateInput;
   this.getCellName            = Calendar_getCellName;
   this.setPreselectedDate     = Calendar_setPreselectedDate;
   this.hideCallBack           = Calendar_hideCallBack;

   //  fields
   //  ~~~
   this.isSenderReciever = isSenderReciever;
   this.name = instancename;
   this.calendarId = (isNaN(parseInt(this.name.substring(this.name.length-2,this.name.length)))) ? parseInt(this.name.substring(this.name.length-1,this.name.length)) : parseInt(this.name.substring(this.name.length-2,this.name.length));
   this.returnContainerElement = document.getElementById(returnContainerId);
   this.returnDayFieldElement = document.getElementById(returnDayId);
   this.returnYearFieldElement = document.getElementById(returnYearId);
   this.returnHiddenFieldId = returnHiddenFieldId;
   this.useDataPeriod = true;
   this.readOnly = true;
	this.showWeekNumbers = true;
	this.internalScrollers = false;
	// deactivates all days before "preselected"
	this.disablePast = true;

   this.viewPeriodS = new Date(startyear,startmonth,startday);
   this.viewPeriodE = new Date(startyear,startmonth,startday);
   this.dataPeriodS = null;
   this.dataPeriodE = null;
	
   if (this.isSenderReciever != "sender") {
      this.refReturnField = returnDayId;
      //alert(this.name + " is not a sender.");
   }
   // check start date parameters - default: value in return field
   //alert(this.name + ".viewPeriodS : " + this.viewPeriodS.getDate());
   if (!this.viewPeriodS.getDate()) {
      if (this.refReturnField != undefined) {
         this.getStartDateFromString(this.refReturnField.value);
         //alert(this.refReturnField);
      } else {
         this.getStartDateFromString("today");
      }
      // PeriodEnd is set in setOneMonthOnly() ...
   }
   this.today = new Date();

   this.selectedDay = null;
   this.selectToday = true;
   this.preSelectedDay = null;
   this.multipleSelect = false;

   this.fullMonthsOnly = true;
   this.setOneMonthOnly(true);
   this.scrollable = true;
   this.hideCallBackName = "";

   this.monthsTexts = new Array();
   this.weekdaysTexts = new Array();
   this.prevMonthHTML = "&lt;";
   this.nextMonthHTML = "&gt;";
   this.weekNoHTML    = "&nbsp;";

   this.closeOnSetDate = true;
   this.showShortYear = false;
   this.howManyDays = 0;
   this.returnCalendarId = undefined;
}

function Calendar_prevMonth() {
   this.viewPeriodS.setMonth(this.viewPeriodS.getMonth()-1);
   this.viewPeriodE.setDate(1);
   this.viewPeriodE.setDate(this.viewPeriodE.getDate()-1);
   this.selectedDay = null;
   this.draw();
}

function Calendar_nextMonth() {
   this.viewPeriodS.setMonth(this.viewPeriodS.getMonth()+1);

   this.viewPeriodE.setDate(1);
   this.viewPeriodE.setMonth(this.viewPeriodE.getMonth()+2);
   this.viewPeriodE.setDate(1);
   this.viewPeriodE.setDate(this.viewPeriodE.getDate()-1);
   this.selectedDay = null;
   this.draw();
}

function Calendar_setFullMonthsOnly(truefalse) {
   this.fullMonthsOnly = truefalse;
   if (this.fullMonthsOnly) {
      this.viewPeriodE = new Date(this.viewPeriodE.getFullYear(),this.viewPeriodE.getMonth()+1,1);
      this.viewPeriodE.setDate(this.viewPeriodE.getDate()-1);
   }
}

function Calendar_setOneMonthOnly(truefalse) {
   // Set viewport to one full month
   this.oneMonthOnly = truefalse;
   if (this.oneMonthOnly) {
      this.viewPeriodS = new Date(this.viewPeriodS.getFullYear(), this.viewPeriodS.getMonth(), 1);
      this.viewPeriodE = new Date(this.viewPeriodS.getFullYear(),this.viewPeriodS.getMonth()+1,1);
      this.viewPeriodE.setDate(this.viewPeriodE.getDate()-1);
   }
}

function Calendar_setScrollable(truefalse) {
   this.scrollable = truefalse;
}

function Calendar_getHowManyDays() {
   var tempdate = new Date( this.viewPeriodS.getFullYear(),this.viewPeriodS.getMonth(),this.viewPeriodS.getDate() );
   var days = 0;
   while (tempdate.getTime() <= this.viewPeriodE.getTime()) {
      days++;
      tempdate.setDate(tempdate.getDate()+1);
   }
   return days;
}
/*
function Calendar_getStartDateFrom(ioField) {
	alert("getfrom used.");
   eval("userInput = "+this.returnWindow+"."+this.returnForm+"."+ioField+".value;");
   this.getStartDateFromString(userInput);
}*/

function Calendar_getStartDateFromString(datestring) {
   if (datestring == "today") {
      this.viewPeriodS = new Date();
   } else {
      this.viewPeriodS = this.parseUserDateInput(datestring);
      if (this.viewPeriodS == undefined) {
         this.viewPeriodS = new Date();
      }
   }
}
/*
function Calendar_getEndDateFrom(ioField) {
   eval("userInput = "+this.returnWindow+"."+this.returnForm+"."+ioField+".value;");
   this.getEndDateFromString(userInput);
}*/


function Calendar_getEndDateFromString(datestring) {
   this.viewPeriodE = this.parseUserDateInput(datestring);
}


function Calendar_setPreselectedDate(date) {
	// read date from given inputfields
	if (!isDate(date)) {
	  //if (this.isSenderReciever != undefined) {
		  var day = null;
        	  var year = null;
		
		  day = this.returnDayFieldElement.value;

		 
		  year = this.returnYearFieldElement.value;
		  //alert("year: "+ year);
		  year = year.split("_");
		  date = new Date(year[1],year[0],day);
	  /*} else {
		  date = this.parseUserDateInput(this.refReturnField.value);
		  alert(this.refReturnField.value)
	  }*/

	}
	this.preSelectedDay = date;
	this.selectedDay = this.getCellName(new Date(date));
	this.viewPeriodS = new Date(date);
	this.viewPeriodS.setDate(1);

	this.viewPeriodE = new Date(date);
	this.viewPeriodE.setDate(1);
	this.viewPeriodE.setMonth(this.viewPeriodE.getMonth()+1);
	this.viewPeriodE.setDate(1);
	this.viewPeriodE.setDate(this.viewPeriodE.getDate()-1);
}

// Speziell fuer Daenemark!
function Calendar_hideCallBack() {
   // da es nur 2 Kalender geben kann - letztes Zeichen nehmen
   //var temp = (isNaN(parseInt(this.name.substring(this.name.length-2,this.name.length)))) ? parseInt(this.name.substring(this.name.length-1,this.name.length)) : parseInt(this.name.substring(this.name.length-2,this.name.length));
   //alert(temp);
   //temp = this.hideCallBackName+"('"+temp+"');";
   temp = this.hideCallBackName;
   //alert(temp);
   eval(temp);
}

function Calendar_parseUserDateInput(userInput){
	if (isString(userInput)) {
		var matchReg = /(\d+)\D+(\d+)\D+(\d+)\D*/;
		matchReg.exec( userInput );

		var userInput_day   = RegExp.$1;
		var userInput_month = RegExp.$2;
		var userInput_year  = RegExp.$3;
		
		userInput_day *= 1; userInput_month *= 1; userInput_year *= 1;
		// attention: userInput_month is 1-12-ranged!
		// ~~~
		if (userInput_month!="") {
			userInput_month -= 1;
			if (userInput_month<0) {
				userInput_month = 11;
			} else if (userInput_month>11) {
				userInput_month = 0;
			}
		}
		if (userInput_year!="") {
			if (userInput_year<100) {
				if (userInput_year<50) {
					userInput_year+=2000;
				} else {
					userInput_year+=1900;
				}
			} else if (userInput_year < 1000) {
				if (userInput_year<200) {
					userInput_year+=1900;
				} else {
					userInput_year+=1000;
				}
			}
		}
      if  ((userInput_year != 0) && (userInput_day != 0)) {
	     return new Date(userInput_year, userInput_month, userInput_day);
		}

	} else if (isDate(userInput)) {
	  return userInput;
	}

	return null;
}

function Calendar_getCellName(date) {
   return this.name+"_df_"+date.getFullYear()+"/"+(date.getMonth())+"/"+date.getDate();
}

// This function toggles the given date's style
function Calendar_setDate(cell) {
   // set the colors by style
   if (!this.readOnly) {
      if (this.multipleSelect) {
         var tempday = document.getElementById(cell);
         tempday.className = (tempday.className == "active") ? "enabled" : "active";
      } else {
         // remove old selection - select ONE day only
         if (this.selectedDay != null) {
            tempday = document.getElementById(this.selectedDay);
            tempday.className = (tempday.className == "active") ? "enabled" : "active";
         }
         this.selectedDay = cell;
         tempday = document.getElementById(cell);
         tempday.className = (tempday.className == "active") ? "enabled" : "active";
         var date = cell.substring((this.name.length)+4,cell.length);
         var temp = date.split("/");
         var year = 1*temp[0];
         var month = 1*temp[1];
         var day = 1*temp[2];
			var datum = new Date(year,month,day);
         if (this.calendarId != undefined) {
            var dayField = "input_day"+this.calendarId;
         	//alert("this.calendarId: " + this.calendarId);
         	//alert("periodStart[this.calendarId]: " +  periodStart[this.calendarId]);
            syncDays(dayField,datum,periodStart[this.calendarId],periodEnd[this.calendarId],false);
             //alert(datum.getDate());
		 this.returnDayFieldElement.value = datum.getDate();
		 //alert((datum.getMonth())+"_"+datum.getFullYear());
		 this.returnYearFieldElement.value = (datum.getMonth())+"_"+datum.getFullYear();

		 //alert(document.getElementById(this.returnHiddenFieldId));
		//document.getElementById(this.returnHiddenFieldId).value = datum.getDate()+"."+(datum.getMonth()+1)+"."+datum.getFullYear();
           
            //var calid = this.name.charAt(this.name.length-1);
            //this.hideCallBack();
            //alert("this.calendarId: "+this.calendarId+"; this.isSenderReciever: "+this.isSenderReciever+"; this.returnCalendarId: " + this.returnCalendarId);
            correctReturnSelection(this.calendarId, this.isSenderReciever, this.returnCalendarId);
            //correctReturnSelection(calid, this.twoway);
         } else {
				date = formatDate(datum,false);

				// calculate weekday & begin week with monday
				var weekday = datum.getDay()-1;
				if (weekday == -1) weekday = 6;
				
				this.refReturnField.value = this.weekdaysTexts[weekday]+", "+date;
  
         }

         this.hideCallBack();
      }
   }
}


//
// This function fills the calendar table with the days of
// the selected month and year.
function Calendar_draw() {
//alert(this.howManyDays);
   this.howManyDays = this.getHowManyDays();

   // autodetect preSelectedDay if non given...
   if ((this.refReturnField != undefined) && (this.preSelectedDay == undefined)) {
      this.preSelectedDay = this.parseUserDateInput(this.refReturnField.value);
      if (this.preSelectedDay == undefined) {
         this.preSelectedDay = new Date();
      }
   }

   if (this.bitfield && this.useDataPeriod) {
      // calc difference in days between viewPeriodS and dataPeriodS
      // to find bitfield begin...
      var tempdate = new Date(this.dataPeriodS);
      var bitfieldindex = 0;
      if (tempdate.getTime() < this.viewPeriodS.getTime()) {
         while (tempdate.getTime() < this.viewPeriodS.getTime()) {
            bitfieldindex++;
            tempdate.setDate(tempdate.getDate()+1);
         }
      } else {
         while (tempdate.getTime() > this.viewPeriodS.getTime()) {
            bitfieldindex--;
            tempdate.setDate(tempdate.getDate()-1);
         }
      }
   }

   var div = document.getElementById(this.name);
   //alert(div.id);
   // create table if it does not already exist
   var table = document.getElementById(this.name+"_table");
   if (table == null) {
      table = document.createElement("TABLE");
      div.insertBefore(table,div.firstChild);
      table.setAttribute("cellSpacing", "0");
      table.setAttribute("cellpadding", "0");
      //next line edited: 14. november 2008 - nikolaj carĝe
      //table.style.width = "160px";
      table.id = this.name+"_table";
      table.className = "calendar";
   }

   // Recycling: remove complete table body...it's recreated => fast delete?
   var tbody = document.getElementById(this.name+"_tbody");
   if (tbody != null) {
      tbody.parentNode.removeChild(tbody);
   }

   // (re-)create tbody
   tbody = document.createElement("TBODY");
   table.appendChild(tbody);
   tbody.id = this.name+"_tbody";
   // update header and status texts
   tempdate = new Date(this.viewPeriodS.getFullYear(),this.viewPeriodS.getMonth(),this.viewPeriodS.getDate());

   // show month name above weekdays
   if (this.oneMonthOnly) {
      // create row for month name
      current_row = document.createElement("TR");
      if (this.scrollable) {
			if (this.internalScrollers) {
				current_cell= document.createElement("TH");
				current_cell.id = this.name+"_heading_months_lt";
			} else {
				current_cell = document.getElementById(this.name+"prev");
			}
         var tempdate2 = new Date(tempdate);
         tempdate2.setDate(1);
         var thistoday = new Date(this.today);
         thistoday.setDate(1);
         if ( ( (!this.useDataPeriod) ||
					 (!this.dataPeriodS) ||
					 (this.dataPeriodS && (tempdate2.getTime() > this.dataPeriodS.getTime())))
			   ) {
				current_cell.innerHTML=this.prevMonthHTML;
            current_cell.className = "prevMonth";
				if (this.internalScrollers) {
					current_cell.onclick = function() {
						var calid = this.id.substring(0,this.id.indexOf("_heading_months_lt"));
						var test = eval('calid')+".prevMonth();";
						eval(test);
					}
				} else {
					current_cell.onclick = function() {
						var calid = this.id.substring(0,this.id.indexOf("prev"));
						var test = eval('calid')+".prevMonth();";
						eval(test);
					}
				}
         } else {
            current_cell.innerHTML= "";
            current_cell.className = "disabled";
         }
			if (this.internalScrollers) {
				current_row.appendChild(current_cell);
			}
      }
      current_cell= document.createElement("TH");
		current_cell.colSpan = ( (this.scrollable) && (this.internalScrollers) ) ? 6 : 8;
		
      current_cell.innerHTML = this.monthsTexts[tempdate.getMonth()]+"&nbsp;"+tempdate.getFullYear();
      current_cell.textAlign="center";
      current_cell.id = this.name+"_heading_months"+tempdate.getMonth();
      if (this.multipleSelect) {
         current_cell.className = "heading_months_enabled";
         current_cell.onclick = function() {
            var calid = this.id.substring(0,this.id.indexOf("_heading_months"));
            var month = this.id.substring(this.id.indexOf("_heading_months")+15,this.id.length);
            var test = eval('calid')+".selectMonth(month);";
            eval(test);
         }
      } else {
         current_cell.className = "heading_months_disabled";
      }
      current_row.appendChild(current_cell);
      if (this.scrollable) {
			if (this.internalScrollers) {
				current_cell = document.createElement("TH");
				current_cell.id = this.name+"_heading_months_gt";
			} else {
				current_cell = document.getElementById(this.name+"next");
			}
         var tempdate2 = new Date(tempdate);
         tempdate2.setDate(1);
         tempdate2.setMonth(tempdate2.getMonth()+1);
         tempdate2.setDate(tempdate2.getDate()-1);
         if ( (!this.useDataPeriod) ||
				  (!this.dataPeriodE) ||
				  (this.dataPeriodE && (tempdate2.getTime() < this.dataPeriodE.getTime() ))
				) {
            current_cell.innerHTML=this.nextMonthHTML;
            current_cell.className = "nextMonth";
				if (this.internalScrollers) {
					current_cell.onclick = function() {
						var calid = this.id.substring(0,this.id.indexOf("_heading_months_gt"));
						var test = eval('calid')+".nextMonth();";
						eval(test);
					}
				} else {
					current_cell.onclick = function() {
						var calid = this.id.substring(0,this.id.indexOf("next"));
						var test = eval('calid')+".nextMonth();";
						eval(test);
					}
				}
          } else {
            current_cell.innerHTML="";
            current_cell.className = "disabled";
         }
			if (this.internalScrollers) {
				current_row.appendChild(current_cell);
			}
      }

      tbody.appendChild(current_row);
   }

   // write weekday names in first (or second) row
   var row = document.createElement("TR");

	// week numbers
	if (this.showWeekNumbers) {
		var cell = document.createElement("TH");
		cell.id = this.name+"_heading_"+d;
		cell.className = "heading_daynames";
		cell.innerHTML = this.weekNoHTML;
		row.appendChild(cell);
   }

	for (d = 0 ; d < 7 ; d++) {
      var cell = document.createElement("TH");
      cell.id = this.name+"_heading_"+d;
      cell.innerHTML = this.weekdaysTexts[d];
      if (this.multipleSelect) {
         cell.className = "enabled";
         cell.onclick = function() {
            var calid = this.id.substring(0,this.id.indexOf("_heading_"));
            var day = this.id.substring(this.id.indexOf("_heading_")+9,this.id.length);
            var test = eval('calid')+".selectDays(day);";
            eval(test);
         }
      } else {
         cell.className = "heading_daynames";
      }
      row.appendChild(cell);
   }

   tbody.appendChild(row);

   // Calculate skip between first table cell and first one with content (which
   // weekday does the calendar start with)
   // if it is 0 (sunday) set to 6 as the week begins on monday
   daystoskip = (tempdate.getDay()-1 < 0) ? 6 : tempdate.getDay()-1;

   var daysdrawn = 0;
   var newmonth = false;
   var oldtempcolspan = 0;
   var colspan = 1;
   var wcount = 0;

   var w = -1;
	var startweek = tempdate.getWeek();
   var newWeekNeeded = true;
   while (newWeekNeeded) {
      w++;

      if (((tempdate.getDate() == 1 && newmonth) || (daysdrawn == 0)) && (tempdate.getTime() >= this.viewPeriodS.getTime())) {
         // a new month begins...

         // which weekday is the current date (e.g. 1st April 2005 is a Friday (5))?
         // if it is 0 (sunday) set to 6 as the week begins on monday
         daystoskip = (tempdate.getDay()-1 < 0) ? 6 : tempdate.getDay()-1;

         if (this.oneMonthOnly == false) {
            // create row for month name
            current_row = document.createElement("TR");
            current_cell= document.createElement("TD");
            current_cell.colSpan = 7;
            //current_cell.innerHTML = "<b>"+this.monthsTexts[tempdate.getMonth()]+" - "+tempdate.getFullYear()+"</b>";
            current_cell.innerHTML = this.monthsTexts[tempdate.getMonth()]+" - "+tempdate.getFullYear();
            current_cell.id = this.name+"_heading_months"+tempdate.getMonth();
            if (this.multipleSelect) {
               current_cell.className = "enabled";
               current_cell.onclick = function() {
                  var calid = this.id.substring(0,this.id.indexOf("_heading_months"));
                  var month = this.id.substring(this.id.indexOf("_heading_months")+15,this.id.length);
                  var test = eval('calid')+".selectMonth(month);";
                  eval(test);
               }
            } else {
               current_cell.className = "disabled";
            }
            current_row.appendChild(current_cell);

            tbody.appendChild(current_row);
         }

      }

      current_row = document.getElementById(this.name+"_row_"+w);
      if (current_row == null) {
         current_row = document.createElement("TR");
         current_row.id = this.name+"_row_"+w;
         tbody.appendChild(current_row);
      }
		
		if (this.showWeekNumbers) {
			cell = document.createElement("TD");
			cell.className = "weekno";
			cell.innerHTML = startweek++;
			current_row.appendChild(cell);
		}
		
    wcount = wcount+1;
		// draws week rows
      for (var d = 0; d < 7; d++) {

			if ((tempdate.getDate() == 1 && newmonth == false) && (daysdrawn != 0)) {
            newmonth = true;
            // append remaining empty cells
//				var td2 = new Date(tempdate);
            for (var e = d; e < 7; e++) {
               cell = document.createElement("TD");
               cell.className = "disabled";
//					cell.innerHTML = td2.getDate();
					// da anfangs schon um 1 erhoeht!
//					td2.setDate(td2.getDate()+1)
               cell.innerHTML = "&nbsp;";
               if (current_row != null) {
                  current_row.appendChild(cell);
               }
            }
            break;
         }

         cell = document.createElement("TD");

         if (daystoskip <= 0 && daysdrawn < this.howManyDays) {
            newmonth = false;
            // Change table cells id to represent current displayed date
            cell.id = this.name+"_df_"+tempdate.getFullYear()+"/"+(tempdate.getMonth())+"/"+tempdate.getDate(); //+"-"+((w*7)+d+1);

            if ((this.useDataPeriod) && (bitfieldindex+daysdrawn >= 0) && (this.dataPeriodS) && (this.dataPeriodE) && (tempdate.getTime() <= this.dataPeriodE.getTime())) {
               cell.className = (this.bitfield.charAt(bitfieldindex+daysdrawn) == "1") ? "working" : "notworking";
            } else {
               cell.className = (this.readOnly == true) ? "disabled" : "enabled";
            }
            cell.innerHTML = tempdate.getDate(); //+":"+(bitfieldindex+daysdrawn)+"-"+this.bitfield.charAt(bitfieldindex+daysdrawn);
            cell.onclick = function(){
               var calid = this.id.substring(0,this.id.indexOf("_df"));
               var test = eval('calid')+".setDate(this.id);";
               eval(test);
            };
            // increase already drawn days by one
            tempdate.setDate(tempdate.getDate()+1);
            daysdrawn += 1;

            //  deactivate cell
         } else {
            cell.className = "disabled";
            //cell.innerHTML = "&nbsp;";
				var td2 = new Date(tempdate);
				td2.setDate(td2.getDate()-daystoskip)
				//cell.innerHTML = td2.getDate();
            cell.innerHTML = "&nbsp;";
            cell.onclick = null;
            daystoskip -= 1;
         }

         // quickhack
			tempdate.setDate(tempdate.getDate()-1);
         if (tempdate.getTime() < this.dataPeriodS.getTime()) {
		 	if (wcount %2) {
				cell.className = "disabled";
			} else {
	            cell.className = "altdisabled";
			}
            cell.onclick = null;
         }
         if (tempdate.getTime() > this.dataPeriodE.getTime()) {
            cell.className = "disabled";
            cell.onclick = null;
         }
			tempdate.setDate(tempdate.getDate()+1);

        if (wcount %2) {cell.className=cell.className +" alt";}
//		alert(wcount);
         current_row.appendChild(cell);
      }
      if ((tempdate > this.viewPeriodE) || (daysdrawn >= this.howManyDays)) {
         newWeekNeeded = false;
      }

   }

   if (w > 5) {
      var row = document.createElement("TR");
      for (var i=0; i <= 7; i++) {
         var cell = document.createElement("TD");
         cell.className = "disabled";
         cell.innerHTML = "&nbsp;";
         row.appendChild(cell);
      }
      tbody.appendChild(row);
   }

   // auto-correction of div size
   document.getElementById(this.name).style.width = "auto";
   if (this.preSelectedDay != undefined) {
      tempday = document.getElementById(this.name+"_df_"+this.preSelectedDay.getFullYear()+"/"+(this.preSelectedDay.getMonth())+"/"+this.preSelectedDay.getDate());
      if (tempday != undefined) {
         if ((!this.dataPeriodS) && (!this.dataPeriodE)) {
            tempday.className = "active";
         } else {
            // should be preselect!!
            tempday.className = "active";
         }
      }
   }

} // - END function Calendar_draw();

Calendar.prototype.getFromVKHEXBitfield = function(bitfield) {
   this.dataPeriodS = new Date("20"+bitfield.substr(4,2),bitfield.substr(2,2),bitfield.substr(0,2));
   this.dataPeriodS.setMonth(this.dataPeriodS.getMonth() - 1);

   this.dataPeriodE = new Date("20"+bitfield.substr(10,2),bitfield.substr(8,2),bitfield.substr(6,2));
   this.dataPeriodE.setMonth(this.dataPeriodE.getMonth() - 1);

   bitfield = bitfield.substring(12,bitfield.length);

   // convert hexadecimal to binary
   this.bitfield = "";
   var temp = "";

   for (var i=0; i < bitfield.length;i += 2) {
      temp = (parseInt(bitfield.substring(i,i+2),16)).toString(2);
      while (temp.length < 8) {
         temp = "0"+temp;
      }
      this.bitfield = this.bitfield + temp;
   }
}


// temporary place for some useful functions - due to be put somewhere else!
// ###############################################################################
	
// Synchronizes select "fields" with hidden date filed
function syncToHidden(calid) {

   var inputday = document.getElementById("input_day"+calid);
   var inputyear = document.getElementById("input_year"+calid);

   var day = inputday.value;
   var temp = inputyear.value;
   temp = temp.split("_");
   var month = temp[0];
   month *= 1;
   month++;
   var year = temp[1];
   var fname = document.getElementById("hafasform"+calid);

   var ename = document.getElementById("dato"+calid);
	if (ename != null) {
	     ename.value = day+"."+month+"."+year;
	}
}

function getDateSelects(calid) {
   if (
        (!document.getElementById("input_day"+calid)) &&
        (!document.getElementById("input_year"+calid))
      ) {
     return;
   }
   var inputday = document.getElementById("input_day"+calid);
   var inputyear = document.getElementById("input_year"+calid);

   var day = inputday.value;
   var temp = inputyear.value;
   temp = temp.split("_");
   var month = temp[0];
   month *= 1;
   month++;
   var year = temp[1];
   var date = new Date(year,month-1,day);
   if (isDate(date)) {
      return date;
   } else {
      return null;
   }
}

function setDateSelects(calid, date, isSenderReciever) {
   var inputday = document.getElementById("input_day"+calid);
   var inputyear = document.getElementById("input_year"+calid);

   inputday.value = date.getDate();
   inputyear.value = (date.getMonth())+'_'+date.getFullYear();
	if (isSenderReciever) {
		syncToHidden(calid);
	}
}

// sets return journey date >= departure
function correctReturnSelection(calid, isSenderReciever, retcalid) {
   //alert("isSenderReciever: " +isSenderReciever)
   if(undefined != isSenderReciever) {
   	    if(isSenderReciever == "sender") {
   	        //sender calendar
	   	    var depdate = getDateSelects(calid);
	   	    var retdate = getDateSelects(retcalid);
	    }
	    if(isSenderReciever == "reciever") {
	        //reciever calendar
	        var depdate = getDateSelects(calid);
		    var retdate = getDateSelects(retcalid);
	    }
   } else {
    //oneway calendar
   	var depdate = getDateSelects(calid);
   }

   if (undefined != isSenderReciever || isSenderReciever != "reciever") {
      //oneway calendar or sender calendar
      if (undefined != depdate) {

         var td = new Date(depdate);
         //td.setDate(td.getDate()+1);
         td.setDate(td.getDate());

         //alert(td);
         //syncDays('input_day0',td,periodStart,periodEnd,false);

         if (undefined != retdate) {

           if (depdate.getTime() >= retdate.getTime()) {
   
             setDateSelects(retcalid,td,isSenderReciever);
             syncDays('input_day'+retcalid,td,periodStart[calid],periodEnd[calid],false);
           }
           if (td.getTime() > periodEnd[calid].getTime()) {
           	
             setDateSelects(retcalid,depdate,isSenderReciever);
             syncDays('input_day'+retcalid,depdate,periodStart[calid],periodEnd[calid],false);
           }
           syncToHidden(calid);
           syncToHidden(retcalid);
           //alert("sender");
         }
      }
   }
   if (isSenderReciever == "reciever") {
      //reciever calendar
      if (undefined != depdate && undefined != retdate) {
        // Commented out code below since changing Return month to "Feb" limited the nbr of days in Dep month to 28 even tho Dep month was January
        /*
        syncDays('input_day'+calid,retdate,periodStart[calid],periodEnd[calid],false);
        syncToHidden(calid);
        
        syncDays('input_day'+retcalid,retdate,periodStart[retcalid],periodEnd[retcalid],false);
        syncToHidden(retcalid);
        */
        //alert("reciever");
      }
      else if (undefined != retdate) {
        syncDays('input_day'+retcalid,retdate,periodStart[retcalid],periodEnd[retcalid],false);
        syncToHidden(retcalid);
      }
   }
}

// synchronizes day with days of month and period.
function syncDays(field,value,periodS,periodE,firstcall) {
  if (isString(value)) {
	  value = value.split("_");
	  var tempdate = new Date(value[1],value[0],1);
  } else if (isDate(value)) {
	  var tempdate = new Date(value);
  } else {
	  return;
  }
  var input = document.getElementById(field);
 var saveit = (firstcall) ? tempdate.getDate() : input.value;

  if((periodS) && (periodE)) {
     periodS = Calendar_parseUserDateInput(periodS);
     periodE = Calendar_parseUserDateInput(periodE);

     var monthS = periodS.getMonth();
     var yearS = periodS.getFullYear();

     var monthE = periodE.getMonth();
     var yearE = periodE.getFullYear();

     var thismonth = tempdate.getMonth();
     var thisyear = tempdate.getFullYear();
     var dayS = 1;
     var dayE = tempdate.getDaysInMonth();
     var mydate = new Date(tempdate);
     mydate.setDate(1);

     // wenn der aktuelle Tag im Monat des Periodenanfangs liegt:
     if ( ( (thismonth == monthS) && (thisyear == yearS) ) && (periodS.getDate() > 1 )) {
       dayS = periodS.getDate();
     }
     // wenn der aktuelle Tag im Monat des Periodenendes liegt:
     if ( ( (thismonth == monthE) && (thisyear == yearE)) && (periodE.getDate() < mydate.getDaysInMonth() ) ) {
       dayE = periodE.getDate();
       saveit = (periodE.getDate() < saveit) ? periodS.getDate() : saveit;
     }
  }
  var d = -1;
  // empty options
  var o = input.options;
  var anz = o.length;
  for (var i = 0; i < anz;i++) {
     o[0] = null;
  }
  for (var i = 1; i <= tempdate.getDaysInMonth(); i++) {
    if( (i >= dayS) && (i <= dayE) ) {
      d++;
      o[d] = new Option(i,i);
      if (i == saveit) {
         o[d].selected = true;    }
      }
  }
}


function printMonths(field, periodS, periodE, preselection) {

  var input = document.getElementById(field);
  var dateS = new Date(periodS);
  var dateE = new Date(periodE);

  while (dateS.getTime() <= dateE.getTime()) {
    if ( (dateS.getMonth() == preselection.getMonth()) && (dateS.getFullYear() == preselection.getFullYear()) ) {
       input.options[input.options.length] = new Option(monthsTexts[dateS.getMonth()]/*+' '+dateS.getFullYear()*/,dateS.getMonth()+"_"+dateS.getFullYear(),true,true);
		 input.options[input.options.length-1].selected = true;
    } else {
       input.options[input.options.length] = new Option(monthsTexts[dateS.getMonth()]/*+' '+dateS.getFullYear()*/,dateS.getMonth()+"_"+dateS.getFullYear());
    }
    dateS.setDate(1);
    dateS.setMonth(dateS.getMonth()+1);
  }
}

function toggleDivCal(calid, dropdownid1, dropdownid2) {
  var distyle = "inline";

  // FIX: Pendlerfahrplan
  /*if (document.hafasform.timeselectfrom) {
     document.hafasform.timeselectfrom.style.display = (document.hafasform.timeselectfrom.style.display != "none") ? "none" : distyle;
  }*/

  var div = document.getElementById("calendar"+calid);
  div.style.position="absolute";
  div.style.top = (getPosY(document.getElementById("callink"+calid))-1)+"px";
  div.style.left = (getPosX(document.getElementById("callink"+calid))-1)+"px";

  div.style.display = (div.style.display != "none") ? "none" : distyle;
  
  if (dropdownid1 != '')
  {
    var dropdown1 = document.getElementById(dropdownid1);
    dropdown1.style.display = (div.style.display != 'none') ? 'none' : '';
  }
  
  if (dropdownid2 != '')
  {
    var dropdown2 = document.getElementById(dropdownid2);
    dropdown2.style.display = (div.style.display != 'none') ? 'none' : '';
  }
}

function formatDate(date, showShortYear) {
	// prepare for display
	if (isDate(date)) {

		var day = date.getDate();
		var month = date.getMonth() + 1;
		var year = date.getFullYear();

		if (day < 10) {
			day = "0"+day;
		}
		if (month < 10) {
			month = "0"+month;
		}

		// has to be after the previous step for interpreting purposes
		if (showShortYear) {
			year -= 2000;
			if (year < 10) {
				year = "0"+year;
			}
		}
	   return day+"."+month+"."+year;
	} else {
		return null;
	}
}
