if(!window.Client)
{
	window.Client = {};
}

Object.extend(window.Client, 
{
	selectable: true,
	
	initialize: function()
	{
		document.observe('keydown', this.keydown.bindAsEventListener(this));
	},
	
	resize: function()
	{
		document.fire('behavior:resize');
	},
	
	select: function()
	{
		return this.selectable;
	},
	
	setSelectable: function(state)
	{
		this.selectable = state;
	},
	
	forceRedraw: function()
	{
		if(Prototype.Browser.IE)
		{
			document.body.addClassName("redraw");
			document.body.removeClassName("redraw");
		}
	},
	
	keydown: function(inEvent)
	{
		if(inEvent.keyCode == 18) // option
		{
			this.toggleOption();
		}
	},
	
	toggleOption: function()
	{
		if(document.body.hasClassName("optionkey"))
		{
			document.body.removeClassName("optionkey");
		}
		else
		{
			document.body.addClassName("optionkey");
		}
	},
	
	link: function(inElement, inTarget)
	{
		if(document.body.hasClassName("optionkey"))
		{
			var element = $(inElement)
			
			var action = element.readAttribute('action');
			
			if(action.startsWith('javascript:'))
			{
				action = action.substring(11);
			}
		
			if(inTarget)
			{
				window.open(action, inTarget, 'toolbar=no,status=no,scrollbars=yes');
			}
			else
			{
				try
				{
					eval(action);
				}
				catch(e)
				{
					window.location.href = action;
				}
			}
			
			document.body.removeClassName("optionkey");
		}
	}
});

window.Client.initialize();

window.onresize = Client.resize.bind(Client);

document.onselectstart = Client.select.bind(Client);

//----------------

function sendemail(inEmail, inSubject, inMessage)
{
	var url = "mailto:" + inEmail + "?subject=" + inSubject + "&body=" + inMessage;

	window.location.href = url;
}

function sendErrorReport(inURL)
{
	window.open(inURL, 'errorreport', 'height=340,width=480,toolbar=no,status=no,scrollbars=yes');
}

function updateErrorDetails()
{
	var sourceWindow = window.opener;
	
	if(sourceWindow)
	{
		var error = sourceWindow.$('error_details');

		if(error)
		{
			$('details').value = error.innerHTML;
		}
		
		var problem = sourceWindow.$('error_problem');
		
		if(problem)
		{
			$('problem').value = problem.innerHTML;
		}
	}
}

// ----------------
// Pickers

var pickerElementID;

var pickerChangeAction;

function openPicker(inURL, inElementID, inChangeAction)
{
	pickerElementID = inElementID;

	pickerChangeAction = inChangeAction;

	var	newWindow = window.open(inURL, 'picker', 'width=640,height=640,menubar=no,resizable=yes,scrollbars=yes,status=no,toolbar=no');
	
	newWindow.focus();
}

function getPickerElement()
{
	if(pickerElementID)
	{
		var element = document.getElementById(pickerElementID);

		if(element)
		{
			return element.value;
		}
	}

	return null;
}

function updatePickerElement(inValue, inHTML)
{
	if(pickerElementID)
	{
		var fireChange = false;

		var element = document.getElementById(pickerElementID);

		if(element)
		{
			element.value = inValue;
		}

		var elementHTML = document.getElementById(pickerElementID + "_html");
		
		if(elementHTML)
		{
			elementHTML.innerHTML = inHTML;
		}

		if(pickerChangeAction)
		{
			eval(pickerChangeAction);
		}
	}

	pickerElementID = null;
}


// -------------
// Cookies

function checkCookies()
{
	var cookietest = getCookie("cookietest");

	var cookies = false;

	if(cookietest)
	{
		cookies = cookietest == "ok";
	}

	var detector = document.getElementById("cookiedetector");

	if(!cookies)
	{
		detector.style.display = "";
	}
	else
	{
		detector.style.display = "none";
	}
}

function setCookie(name, value, expirydays, path)
{
	var expiry;

	if(!name || name == "")
		return;
		
	if(expirydays && expirydays > 0)
	{
		var	expiryDate = new Date();
		
		expiryDate.setTime(expiryDate.getTime() + (expirydays * 24 * 60 * 60 * 1000));
		
		expiry = expiryDate.toGMTString();
	}
	
	var cookieString = name + "=" + escape(value) +
					   ((!expiry) ? "" : ("; expires=" + expiry)) +
					   ((!path)   ? "" : ("; path=" + path));

	document.cookie = cookieString;
}

