String.prototype.replaceAll = function(stringToFind,stringToReplace){

    var temp = this;
    var index = temp.indexOf(stringToFind);
    while(index != -1){
        temp = temp.replace(stringToFind,stringToReplace);
        index = temp.indexOf(stringToFind);
    }
    return temp;
}

String.prototype.startsWith = function(str){
	if (this.length < str) return false;
	if (this.substring(0, str.length) == str) return true;
	return false;
}

 

function hilightRow(id)
{
	document.getElementById(id).style.background = "#CCDDFF";
}
function lowlightRow(id, count)
{
	if (count % 2 == 0)
		document.getElementById(id).style.background = "#EEEEEE";
	else
		document.getElementById(id).style.background = "#DDDDDD";
}
function lowlightRow2(id, color)
{
	document.getElementById(id).style.background = color;
}

function show(id)
{
	document.getElementById(id).style.visibility = "visible";
}
function hide(id)
{
	document.getElementById(id).style.visibility = "hidden";
}

function setValue(input, value)
{
	input.value = value;
}
function enter(BTN)
{
   BTN.style.backgroundImage = "url('/img/blue.gif')";	
   BTN.style.cursor = 'hand';
   
}
function exitblue(BTN)
{
   BTN.style.backgroundImage = "url('/img/gray2.gif')";	
   BTN.style.cursor = '';
}
function exitwhite(BTN)
{
   BTN.style.backgroundImage = "url('/img/gray2.gif')";	
   BTN.style.cursor = '';
}
function exitblack(BTN)
{
   BTN.style.backgroundImage = "url('/img/gray.gif')";	
   BTN.style.cursor = '';
}

function isenter()
{
	return (window.event && window.event.keyCode == 13);
}

function count(field, countfield, max) {
if (field.value.length > max)
	field.value = field.value.substring(0, max);
else 
	countfield.value = max - field.value.length;
}

function showElement(id) {
	document.getElementById(id).style.visibility = "visible";
}
function hideElement(id) {
	document.getElementById(id).style.visibility = "hidden";
}

function setSelectedValue(selectObj, value) {
	for (var i=0; i < selectObj.length; i++) {
		if (selectObj[i].value == value) {
			selectObj[i].selected = true;
		}
	}
}

function getSelectedValue(selectObj) {
	for (var i=0; i < selectObj.length; i++) {
		if (selectObj[i].selected) {
			return selectObj[i].value;
		}
	}
	return null;
}



function getCheckedValue(radioObj) {
	if(!radioObj)
		return "";
	var radioLength = radioObj.length;
	if(radioLength == undefined)
		if(radioObj.checked)
			return radioObj.value;
		else
			return "";
	for(var i = 0; i < radioLength; i++) {
		if(radioObj[i].checked) {
			return radioObj[i].value;
		}
	}
	return "";
}

function setCheckedValue(radioObj, newValue) {
	if(!radioObj)
		return;
	var radioLength = radioObj.length;
	if(radioLength == undefined) {
		radioObj.checked = (radioObj.value == newValue.toString());
		return;
	}
	for(var i = 0; i < radioLength; i++) {
		radioObj[i].checked = false;
		if(radioObj[i].value == newValue.toString()) {
			radioObj[i].checked = true;
		}
	}
}

function getValue(field)
{
	return parseNumber(document.forms.propform[field].value);
}
function percentage(value)
{
	return onedecimal("" + value*100) + "%";
}
function percentage2(value)
{
	return nodecimal("" + value*100) + "%";
}

function setValue(field, value)
{
	var div = document.getElementById(field);
	if (div != null)
	{
		setText(div, value);
	}
	else
	{	
		//document.forms.propform[field].value = value;
	}
}

