﻿var NOW = new Date();
$.browser.msie6 = $.browser.msie && ($.browser.version && $.browser.version < 7 || /MSIE 6.0/.test(navigator.userAgent));

if (typeof JS_BASEPATH == "undefined")
	JS_BASEPATH = ""

/********************************************************
 * Prototype functions
 *
 * String.trim()
 *
 *
 ********************************************************/

String.prototype.trim = function()
{
	return this.replace(/(^[\s]*)|([\s]*$)/g, "");
}

/********************************************************
 * AJAX
 *
 * ajaxInclude(url, elem)
 * ajaxInvoke(url, callback)
 * ajaxPulldown(url, elem, sep, callback)
 * ajaxSubmit(form, blocking)
 *
 ********************************************************/

function ajaxInclude(url, el, history, callback)
{
	if (history)
		$.history.save(url)

	if (typeof el == "string") el = gE(el)

	var l919 = $('<div id=div919 style="position:absolute; background:#fff url('+JS_BASEPATH+'/static/GUIControl/wait.gif); filter:alpha(opacity=40); -moz-opacity:0.4; opacity:0.4; display:none;"></div>')
	l919.prependTo(el);
	var div919 = gE("div919")

 	if (div919.style)
 	{
		moveRelTo(gE("div919"), el)
		div919.style.width = el.offsetWidth;
		div919.style.height = el.offsetHeight;
	}

	$(el).load(url.replace(/ /, "+"), null, callback)
}

function ajaxInvoke(url, callback)
{
	$.getScript(url, callback)
}

function ajaxPulldown(url, el, sep, callback)
{
	if (typeof el == "string") el = gE(el)
	el.disabled = 1

	$.get(url, null, function(str){
		var arr = str.trim().split(sep)

		for (var i=el.options.length; --i>=0;)
			el.options[i]=null

		for (var i in arr)
		{
			var vals = arr[i].trim().split('=')

			if (vals.length>1)
				el.options[el.length] = new Option(vals[1].trim(), vals[0].trim())
		}

		el.disabled = 0

		if (callback)
			callback()
		else if (el.type == "select-one")
			$(el).trigger("change")
	})
}

function ajaxSubmit(f, blocking, el)
{
	if (blocking)
		waitforinput(true)

	$.ajax({
		type: "POST", url: f.action, data: $(f).serialize(), dataType: el ? "html" : "script",
		success: el ? function(x) { $(el).html(x); return this } : null
	})
}

// refer to: http://valums.com/ajax-upload/
ajaxUpload_uuid=0
function ajaxUpload2(button, action, onselect, oncomplete)
{
	button = $(button)
	var wrapper = $("<div style=position:relative;display:block;overflow:hidden;width:"+button.outerWidth(1)+"px;height:"+button.outerHeight(1)+"px ></div>").insertAfter(button).append(button)
	wrapper._input = $("<input type=file name="+button.attr("name")+" style=position:absolute;margin:0;padding:0;width:220px;height:10px;filter:alpha(opacity=0);-moz-opacity:0;opacity:0;cursor:pointer />").appendTo(wrapper)
	wrapper._action = action
	wrapper._onselect = onselect
	wrapper._oncomplete = oncomplete
	wrapper.mousemove(function(e){
		var ofs = wrapper.offset()
		wrapper._input.css("top", (e.pageY - ofs.top - 5) + "px").css("left", (e.pageX - ofs.left - 170) + "px")
	});

	wrapper._input.change(function(){
		if (!wrapper._input.val())
			return

		var data = {}

		if (wrapper._onselect && !wrapper._onselect(wrapper._input.val(), data))
			return

		var iframe = $("<iframe name=ajaxuploadiframe"+ajaxUpload_uuid+" style=display:none ></iframe>").appendTo("body")
		var form = $("<form action='"+wrapper._action+"' method=post target=ajaxuploadiframe"+ajaxUpload_uuid+" enctype='multipart/form-data' style=display:none ></form>").appendTo("body")

		for (var name in data)
			$("<input name="+name+" />").appendTo(form).val(data[name])

		wrapper._input.appendTo(form)
		ajaxUpload_uuid++

		iframe.load(function(){
			if (iframe[0].src == "about:blank")
				return;

			wrapper.children(0).focus()

			if (wrapper._oncomplete)
				wrapper._oncomplete(wrapper._input.val() + "\n" + iframe.contents().find('body').html())
		});

		form.submit()
		wrapper._input.appendTo(wrapper).val("")
	})
}
ajaxUpload = function(url, onselect, oncomplete, onerror)
{
	if (typeof ajaxuploadDiv == "undefined")
	{
		$("<div id=ajaxuploadDiv></div>").appendTo(document.body)

		var swf = new SWFObject(JS_BASEPATH + "/static/GUIControl/fileupload.lzx.swf", "ajaxfileupload", 0, 0, 8, "", true)
		swf.addVariable("browseOnStart", true)
		swf.write("ajaxuploadDiv")
	}
	else
		window.document.ajaxfileupload.browse()

	var ajaxuploadDiv = gE("ajaxuploadDiv")
	ajaxuploadDiv.onselect = function() { if (!onselect || onselect()) window.document.ajaxfileupload.upload(url); }
	ajaxuploadDiv.oncomplete = oncomplete
	ajaxuploadDiv.onerror = onerror
}