function getCookie(name)
{
	var arg = name + "=";
	var arglength = arg.length;
	var cookielength = document.cookie.length;
	var i = 0;
	
	while(i < cookielength)
	{
		var j = i + arglength;
		
		if(document.cookie.substring(i, j) == arg)
		{
			k = document.cookie.indexOf(";", j);
			
			if(k < 0)
			{
				k = cookielength;
			}
			
			return unescape(document.cookie.substring(j, k));
		}
			
		i = document.cookie.indexOf(" ", i) + 1;
		
		if(i == 0)
		{
			break;
		}
	}
	
	return "";
}

function checkCapsLock(e)
{
	var myKeyCode = 0;
	var myShiftKey = false;
	var myCapsLock = false;

	if(document.all) // Internet Explorer
	{
		e = window.event;
		myKeyCode = e.keyCode;
		myShiftKey = e.shiftKey;
	}
	else if(document.layers) // Netscape 4
	{
		myKeyCode = e.which;
		myShiftKey = (myKeyCode == 16) ? true : false;
	}
	else if(document.getElementById) // Netscape 6
	{
		myKeyCode = e.which;
		myShiftKey = e.shiftKey || ( e.modifiers && ( e.modifiers & 4 ) );
	}

	if((myKeyCode >= 65 && myKeyCode <= 90) && !myShiftKey)
	{
		myCapsLock = true;
	}
	else if((myKeyCode >= 97 && myKeyCode <= 122) && myShiftKey)
	{
		myCapsLock = true;
	}

	var detector = document.getElementById("capslockdetector");

	if(myCapsLock)
	{
		detector.style.display = "";
	}
	else
	{
		detector.style.display = "none";
	}
}

// -------------
// messages

function verify(msg)
{
	return confirm(msg);
}

function question(inMessage, inDefault, inObject)
{
	var value = prompt(inMessage, inDefault);
	
	if(value)
	{
		inObject.value = value;
		
		return true;
	}
	
	return false;
}

var alreadyVerified = false;

function verifyOnce(msg)
{
	if(!alreadyVerified)
	{
		alreadyVerified = verify(msg);
	}
	
	return alreadyVerified;
}

// -------------------
// ui

function toggleRadioCheckBoxes(current)
{
	var isChecked = current.checked;

	for(i=0 ; i < eval('current.form.' + current.name + '.length'); i++)
	{
		eval('current.form.' + current.name + '[' + i + ']').checked = false;
	}

	if(isChecked)
	{
		current.checked = true;
	}
}

function updateRadioButtons(inName, inID, inTotal)
{
	for(var i = 1; i <= inTotal; i++)
	{
		var element = document.getElementById("other" + inName + i);
		
		if(element)
		{
			if(i == inID)
			{
				element.style.display = "";
			}
			else
			{
				element.style.display = "none";
			}
		}
	}
}

var inlineFrames = new Array();

function registerFrame(inName)
{
	inlineFrames[inlineFrames.length] = inName;
	
	resizeFrame(inName);
}

function resizeFrame(inName)
{
	var frame = document.getElementById("frameid_" + inName);
	
	if(frame)
	{
		var source = window.frames["framename_" + inName].document;
		
		if(source)
		{
			var offset = 0;
			
			if(document.getElementById && !document.all)
			{
				offset=20;
			}
			
			if (navigator.appName.indexOf("Microsoft")!=-1)
			{
				frame.height = source.body.scrollHeight;
			}
			else
			{
				frame.height = source.body.offsetHeight + offset;
			}
		}
	}
}

function resizeFrames()
{
	for(i = 0; i < inlineFrames.length; i++)
	{
		resizeFrame(inlineFrames[i]);
	}
}

function maxLength(inEvent, inElement, inLength)
{
	if(Prototype.Browser.IE)
	{
		;
	}
	else
	{
		if(inElement.selectionStart != inElement.selectionEnd)
		{
			return true;
		}
		else if(inEvent.which == 0 || inEvent.which == inEvent.DOM_VK_BACK_SPACE)
		{
			return true;
		}
	}
	
	if(inElement.value.length >= inLength)
	{
		inElement.value = inElement.value.substring(0, inLength);
		
		return false;
	}
	
	return true;
}

function trimLength(element, length)
{
	if(element.value.length >= length)
	{
		element.value = element.value.substring(0, length);
	}
}

// --------
// Messages

function Message(inName, inMessage)
{
	this.name = inName;
	this.message = inMessage;
}

var messages = new Array();

function addMessage(inName, inMessage)
{
	messages[messages.length] = new Message(inName, inMessage);
}

function getMessage(inName)
{
	for(i = 0; i < messages.length; i++)
	{
		if(messages[i].name == inName)
		{
			return messages[i].message;
		}
	}
}

// ---------
// Events

function cancelEvent(event)
{
	if(!event)
	{
		event = window.event;
	}

	if(event.stopPropagation)
	{
		event.stopPropagation();
	}
	else
	{
		event.cancelBubble = true;
	}
	
	if(Prototype.Browser.IE)
	{
		var targetElement = event.srcElement;
	}
	else
	{
		var targetElement = event.target || event.srcElement;
	}
	
	return false;
}

