FSite2._selectClose = function(dropdown)
{
	if (this && !dropdown)
		dropdown = this;
	if (dropdown._options)
	{
		dropdown._options.style.display = 'none';
		//this._timeout = setTimeout(FSite2._callRef(FSite2._selectClose, dropdown._options), 10);
		dropdown._options.parentNode.removeChild(dropdown._options);
	}
	dropdown._options = null;
}

FSite2._selectInitClose = function()
{
	this._timeout = setTimeout(FSite2._callRef(FSite2._selectClose, this), 200);
}

FSite2._selectCancelClose = function(dropdown)
{
	if (this && !dropdown)
		dropdown = this;
	if (dropdown._timeout)
	{
		clearTimeout(dropdown._timeout);
		dropdown._timeout = null;
	}
}

FSite2._selectInitCancelClose = function()
{
	setTimeout(FSite2._callRef(FSite2._selectCancelClose, this), 100);
}

FSite2._selectCreateOptions = function(containerElement)
{
	// create table and tbody elements
	var table = document.createElement('table');
	var body = document.createElement('tbody');
	var row;
	var cell;
	// create rows and cells
	for (i = 0; i < this._hiddenInput.options.length; i++)
	{
		row = document.createElement('tr');
		cell = document.createElement('td');
		// assign basic parameters such as dropdown reference, value and text to table cell
		if (this._images)
			cell.style.backgroundImage = "url('" + this._hiddenInput.options[i].text + "')";
		else
			cell.innerHTML = this._hiddenInput.options[i].text;
		cell._option = this._hiddenInput.options[i];
		cell._value = this._hiddenInput.options[i].value;
		if (this._hiddenInput.options[i].selected)
		{
			if (!this._hiddenInput.multiple && containerElement)
				containerElement._selected = cell;
			cell.className = 'selected';
		}
		// assing event handlers to table cell
		cell.onmousedown = function(event) {return false;};
		if (this._hiddenInput.multiple)
		{
			cell._select = this;
			cell.onclick = function(event) {
				if (!event) event = window.event;
				this._select._selectChange(this, event.ctrlKey);
				this._select.focus();
			}
		}
		else
		{
			cell._dropdown = this;
			cell.onclick = function(event) {
				this._dropdown._selectInitClose();
				this._dropdown._selectChange(this);
			}
		}
		cell.onmouseover = function() {
			if (this._option.selected)
				this.className = 'selected hover';
			else
				this.className = 'hover';
		}
		cell.onmouseout = function() {
			if (this._option.selected)
				this.className = 'selected';
			else
				this.className = '';
		}
		row.appendChild(cell);
		body.appendChild(row);
	}
	table.appendChild(body);
	if (containerElement)
		containerElement.appendChild(table);
	return table;
}

FSite2._selectOnDrop = function(event)
{
	if (!event) event = window.event;
	if (this._hiddenInput.disabled) return false;
	if (this._options) { this._selectClose(); if (event) event.cancelBubble = true; return false; };
	this._selectCancelClose();
	// create div element - container for table holding simulated select options
	var div = document.createElement('div');
	div._dropdown = this;
	div.className = this.className;
	div.style.position = 'absolute';
	div.style.overflow = 'auto';
	div.onscroll = function(event) {this._dropdown.focus();};
	var table = this._selectCreateOptions(div);
	// insert div element into document after dropdown
	this.parentNode.insertBefore(div, this);
	this.parentNode.removeChild(this);
	div.parentNode.insertBefore(this, div);
	// decrease width of inner table if its height is too big to fit in div element
	div.style.display = 'block';
	if (table.clientHeight > div.clientHeight)
		table.style.width = (div.offsetWidth - 20) + 'px';
	// assign options container to dropdown, set focus
	this._options = div;
	this._selectScrollToSelected();
	this.focus();
	// fix blur events in various browsers
	this._selectCancelClose();
	this._selectInitCancelClose();
	if (event)
		event.cancelBubble = true;
	return false;
}