if ($.browser.msie)
ajaxUpload = function(url, onselect, oncomplete, onerror)
{
	if (typeof ifUpload == "undefined")
		$("<iframe id=ifUpload style=width:0;height:0 onload=ajaxuploadcallback()></iframe>").appendTo(document.body)

	var fr = gE("ifUpload")
	fr._url = url
	fr._onselect = onselect
	fr._oncomplete = oncomplete
	fr._onerror = onerror
	fr._mode = 1

	if (ifUpload.document.body)
		ajaxuploadcallback()
}
	ajaxuploadcallback = function()
	{
		var d = ifUpload.document
		var fr = gE("ifUpload")

		if (fr._mode)
		{
			fr._mode = 0
			d.charset = document.charset
			d.body.innerHTML = "<form name=f method=post enctype='multipart/form-data'><input name=file type=file></form>";

			d.f.action = fr._url
			d.f.file.onchange = function() {
				if (!fr._onselect || fr._onselect(d.f.file.value)) d.f.submit(); }
			d.f.file.click()
		}
		else if (d.body.innerHTML && d.body.innerHTML != "ERROR")
			fr._oncomplete(d.body.innerHTML)
		else
			fr._onerror(d.body.innerHTML)
	}

function urlencode(s)
{
	var v = ""

	for (var i = 0, l = s.length; i<l; i++)
	{
		var ch = s.charCodeAt(i)

		if (ch < 128)
		{
			v += s.charAt(i)
		}
		else
		{
			var c1 = (ch & 0xff00) >> 8
			var c2 = ch & 0x00ff

			if (ch < 2048)
			{
				// 110xxxxx 10xxxxxx
				var x1 = 192 | (c1 << 2 & 28) | (c2 >> 6)
				var x2 = 128 | (c2 & 63)

				v += "%" + x1.toString(16) + "%" + x2.toString(16)
			}
			else if (ch < 65536)
			{
				// 1110xxxx 10xxxxxx 10xxxxxx
				var x1 = 224 | (c1 >> 4)
				var x2 = 128 | (c1 << 2 & 60) | (c2 >> 6)
				var x3 = 128 | (c2 & 63)

				v += "%" + x1.toString(16) + "%" + x2.toString(16) + "%" + x3.toString(16)
			}
		}
	}

	return v
}

/********************************************************
 * Basic checking functions
 *
 * isDecimalNumber(input,precision,scale)
 * isIpAddress(ip)
 * isEmail(s)
 * isSimpleWord(s)
 * isChineseSimpleWord(s)
 * isBefore(d1, d2)
 *
 ********************************************************/

function isDecimalNumber(input, precision, scale)
{
	var dotPos = input.indexOf(".");
	var len = input.length;

	if (dotPos > 0)
	{
		if (dotPos > precision - scale) // check the LHS of the decimcal-point
			return false;

		if (len - dotPos - 1 > scale) // check the RHS of the decimal-point
			return false;
	}
	else
	{
		if (len > precision - scale)
			return false;
	}

	return !isNaN(input);
}

// check if the string is an email
function isEmail(s)
{
	if ("@.".indexOf(s.charAt(0)) != -1)
		return false

	var p = s.split("@")
	var regex = /^[-\d\w]*$/;

	for (var i in p)
	{
		var q = p[i].split(".")

		if (i > 0 && q.length < 2)
			return false

		for (var j in q)
		{
			if (!q[j] && i > 0)
				return false

			if (!regex.test(q[j]))
				return false
		}
	}

	return p.length == 2
}

// check if the string is a valid variable-syntaxed string
function isSimpleWord(s)
{
	var regex = /^[_\w\d]*$/;
	return regex.test(s)
}

function isChineseSimpleWord(s)
{
	var regex = /^[_\w\d\u4E00-\u9FA5]{0,20}$/;
	return regex.test(s)
}

function isIpAddress(ip)
{
	var regex = /^\d{1,3}[.]\d{1,3}[.]\d{1,3}$/;
	return regex.test(ip);
}

