/**
 * Class to instantiate a smart-finder based upon an existing (populated) SELECT element
 *
 * SmartFinder functionality depends on the existence of a holding DIV element for the SELECT element.
 * By default, it skips the first element of the SELECT, but can be configured to work with a startIndex
 *
 */
function highlight_item(item) {
	return new Effect.Highlight(item, {startcolor:'#dedede', endcolor:$(item).backgroundColor, keepBackgroundImage:true, restorecolor:''});
}
// the static method below is just used for running the handlers on an existing standard (click, keyup etc) event
Event.fireEvent = function(eventName, subject) {
	for(var i = 0; i < Event.observers.length; i++) {
		var observer = Event.observers[i];
		if(observer[0] == subject && observer[1] == eventName) {
			var handlerFunction = observer[2];
			handlerFunction(subject);
		}
	}
}

//USED TO MAKE SURE THE SMART FINDER IS INITIALISED (MUST APPEAR DIRECTLY AFTER THE <body> TAG)
initialise_smart_finder = true;

document.write('<script type="text/javascript" src="/generic/js/SmartFinder/SmartShim.js"></script>');

//USED TO MAKE SURE WE HAVE THE CORRECT CSS FO THE SMART FINDER
document.write('<link rel="stylesheet" href="/generic/js/SmartFinder/SmartFinder.css" type="text/css" />');
if(BrowserDetect.browser == "Explorer"  &&  BrowserDetect.version == 7) {
	document.write('<link rel="stylesheet" href="/generic/js/SmartFinder/SmartFinder-ie7.css" type="text/css" />');
} else if(BrowserDetect.browser == "Explorer"  &&  BrowserDetect.version == 6) {
	document.write('<link rel="stylesheet" href="/generic/js/SmartFinder/SmartFinder-ie6.css" type="text/css" />');
}