function setMoney(field, value)
{
	var div = document.getElementById(field);
	if (div != null)
	{
		if (value < 0) 
			div.style.color = "#880000";
		else
			div.style.color = "#000000";
		setText(div, dollars(value));
	}
	else
	{	
		//document.forms.propform[field].value = value;
	}
}
function setPercentage(field, value)
{
	var div = document.getElementById(field);
	if (div != null)
	{
		if (value < 0) 
			div.style.color = "#880000";
		else
			div.style.color = "#000000";
		setText(div, percentage(value));
	}
	else
	{	
		//document.forms.propform[field].value = value;
	}
}
function setPercentage2(field, value)
{
	var div = document.getElementById(field);
	if (div != null)
	{
		if (value < 0) 
			div.style.color = "#880000";
		else
			div.style.color = "#000000";
		setText(div, percentage2(value));
	}
	else
	{	
		//document.forms.propform[field].value = value;
	}
}
function dollars(value)
{
	if (value == 0) return "-";
	var strvalue;
	var num = nodecimal("" + Math.round(value));
	for (var i = 0; i < Math.floor((num.length-(1+i))/3); i++)
	{
		num = num.substring(0,num.length-(4*i+3))+','+
		num.substring(num.length-(4*i+3));
	}
	strvalue = num;
	//var strvalue = nodecimal("" + Math.round(value));
	if (value >= 0) return "$" + strvalue;
	
	strvalue = strvalue.substring(1);
	if (strvalue.indexOf(",") == 0)
		strvalue = strvalue.substring(1);
	return '($' + strvalue + ')';
}
function nodecimal(value)
{
	var index = value.indexOf(".");
	if (index > 0)
		return value.substring(0, index);
	else 
		return value;
}
function onedecimal(value)
{
	var strvalue = "" + (value * 10);
	var index = strvalue.indexOf(".");
	if (index > 0)
	{
		strvalue = strvalue.substring(0, index);
		value = strvalue;
		value = value / 10;
	}
	return value;
}

function parseNumber(number)
{
	if (number == "") return 0;
	return parseFloat(number.replace("$","").replace(",",""));
}


Date.prototype.setISO8601 = function (string) {
    var regexp = "([0-9]{4})(-([0-9]{2})(-([0-9]{2})" +
        "(T([0-9]{2}):([0-9]{2})(:([0-9]{2})(\.([0-9]+))?)?" +
        "(Z|(([-+])([0-9]{2}):([0-9]{2})))?)?)?)?";
    var d = string.match(new RegExp(regexp));

    var offset = 0;
    var date = new Date(d[1], 0, 1);

    if (d[3]) { date.setMonth(d[3] - 1); }
    if (d[5]) { date.setDate(d[5]); }
    if (d[7]) { date.setHours(d[7]); }
    if (d[8]) { date.setMinutes(d[8]); }
    if (d[10]) { date.setSeconds(d[10]); }
    if (d[12]) { date.setMilliseconds(Number("0." + d[12]) * 1000); }
    if (d[14]) {
        offset = (Number(d[16]) * 60) + Number(d[17]);
        offset *= ((d[15] == '-') ? 1 : -1);
    }

    offset -= date.getTimezoneOffset();
    time = (Number(date) + (offset * 60 * 1000));
    this.setTime(Number(time));
}



function createCookie(name,value,days) {
  if (days) {
    var date = new Date();
    date.setTime(date.getTime()+(days*24*60*60*1000));
    var expires = "; expires="+date.toGMTString();
  }
  else expires = "";
  document.cookie = name+"="+value+expires+"; path=/";
}

function readCookie(name) {
  var nameEQ = name + "=";
  var ca = document.cookie.split(';');
  for(var i=0;i < ca.length;i++) {
    var c = ca[i];
    while (c.charAt(0)==' ') c = c.substring(1,c.length);
    if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length,c.length);
  }
  return null;
}
function setCaretPosition(ctrl, pos){
	if(ctrl.setSelectionRange)
	{
		ctrl.focus();
		ctrl.setSelectionRange(pos,pos);
	}
	else if (ctrl.createTextRange) {
		var range = ctrl.createTextRange();
		range.collapse(true);
		range.moveEnd('character', pos);
		range.moveStart('character', pos);
		range.select();
	}
}
function setCaretSelection(ctrl, start, end){
	if(ctrl.setSelectionRange)
	{
		ctrl.focus();
		ctrl.setSelectionRange(start, end);
	}
	else if (ctrl.createTextRange) {
		var range = ctrl.createTextRange();
		range.collapse(true);
		range.moveEnd('character', end);
		range.moveStart('character', start);
		range.select();
	}
}


function RandomIterator(array)
{
	this.index_list = new Array();
	this.hasNext  = function()
	{
		return this.index_list.length > 0;
	}
	this.next = function ()
	{
		return this.index_list.pop();
	}
	
	var array_copy = [].concat(array); // copy the original array
	while (array_copy.length > 0)
	{
		var rand = Math.floor(Math.random()*array_copy.length);
		this.index_list.push(array_copy[rand]);
		array_copy.remove(rand)
	}
}