FSite2._selectUpdateLabel = function()
{
	if ((this._hiddenInput.selectedIndex >= 0) && this._label)
	{
		var currentOptionText = this._hiddenInput.options[this._hiddenInput.selectedIndex].text;
		if (this._images && (this._label.style.backgroundImage != "url('" + currentOptionText + "')"))
		{
			this._label.style.backgroundImage = "url('" + currentOptionText + "')";
		}
		else if (!this._images && (this._label.innerText != currentOptionText) &&
			(!this._hiddenInput.options[this._hiddenInput.selectedIndex]._HTML || (this._label._innerHTML != this._hiddenInput.options[this._hiddenInput.selectedIndex]._HTML)))
		{
			if (this._label.offsetWidth && this._label.parentNode.offsetHeight)
			{
				if (!this._label.style.width || !this._label.style.height || !this._label.style.lineHeight)
				{
					this._label.style.width = this._label.offsetWidth + 'px';
					this._label.style.height = this._label.parentNode.offsetHeight + 'px';
					this._label.style.lineHeight = this._label.parentNode.offsetHeight + 'px';
				} 
				if (currentOptionText != this._label._innerHTML)
				{
					this._label.innerHTML = currentOptionText;
					FSite2.recursiveReplace(this._label, / /g, '\xA0');
					this._label._innerHTML = currentOptionText;
				}
			}
		}
	}
	if (this._disabledClassName)
	{
		if (this._hiddenInput.disabled && !RegExp('\\b' + this._disabledClassName + '\\b','gi').test(this.className))
			this.className = this.className + ' ' + this._disabledClassName;
		else if (!this._hiddenInput.disabled && RegExp('\\b' + this._disabledClassName + '\\b','gi').test(this.className))
			this.className = this.className.replace(new RegExp('\\s*\\b' + this._disabledClassName + '\\b\\s*','gi'), '');
	}
}

FSite2._selectChange = function(option, toggle)
{
	if (this._options)
	{
		var change = false;
		if (toggle)
		{
			if (option._option.selected)
			{
				if (option.className == 'selected hover')
					option.className = 'hover';
				else
					option.className = '';
				option._option.selected = false;
			}
			else
			{
				if (option.className == 'hover')
					option.className = 'selected hover';
				else
					option.className = 'selected';
				option._option.selected = true;
			}
			change = true;
		}
		else
		{
			if (!option._option.selected)
				change = true;
			var deselected = this._selectDeselectAll();
//			alert(option._option.selected);
			if (!change && (deselected > 1))
				change = true;
			else if (change && (deselected > 0))
				change = true;
			option._option.selected = true;
			if ((option.className == 'hover') || (option.className == 'selected hover'))
				option.className = 'selected hover';
			else
				option.className = 'selected';
		}
		this._options._selected = option;
		this._selectScrollToSelected();
		if (this._hiddenInput.onchange && change)
			this._hiddenInput.onchange();
		this.focus();
	}
	if (this._updateState)
		this._updateState();
}

FSite2._selectDeselectAll = function()
{
	var options = this._options.firstChild.firstChild.childNodes;
	var counter = 0;
	for (i = 0; i < options.length; i++)
	{
		var option = options[i].firstChild;
		if ((option.className == 'hover') || (option.className == 'selected hover'))
			option.className = 'hover';
		else
			option.className = '';
		if (option._option.selected)
			counter++;
		option._option.selected = false;
	}
	return counter;
}

FSite2._selectScrollToSelected = function()
{
	if (this._options._selected)
	{
		if (this._options._selected.offsetTop + this._options._selected.offsetHeight > this._options.scrollTop + this._options.clientHeight)
			this._options.scrollTop = this._options._selected.offsetTop + this._options._selected.offsetHeight - this._options.clientHeight;
		if (this._options._selected.offsetTop < this._options.scrollTop)
			this._options.scrollTop = this._options._selected.offsetTop;
	}
}

FSite2._selectOptionOnClick = function()
{
	this._dropdown._selectInitClose();
	this._dropdown._selectChange(this);
}