function isPhone(s)
{
	//校验普通电话、传真号码：可以“+”开头，除数字外，可含有“-”
	//var regex = /^[\d \-\+\(\)]{1,20}$/;
	var regex = /^[+]{0,1}(\d){1,3}[ ]?([-]?((\d)|[ ]){1,12})+$/ ;
	return regex.test(s);
}

/**
 * @return true if s1 is earlier than s2
 */
function isBefore(s1, s2)
{
	if (s1 == "" || s2 == "")
		return true;

	var d1 = parseDate2(s1, "yyyy-MM-dd") || parseDate2(s1, "yyyy-MM-dd HH:mm") || parseDate2(s1, "yyyy-MM-dd HH:mm:ss")
	var d2 = parseDate2(s2, "yyyy-MM-dd") || parseDate2(s2, "yyyy-MM-dd HH:mm") || parseDate2(s2, "yyyy-MM-dd HH:mm:ss")

	return d1 <= d2
}

function keycode(e)
{
	if ($.browser.msie)
		return typeof window.event != "undefined" ? window.event.keyCode : 0
	else
		return typeof e != "undefined" ? e.which : 0
}






/********************************************************
 * Date related functions
 *
 * formatDate(date, formatStr)
 * parseDate2(dateStr, formatStr)
 *
 *
 ********************************************************/

var MONTH_NAMES=new Array('January','February','March','April','May','June','July','August','September','October','November','December','Jan','Feb','Mar','Apr','May','Jun','Jul','Aug','Sep','Oct','Nov','Dec');
var DAY_NAMES=new Array('Sunday','Monday','Tuesday','Wednesday','Thursday','Friday','Saturday','Sun','Mon','Tue','Wed','Thu','Fri','Sat');
function LZ(x) {return(x<0||x>9?"":"0")+x}

// Returns a date in the output format specified.
function formatDate(date,format) {
	format=format+"";
	var result="";
	var i_format=0;
	var c="";
	var token="";
	var y=date.getYear()+"";
	var M=date.getMonth()+1;
	var d=date.getDate();
	var E=date.getDay();
	var H=date.getHours();
	var m=date.getMinutes();
	var s=date.getSeconds();
	var yyyy,yy,MMM,MM,dd,hh,h,mm,ss,ampm,HH,H,KK,K,kk,k;
	// Convert real date parts into formatted versions
	var value=new Object();
	if (y.length < 4) {y=""+(y-0+1900);}
	value["y"]=""+y;
	value["yyyy"]=y;
	value["yy"]=y.substring(2,4);
	value["M"]=M;
	value["MM"]=LZ(M);
	value["MMM"]=MONTH_NAMES[M-1];
	value["NNN"]=MONTH_NAMES[M+11];
	value["d"]=d;
	value["dd"]=LZ(d);
	value["E"]=DAY_NAMES[E+7];
	value["EE"]=DAY_NAMES[E];
	value["H"]=H;
	value["HH"]=LZ(H);
	if (H==0){value["h"]=12;}
	else if (H>12){value["h"]=H-12;}
	else {value["h"]=H;}
	value["hh"]=LZ(value["h"]);
	if (H>11){value["K"]=H-12;} else {value["K"]=H;}
	value["k"]=H+1;
	value["KK"]=LZ(value["K"]);
	value["kk"]=LZ(value["k"]);
	if (H > 11) { value["a"]="PM"; }
	else { value["a"]="AM"; }
	value["m"]=m;
	value["mm"]=LZ(m);
	value["s"]=s;
	value["ss"]=LZ(s);
	while (i_format < format.length) {
		c=format.charAt(i_format);
		token="";
		while ((format.charAt(i_format)==c) && (i_format < format.length)) {
			token += format.charAt(i_format++);
			}
		if (value[token] != null) { result=result + value[token]; }
		else { result=result + token; }
		}
	return result;
	}