/** windows size ***/

function getWindowWidth() {
  if( typeof( window.innerWidth ) == 'number' ) {
	return window.innerWidth;
  } else if( document.documentElement && ( document.documentElement.clientWidth || document.documentElement.clientHeight ) ) {
  	return document.documentElement.clientWidth;
  } else if( document.body && ( document.body.clientWidth || document.body.clientHeight ) ) {
    return document.body.clientWidth;
  }
}

function getWindowHeight()
{
  if( typeof( window.innerWidth ) == 'number' ) {
    return window.innerHeight;
  } else if( document.documentElement && ( document.documentElement.clientWidth || document.documentElement.clientHeight ) ) {
    return document.documentElement.clientHeight;
  } else if( document.body && ( document.body.clientWidth || document.body.clientHeight ) ) {
    return document.body.clientHeight;
  }
}

function getPageWidth()
{
	if( window.innerHeight && window.scrollMaxY )
		return window.innerWidth + window.scrollMaxX;
	else if( document.body.scrollHeight > document.body.offsetHeight ) // all but Explorer Mac
		return document.body.scrollWidth;
	else // works in Explorer 6 Strict, Mozilla (not FF) and Safari
		return document.body.offsetWidth + document.body.offsetLeft; 
}
function getPageHeight()
{
	if( window.innerHeight && window.scrollMaxY )
		return window.innerHeight + window.scrollMaxY;
	else if( document.body.scrollHeight > document.body.offsetHeight ) // all but Explorer Mac
		return document.body.scrollHeight;
	else // works in Explorer 6 Strict, Mozilla (not FF) and Safari
		return document.body.offsetHeight + document.body.offsetTop;
}

/*
var Viewport = { // Test? FF/IE 
	getPage: function() { var pageWidth = 720; var pageHeight = 576; var scrollArr = this.getScroll(); var winArr = this.getWindow(); pageWidth = winArr.width + scrollArr.left; pageHeight = winArr.height + scrollArr.top; 
	return { scrollX: scrollArr.left, scrollY: scrollArr.top, winW: winArr.width, winH: winArr.height, pageW: pageWidth, pageY: pageHeight };
	}, 
	getScroll: function() { return { left: this.scrollLeft(), top: this.scrollTop() }; }, 
	getWindow: function() { return { width: this.windowWidth(), height: this.windowHeight() }; }, 
	scrollLeft: function() { var xScroll = 0; if (self.pageXOffset) xScroll = self.pageXOffset; else if (document.documentElement && document.documentElement.scrollLeft) xScroll = document.documentElement.scrollLeft; else if (document.body) xScroll = document.body.scrollLeft; return xScroll; }, 
	scrollTop: function() { var yScroll = 0; if (self.pageYOffset) yScroll = self.pageYOffset; else if (document.documentElement && document.documentElement.scrollTop) yScroll = document.documentElement.scrollTop; else if (document.body) yScroll = document.body.scrollTop; return yScroll; }, 
	windowWidth: function() { var xWin = 720; if (self.innerHeight) xWin = self.innerWidth; else if (document.documentElement && document.documentElement.clientWidth) xWin = document.documentElement.clientWidth; else if (document.body) xWin = document.body.clientWidth; return xWin; }, 
	windowHeight: function() { var yWin = 576; if (self.innerHeight) yWin = self.innerHeight; else if (document.documentElement && document.documentElement.clientHeight) yWin = document.documentElement.clientHeight; else if (document.body) yWin = document.body.clientHeight; return yWin; }
};
*/

function f_clientWidth() {
	return f_filterResults (
		window.innerWidth ? window.innerWidth : 0,
		document.documentElement ? document.documentElement.clientWidth : 0,
		document.body ? document.body.clientWidth : 0
	);
}
function f_clientHeight() {
	return f_filterResults (
		window.innerHeight ? window.innerHeight : 0,
		document.documentElement ? document.documentElement.clientHeight : 0,
		document.body ? document.body.clientHeight : 0
	);
}
function f_scrollLeft() {
	return f_filterResults (
		window.pageXOffset ? window.pageXOffset : 0,
		document.documentElement ? document.documentElement.scrollLeft : 0,
		document.body ? document.body.scrollLeft : 0
	);
}
function f_scrollTop() {
	return f_filterResults (
		window.pageYOffset ? window.pageYOffset : 0,
		document.documentElement ? document.documentElement.scrollTop : 0,
		document.body ? document.body.scrollTop : 0
	);
}
function f_filterResults(n_win, n_docel, n_body) {
	var n_result = n_win ? n_win : 0;
	if (n_docel && (!n_result || (n_result > n_docel)))
		n_result = n_docel;
	return n_body && (!n_result || (n_result > n_body)) ? n_body : n_result;
}




