if (typeof(CL) == 'undefined') CL = function() {};

// CL.Calender コンストラクタの定義
CL.Calender = function(eid, fid, labelname, inputname, monthflag, fetureflag)
{
	// 月指定有りか
	if (monthflag == undefined) {
		monthflag = true;
	}

	// 未来日の指定が可能か
	if (fetureflag == undefined) {
		fetureflag = true;
	}

	this.eid = eid;
	this.formid = fid;
	this.labelname = labelname;
	this.inputname = inputname;
	this.monthflag = monthflag;
	this.fetureflag = fetureflag;

	this.__dispelem = null;		// カレンダー表示欄エレメント
	this.__textelem = null; 	// テキスト入力欄エレメント
	this.__inputelem = null;	// 入力エレメント

	this.date = new Date();		// 現在日付
	this.style = new CL.Calender.Style();

	return this;
}


// CL.Calender.Style
CL.Calender.Style = function()
{
	this.frame_width         = "220px";
	this.frame_color         = "#43A5BA";       // フレーム 色
//	this.font_size           = "12px";
	this.day_bgcolor         = "#FFFFFF";       // カレンダーの背景色
	this.month_color         = "#FFFFFF";
	this.month_hover_color   = "#F0F0FF";
	this.month_hover_bgcolor = "#FFA020";
	this.weekday_color       = "#6E2C23";       // 月曜～金曜の色
	this.saturday_color      = "#0040D0";       // 土曜の色
	this.sunday_color        = "#D00000";       // 日曜の色
	this.others_color        = "#999999";       // 他の月の色
	this.day_hover_bgcolor   = "#FFA020";

	return this;
}


CL.Calender.Style.prototype.set = function(key, val)
{
	this[key] = val;
}


CL.Calender.Style.prototype.get = function(key)
{ 
	return this[key];
}


CL.Calender.prototype.setStyle = function(key, val)
{
	this.style.set(key,val);
}


CL.Calender.prototype.getStyle = function(key)
{
	return this.style.get(key);
}


// カレンダー表示欄のエレメントを返す
CL.Calender.prototype.getCalenderElement = function ()
{
	if (this.__dispelem) {
		return this.__dispelem;
	}

	this.__dispelem = document.getElementById( this.eid )
	return this.__dispelem;
}


// 表示ラベルのエレメントを返す
CL.Calender.prototype.getFormElement = function ()
{
    if (this.__textelem) {
		return this.__textelem;
	}

	this.__textelem = document.getElementById( this.labelname );
	return this.__textelem;
}


// 入力のエレメントを返す
CL.Calender.prototype.getInputElement = function ()
{
    if (this.__inputelem) {
		return this.__inputelem;
	}

	this.__inputelem = document.getElementById( this.inputname );
	return this.__inputelem;
}


// オブジェクトに日付を記憶する（YYYY-MM-DD形式で指定する）
CL.Calender.prototype.setDateYMD = function (ymd)
{
	var splt = ymd.split( "-" );

	if (splt[0] > 0 && 
		splt[1] >= 1 && splt[1] <= 12 &&
		splt[2] >= 1 && splt[2] <= 31) {
		this.date.setYear( splt[0] );
		this.date.setMonth( splt[1]-1 );
		this.date.setDate( splt[2] );
	} else {
		ymd = "";
	}
	return ymd;
}


// オブジェクトから日付を取り出す（YYYY-MM-DD形式で返る）
CL.Calender.prototype.getDateYMD = function (dd)
{
    if (dd == null) {
		dd = this.date;
	}
    return dd.getFullYear() + "-" + (dd.getMonth()+1) + "-" + dd.getDate();
}


// 現在までの日付かチェック
CL.Calender.prototype.isTodate = function (dd) 
{
	if (dd == null) {
		return false;
	}

	var now = new Date();

	if (dd <= now) {
		return true;
	}
	
	return false;
}


// テキスト入力欄の値を返す（ついでにオブジェクトも更新する）
CL.Calender.prototype.getFormValue = function ()
{
	var input = this.getInputElement();
	if (input == null) {
		return "";
	}

	var date1 = this.setDateYMD( input.value );
	return date1;
}


// 年月日のフォーマットに変換
CL.Calender.prototype.toDisplayDate = function (ymd)
{
	var splt = ymd.split( "-" );

	if (splt[2] == undefined) {
		return splt[0] + "年" + splt[1] + "月";
	} else {
		return splt[0] + "年" + splt[1] + "月" + splt[2] + "日";
	}
}

