/*
REQUIRE:
- /_js/domain-search/domain-search-ajax.js
- /_js/domain-search/related-domain-search-ajax.js
- /_js/dom/event.js
- /_js/signup/signup-form.js
- /_js/dom/checkbox.js
- /_js/dom/select.js

DESC:
- post domain name (no ext) to ajax for search, with extension selected in <select> as visual hint to user and to auto-select result domains
- get search result and:
   - display available ext in extension checkbox list (pre-fill with hourglass)
   - display available related domain name in checkbox list (ditto)
- move box (containing "name to search" & "search" button box below new search result
- this box in turn allow more search in the same fashion

- FORM VAR TO POST:
- searchedNames (hidden field, string of comma-list)
- selectedExtList_mynewdomain (multi-checkbox)
- selectedRelatedDomainNameList_mynewdomain (multi-checkbox)
- availableExtList_mynewdomain (hidden field, string of comma-list)
- availableRelatedDomainNameList_mynewdomain (hidden field, string of comma-list)


- EXAMPLE:
- Enter "mynewdomain" for search
- For one entered domain name (no ext):
  - search and show list of available extension checkboxes
    - name="selectedExtList_mynewdomain" value="com"
    - name="selectedExtList_mynewdomain" value="org"
    - name="selectedExtList_mynewdomain" value="co.uk"

  - search and show list of related domain name checkboxes
    - name="selectedRelatedDomainNameList_mynewdomain" value="mydomain2000.com"
    - name="selectedRelatedDomainNameList_mynewdomain" value="mydomain2000.net"
    - name="selectedRelatedDomainNameList_mynewdomain" value="idomain.tv"
	- ...

  - create hidden fields: 
    1. name="searchedNames" value="mydomain,writemesometext"
    2. name="availableExtList_mynewdomain" value="com,org,co.uk"
    3. name="availableRelatedDomainNameList_mynewdomain"
		value="mydomain2000.com,mydomain2000.net,idomain.tv,..."

- HTML STRUCTURE IT WILL CREATE
	<div id="one-name-search-section-mydomain" class="one-name-search-section">

		<!--- header --->
		<div class="header"></div>

		<!--- list of available extension checkboxes, see this.writeBlankExtList() --->
		<ul id="list-%strDomainNameNoExt_VarSafe" class="ext-result"></ul>

		<!--- list of available extension checkboxes, see this.writeBlankExtList() --->
		<ul id="list-related-%strDomainNameNoExt_VarSafe" class="related-domain-names-result"></ul>

	</div>
*/


// in production, define it by drawing value from Extension.cfc
var EXTENSION_LIST = 'com,net,org,biz,info,co.uk,org.uk,me.uk,us,ca,eu,mobi,tv';
var NUMBER_OF_RELATED_DOMAINS = 20; // sync this number with var NUMBER_OF_RELATED_DOMAINS in inc_write_new-domain-area.cfm
var NUMBER_OF_RELATED_DOMAINS_COLUMNS = 3; // sync this number with var NUMBER_OF_COLUMNS_OF_RELATED_DOMAINS in inc_write_new-domain-area.cfm
var WIZARDFORM = document.wizardform;