// ---------
// Padding Button

var PaddingButton = Class.create(
{
	initialize: function(element, action, options)
	{
		this.element = $(element);
		this.action = action;
		
		if(!this.element)
		{
			return;
		}

		this.cursor = this.element.getStyle("cursor");
		this.paddingRight = parseInt(this.element.getStyle("paddingRight"));
		this.paddingLeft = parseInt(this.element.getStyle("paddingLeft"));
		this.paddingTop = parseInt(this.element.getStyle("paddingTop"));
		this.paddingBottom = parseInt(this.element.getStyle("paddingBottom"));
		this.options = {cursor: this.cursor };
		
		Object.extend(this.options, options || { });
		
		if(this.action && this.action.length > 0)
		{
			this.options.cursor = "pointer";
		}

		this.element.observe('click',		this.click.bindAsEventListener(this));
		this.element.observe('mousemove',	this.mousemove.bindAsEventListener(this));
	},
	
	click: function(event)
	{
		if(this.outside(event))
		{
			eval(this.action);
		}
	},
	
	mousemove: function(event)
	{
		if(this.outside(event))
		{
			this.element.setStyle({cursor: this.options.cursor});
		}
		else
		{
			this.element.setStyle({cursor: this.cursor});
		}
	},
	
	outside: function(event)
	{
		var offset = this.element.cumulativeOffset();
		var dimensions = this.element.getDimensions();

		var x = event.pointerX();
		var y = event.pointerY();
		
		if(x > offset.left + dimensions.width - this.paddingRight || x < offset.left + this.paddingLeft)
		{
			return true;
		}
		else if(y > offset.top + dimensions.height - this.paddingBottom || y < offset.top + this.paddingTop)
		{
			return true;
		}
		else
		{
			return false;
		}
	}
});