//CONSTRUCTOR TO INSTANTIATE THE SMARTFINDER'S SUPPORTING INPUT ELEMENTS
function SmartFinder(selectId, startIndex, autoActivate, optionsType, wideOptions) {
	this.startIndex = startIndex;
	if(startIndex == null) {
		this.startIndex = 1;
	}

	//keep record of the type of options e.g. Trades or Claims
	this.optionsType = optionsType;

	//keep record of wether the options need to be wide
	this.wideOptions = wideOptions;

	//this is used to hold the index of the element which has been selected
	this.oldInputValue = '';

	//this is used to stop simultaneous Scriptaculous effects being fired on the same instance
	this.isBusy = false;

	//sets the value of the minimum number of characters to type before searching for matches
	this.minimumInputLength = SmartFinder.MINIMUM_INPUT_LENGTH_DEFAULT;

	//locates the SELECT element, from which we need to proceed
	var selectElement = $(selectId);
	if(selectElement == null || selectElement.tagName != 'SELECT') {
		return;
	}
	selectElement.className = selectElement.className + ' ' + SmartFinder.CLASS_NAME;

	// set wide options class if needed
	if(this.wideOptions) {
		selectElement.className = selectElement.className + ' ' + SmartFinder.CLASS_NAME + 'Wide';
	}
	this.selectElement = selectElement;

	//locates the holding div for the SELECT element
	var selectHolderDiv = selectElement.parentNode;
	if(selectHolderDiv == null || selectHolderDiv.tagName != 'DIV') {
		return;
	}
	selectHolderDiv.className = selectHolderDiv.className + ' ' + SmartFinder.SELECT_HOLDER_DIV_CLASS;
	selectHolderDiv.style.zIndex = SmartFinder.Z_INDEX;
	selectHolderDiv.style.backgroundColor = 'white';
	selectHolderDiv.style.paddingTop = '2px';
	this.selectHolderDiv = selectHolderDiv;

	//hides the holding DIV element
	this.hideSelectHolderDiv(true);

	//creates a text input for recieving user input + container div for IE7 background fix + image for IE6 fake dropdown fix
	document.writeln('<div id="' + selectId + SmartFinder.INPUT_ID_SUFFIX + '_background" class="SmartFinderBackground"><input type="text" id="' + selectId + SmartFinder.INPUT_ID_SUFFIX + '" class="' + SmartFinder.INPUT_CLASS_NAME + '" autocomplete="off" /><img src="/generic/js/SmartFinder/' + SmartFinder.IE6_ARROW_IMG + '" alt="" id="img_' + selectId + SmartFinder.INPUT_ID_SUFFIX + '" class="hidden" /></div>');
	this.selectSmartFinder = $(selectId + SmartFinder.INPUT_ID_SUFFIX);
	this.imageArrow = $('img_' + selectId + SmartFinder.INPUT_ID_SUFFIX);
	this.selectSmartFinder.tabIndex = '50';
	this.selectElement.tabIndex = '50';

	// identify the background div and add to end of the div which contains the holder div
	this.selectSmartFinderBackground = $(selectId + SmartFinder.INPUT_ID_SUFFIX + '_background');
	this.selectHolderDiv.parentNode.appendChild(this.selectSmartFinderBackground);

	//creates a hidden variable to hold the index of the currently selected value
	var selectedValue = Builder.node('input', { type: 'hidden', id: selectId + '_SmartFinderIndex', value: ''});
	if(selectedValue == null) {
		return;
	}
	this.selectedValue = selectedValue;
	this.selectHolderDiv.appendChild(this.selectedValue);

	//if there is something selected in the SELECT list, put this value in the SmartFinder box
	if(selectElement.selectedIndex > startIndex) {
		this.selectedValue.value = selectElement.options[selectElement.selectedIndex].value;
		this.selectSmartFinder.value = selectElement.options[selectElement.options.selectedIndex].text;
		this.oldInputValue = this.selectSmartFinder.value;
		this.showDropDownArrow();
	}
	this.helperPromptHidden = true;
	this.activated = false;
	if(autoActivate == null) {
		autoActivate = true;
	}
	if(autoActivate) {
		this.activate();
	}
	this.dependantBlocksShown = false;
	this.shim = null;

	//Attach events to related elements
	//Click or type in SmartFinder box gets matches
	Event.observe(this.selectSmartFinder, 'keyup', SmartFinder.prototype.doSmartFinderAction.bindAsEventListener(this));
	Event.observe(this.selectSmartFinder, 'click', SmartFinder.prototype.doSmartFinderAction.bindAsEventListener(this));
	Event.observe(this.selectSmartFinder, 'focus', SmartFinder.prototype.doSmartFinderAction.bindAsEventListener(this));
	Event.observe(this.selectSmartFinder, 'blur', SmartFinder.prototype.showHelperPrompt.bindAsEventListener(this));
	Event.observe(this.imageArrow, 'click', SmartFinder.prototype.doSmartFinderAction.bindAsEventListener(this));

	//pressing down on the SmartFinder box, jumps into the select list
	Event.observe(this.selectSmartFinder, 'keydown', SmartFinder.prototype.doSmartFinderKeyNavigation.bindAsEventListener(this));

	//pressing up within the SELECT jumps to the SmartFinder
	Event.observe(this.selectElement, 'keydown', SmartFinder.prototype.doSmartFinderKeyNavigation.bindAsEventListener(this));

	//clicking on SELECT option, populates SmartFinder
	Event.observe(this.selectElement, 'click', SmartFinder.prototype.doUpdateSmartFinderContent.bindAsEventListener(this));
	Event.observe(this.selectElement, 'change', SmartFinder.prototype.doUpdateSmartFinderContentRaw.bindAsEventListener(this));

	//clicking away from the SELECT box closes it
	Event.observe(document, 'click', SmartFinder.prototype.doTurnOffSelectBox.bindAsEventListener(this));

	//when the text input has been blurred, validation is kicked off
	Event.observe(this.selectSmartFinder, 'blur', SmartFinder.prototype.doValidateInput.bindAsEventListener(this));
}