function DomainSearchHandler(strObjName) {

	var me = this;
	var strObjName = strObjName;

	this.arrSearchedNames = [];
	
	this.strSearchConId = '';
	this.strSearchInputId = '';
	this.strSearchButtonId = '';
	this.strResultDockId = '';
	this.strSearchToolTopId = '';
	this.strExtSelectId = '';
	this.strSearchedNamesInputId = '';

	this.domSearchCon;
	this.domSearchInput;
	this.domSearchButton;
	this.domResultDock;
	this.domSearchToolTop;
	this.domSearchToolBottom;
	this.domExtSelect;
	this.domSearchedNamesInput;
	this.objDomainPromo;

	this.boolSearchToolMoved = false; // flag to indicate if the search tool has been move
	
	this.init = function(strSearchConId, strSearchInputId, strSearchButtonId, strResultDockId, strSearchToolTopId, strSearchToolBottomId, strExtSelectId, strSearchedNamesInputId, objDomainPromo, objSignUpForm, blnSearchRelatedDomains) {
		
		// set object properties
		this.strSearchConId = strSearchConId;
		this.strSearchInputId = strSearchInputId;
		this.strSearchButtonId = strSearchButtonId;
		this.strResultDockId = strResultDockId;
		this.strSearchToolTopId = strSearchToolTopId;
		this.strSearchToolBottomId = strSearchToolBottomId;
		this.strExtSelectId = strExtSelectId;
		this.strSearchedNamesInputId = strSearchedNamesInputId;

		this.domSearchCon = ge(strSearchConId);
		this.domSearchInput = ge(strSearchInputId);
		this.domSearchButton = ge(strSearchButtonId);
		this.domResultDock = ge(strResultDockId);
		this.domSearchToolTop = ge(strSearchToolTopId);
		this.domSearchToolBottom = ge(strSearchToolBottomId);
		this.domExtSelect = ge(strExtSelectId);
		this.domSearchedNamesInput = ge(strSearchedNamesInputId);
		if (this.domSearchedNamesInput.value != '') {
			this.arrSearchedNames = this.domSearchedNamesInput.value.split(',');			
		}
		this.objDomainPromo = objDomainPromo;
		this.objSignUpForm = objSignUpForm;
		this.blnSearchRelatedDomains = blnSearchRelatedDomains;
		if (this.blnSearchRelatedDomains != false) {
			this.blnSearchRelatedDomains = true;
		}

		// patch event handlers
		this.mapEventHandlers();

/* [OBSOLETE]
		// write hidden form field to dock for storing searchedNames
		var strHiddenInputHtml = '';
		strHiddenInputHtml += '<input type="hidden" id="searched-names" name="searchedNames" value="">';
		// convert html to dom elem
		this.domSearchedNamesHiddenField = h2e(strHiddenInputHtml);	
		// put into dock, append as last elem
		me.domResultDock.appendChild(this.domSearchedNamesHiddenField);
*/

}
	
	// map event handlers
	this.mapEventHandlers = function() {
		// map search button click to this.submitSearch();
		addListener(me.domSearchButton, 'click', eval(strObjName+'.submitSearch'));
		// map search box keypress to this.submitSearch();
		addListener(me.domSearchInput, 'keypress', eval(strObjName+'.handleSearchInputKeyPress'));
	}

	// submit domain search to ajax
	this.submitSearch = function() {

	/*
	GET domain name entered
	*/
		var strDomainNameNoExt = me.domSearchInput.value;
		var strDomainNameNoExt_VarSafe = me.formatVarSafeName(strDomainNameNoExt);

	/*
	VALIDATE name
	*/
		var strNameValidate = me.validateName(strDomainNameNoExt);
		if (strNameValidate != '') {
			alert(strNameValidate);
			return;
		}

	/*
	WRITE blank result list into the dock
	*/
		// create section
		var domSection = me.writeOneNameSearchSection(strDomainNameNoExt);
		// write and put blank ext list into section
		me.writeBlankExtList(strDomainNameNoExt, domSection);
		if (me.blnSearchRelatedDomains) {
			// write and put blank related domain names list into section
			me.writeBlankRelatedDomainNamesList(strDomainNameNoExt, domSection);
		} else {
			// add spacing to domSection
			var domSpace = document.createElement('div');
			domSpace.className = 'related-domain-names-result-space';
			domSection.appendChild(domSpace);
		}
		// append section dom into the dock
		me.domResultDock.appendChild(domSection);

	/*
	POST EXT SEARCH to ajax, which will wait for the result
	IMPORTANT: make this object in the public scope so the ajax callback function can gain access.  Also make this object name unique to the search string, so multiple instance can co-exist.
	*/
		var strDomainSearchObjName = 'objDS_' + strObjName + '_' + strDomainNameNoExt_VarSafe;
		eval(strDomainSearchObjName + ' = new DomainSearchAjax(\''+ strDomainSearchObjName +'\');');
		// make alias to this object
		var objTempDS = eval(strDomainSearchObjName);
		objTempDS.onDeliverResult = function() { if (/*use 'this'*/this.boolAnyExtAvailable) { me.objSignUpForm.showFormButtons() } }; // NOTE!!: 'this' refers to objTempDS object
		objTempDS.arrPreCheckedExt = [getSelectedValue(me.strExtSelectId)];
		objTempDS.init(strDomainNameNoExt, 'list-'+strDomainNameNoExt_VarSafe, 'available-ext-list-'+strDomainNameNoExt_VarSafe);
		objTempDS.submitSearchAllGroup();


	/*
	POST RELATED DOMAIN NAMES SEARCH to ajax, which will wait for the result
	IMPORTANT: make this object in the public scope so the ajax callback function can gain access.  Also make this object name unique to the search string, so multiple instance can co-exist.
	*/
		if (me.blnSearchRelatedDomains) {
			var strRelatedDomainSearchObjName = 'objRDS_' + strObjName + '_' + strDomainNameNoExt_VarSafe;
			eval(strRelatedDomainSearchObjName + ' = new RelatedDomainSearch(\''+ strRelatedDomainSearchObjName +'\');');
			// make alias to this object
			var objTempRDS = eval(strRelatedDomainSearchObjName);
			// set event handler
//			objTempRDS.onDeliverResult = me.objSignUpForm.showFormButtons;
			objTempRDS.NUMBER_OF_DOMAINS = NUMBER_OF_RELATED_DOMAINS;
			objTempRDS.init(strDomainNameNoExt, 'list-related-'+strDomainNameNoExt_VarSafe, 'available-related-domain-names-list-'+strDomainNameNoExt_VarSafe, 'related-domain-names-error-'+strDomainNameNoExt_VarSafe);		
			objTempRDS.submitSearch();
			// prep next search, e.g., move search box to bottom, change caption, etc...
		}


	/*
	ADD HIDDEN <input> for available names
	NOTE: value to be filled AFTER ajax searcher has done searching
	*/
		var strHiddenInputHtml = '';
		var strDomainNameNoExt_VarSafe = me.formatVarSafeName(strDomainNameNoExt);
		strHiddenInputHtml += '<input type="hidden" name="availableExtList_' + strDomainNameNoExt_VarSafe + '" value="">';
		// convert html to dom elem
		var domHIH = h2e(strHiddenInputHtml);	
		// put into dock, append as last elem
		me.domResultDock.appendChild(domHIH);


	/*
	RECORD name as searched
	*/
		// update array
		me.arrSearchedNames.push(strDomainNameNoExt);
		// update hidden field
		me.domSearchedNamesInput.value = me.arrSearchedNames.join(',');
		

	/*
	PREP FOR NEXT SEARCH
	*/
		me.prepareNextSearch();

	}



	// handle keypress event of search input box
	this.handleSearchInputKeyPress = function(e) {
		var e = (window.event)?window.event:e;
		if (e && e.keyCode == 13) {
			me.submitSearch();
		}
	}
	
	
	// write empty result div, with header title, into the dock
	// RETURN div as dom elem
	this.writeOneNameSearchSection = function(strDomainNameNoExt) {
		var strDomainNameNoExt_VarSafe = me.formatVarSafeName(strDomainNameNoExt);
		var strHtml = '<div id="one-name-search-section-' + strDomainNameNoExt_VarSafe + '" class="one-name-search-section"><div class="header">Search Result for "' + strDomainNameNoExt + '"</div></div>';
		// convert html to dom elem
		var domSection = h2e(strHtml);
		return domSection;
	}
	

	// write extension list without search result, into the dock
	// NO pre-fill of hourglass, cos it'll be done by the ajax searcher
	this.writeBlankExtList = function(strDomainNameNoExt, domContainer) {
		var strHtml = '';
		var arrExt = EXTENSION_LIST.split(',');
		var strDomainNameNoExt_VarSafe = me.formatVarSafeName(strDomainNameNoExt);
		// write ext list as <ul>...</ul>
		strHtml += '<ul id="list-' + strDomainNameNoExt_VarSafe + '" class="ext-result">';
		for (numIndex in arrExt) {
			var strExt = arrExt[numIndex];
			var strExtVarSafe = me.formatVarSafeName(strExt);
			var labelToWrite = '.' + strExt;
			if (me.objDomainPromo && me.objDomainPromo.store[strExt]) {
				var labelToWrite = me.objDomainPromo.getPromoTagHtml(strExt);
			}
			strHtml += '<li class="' + strExtVarSafe + ' ext"><div class="label"><label>' + labelToWrite + '</label><div class="promo"></div></div><div class="input"><input type="checkbox" class="domain-select" name="selectedExtList_' + strDomainNameNoExt_VarSafe + '" value="' + strExt + '"></div><div class="message"></div></li>';
		}

		/*
		  - write hidden fields: 
			name="availableExtList_mynewdomain" value="com,org,co.uk"
		*/
		strHtml += '<input type="hidden" id="available-ext-list-' + strDomainNameNoExt_VarSafe + '" name="availableExtList_' + strDomainNameNoExt_VarSafe + '" value="" />';
		
		strHtml += '</ul>';

		// convert html to dom elem
		var domUL = h2e(strHtml);
		
		// put into given container, append as last elem
		domContainer.appendChild(domUL);

	}

	// write related domain name list without search result, into the dock
	// NO pre-fill of hourglass, cos it'll be done by the ajax searcher
	this.writeBlankRelatedDomainNamesList = function(strDomainNameNoExt, domContainer) {
		var strHtml = '';
		var strDomainNameNoExt_VarSafe = me.formatVarSafeName(strDomainNameNoExt);
		// write ext list as <ul>...</ul>
		strHtml += '<ul id="list-related-' + strDomainNameNoExt_VarSafe + '" class="related-domain-names-result"><div class="title">Also available:</div>';
		var columnSize = Math.ceil(NUMBER_OF_RELATED_DOMAINS / NUMBER_OF_RELATED_DOMAINS_COLUMNS);
		for (var ii=0;ii<NUMBER_OF_RELATED_DOMAINS;ii++) {
			// write column container
			var writeColConStartTag = false;
			var writeColConEndTag = false;
			if (ii%columnSize == 0) {
				writeColConStartTag = true;
			}
			if (ii%columnSize == columnSize-1 || ii == NUMBER_OF_RELATED_DOMAINS-1) {
				writeColConEndTag = true;
			}
			if (writeColConStartTag) {
				strHtml += '<div class="column">';
			}
			// write <li><input type="checkbox">...</li>
			// NOTE: input 'value' will be filled by ajax-searcher
			strHtml += '<li class="domainname-con domain-' + ii + '"><div class="input"><input type="checkbox" class="checkbox domain-select" name="selectedRelatedDomainNameList_' + strDomainNameNoExt_VarSafe + '" value=""></div><div class="domainname"></div></li>';
			if (writeColConEndTag) {
				strHtml += '</div>';
			}

		}
		strHtml += '<br clear="all" />';

		/*
 		  - write hidden field: 
			name="availableRelatedDomainNameList_mynewdomain" value="mydomain2000.com,mydomain2000.net,idomain.tv,..."
		*/
		strHtml += '<input type="hidden" id="available-related-domain-names-list-' + strDomainNameNoExt_VarSafe + '" name="availableRelatedDomainNameList_' + strDomainNameNoExt_VarSafe + '" value="" />';
		
		/*
 		  - write hidden field: 
			name="relatedDomainNameError_mynewdomain" value="error message if any"
		*/
		strHtml += '<input type="hidden" id="related-domain-names-error-' + strDomainNameNoExt_VarSafe + '" name="relatedDomainNameError_' + strDomainNameNoExt_VarSafe + '" value="" />';

		
		strHtml += '<li class="error-message"></li>';
		strHtml += '</ul>';

		// convert html to dom elem
		var domUL = h2e(strHtml);
		
		// put into given container, append as last elem
		domContainer.appendChild(domUL);

	}

	// move search box down, and change wording to search for "more" etc...
	this.prepareNextSearch = function() {
		// move search tool from top position to bottom position, if not done yet.
		if (!me.boolSearchToolMoved) {
			// move
			me.domSearchToolBottom.appendChild(me.domSearchCon);
			// mark as moved
			this.boolSearchToolMoved = true;
			// get title div
			var domTitle = gtc(me.domSearchCon, 'div', 'title')[0];
			// change wording
			if (domTitle) {
				domTitle.innerHTML = 'Search for More Domain Names:';
			}
			// reveal next-step-note message
			var domNextStepNote = gtc(me.domSearchCon, 'div', 'next-step-note')[0];
			domNextStepNote.style.display = 'block';
		}
			// clear input box
			me.domSearchInput.value = '';	
			// focus on input box
			me.domSearchInput.focus();	
	}


	/*
	Validate Name Entered.  Return error message.  '' means no error
	*/
	this.validateName = function(strName) {
		var strErrorMessage = '';

// check if name already searched. check this.arrSearchedNames
		for (ii in me.arrSearchedNames) {
			if (me.arrSearchedNames[ii].toLowerCase() == strName.toLowerCase()) {
				strErrorMessage = 'Name \'' + strName + '\' is already searched.';
				return strErrorMessage;
			}
		}
		
		/*
		check name syntax
		*/
		// name required
		if (strName.length == '') {
			strErrorMessage = 'Please enter a Name to search.';
			return strErrorMessage;
		}

		// min length
		if (strName.length != '' && strName.length < 2) {
			strErrorMessage = 'Name too Short.  At least 2 characters.';
			return strErrorMessage;
		}

		// check name syntax
		// max length
		if (strName.length > 62) {
			strErrorMessage = 'Name too Long.  Max 62 characters.';
			return strErrorMessage;
		}
		
		// only allow alphanumeric and dash
		if (!strName.match(/^[a-z0-9][a-z0-9-]*[a-z0-9]$/i)) {
			strErrorMessage = 'Domain Name not valid, only allow A-Z, 0-9 and Dash (-), and not starting or ending with a dash.';
			return strErrorMessage;
		}

		// return error message
		return strErrorMessage;
	}

// function to format var-safe-name: trim leading dot from the given string and convert inner dot to underscore, if any.  for use of preping ext name
	this.formatVarSafeName = function(str) {
		var strResult = str;
		strResult = strResult.replace(/\-/g, '__');
		strResult = strResult.replace(/\./g, '_');
		return strResult;
	}

// check if any domain name (checkbox) selectable
	this.hasSelectableDomainNames = function() {
		if (me.domResultDock) {
			var arrInput = gtc(me.domResultDock, 'input', 'domain-select');
		} else {
			return false;
		}
		if (arrInput.length > 0) {
			return true;
		} else {
			return false;
		}
	}

// getCheckedValues
	this.getSelectedDomainNames = function() {
		
		var arrDomainNames = [];
		for (var ii=0; ii<me.arrSearchedNames.length; ii++) {
			var oneName = me.arrSearchedNames[ii];
			var oneName_VarSafe = me.formatVarSafeName(oneName);
			// get selected extensions
			var oneFieldName_SelectedExtList = 'selectedExtList_' + oneName_VarSafe;
			
			var arrSelectedExt = getCheckedValues(eval('WIZARDFORM.'+oneFieldName_SelectedExtList));
			// add to result: domain name with selected extension
			for (var jj=0;jj<arrSelectedExt.length;jj++) {
				arrDomainNames.push(oneName + '.' + arrSelectedExt[jj]);
			}


			// get selected related domain name
			var oneFieldName_SelectedRelatedDomainNameList = 'selectedRelatedDomainNameList_' + oneName_VarSafe;
			
			// if the related checkboxes are present
			if (eval('WIZARDFORM.'+oneFieldName_SelectedRelatedDomainNameList)) {
				var arrSelectedRelatedDomainName = getCheckedValues(eval('WIZARDFORM.'+oneFieldName_SelectedRelatedDomainNameList));
				// add to result: domain name with selected extension
				for (var kk=0;kk<arrSelectedRelatedDomainName.length;kk++) {
					arrDomainNames.push(arrSelectedRelatedDomainName[kk]);
				}
			}


		}
		return arrDomainNames;
	}

}