//#######################################################
// GLOBAL FUNCTIONS:
function trueReturn() {return true;}
function falseReturn() {return false;}
//# suppress errors for older browsers:
// window.onerror = trueReturn;

//# generic object detection:
function objP(o) {return ((typeof o == 'object' && o != null)?1:0) }
function numP(o) {return (typeof o == 'number') }
function strP(o) {return ((typeof o == 'string' && o)?1:0) }
function funcP(o) {return (typeof o == 'function') }
function boolP(o) {return (typeof o == 'boolean') }

function isFnObj(o) {return (objP(o) || funcP(o)) }

//#######################################################
//# QS:

function get_url_query_fragment(o) {
	var qs_str = (objP(o))?(o.search?o.search:o.href?extractQString(o.href):''):extractQString(o);

	// alert("get_url_query_fragment:"+qs_str)

	return qs_str;
}

function extractQString(s) {
	var url_frag = String(s);
	var firstQmark = url_frag.indexOf("?");
	var lastHash = url_frag.lastIndexOf("#");

	//var startCut = firstQmark+1;
	//var endCut = (lastHash>=0)?lastHash-1:url_frag.length;
	//return url_frag.substr(startCut,endCut);
	
	return (firstQmark<0)?'':url_frag.substr(firstQmark+1,(lastHash>=0)?lastHash-1:url_frag.length);

}

function QS_serialize(obj) {
	return serialize(obj, "&", "=", true);
}
function QS_deserialize(qs) {
	var qsStr = extractQString(qs);

	//qsStr= qsStr.replace(/%2526/g,"&");
	//qsStr= qsStr.replace(/%26/g,"&");
	qsStr= qsStr.replace(/\+/g," ");

	//alert("qsStr:"+qsStr)
	return deserialize(qsStr, "&", "=");
}

function serialize(obj, paramDelim, nvDelim, doEscape) {
	var s = "";

	if (objP(obj)) {
		for (prop in obj) {
			//alert("prop:"+prop);
			var v = obj[prop];
			//if (typeof v != "undefined" && v!=null && v!="") {
			if (prop && (v!=undefined) && (strP(v) || numP(v) || boolP(v))) {
				s += (s=="")?"":paramDelim;
				s += prop + nvDelim + ((doEscape==false)?String(v):my_escape(String(v)));
			}
		}
	}
	return s;
}

function deserialize(s, paramDelim, nvDelim) {
//alert("deserialize s:"+s+"\n paramDelim:"+paramDelim +"\n nvDelim:"+nvDelim)
	var o = new Object();
	if (strP(s) && strP(paramDelim) && strP(nvDelim)) {
		var param_arr = s.split(paramDelim);
		for (var i=0; i<param_arr.length; i++) {
			var nv_pair = param_arr[i];
			//alert("nv_pair:"+nv_pair)
			var nv_arr = nv_pair.split(nvDelim);
			o[nv_arr[0]] = my_unescape(nv_arr[1]);
			//alert(nv_arr[0] +"=="+ my_unescape(nv_arr[1]));
		}
	}
	return o;
}

function synchronizeObjects(obj1, obj2) {
	for (prop in obj2) {
		obj1[prop] = obj2[prop];
	}
	return obj1;
}
function unionObjects() {
	var o = {};
	for (var i=0; i<arguments.length; i++) {
		var obj = arguments[i];
		if (objP(obj)) {
			for (prop in obj) {
			//alert("arguments["+i+"] \n o["+prop+"]:"+o[prop] +" \n obj["+prop+"]:"+obj[prop])
				if (typeof obj[prop] != "undefined") {
					o[prop] = obj[prop];
				}
			}
		};
	}
	return o;
}
function cloneObject(o) {
	return unionObjects(o);
}

function getData(key, dataObj) {
	return (!objP(dataObj) && strP(self[key]))?self[key]:getQSparam(key,dataObj);
}


function getQSparam(key, dataObj) {
	//alert("key:"+key);
	var use_obj = (dataObj)?dataObj:self["QS_DATA"];
	if (typeof use_obj == "object") {
		var v=use_obj[key]; 
		return (strP(v)?v:"");
	}
}


function setData(key,val,dataObj) {
	var use_obj = (dataObj)?dataObj:self["QS_DATA"];
	if (key && typeof use_obj == "object") {
		use_obj[key] = val;
	};
}
function isFirstParam(url_str) {return (url_str.indexOf('?')<=0)}
function appendParams(url_str,nv_pair) {return (nv_pair)?(url_str+(isFirstParam(url_str)?"?":"&") + nv_pair):url_str}
function getQSpair(s) {return (strP(getQSparam(s))?(s+'='+my_escape(getQSparam(s))):'')}
//# capability, browser sniff:
function getIsWin() {
	var s=(typeof navigator=='object' && strP(navigator.platform))?(navigator.platform.toLowerCase()):'';
	return ((s.indexOf('win')==-1)?0:1);
}

