var ACSearch = {
	
  	// Object for retaining search state between AJAX calls - initiated with defaults
  	searchState : { searchTerm: "", facet: "all", archive: "false", date: "all", security: "internalexternal", sort: "relevancy", product: "", results: 0, requestId: 1 },
  	// list of products for the dropdown in advanced search
  	products: [],
  	// know if last request has been fully loaded or not
  	loading: false, 
  	// keep track of which request is the last
  	lastReceivedRequestId: 1,
  	// how many products on the last clicked level
  	totalProducts: 0, 
  	// localized strings
  	localized: {},
  	// set flag to prevent issues when double clicking pagination links
  	preparingAjax: false, 
  	// callback function that is being used when product facets are returned
  	callback: function(){},
  	filterDropDowns:['product','documentTypeFilter','archiveTypeFilter'],
  	supportedBentoLocales:['en_US','ja_JP','en_GB'],
  	descriptionTruncateLength:60,
  	
  	// getting set up!
	'initialize': function() {
  		
		ACSearch.searchState.searchTerm = $F('searchsupport');
		ACSearch.updateRecentSearches(ACUtil.inputCleanup(ACSearch.searchState.searchTerm));
				
		if (!ACSearch.isAdvancedSearch){
			ACSearch.populateWithProducts();
			
			if (ACSearch.supportedBentoLocales.indexOf(ACProductBrowser.locale)>-1){
				$('sidebar').show();
				$('www_more').writeAttribute('href', 'http://www.apple.com' + (ACSearch.getCountry()=='us'?'':'/'+ACSearch.getCountry()) + '/search/?q=' + ACSearch.searchState.searchTerm);
				$('aos_more').writeAttribute('href', 'http://store.apple.com/' + ACSearch.getCountry() + '/search?find=' + ACSearch.searchState.searchTerm);
				ACSearch.requestProductInfoResults();
				ACSearch.requestAppleStoreResults();
			}else{
				$('content').removeClassName('box').addClassName('nosidebar');
			}
		}
		if(ACUtil.gup("product")!="") {
  			ACSearch.searchState.product = ACUtil.gup("product");
  		}
  		
  		if(ACUtil.gup('archive')=='y'){
  			$('archiveTypeFilter').selectedIndex = 1;
  		}
		
		if(ACSearch.searchState.searchTerm!='') {
			if(ACUtil.gup('fac')) {
				ACSearch.searchState.facet = ACUtil.gup('fac');
			}
			if(ACUtil.gup('archive')) {
				ACSearch.searchState.archive = "true";
			}
			
			ACSearch.displayResults($('results_all').innerHTML, 'all', 1);
			ACHistory.addSearch(ACSearch.searchState.searchTerm, 'en_US');
			
			// defining the function that is called after there has been a change in the product browser
			ACProductBrowser.callbackTrigger = function(strID) {
				
				var linkHTML;
				
				if (strID == ACProductBrowser.rootProduct) {
					linkHTML = ACSearch.localized.improve;
					ACSearch.loadMainFacets(function() {
						ACSearch.loadProducts(ACProductBrowser.rootProduct);
					});
				} else {
					linkHTML = ACSearch.localized.resultsRestricted + " <span class=\"productname\">" + ACProductBrowser.getProductName(strID, ACProductBrowser.genericProducts) + "</span>";
				}
				
				$('pb-restrict').update(linkHTML);
				
				ACSearch.searchState.facet = 'all';
				
				if(strID!=ACProductBrowser.rootProduct) {
					ACSearch.searchAJAX('product_' + strID, undefined, 'y');
				}
				else {
					ACSearch.searchAJAX('product_' + ACProductBrowser.rootProduct, undefined, 'y');
				}
			};
			
		}
		
	},
  	// Perform AJAX search
  	'searchAJAX' : function(filterName, type, getFilters, sort, origin) {
  		
  		if(ACSearch.preparingAjax) {
  			return;
  		}
  		ACSearch.preparingAjax = true;
  		
	  	var loading = $('loading');
		var results_all = $('results_all');
		var disambiguation = $('disambiguation');
		var featured = $('featured');
	  	
		var searchTerm = $F('searchsupport');
		// if placeholder search field text is the same as searchTerm, return
		if(ACSearch.localized.searchBoxPlaceHolder == searchTerm) {
			ACSearch.preparingAjax = false;
			return;
		}
		
		if((origin!='form' && searchTerm==="") || (origin!='form' && $F('searchsupport')!=ACUtil.trim(ACSearch.searchState.searchTerm.replace(/\+/g, " ")) )) {
			// this could mean the user has removed the previous search query without submitting the form
			// or the user started writing a new query without submitting
			searchTerm = ACSearch.searchState.searchTerm;
			$('searchsupport').value = searchTerm;
		}
		
		// object to contain key/value pairs of all query parameters
		var queryParameters = {};
		
		var src = $('src') ? $('src').value : "";
		
		if(filterName!==undefined) {
			var filterType = filterName.substr(0, filterName.indexOf("_"));
			var filterValue = filterName.substr(filterName.indexOf("_")+1, 35);
			ACSearch.searchState[filterType] = filterValue;
		}
		
		if(searchTerm!=="" && (ACSearch.searchState.searchTerm!=searchTerm || ACUtil.parseUri().query.indexOf("&q=")==-1)) {
		   	// do a page flip instead of AJAX call to update URL for bookmarking
			
			queryParameters['product'] = "";
			queryParameters['q'] = unescape(searchTerm).replace(/\&/g, "%26");
		    
		   	window.location = ACSearch.generateGetUrl("search", queryParameters);
		   	ACSearch.preparingAjax = false;
		   	return;
		   	
		}
		else if(searchTerm=='') {
			ACSearch.preparingAjax = false;
			return;
		}
		
		ACSearch.searchState.searchTerm = searchTerm;
		ACSearch.updateRecentSearches(ACUtil.inputCleanup(ACSearch.searchState.searchTerm));
		
		queryParameters['q'] = searchTerm;
		
		if(ACSearch.searchState.facet==="all") {
			getFilters = "y";
		}
		
		if(getFilters!==undefined && getFilters==="y") {
			queryParameters['getFilters'] = true;
		}
		
		if(ACSearch.searchState.archive==="true") {
			queryParameters['archive'] = true;
		}
		if(ACSearch.searchState.facet!=="" && ACSearch.searchState.facet!=="") {
			queryParameters['fac'] = ACSearch.searchState.facet;
		}
		if(ACSearch.searchState.security!=="") {
			queryParameters['security'] = ACSearch.searchState.security;
		}
		if(ACSearch.searchState.date!=="") {
			queryParameters['date'] = ACSearch.searchState.date;
		}
		if(ACSearch.searchState.product!=="" && ACSearch.searchState.product!='MAIN_PRODUCTS') {
			queryParameters['product'] = ACSearch.searchState.product;
		}
		
		// sort can be done by recency (or default by relevancy)
		if(ACSearch.searchState.sort==="recency") {
			queryParameters['sort'] = 'recency';
		}
		
		// type can be 'backward' and 'forward' as well as 'search' which is default
		if(type!==undefined  && !(ACSearch.searchState.facet=="all" && type=="0")) {
			queryParameters['type'] = type
		}
		
		if(src!=="") {
			queryParameters['src'] = src;
		}
		
		ACSearch.searchState.requestId = ACSearch.searchState.requestId+1;
		queryParameters['requestid'] = ACSearch.searchState.requestId;
		queryParameters['locale'] = ACProductBrowser.locale;
		
		if(ACUtil.readCookie('s_vi')!==null) {
			// pass site catalyst session ID for reporting
			queryParameters['sitecatalystid'] = escape(ACUtil.readCookie('s_vi'));
		}
		
		// add randomized parameter on the end to circumvent caching through mod_jk
		queryParameters['nocache'] = ACUtil.randomString();
		
		new Ajax.Request(ACSearch.generateGetUrl("ajax", queryParameters), {
			method: 'get',
			onSuccess: function(transport) {
				var reqId = transport.getHeader('RequestId');
		  		ACSearch.displayResults(transport.responseText, type, reqId);
			},
			onFailure: function() { 
				ACSearch.showFailureMessage(ACSearch.localized.error);
			} 
		});
		
		clearInterval(ACSearch.spinnerInterval);
		clearInterval(ACSearch.resultInterval);
		
		if(!ACSearch.loading) {
			
			ACSearch.resultInterval = window.setInterval(function () {
				// hide main content if wait is over 300 milliseconds
				if(!ACSearch.loading && ACSearch.searchState.requestId==(ACSearch.lastReceivedRequestId+1)) results_all.hide();
			}, 500);
	
			ACSearch.spinnerInterval = window.setInterval(function () {
				// only show spinner if search is taking more than 700 milliseconds
				if(!ACSearch.loading && ACSearch.searchState.requestId==(ACSearch.lastReceivedRequestId+1)) loading.show();
			}, 1000);
		
		}
		
	},
	
	'generateGetUrl': function(page, queryParameters) {
		var currentUri = ACUtil.getCurrentUri();
		var returnUrl = "index?page=" + page;
		
		for(var query in queryParameters) {
			var value = typeof queryParameters[query] == 'boolean' ? "y" : queryParameters[query];
			returnUrl += "&" + query + "=" + value;
		}
		
		return returnUrl;
	},
	
	'displayResults': function(responseText, type, requestId) {
		
		clearInterval(ACSearch.spinnerInterval);
		clearInterval(ACSearch.resultInterval);
		
		ACSearch.preparingAjax = false;
		
		if(requestId!=ACSearch.searchState.requestId) {
			//avoid spinner that does not disappear
			return;
		}
		
		ACSearch.lastReceivedRequestId = parseInt(requestId);
		
  		ACSearch.loading = true;
  		ACSearch.totalProducts = 0;
		
		var loading = $('loading');
		var results_all = $('results_all');
		
		var src = $('src').value;
		
		var disambiguation = $('disambiguation');
		var featured = $('featured');
		
		$('query').show();
		
		if(ACUtil.trim(responseText)==="") {
			ACSearch.showFailureMessage(ACSearch.localized.errorBusy);
			return;
		}
		else {
			results_all.innerHTML = responseText;
		}
		
		// first check if the result is a PSP page (redirect from SN)
		if($('redirect_url')) {
			eval($('redirect_url').innerHTML);
			return;
		}
		
		if($("showing_results") && $("results-Support-ul")) {
			$("showing_results").innerHTML = parseInt($("showing_results").innerHTML, 10) + $("results-Support-ul").getElementsByTagName("li").length;
			if($("definition")) { $("showing_results").innerHTML = parseInt($("showing_results").innerHTML, 10) + 1; }
		}
		
		if(type===undefined && $('total_results')) {
			
			// due to a bug in totalResults, the value for totalResults has to be set if it is lower than showing_results
			if($("showing_results") && parseInt($('total_results').innerHTML, 10)>parseInt($("showing_results").innerHTML, 10) && parseInt($('total_results').innerHTML, 10)<=10) {
				$('total_results').innerHTML = $("showing_results").innerHTML;
			}
			
		}
		
		if($('total_results') && ($('total_results').innerHTML=="" || $('total_results').innerHTML=="0")) {
			$('total_results').innerHTML = ACSearch.searchState.results;
		}
		
		if(!$('total_results')) {
			ACSearch.showFailureMessage(ACSearch.localized.error);
			return;
		}
		

		ACSearch.searchState.results = $('total_results').innerHTML;
		
		if(ACSearch.searchState.results==0) {
			$('query').hide();
		}
		
		if ($('ajax_pagination')){
			$('pagination').update($('ajax_pagination').innerHTML);
		}else{
			$('pagination').update('');
		}
		if ($('ajax_filter')){
			var s = $('ajax_filter').innerHTML;
			//strip out ids
			s = s.replace(/id=\"[A-Za-z0-9_]+\"/g, '');
			s = s.replace(/id=[A-Za-z0-9_]+/g,''); //ie6 fix
			$('filter').update(s);
		}	
		if($('ajax_filters')) {
			// ajax_filters is the complete content block with all possible filters:
			// facets, security and date
			if($('ajax_facets')) {
				ACSearch.populateDropDown($('documentTypeFilter'), $('ajax_facets'), 'facet_'+ACSearch.searchState.facet);
			}
			
			Element.remove($('ajax_filters'));
		}
		
		if(ACSearch.searchState.product=='') {
			if($('ajax_disambiguation') ) {
				disambiguation.innerHTML = $('ajax_disambiguation').innerHTML;
				Element.remove($('ajax_disambiguation'));
				disambiguation.show();
			}else{
				$('query').hide();
			}
			if($('ajax_featured') && (ACProductBrowser.locale.indexOf('en_')==0||ACProductBrowser.locale.indexOf('ja_')==0)) {
				featured.innerHTML = $('ajax_featured').innerHTML;
				Element.remove($('ajax_featured'));
				featured.show();
			}
		}
		
		ACSearch.enableFilters();
		loading.hide();
		
		// delay results slightly for product restriction
		if(ACSearch.searchState.product!="" && ACSearch.totalProducts>1) {
			setTimeout("$('results_all').show();", 600);
		}
		else {
			$('results_all').show();
		}

		ACSearch.loading = false;
	},
	
	// remove category selections
	'removeCategorySelection' : function(element) {
		var lis = $(element).getElementsByTagName('li');
		for(var i=0;i<lis.length;i++) {
			var li = lis[i];
			Element.removeClassName(li.getElementsByTagName('a')[0], 'selected');
		}
	},
	
	'applySearchFilters': function(element, selectedFilter, getFilters) {
	
		var lis = element.getElementsByTagName('li');
		for(var i=0;i<lis.length;i++){
		  var li = lis[i];
		  var elementId = li.getElementsByTagName('a')[0].getAttribute('id');
		  
		  var elementShortId = elementId.substr(elementId.indexOf("_")+1,15);
		
		  if(elementId==selectedFilter) {
			  Element.addClassName(li.getElementsByTagName('a')[0], 'selected');
		  }
		  
		  li.onclick = function(element) {
			  var elementId = this.getElementsByTagName('a')[0].getAttribute('id');
	
			  ACSearch.searchAJAX(elementId, '0', getFilters, undefined, 'facet');
			  ACSearch.removeCategorySelection(this.parentNode);
			  Element.addClassName(this.getElementsByTagName('a')[0], 'selected');
			  return false;
		  };
	
		}
	},
	
	'performNewSearch' : function(searchTerm) {
		$('searchsupport').value = searchTerm;
		ACSearch.searchAJAX(undefined, undefined, 'y', undefined, 'form');
	},
	
	'updateRecentSearches' : function(searchTerm) {
		
  		var searchTerms = [];
  
		if(searchTerm!==undefined) {
  			
			searchTerm = searchTerm.substr(0,100);
			
			if(ACUtil.readCookie('ac_search')===null) {
				searchTerms[0] = searchTerm;
			}
			else {
				searchTerms = ACUtil.readCookie('ac_search').split('||');
				var searchTermsUCase = ACUtil.readCookie('ac_search').toUpperCase().split('||');
				
				if(searchTermsUCase.indexOf(searchTerm.toUpperCase())!=-1) {
					// make sure to remove the search term if it already exists so we can move it to the top
					searchTerms.splice(searchTermsUCase.indexOf(searchTerm.toUpperCase()), 1);
				}
				
				if(searchTerms.length>5) {
					searchTerms.pop();
				}
				searchTerms.reverse();
				searchTerms.push(searchTerm);
				searchTerms.reverse();

			}
			
			ACUtil.writeCookie('ac_search', searchTerms.join('||'));
		
		}
		
		searchTerms = ACUtil.readCookie('ac_search')!==null ? ACUtil.readCookie('ac_search').split('||') : [];
		var ulList = '';
		
		for(var i = 0; i < searchTerms.length; i++) {
			if(ACUtil.trim(searchTerms[i]).length>0) {
				var searchTermDisplay = searchTerms[i].replace(/&quot;/g, "%22");
				var searchTermValue = searchTerms[i].replace(/&amp;/g, "&");
				
				var displaySearchTerm = searchTermDisplay.length>25 ? searchTermDisplay.substr(0,23) + "..." : searchTermDisplay;
				
				ulList += '<li><a href="index?page=search&q=' + unescape(searchTermValue).replace(/\"/g, "%22").replace(/\&/g, "%26") + '">' + displaySearchTerm + '</li>';
			}
		}
		
		//TODO
		//$('previous-searches-ul').innerHTML = ulList;
	},
	
	'clearRecentSearches' : function() {
		ACUtil.writeCookie('ac_search', '');
		ACSearch.updateRecentSearches();
	},
	
	'showFailureMessage' : function(errorMessage) {
		$('loading').hide();
		var results_all = $('results_all');
		results_all.innerHTML = '<div class="filter">' + errorMessage + '</div>';
		results_all.show();
	},
	
	'sortByRecency' : function() {
		ACSearch.searchState.sort = 'recency';
		ACSearch.searchAJAX();
	},
	
	'sortByRelevancy' : function() {
		ACSearch.searchState.sort = 'relevancy';
		ACSearch.searchAJAX();
	},
	'initializeProducts': function() {
		// this function is called if user clicks to expand facet or user comes in with product pre selected
		var product = ACUtil.gup("product");
		
		ACSearch.searchState.product = product;
		ACSearch.populateProducts();	
	},
	
	'populateProducts': function() {
		
		ACProductBrowser.displayProducts(ACProductBrowser.rootProduct, undefined, function() {
			if(ACSearch.searchState.product!="") {
				ACProductBrowser.rootProduct = ACProductBrowser.getProduct(ACSearch.searchState.product, ACProductBrowser.genericProducts).parentid;
				$('pb-restrict').update(ACSearch.localized.resultsRestricted + " <span class=\"productname\">" + ACProductBrowser.getProductName(ACSearch.searchState.product, ACProductBrowser.genericProducts) + "</span>");
			}
			ACSearch.loadProducts(ACProductBrowser.rootProduct);
		});
		
	},
	'loadProducts': function(loadProduct) {
		
		if(($('products') && ACUtil.trim($('products').innerHTML)!="") && 
				(ACSearch.searchState.product=="" || ACSearch.searchState.product!=ACUtil.gup("product") || ACSearch.searchState.requestId>1)) {
			
			// find all products that are returned from search query
			var products = {
				"id": loadProduct , "products": []
			};
			var searchProducts = [];
			searchProducts = eval("[" + $('products').innerHTML + "]");
			
			var totalProducts = 0;
			
			for(var i=0;i<searchProducts.length;i++) {
				var product = Object.clone(ACProductBrowser.getProduct(searchProducts[i], ACProductBrowser.genericProducts));
				if(product && product.thumbnail) {
					// empty sub products
					product.products = [];
					products['products'][totalProducts] = product;
					totalProducts++;
				}
			}
			
			ACSearch.totalProducts = totalProducts;
			
			if(loadProduct!=ACProductBrowser.rootProduct) {
				ACProductBrowser.insertProductsAtLevel(ACProductBrowser.products, loadProduct, products['products']);
			}
			else if(totalProducts==0){
				ACProductBrowser.products = ACUtil.clone(ACProductBrowser.genericProducts);
			}
			else {
				ACProductBrowser.products.products = products['products'];
			}
			ACProductBrowser.populateBrowser(loadProduct);
		}
		else if(ACUtil.gup("product")!="") {
			// coming in with a preset product as parameter
			// show all products on this level, but delete products afterwards to start fresh
			loadProduct = ACProductBrowser.rootProduct;
			ACProductBrowser.products.id = loadProduct;
			
			var cloneGeneric = ACUtil.clone(ACProductBrowser.genericProducts);
			ACProductBrowser.products = cloneGeneric;

			ACProductBrowser.populateBrowser(loadProduct);
			ACProductBrowser.hiliteProduct(ACSearch.searchState.product);
			
			//fix iphone internal/external loading issue
			/*
			for(var i=0;i<ACProductBrowser.products.products.length;i++) {
				ACProductBrowser.products.products[i].products = [];
			}
			*/
			
			$('pb-restrict').update(ACSearch.localized.resultsRestricted + " <span class=\"productname\">" + ACProductBrowser.getProductName(ACSearch.searchState.product, ACProductBrowser.genericProducts) + "</span>");
			
			ACProductBrowser.rootProduct = 'MAIN_PRODUCTS';
		}
		
	},
	
	'advancedSearch': function() {
		// object to contain key/value pairs of all query parameters
		var queryParameters = {};
		
		if(ACSearch.searchState.product!="" && ACSearch.searchState.product!=ACProductBrowser.rootProduct) {
			queryParameters['product'] = ACSearch.searchState.product;
	   	}
	   	if($('facet') && $('facet').value!="all") {
	   		queryParameters['fac'] = $('facet').value;
	   	}
	   	if($('archiveval') && $('archiveval').value!="n") {
	   		queryParameters['archive'] = $('archiveval').value;
	   	}
	   	if($('product') && $('product').value!="all") {
	   		queryParameters['product'] = $('product').value;
	   	}
	   	
	   	var searchTerm = ACUtil.trim($F('searchsupport'));
	   	var boolSelector = $$('input:checked[type="radio"][name="boolselector"]').pluck('value');
	   	// convert spaces to OR operators if "All keywords" is checked
	   	if(boolSelector=="AND") {
	   		var arrTerms = ACUtil.trim(searchTerm.replace(/\s+/g, " ")).match(/("[^"]+"|[\w]+)/g);
	   		searchTerm = "";
	   		for (var i=0; i<arrTerms.length; i++){
	   			if (arrTerms[i].toLowerCase()!="and"){
	   				if (i<arrTerms.length-1)
		   				searchTerm += arrTerms[i] + " AND ";
		   			else
		   				searchTerm += arrTerms[i];
	   			}
	   		}
	   	}
	   	// put NOT in front of every term in the "Exclude keywords" field
	   	if(searchTerm && searchTerm!="" && ACUtil.trim($F('exclude'))!="") {
	   		searchTerm += " NOT " + ACUtil.trim($F('exclude').replace(/\s+/g, " ")).replace(/\s/g, " NOT ");
	   	}
	   	
	   	if(!searchTerm || searchTerm=="") {
	   		alert(ACSearch.localized.errorNoSearchTerm);
	   		return;
	   	}
	   	
	   	queryParameters['q'] = unescape(searchTerm).replace(/\&/g, "%26");
	   	
	   	window.location = ACSearch.generateGetUrl("search", queryParameters);
	   	
	   	return false;
	},
	
	'populateWithProducts': function() {
		ACProductBrowser.fetchProducts(undefined, 'ACSearch.receiveGenericProducts', '');
	},
	
	// used for advanced search drop down menu only
	'receiveGenericProducts': function(json) {
		
		var productDropDown = $('product');
		productDropDown.options.length = 1;
		
		// iterate through the product list and only populate ACSearch.products with lowest level
		ACSearch.findLowestLevelProducts(json);
		
		// sort by name (localized and case insensitive)
		var compare = function(a, b) {
			return (b.name.toUpperCase() < a.name.toUpperCase()) - (a.name.toUpperCase() < b.name.toUpperCase());
		};
		ACSearch.products.sort(compare);
		
		for (var i=0;i<=ACSearch.products.length;i++) {
			if(ACSearch.products[i] && ACSearch.products[i].name && ACSearch.products[i].id) {
				productDropDown.options[productDropDown.options.length] = new Option(ACSearch.products[i].name, ACSearch.products[i].id, (ACUtil.gup('product')==ACSearch.products[i].id));
				if(ACUtil.gup('product')==ACSearch.products[i].id){
					productDropDown.selectedIndex = productDropDown.options.length-1;
					ACSearch.doPreview(productDropDown);
				}
			}
		}
		
	},
	
	'findLowestLevelProducts': function(json) {
		
		if(!json.products) {
			return;
		}
		
		for (var i=0;i<=json.products.length-1;i++) {
			if(json.products[i].products && json.products[i].products.length>1) {
				ACSearch.findLowestLevelProducts(json.products[i]);
			}
			else if(json.products[i].order!="999") {
				// add to products array
				ACSearch.products[ACSearch.products.length] = { "name": json.products[i].name, "id": json.products[i].id };
			}
		}
	},
	
	'doPreview': function(dropDown) {
		var productId = dropDown.options[dropDown.selectedIndex].value;
		if (productId=='' || productId=='all') {
			$('productpreview').hide();
			$('productpreview').update('');
		} else {
			$('productpreview').update('<img src="' + ACProductBrowser.akamaiUrl + '/kb/image.jsp?productid=' + productId + '">');
			$('productpreview').show();
		}
	},
	'populateDropDown':function(dropDownElem,sourceElem,defaultSelection){
		var itms = sourceElem.select('li a');
	
		dropDownElem.options.length = 0;
		for(var i=dropDownElem.length;i>=0;i--){
			dropDownElem.options[i] = null;
		}
		for(var i=0;i<itms.length;i++){
			var elementId = itms[i].getAttribute('id');
			var displayName = itms[i].innerHTML;
			var l = dropDownElem.options.length;
			
			dropDownElem.options[l] = new Option(displayName, elementId, (elementId==defaultSelection));
			if (elementId==defaultSelection){
				dropDownElem.selectedIndex = l;
			}
		}
	},
	'requestProductInfoResults': function() {
		var searchTerm;
		var params = location.href.toQueryParams();
		
		if (params.q) { 
			searchTerm = params.q;
		} 
		else { 
			searchTerm = ACSearch.searchState.searchTerm;
		}

		var productInfoRequestUrl = 'index?page=searchdata&q=' + searchTerm + '&site=' + ACSearch.getCountry() + '_www&num=5&filter=1&callback=ACSearch.productInfoCallback';
		ACSearch.makeScriptReq(productInfoRequestUrl);

		$('product-loading').show();  // show product spinner
	},
	
	'productInfoCallback': function(response) {

		$('product-loading').hide(); // hide product spinner

		// convert response to xml object
		response = response.replace(/<!--.*?-->/g,''); // strips any comments from XML
		response = response.replace(/^\s*|\s*$/,'');	// strips leading spaces
		response = response.replace(/<!DOCTYPE GSP SYSTEM \"google.dtd\">/g, ''); //ie no likey
		var responseXML = stringToXML(response);
		
		// console.log(responseXML);

		var results;
		var gsp = responseXML.getElementsByTagName('GSP')[0]; // target first group of results
		if (gsp) {
			results = gsp.getElementsByTagName('R');
		}
		if(!gsp || results.length == 0) {
			// show zero result text and search link
			$('product-zero').show();
			//$('product-search').show();
		}
		else {
			// build results list
			var resultsFound = false;
			var list = new Element('ul');
			list.addClassName('results');

			for(var i=0; i<results.length; i++) {

				var t = getNodeValue(results[i], 'T');
				var u = getNodeValue(results[i], 'U');
				var d = getDescription(results[i]);
				var s = d?d:getNodeValue(results[i], 'S');
				
				if (t && u && s) {

					var listItem = new Element('li');

					var item = new Element('span');
					item.addClassName('item');
					var htmlBlob = '<a href="' + u + '">';
					htmlBlob += t + '</a>';
					item.update(htmlBlob);
					listItem.insert(item);

					var excerpt = new Element('span');
					excerpt.addClassName('excerpt');
					htmlBlob = s;
					htmlBlob = htmlBlob.stripTags().stripPunctuationAtStart().truncate(ACSearch.descriptionTruncateLength);
					excerpt.update(htmlBlob);
					listItem.insert(excerpt);

					list.insert(listItem);
					resultsFound = true;
				}
			}
			if (!resultsFound) {
				// show zero result text and search link
				$('product-zero').show();
				//$('product-search').show();
			} else {
				// show results and more link
				var productInfoResultsElement = $('sidebar').down('.product');
				productInfoResultsElement.insert({'top':list});
				$('product-more').show();
			}
		}
	},
	
	'requestAppleStoreResults': function() {
		var searchTerm;
		
		var params = location.href.toQueryParams();
		
		if (params.q) { 
			searchTerm = params.q;
		} else { 
			searchTerm = ACSearch.searchState.searchTerm;
		}
		
		var appleStoreRequestUrl = ACSearch.AOSFeed + '?term=' + searchTerm + '&limit=5&country=' + ACSearch.getCountry() + '&callback=ACSearch.appleStoreCallback';
		ACSearch.makeScriptReq(appleStoreRequestUrl);
		$('store-loading').show();  // show store spinner
	},
	
	'appleStoreCallback': function(response) {

		$('store-loading').hide(); // hide store spinner

		var appleStoreResultsElement = $('sidebar').down('.store');
		
		var list = new Element('ul');
		list.addClassName('results');
		
		if(response.results.length == 0) {
			// show zero result text and search link
			$('store-zero').show();
			//$('store-search').show();
		}
		else {
			// build results list
			for(var i=0; i<response.results.length; i++) {

				var listItem = new Element('li');

				var htmlBlob = '<a href="' + response.results[i].url + '">';
				htmlBlob += '<img src="' + response.results[i].imageUrl + '" alt=""></a>'
				listItem.update(htmlBlob);

				var item = new Element('span');
				item.addClassName('item');
				htmlBlob = '<a href="' + response.results[i].url + '">' + response.results[i].displayName + '</a>';
				item.update(htmlBlob);
				listItem.insert(item);

				var price = new Element('span');
				price.addClassName('price');
				price.update(response.results[i].price);
				listItem.insert(price);

				var defstar = new Element('span');
				defstar.addClassName('defstar');
				var numStars = response.results[i].ratingStars;
				if (numStars && (numStars != '0.0') && (numStars != '0.5')) {
					htmlBlob = '<img class="rating" width="61" height="13" alt="4.5" src="http://a248.e.akamai.net/7/248/2041/1590/store.apple.com/rs1/img/stars_61x13_bluonwht_';
					htmlBlob += numStars * 10 + '.gif"/>'; // image url doesn't have decimal point
					defstar.update(htmlBlob);
					listItem.insert(defstar);
				}

				list.insert(listItem);
			}

			// show results and more link
			appleStoreResultsElement.insert({'top':list});
			$('store-more').show();
		}

	},
	enableFilters:function(){
		var a = ACSearch.filterDropDowns;
		for (var i=0; i<a.length; i++){
			$(a[i]).enable();
		}
	},
	disableFilters:function(){
		var a = ACSearch.filterDropDowns;
		for (var i=0; i<a.length; i++){
			$(a[i]).disable();
		}
	},
	getCountry:function(){
		var localeValues = ACProductBrowser.locale.split('_');
		country = localeValues[1].toLowerCase();
		if (country=='gb'){country = 'uk'}
		return country;
	},
	makeScriptReq:function(url){
		//JSONscriptRequest is defined in KmLoader.js
		var scriptReq = new JSONscriptRequest(url);
		if(scriptReq) {
			
			try{
				scriptReq.buildScriptTag();
				scriptReq.addScriptTag();
			}
			catch(ex) {
				// IE 5 for Mac will throw an exception here.
			}
		}		
	}

};

// convert string into XML
function stringToXML(txt) {
	try {
		//Internet Explorer
		xmlDoc=new ActiveXObject("Microsoft.XMLDOM");
		xmlDoc.async="false";
		xmlDoc.loadXML(txt);
		return xmlDoc; 
	}
	catch(e)
	{
		// other browsers
		parser=new DOMParser();
		xmlDoc=parser.parseFromString(txt,"text/xml");
		return xmlDoc;
	}
}

// xml utility function to get value of a node under a given root
function getNodeValue(root, name) {
	var elementsFound = root.getElementsByTagName(name);
	if (elementsFound.length == 0) { return null; }
	else {
		var element = elementsFound[0].firstChild;
		if (element) { return element.nodeValue; }
		else { return null; }
	}
}
// get description text from <MT N="Description" V="value">
function getDescription(root) {
	var elementsFound = root.getElementsByTagName('MT');
	if (elementsFound.length == 0) { return null; }
	else {
		for (var i=0; i<elementsFound.length; i++) {
			if (elementsFound[i].getAttribute('N') == 'Description') {
				return elementsFound[i].getAttribute('V');
			}
		}
	}
	return null;
}


//  Sets all event handlers for the page load on search results

var domTriggers = {
	'clear-searches' : function(element) {
		element.onclick = function(){
			ACSearch.clearRecentSearches();
			return false;
		};
	},
	'searchform' : function(element) {
		element.onsubmit = function() { 
			ACSearch.searchAJAX('facet_all', undefined, 'y', undefined, 'form');
			return false; 
		};
	},
	'product' : function(element){
		element.onchange = function(){
			var strID = this.options[this.selectedIndex].value;
			ACSearch.doPreview(this);
			if (!ACSearch.isAdvancedSearch){
				ACSearch.disableFilters();
				strID = (strID=='all')?'MAIN_PRODUCTS':strID;
				ACSearch.searchState.facet = 'all'; //reset doctype filter
				ACSearch.searchAJAX('product_' + strID, undefined, 'y', undefined, 'product');
			}
		}
	},
	'documentTypeFilter' : function(element){
		element.onchange = function(){
			var selectedId = this.options[this.selectedIndex].value;
			ACSearch.disableFilters();
			ACSearch.searchAJAX(selectedId, '0', undefined, undefined, 'facet');
		}
	},
	'archiveTypeFilter' : function(element){
		element.onchange = function(){
			var val = this.options[this.selectedIndex].value;
			ACSearch.disableFilters();
			ACSearch.searchAJAX(val, '0', 'y', undefined, 'facet');
		}
	}
};

function domHandlers(obj){
  for(property in obj){
	if ($(property)){ obj[property]($(property)); }
  }
}

Event.observe(window, 'load', function() {
	domHandlers(domTriggers);
});