FSite2._selectOnKeyDown = function(event)
{
	if (!event) var event = window.event;
	var re = /[A-Z]|\d/;
	this._lastKeyNonChar = true;
	if (event.keyCode == 0x20)
	{
		if (this._label)
			this.onclick();
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	else if (this._label && ((event.keyCode == 27) || (event.keyCode == 9)) && this._options)
		this.onclick();
	else if (event.keyCode == 36)
	{
		if (!this._options && this._label)
			this.onclick();
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		var newSelected = this._options.firstChild.firstChild.firstChild;
		if (newSelected)
			this._selectChange(newSelected.firstChild);
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	else if (event.keyCode == 35)
	{
		if (!this._options && this._label)
			this.onclick();
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		var newSelected = this._options.firstChild.firstChild.lastChild;
		if (newSelected)
			this._selectChange(newSelected.firstChild);
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	else if (event.keyCode == 34)
	{
		if (!this._options && this._label)
			this.onclick();
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		var newSelected;
		if (this._options._selected)
			newSelected = this._options._selected.parentNode;
		else
			newSelected = this._options.firstChild.firstChild.firstChild;
		if (newSelected)
		{
			var pageCount = Math.floor(this._options.clientHeight / newSelected.offsetHeight);
			var i;
			for (i = 0; (i < pageCount) && newSelected.nextSibling; i++)
				newSelected = newSelected.nextSibling;
			this._selectChange(newSelected.firstChild);
		}
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	else if (event.keyCode == 33)
	{
		if (!this._options && this._label)
			this.onclick();
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		var newSelected;
		if (this._options._selected)
			newSelected = this._options._selected.parentNode;
		else
			newSelected = this._options.firstChild.firstChild.lastChild;
		if (newSelected)
		{
			var pageCount = Math.floor(this._options.clientHeight / newSelected.offsetHeight);
			var i;
			for (i = 0; (i < pageCount) && newSelected.previousSibling; i++)
				newSelected = newSelected.previousSibling;
			this._selectChange(newSelected.firstChild);
		}
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	else if ((event.keyCode == 39) || (event.keyCode == 40))
	{
		if (!this._options && this._label)
			this.onclick();
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		var newSelected;
		if (this._options._selected)
			newSelected = this._options._selected.parentNode.nextSibling;
		else
			newSelected = this._options.firstChild.firstChild.firstChild;
		if (newSelected)
			this._selectChange(newSelected.firstChild);
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	else if ((event.keyCode == 37) || (event.keyCode == 38))
	{
		if (!this._options && this._label)
			this.onclick();
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		var newSelected;
		if (this._options._selected)
			newSelected = this._options._selected.parentNode.previousSibling;
		else
			newSelected = this._options.firstChild.firstChild.lastChild;
		if (newSelected)
			this._selectChange(newSelected.firstChild);
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	else if (re.test(String.fromCharCode(event.keyCode)) && !event.ctrlKey && !event.altKey)
	{
		this._lastKeyNonChar = false;
		var onepass;
		if (!this._options && this._label)
		{
			this.onclick();
			onepass = true;
		}
		var currentOptionRow = this._options._selected ? this._options._selected.parentNode : this._options.firstChild.firstChild.firstChild;
		while (currentOptionRow = currentOptionRow.nextSibling)
		{
			if (currentOptionRow.firstChild.innerHTML.replace(new RegExp('<[^>]*>', 'g'), '').substring(0, 1).toLowerCase() == String.fromCharCode(event.keyCode).toLowerCase())
			{
				this._selectChange(currentOptionRow.firstChild);
				break;
			}
		}
		if (!currentOptionRow && !onepass)
		{
			currentOptionRow = this._options.firstChild.firstChild.firstChild;
			do {
				if (currentOptionRow.firstChild == this._options._selected)
					break;
				if (currentOptionRow.firstChild.innerHTML.substring(0, 1).toLowerCase() == String.fromCharCode(event.keyCode).toLowerCase())
				{
					this._selectChange(currentOptionRow.firstChild);
					break;
				}
			} while (currentOptionRow = currentOptionRow.nextSibling);
		}
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		this.focus();
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	return true;
}

FSite2._selectOnKeyPress = function(event)
{
	if (!event) var event = window.event;
	var charCode = (event.charCode) ? event.charCode : event.keyCode;
	var re = /\w|\d/;
	if ((event.keyCode == 36) || (event.keyCode == 35) || (event.keyCode == 39) || (event.keyCode == 40) ||
		(event.keyCode == 37) || (event.keyCode == 38) || (event.keyCode == 33) || (event.keyCode == 34) ||
		(event.keyCode == 20) || (!this._lastKeyNonChar && re.test(String.fromCharCode(charCode))))
	{
		if (this._selectInitCancelClose)
			this._selectInitCancelClose();
		this.focus();
		event.cancelBubble = true;
		event.returnValue = false;
		if (event.preventDefault)
			event.preventDefault();
		return false;
	}
	return true;
}

FSite2._selectConvertOptions = function(e)
{
	htmlConverter = document.createElement('div');
	htmlConverter.style.display = 'none';
	document.body.appendChild(htmlConverter);
	for (var i = 0; i < e.options.length; i++)
	{
		htmlConverter.innerHTML = e.options[i].text;
		e.options[i]._HTML = htmlConverter.innerHTML;
	}
	document.body.removeChild(htmlConverter);
}

FSite2.selects = new Array();

FSite2._selectsTimerProc = function()
{
	var i;
	for (i = FSite2.selects.length - 1; i >= 0; i--)
		FSite2.selects[i]._replacement._updateState();
}

FSite2.extendSelect = function(e, c, i, dc)
{
	if (e._replacement)
		return;
	if (e.multiple)
		FSite2.extendMultipleSelect(e, c, i, dc);
	else
		FSite2.extendSingleSelect(e, c, i, dc);
}

FSite2.extendSingleSelect = function(e, c, i, dc)
{
	// check if given element is a select element
	if (e.tagName != 'SELECT')
		throw new Error('Given element is not a select element');
	// create a element as a replacement for given select
	var replacement = document.createElement('a');
	e._replacement = replacement;
	e._onfocus = e.onfocus;
	e.onfocus = function(ev)
	{
		if (!ev) ev = window.event;
		if (this._onblur)
			this.onblur(ev);
		this._replacement.focus();
	}
	e._onblur = e.onblur;
	e.onblur = function(ev)
	{
		if (!ev) ev = window.event;
		if (this._onblur)
			this.onblur(ev);
		this._replacement.blur();
	}
	replacement._hiddenInput = e;
	replacement._images = i;
	replacement.className = c;
	replacement._disabledClassName = dc;
	replacement.style.display = 'block';
	replacement.style.cursor = 'default';
	replacement.style.textDecoration = 'none';
	replacement.href = '#';
	replacement.onmouseover = function () {return false;};
	replacement.onkeydown = function(event) {if (!event) var event = window.event; FSite2._selectOnKeyDown.apply(this, new Array(event)); };
	replacement.onkeypress = function(event) {if (!event) var event = window.event; FSite2._selectOnKeyPress.apply(this, new Array(event)); };
	replacement.onkeyup = function(event) {this.focus(); this._lastKeyNonChar = true; };
	replacement.onfocus = function(event) {if (!event) event = window.event; this._selectCancelClose(); if (this._hiddenInput._onfocus) this._hiddenInput._onfocus(event); };
	replacement.onblur = function(event) {if (!event) event = window.event; this._selectInitClose(); if (this._hiddenInput._onblur) this._hiddenInput._onblur(event); };
	replacement.onclick = FSite2._selectOnDrop;
	replacement._selectClose = FSite2._selectClose;
	replacement._selectInitClose = FSite2._selectInitClose;
	replacement._selectCancelClose = FSite2._selectCancelClose;
	replacement._selectInitCancelClose = FSite2._selectInitCancelClose;
	replacement._selectCreateOptions = FSite2._selectCreateOptions;
	replacement._selectChange = function(option) { FSite2._selectChange.apply(this, new Array(option)); };
	replacement._selectDeselectAll = function() { FSite2._selectDeselectAll.apply(this); };
	replacement._selectScrollToSelected = FSite2._selectScrollToSelected;
	replacement._updateState = FSite2._selectUpdateLabel;
	var table = document.createElement('table');
	var body = document.createElement('tbody');
	var row = document.createElement('tr');
	var cell = document.createElement('td');
	var div = document.createElement('div');
	div.innerHTML = '&nbsp;';
	div.style.overflow = 'hidden';
	cell.appendChild(div);
	cell.className = 'text';
	replacement._label = div;
	row.appendChild(cell);
	cell = document.createElement('td');
	cell.className = 'drop';
	cell.innerHTML = ' ';
	replacement._drop = cell;
	row.appendChild(cell);
	body.appendChild(row);
	table.appendChild(body)
	replacement.appendChild(table);
	// assign given real select to replacement image
	replacement._hiddenInput = e;
	// hide given real select
	e.style.display = 'none';
	// insert replacement image into document
	e.parentNode.insertBefore(replacement, e);
	e._updateState = function() { this._replacement._updateState(); };
	FSite2._selectConvertOptions(e);
	FSite2.selects[FSite2.selects.length] = e;
	if (!FSite2._selectsTimer)
		FSite2._selectsTimer = setInterval(FSite2._selectsTimerProc, 250);
}

FSite2.extendMultipleSelect = function(e, c, i, dc)
{
	// check if given element is a select element
	if (e.tagName != 'SELECT')
		throw new Error('Given element is not a select element');
	// create a element as a replacement for given select
	var replacement = document.createElement('a');
	e._replacement = replacement;
	e._onfocus = e.onfocus;
	e.onfocus = function(ev)
	{
		if (!ev) ev = window.event;
		if (this._onblur)
			this.onblur(ev);
		this._replacement.focus();
	}
	e._onblur = e.onblur;
	e.onblur = function(ev)
	{
		if (!ev) ev = window.event;
		if (this._onblur)
			this.onblur(ev);
		this._replacement.blur();
	}
	// assign given real select to replacement image
	replacement._hiddenInput = e;
	replacement._images = i;
	replacement.className = c;
	replacement._disabledClassName = dc;
	replacement.href = '#';
	replacement.style.cursor = 'default';
	replacement.style.display = 'block';
	replacement.style.textDecoration = 'none';
	replacement.onfocus = function (event) {
		if (!event) event = window.event;
		if (window.getSelection) window.getSelection().removeAllRanges();
		if (this._hiddenInput._onfocus) this._hiddenInput._onfocus(event);
		return false;
	};
	replacement.onblur = function (event) {if (!event) event = window.event; if (this._hiddenInput._onblur) this._hiddenInput._onblur(event); return false; };
	replacement.onclick = function (event) {if (!event) event = window.event; event.cancelBubble = true; return false; };
	var div = document.createElement('div');
	replacement._options = div;
	// create table and tbody elements
	replacement.onkeydown = FSite2._selectOnKeyDown;
	replacement.onkeypress = FSite2._selectOnKeyPress;
	replacement.onkeyup = function(event) {this.focus(); this._lastKeyNonChar = true;};
	div.onmousedown = function(event) {if (!event) event = window.event; event.cancelBubble = true; return false;};
	replacement._selectCreateOptions = FSite2._selectCreateOptions;
	replacement._selectChange = function(option, add) { FSite2._selectChange.apply(this, add ? new Array(option, add) : new Array(option)); };
	replacement._selectDeselectAll = function() { return FSite2._selectDeselectAll.apply(this); };
	replacement._selectScrollToSelected = FSite2._selectScrollToSelected;
	var table = replacement._selectCreateOptions(div);
	replacement.appendChild(div);
	// hide given real select
	e.style.display = 'none';
	// insert replacement image into document
	e.parentNode.insertBefore(replacement, e);
	// decrease width of inner table if its height is too big to fit in div element
	if (table.clientHeight > replacement.clientHeight)
		table.style.width = (replacement.offsetWidth - 20) + 'px';
}

