var Portal = Class.create({
	
	initialize: function() {
		this.browser = new BrowserDetect();
		this.formValidator = new FormValidator();
		//alert(this.browser.browser + ' | ' + this.browser.version + ' | ' + this.browser.OS);
		this.bodyElement = document.getElementsByTagName("body")[0];
		this.verticalScrollActived = false;
		this._moduleTabIsRenamed = false;
		this.addedScripts = new Array();
		this.addedStyleSheets = new Array();
		this.preloadedImages = new Array();
		this._widgetsWithChartsByID = new Hash();
		this._modulesById = new Hash();
		this._modulesByIndex = new Hash();
		this.properties = new Hash();
		this.observers = new Hash();
		this._eventItems = new Array();
		this._expansionEventItems = [];
		this._eventToDesactiveDuringModification = new Array();
		this._modificationEvents = new Array();
		//use same code as in EventHandler since it is not loaded yet
		if (document.addEventListener) {
			window.addEventListener('unload', this._onWindowUnload.bind(this), false);
		} else if (document.attachEvent) {
			window.attachEvent('onunload', this._onWindowUnload.bind(this))
		}
		new ScriptLoader(Portal.SCRIPT_FILES_TO_LOAD, Portal.SCRIPT_OBJECTS_TO_LOAD, this.addedScripts, this.init.bindAsEventListener(this));
	},
	
	init: function() {		
		new CSSLoader(Portal.CSS_TO_LOAD, this.addedStyleSheets);
		this.access = new Access(this._onNotLoggedError.bind(this));	
		this.dimensionsHandler = new DimensionsHandler(this.access);
		this.languageManager = new LanguageManager(this._getLocaleFromCookie());
		this.languageManager.loadPortalStrings(this._onTempLanguageLoaded.bind(this));
	},
	
	_getLocaleFromCookie: function() {
		var allCookies = document.cookie;
		var pos = allCookies.indexOf(Portal.LOCALE_COOKIE_NAME);
		if (pos != -1) {
			var start = pos + Portal.LOCALE_COOKIE_NAME.length + 1;
			var end = allCookies.indexOf(';', start);
			if (end == -1) {
				end = allCookies.length;
			}
			return allCookies.substring(start, end);
		}
		else {
			return null;
		}
	},
	
	_saveLocaleInCookie: function(locale) {
		document.cookie = Portal.LOCALE_COOKIE_NAME+'='+locale+'; max-age='+(60*60*24*365);
	},
	
	_onTempLanguageLoaded: function() {
		Utils.init(this.languageManager);
		TimeSerieChart.init(this.languageManager);
		this.access.requestUserProfile(this._onUserProfileRetrieved.bind(this, false));
	},
	
	_relog: function() {
		this._loginDialog.showWaiting();
		this.access.requestLogin(this._loginDialog.getUsername(), this._loginDialog.getPassword(), this._onReloginOKResponseReceived.bind(this), this._onLoginErrorResponseReceived.bind(this));
	},
	
	_onReloginOKResponseReceived: function(loginResponse) {
		this.dimensionsHandler = new DimensionsHandler(this.access);
		this.access.requestUserProfile(this._onUserProfileRetrieved.bind(this, true));
		this._loginDialog.hideAndDispose(this.access.resubmitPendingRequests.bind(this.access));
		delete this._loginDialog;
	},
	
	_onUserProfileRetrieved: function(isRelog, userProfile) {
		this.userProfile = userProfile;
		if (this.userProfile.properties != null) 
			this.userProfile.properties = eval('('+this.userProfile.properties+')');
		else
			this.userProfile.properties = new Object();
		if (Object.isUndefined(this.userProfile.properties.separator))
			this.userProfile.properties.separator = Portal.DEFAULT_CSV_SEPARATOR;
		if (Object.isUndefined(this.userProfile.properties.encoding))
			this.userProfile.properties.encoding = Portal.DEFAULT_CSV_ENCODING;
		if (userProfile.locale != this._getLocaleFromCookie()) {
			this._saveLocaleInCookie(userProfile.locale);
			this.languageManager.setLocale(userProfile.locale);
			this.languageManager.loadPortalStrings(this._onLanguageLoaded.bind(this, isRelog));
		}
		else {
			this._saveLocaleInCookie(userProfile.locale);
			this._onLanguageLoaded(isRelog);
		}
	},
	
	_onLanguageLoaded: function(isRelog) {
		Utils.init(this.languageManager);
		Table.init(this.languageManager, this.access, this.userProfile.properties.separator, this.userProfile.properties.encoding);
		//Calendar.init(this.languageManager);
		this._buildPortal(isRelog);
		this.adaptContainersSizes();
		this.access.requestModuleHeaders(this._loadModuleHeaders.bindAsEventListener(this));	
		this._windowResizeEvent = this.observeEvent(window, 'resize', this.adaptContainersSizes.bindAsEventListener(this));  			
	},
		
	_onNotLoggedError: function() {
		if (this._globalContainerElement != null) {
			this.access.cancelAllRequests();
			setTimeout(this._reloadWindow.bind(this), 100); // to avoid an exception in Firebug
		}
		else
			this._loginDialog = new LoginDialog(this.bodyElement, this._onLoginButtonClicked.bind(this), this);
	},
	
	_reloadWindow: function() {
		window.location.reload();
	},
	
	_onLoginButtonClicked: function() {
		this._loginDialog.showWaiting();
		this.access.requestLogin(this._loginDialog.getUsername(), this._loginDialog.getPassword(), this._onLoginOKResponseReceived.bind(this), this._onLoginErrorResponseReceived.bind(this));
	},
	
	_onLoginErrorResponseReceived: function(errorCode) {
		this._loginDialog.hideWaiting();
		if (errorCode == Access._RESULT_CODE_ALREADY_LOGGED_IN) {
			this._loginDialog.showErrorMessage(this.getString('already_logged'));			
		}
		else {
			this._loginDialog.showErrorMessage(this.getString('login_failed'));
		}
	},
	
	_onLoginOKResponseReceived: function(loginResponse) {
		if (this._globalContainerElement != null) {
			this._globalContainerElement.show();
			this._globalContainerElement.setOpacity(1.0);			
		}
		this._loginDialog.hideAndDispose(this.access.resubmitPendingRequests.bind(this.access));
		delete this._loginDialog;
		this.showCharts();
	},
	
	_onLogoutButtonClicked: function() {
		this.access.requestLogout(this._onLogoutResponseReceived.bind(this));
	},
	
	_onLogoutResponseReceived: function(logoutResponse) {
		this.access.cancelAllRequests();
		if (this._windowResizeEvent != null) {
			this.stopObservingEvent(this._windowResizeEvent);
			this._windowResizeEvent = null;
		}
		this._loginDialog = new LoginDialog(this.bodyElement, this._relog.bind(this), this);
		new Effect.Fade(this._globalContainerElement, {duration: 0.3, afterFinish: this._removeGlobalContainer.bind(this)});
		this._disposeContent();
	},
	
	_onAddModuleButtonClicked: function() {
		this._scrollMenu.toggle();
		var moduleHeader = new Object();
		moduleHeader.moduleID = this._modulesById.keys().length;
		moduleHeader.index = this._modulesByIndex.values().length + 1;
		moduleHeader.locked = false;
		moduleHeader.unlockable = false;
		moduleHeader.caption = this.getString('create_module_caption');
		moduleHeader.renamable = 1;
		var moduleToAdd = new Module(moduleHeader, this);
		/** APPLY REORDERMODULES **/
		this.access.requestCreateModule(moduleToAdd, this._createModuleCallback.bind(this, moduleToAdd));
		/**************************/
		
	},
	
	_createModuleCallback: function(moduleToAdd, result) {
		moduleToAdd.id = result.moduleID;
		this._modulesById.set(moduleToAdd.id, moduleToAdd);
		this._modulesByIndex.set(moduleToAdd.index, moduleToAdd);
		this._addModuleTabToDom(moduleToAdd);
		this._applyTabSortable();
		this.selectModule(moduleToAdd.id);	
		this.adaptContainersSizes();	
	},
	
	_onAddCategoryButtonClicked: function() {
		this._scrollMenu.toggle();
		this._selectedModule.createNewPage(true);
	},
	
	_onAddPageButtonClicked: function() {
		this._scrollMenu.toggle();
		this._selectedModule.createNewPage(false);
	},
	
	_removeGlobalContainer: function() {
		if (this._globalContainerElement != null)
			Utils.removeElement(this._globalContainerElement);
		this.tooltip.dispose();
		Utils.removeElement($('historyStorageForm'));
		if (this.browser.browser == "Explorer") {
			Utils.removeElement($('DhtmlHistoryFrame'));	
		}
		this._globalContainerElement = null;
	},
	
	_buildPortal: function(isRelog) {
		//this.access.initFakeData();
		
		historyStorage.init();
		dhtmlHistory.create();
		dhtmlHistory.initialize();
		dhtmlHistory.addListener(this._onHistoryChanged.bindAsEventListener(this));
		if (dhtmlHistory.getCurrentLocation() != '' && !isRelog) {
			var splits = dhtmlHistory.getCurrentLocation().split(':');
        	this.initialModuleID = splits[0];
        	this.initialPageID = splits[1];
		}
				
		this._globalContainerElement = Element.extend(document.createElement('div'));
		this._globalContainerElement.id = 'global_container';
		this.bodyElement.appendChild(this._globalContainerElement);
		
		this.library = new Library(this._globalContainerElement, this, this._onAddToPortalClicked.bind(this));
		this._globalPortalContainerElement = Element.extend(document.createElement('div'));
		this._globalPortalContainerElement.id = 'portal_global_container';
		this._globalContainerElement.appendChild(this._globalPortalContainerElement);
		
		this.tooltip = new Tooltip(this.bodyElement);
		
		this.headerElement = Element.extend(document.createElement('div'));
		this.headerElement.id = 'portal_header';
		this._globalPortalContainerElement.appendChild(this.headerElement);
		
		var logoElement = Element.extend(document.createElement('div'));
		var label = 'NEXThink Portal<br/>v. '+this.userProfile.portalVersion;
		logoElement.id = 'portal_logo';
		this._eventItems.push(this.observeEvent(logoElement, 'mouseover', this.tooltip.show.bind(this.tooltip, label)));
		this._eventItems.push(this.observeEvent(logoElement, 'mouseout', this.tooltip.hide.bind(this.tooltip)));
		this.headerElement.appendChild(logoElement);
		
		this.moduleElement = Element.extend(document.createElement('div'));
		this.moduleElement.id = 'portal_module_content';
		this._globalPortalContainerElement.appendChild(this.moduleElement);
		
		this._pageMenuContainerElement = Element.extend(document.createElement('div'));
		this._pageMenuContainerElement.id = 'module_page_menu_container';
		this.moduleElement.appendChild(this._pageMenuContainerElement);
		
		this.pageMenuElement = Element.extend(document.createElement('div'));
		this.pageMenuElement.id = 'module_page_menu';
		this._pageMenuContainerElement.appendChild(this.pageMenuElement);
		
		this.pageContentElement = Element.extend(document.createElement('div'));
		this.pageContentElement.id = 'module_page_content';
		this.moduleElement.appendChild(this.pageContentElement);
		
		this.pageContentContainerElement = Element.extend(document.createElement('div'));
		this.pageContentContainerElement.id = 'module_page_content_container';
		this.pageContentElement.appendChild(this.pageContentContainerElement);
				
		this.userPanel = new UserPanel(this.headerElement, this.userProfile, this._onLogoutButtonClicked.bind(this), this._onPreferencesClicked.bind(this), this.onAddContentClicked.bind(this), this);
		this._preferencesDialog = new DialogBox(this.bodyElement, null, this);
		this._setupPreferencesDialog();
		
		this.compenseElement = Element.extend(document.createElement('div'));
		this.compenseElement.id = 'module_page_compense_height';
		this.headerElement.appendChild(this.compenseElement);
		
		this.calendarPanel = Element.extend(document.createElement('div'));
		this.calendarPanel.id = 'portal_calendar_panel';
		this.calendarPanel.style.display = 'none';
		
		this.waitingPagesDiv = Element.extend(document.createElement('div'));
		this.waitingPagesDiv.hide();
		this.waitingPagesDiv.addClassName('portal_pageMenu_loading');
		this.waitingPagesDiv.innerHTML = this.getString('loading_module');
		this._globalPortalContainerElement.appendChild(this.waitingPagesDiv);
		
		this.waitingWidgetsDiv = Element.extend(document.createElement('div'));
		this.waitingWidgetsDiv.hide();
		this.waitingWidgetsDiv.addClassName('portal_widgets_loading');
		this.waitingWidgetsDiv.innerHTML = this.getString('loading_page');
		this._globalPortalContainerElement.appendChild(this.waitingWidgetsDiv);
		
		
		this._scrollMenu = new ScrollMenu(this._pageMenuContainerElement, this, this._onAddModuleButtonClicked.bind(this), this._onAddCategoryButtonClicked.bind(this), this._onAddPageButtonClicked.bind(this));
		
		if (this.userProfile.lastDate != null && this.userProfile.lastDate.length > 0) {
			Utils.lastDate = Utils.parseDate(this.userProfile.lastDate);
		}
		else {
			var now = new Date();
			Utils.lastDate = new Date(now.getFullYear(), now.getMonth(), now.getDate()-1);
		}
		
		this.setProperty('selectedDate', Utils.getYesterdayDate());
		//this._calendar = new Calendar(this.calendarPanel, Utils.getYesterdayDate(), this._onSelectedDateChanged.bind(this));
		//this.addObserver('dateChanged', this._calendar.selectAndDisplayDate.bind(this._calendar));
		this._pageMenuContainerElement.appendChild(this.calendarPanel);	
		var parameters = new Object();
		parameters['query'] = 'getSupportedEncodings';
		this.access.genericRequest(parameters, this._onEncodingReceived.bind(this));
	},
	
	addObserver: function(eventName, observerCallback) {
		if (this.observers.get(eventName) == null) {
			this.observers.set(eventName, new Array());
		}
		this.observers.get(eventName).push(observerCallback);
	},
	
	removeObserver: function(eventName, observerCallback) {
		if (this.observers.get(eventName) != null) {
			this.observers.set(eventName, this.observers.get(eventName).without(observerCallback));
		}
	},

	notify: function(eventName, args) {
		if (this.observers.get(eventName) != null) {
		    for(var i=0; i<this.observers.get(eventName).length; i++)
			{
				this.observers.get(eventName)[i](args);
			}
		}
	}, 
	
	adaptPageContentSize: function() {
		var pageSize = Utils.getPageSize();
		var windowHeight = pageSize[3];
		var windowWidth = pageSize[2]
		var moduleContentOffsets = Position.cumulativeOffset(this.moduleElement);
		var minHeight = windowHeight - moduleContentOffsets[1] - 11;
		if (this.browser.browser == 'Explorer' && this.browser.version == 6) {
			var width = windowWidth - moduleContentOffsets[0] - 201;	//IE6
		} else {
			var width = windowWidth - moduleContentOffsets[0] - 211; //Firefox, Safari, IE7	
		}
		this.pageContentElement.setStyle({
			height: minHeight + 'px',
			width: width + 'px'
		});
		this.verticalScrollActived = false;
	},
	
	adaptPageContentContainerSize: function() {
		var pageContentWidth = this.pageContentElement.getWidth() - 10;
		var pageContentMinWidth = this.pageContentContainerElement.readAttribute('wrminwidth');
		if (pageContentWidth > pageContentMinWidth) {
			if (pageContentWidth - pageContentMinWidth > 17) var pageContainerWidth = pageContentWidth - 17;
			else var pageContainerWidth = pageContentWidth;
		} else {
			var pageContainerWidth = pageContentMinWidth;
		}
		this.pageContentContainerElement.setStyle({ width: pageContainerWidth + 'px' });
	},
	
	adaptPageMenuContainerHeight: function() {
		var height = this.pageContentElement.getHeight()+1;
		this.moduleElement.setStyle({ height: height + 'px' });
		this._pageMenuContainerElement.setStyle({height: height + 'px'});
		this.defineOverflowOnPageMenu();
	},
	
	defineOverflowOnPageMenu: function() {
		if (typeof this._selectedModule != 'undefined' && this._selectedModule != null && this._selectedModule.pageMenu != null) {
			var test = this.pageContentElement.getHeight() + 1 - 25;
			this.pageMenuElement.style.height = test + 'px';
			if (test < this._selectedModule.pageMenu.getHeight()) {
				if (!this.pageMenuElement.hasClassName('page_menu_overflow'))
				this.pageMenuElement.addClassName('page_menu_overflow');
			} else {
				if (this.pageMenuElement.hasClassName('page_menu_overflow'))
					this.pageMenuElement.removeClassName('page_menu_overflow')
			}	
		}		
	},
	
	adaptContainersSizes: function() {
		if (this._selectedModule != null) {
			this.adaptPageContentSize();
			this.adaptPageContentContainerSize();
			this.adaptPageMenuContainerHeight();
			if (typeof this._selectedModule != 'undefined' &&
            	typeof this._selectedModule.selectedPage != 'undefined' &&
            	this._selectedModule.selectedPage != null) {
		 		this._selectedModule.selectedPage.correctAllWidgetsWidth();
	     	   this._selectedModule.selectedPage.notify('sizeChanged');
        	}	
		}
		else {
			this.adaptPageContentSize();
			this.adaptPageContentContainerSize();
			this.adaptPageMenuContainerHeight();
		}
        this.notify('containerSizedChanged');
	},
	
	displayAndMaskLibraryRecurcive: function(aChangeHeight) {
		if (this.browser.browser == 'Explorer' && this.browser.version == 6) { // IE6
			var currentPageHeight = this.pageContentElement.getHeight();
		} else {
			var currentPageHeight = this.pageContentElement.getHeight() -1; // FF, Safari, IE7
		}
		var newHeight = currentPageHeight - aChangeHeight;
		this.pageContentElement.setStyle({ height: newHeight + 'px' });
		this.adaptPageMenuContainerHeight();
	},
	
	_loadModuleHeaders: function(moduleHeaders) {
		if (Object.isUndefined(this.userProfile.lastDate)) {
			this.setProperty('linkDate', Utils.serializeDate(Utils.getYesterdayDate()));
			var endDate = Utils.getYesterdayDate();
			var startDate = Utils.getDateDaysBefore(endDate, 10);
			this.setProperty('linkPeriod', Utils.serializeDate(startDate) + '..' + Utils.serializeDate(endDate));
		} else {
			this.setProperty('linkDate', this.userProfile.lastDate);
			var endDate = Utils.parseDate(this.userProfile.lastDate);
			var startDate = Utils.getDateDaysBefore(endDate, 10);
			this.setProperty('linkPeriod', Utils.serializeDate(startDate) + '..' + Utils.serializeDate(endDate));
		}
		//this.tabsUlContainer = Element.extend(document.createElement('div'));
		//this.tabsUlContainer.id = 'portal_modules_tabs_container';
		//this.headerElement.appendChild(this.tabsUlContainer);
		this._tabsUl = Element.extend(document.createElement('ul'));
		this._tabsUl.id = 'portal_modules_tabs';
		this.headerElement.appendChild(this._tabsUl);
		//this.tabsUlContainer.appendChild(this._tabsUl);
		var currentModule;
		var firstModuleID = -1;
		if (moduleHeaders.length == 0) {
			this._scrollMenu.hideAddPageAndCategory();
			this._scrollMenu.hideExportButton();
		} else {
			if (!this._scrollMenu.isPageAndCategoryVisible()) {
				this._scrollMenu.showAddPageAndCategory();
			}
		}
		moduleHeaders.sort(function(a, b) {return a.index-b.index;})
		for (var i=0; i<moduleHeaders.length; i++) {
			currentModule = new Module(moduleHeaders[i], this);
			if (i == 0) {
				firstModuleID = currentModule.id;
			}
			this._modulesById.set(currentModule.id, currentModule);
			this._modulesByIndex.set(currentModule.index, currentModule);
			this._addModuleTabToDom(currentModule);
		}
		if (this.initialModuleID != null && this._modulesById.get(this.initialModuleID) != null) {
			this.selectModule(this.initialModuleID);	
			delete this.initialModuleID;
		}
		else {
			if (firstModuleID != -1) {
				this.selectModule(firstModuleID);
			}				
		}
		this._applyTabSortable();
	}, 
	
	_addModuleTabToDom: function(aModule) {
			var currentTabLi = document.createElement('li');
			currentTabLi.id = Portal.MODULE_TAB_ID_PREFIX+aModule.id;		
			currentTabLi.moduleID = aModule.id;
			var cornerLiLeft = Element.extend(document.createElement('img'));
			cornerLiLeft.src= './portal/images/module/tab_bg_left.gif';
			cornerLiLeft.addClassName('moduleTab_corner_left');
			currentTabLi.appendChild(cornerLiLeft);
			var currentTitleLi = Element.extend(document.createElement('span'));
			currentTitleLi.innerHTML = aModule.caption;
			currentTitleLi.moduleID = aModule.id;
			currentTabLi.appendChild(currentTitleLi);
			var currentLockingButton = Element.extend(document.createElement('img'));
			currentLockingButton.src = './portal/images/locked_icon.gif';
			currentLockingButton.addClassName('moduleTab_locking_button');
			currentLockingButton.moduleID = aModule.id;
			currentTabLi.appendChild(currentLockingButton);
			currentLockingButton.hide();
			if (aModule.unlockable) {
				this._eventItems.push(this.observeEvent(currentLockingButton, 'click', this._moduleTabUnlock.bindAsEventListener(this)));
			}
			var currentRemoveButton = Element.extend(document.createElement('img'));
			currentRemoveButton.src= './portal/images/module/tab_selected_close_button.gif';
			currentRemoveButton.addClassName('moduleTab_remove_button');
			currentRemoveButton.moduleID = aModule.id;
			currentRemoveButton.hide();
			currentTabLi.appendChild(currentRemoveButton);
			this._eventItems.push(this.observeEvent(currentRemoveButton, 'click', this._moduleTabRemoveButtonClicked.bindAsEventListener(this)));
			if (aModule.locked) {
				currentRemoveButton.hide();
			}
			var cornerLiRight = Element.extend(document.createElement('img'));
			cornerLiRight.src= './portal/images/module/tab_bg_right.gif';
			cornerLiRight.addClassName('moduleTab_corner_right');
			currentTabLi.appendChild(cornerLiRight);
			this._eventItems.push(this.observeEvent(currentTitleLi, 'click', this._moduleTabClicked.bindAsEventListener(this)));
			if (aModule.renamable == 1 && !aModule.locked) {
				this._createRenameModuleTabEvent(currentTitleLi);
			}
			if (aModule.locked) {
				if (aModule.unlockable) {
					var currentEventItem = this.observeEvent(currentLockingButton,'mouseover',this.tooltip.show.bind(this.tooltip, this.getString('locked_module')));
					this._eventItems.push(currentEventItem);
					aModule.tooltipEvent['mouseover'] = currentEventItem;
					currentEventItem = this.observeEvent(currentLockingButton, 'mouseout', this.tooltip.hide.bind(this.tooltip));
					this._eventItems.push(currentEventItem);
					aModule.tooltipEvent['mouseout'] = currentEventItem;
				} else {
					var currentEventItem = this.observeEvent(currentLockingButton, 'mouseover', this.tooltip.show.bind(this.tooltip, this.getString('locked_not_unlockable')));
					this._eventItems.push(currentEventItem);
					aModule.tooltipEvent['mouseover'] = currentEventItem;
					currentEventItem = this.observeEvent(currentLockingButton, 'mouseout', this.tooltip.hide.bind(this.tooltip));
					this._eventItems.push(currentEventItem);
					aModule.tooltipEvent['mouseout'] = currentEventItem;
				}
			}
			this._tabsUl.appendChild(currentTabLi);
	},
		
	_applyTabSortable: function() {
		Sortable.create(this._tabsUl.id, {
			tag: 'li',
			overlap: 'horizontal',
			constraint: 'horizontal',
			onUpdate: this.onUpdateTabList.bind(this)
		});
	},
	
	updateMenuSortable: function() {
		Sortable.destroy(this._tabsUl.id);
		this._applyTabSortable();
	},
	
	onUpdateTabList: function() {
		var sortableList = Sortable.serialize(this._tabsUl.id);
		if (sortableList != '') {
			orderList = sortableList.split("&");
			for (var i = 0; i < orderList.length; i++) {
				var moduleId = orderList[i].substring(orderList[i].indexOf('=')+1);
				var aModule = this._modulesById.get(moduleId);
				aModule.index = i + 1;
				this._modulesByIndex.set(i + 1, aModule);	
			}
			var jsonData = new Array();
			this._modulesById.each(function(module) {
				jsonData.push(module.value.getModuleHashForReorder());
			});
			jsonData = jsonData.flatten().toJSON();
			/** APPLY REORDERMODULES **/
			this.access.requestReorderModules(jsonData);
			/**************************/
		}
	},
	
	displayModuleWithIndex: function(moduleIndex, pageIndex, widgetX, widgetY) {
		var module = this._modulesByIndex.get(moduleIndex);
		if (module != null) {
			module.initialPageIndex = pageIndex;
			module.initialWidgetX = widgetX;
			module.initialWidgetY = widgetY;
			this.selectModule(module.id);
		}
	},
	
	selectModule: function(moduleID) {
		if (this._moduleTabIsRenamed) return;
		//if (this._selectedModule != null && this._selectedModule.selectedPage != null && this._selectedModule.selectedPage.isLoading())
		//	return;
		var module = this._modulesById.get(moduleID);
		if (module != null && !module.selected) {
			if (this._selectedModule != null /*&& this._selectedModule.id != moduleID*/) {
				$(Portal.MODULE_TAB_ID_PREFIX + this._selectedModule.id).removeClassName('selected');
				$(Portal.MODULE_TAB_ID_PREFIX + this._selectedModule.id).down('img.moduleTab_corner_left').src = './portal/images/module/tab_bg_left.gif';
				$(Portal.MODULE_TAB_ID_PREFIX + this._selectedModule.id).down('img.moduleTab_corner_right').src = './portal/images/module/tab_bg_right.gif';
				if (this._selectedModule.locked) {
					$(Portal.MODULE_TAB_ID_PREFIX + this._selectedModule.id).down('img.moduleTab_locking_button').hide();
				}
				if (!this._selectedModule.locked) {
					$(Portal.MODULE_TAB_ID_PREFIX + this._selectedModule.id).down('img.moduleTab_remove_button').hide();
				}
				this._selectedModule.selected = false;
				if (this._selectedModule.selectedPage != null) {
					this._selectedModule.selectedPage.selected = false;
					this._selectedModule.selectedPage.dispose();
				}
				this._selectedModule.disposeContent();
			}
			$(Portal.MODULE_TAB_ID_PREFIX + module.id).addClassName('selected');
			$(Portal.MODULE_TAB_ID_PREFIX + module.id).down('img.moduleTab_corner_left').src = './portal/images/module/tab_selected_bg_left.gif';
			$(Portal.MODULE_TAB_ID_PREFIX + module.id).down('img.moduleTab_corner_right').src = './portal/images/module/tab_selected_bg_right.gif';
			/* locking */
			if (module.locked) {
				this._scrollMenu.hideAddPageAndCategory();
				var locking = $(Portal.MODULE_TAB_ID_PREFIX + module.id).down('img.moduleTab_locking_button');
				locking.show();	
				if (module.unlockable == true) {
					locking.addClassName('clickable');
					this._eventItems.push(this.observeEvent(locking, 'mouseover', this._moduleTabLockingMouseOver.bindAsEventListener(this)));
					this._eventItems.push(this.observeEvent(locking, 'mouseout', this._moduleTabLockingMouseOut.bindAsEventListener(this)));
				}
			} else {
				$(Portal.MODULE_TAB_ID_PREFIX + module.id).down('img.moduleTab_remove_button').show();
				if (!this._scrollMenu.isPageAndCategoryVisible()) {
					this._scrollMenu.showAddPageAndCategory();
				}
			}
			/* ------- */
			if (!module.locked) {
				$(Portal.MODULE_TAB_ID_PREFIX + module.id).down('img.moduleTab_remove_button').src = './portal/images/module/tab_selected_close_button.gif';
			}
			
			if (module.isAdmin) 
				this._scrollMenu.hideExportButton();
			else {
				this._scrollMenu.showExportButton();
				this._scrollMenu.setExportModuleLink(module.id, module.caption);
			}
			
			this._selectedModule = module;
			this._selectedModule.selected = true;
			module.load();
			module.displayPagesMenu();
		}
	},
	
	_moduleTabClicked: function(event) {
		var moduleID = Event.element(event).moduleID;	
		this.selectModule(moduleID);
	},
	
	_moduleTabRemoveButtonClicked: function(event) {
		//if (this._selectedModule != null && this._selectedModule.selectedPage != null && this._selectedModule.selectedPage.isLoading())
		//	return;
		this._moduleDomToDelete = Event.element(event).up('li');
		var module = this._modulesById.get(this._moduleDomToDelete.moduleID);
		if (confirm(this.getString('confirmBox_module_question', module.caption))) {
			var nbModule = 0;
			this._modulesById.each(function(m) {
				nbModule++;
			});
			var changeModule = false;
			if (this._moduleDomToDelete.hasClassName('selected')) {
				var changeModule = true;
			}
			var module = this._modulesById.get(Event.element(event).moduleID);
			/** APPLY REMOVEMODULE **/
			this.access.requestRemoveModule(module);
			/**************************/
			this._modulesById.unset(module.id);
			this._modulesByIndex.unset(module.index);		
			Utils.removeElement(this._moduleDomToDelete);
			this.updateTabListAfterDelete();
			if (nbModule <= 1) {
				if (this._selectedModule.selectedPage != null) {
					this._selectedModule.selectedPage.dispose();	
				}
				this._selectedModule.dispose();
				this._selectedModule = null;
				this._scrollMenu.hideAddPageAndCategory();
			}  else {
				if (changeModule) {
					this._selectedModule = null;
					this.selectModule(this._modulesByIndex.get(1).id);
				}
			}
			delete this._moduleDomToDelete;
			this.updateMenuSortable();
			this.adaptContainersSizes();
		}
	},
	
	_moduleTabLockingMouseOver: function(event) {
		Event.element(event).src = './portal/images/unlock_icon.gif';
	},
	
	_moduleTabLockingMouseOut: function(event) {
		Event.element(event).src = './portal/images/locked_icon.gif';
	},
	
	_moduleTabUnlock: function(event) {
		var module = this._modulesById.get(Event.element(event).moduleID);
		if (confirm(this.getString('confirmBox_unlock_module', module.caption))) {
			module.locked = false;
			module.activeDraggableMenu();
			Event.element(event).next('img').src= './portal/images/module/tab_selected_close_button.gif';
			Event.element(event).next('img').show();
			Event.element(event).hide();
			this._createRenameModuleTabEvent(Event.element(event).previous('span'));
			this._scrollMenu.showAddPageAndCategory();
			this._selectedModule.changePageMenuTooltips();
			this._selectedModule.activeRemovePageMenu();
			/** APPLY UNLOCKMODULE **/
			this.access.requestUnlockModule(module,  this._unlockModuleCallback.bind(this));
			/**************************/
		}		
	},
	
	_unlockModuleCallback: function(result) {
		this._selectedModule.unlockPages(result.unlockedPages);
	},
	
	_createRenameModuleTabEvent: function(currentTitleLi) {
		this._eventToDesactiveDuringModification.push(this.observeEvent(currentTitleLi, 'dblclick', this._moduleTabTitleDoubleClicked.bindAsEventListener(this))); 
	},
	
	updateTabListAfterDelete: function() {
		var sortableList = Sortable.serialize(this._tabsUl.id);
		var newModulesByIndex = new Hash();
		if (sortableList != '') {
			orderList = sortableList.split("&");
			for (var i = 0; i < orderList.length; i++) {
				var moduleId = orderList[i].substring(orderList[i].indexOf('=')+1);
				var aModule = this._modulesById.get(moduleId);
				aModule.index = i + 1;
				newModulesByIndex.set(i + 1, aModule);	
			}
			this._modulesByIndex = newModulesByIndex;
			delete newModulesByIndex;
			var jsonData = new Array();
			this._modulesById.each(function(module) {
				jsonData.push(module.value.getModuleHashForReorder());
			});
			jsonData = jsonData.flatten().toJSON();
			/** APPLY REORDERMODULES **/
			this.access.requestReorderModules(jsonData);
			/**************************/
		}
	},
	
	_moduleTabTitleDoubleClicked: function(event) {
		if (this._eventToDesactiveDuringModification != null) {
			for (var i=0; i< this._eventToDesactiveDuringModification.length; i++) {
				var toDelete = Object.clone(this._eventToDesactiveDuringModification[i])
				this.stopObservingEvent(toDelete); 
			}
		} 
		this._moduleTabIsRenamed = true;
		this.spanModify = Event.element(event);
		var module = this.spanModify.ancestors()[0];
		var modify = Element.extend(document.createElement('input'));
		modify.setAttribute('maxLength', 50);
		modify.addClassName('moduleModifyBox');
		modify.value = this.spanModify.innerHTML.unescapeHTML();
		this.spanModify.insert({ after: modify });	
		this.spanModify.hide();
		modify.activate();
		this._modificationEvents.push(this.observeEvent(modify, 'keypress', this._moduleTabModifyKeyPressed.bindAsEventListener(this)));
		this._modificationEvents.push(this.observeEvent(modify,'blur',this._moduleTabModifyBlur.bindAsEventListener(this))); 
	},
	
	_moduleTabModifyKeyPressed: function(event){
		if (event.keyCode == Event.KEY_RETURN) {
			var modify = Event.element(event);
			var value = modify.value.escapeHTML();
			if (this.formValidator.checkElement(value, FormValidator.TEXT) && modify.value != 'Administration') {
				this.spanModify.innerHTML = value;
				this.spanModify.show();
				this._modulesById.get(this.spanModify.up(0).moduleID).setCaption(value);
				for (var i=0; i<this._modificationEvents.length; i++)
					this.stopObservingEvent(this._modificationEvents[i]);
				this._modificationEvents.clear();
				if (this._eventToDesactiveDuringModification != null) {
					for (var i=0; i< this._eventToDesactiveDuringModification.length; i++) {
						var currentEventItem = this._eventToDesactiveDuringModification[i];
						this.observeEvent(currentEventItem.element, currentEventItem.eventType, currentEventItem.handler);
					}
				}
				this._moduleTabIsRenamed = false;
				Utils.removeElement(modify);
				delete this.spanModify;
			}
			else {
				alert(this.getString('invalid_module_name'));
				modify.activate();
			}
		}
		else 
			if (event.keyCode == Event.KEY_ESC) {
				var modify = Event.element(event);
				this.spanModify.show();
				Utils.removeElement(modify);
				delete this.spanModify;
				for (var i=0; i<this._modificationEvents.length; i++)
					this.stopObservingEvent(this._modificationEvents[i]);
				this._modificationEvents.clear();
				if (this._eventToDesactiveDuringModification != null) {
					for (var i=0; i< this._eventToDesactiveDuringModification.length; i++) {
						var currentEventItem = this._eventToDesactiveDuringModification[i];
						this.observeEvent(currentEventItem.element, currentEventItem.eventType, currentEventItem.handler); 
					}
				}
				this._moduleTabIsRenamed = false;
			}
	},
	
	_moduleTabModifyBlur: function(event) {
		var modify = Event.element(event);
		this.spanModify.show();
		Utils.removeElement(modify);
		delete this.spanModify;
		for (var i=0; i<this._modificationEvents.length; i++)
			this.stopObservingEvent(this._modificationEvents[i]);
		this._modificationEvents.clear();
		if (this._eventToDesactiveDuringModification != null) {
			for (var i=0; i< this._eventToDesactiveDuringModification.length; i++) {
				var currentEventItem = this._eventToDesactiveDuringModification[i];
				this.observeEvent(currentEventItem.element, currentEventItem.eventType, currentEventItem.handler);
			}
		}
		this._moduleTabIsRenamed = false;
	},
	
	setState: function(moduleID, pageID, title) {
		this.currentTitle = title;
		if (pageID == null) dhtmlHistory.add(moduleID+':0');
		else dhtmlHistory.add(moduleID+':'+pageID);
		setTimeout(this.setTitle.bind(this),0);
	},
	
	setTitle: function() {
		window.document.title = this.currentTitle;	
	},
	
	_onHistoryChanged: function(newLocation, historyData) {
		if (newLocation != null) {
	        var splits = newLocation.split(':');
	        var moduleID = splits[0];
	        if ($(Portal.MODULE_TAB_ID_PREFIX + moduleID) == null) { // a event is thrown when _relog
	        	return;
	        }
	        
	        var pageID = splits[1];
	        
	        if (this._selectedModule == null) {
	       		this.selectModule(moduleID);	
	        	this.initialPageID = pageID;	
	        }
	        else {
	        	if (this._selectedModule.id != moduleID) {
	        		this._selectedModule.selectedPage.removeCurrentDialogBox();
	        		this.initialPageID = pageID;
	        		this.selectModule(moduleID);		        		
	        	}	
	        	else {
	        		if (this._selectedModule.selectedPage == null) {
	        			this._selectedModule.selectPage(pageID);
	        		}
	        		else {
	        			if (this._selectedModule.selectedPage.id != pageID) {
	        				this._selectedModule.selectedPage.removeCurrentDialogBox();
		        			this._selectedModule.selectPage(pageID);
	        			}
	        		}
	        	}
	        }
		}
	},
	
	_onSelectedDateChanged: function(date) {
		this.setProperty('linkDate', date);
		if (this._selectedModule != null && this._selectedModule.selectedPage != null) {
			this._selectedModule.selectedPage.notify('dateChanged', date);
		}
	},
	
	_moveOnPreviousDays: function(){ 
		if (this._selectedModule != null && this._selectedModule.selectedPage != null) {
			this._selectedModule.selectedPage.notify('previousDays');
		}
	},
	
	_moveOnNextDays: function(){ 
		if (this._selectedModule != null && this._selectedModule.selectedPage != null) {
			this._selectedModule.selectedPage.notify('nextDays');
		}
	},
	
	_onSelectedOverviewPeriodChanged: function(stringDates) {
		this.setProperty('linkPeriod', stringDates);
	},
	
	_onSelectedEngineIdChanged: function(engineID) {
		this.setProperty('linkEngineID', engineID);
		if (this._selectedModule != null && this._selectedModule.selectedPage != null) {
			this._selectedModule.selectedPage.notify('engineChanged', engineID);
		}
	},
	
	setProperty: function(name, value) {
		this.properties.set(name, value);
	},
	
	_onEncodingReceived: function(encoding) {
		for (var i=0; i<encoding.length; i++) {
			this._preferences_encodingComboBox.options[this._preferences_encodingComboBox.options.length] = new Option(encoding[i], encoding[i]);
		}
	},
	
	_onPreferencesClicked: function() {
		if (this._selectedModule != null && this._selectedModule.selectedPage != null && this._selectedModule.selectedPage.isLoading())
			return;
		this._preferences_fullNameTextBox.value = this.userProfile.fullName.unescapeHTML();
		this._preferences_passwordTextBox.value = '';
		this._preferences_password2TextBox.value = '';
		this._preferences_errorMessage.innerHTML = '';
		this._preferences_separatorTextBox.value = this.userProfile.properties.separator;
		for (var i=0; i<this._preferences_encodingComboBox.options.length; i++) {
			if (this._preferences_encodingComboBox.options[i].value == this.userProfile.properties.encoding) {
				this._preferences_encodingComboBox.selectedIndex = i;
				break;
			}
		}
		
		/*var currentLanguage = this.userProfile.locale.split('_')[0];
		var currentCountry = this.userProfile.locale.split('_')[1];
		for (var i = 0; i < this._preferences_languageComboBox.options.length; i++) 
			if (this._preferences_languageComboBox.options[i].value == currentLanguage) {
				this._preferences_languageComboBox.options[i].selected = true;
				break;
			}
		*/

		this._preferencesDialog.focusOn(this._preferences_fullNameTextBox);
		this._preferencesDialog.show();		
	},
	
	onAddContentClicked: function() {
		this.library.toggle();
		this.userPanel.changeAddContentLabel(this.library.getIsOpen());
	},
	
	_onAddToPortalClicked: function(anItemId, aTypeID) {
		switch(aTypeID) {
		    case Library.MODULES_ITEM_ID :
		       	var params = new Object();
		       	params.itemID = anItemId;
		       	params.index = this._modulesByIndex.values().length + 1;
		       	this.access.requestLibraryAddModule(params, this._addModuleCallback.bind(this))
		        break;
		    case Library.DASHBOARDS_ITEM_ID :
				if (this._selectedModule != null && typeof this._selectedModule != 'undefined') {
		   			this._selectedModule.addPageFromLibrary(anItemId);
		  		} else {
		  			alert(this.getString('invalid_empty_add_page'));
		  		}	
		        break;
		    case Library.WIDGETS_ITEM_ID :
		    	if (this._selectedModule != null && typeof this._selectedModule != 'undefined') {
		    		if (this._selectedModule.selectedPage != null && typeof this._selectedModule.selectedPage != 'undefined') {
			    		this._selectedModule.selectedPage.addWidgetFromLibrary(anItemId);	
			    	} else {
			    		alert(this.getString('invalid_empty_add_widget'));
			    	}	
		    	} else {
		    		alert(this.getString('invalid_empty_add_widget'));
		    	}
		        break;
		}
	},
	
	_addModuleCallback: function(result) {
		var moduleToAdd = new Module(result, this);
		this._modulesById.set(moduleToAdd.id, moduleToAdd);
		this._modulesByIndex.set(moduleToAdd.index, moduleToAdd);
		this._addModuleTabToDom(moduleToAdd);
		this._applyTabSortable();
		this.selectModule(moduleToAdd.id);
	},
	
	_onPreferencesOkClicked: function() {
		if (!this.formValidator.checkElement(this._preferences_fullNameTextBox.value, FormValidator.TEXT)) {
			this._preferencesDialog.shake();
			this._preferences_errorMessage.innerHTML = this.getString('invalid_fullname');
			return;
		}
		if (this._preferencesPasswordEditNeeded()) {
			if (this._preferences_passwordTextBox.value != this._preferences_password2TextBox.value) {
				this._preferencesDialog.shake();
				this._preferences_errorMessage.innerHTML = this.getString('passwords_not_matching');
				return;
			}
		}
		if (this._preferences_separatorTextBox.value.length > 1) {
			this._preferencesDialog.shake();
			this._preferences_errorMessage.innerHTML = this.getString('invalid_csv_separator');
			return;
		}
		this._preferencesDialog.showWaiting();
		//var currentCountry = this.userProfile.locale.split('_')[1];
		//var newLocale = this._preferences_languageComboBox.options[this._preferences_languageComboBox.selectedIndex].value + '_' + currentCountry;
		this.userProfile.properties.separator = this._preferences_separatorTextBox.value;
		this.userProfile.properties.encoding = this._preferences_encodingComboBox.options[this._preferences_encodingComboBox.selectedIndex].value;
		this.access.requestEditUserProfile(this._preferences_fullNameTextBox.value.escapeHTML(), (this._preferencesPasswordEditNeeded() ? this._preferences_passwordTextBox.value : null), this.userProfile.locale, this.userProfile.properties, this._onPreferencesEdited.bind(this))
		//this._preferencesDialog.hide();
	},
	
	_onPreferencesEdited: function() {
		this.userProfile.fullName = this._preferences_fullNameTextBox.value.escapeHTML();
		this.userPanel.setFullName(this.userProfile.fullName.unescapeHTML());
		Table.updateCSVParameters(this.userProfile.properties.separator, this.userProfile.properties.encoding);
		this._preferencesDialog.hide();
	},
	
	_preferencesPasswordEditNeeded: function() {
		if (this.formValidator.checkElement(this._preferences_passwordTextBox.value, FormValidator.EMPTY) && this.formValidator.checkElement(this._preferences_fullNameTextBox.value, FormValidator.EMPTY)) {
		//if ((this._preferences_passwordTextBox.value == null || this._preferences_passwordTextBox.value.length == 0) && (this._preferences_password2TextBox.value == null || this._preferences_password2TextBox.value.length == 0)) {
			return false;
		}
		return true;
	},
	
	_onPreferencesCancelClicked: function() {
		this._preferencesDialog.hide();
	},
	
	_onExpansionClicked: function() {
		for (var i=0; i<this._expansionEventItems.length; i++)
			this.stopObservingEvent(this._expansionEventItems[i]);
		this._expansionEventItems = [];
		//get expansion button
		var expansionButton = this._csvParametersTitle.childElements()[0];
		expansionButton.src = './portal/images/reduction_button.jpg';
		this._expansionEventItems.push(this.observeEvent(expansionButton, 'click', this._onReductionClicked.bind(this)));
		this._csvSeparatorPanel.show();
		this._csvEncodingPanel.show();
		this._preferencesDialog.editHeight(285);
	},
		_onReductionClicked: function() {
		for (var i=0;i<this._expansionEventItems.length; i++)
			this.stopObservingEvent(this._expansionEventItems[i]);
		this._expansionEventItems = [];
		//get expansion button
		var expansionButton = this._csvParametersTitle.childElements()[0];
		expansionButton.src = './portal/images/expansion_button.jpg';
		this._expansionEventItems.push(this.observeEvent(expansionButton, 'click', this._onExpansionClicked.bind(this)));
		this._csvSeparatorPanel.hide();
		this._csvEncodingPanel.hide();
		this._preferencesDialog.editHeight(235);
	},
	
	_setupPreferencesDialog: function() {
		var root = Element.extend(document.createElement('div'));
			
		var usernamePanel = Element.extend(document.createElement('div'));
		usernamePanel.addClassName('portal_preferences_item');
		usernamePanel.appendChild(document.createTextNode(this.getString('preferences_username')+':'));
		//usernamePanel.appendChild(document.createTextNode(this.userProfile.username));
		var usernameTextBox = Element.extend(document.createElement('input'));
		usernameTextBox.type = 'text';
		usernameTextBox.addClassName('portal_preferences_textbox');
		usernameTextBox.value = this.userProfile.username;
		usernameTextBox.disabled = true;
		usernameTextBox.setAttribute('tabindex', -1);
		usernamePanel.appendChild(usernameTextBox);
		root.appendChild(usernamePanel);	
					
		var fullNamePanel = Element.extend(document.createElement('div'));
		fullNamePanel.addClassName('portal_preferences_item');
		fullNamePanel.appendChild(document.createTextNode(this.getString('preferences_fullname')+':'));
		var divFocusBugFullName = Element.extend(document.createElement('div'));
		divFocusBugFullName.setStyle({ overflow: 'auto', outline: 'none' });
		divFocusBugFullName.setAttribute('tabindex', -1);
		fullNamePanel.appendChild(divFocusBugFullName);
		this._preferences_fullNameTextBox = Element.extend(document.createElement('input'));
		this._preferences_fullNameTextBox.setAttribute('maxLength', 25);
		this._preferences_fullNameTextBox.type = 'text';
		this._preferences_fullNameTextBox.addClassName('portal_preferences_textbox');
		this._preferences_fullNameTextBox.setAttribute('tabindex', 1);
		this._eventItems.push(this.observeEvent(this._preferences_fullNameTextBox, 'keypress', this._onPreferencesKeyPressed.bind(this)));
		divFocusBugFullName.appendChild(this._preferences_fullNameTextBox);
		root.appendChild(fullNamePanel);
		
		var passwordPanel = Element.extend(document.createElement('div'));
		passwordPanel.addClassName('portal_preferences_item');
		passwordPanel.appendChild(document.createTextNode(this.getString('preferences_password')+':'));
		var divFocusBugPasswordText = Element.extend(document.createElement('div'));
		divFocusBugPasswordText.setStyle({ overflow: 'auto', outline: 'none' });
		divFocusBugPasswordText.setAttribute('tabindex', -1);
		passwordPanel.appendChild(divFocusBugPasswordText);
		this._preferences_passwordTextBox = Element.extend(document.createElement('input'));
		this._preferences_passwordTextBox.type = 'password';
		this._preferences_passwordTextBox.setAttribute('maxLength', 25);
		this._preferences_passwordTextBox.addClassName('portal_preferences_textbox');
		this._preferences_passwordTextBox.setAttribute('tabindex', 2);
		this._eventItems.push(this.observeEvent(this._preferences_passwordTextBox, 'keypress', this._onPreferencesKeyPressed.bind(this)));
		divFocusBugPasswordText.appendChild(this._preferences_passwordTextBox);
		root.appendChild(passwordPanel);
		
		var password2Panel = Element.extend(document.createElement('div'));
		password2Panel.addClassName('portal_preferences_item');
		password2Panel.appendChild(document.createTextNode(this.getString('preferences_password2')+':'));
		var divFocusBugPassword2Text = Element.extend(document.createElement('div'));
		divFocusBugPassword2Text.setStyle({ overflow: 'auto', outline: 'none' });
		divFocusBugPassword2Text.setAttribute('tabindex', -1);
		password2Panel.appendChild(divFocusBugPassword2Text);
		this._preferences_password2TextBox = Element.extend(document.createElement('input'));
		this._preferences_password2TextBox.setAttribute('maxLength', 25);
		this._preferences_password2TextBox.type = 'password';
		this._preferences_password2TextBox.addClassName('portal_preferences_textbox');
		this._preferences_password2TextBox.setAttribute('tabindex', 3);
		this._eventItems.push(this.observeEvent(this._preferences_password2TextBox, 'keypress', this._onPreferencesKeyPressed.bind(this)));
		divFocusBugPassword2Text.appendChild(this._preferences_password2TextBox);
		root.appendChild(password2Panel);
		
		this._csvParametersTitle = Element.extend(document.createElement('div'));
		this._csvParametersTitle.addClassName('portal_preferences_item');
		root.appendChild(this._csvParametersTitle);
		var expansionButton = new Element('img');
		expansionButton.addClassName('portal_preferences_expansionButton');
		expansionButton.id = 'preferences_expansion_button';
		expansionButton.src = './portal/images/expansion_button.jpg';
		this._expansionEventItems.push(this.observeEvent(expansionButton, 'click', this._onExpansionClicked.bind(this)));
		this._expansionEventItems.push(this.observeEvent(this._csvParametersTitle, 'click', this._onExpansionClicked.bind(this)));
		this._csvParametersTitle.appendChild(expansionButton);
		this._csvParametersTitle.appendChild(document.createTextNode(this.getString('csv_parameters')));
		this._csvSeparatorPanel = Element.extend(document.createElement('div'));
        this._csvSeparatorPanel.addClassName('portal_preferences_item');
        this._csvSeparatorPanel.addClassName('portal_indented_preferences_item')
        this._csvSeparatorPanel.appendChild(document.createTextNode(this.getString('csv_separator')+':'));
        this._preferences_separatorTextBox = Element.extend(document.createElement('input'));
        this._preferences_separatorTextBox.setAttribute('maxLength', 1);
		this._preferences_separatorTextBox.type = 'text';
        this._preferences_separatorTextBox.addClassName('portal_indented_preferences_textbox');
		this._preferences_separatorTextBox.setAttribute('tabindex', 4);
		this._eventItems.push(this.observeEvent(this._preferences_separatorTextBox, 'keypress', this._onPreferencesKeyPressed.bind(this)));
        this._csvSeparatorPanel.appendChild(this._preferences_separatorTextBox);
        root.appendChild(this._csvSeparatorPanel);
        this._csvSeparatorPanel.hide();
        this._csvEncodingPanel = Element.extend(document.createElement('div'));
        this._csvEncodingPanel.addClassName('portal_preferences_item');
        this._csvEncodingPanel.addClassName('portal_indented_preferences_item')
        this._csvEncodingPanel.appendChild(document.createTextNode(this.getString('csv_encoding')+':'));
        this._preferences_encodingComboBox = Element.extend(document.createElement('select'));
        this._preferences_encodingComboBox.addClassName('portal_indented_preferences_combobox');
		this._preferences_encodingComboBox.setAttribute('tabindex', 5);
        this._csvEncodingPanel.appendChild(this._preferences_encodingComboBox);
        root.appendChild(this._csvEncodingPanel);
        this._csvEncodingPanel.hide();
		
    	/*var languagePanel = Element.extend(document.createElement('div'));
        languagePanel.addClassName('portal_preferences_item');
        languagePanel.appendChild(document.createTextNode(this.getString('preferences_language')+':'));
        languagePanel.appendChild(document.createElement('br'));
        this._preferences_languageComboBox = Element.extend(document.createElement('select'));
        this._preferences_languageComboBox.addClassName('portal_preferences_combobox');
        this._preferences_languageComboBox.options[this._preferences_languageComboBox.options.length] = new Option(this.getString('preferences_english'), 'en');               
        this._preferences_languageComboBox.options[this._preferences_languageComboBox.options.length] = new Option(this.getString('preferences_french'), 'fr');               
        languagePanel.appendChild(this._preferences_languageComboBox);
        root.appendChild(languagePanel);*/
			
		this._preferences_errorMessage = Element.extend(document.createElement('div'));
		this._preferences_errorMessage.addClassName('portal_preferences_error');
		root.appendChild(this._preferences_errorMessage);
		
		var buttonsPanel = Element.extend(document.createElement('div'));
		buttonsPanel.addClassName('portal_preferences_buttons');
		var okButton = Element.extend(document.createElement('button'));
		okButton.addClassName('portal_button');
		okButton.addClassName('portal_preferences_okCancelbutton');
		okButton.setAttribute('tabindex', 5);
		okButton.innerHTML = this.getString('preferences_ok');
		
		this._eventItems.push(this.observeEvent(okButton, 'click', this._onPreferencesOkClicked.bind(this)));
		buttonsPanel.appendChild(okButton);			
		var cancelButton = Element.extend(document.createElement('button'));
		cancelButton.addClassName('portal_button');
		cancelButton.addClassName('portal_preferences_okCancelbutton');
		cancelButton.innerHTML = this.getString('preferences_cancel');
		cancelButton.setAttribute('tabindex', 6);
		this._eventItems.push(this.observeEvent(cancelButton, 'click', this._onPreferencesCancelClicked.bind(this)));
		buttonsPanel.appendChild(cancelButton);
		root.appendChild(buttonsPanel);
		this._preferencesDialog.setContent(this.getString('preferences_caption'), root, 205, 235);	
	},
	
	_onPreferencesKeyPressed: function(event) {
		if (event.keyCode == Event.KEY_RETURN) {
			this._onPreferencesOkClicked();
		}
		if (event.keyCode == Event.KEY_ESC) {
			this._onPreferencesCancelClicked();
		}
	},

	getString: function(stringID) {
		var parameters = new Array();
		if (arguments.length > 1) {
			for (var i=1; i<arguments.length; i++) {
				parameters.push(arguments[i]);
			}
		}
		return this.languageManager.getPortalString(stringID, parameters);
	},
	
	registerWidgetWithChart: function(widget) {
		this._widgetsWithChartsByID.set(widget.getWidgetID(), widget);
	},
	
	unregisterWidgetWithChart: function(widget) {
		this._widgetsWithChartsByID.unset(widget.getWidgetID());
	},
	
	setLoadingCursor: function(loading) {
		if (loading)
			this._globalContainerElement.addClassName('loading');
		else 
			this._globalContainerElement.removeClassName('loading');
	},
	
	showCharts: function() {		
		var widgets = this._widgetsWithChartsByID.values();
		for (var i = 0; i < widgets.length; i++) 
			widgets[i].showCharts();
	},
	
	hideCharts: function() {
		var widgets = this._widgetsWithChartsByID.values();
		for (var i = 0; i < widgets.length; i++) 
			widgets[i].hideCharts();
	},
	
	observeEvent: function(element, eventName, handler) {
		return EventHandler.add(element, eventName, handler);
	},
	
	stopObservingEvent: function(eventItem) {
		EventHandler.remove(eventItem);
	},
	
	_onWindowUnload: function() {
		this._disposeContent();
		this._removeGlobalContainer();
	},
	
	_disposeContent: function() {
		if (this._eventItems != null) {
			for (var i=0; i<this._eventItems.length; i++)
				this.stopObservingEvent(this._eventItems[i]);
			this._eventItems.clear();
		}
		if (this._modificationEvents != null) {
			for (var i=0; i<this._modificationEvents.length; i++)
				this.stopObservingEvent(this._modificationEvents[i]);
			this._modificationEvents.clear();
		}
		if (this._eventToDesactiveDuringModification != null) {
			for (var i=0; i< this._eventToDesactiveDuringModification.length; i++) {
				this.stopObservingEvent(this._eventToDesactiveDuringModification[i]); 
			}
			this._eventToDesactiveDuringModification.clear();
		}
		if (this._selectedModule != null && this._selectedModule.selectedPage != null) { 
			this._selectedModule.selectedPage.dispose();
			this._selectedModule.dispose();
		}
		this._selectedModule = null;
		if (this.userPanel != null)
			this.userPanel.dispose();
		this.userPanel = null;
		if (this._scrollMenu != null)
			this._scrollMenu.dispose();
		this._scrollMenu = null;
		if (this.library != null)
			this.library.dispose();
		this.library = null;
		if (this._preferencesDialog != null)
			this._preferencesDialog.dispose();
		this._preferencesDialog = null;
	},
	
	setExportPageLink: function(pageID, pageCaption) {
		this._scrollMenu.setExportPageLink(pageID, pageCaption);
	},
	
	showExportButton: function() {
		this._scrollMenu.showExportButton();
	},
	
	hideExportButton: function() {
		this._scrollMenu.hideExportButton();
	}
	
});