//STATIC CLASS ATTRIBUTES
SmartFinder.MINIMUM_INPUT_LENGTH_DEFAULT = 1;
SmartFinder.SELECT_LIST_HEIGHT = 5;
SmartFinder.SELECT_LIST_HEIGHT_SHOW_ALL = SmartFinder.SELECT_LIST_HEIGHT * 4;
SmartFinder.CLASS_NAME = 'SmartFinder';
SmartFinder.INPUT_ID_SUFFIX = '_' + SmartFinder.CLASS_NAME;
SmartFinder.NO_MATCH_ID_SUFFIX = SmartFinder.INPUT_ID_SUFFIX + 'NoMatch';
SmartFinder.SELECT_HOLDER_DIV_CLASS = SmartFinder.CLASS_NAME + 'SelectDivHolder';
SmartFinder.SHOW_ALL_OPTIONS_BUTTON_ORIGINAL_CLASS = SmartFinder.INPUT_ID_SUFFIX + '_ShowAllOptions';
SmartFinder.INPUT_CLASS_NAME = 'text ' + SmartFinder.CLASS_NAME;
SmartFinder.INPUT_CLASS_NAME_WITH_ARROW = SmartFinder.INPUT_CLASS_NAME + 'WithArrow';
SmartFinder.SCROLL_CLICK_THRESHOLD = 10;
SmartFinder.DROPDOWN_ARROW_IMAGE_WIDTH_PX = 0;
SmartFinder.INPUT_FIELD_RIGHT_PADDING_PX = 0;
SmartFinder.NO_MATCH_TEXT = '<div class="no_match_text">We cannot find an option to match the description, please type another description or click the "View All" button to select an option from the available list.</div>';
SmartFinder.Z_INDEX = 99;
SmartFinder.HELPER_PROMPT = "Start typing here to search";
SmartFinder.IE6_ARROW_IMG = 'SmartFinder-Property-Arrow-IE6.gif';
SmartFinder.OPTIONS_TYPE_TRADES = 1;
SmartFinder.OPTIONS_TYPE_CLAIMS = 2;
SmartFinder.OPTIONS = {};

//STATIC METHODS
SmartFinder.initialize = function() {
	var showAllLink = Builder.node('a', { href: '#', onclick: 'return false' });
	showAllLink.innerHTML = '<img src="/generic/js/SmartFinder/show-all-button.gif" alt="Show all" height="29">';
	var showAllDiv = Builder.node('div', { id: '_SmartFinder_ShowAllOptions', style: 'display: none' });
	showAllDiv.appendChild(showAllLink);
	SmartFinder.SHOW_ALL_DIV = showAllDiv;

	var showAllLinkWide = Builder.node('a', { href: '#', onclick: 'return false' });
	showAllLinkWide.innerHTML = '<img src="/generic/js/SmartFinder/show-all-button-wide.gif" alt="Show all" height="29">';
	var showAllDivWide = Builder.node('div', { id: '_SmartFinder_ShowAllOptionsWide', style: 'display: none' });
	showAllDivWide.appendChild(showAllLinkWide);
	SmartFinder.SHOW_ALL_DIV_WIDE = showAllDivWide;
}

