function CatalogEngine() {
	this.debug = false;
	this.msie = (navigator.appName == 'Microsoft Internet Explorer') ? true : false;
	this.msie6 = (navigator.appVersion.search(new RegExp('MSIE 6','i'))>-1) ? true : false;
	
	/*
	 this.regularExpressions = [
		[new RegExp('([aàáâäã])','ig'),'[aàáâäã]'],
		[new RegExp('([cçč])','ig'),'[cçč]'],
		[new RegExp('([eéèêëě])','ig'),'[eéèêëě]'],
		[new RegExp('([iîïìí])','ig'),'[iîïìí]'],
		[new RegExp('([nñ])','ig'),'[nñ]'],
		[new RegExp('([oôö])','ig'),'[oôö]'],
		[new RegExp('([rř])','ig'),'[rř]'],
		[new RegExp('([sšß])','ig'),'[sšß]'],// Cas du ss = ß non géré
		[new RegExp('([uùûüů])','ig'),'[uùûüů]'],
		[new RegExp('([yý])','ig'),'[yý]'],
		[new RegExp('([zž])','ig'),'[zž]'],
		[new RegExp('([ ])','ig'),'[\\W_\\s]{1,3}']
	];
	 */
	this.regularExpressions = [
		[new RegExp('([a])','ig'),'[aàáâäã]'],
		[new RegExp('([c])','ig'),'[cçč]'],
		[new RegExp('([e])','ig'),'[eéèêëě]'],
		[new RegExp('([i])','ig'),'[iîïìí]'],
		[new RegExp('([n])','ig'),'[nñ]'],
		[new RegExp('([o])','ig'),'[oôö]'],
		[new RegExp('([r])','ig'),'[rř]'],
		[new RegExp('([s])','ig'),'[sš]'],
		[new RegExp('(\\[sš\\]\\[sš\\])','ig'),'([s]{2}|[ß])'], // Cas : ss = ß
		[new RegExp('([u])','ig'),'[uùûüů]'],
		[new RegExp('([y])','ig'),'[yý]'],
		[new RegExp('([z])','ig'),'[zž]'],
		[new RegExp('([ ])','ig'),'[\\W_\\s]{1,3}']
	];
	// "os" => /([oôö][sš])/gi
	// "oss" => /([oôö]([s]{2}|[ß]))/gi
	this.resort_id = null;
	this.previous_resort_id = null;
}

CatalogEngine.prototype.constructor = CatalogEngine;