var Bounds = Class.create(
{
	initialize: function()
	{
		if(arguments.length == 4)
		{	
			this.top = arguments[0];
			this.right = arguments[1];
			this.bottom = arguments[2];
			this.left = arguments[3];
		}
		else if(arguments.length == 1)
		{
			this.element = arguments[0];
			
			this.update();
		}
	},

	update: function()
	{
		if(this.element)
		{
			if(this.element.cumulativeOffset)
			{
				var offset = document.viewport.getScrollOffsets();
			
				if(!this.initialized)
				{
					this.initialized = true;
					
					this.fixed = this.element.getStyle('position') == "fixed";
	
					this.borderLeft = 0;	
					this.borderTop = 0;
	
					var ancestors = this.element.ancestors();
	
					for(var i = 0; i < ancestors.length; i++)
					{
						var position = ancestors[i].getStyle('position');
	
						if(position == 'relative')
						{
							this.borderLeft += parseInt(ancestors[i].getStyle("borderLeftWidth")) || 0;
							this.borderTop += parseInt(ancestors[i].getStyle("borderTopWidth")) || 0;
						}
						else if(position == 'fixed')
						{
							this.fixed = true;
						}
					}
	
					if(this.fixed)
					{
						this.borderLeft += offset.left;
						this.borderTop += offset.top;
					}
				}

				var position = this.element.cumulativeOffset();
				var scrollOffset = this.element.cumulativeScrollOffset();
				var dimensions = this.element.getDimensions();
				
				scrollOffset.left -= offset.left;
				scrollOffset.top -= offset.top;

				this.top = position.top + this.element.scrollTop + this.borderTop - scrollOffset.top; 
				this.bottom = this.top + dimensions.height;
				this.left = position.left + this.element.scrollLeft + this.borderLeft - scrollOffset.left;
				this.right = this.left + dimensions.width;
			}
			else if(this.element.getScrollOffsets)
			{
				var offset = this.element.getScrollOffsets();
				var dimensions = this.element.getDimensions();

				this.top = offset.top;
				this.bottom = offset.top + dimensions.height;
				this.left = offset.left;
				this.right = offset.left + dimensions.width;
			}
		}
	},

	syncElement: function(inElement)
	{
		var element = $(inElement);

		if(!element)
		{
			element = this.element;
		}

		if(element)
		{
			var elementBounds = new Bounds(element);

			var position = element.positionedOffset();

			element.setStyle({left: (position.left + this.left - elementBounds.left) + "px", top: (position.top + this.top - elementBounds.top) + "px"});
		}
	},

	clone: function()
	{
		return new Bounds(this.top, this.right, this.bottom, this.left);
	},

	getWidth: function()
	{
		return this.right - this.left;
	},

	getHeight: function()
	{
		return this.bottom - this.top;
	},

	moveBy: function(inDeltaX, inDeltaY)
	{
		this.top += inDeltaY;
		this.bottom += inDeltaY;
		this.left += inDeltaX;
		this.right += inDeltaX;

		return this;
	},

	moveTo: function(inX, inY)
	{
		var x = inX - this.left;
		var y = inY - this.top;

		this.moveBy(x, y);

		return {x: x, y: y};
	},

	moveWithin: function(inBounds)
	{
		var x = 0;
		var y = 0;

		if(this.left < inBounds.left)
		{
			x = inBounds.left - this.left;
		}
		else if(this.right > inBounds.right)
		{
			x = inBounds.right - this.right;
		}

		if(this.top < inBounds.top)
		{
			y = inBounds.top - this.top;
		}
		else if(this.bottom > inBounds.bottom)
		{
			y = inBounds.bottom - this.bottom;
		}

		this.moveBy(x, y);

		return {x: x, y: y};
	},

	moveRelative: function(inLocation, inRelativeBounds, inRelativeLocation, inOffsetX, inOffsetY)
	{
		var position = this.getPosition(inLocation);

		var relataivePosition = inRelativeBounds.getPosition(inRelativeLocation, inOffsetX, inOffsetY);
		
		var x = relataivePosition.x - position.x;
		var y = relataivePosition.y - position.y;

		this.moveBy(x, y);

		return {x: x, y: y};
	},

	moveCentered: function(inOuterBounds, inOffsetX, inOffsetY)
	{
		var offsetX = .5;
		var offsetY = .5;

		if(inOffsetX != undefined)
		{
			offsetX = inOffsetX;
			offsetY = inOffsetX;
		}

		if(inOffsetY != undefined)
		{
			offsetY = inOffsetY;
		}

		var left = inOuterBounds.left + (inOuterBounds.getWidth() - this.getWidth()) * offsetX;
		var top = inOuterBounds.top + (inOuterBounds.getHeight() - this.getHeight()) * offsetY;

		return this.moveTo(left, top);
	},

	contains: function(inX, inY)
	{
		return(inX >= this.left && inX <= this.right && inY >= this.top && inY <= this.bottom);
	},

	overlaps: function(inBounds)
	{
		if(this.contains(inBounds.left, inBounds.top)) return true;
		if(inBounds.contains(this.left, this.top)) return true;

		if(this.contains(inBounds.right, inBounds.top)) return true;
		if(inBounds.contains(this.right, this.top)) return true;

		if(this.contains(inBounds.left, inBounds.bottom)) return true;
		if(inBounds.contains(this.left, this.bottom)) return true;

		if(this.contains(inBounds.right, inBounds.bottom)) return true;
		if(inBounds.contains(this.right, this.bottom)) return true;

		return false;
	},

	getMiddle: function()
	{
		return { x: (this.left + this.right) / 2, y: (this.top + this.bottom) / 2 };
	},

	getPosition: function(inLocation, inOffsetX, inOffsetY)
	{
		var position = this.getMiddle();

		if(inLocation.indexOf("top") >= 0) position.y = this.top;
		else if(inLocation.indexOf("bottom") >= 0) position.y = this.bottom;

		if(inLocation.indexOf("left") >= 0) position.x = this.left;
		else if(inLocation.indexOf("right") >= 0) position.x = this.right;

		if(inOffsetX != undefined)
		{
			position.x += inOffsetX;
		}

		if(inOffsetY != undefined)
		{
			position.y += inOffsetY;
		}

		return position;
	},

	expand: function(inOffsetX, inOffsetY)
	{
		var offsetX = 0;
		var offsetY = 0;

		if(inOffsetX)
		{
			offsetX = inOffsetX;
			offsetY = inOffsetX;
		}

		if(inOffsetY)
		{
			offsetY = inOffsetY;
		}

		this.left -= offsetX;
		this.right += offsetX;

		this.top -= offsetY;
		this.bottom += offsetY;

		return this;
	},

	shrink: function(inOffsetX, inOffsetY)
	{
		return this.expand(-inOffsetX, -inOffsetY);
	}
});

function fixIE()
{
	if(Prototype.Browser.IE)
	{
		var cells = $(document.body).select('td');
		
		for(var i = 0; i < cells.length; i++)
		{
			var minWidth = cells[i].getStyle("min-width");
			
			var whiteSpace = cells[i].getStyle("white-space");

			if(minWidth && minWidth != "auto")
			{
				cells[i].insert({bottom: "<div style='width:" + parseInt(minWidth) + "px; margin:0px !important; padding:0px !important; border:0px !important; line-height:0px !important; height:0px !important;'>&nbsp;</div>"});
			}
			
			if(whiteSpace && whiteSpace == "nowrap")
			{
				cells[i].setAttribute("nowrap", "nowrap");
			}
		}
	}
}