// 内容だけリセット
CL.Calender.prototype.resetvalue = function ()
{
	var form1 = this.getFormElement();
	if (form1) {
		this.writeLabel(form1, "指定なし");
	}

	var input1 = this.getInputElement();
	if (input1) {
		input1.value = "";
	}
}


// 内容がテキストだけの場合のみ
CL.Calender.prototype.writeLabel = function (obj, value)
{
	if (obj.firstChild) {
		// DOM1
		obj.firstChild.nodeValue=value; 
	} else if(typeof(obj.innerText)=="string") {
		// IE4
		obj.innerText = value;
	} else if(document.createTextNode) {
		// DOM1
		var newText = document.createTextNode(value); 
		obj.appendChild(newText); 
	}
}


// フォーム入力欄に指定した値を書き込む
CL.Calender.prototype.setFormValue = function (ymd)
{
	// 無指定時はオブジェクトから？
	if (!ymd) {
		ymd = this.getDateYMD();
	}

	var form1 = this.getFormElement();
	if (form1) {
		this.writeLabel(form1, this.toDisplayDate(ymd));
	}

	var input1 = this.getInputElement();
	if (input1) {
		input1.value = ymd;
	}
}


//  カレンダー表示欄を表示する
CL.Calender.prototype.show = function ()
{
    this.getCalenderElement().style.display = "";
}


//  カレンダー表示欄を即座に隠す
CL.Calender.prototype.hide = function ()
{
    this.getCalenderElement().style.display = "none";
}


//  カレンダー表示欄を終了
CL.Calender.prototype.close = function ()
{
    this.hide();
}


// 月単位で移動する
CL.Calender.prototype.moveMonth = function (mon)
{
	// 前へ移動
	for ( ; mon<0; mon++) {
		this.date.setDate(1);   // 毎月1日の1日前は必ず前の月
		this.date.setTime( this.date.getTime() - (24*3600*1000) );
	}

	// 後へ移動
	for ( ; mon>0; mon--) {
		this.date.setDate(1);   // 毎月1日の32日後は必ず次の月
		this.date.setTime( this.date.getTime() + (24*3600*1000)*32 );
	}

	this.date.setDate(1);       // 当月の1日に戻す
	this.write();               // 描画する
}


