function DateChooser( targetElement, callback, year, month, day )
{
  this.render = function( year, month )
  {
    var nextMonthMonth = ( month % 12 ) + 1;
    var nextMonthYear = month == 12 ? year + 1 : year;

    var previousMonthMonth = ( ( month + 10 ) % 12 ) + 1;
    var previousMonthYear = month == 1 ? year - 1 : year;

    var dateChooserHead = "<div class=\"datechooser\"><div class=\"datechoosertop\"><div class=\"datechoosertopcorner\"></div><div class=\"datechoosermain\"><table cellpadding=\"0\" cellspacing=\"1\"><thead><tr>";
    dateChooserHead += "<td width=\"25\"><a href=\"#\" onclick=\"DateChooser.getById(" + this.id + ").render( " + ( year - 1 ) + ", " + month + " ); return false;\">&lt;&lt;</a></td>";
    dateChooserHead += "<td width=\"25\"><a href=\"#\" onclick=\"DateChooser.getById(" + this.id + ").render( " + previousMonthYear + ", " + previousMonthMonth + " ); return false;\">&lt;</a></td>";
    dateChooserHead += "<td style=\"text-align: center;\" colspan=\"3\" width=\"75\" class=\"monthandyear\"><div style=\"text-align: center; width: 75px;\">#month# #year#</div></td>";
    dateChooserHead += "<td width=\"25\"><a href=\"#\" onclick=\"DateChooser.getById(" + this.id + ").render( " + nextMonthYear + ", " + nextMonthMonth + " ); return false;\">&gt;</a></td>";
    dateChooserHead += "<td width=\"25\"><a href=\"#\" onclick=\"DateChooser.getById(" + this.id + ").render( " + ( year + 1 ) + ", " + month + " ); return false;\">&gt;&gt;</a></td></tr></thead>";

    var monthNames = [
      "Jan",
      "Feb",
      "Mar",
      "Apr",
      "Mai",
      "Jun",
      "Jul",
      "Aug",
      "Sep",
      "Okt",
      "Nov",
      "Dez"
    ];
    var daysInMonth = new Array(31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
    var daysInThisMonth = daysInMonth[month - 1];
    var today = new Date();
    var todayDay = today.getFullYear() == year && today.getMonth() + 1 == month ? today.getDate() : -1;
    var date = new Date(year, month - 1, 1);
    var startDay = (date.getDay() + 6) % 7;

    if( month == 2 && year % 4 == 0 && ( year % 100 != 0 || year % 400 == 0 ) )
    {
      daysInThisMonth++;
    }

    dateChooserHead = dateChooserHead.replace("#year#", year).replace("#month#", monthNames[month - 1]);

    var html = dateChooserHead;

    html += "<tbody><tr>";

    var pos;
    for( pos = 0; pos < startDay; pos++ ) {
      html += "<td width=\"25\" class=\"noday\">&nbsp;</td>";
    }

    for( day = 0; day < daysInThisMonth; day++ ) {
      if( pos % 7 == 0 && pos != 0 ) {
        html += "</tr><tr>";
      }

      this.elementClass = ( ( pos % 7 ) < 5 ? "weekday" : "weekend" );
      if( this.selectedYear == year && this.selectedMonth == month && this.selectedDay == (day + 1) ) {
        this.elementClass = "selectedday";
      } else if( todayDay == (day + 1) ) {
        this.elementClass = "today";
      }
      html += "<td width=\"25\" class=\"" + this.elementClass + "\"><a href=\"#\" onclick=\"DateChooser.getById(" + this.id + ").choose( " + year + ", " + month + ", " + ( day + 1 ) + " ); return false;\">" + ( day + 1 ) + "</a></td>";

      pos++;
    }

    for( ; pos <= 42; pos++ ) {
      if( pos % 7 == 0 ) {
        html += "</tr>";
        break;
      }
      html += "<td width=\"25\" class=\"noday\">&nbsp;</td>";
    }

    html += "</tbody><tfoot><tr><td colspan=\"7\"><div style=\"text-align: center; width: 181px;\"><a href=\"#\" onclick=\"DateChooser.getById(" + this.id + ").close(); return false;\">" + "schliessen" + "</a></div></td></tr></tfoot></table></div></div></div>";

    targetElement.innerHTML = html;
  };

  this.getId = function()
  {
    return this.id;
  };

  this.setDate = function( year, month, day )
  {
    this.selectedYear = year;
    this.selectedMonth = month;
    this.selectedDay = day;
  };

  this.open = function()
  {
    this.render(this.selectedYear, this.selectedMonth);
    this.isOpen = true;
  };

  this.close = function()
  {
    targetElement.innerHTML = "";
    this.isOpen = false;
  };

  this.toggle = function()
  {
    if( this.isOpen )
    {
      this.close();
    }
    else
    {
      this.open();
    }
  };

  this.choose = function( year, month, day )
  {
    this.selectedYear = year;
    this.selectedMonth = month;
    this.selectedDay = day;

    this.callback(year, month, day);
  };

{
  if( year == null || year == undefined || month == null || month == undefined || day == null || day == undefined )
  {
    var today = new Date();
    year = today.getFullYear();
    month = today.getMonth() + 1;
    day = today.getDate();
  }

  this.selectedYear = year;
  this.selectedMonth = month;
  this.selectedDay = day;

  this.isOpen = false;

  if( DateChooser.elements == undefined || DateChooser.elements == null )
  {
    DateChooser.elements = [];
  }
  if( DateChooser.elementsById == undefined || DateChooser.elementsById == null )
  {
    DateChooser.elementsById = {};
  }

  this.id = DateChooser.elements.length;

  if( typeof( targetElement ) == "string" )
  {
    targetElement = document.getElementById(targetElement);
  }

  this.targetElement = targetElement;

  this.callback = callback;

  DateChooser.elements.push(this);
  DateChooser.elementsById[targetElement.id] = this;
}
}

DateChooser.getById = function( id )
{
  return DateChooser.elements[id];
};

DateChooser.getByElementId = function( id )
{
  return DateChooser.elementsById[id];
};