// This function takes a date string and a format string. It matches
// If the date string matches the format string, it returns the
// getTime() of the date. If it does not match, it returns 0.
function parseDate2(val,format) {
	val=val+"";
	format=format+"";
	var i_val=0;
	var i_format=0;
	var c="";
	var token="";
	var token2="";
	var x,y;
	var now=new Date();
	var year=now.getYear();
	var month=now.getMonth()+1;
	var date=1;
	var hh=now.getHours();
	var mm=now.getMinutes();
	var ss=now.getSeconds();
	var ampm="";

	while (i_format < format.length) {
		// Get next token from format string
		c=format.charAt(i_format);
		token="";
		while ((format.charAt(i_format)==c) && (i_format < format.length)) {
			token += format.charAt(i_format++);
			}
		// Extract contents of value based on format token
		if (token=="yyyy" || token=="yy" || token=="y") {
			if (token=="yyyy") { x=4;y=4; }
			if (token=="yy")   { x=2;y=2; }
			if (token=="y")    { x=2;y=4; }
			year=_getInt(val,i_val,x,y);
			if (year==null) { return 0; }
			i_val += year.length;
			if (year.length==2) {
				if (year > 70) { year=1900+(year-0); }
				else { year=2000+(year-0); }
				}
			}
		else if (token=="MMM"||token=="NNN"){
			month=0;
			for (var i=0; i<MONTH_NAMES.length; i++) {
				var month_name=MONTH_NAMES[i];
				if (val.substring(i_val,i_val+month_name.length).toLowerCase()==month_name.toLowerCase()) {
					if (token=="MMM"||(token=="NNN"&&i>11)) {
						month=i+1;
						if (month>12) { month -= 12; }
						i_val += month_name.length;
						break;
						}
					}
				}
			if ((month < 1)||(month>12)){return 0;}
			}
		else if (token=="EE"||token=="E"){
			for (var i=0; i<DAY_NAMES.length; i++) {
				var day_name=DAY_NAMES[i];
				if (val.substring(i_val,i_val+day_name.length).toLowerCase()==day_name.toLowerCase()) {
					i_val += day_name.length;
					break;
					}
				}
			}
		else if (token=="MM"||token=="M") {
			month=_getInt(val,i_val,token.length,2);
			if(month==null||(month<1)||(month>12)){return 0;}
			i_val+=month.length;}
		else if (token=="dd"||token=="d") {
			date=_getInt(val,i_val,token.length,2);
			if(date==null||(date<1)||(date>31)){return 0;}
			i_val+=date.length;}
		else if (token=="hh"||token=="h") {
			hh=_getInt(val,i_val,token.length,2);
			if(hh==null||(hh<1)||(hh>12)){return 0;}
			i_val+=hh.length;}
		else if (token=="HH"||token=="H") {
			hh=_getInt(val,i_val,token.length,2);
			if(hh==null||(hh<0)||(hh>23)){return 0;}
			i_val+=hh.length;}
		else if (token=="KK"||token=="K") {
			hh=_getInt(val,i_val,token.length,2);
			if(hh==null||(hh<0)||(hh>11)){return 0;}
			i_val+=hh.length;}
		else if (token=="kk"||token=="k") {
			hh=_getInt(val,i_val,token.length,2);
			if(hh==null||(hh<1)||(hh>24)){return 0;}
			i_val+=hh.length;hh--;}
		else if (token=="mm"||token=="m") {
			mm=_getInt(val,i_val,token.length,2);
			if(mm==null||(mm<0)||(mm>59)){return 0;}
			i_val+=mm.length;}
		else if (token=="ss"||token=="s") {
			ss=_getInt(val,i_val,token.length,2);
			if(ss==null||(ss<0)||(ss>59)){return 0;}
			i_val+=ss.length;}
		else if (token=="a") {
			if (val.substring(i_val,i_val+2).toLowerCase()=="am") {ampm="AM";}
			else if (val.substring(i_val,i_val+2).toLowerCase()=="pm") {ampm="PM";}
			else {return 0;}
			i_val+=2;}
		else {
			if (val.substring(i_val,i_val+token.length)!=token) {return 0;}
			else {i_val+=token.length;}
			}
		}
	// If there are any trailing characters left in the value, it doesn't match
	if (i_val != val.length) { return 0; }
	// Is date valid for month?
	if (month==2) {
		// Check for leap year
		if ( ( (year%4==0)&&(year%100 != 0) ) || (year%400==0) ) { // leap year
			if (date > 29){ return 0; }
			}
		else { if (date > 28) { return 0; } }
		}
	if ((month==4)||(month==6)||(month==9)||(month==11)) {
		if (date > 30) { return 0; }
		}
	// Correct hours value
	if (hh<12 && ampm=="PM") { hh=hh-0+12; }
	else if (hh>11 && ampm=="AM") { hh-=12; }
	var newdate=new Date(year,month-1,date,hh,mm,ss);
	return newdate.getTime();
}
function _isInteger(val) {
	var digits="1234567890";
	for (var i=0; i < val.length; i++) {
		if (digits.indexOf(val.charAt(i))==-1) { return false; }
		}
	return true;
	}
function _getInt(str,i,minlength,maxlength) {
	for (var x=maxlength; x>=minlength; x--) {
		var token=str.substring(i,i+x);
		if (token.length < minlength) { return null; }
		if (_isInteger(token)) { return token; }
		}
	return null;
	}