// カレンダーを描画する
CL.Calender.prototype.write = function ()
{
	var date = new Date();
	date.setTime( this.date.getTime() );
	var year = date.getFullYear();		// 指定年
	var mon  = date.getMonth();			// 指定月
	var today = date.getDate();			// 指定日
	var ymid = year + "-" + (mon+1);	// 年月

	// 直前の月曜日まで戻す

	// 1日に戻す
	date.setDate(1);

	var wday = date.getDay();// 曜日取得 日曜(0)～土曜(6)
	if (wday != 0) {
		date.setTime( date.getTime() - (24*3600*1000)*(wday) );
	}

	// 最大で7日×6週間＝42日分のループ
	var list = new Array();
	for (var i = 0; i < 42; i++) {
		var tmp = new Date();
		tmp.setTime( date.getTime() + (24*3600*1000)*i );
		if ( i && i%7==0 && tmp.getMonth() != mon ) break;
		list[list.length] = tmp;
	}

	// スタイルシートを生成する
	var month_table_style = 'width: 100%; ';
	month_table_style += 'background: '+this.style.frame_color+'; ';
	month_table_style += 'border: 1px solid '+this.style.frame_color+';';
	month_table_style += 'cursor: default;';

	var week_table_style = 'width: 100%; ';
	week_table_style += 'background: '+this.style.day_bgcolor+'; ';
	week_table_style += 'border-left: 1px solid '+this.style.frame_color+'; ';
	week_table_style += 'border-right: 1px solid '+this.style.frame_color+'; ';
	week_table_style += 'cursor: default;';

	var days_table_style = 'width: 100%; ';
	days_table_style += 'background: '+this.style.day_bgcolor+'; ';
	days_table_style += 'border: 1px solid '+this.style.frame_color+'; ';
	days_table_style += 'cursor: default;';

	var month_td_style = "";
	month_td_style += 'font-size: '+this.style.font_size+'; ';
	month_td_style += 'color: '+this.style.month_color+'; ';
	month_td_style += 'padding: 4px 0px 2px 0px; ';
	month_td_style += 'text-align: center; ';
	month_td_style += 'font-weight: bold;';

	var week_td_style = "";
	week_td_style += 'font-size: '+this.style.font_size+'; ';
	week_td_style += 'padding: 2px 0px 2px 0px; ';
	week_td_style += 'font-weight: bold;';
	week_td_style += 'text-align: center;';

	var days_td_style = "";
	days_td_style += 'font-size: '+this.style.font_size+'; ';
	days_td_style += 'padding: 1px; ';
	days_td_style += 'text-align: center; ';
	days_td_style += 'font-weight: bold;';

	// HTMLソースを生成する
	var src1 = "";

	src1 += '<table border="0" cellpadding="0" cellspacing="0" style="' + month_table_style + '">';
	src1 += '<tr style="' + month_table_style + '">';
	src1 += '<td style="' + month_td_style + '"></td>';
	src1 += '<td style="' + month_td_style + '"></td>';
	src1 += '<td style="' + month_td_style + '"></td>';
	src1 += '<td style="' + month_td_style + '"></td>';
	src1 += '<td style="' + month_td_style + '"></td>';
	src1 += '<td style="' + month_td_style + '"></td>';
	src1 += '<td id="__close" style="' + month_td_style + ' font-weight: bold;">×</td>';
	src1 += '</tr>';

	src1 += '<tr style="' + month_table_style + '">';
	src1 += '<td id="__' + this.eid + '_year_prev" title="前の年へ" style="' + month_td_style + '">≪</td>';
	src1 += '<td style="' + month_td_style + '" colspan=5>' + (year) + '</span>年 ' + '</td>';
	src1 += '<td id="__' + this.eid + '_year_next" title="次の年へ" style="' + month_td_style + '">≫</td>';
	src1 += '</tr>';

	src1 += '<tr style="' + month_table_style + '">';
	src1 += '<td id="__' + this.eid + '_btn_prev" title="前の月へ" style="' + month_td_style + '" colspan=2>≪</td>';
	if (this.fetureflag || this.isTodate(date)) {
		src1 += '<td id="__' + this.eid + '_month#' + ymid + '" style="' + month_td_style + '"colspan=3>' + (mon+1) + '</span>月</td>';
	} else {
		src1 += '<td style="' + month_td_style + '" colspan=3>' + (mon+1) + '</span>月</td>';
	}
	src1 += '<td id="__' + this.eid + '_btn_next" title="次の月へ" style="' + month_td_style + '"colspan=2>≫</td>';
	src1 += '</tr>';

	src1 += '<tr style="' + week_table_style + '">';
	src1 += '<td style="color: '+this.style.sunday_color+'; '+week_td_style+'">日</td>';
	src1 += '<td style="color: '+this.style.weekday_color+'; '+week_td_style+'">月</td>';
	src1 += '<td style="color: '+this.style.weekday_color+'; '+week_td_style+'">火</td>';
	src1 += '<td style="color: '+this.style.weekday_color+'; '+week_td_style+'">水</td>';
	src1 += '<td style="color: '+this.style.weekday_color+'; '+week_td_style+'">木</td>';
	src1 += '<td style="color: '+this.style.weekday_color+'; '+week_td_style+'">金</td>';
	src1 += '<td style="color: '+this.style.saturday_color+'; '+week_td_style+'">土</td>';
	src1 += '</tr>';

	for (var i = 0; i < list.length; i++) {
		var dd = list[i];

		var ww = dd.getDay();
		if (ww == 0) {
			// 月曜日の前
			src1 += '<tr style="'+days_table_style+'">';
		}

		var cc;
		if (mon != dd.getMonth()) {
			// 指定月以外
			cc = this.style.others_color;
		} else {
			switch (ww) {
				case 0:
					cc = this.style.sunday_color;
					break;
				case 6:
					cc = this.style.saturday_color;
					break;
				default:
					cc = this.style.weekday_color;
					break;
			}
		}

		var ss = this.getDateYMD(dd);
		
		if (this.fetureflag || this.isTodate(dd)) {
			src1 += '<td style="color: '+cc+'; '+days_td_style+'" title='+ss+' id="__'+this.eid+'_td_#'+ss+'">'+dd.getDate()+'</td>';
		} else {
			cc = this.style.others_color;
			src1 += '<td style="color: '+cc+'; '+days_td_style+'" title='+ss+'>'+dd.getDate()+'</td>';
		}

		if (ww == 6) {
			// 土曜日の後ろ
			src1 += '</tr>';
		}
	}
	src1 += "</table>\n";

    // カレンダーを書き換える
    var cal1 = this.getCalenderElement();
    if (!cal1) return;
    cal1.style.width = this.style.frame_width;
    cal1.style.position = "absolute";
    cal1.innerHTML = src1;

    // イベントを登録する
    var copy = this;

	// 閉じるボタン
	var tdclose = document.getElementById( "__close" );
	tdclose.onclick = function () {
		copy.close();
	}
	tdclose.onmouseover = function () {
	    // this.style.textDecoration = "underline";
	    this.style.color = copy.style.month_hover_color;
	    this.style.background = copy.style.month_hover_bgcolor;
	}
	tdclose.onmouseout = function () {
	    // this.style.textDecoration = "none";
	    this.style.color = copy.style.month_color;
	    this.style.background = copy.style.frame_color;
	}

	// 月で指定
	if (this.monthflag) {
	    var tdmonth = document.getElementById( "__"+this.eid+"_month#" + ymid );
		if (tdmonth != null) {
		    tdmonth.onclick = function () {
		        var splt = this.id.split( "#" );
		        copy.setFormValue( splt[1] );
		        copy.close();
		    }
		    tdmonth.onmouseover = function () {
		        // this.style.textDecoration = "underline";
		        this.style.color = copy.style.month_hover_color;
		        this.style.background = copy.style.month_hover_bgcolor;
		    }
		    tdmonth.onmouseout = function () {
		        // this.style.textDecoration = "none";
		        this.style.color = copy.style.month_color;
		        this.style.background = copy.style.frame_color;
		    }
		}
	}

	// 前の年へ
	var tdyprev = document.getElementById( "__"+this.eid+"_year_prev" );
	tdyprev.onclick = function () {
	    copy.moveMonth( -12 );
	}
	tdyprev.onmouseover = function () {
	    // this.style.textDecoration = "underline";
	    this.style.color = copy.style.month_hover_color;
	    this.style.background = copy.style.month_hover_bgcolor;
	}
	tdyprev.onmouseout = function () {
	    // this.style.textDecoration = "none";
	    this.style.color = copy.style.month_color;
	    this.style.background = copy.style.frame_color;
	}
	// 次の年へ
	var tdynext = document.getElementById( "__"+this.eid+"_year_next" );
	tdynext.onclick = function () {
	    copy.moveMonth( +12 );
	}
	tdynext.onmouseover = function () {
	    // this.style.textDecoration = "underline";
	    this.style.color = copy.style.month_hover_color;
	    this.style.background = copy.style.month_hover_bgcolor;
	}
	tdynext.onmouseout = function () {
	    // this.style.textDecoration = "none";
	    this.style.color = copy.style.month_color;
	    this.style.background = copy.style.frame_color;
	}

	// 前の月へ
	var tdprev = document.getElementById( "__"+this.eid+"_btn_prev" );
	tdprev.onclick = function () {
	    copy.moveMonth( -1 );
	}
	tdprev.onmouseover = function () {
	    // this.style.textDecoration = "underline";
	    this.style.color = copy.style.month_hover_color;
	    this.style.background = copy.style.month_hover_bgcolor;
	}
	tdprev.onmouseout = function () {
	    // this.style.textDecoration = "none";
	    this.style.color = copy.style.month_color;
	    this.style.background = copy.style.frame_color;
	}
	// 次の月へ
	var tdnext = document.getElementById( "__"+this.eid+"_btn_next" );
	tdnext.onclick = function () {
	    copy.moveMonth( +1 );
	}
	tdnext.onmouseover = function () {
	    // this.style.textDecoration = "underline";
	    this.style.color = copy.style.month_hover_color;
	    this.style.background = copy.style.month_hover_bgcolor;
	}
	tdnext.onmouseout = function () {
	    // this.style.textDecoration = "none";
	    this.style.color = copy.style.month_color;
	    this.style.background = copy.style.frame_color;
	}

	// セルごとのイベントを登録する
	for ( var i=0; i<list.length; i++ ) {
		var dd = list[i];
		if ( mon != dd.getMonth() ) continue;   // 今月のみ設定する
		var ss = this.getDateYMD(dd);
		var cc = document.getElementById( "__"+this.eid+"_td_#"+ss );
		if (!cc) {
			continue;
		}
		cc.onmouseover = function () {
		    // this.style.textDecoration = "underline";
		    this.style.background = copy.style.day_hover_bgcolor;
		}
		cc.onmouseout = function () {
		    // this.style.textDecoration = "none";
		    this.style.background = copy.style.day_bgcolor;
		}
		cc.onclick = function () {
		    var splt = this.id.split( "#" );
		    copy.setFormValue( splt[1] );
		    copy.close( 1.0 );
		}
	}

    // 表示する
    this.show();
}