//#######################################################
//# Flash-specific, and unicode escaping:

function my_unescape(s) {
	try {
		var s2 = decodeURIComponent(s);
	} catch(e) {
		var s2 = unescape(s);
	};
	//return s2.replace(/%26/g,"&");
	return s2;
	//return s2.replace(/\+/g," ");
}

function my_escape(s) {
	try {
		return encodeURIComponent(s);
	} catch(e) {
		return escape(s);
	}
}

//#######################################################
var isSafari = (navigator.userAgent.indexOf('Safari')>=0)?1:0;
var isNS = (navigator.appName.indexOf('Netscape')>=0 && !isSafari)?1:0;
var isNS6 = (navigator.userAgent.indexOf('Netscape6')>=0)?1:0;
var isMoz = (isNS && navigator.userAgent.indexOf('Mozilla')>=0)?1:0;
var isMac = !(getIsWin());
var cantTalkToFlash = (isNS6 || ((isMac || isNS) && (!isMoz)));// (isNS6 && > FLASH6r40 )||

//#######################################################
//# DHTML, container retreival:

function getObjByID(s, win) {
	var d = (objP(win))? win.document : self.document;
	if (objP(d) ) {
		//var domObj = (!(funcP(d.getElementById)) && objP(d.all))? d.all : d;
		return (funcP(d.getElementById))?d.getElementById(s): (objP(d.all) && objP(d.all[s]))? d.all[s] : d[s];
	} else {
		return '';
	};
}
function setClassById(id,c,win) {
	var el = getObjByID(id, win);
	setClass(el,c);
}


function setClass(o,c) {
	if (hasClass(o)) {
		o.className = c;
	};
}

function hasClass(o) {
	return (objP(o) && objP(o.style));
}

function hasStyle(o) {
	return (objP(o) && objP(o.style));
}

//#######################################################

function setInnerHTML(el_id, s) {
	var el = getObjByID(el_id);
	if (objP(el)) {
		el.innerHTML = s;
	}
	return el;
}


// *********************************

function getCookie(cookName) {
	if (document.cookie.length > 0) {
		begin = document.cookie.indexOf(cookName+"="); 
		if (begin != -1) {
			begin += cookName.length+1; 
			end = document.cookie.indexOf(";", begin);
			if (end == -1) end = document.cookie.length;
			return unescape(document.cookie.substring(begin, end));
		}
	}
	return undefined; 
}

function setCookie(cookName, value, expiredays) {
	var ExpireDate = new Date();
	ExpireDate.setTime(ExpireDate.getTime() + (expiredays * 24 * 3600 * 1000));
	document.cookie = cookName + "=" + value + "; path=/" + ((expiredays == null) ? "" : "; expires=" + ExpireDate.toGMTString());
}

function delCookie(cookName) {
	if (getCookie(cookName)) {
		setCookie(cookName, '', -366);
		//document.cookie = cookName + "=" + "; path=/" + "; expires=Thu, 01-Jan-70 00:00:01 GMT";
	}
}

// *********************************



//#######################################################
//# debugging:
var debugWin;
function db() {alert("db")
	if (typeof debugWin == "object") {
		try {
			debugWin.close();
		} catch (er) {
		};
	}

	debugWin = window.open("about:blank","debugWin");
	var dbTxt='';
	for (var i=0; i<db.arguments.length; i++) {
		dbTxt += '<hr size=5 noshade>'+String(db.arguments[i])+'<hr>';

		var recurseDepth = 0;
		dbTxt += dbObj(db.arguments[i], recurseDepth);
	};
	var d = debugWin.document;
	d.open("text/html");
	d.writeln(dbTxt);
	d.close();
	//setTimeout("setOpener(debugWin,true);",500);
}

function dbObj(objIn, recurseDepth) {
	var dbTxtObj = {TAINTED:true};
	if (!objP(objIn)) {return "not an object."};
	for (prop in objIn) {
		try {
			var checkObj = objIn[prop];
			if (!objIn.TAINTED && recurseDepth<4) {
				var pType = (typeof checkObj);
				var pGroup = (pType=="object"||pType=="string"||pType=="number"||pType=="function")?(pType.toUpperCase()):"OTHER";
				if (!dbTxtObj[pGroup]) {
					dbTxtObj[pGroup] = "\n<HR><H2>"+pGroup+"</H2>";
					//alert("dbTxtObj["+pGroup+"]:\n"+dbTxtObj[pGroup])
				};
				dbTxtObj[pGroup] += "\n<BR><B>" + prop + "</B>: ";
				dbTxtObj[pGroup] += (pGroup=="OTHER")?"[" + pType + "] ":"";
				try {
					dbTxtObj[pGroup] += checkObj +"\n<BR>";
				} catch (er) {
					dbTxtObj[pGroup] += getErrText(er);
				}
			}
		} catch(er) {
		
		}
	}
	objIn.TAINTED = true;

	return(serialize(dbTxtObj,"","",false));
}

// alert("global.js loaded")