/*** prototypes for missing functions ***/

if (typeof Array.indexOf != 'function') {
	Array.prototype.indexOf = function(f, s) {
		if (typeof s == 'undefined') s = 0;
		for (var i = s; i < this.length; i++) {
            if (f === this[i]) return i;
        }
        return -1;
    };
}

if (typeof Array.remove != 'function') {
	Array.prototype.remove = function(from, to) {
	  var rest = this.slice((to || from) + 1 || this.length);
	  this.length = from < 0 ? this.length + from : from;
	  return this.push.apply(this, rest);
	};
}

/**** event scheduler for timed javascript events ****/
function SchedulerEvent(event, time)
{
	this.event = event;
	this.time = time;
}
// use var scheduler = new Scheduler("scheduler") // names must match!
// scheduler.start();
// scheduler.pause();
// scheduler.stop();
// scheduler.schedule("alert('hi')", 1000);
function Scheduler(name, callback)
{
	this.name = name;
	this.callback = callback;
	this.events = new Array();
	this.is_paused = false;
	this.current_time = 0;
	
	this.schedule = function(event, time)
	{
		var e = new SchedulerEvent(event, time+this.current_time);
		this.events.push(e);
	}
	this.run = function(new_time)
	{
		this.current_time = new_time;
		if (this.is_paused) return;
		
		for (i = 0; i < this.events.length; i++)
		{
			while (i < this.events.length && this.events[i].time <= this.current_time)
			{
				eval(this.events[i].event);
				this.events.remove(i);
			}
		}
		if (this.events.length == 0 && this.callback)
			this.callback();
		setTimeout(this.name + ".run(" + (this.current_time+1000) + ")", 1000);
	}
	this.paused = function()
	{
		return this.is_paused;
	}
	// pause is actually pause/play
	this.pause = function()
	{
		this.is_paused = true;
	}
	this.start = function()
	{
		this.is_paused = false;
		this.run(this.current_time);
	}
	this.stop = function()
	{
		this.events = new Array();
	}
	this.done = function()
	{
		return this.events.length == 0;
	}
}
        

function is_array(input){
    return typeof(input)=='object'&&(input instanceof Array);
}

String.prototype.trim = function() {
	return this.replace(/^\s+|\s+$/g,"");
}
String.prototype.ltrim = function() {
	return this.replace(/^\s+/,"");
}
String.prototype.rtrim = function() {
	return this.replace(/\s+$/,"");
}


/**
 * Combines a hash table and an array to make it easy to look things
 *  and also easy to iterate over our contents, add things, and remove things
 * Whatever you add needs to define .id 
 */
function HashedArray()
{
	this.hash = new Array();
	this.array = new Array();
	this.length = 0;
	
	this.clear = function()
	{
		this.hash = new Array();
		this.array = new Array();
		this.length = 0;
	}
	
	this.add = function(r)
	{
		this.hash[r.id] = r;
		this.array.push(r);
		this.length++;
	}
	
	this.indexOf = function(id)
	{
		for (this.i = 0; this.i < this.array.length; this.i++)
		{
			var r = this.array[this.i];
			if (r.id == id) return this.i;
		}
		return -1;
	}
	
	this.get = function(id)
	{
		return this.hash[id];
	}
	
	this.has = function(id)
	{
		return this.indexOf(id) >= 0;
	}
	
	this.remove = function(id)
	{
		if (!this.has(id)) return;
		this.hash[id] = null;
		this.array.remove(this.indexOf(id));
		this.length--;
	}
	
	// func(index, report)
	// strange... we actually have to scope the i variable in "this" because otherwise
	// if we're looping within a loop it actually will screw everything up.. weird..
	this.i = 0;
	this.each = function(func)
	{
		for (this.i = 0; this.i < this.length; this.i++)
		{
			var r = this.array[this.i];
			func(this.i, r);
		}
	}
	
	this.first = function()
	{
		return this.array[0];
	}
	this.last = function()
	{
		return this.array[this.length-1];
	}
	this.toString = function()
	{
		return this.array.toString();
	}
}