CatalogEngine.prototype = {
	HTML: {
		div: {
			resort:null,
			flags:null
		},
		img: {
			alert:null
		},
		span: {
			flags:null,
			date:null,
			alert:null
		},
		input: {
			hidden:null,
			resort:null
		},
		select: {
			resort:null,
			year:null,
			month:null,
			day:null
		}
	},
	interval: {
		suggest: {
			hide: false,
			show: false,
			block: false
		}
	},
	
	associateHTMLForm: function() {
		var CatalogEngine = this;
		this.HTML.form = ('string' == typeof(arguments[0])) ? document.getElementById(arguments[0]) : (('object' == typeof(arguments[0])) ? arguments[0] : null);
		this.HTML.form.onsubmit = function() {
			if(
				null != CatalogEngine.HTML.div.resort &&
				undefined != CatalogEngine.HTML.div.resort &&
				CatalogEngine.HTML.div.resort.displayed
			) {
				return false;
			}
			else {
				return CatalogEngine.controlForm();
			}
		};
		return true;
	},
	
	associateHTMLSelects: function() {
		var CatalogEngine = this;
		this.HTML.select.resort = ('string'==typeof(arguments[0])) ? document.getElementById(arguments[0]) : (('object'==typeof(arguments[0])) ? arguments[0] : null);
		this.HTML.select.year = ('string'==typeof(arguments[1])) ? document.getElementById(arguments[1]) : (('object'==typeof(arguments[1])) ? arguments[1] : null);
		this.HTML.select.month = ('string'==typeof(arguments[2])) ? document.getElementById(arguments[2]) : (('object'==typeof(arguments[2])) ? arguments[2] : null);
		this.HTML.select.day = ('string'==typeof(arguments[3])) ? document.getElementById(arguments[3]) : (('object'==typeof(arguments[3])) ? arguments[3] : null);
		if(null!=this.HTML.select.year&&null!=this.HTML.select.month&&null!=this.HTML.select.day) {
			addEvent(this.HTML.select.year,'change',function() { CatalogEngine.setSelectedDate(); });
			addEvent(this.HTML.select.month,'change',function() { CatalogEngine.setSelectedDate(); });
			addEvent(this.HTML.select.day,'change',function() { CatalogEngine.setSelectedDate(); });
		}
		this.HTML.span.date = document.createElement('span');
		this.HTML.span.date.className = 'alert';
		document.body.appendChild(this.HTML.span.date);
		this.HTML.span.alert = document.createElement('span');
		this.HTML.span.alert.className = 'alert_icon';
		this.HTML.select.year.parentNode.appendChild(this.HTML.span.alert);
		
		toolTip = new ToolTip();
		toolTip.init({
			source:CatalogEngine.HTML.select.year.parentNode,
			target:CatalogEngine.HTML.span.date,
			position:'absolute',
			align:'bottom center',
			time:0
		});
		toolTip.addTrigger(this.HTML.span.alert);
		toolTip.setDimension(CatalogEngine.HTML.select.year.parentNode.offsetWidth-20);
		
		return true;
	},
	
	clickedOut: function(e) {
		if(!e) { e = window.event; elt = e.srcElement; }
		else { elt = e.target; }
		while(undefined!=elt) {
			if(
				elt==this.HTML.input.resort || 
				elt==this.HTML.div.resort || 
				elt==this.HTML.div.flags
			) {
				return false;
			}
			if(elt.tagName.toLowerCase()=='html') {
				this.hideHTMLDivSuggest();
				return true;
			}
			elt = elt.parentNode;
		}
		return false;
	},
	
	controlDate: function() {
		//window.alert('CatalogEngine.controlDate('+arguments[0]+','+this.date.start+','+this.date.finish+')');
		if(this.date.start||this.date.finish) {
			rtn = this.date.compare(arguments[0],this.date.start,this.date.finish);
			switch(rtn) {
				case -1:
					rtn = {'title':TLT.dateNotValdid[this.language],'class':'disabled','event':false};
					break;
				case +1:
					rtn = {'title':TLT.dateNotValdid[this.language],'class':'disabled','event':false};
					break;
				case 0:
					rtn = true;
					break;
			}
		}
		else {
			rtn = true;
		}
		return rtn;
	},
	
	controlForm: function() {
		str = null;
		rtn = this.controlDate(this.date.selected);
		if(!this.resort_id) {
			window.alert(TLT.alertResort[this.language]);
			rtn = false;
		}
		else if('object'==typeof(rtn)) {
			window.alert(rtn['title']);
			rtn = false;
		}
		else if(this.previous_resort_id != null && this.previous_resort_id != this.resort_id) {
			rtn = window.confirm(TLT.confirmResort[this.language]);
		}
		
		if(!rtn) {
			return false
		}
		else {
			this.HTML.form.submit();
		}
		return true;
	},
	
	controlKeyCode: function(e,selectResort) {
		if(!e) { e = window.event; element = e.srcElement; }
		else { element = e.target; }
		rtn = false;
		if(selectResort) {
			index = null;
			switch(e.keyCode) {
				case  13: // Enter key
					bool = true;
					index = this.HTML.div.resort.selectedIndex;
					if(this.HTML.div.resort.displayed) {
						stopEventPropagation(e);
						this.hideHTMLDivSuggest(true);
					}
					break;
				/*
				case  32: // Start key
					index = 1;
					break;
				*/
				case  33: // Previous page
					index = this.HTML.div.resort.selectedIndex-10;
					break;
				case  37: // Left arrow
					if(!this.HTML.input.resort.used) {
						index = this.HTML.div.resort.selectedIndex-1;
					}
					break;
				case  38: // Up arrow
					index = this.HTML.div.resort.selectedIndex-1;
					break;
				case  34: // Next page
					index = this.HTML.div.resort.selectedIndex+10;
					break;
				/*
				case  35: // End key
					index = this.HTML.div.resort.childNodes.length-1;
					break;
				*/
				case  39: // Right arrow
					if(!this.HTML.input.resort.used) {
						index = this.HTML.div.resort.selectedIndex+1;
					}
					break;
				case  40: // Bottom arrow
					index = this.HTML.div.resort.selectedIndex+1;
					break;
			}
			if('number' == typeof(index)) {
				this.selectResortByIndex(index);
			}
		}
		else {
			switch(e.keyCode) {
				case   9: // Tabulation
				case  13: // Enter key
				case  16: // Capital key
				case  17: // Control key	
				case  18: // Alt key
				case  20: // Capital lock
				case  32: // Start key
				case  33: // Previous page
				case  34: // Next page
				case  35: // End key
				case  37: // Left arrow
				case  38: // Up arrow
				case  39: // Right arrow
				case  40: // Bottom arrow
				case  91: // "Windows" key
				case  93: // "Right click" key
				case 144: // Numeric lock
					rtn = false;
					break;
				
				case   8: // Backspace key
				case  46: // Delete key
				default:
					rtn = true;
					break;
			}
		}
		return rtn;
	},
	
	
	drawHTMLDivSuggest: function() {
		var CatalogEngine = this;
		addClassName(this.HTML.input.resort,'active');
		while(undefined != this.HTML.div.resort.firstChild) {
			this.HTML.div.resort.removeChild(this.HTML.div.resort.firstChild);
		}
		txt = arguments[0] || '';
		resorts = this.searchResort('name',txt);
		resort_found = false;
		
		this.HTML.div.resort.scrollTop = 0;
		this.HTML.div.resort.selectedIndex = 0;

		
		for(i=0;i<resorts.length;i++) {
			elt = document.createElement('div');
			elt.index = i;
			elt.value = resorts[i].id;
			elt.innerHTML = resorts[i].formattedName;
			elt.title  = resorts[i].country;
			elt.title += (resorts[i].department) ? ' - '+resorts[i].department : '';
			elt.className = resorts[i].country_id;
			this.HTML.div.resort.appendChild(elt);
			if(i==0) {
				elt.title = '';
				elt.className = 'result_number';
			}
			else if(resorts[i].id == this.resort_id) {
				resort_found = true;
				addClassName(elt,'selected');
				this.HTML.div.resort.selectedIndex = i;
				this.HTML.div.resort.scrollTop = elt.previousSibling.offsetTop;
			}
			if(i>0) {
				addEvent(elt,'mouseover',function(e) {
					elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
					addClassName(elt,'hover');
				});
				addEvent(elt,'mouseout',function(e) {
					elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
					removeClassName(elt,'hover');
				});
				addEvent(elt,'mousedown',function(e) {
					elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
					CatalogEngine.hideHTMLDivSuggest(true);
					CatalogEngine.selectResortByIndex(elt.index);
				});
			}
		}
		
		delete(i);
		
		this.HTML.div.resort.style.height = '';
		
		switch(resorts.length) {
			case 1:
				this.HTML.div.resort.scrollTop = 0;
				this.HTML.div.resort.selectedIndex = null;
				break;
			case 2:
				if(this.resort_id != resorts[1].id) {
					this.setSelectedResort(resorts[1].id);
					this.HTML.div.resort.selectedIndex = 1;
					addClassName(this.HTML.div.resort.childNodes[1],'selected');
					this.HTML.input.resort.disabled = 'disabled';
					window.setTimeout(function() {
						CatalogEngine.HTML.input.resort.disabled = '';
						CatalogEngine.HTML.input.resort.select();
					},1000);
				}
				break;
		}
		removeClassName(this.HTML.input.resort,'active');
	},
	
	searchResort: function(type,txt) {
		rtn = new Array();
		if(type == 'id' && txt != '') {
			for(i=0;i<this.resorts.length;i++) {
				if(this.resorts[i].id == txt) {
					rtn.push(this.resorts[i]);
					i=this.resorts.length;
				}
			}
		}
		else if(txt == '') {
			for(i=0;i<this.resorts.length;i++) {
				if(!this.country_id||this.resorts[i].country_id==this.country_id) {
					rst = this.resorts[i];
					rst.formattedName = rst.name;
					rtn.push(rst);
				}
			}
		}
		else {
			tmp = new Array();
			reg = this.setRegExp(txt.setSpaces());
			for(i=0;i<this.resorts.length;i++) {
				if(!this.country_id||this.resorts[i].country_id==this.country_id) {
					pos = this.resorts[i].name.search(reg)
					if(pos!=-1) {
						if(undefined == tmp[parseInt(pos,10)]) { tmp[pos] = new Array(); }
						rst = this.resorts[i];
						rst.formattedName = rst.name.replace(reg,'<b>$1</b>');
						tmp[parseInt(pos,10)].push(rst);
					}
				}
			}
			index = new Array();
			for(k in tmp) { index.push(k); }
			index.sort(sortIntegerAsc);
			rtn = new Array();
			for(i=0;i<index.length;i++) {
				for(j=0;j<tmp[index[i]].length;j++) {
					rtn.push(tmp[index[i]][j]);
				}
			}
		}
		fName  = '<span>'+rtn.length+' '+((rtn.length<2) ? TLT.resort[this.language] : TLT.resorts[this.language]);
		fName += ((this.country_id) ? ' - '+this.countries[this.country_id] : '');
		fName += '</span>';
		rtn.unshift({
			id:null,
			name:null,
			country:null,
			department:null,
			formattedName:fName
		});
		return rtn;
	},
	
	setCalendar: function(arg) {
		if(this.dbg) { window.alert('CatalogEngine.setCalendar('+arg+')'); }
		var CatalogEngine = this;
		this.Calendar = new Calendar({
			anchor: 'calendar_opener',
			opener: 'calendar_opener'
		});
		this.setValidDatesInterval('now');
		this.Calendar.setLanguage(this.language);
		this.Calendar.setHTML();
		this.Calendar.setSelectedDate(this.date.selected);
		this.Calendar.functions.returnSelectedDate = function(y,m,d) {
			CatalogEngine.setSelectedDate(y,m,d);
		};
		this.Calendar.functions.controlDate = function(y,m,d,h,i,s) {
			return CatalogEngine.controlDate(new Date(y,m-1,d,h,i,s));
		};
	},
	
	setCountry: function(id) {
		rtn = false;
		if(!id) {
			this.country_id = false;
			rtn = true;
		}
		else {
			for(cny in this.countries) {
				if(cny == id) {
					this.country_id = cny;
					rtn = true;
					break;
				}
			}
		}
		if(rtn) {
			for(cny in this.HTML.span.flags) {
				removeClassName(this.HTML.span.flags[cny],'selected');
			}
			id = (id) ? id : 'none';
			addClassName(this.HTML.span.flags[id],'selected');
		}
		return rtn;
	},
	
	setCountriesList: function() {
		this.countries = new Array();
		for(i=0;i<arguments.length;i++) {
			this.countries[arguments[i][0]] = arguments[i][1];
		}
	},
	
	setHTMLDivSuggestDimensionAndPosition: function() {
		
		
		if(this.msie6) {
			this.HTML.div.resort.style.top = (getTop(this.HTML.input.resort))+'px';
			this.HTML.div.resort.style.left = (getLeft(this.HTML.input.resort)+this.HTML.input.resort.offsetWidth+10)+'px';
		}
		else {
			marge = (this.msie) ? -1 : 0;
			this.HTML.div.resort.style.top = (getTop(this.HTML.input.resort)+this.HTML.input.resort.offsetHeight+marge)+'px';
			marge = (this.msie) ? 0 : 1;
			this.HTML.div.resort.style.left = (getLeft(this.HTML.input.resort)+marge)+'px';
		}
		if(this.msie && this.HTML.div.resort.offsetHeight>250) { this.HTML.div.resort.style.height = '250px'; }
	},
	
	setHTMLDivSuggest: function(blocked) {
		var CatalogEngine = this;
		this.resorts = new Array();
		this.blocked = blocked;
		
		// Add confirm message before new booking
		if(link=document.getElementById('catalog_new_booking')) {
			addEvent(link,'click',function(e) {
				rtn = window.confirm(TLT.confirmResort[CatalogEngine.language]);
				return (rtn) ? true : stopEventPropagation(e);
			});
			addEvent(link,'keypress',function(e) {
				rtn = window.confirm(TLT.confirmResort[CatalogEngine.language]);
				return (rtn) ? true : stopEventPropagation(e);
			});
		}
		
		// Parse resort select's options
		for(i=1;i<this.HTML.select.resort.options.length;i++) {
			this.resorts.push({
				id:this.HTML.select.resort.options[i].value,
				name:this.HTML.select.resort.options[i].text,
				country:this.countries[this.HTML.select.resort.options[i].getAttribute('xml:cny')],
				country_id:this.HTML.select.resort.options[i].getAttribute('xml:cny'),
				department:this.HTML.select.resort.options[i].getAttribute('xml:sub'),
				formattedName:this.HTML.select.resort.options[i].text
			});
		}
		
		this.resorts.sort(this.sortResorts);
		// Create hidden <input> for sending good parameter (can't be changed by user)
		this.HTML.input.hidden = document.createElement('input');
		this.HTML.input.hidden.id = this.HTML.select.resort.id;
		this.HTML.input.hidden.name = this.HTML.select.resort.name;
		this.HTML.input.hidden.type = 'hidden';
		if(this.resort_id) {
			this.HTML.input.hidden.value = this.resort_id;
		}
		// Create text <input>
		this.HTML.input.resort = document.createElement('input');
		this.HTML.input.resort.type = 'text';
		this.HTML.input.resort.className = 'dft';
		
		this.HTML.input.resort.used = false;
		this.HTML.input.resort.defaultValue = this.HTML.select.resort.options[0].innerHTML;
		this.HTML.input.resort.value = this.HTML.input.resort.defaultValue;
		this.HTML.input.resort.setAttribute('autocomplete','off');
		
		this.HTML.input.resort.style.width = this.HTML.select.resort.offsetWidth+'px';
		marge = (this.msie) ? -3 : -2;
		this.HTML.input.resort.style.height = (this.HTML.select.resort.offsetHeight+marge)+'px';
		
		this.HTML.select.resort.parentNode.insertBefore(this.HTML.input.hidden,this.HTML.select.resort);
		this.HTML.select.resort.parentNode.insertBefore(this.HTML.input.resort,this.HTML.select.resort);
		this.HTML.select.resort.parentNode.removeChild(this.HTML.select.resort);
		this.HTML.select.resort = null;
		
		this.HTML.div.flags = document.getElementById('catalog_select_country');
		
		this.HTML.span.flags = new Object();
		
		for(var cny in this.countries) {
			this.HTML.span.flags[cny] = document.createElement('span');
			this.HTML.span.flags[cny].cny = cny;
			this.HTML.span.flags[cny].title = this.countries[cny];
			this.HTML.span.flags[cny].className = 'select_country '+cny;
			this.HTML.div.flags.appendChild(this.HTML.span.flags[cny]);
			if(!blocked) {
				addEvent(this.HTML.span.flags[cny],'click',function(e) {
					elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
					CatalogEngine.setCountry(elt.cny);
					CatalogEngine.drawHTMLDivSuggest();
					CatalogEngine.showHTMLDivSuggest();
					CatalogEngine.HTML.input.resort.focus();
					CatalogEngine.HTML.input.resort.select();
				});
				addEvent(this.HTML.span.flags[cny],'mouseover',function(e) {
					elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
					addClassName(elt,'hover');
				});
				addEvent(this.HTML.span.flags[cny],'mouseout',function(e) {
					elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
					removeClassName(elt,'hover');
				});
			}
		}
		
		this.HTML.span.flags['none'] = document.createElement('span');
		this.HTML.span.flags['none'].cny = false;
		//this.HTML.span.flags['none'].title = TLT.noCountry[this.language_id];
		this.HTML.span.flags['none'].className = 'select_country none';
		this.HTML.div.flags.appendChild(this.HTML.span.flags['none']);
		
		if(!blocked) {
			addEvent(this.HTML.span.flags['none'],'click',function(e) {
				CatalogEngine.setCountry(false);
				CatalogEngine.drawHTMLDivSuggest();
				CatalogEngine.showHTMLDivSuggest();
				CatalogEngine.HTML.input.resort.select();
			});
			addEvent(this.HTML.span.flags['none'],'mouseover',function(e) {
				elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
				addClassName(elt,'hover');
			});
			addEvent(this.HTML.span.flags['none'],'mouseout',function(e) {
				elt = (CatalogEngine.msie) ? window.event.srcElement : e.target;
				removeClassName(elt,'hover');
			});

			this.HTML.input.resort.focus();
			this.HTML.input.resort.value = this.HTML.input.resort.defaultValue;
			this.HTML.input.resort.select();
			
			this.HTML.div.resort = document.createElement('div');
			this.HTML.div.resort.displayed = false;
			this.HTML.div.resort.className = 'engine_resort_list';
			
			marge = (this.msie) ? -6 : -6;
			this.HTML.div.resort.style.width = (this.HTML.input.resort.offsetWidth+marge)+'px'; // Padding + border
			
			document.body.appendChild(this.HTML.div.resort);
		}
		
		if(this.previous_resort_id != null) {
			this.setSelectedResort(this.previous_resort_id);
		}
		
		if(!blocked) {
			this.drawHTMLDivSuggest();
			this.setHTMLDivSuggestDimensionAndPosition();
			this.hideHTMLDivSuggest(true);
			
			// Document events
			addEvent(document,'click',function(e) { CatalogEngine.clickedOut(e); });
			addEvent(document,'keydown',function(e) {
				if(CatalogEngine.HTML.input.resort.used || CatalogEngine.HTML.div.resort.displayed) {
					CatalogEngine.controlKeyCode(e,true);
				}
			});
			// Window events
			addEvent(window,'resize',function(e) {
				if(CatalogEngine.HTML.div.resort.displayed) {
					CatalogEngine.setHTMLDivSuggestPosition();
				}
			});
			// HTML Form events
			if(this.msie) {
				//	Add delay for prevent "input.select()" and "input.focus()" conflict
				window.setTimeout(function() {
					addEvent(CatalogEngine.HTML.input.resort,'focus',function() {
						if(CatalogEngine.HTML.input.resort.value == CatalogEngine.HTML.input.resort.defaultValue) {
							CatalogEngine.HTML.input.resort.value = '';
						}
						CatalogEngine.HTML.input.resort.used = true;
					});
				},1000);
			}
			else {
				addEvent(this.HTML.input.resort,'focus',function() {
					if(CatalogEngine.HTML.input.resort.value == CatalogEngine.HTML.input.resort.defaultValue) {
						CatalogEngine.HTML.input.resort.value = '';
					}
					CatalogEngine.HTML.input.resort.used = true;
				});
			}
			
			addEvent(this.HTML.input.resort,'blur',function() {
				if(CatalogEngine.HTML.input.resort.value==''||CatalogEngine.HTML.input.resort.value==null) {
					CatalogEngine.HTML.input.resort.value = CatalogEngine.HTML.input.resort.defaultValue;
				}
				CatalogEngine.HTML.input.resort.used = false;
				CatalogEngine.hideHTMLDivSuggest(true);
			});
			
			addEvent(this.HTML.input.resort,'mouseover',function() { CatalogEngine.showHTMLDivSuggest(); });
			addEvent(this.HTML.input.resort,'mouseout',function() { CatalogEngine.hideHTMLDivSuggest(false); });
			
			addEvent(this.HTML.div.resort,'mouseover',function() {
				CatalogEngine.HTML.div.resort.over = true;
				CatalogEngine.showHTMLDivSuggest();
			});
			
			addEvent(this.HTML.div.resort,'mouseout',function() {
				CatalogEngine.HTML.div.resort.over = false;
				CatalogEngine.hideHTMLDivSuggest(false);
			});
			
			addEvent(this.HTML.input.resort,'keyup',function(e) {
				if(CatalogEngine.controlKeyCode(e,false)==true) {
					CatalogEngine.drawHTMLDivSuggest(CatalogEngine.HTML.input.resort.value);
					CatalogEngine.showHTMLDivSuggest();
				}
			});
		}
		else {
			this.HTML.input.resort.setAttribute('disabled','disabled');
		}
	},

	setLanguage: function(language) {
		switch(language) {
			case 'fre':
				this.language = 'fre';
				break;
			case 'ger':
				this.language = 'ger';
				break;
			case 'ita':
				this.language = 'ita';
				break;
			case 'nld':
				this.language = 'nld';
				break;
			case 'spa':
				this.language = 'spa';
				break;
			case 'zho':
				this.language = 'zho';
				break;
			
			default:
			case 'eng':
				this.language = 'eng';
				break;
		}
	},
	
	setRegExp: function(text) {
		for(i=0;i<this.regularExpressions.length;i++) {
			text = text.replace(this.regularExpressions[i][0],this.regularExpressions[i][1]);
		}
		return new RegExp('('+text+')','ig');
	},
	
	setSelectedDate: function() {
		switch(arguments.length) {
			case 0:
				date = new Date(this.HTML.select.year.value,parseInt(this.HTML.select.month.value,10)-1,this.HTML.select.day.value,0,0,0);
				break;
			case 1:
				date = arguments[0];
				break;
			case 3:
			case 4:
			case 5:
			case 6:
				y = ('number' == typeof(arguments[0])) ? parseInt(arguments[0],10) : 0;
				m = ('number' == typeof(arguments[1])) ? parseInt(arguments[1],10) : 0;
				d = ('number' == typeof(arguments[2])) ? parseInt(arguments[2],10) : 0;
				h = ('number' == typeof(arguments[3])) ? parseInt(arguments[3],10) : 0;
				i = ('number' == typeof(arguments[4])) ? parseInt(arguments[4],10) : 0;
				s = ('number' == typeof(arguments[5])) ? parseInt(arguments[5],10) : 0;
				date = new Date(y,m-1,d,h,i,s);
				break;
		}
		ctl = this.controlDate(date);
		 
		if('object'==typeof(ctl)) {
			this.HTML.span.date.innerHTML = ctl['title'];
			this.HTML.span.alert.style.visibility = 'visible';
		}
		else {
			this.HTML.span.date.innerHTML = '';
            this.HTML.span.alert.style.visibility = 'hidden';
		}
		
		this.date.selected = date;
		if(this.Calendar) {
			this.Calendar.setSelectedDate(date);
		}
		this.updateDateSelectsOptions(this.date.selected.getFullYear(),this.date.selected.getMonth()+1,this.date.selected.getDate(),false);
		if(this.debug) { window.alert('CatalogEngine.setSelectedDate(): '+date); }
	},
	
	setPreviousResort: function(id) {
		this.previous_resort_id = id;
	},
	
	setSelectedResort: function(id) {
		this.resort_id = id;
		this.HTML.input.hidden.value = id;
		this.HTML.input.resort.value = this.searchResort('id',id)[1].name;
		this.HTML.input.resort.focus();
		this.HTML.input.resort.select();
	},
	
	setValidDatesInterval: function() {
		if(arguments.length == 1) {
			arguments[1] = null;
		}
		this.date.start = ('object'==typeof(arguments[0])) ? arguments[0] : new Date(this.date.now.getFullYear(),this.date.now.getMonth(),this.date.now.getDate(),0,0,0);
		//window.alert('this.date.start: '+this.date.start);
		this.date.finish = ('object'==typeof(arguments[1])) ? arguments[1] : null;
		//window.alert('this.date.finish: '+this.date.finish);
		if(this.date.compare(this.date.selected,this.date.start)<0) {
			this.setSelectedDate(this.date.start);
		}
		else if(this.date.compare(this.date.selected,this.date.finish)>0) {
			this.setSelectedDate(this.date.finish);
		}
	},
	
	sortResorts: function(a,b) {
		if(a.name<b.name) { return -1; }
		else if(a.name>b.name) { return 1; }
		else { return 0; }
	},
	
	sortResortsByGeo: function(a,b) {
		if(a.country<b.country) { return -1; }
		else if(a.country>b.country) { return 1; }
		
		if(a.department<b.department) { return -1; }
		else if(a.department>b.department) { return 1; }
		
		if(a.name<b.name) { return -1; }
		else if(a.name>b.name) { return 1; }
		else { return 0; }
	},
	
	hideHTMLDivSuggest: function(force) {
		var CatalogEngine = this;
		var force = (force) ? true : false;
		if(!force && this.interval.suggest.hide == null) {
			time = (this.msie) ? 500 : 250;
			this.interval.suggest.hide = window.setTimeout(function() {
				CatalogEngine.hideHTMLDivSuggest(false);
			},time);
		}
		else {
			if(force || (this.HTML.div.resort.displayed && !this.HTML.div.resort.over)) {
				this.HTML.div.resort.style.visibility = 'hidden';
				this.HTML.div.resort.displayed = false;
			}
			this.interval.suggest.hide = null;
		}
	},
	
	showHTMLDivSuggest: function() {
		if(!this.blocked) {
			if(this.interval.suggest.hide != null) {
				window.clearTimeout(this.interval.suggest.hide);
				this.interval.suggest.hide = null;
			}
			if(this.interval.suggest.hide == null && this.HTML.div.resort.displayed == false) {
				this.setHTMLDivSuggestDimensionAndPosition();
				this.HTML.div.resort.style.visibility = 'visible';
				this.HTML.div.resort.displayed = true;
			}
		}
	},
	
	selectResortByIndex: function() {
		min = 1;
		max = this.HTML.div.resort.childNodes.length;
		index = ('number' == typeof(arguments[0])) ? arguments[0] : this.HTML.div.resort.selectedIndex;
		if(index < min) { index = min; }
		else if(index >= max) { index = max-1; }
		for(i=min;i<max;i++) {
			removeClassName(this.HTML.div.resort.childNodes[i],'selected');
		}
		if(min <= index && index < max) {
			this.setSelectedResort(this.HTML.div.resort.childNodes[index].value);
			addClassName(this.HTML.div.resort.childNodes[index],'selected');
			this.HTML.div.resort.scrollTop = this.HTML.div.resort.childNodes[index-1].offsetTop;
			this.HTML.div.resort.selectedIndex = index;
		}
		this.HTML.input.resort.focus();
		this.HTML.input.resort.select();
		return true;
	},
	
	updateDateSelectsOptions: function(y,m,d,dspAlert) {
		if(this.dbg) { window.alert('CatalogEngine.updateDateSelectsOptions('+y+','+m+','+d+','+dspAlert+')'); }
		hidden = 0;
		switch(parseInt(m,10)) {
			case  1:
			case  3:
			case  5:
			case  7:
			case  8:
			case 10:
			case 12:
			hidden = 0;
			break;
			
			case  4:
			case  6:
			case  9:
			case 11:
			hidden = 1;
			if(d == 31) {
				this.HTML.select.day.value = '30';
				this.HTML.select.day.options[29].selected = true;
			}
			break;
			
			case  2:
			if((y%4) == 0 && (y%100) !== 0 || (y%400) == 0) {
				hidden = 2;
			}
			else {
				hidden = 3;
			}
			break;
		}
		
		opt_num = this.HTML.select.day.childNodes.length;
		if(opt_num > (31-hidden)) {
			for(i = 27; i < opt_num; i++) {
				if(parseInt(this.HTML.select.day.options[i].value,10) > (31 - hidden)) {
					this.HTML.select.day.removeChild(this.HTML.select.day.childNodes[i]);
					i--;
					opt_num--;
				}
			}
		}
		else {
			for(i = opt_num; i < (31-hidden); i++) {
				opt = document.createElement("option");
				opt = new Option((i+1),(i+1),false,false);
				opt.innerHTML = i+1;
				this.HTML.select.day.appendChild(opt);
			}
		}
		
		y = parseInt(y,10);
		m = parseInt(m,10);
		d = (d < this.HTML.select.day.childNodes.length) ? parseInt(d,10) : this.HTML.select.day.childNodes.length;
		this.date.selected = new Date(y,(m-1),d);
		y_str = addZero(y);
		m_str = addZero(m);
		d_str = addZero(d);
		this.HTML.select.year.value = y_str;
		this.HTML.select.month.value = m_str;
		this.HTML.select.day.value = d_str;
		
		try {
			this.HTML.select.year.options[y-this.date.now.getFullYear()].selected = true;
			this.HTML.select.month.options[m-1].selected = true;
			this.HTML.select.day.options[d-1].selected = true;
		}
		catch(e) {	//	IE6
			this.HTML.select.year.selectedIndex = y-this.date.now.getFullYear();
			this.HTML.select.month.selectedIndex = m-1;
			this.HTML.select.day.selectedIndex = d-1;
		}
		
		//	DES TITLES DANS LES OPTIONS EMPÊCHENT LEUR ENVOI PAR POST
		for(i = 0; i < this.HTML.select.day.childNodes.length; i++) {
			css = '';
			/*
			date_cur = new Date(y,m-1,i+1,0,0,0);
			if(ofr = this.ctlOfr(date_cur)) {
				css = (((parseFloat(this.prd.prc.ini)+(parseFloat(ofr[2])/10))>0)?'spc':'dsb');
				css += (css == 'spc' && (parseFloat(ofr[2])<0)?' promo':'');
				this.HTML.select.day.childNodes[i].title = (css == 'dsb') ? ofr[3] : '';
			}
			else { this.HTML.select.day.childNodes[i].title = ''; }
			*/
			this.HTML.select.day.childNodes[i].disabled = (css =='dsb') ? true : false;
			this.HTML.select.day.childNodes[i].className = css;
		}
		return true;
	},
	
	date: {
		now: new Date(),
		start: null,
		finish: null,
		selected: null,
		/*
		 	CatalogEngine.date.compare():
				2 dates:
					return:
						-1 => date1 < date2
						 0 => date1 == date2
						 1 => date1 > date2
				3 dates:
					return:
						-1 => date1 < date2
						 0 => date2 <= date1 <= date3
						 1 => date1 > date3
				4 dates:
					return:
						[-1,-1] => date1 < date3 && date2 < date3
						[-1, 0] => date1 < date3 && date3 <= date2 <= date4
						[-1, 1] => date1 < date3 && date3 < date2
						[ 0, 0] => date3 <= date1 <= date4 && date3 <= date2 <= date4
						[ 0, 1] => date3 <= date1 <= date4 && date3 < date2
						[ 1, 1] => date3 < date1 && date3 < date2
		*/
		compare: function() {
			switch(arguments.length) {
				case 4:
				rtn = this.compareDatesIntervals(arguments[0],arguments[1],arguments[2],arguments[3]);
				break;
				case 3:
				rtn = this.compareDateAndInterval(arguments[0],arguments[1],arguments[2]);
				break;
				case 2:
				rtn = this.compareDates(arguments[0],arguments[1]);
				break;
			}
			// window.alert('CatalogEngine.date.compare:\n\t'+arguments[0]+'\n\t'+arguments[1]+'\n\t'+arguments[2]+'\n\t'+arguments[3]+'\nreturn: '+rtn);
			return rtn;
		},
		
		compareDates: function() {
			rtn = (null!=arguments[1]&&'object'==typeof(arguments[1])) ? arguments[0].getTime()-arguments[1].getTime() : -1;
			return (rtn==0) ? rtn : rtn/Math.abs(rtn);
		},
		
		compareDateAndInterval: function() {
			rtn = this.compareDates(arguments[0],arguments[1]);
			if(rtn==1) {
				rtn = this.compareDates(arguments[0],arguments[2]);
				rtn = (rtn<=0) ? 0 : 1;
			}
			return rtn;
		},
		
		compareDatesIntervals: function() {
			cmp1 = this.compareDateAndInterval(arguments[0],arguments[2],arguments[3]);
			cmp2 = this.compareDateAndInterval(arguments[1],arguments[2],arguments[3]);
			return [cmp1,cmp2];
		}
	}
};