//INSTANCE METHODS
//Activates the SmartFinder's functionality
SmartFinder.prototype.activate = function() {
	if(this.activated) {
		return;
	}
	this.activated = true;

	//stores the original TEXTBOX width and padding
	this.originalInputWidth = (BrowserDetect.browser == "Explorer") ? 292 : 295 //parseInt(Element.getStyle(this.selectSmartFinder, 'width').replace('px', ''), 10); // not sure why it is not working... TO INVESTIGATE LATER
	this.hideDropDownArrow();

	//store a local copy of the original SELECT options and empty the original
	//It uses the StartIndex value to skip unneeded values e.g. "Please select"
	if(this.optionsType != null) {
		if(SmartFinder.OPTIONS[this.optionsType] == null) {
			SmartFinder.OPTIONS[this.optionsType] = this.getOptionsFromSelect();
		}
		this.options = SmartFinder.OPTIONS[this.optionsType];
	}
	else {
		this.options = this.getOptionsFromSelect();
	}

  // There is a bug in IE6 where it needs to pause before running the following
  // - It worked when we had "alert()" in between calls!
	if(BrowserDetect.browser != "Explorer"  ||  BrowserDetect.version > 6) {
		this.IE6Fixer();
	} else {
	  // IE6
		setTimeout(this.IE6Fixer.bind(this), 1000);
	}

	this.showHelperPrompt(null);
}

SmartFinder.prototype.IE6Fixer = function() {
	var selectedOption = null;
	if(this.selectElement.selectedIndex >= this.startIndex) {
		selectedOption = this.selectElement.options[this.selectElement.selectedIndex];
	}

	this.selectElement.options.length = parseInt('0');

	//if something was already selected in the SELECT box, leave that one in
	if(selectedOption != null) {
		this.selectElement.options[this.selectElement.length] = selectedOption;
		this.selectElement.selectedIndex = 0; // This should not be necessary because with only one item it is 'automatically' selected
		this.selectSmartFinder.value = selectedOption.text;
		this.selectedValue.value = selectedOption.value;
		this.oldInputValue = this.selectedValue.value;
	}
}

//Returns an array of OPTIONS from the SELECT drop-down used for the SmartFinder.
SmartFinder.prototype.getOptionsFromSelect = function() {
	var selectOptions = new Array(this.selectElement.options.length-this.startIndex);
	for(var i = 0; i < (this.selectElement.options.length - this.startIndex); i++) {
		selectOptions[i] = new Option(this.selectElement.options[i+this.startIndex].text, this.selectElement.options[i+this.startIndex].value);
	}
	return selectOptions;
}

//Hides the DIV containing the SELECT element
SmartFinder.prototype.hideSelectHolderDiv = function(quickHide) {
	if(!this.selectHolderHidden && this.isBusy == false) {
		if(quickHide) {
			this.selectHolderDiv.style.display = 'none';
		}
		else {
			new Effect.BlindUp(this.selectHolderDiv, {
				beforeStart: SmartFinder.prototype.effectStarted.bindAsEventListener(this),
				afterFinish: SmartFinder.prototype.effectFinshed.bindAsEventListener(this),
				duration: 0.15
			});
		}
		this.selectHolderHidden = true;
	}
}
//Displays the DIV containing the SELECT element
SmartFinder.prototype.showSelectHolderDiv = function() {
	if(this.selectHolderHidden && this.isBusy == false) {

		new Effect.BlindDown(this.selectHolderDiv, {
				beforeStart: SmartFinder.prototype.effectStarted.bindAsEventListener(this),
				afterFinish: SmartFinder.prototype.effectFinshed.bindAsEventListener(this),
				duration: 0.15
		});
		this.selectHolderHidden = false;
	}
}

//Event handler for a Scriptaculous effect beginning
SmartFinder.prototype.effectStarted = function() {
	this.isBusy = true;
}

//Event handler for a Scriptaculous effect ending
SmartFinder.prototype.effectFinshed = function() {
	this.selectHolderDiv.style.bottom='';
	this.isBusy = false;
}

//shows helper text in the SmartFinder TEXT
SmartFinder.prototype.showHelperPrompt = function(event) {
	if(this.selectSmartFinder.value != ''  ||  this.selectSmartFinder.value == SmartFinder.HELPER_PROMPT) {
		return;
	}
	this.helperPromptHidden = false;
	this.selectSmartFinder.originalColor = this.selectSmartFinder.style.color;
	this.selectSmartFinder.style.color = '#999999';
	this.selectSmartFinder.value = SmartFinder.HELPER_PROMPT;
	this.selectHolderDiv.className = this.selectHolderDiv.className.replace(' arrow', '');
}