Portal.WIDGETS_DIR = 'PortalServlet/';
Portal.PORTAL_SCRIPTS_DIR = './portal/js/';
Portal.PORTAL_CSS_DIR = './portal/css/';
Portal.PORTAL_IMAGES_DIR = './portal/images/';
Portal.COMPONENTS_DIR = './components/';
Portal.MODULE_TAB_ID_PREFIX = 'moduleTab_';
Portal.SCRIPT_FILES_TO_LOAD = [Portal.PORTAL_SCRIPTS_DIR+'access/Access.js', 
								Portal.PORTAL_SCRIPTS_DIR+'widget/Widget.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/EventHandler.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/CSSLoader.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/ImagePreloader.js',
								Portal.PORTAL_SCRIPTS_DIR+'internationalization/LanguageLoader.js', 
								Portal.PORTAL_SCRIPTS_DIR+'internationalization/LanguageManager.js',  
								Portal.PORTAL_SCRIPTS_DIR+'access/AjaxRequest.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/Module.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/Library.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/LibraryMenu.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/ScrollMenu.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/Page.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/WidgetsRow.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/LoginDialog.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/UserPanel.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/Utils.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/Mutex.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/Tooltip.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/DialogBox.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/FlexCallbackManager.js',
								Portal.PORTAL_SCRIPTS_DIR+'portal/Gripper.js', 
								Portal.PORTAL_SCRIPTS_DIR+'portal/PageMenuObserver.js',
								Portal.PORTAL_SCRIPTS_DIR+'indicators/DimensionsHandler.js',
								Portal.COMPONENTS_DIR+'calendar/js/Calendar.js',
								Portal.COMPONENTS_DIR+'enginesCompute/js/EnginesCompute.js',
								Portal.COMPONENTS_DIR+'stateCompute/js/StateCompute.js',
								Portal.COMPONENTS_DIR+'widgetToolBar/js/WidgetToolBar.js',
								Portal.COMPONENTS_DIR+'table/js/Table.js',	
								Portal.COMPONENTS_DIR+'table/js/TableOld.js',
								Portal.COMPONENTS_DIR+'textEditor/js/TextEditor.js',
								Portal.COMPONENTS_DIR+'engineSelection/js/EngineSelection.js',
								Portal.COMPONENTS_DIR+'timeSerieChart/js/TimeSerieChart.js'];							