/********************************************************
 * Form validation object
 *
 * .checkEmpty(input, msg)
 * .checkNonLatin(input, msg)
 * .checkLength(input, msg, min, max)
 * .checkNumber(input, msg, precision, scale, minVal, maxVal)
 * .checkEmail(input, msg)
 * .checkSimpleWord(input, msg)
 * .checkPhone(input, msg)
 * .checkAfter(input1, input2, msg)
 * .checkDate(input1, msg)
 * .execute(msg)
 *
 *
 ********************************************************/

// form submission check
function Checker(form, skipcheck)
{
	this.frm = form;
	this.msg = "";
	this.err = [];

	if (typeof FCKeditorAPI != "undefined")
		for (var i=0; i<form.elements.length; i++)
		{
			var n = form.elements[i].name;
			if (gE("fck_"+n) && gE("fck_"+n).fckOK)
				form.elements[n].value = FCKeditorAPI.GetInstance("fck_"+n).GetXHTML(true)
		}

	if ((typeof skipcheck == "undefined" || !skipcheck) && typeof this.frm.chk != "undefined")
		for (var name in this.frm.chk)
		{
			var arr = this.frm.chk[name]
			var ctl = this.frm.elements[name]
			var tit = arr.length >= 3 ? arr[2] : this._titleOf(ctl)

			if (arr[1]) // mandatory
				this.checkEmpty(ctl, tit + _L12N_["REQ"])

			if (arr[0].toLowerCase() == "integer")
				this.checkNumber(ctl, tit + _L12N_["REQ_INT"], 38, 0, -100000000, 100000000)
			else if (arr[0].toLowerCase() == "float")
				this.checkNumber(ctl, tit + _L12N_["REQ_NUM"], 38, 2, -100000000, 100000000)
			else if (arr[0].toLowerCase() == "date" || arr[0].toLowerCase() == "datetime")
				this.checkDate(ctl, tit + _L12N_["REQ_DATE"])
			else if ((arr[0].toLowerCase() == "longtext" || arr[0].toLowerCase() == "multiline") && ctl.maxlength > 0)
				this.checkLength(ctl, tit + _L12N_["REQ_MAXLENGTH1"] + ctl.maxlength + _L12N_["REQ_MAXLENGTH2"], 0, ctl.maxlength)
			else if (arr[0] == "MULTIPLELOOKUP")
				for (var i=0; i<ctl.options.length; i++)
					ctl.options[i].selected = true;
			else if (arr[0].toLowerCase() == "email")
				this.checkEmail(ctl, tit + _L12N_["REQ_EMAIL"])
		}
}

Checker.prototype._titleOf = function(obj)
{
	if (!obj)
		return ""

	if (obj.type != "select-one" && typeof obj.length == "number" && obj.length > 0)
		return obj[0].title

	return obj.title
}

Checker.prototype.appendErr = function(input, msg)
{
	msg = msg.trim()

	if (msg.length > 0)
	{
		this.msg += "\n"

		if (msg.charAt(0) != "-")
			this.msg += "- ";

		this.msg += msg;
	}

	if (typeof input == "object" && input != null)
		this.err.push(input.name);
	else if (input)
		this.err.push(input);

	return false;
}

Checker.prototype.valueOf = function(input)
{
	if (typeof input == "number")
		return input

	var v = typeof input == "string" ? this.frm[input].value : valueOf(input)
	return v == null ? "" : v.trim();
}

/**
 * validate this specified input field value is null or empty string.
 *
 * @param input - input field name
 * @param msg - error message when validat failed
 * @return - when the input value is null or empty string, return true. Otherwise, return false.
 **/
Checker.prototype.checkEmpty = function(input, msg)
{
	if (this.valueOf(input).length == 0 && countSelected(input) == 0)
		return this.appendErr(input, msg);

	return true;
}

/**
 * check if the given input contains any Chinese character
 *
 * @param input - input field name
 * @param msg - error message when validat failed
 * @return - when the input value is null or empty string, return true. Otherwise, return false.
 **/