//shows helper text in the SmartFinder TEXT
SmartFinder.prototype.hideHelperPrompt = function() {
	if(this.helperPromptHidden) {
		return;
	}
	this.selectSmartFinder.value = '';
	this.selectSmartFinder.style.color = this.selectSmartFinder.originalColor;
	this.helperPromptHidden = true;
}

//Hides the "Show All Options" button
SmartFinder.prototype.hideShowAllOptionsButton = function() {
	this.showAllOptionsButton.style.display = 'none';
}
//Shows the "Show All Options" button
SmartFinder.prototype.showShowAllOptionsButton = function() {
	this.showAllOptionsButton.style.display = 'block';
}
//Hides the dropdown arrow for the SmartFinder
SmartFinder.prototype.hideDropDownArrow = function() {
	this.selectSmartFinder.className = SmartFinder.INPUT_CLASS_NAME;
	if(BrowserDetect.browser == "Explorer"  &&  BrowserDetect.version == 6) {
		$('img_' + this.selectSmartFinder.id).className = 'hidden';
	}
	Element.setStyle(this.selectSmartFinder, { width: this.originalInputWidth + 'px', paddingRight: SmartFinder.INPUT_FIELD_RIGHT_PADDING_PX + 'px' });
}
//Shows the dropdown arrow for the SmartFinder
SmartFinder.prototype.showDropDownArrow = function() {
	this.selectSmartFinder.className = SmartFinder.INPUT_CLASS_NAME_WITH_ARROW;
	this.selectHolderDiv.className += ' arrow';
	var new_width = (this.originalInputWidth - SmartFinder.DROPDOWN_ARROW_IMAGE_WIDTH_PX + SmartFinder.INPUT_FIELD_RIGHT_PADDING_PX);
	if(BrowserDetect.browser == "Explorer"  &&  BrowserDetect.version == 6) {
		$('img_' + this.selectSmartFinder.id).className = SmartFinder.INPUT_CLASS_NAME_WITH_ARROW;
	}
  // This calculation becomes NaN when the page is revisited (from the quote/2nd page)
	if(!isNaN(parseInt(new_width))) {
		if(BrowserDetect.browser == "Explorer"  &&  BrowserDetect.version == 6) {
			//Element.setStyle(this.selectSmartFinder, { paddingRight: SmartFinder.DROPDOWN_ARROW_IMAGE_WIDTH_PX + 'px' });
		}
		else {
			Element.setStyle(this.selectSmartFinder, { width: new_width + 'px', paddingRight: SmartFinder.DROPDOWN_ARROW_IMAGE_WIDTH_PX + 'px' });
		}
	}
}

//Perform matching of the options based on supplied input
//Returns an array of Option objects
SmartFinder.prototype.returnMatches = function(inputText) {

	// RB255-OR253: trim any leading and trailing whitespace
	inputText = inputText.replace(/^\s+|\s+$/g,"");

	var partialMatchCount = 0;
	var matchCount = 0;
	var matches = new Array();
	var partialMatches = new Array();
	for(var i = 0; i < this.options.length; i++) {
		var optionText = this.options[i].text;
		var matchPostion = optionText.toLowerCase().indexOf(inputText.toLowerCase());
		if(matchPostion > -1) {
//			myregexp = new RegExp("^" + inputText.toLowerCase()); // If they do not want to use a 'full word' but letters, use this line and comment-out the line below

			myregexp = new RegExp("\\b" + inputText.toLowerCase().replace(/([\(\)])/gi, /\$1/) + "\\b");
			match = myregexp.exec(optionText.toLowerCase());
			if(match != null) {
				matches[matchCount] = new Option(optionText, this.options[i].value);
				matchCount++;
			}
			else {
				partialMatches[partialMatchCount] = new Option(optionText, this.options[i].value);
				partialMatchCount++;
			}
		}
	}
	if((matchCount + partialMatchCount) > 0) {
		for(i = 0; i < partialMatchCount; i++) {
			matches[matchCount + i] = partialMatches[i];
		}
	}
	return matches;
}