Portal.SCRIPT_OBJECTS_TO_LOAD = ['Access', 'Widget', 'CSSLoader', 'ImagePreloader', 'LanguageLoader', 'LanguageManager', 'AjaxRequest', 'Module', 'Library', 'LibraryMenu','ScrollMenu', 'Page', 'WidgetsRow', 'Gripper', 'PageMenuObserver', 'LoginDialog', 'UserPanel', 'Utils', 'Mutex', 'Tooltip', 'DialogBox', 'FlexCallbackManager', 'DimensionsHandler', 'Table', 'TableOld', 'WidgetToolBar', 'EngineSelection'];
Portal.CSS_TO_LOAD = [Portal.PORTAL_CSS_DIR+'portal.css', Portal.PORTAL_CSS_DIR+'library.css', Portal.PORTAL_CSS_DIR+'widget.css', Portal.PORTAL_CSS_DIR+'drag-drop-tree.css', Portal.COMPONENTS_DIR+'calendar/css/calendar.css', Portal.COMPONENTS_DIR+'widgetToolBar/css/widgetToolBar.css', Portal.COMPONENTS_DIR+'table/css/table.css', Portal.COMPONENTS_DIR+'table/css/tableOld.css', Portal.COMPONENTS_DIR+'enginesCompute/css/enginesCompute.css', Portal.COMPONENTS_DIR+'stateCompute/css/stateCompute.css', Portal.COMPONENTS_DIR+'engineSelection/css/engineSelection.css', Portal.COMPONENTS_DIR+'textEditor/css/textEditor.css', Portal.COMPONENTS_DIR+'timeSerieChart/css/timeSerieChart.css'];
Portal.TOP_OFFSET_CALENDAR = 20;
Portal.OFFSET_COPYRIGHT = 20;
Portal.LOCALE_COOKIE_NAME = 'NEXThinkPortal-Locale';
Portal.DEFAULT_CSV_SEPARATOR = ';';
Portal.DEFAULT_CSV_ENCODING = 'ISO-8859-1';