Checker.prototype.checkNonLatin = function(input, msg)
{
	if (this.valueOf(input).search(/[^\x00-\x80]/) >= 0)
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkLength = function(input, msg, min, max)
{
	var s = this.valueOf(input)

	if (s.length < min || s.length > max)
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkNumber = function(input, msg, precision, scale, minVal, maxVal)
{
	var v = this.valueOf(input)
	precision = precision == null ? 38 : precision
	scale = scale == null ? 8 : scale

	if (typeof minVal == "undefined") minVal = -32768
	if (typeof maxVal == "undefined") maxVal = 32767

	if (v.length > 0 && (!isDecimalNumber(v, precision, scale) || v < minVal || v > maxVal))
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkPhone = function(input, msg)
{
	var v = this.valueOf(input)

	if (v.length > 0 && !isPhone(v))
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkEmail = function(input, msg)
{
	var v = this.valueOf(input)

	if (v.length > 0 && !isEmail(v))
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkSimpleWord = function(input, msg)
{
	var v = this.valueOf(input)

	if (v.length > 0 && !isSimpleWord(v))
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkChineseSimpleWord = function(input, msg)
{
	var v = this.valueOf(input)

	if (v.length > 0 && !isChineseSimpleWord(v))
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkPassword = function(input, msg)
{
	var v = this.valueOf(input)

	if (v.length > 0 && !(/\d/.test(v) && /[a-zA-Z]/.test(v)))
		return this.appendErr(input, msg);

	return true;
}

// if input2 is after input1, return true
Checker.prototype.checkAfter = function(input1, input2, msg)
{
	var TODAY = "[TODAY]";
	var t = new Date();
	var d1, d2;

	if (input1 == TODAY)
		d1 = t.getFullYear()+"-"+a0(t.getMonth()+1)+"-"+a0(t.getDate())
	else
		d1 = this.valueOf(input1)

	if (input2 == TODAY)
		d2 = t.getFullYear()+"-"+a0(t.getMonth()+1)+"-"+a0(t.getDate())
	else
		d2 = this.valueOf(input2)

	if (d1.length > 0 && d2.length > 0 && !isBefore(d1, d2)) // d1 < d2 ==> true
	{
		this.appendErr(input1, ""); // highlight only
	return this.appendErr(input2, msg);
	}

	return true;
}

Checker.prototype.checkDate = function(input, msg)
{
	var d = this.valueOf(input)

	if (d.length > 0 && parseDate2(d, "yyyy-MM-dd") == 0 &&
		parseDate2(d, "yyyy-MM-dd HH:mm") == 0 &&
		parseDate2(d, "yyyy-MM-dd HH:mm:ss") == 0)
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.checkTrue = function(input, bool, msg)
{
	if (bool)
		return this.appendErr(input, msg);

	return true;
}

Checker.prototype.execute = function(msg)
{
	for (var i in this.frm.elements)
	{
		var f = this.frm.elements[i]
		if (f != null && typeof f.type != "undefined" && typeof f.borderColor_ != "undefined")
			if (f.type == "text" || f.type == "password" || f.type == "textarea" || f.type == "file")
				f.style.borderColor = f.borderColor_;
	}

	if (this.msg != "")
	{
		__alert((msg||_L12N_["PLS_RETRY"]) + this.msg);

		for (var i in this.frm.elements)
		{
			var f = this.frm.elements[i]

			if (f != null && typeof f.type != "undefined")
				if (f.type == "text" || f.type == "password" || f.type == "checkbox" || f.type == "textarea" || f.type == "file")
					if ($.inArray(f.name, this.err) != -1)
					{
						f.borderColor_ = f.style.borderColor
						f.style.borderColor = "red";
					}
		}

		return false;
	}

	this.frm.dirty=0
	return true;
}

/********************************************************
 * Misc functions
 *
 * gE()
 * v()
 * __alert(msg)
 * valueOf(o)
 * selectItem()
 * toggleDisplay(arr)
 * swapImg(obj, imagename)
 * moveOption(list1, list2, val)
 *
 ********************************************************/

gE = function(s)
{
	var obj = document.getElementById(s)

	if(obj == null && $.browser.mozilla)
		obj = document.getElementsByName(s)[0]

	return obj
}
__alert = function(msg) { alert(msg.replace("<t>", "").replace("</t>", "")); }

/*
 * Return the given object's value
 * If the given object contains multiple instance (such as checkbox or an array of text input),
 * this function will return a comma-delimited string with all the values
 *
 * @param o - the specified object
 * @return - the string to be returned
 * NOTE: all string value are trimmed
 */
var v = valueOf = function(o, asArray)
{
	if (!o)
		return ""

	if (typeof o == "string" || typeof o == "number")
		return o

	if (typeof o == "object" || typeof o == "function") // assume it is a form object
	{
		var t = o.type

		if (t == "select-one")
		{
			if (o.selectedIndex != -1)
				return o.options[o.selectedIndex].value
		}
		else if (o.length)
		{
			var l = o.length
			var arr = []
			var isRadio = false
			// TODO: work with IE only :(
			// <select name="...." submit = "ALL|SELECTED" ><option....
			var submitSelected = typeof o.submit != "undefined" && o.submit == "SELECTED"

			for (var i = 0; i < l; i++)
			{
				if (i == 0 && !isRadio)
					isRadio = o[i].type == "radio"

				var v = valueOf(o[i])

				if (isRadio && v)
					return v

				if (v)
				{
					if (submitSelected)
					{
						if (o[i].selected)
							arr.push(v)
					}
					else
						arr.push(v)
				}
			}

			if (arr.length > 0)
				return asArray ? arr : arr.join(",");
		}
		else
		{
			if (t == "checkbox" || t == "radio")
			{
				if (o.checked)
					return o.value
				else
					return "";
			}
			else // if (t == "text" || t == "textarea" || t == "hidden" || t == "select")
			{
				var v = typeof o.submitvalue != "undefined" ? o.submitvalue : o.value

				if (v == "undefined")
					return ""

				if (typeof v == "string")
					return v.trim()

				return v
			}
		}
	}

	return ""
}

// count how many item was selected in a checkbox / radiogroup / listbox
function countSelected(o)
{
	if (!o)
		return 0

	if (o.type == "checkbox" || o.type == "radio")
		return o.checked ? 1 : 0;

	if (o.type == "select-one")
		//return o.selectedIndex != -1 ? 1 : 0;
		return 0

	var sel = 0;
	for (var i=o.length; --i>=0; )
		if (o[i].checked || o[i].selected)
			sel++;

	return sel;
}

// pre-select options according to the variables passed
var SELECT_ALL  = "@@SELECT_ALL@@"
var SELECT_NONE = "@@SELECT_NONE@@"
function selectItem()
{
	var args = selectItem.arguments;
	var frm

	for (var i=0; i<args.length-1; i+=2)
	{
		var obj = args[i]
		var val = args[i + 1]

		if (typeof obj == "undefined")
			continue

		if (typeof obj == "string")
			obj = frm.elements[args[i]];

		var t = obj.type

		if (t == 'checkbox' || t == 'radio')
		{
			obj.checked = (obj.value == val || val == SELECT_ALL) && val != SELECT_NONE;
		}
		else if (t == 'select-one' || t == 'select-multiple')
		{
			for (var j=0; j<obj.options.length; j++)
			{
				if (obj.options[j].value == val || val == SELECT_ALL)
					obj.options[j].selected = true;
				else if (val == SELECT_NONE)
					obj.options[j].selected = false;
			}
		}
		else if (obj.length)
		{
			for (var j=0; j < obj.length; j++)
			{
				var obj_ = obj[j]

				if (obj_.type == 'radio' || obj_.type == 'checkbox')
				{
					if (obj_.value == val || val == SELECT_ALL)
						obj_.checked = true;
					else if (val == SELECT_NONE)
						obj_.checked = false;
				}
				else if (obj_.type == 'text')
					obj_.value = val;
			}
		}
		else
			obj.value = args[i+1]
	}
}

function toggleDisplay(arr, state)
{
	for (var i=arr.length; --i>=0; )
	{
		if (typeof arr[i] == "string")
			arr[i] = gE(arr[i])

		if (arr[i])
			arr[i].style.display = state || (_style(arr[i],'display') == 'none' ? 'block' : 'none')
	}
}

function a0(i)
{
	return i>9 ? i : "0"+i
}

function swapImg(o,s)
{
	if (o == null)
		return

	if (o.tagName != "IMG")
	{
		if (s)
		{
			var x = _style(o, $.browser.msie ? "backgroundImage" : "background-image")
			o._src=x
			var j = x.lastIndexOf('/')
			o.style.backgroundImage = s.indexOf('/') < 0 ? x.substring(0,j+1) + s + ")" : s
		}
		else if (o._src)
			o.style.backgroundImage=o._src
	}
	else
	{
		if (s)
		{
			o._src=o.src
			var j = o.src.lastIndexOf('/')
			o.src = s.indexOf('/') < 0 ? o.src.substring(0,j+1) + s : s
		}
		else if (o._src)
			o.src=o._src
	}
}

function moveOption(src, dst, val)
{
	var sel = src.options.selectedIndex;

	if (sel == -1 && !val)
		;
	else
	{
		for (i=0; i<src.options.length; i++)
			if (src.options[i].selected || (val && src.options[i].value == val))
			{
				var o = new Option(src.options[i].text, src.options[i].value)
				dst.options[dst.options.length] = o;
				src.options[i--] = null;
			}
	}
}

var waitforinput_onresize=null
function waitforinput(bool)
{
	if (!gE("ifWaitfor"))
	{
		if (bool)
		{
			$('<div id=ifWaitfor style="position:absolute;top:0;left:0;right:0;bottom:0;filter:alpha(opacity=70);-moz-opacity:0.7;opacity:0.7;display:none;z-index:1200;background:#cccccc" ></div>').appendTo(document.body)
			waitforinput(true)
		}
	}
	else
	{
		var x = gE("ifWaitfor").style
		var b = truebody()
		var innerWidth = $.browser.msie ? document.body.clientWidth : window.innerWidth
		var innerHeight = $.browser.msie ? document.body.clientHeight : window.innerHeight

		x.width   = Math.max(b.scrollWidth, innerWidth)
		x.height  = Math.max(b.scrollHeight, innerHeight)

		if (bool)
		{
			if (x.display == "none")
			{
				waitforinput_onresize = window.onresize
				window.onresize=function() { waitforinput(true); }
			}
		}
		else
			window.onresize = waitforinput_onresize

		x.display = bool ? "block" : "none"
	}
}

	function truebody() { return (!window.opera && document.compatMode && document.compatMode!="BackCompat")? document.documentElement : document.body; }

if (typeof _L12N_ == "undefined")
{
	var _L12N_ = {}

	_L12N_["REQ"]            = " cannot be empty"
	_L12N_["REQ_INT"]        = " must be an integer"
	_L12N_["REQ_NUM"]        = " must be numeric value"
	_L12N_["REQ_DATE"]       = " must be a valid date"
	_L12N_["REQ_MAXLENGTH1"] = " cannot contains more than "
	_L12N_["REQ_MAXLENGTH2"] = " characters"
	_L12N_["PLS_RETRY"]      = "Please correct the following problem and submit again.\n";
	_L12N_["REQ_EMAIL"]      = " must be a valid email"
}

function moveRelTo(o1, o2, x, y)
{
	x = x || 0; y = y || 0;

	while (o2 && o2.tagName != "BODY")
	{
		x += o2.offsetLeft;
		y += o2.offsetTop;
		o2 = o2.offsetParent;
	}

	o1.style.left = x + "px"
	o1.style.top = y + "px"
	o1.style.display = "block"
}

$(function(){ if ($.browser.msie && typeof jlink == "undefined") $(document.body).append("<a id=jlink href=# ></a>") })

j = jumpTo = function(url, target)
{
	if ($.browser.msie)
	{
		jlink.href = url || location;
		jlink.target = typeof target == "undefined" ? "" : target
		jlink.click();
	}
	else if (target)
	{
		if (!window.open(url, target, "menubar=yes,toolbar=yes,scrollbars=yes,resizable=yes"))
			alert('You have a popup blocker enabled.');
	}
	else
		location.href = url || location.href
}

function _style(el,styleProp)
{
	if (el.currentStyle)
		return el.currentStyle[styleProp];
	else if (window.getComputedStyle)
		return document.defaultView.getComputedStyle(el,null).getPropertyValue(styleProp);
}

function switchLang(lang)
{
  var l = location + "";

	if (l.indexOf("?") == -1)
	{
	  l = l.replace(/$/, "?lang=" + lang);
	  j( l.replace(/#/, "?lang=" + lang + "#") );
	}
	else
	{
	  l = l.replace(/(\?|&)lang=[^&#]*/, "$1");
	  j( l.replace(/\?(&*)(.*)/, "?lang=" + lang + "&$2") );
	}
}

function alert_fmt(msg)
{
	if (msg.indexOf("_FAIL_") > 0 || msg.indexOf("_SUCCESS") > 0)
		alert(msg.charAt(0) + msg.replace("_SUCCESS", "_SUCCEED.").replace("_FAIL_", "_FAILED.__").replace(/_/g, ' ').toLowerCase().substring(1))
	else if (msg)
		alert(msg)
}

window.openDialog = function(url, w, h, scrollable)
{
	var dh = 0

	if ($.browser.msie6)
	{
		w += 8
		h += 54
	}
	else if ($.browser.safari)
		dh = 56
	else
		dh = 88

	var x = (window.screen.width - w) / 2;
	var y = (window.screen.height - h - dh) / 2;

	// CHANGED: window.open for the browsers which do not support showModalDialog(), by Nicky @ Sept 4
	if (window.showModalDialog)
		var rval = window.showModalDialog(url, window,
			"dialogHeight: " + h + "px; dialogWidth: " + w + "px; dialogTop: " + y + "px; dialogLeft: " + x + "px; edge: Raised; center: Yes; help: No; resizable: Yes; status: No; scroll: " + (scrollable?'Yes':'No'));
	else
		var rval = window.open(url, window,
			"dialogHeight: " + h + "px; dialogWidth: " + w + "px; dialogTop: " + y + "px; dialogLeft: " + x + "px; edge: Raised; center: Yes; help: No; resizable: Yes; status: No; scroll: " + (scrollable?'Yes':'No'));

	return rval
}

$(function(){
	if (!$.cookie("TIMEZONE"))
	{
		var ofs = (new Date().getTimezoneOffset() / 60) * -1;
		$.cookie("TIMEZONE", (ofs > 0 ? "GMT+" : "GMT") + ofs, {path: '/'})
	}
})