//EVENT HANDLERS FOR SMARTFINDER ELEMENTS
//When the text field is blurred, the element should be validated
SmartFinder.prototype.doValidateInput = function() {
	//if there is some input, fire off an event signalling that the drop has changed
	Event.fireEvent('blur', this.selectElement);
	Event.fireEvent('update', this);
}

//Shows the DIVs required for the SmartFinder to work properly
SmartFinder.prototype.showDependantBlocks = function() {
	if(this.dependantBlocksShown) {
		return;
	}

	this.dependantBlocksShown = true;

	//have special 'No match' text block
	this.noMatchText = Builder.node('div', { display: 'none', id: this.selectElement.id + SmartFinder.NO_MATCH_ID_SUFFIX });
	Element.setStyle(this.noMatchText, { padding: '3px', width: '270px', border: '1px solid #949494', borderBottom: '0', marginTop: '2px' });
	// modify width if using wide options
	if(this.wideOptions) {
		if(BrowserDetect.browser == "Explorer")
			Element.setStyle(this.noMatchText, {width: '295px'});
		else
			Element.setStyle(this.noMatchText, {width: '287px'});			
	}
	this.noMatchText.innerHTML = SmartFinder.NO_MATCH_TEXT;
	this.selectHolderDiv.appendChild(this.noMatchText);

	// insert shim behind 'No match' text block
 	if(this.wideOptions) {
		this.shim = new SmartShim(this.selectElement.id + SmartFinder.NO_MATCH_ID_SUFFIX, {fixedWidth:295, fixedHeight: 79});
	} else {
		this.shim = new SmartShim(this.selectElement.id + SmartFinder.NO_MATCH_ID_SUFFIX, {fixedWidth:280, fixedHeight: 90});
	}
	this.selectHolderDiv.appendChild(this.shim.getShim()); // insert into selectHolder

	//locate the "Show All" button and attach associated event to it
	if(this.wideOptions) {
		var showAllOptionsButton = SmartFinder.SHOW_ALL_DIV_WIDE.cloneNode(true);
	} else {
		var showAllOptionsButton = SmartFinder.SHOW_ALL_DIV.cloneNode(true);
	}
	showAllOptionsButton.id = this.selectElement.id + showAllOptionsButton.id;
	showAllOptionsButton.style.display = 'block';
	if(showAllOptionsButton == null) {
		return null;
	}
	this.showAllOptionsButton = showAllOptionsButton;
	this.selectHolderDiv.appendChild(showAllOptionsButton);

	//Click on 'Show all options' button shows all the options!
	Event.observe(this.showAllOptionsButton.firstChild, 'click', SmartFinder.prototype.doShowAllOptionsAction.bindAsEventListener(this));
}

//When user enters input, a match is performed and the SELECT box is updated
SmartFinder.prototype.doSmartFinderAction = function() {
	if(!this.activated) {
		return null;
	}
	this.showDependantBlocks();

	this.hideHelperPrompt();

	//if we have already selected a value and not changed it then show all
	if(this.selectedValue.value != '') {
		if(this.oldInputValue == this.selectSmartFinder.value) {
			//show all the options available
			if(this.selectHolderHidden) {
				this.doShowAllOptionsAction();
			}
			else {
				this.hideSelectHolderDiv();
			}
			return;
		}
		else {
			//hide dropdown arrow for the SmartFinder
			this.hideDropDownArrow();
			this.selectedValue.value = '';
		}
	}
	this.oldInputValue = this.selectSmartFinder.value;

	//only return matches after we have entered the minimum number of characters for input
	var inputText = this.selectSmartFinder.value;
	var matches = new Array();
	if(inputText.length >= this.minimumInputLength) {
		matches = this.returnMatches(inputText);
	}

	//if there were no matches, we can hide the SELECT box...
	//...else populate the SELECT box and select the correct OPTION
	this.selectElement.options.length = 0;
	if(matches.length > 0) {
		this.hideNoMatchText();
		var inputTextFound = false;
		for(var i = 0; i < matches.length; i++) {
			this.selectElement.options[i] = matches[i];
			if(matches[i].text.toLowerCase() == inputText.toLowerCase()) {
				this.selectElement.selectedIndex = i;
				inputTextFound = true;
			}
		}
		if(!inputTextFound) {
			this.selectElement.options.selectedIndex = -1;
		}

		//make the original SELECT element have a larger height
		this.selectElement.size = SmartFinder.SELECT_LIST_HEIGHT;
		if(matches.length < this.options.length) {
			this.showShowAllOptionsButton();
		}
		this.showSelectHolderDiv();
	}
	else {
		if(this.selectSmartFinder.value != '') {
			this.showNoMatchText();
		}
	}
}

//Shows text to state that a match has not been found. The 'View all' options button will be show also.
SmartFinder.prototype.showNoMatchText = function() {
	this.showSelectHolderDiv();
	// insert special blank option to prevent Firefox from showing XX in select box
	this.selectElement.options[0] = new Option("","");
	this.selectElement.hide();
	this.noMatchText.show();
	this.showShowAllOptionsButton();
	this.shim.resize();
	//this.shim.showShim();
}

//Hides the text to show that there is no match
SmartFinder.prototype.hideNoMatchText = function() {
	this.selectElement.show();
	this.noMatchText.hide();
	this.shim.hideShim();
}

//Shows all available options to the user irrespective of input entered
SmartFinder.prototype.doShowAllOptionsAction = function(event) {
	this.hideNoMatchText();

	this.selectElement.options.length = 0;

	inputTextFound = false;
	var input_text = this.selectSmartFinder.value;
	input_text = input_text.toLowerCase();
	for(var i = 0; i < this.options.length; i++) {
		var dropdown_text = this.options[i].text;
		this.selectElement.options[i] = new Option(dropdown_text, this.options[i].value, false, false);
		dropdown_text = dropdown_text.toLowerCase();
		if(dropdown_text == input_text) {
			this.selectElement.selectedIndex = i;
			inputTextFound = true;
		}
	}

	if(!inputTextFound) {
		this.selectElement.options.selectedIndex = -1;
	}
	this.selectElement.size = SmartFinder.SELECT_LIST_HEIGHT_SHOW_ALL;
	if(event) {
		highlight_item(this.selectElement);
	}
	this.hideShowAllOptionsButton();
	this.showSelectHolderDiv();
}

//handles navigation to and from the SELECT box and the SmartFinder box
SmartFinder.prototype.doSmartFinderKeyNavigation = function(event) {
	var target = Event.element(event);
	var keyCode = event.which || event.keyCode;
	//if we are in the SmartFinder field, jump to the SELECT list
	if(target.tagName == 'INPUT' && keyCode == Event.KEY_DOWN) {
		if(this.selectElement.options.length > 0 && !this.selectHolderHidden) {
			this.selectElement.focus();
		}
	}
	//if we are in the SELECT list, jump to the SmartFinder field
	else if(target.tagName == 'SELECT' && keyCode == Event.KEY_UP) {
		if(this.selectElement.selectedIndex == 0) {
			this.selectSmartFinder.focus();
		}
	}
	//if we are in the SELECT list, allow enter key to populate the SmartFinder
	else if(target.tagName == 'SELECT' && keyCode == Event.KEY_RETURN) {
		this.doUpdateSmartFinderContent();
	}
}

//When we select an option from the SELECT box, the correct value is entered into the SmartFinder box
//NOTE: This does not hide the SELECT list afterwards
SmartFinder.prototype.doUpdateSmartFinderContentRaw = function() {

	// dont allow special blank option to be selected
	if(this.selectElement.selectedIndex > -1 && this.selectElement.options[this.selectElement.selectedIndex].value == "")
		this.selectElement.selectedIndex = -1;

	//populates the input fields with values from the Select
	if(this.selectElement.selectedIndex > -1) {
		this.selectSmartFinder.value = this.selectElement.options[this.selectElement.selectedIndex].text;
		this.selectedValue.value = this.selectElement.options[this.selectElement.selectedIndex].value;
		this.oldInputValue = this.selectSmartFinder.value;

		//Do a fake blur to revalidate if moving up or down the SELECT with arrow keys
		Event.fireEvent('blur', this.selectElement);
	}
}

//When we select an option from the SELECT box, the correct value is entered into the SmartFinder box
SmartFinder.prototype.doUpdateSmartFinderContent = function(event) {
	/*
	// Dont process click event if it happens near the scrollbar (this only seems to affect IE7)
	if(event)  {  // event is missing when using keyboard only
		var inputPos = Position.positionedOffset(this.selectSmartFinder);
		if(event.clientX > (inputPos[0] + this.selectSmartFinder.clientWidth - SmartFinder.SCROLL_CLICK_THRESHOLD)) {
			return;
		}
	}
	*/
	this.doUpdateSmartFinderContentRaw();
	//convert the SmartFinder into a dropdown
	this.showDropDownArrow();
	//hide the select list
	this.hideSelectHolderDiv();
	// trigger fake blur event to revalidate row
	this.doValidateInput();
}

//Closes the SELECT box when not needed i.e. when anything other than the SmartFinder or SELECT have been clicked
SmartFinder.prototype.doTurnOffSelectBox = function(event) {

	//only deal with clicks
	if(event.type != 'click')
		return;

	var target = Event.element(event);

	// do not blindup if focus transferred to an element relating to the current checkbox
	try{
		if(target == this.selectElement
				|| target == this.selectSmartFinder
				|| (this.showAllOptionsButton && target == this.showAllOptionsButton.firstChild.firstChild )) {
			return;
		}
	}catch(e){
		return;
	}
	//dont worry if the select box is already hidden
	if(this.selectHolderHidden) {
		return;
	}

	this.hideSelectHolderDiv();
}

//Standard Setters
SmartFinder.prototype.setMinimumInputLength = function(minimumInputLength) {
	this.minimumInputLength = minimumInputLength;
}

//Duplicates the state of the current SmartFinder instance to another SmartFinder instance, but does not
//change the elements to which they are attached.
SmartFinder.prototype.copyState = function(destination) {

	if (destination==null) return false;

	// copy value of text input
	destination.selectSmartFinder.value = this.selectSmartFinder.value;

	// copy value of hidden input
	destination.selectedValue.value = this.selectedValue.value;

	// copy current select options
	destination.selectElement.length = 0;
	for(var i = 0; i < this.selectElement.options.length; i++) {
		destination.selectElement.options[i] = new Option(this.selectElement.options[i].text, this.selectElement.options[i].value, false, this.selectElement.options[i].selected);
	}

	// copy class (determines if drop-down arrow is showing or not)
	destination.selectSmartFinder.className = this.selectSmartFinder.className;

}

//Clears the current state (select items, text input value, hidden input value etc.)
SmartFinder.prototype.resetState = function() {

	// for SSP to capture the change, we need to make sure the 'Please select' option is re-inserted and selected
	this.selectElement.options[0] = new Option('Please select', '', true, true);

	// reinstate all select objects
	for(var i = 0; i < this.options.length; i++)
		this.selectElement.options[(i+1)] = new Option(this.options[i].text, this.options[i].value);

	// reset selected index (should be done above with the 'Please select' option but this makes sure)
	this.selectElement.selectedIndex = 0;

	// clear value of text input
	this.selectSmartFinder.value = "";

	// clear value of hidden input
	this.selectedValue.value = "";

	// hide dropdown arrow
	this.hideDropDownArrow();

}

