function UbpMarketClass() {
	var TAB_CLASS = 'tab';
	var TAB_ACTIVE_CLASS = 'active';
	var COL_MIN_HEIGHT = 376;
	
	var refreshDelay = 60000; //not loaded from context
	
	var REFRESH_DELAY = refreshDelay;
	var AJAX_URL = context + "/cache/bypass/template/ubpmarket_boxcontent.jsp";
	var BOX_MENU_MIN_CONTENT= '&nbsp;';
	var BOX_MENU_MIN_CLASS = 'min';
	var BOX_MENU_MAX_CONTENT = '&nbsp;';
	var BOX_MENU_MAX_CLASS = 'max';
	var BOX_MENU_REMOVE_CONTENT = '&nbsp;';
	var BOX_MENU_REMOVE_CLASS = 'remove';
	var BOX_MENU_DROPDOWN_LINK = '&nbsp;';
	var BOX_MENU_DROPDOWN_DATA_TEXT = 'data hide/show';
	var BOX_MENU_DROPDOWN_QUOTES_TEXT = 'quotes hide/show';
	var BOX_MENU_DROPDOWN_CHART_TEXT = 'chart hide/show';	
	
	var BOX_MENU_CHART_OPTION1_LABEL = 'Today';
	var BOX_MENU_CHART_OPTION1_VALUE = 'AVAIL';
	var BOX_MENU_CHART_OPTION2_LABEL = 'Last 3 months';
	var BOX_MENU_CHART_OPTION2_VALUE = 'MONTH3';
	var BOX_MENU_CHART_OPTION3_LABEL = 'Last year';
	var BOX_MENU_CHART_OPTION3_VALUE = 'YEAR1';
	var BOX_MENU_CHART_OPTION4_LABEL = 'Last 5 years';
	var BOX_MENU_CHART_OPTION4_VALUE = 'YEAR5';
	
	this.activeTab = 0;
	
	this.profile = {
		tabs: []
	};
	
	this.loadProfile = function() {
		//console.log("loadProfile");
		UBPMAjax.loadFullProfile(function(profileStr) {
			getUbpMarket().callbackLoadProfile(profileStr);
		});
	};
	
	this.callbackLoadProfile = function(profile) {
		//console.log("callbackLoadProfile");
		this.profile = jQuery.secureEvalJSON(profile);
		this.refreshTabMenu();
		this.refreshTab();
		this.updateTask();
	};
	
	this.refreshTabMenu = function() {
		//console.log("refreshTabMenu");
		jQuery('#tabs').append().html(this.renderTabMenu());
		this.registerTabMenuAction();
	};
	
	this.renderTabMenu = function() {
		//console.log("renderTabMenu");
		var tabMenuHtml = [];
		
		for (var tabIndex = 0; tabIndex < this.profile.tabs.length; tabIndex++) {
			var currentTab = this.profile.tabs[tabIndex];
			var tabMenuItemClass = TAB_CLASS;
			if (tabIndex == this.activeTab) {
				tabMenuItemClass += ' ' + TAB_ACTIVE_CLASS;
			}
			
			tabMenuHtml[tabMenuHtml.length] = '<a href="#'+currentTab.tabid+'" ';
			tabMenuHtml[tabMenuHtml.length] =  		'tabid="'+tabIndex+'" ';
			tabMenuHtml[tabMenuHtml.length] =  		'class="'+tabMenuItemClass+'" ';
			tabMenuHtml[tabMenuHtml.length] =  		'title="">';
			tabMenuHtml[tabMenuHtml.length] = 	currentTab.name;
			tabMenuHtml[tabMenuHtml.length] = '</a>';
		}
		
		// Uncomment to activate addTab link
		//tabMenuHtml[tabMenuHtml.length] = '<a href="#addTab" id="addTab" title="add new tab">+</a>';
		
		return tabMenuHtml.join("");
	};
	
	this.registerTabMenuAction = function() {
		//console.log("registerTabMenuAction");
		var tabs = jQuery("#tabs a.tab");
		tabs.click(function() {
			var selectedTab = jQuery(this);
			tabs.removeClass(TAB_ACTIVE_CLASS);
			selectedTab.addClass(TAB_ACTIVE_CLASS);
			getUbpMarket().activeTab = selectedTab.attr('tabid');
			getUbpMarket().refreshTab();
			getUbpMarket().refreshBoxes();
		});
	};
	
	this.refreshTab = function() {
		//console.log("refreshTab");
		jQuery('div#cols').html(this.renderTab(this.activeTab));
		
		//hover titre
		jQuery('.col .ui-dialog-titlebar').hover(
			function () {
				jQuery(this).addClass('ui-hover-state');
				jQuery(this).find('span.hidder').fadeIn('fast');
		    }, 
		    function () {
		        jQuery(this).removeClass('ui-hover-state');
		        jQuery(this).find('span.hidder').fadeOut('fast');           
		    }
		);
		
		//showHide Drop Down
		jQuery('span.dropDown a.dropDown').click(function() {
			//jQuery('span.dropDown > ul:visible').fadeOut();				
			jQuery(this).parent().find('> ul:hidden').fadeIn();
		});

		jQuery('span.options ul.dropDownUl').bind("mouseleave",function(){
			jQuery('span.dropDown ul').fadeOut();
		});
		
		//showHide chartAction menu
		jQuery('span.options ul.dropDownUl li.chart').hover( 
			function () {
			jQuery(this).find('ul').show();
			},
			function () {
				jQuery(this).find('ul').hide();
			}
		);
		
		if (this.profile.tabs[this.activeTab].tabid == "tab5") {
			getUbpMarketSearch().actionShowSearch();
		} else {
			getUbpMarketSearch().actionHideSearch();
		}
		
		this.updateColsHeight();
		
		makeSortable();
	};
	
	this.renderTab = function(tabIndex) {
		//console.log("renderTab");
		var currentTab = this.profile.tabs[tabIndex];
		var tabHtml = [];
		for (var colIndex = 0; colIndex < currentTab.cols.length; colIndex++) {
			var currentCol = currentTab.cols[colIndex];
			var colClass = "col evenCol";
			if (colIndex % 2 == 0) colClass = "col oddCol";
			tabHtml[tabHtml.length] = '<div id="'+currentCol.colid+'" class="'+colClass+'">';
			tabHtml[tabHtml.length] = 	this.renderCol(tabIndex, colIndex);
			tabHtml[tabHtml.length] = '</div>';
		}
		
		return tabHtml.join("");
	};
	
	this.renderCol = function(tabIndex, colIndex) {
		//console.log("renderCol");
		var currentCol = this.profile.tabs[tabIndex].cols[colIndex];
		var colHtml = [];
		for (var boxIndex = 0; boxIndex < currentCol.boxes.length; boxIndex++) {
			var currentBox = currentCol.boxes[boxIndex];
			
			boxClass = ' max';
			if (currentBox.disp[0].state == 'min'){
				boxClass = ' min';
			}
			
			colHtml[colHtml.length] = '<dl id="box'+currentBox.id+'" class="ui-dialog-container'+boxClass+'">';
			colHtml[colHtml.length] = 	'<dt class="ui-dialog-titlebar">';
			colHtml[colHtml.length] = 		currentBox.title;
			colHtml[colHtml.length] = 		this.renderBoxMenu(tabIndex, colIndex, boxIndex);
			colHtml[colHtml.length] = 	'</dt>';
			colHtml[colHtml.length] = 	'<dd></dd>';
			colHtml[colHtml.length] = '</dl>';
		}
		
		return colHtml.join("");
	};
	
	this.renderBoxMenu = function(tabIndex, colIndex, boxIndex) {
		//console.log("renderBoxMenu");
		var currentBox = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex];
		var boxMenuHtml = [];
		
		var boxMenuContent = BOX_MENU_MIN_CONTENT;
		var boxMenuClass = BOX_MENU_MIN_CLASS;
		if (currentBox.disp[0].state == 'min'){
			boxMenuContent = BOX_MENU_MAX_CONTENT;
			boxMenuClass = BOX_MENU_MAX_CLASS;
		}
		
		boxMenuHtml[boxMenuHtml.length] = '<span class="options">';
		boxMenuHtml[boxMenuHtml.length] =	 '<span class="dropDown">';
		boxMenuHtml[boxMenuHtml.length] = 		this.renderBoxMenuDropDown(tabIndex, colIndex, boxIndex);
		boxMenuHtml[boxMenuHtml.length] = 	'</span>';
		boxMenuHtml[boxMenuHtml.length] =	 '<a class="expand '+boxMenuClass+'" title="minimize/maximize" href="javascript:getUbpMarket().actionToggleBox('+tabIndex+', '+colIndex+', '+boxIndex+')">';
		boxMenuHtml[boxMenuHtml.length] =	 	boxMenuContent;
		boxMenuHtml[boxMenuHtml.length] =	 '</a>';
		boxMenuHtml[boxMenuHtml.length] =	 '<a class="'+BOX_MENU_REMOVE_CLASS+'" title="remove box" href="javascript:getUbpMarket().actionRemoveBox('+tabIndex+', '+colIndex+', '+boxIndex+')">';
		boxMenuHtml[boxMenuHtml.length] =	 	BOX_MENU_REMOVE_CONTENT;
		boxMenuHtml[boxMenuHtml.length] =	 '</a>';
		boxMenuHtml[boxMenuHtml.length] = '</span>';
		
		return boxMenuHtml.join("");
	};
	
	this.renderBoxMenuDropDown = function(tabIndex, colIndex, boxIndex) {
		//console.log("renderBoxMenuDropDown");
		var currentBox = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex];
		var html = [];
		
		html[html.length] = '<a class="dropDown" href="#dropDown">';
		html[html.length] = 	BOX_MENU_DROPDOWN_LINK;
		html[html.length] = '</a>';
		html[html.length] = '<ul class="dropDownUl" style="display:none;">';
		html[html.length] = 	'<li>';
		html[html.length] = 		'<a class="data" title="'+BOX_MENU_DROPDOWN_DATA_TEXT+'" href="javascript:getUbpMarket().actionToggleData('+tabIndex+', '+colIndex+', '+boxIndex+')">';
		html[html.length] = 			BOX_MENU_DROPDOWN_DATA_TEXT;
		html[html.length] = 		'</a>';
		html[html.length] = 	'</li>';
		html[html.length] = 	'<li>';
		html[html.length] = 		'<a class="quotes" title="'+BOX_MENU_DROPDOWN_QUOTES_TEXT+'" href="javascript:getUbpMarket().actionToggleQuotes('+tabIndex+', '+colIndex+', '+boxIndex+')">';
		html[html.length] = 			BOX_MENU_DROPDOWN_QUOTES_TEXT;
		html[html.length] = 		'</a>';
		html[html.length] = 	'</li>';
		html[html.length] = 	'<li class="chart">';
		html[html.length] = 		'<a chartParam="'+BOX_MENU_DROPDOWN_CHART_TEXT+'" href="javascript:getUbpMarket().actionToggleChart('+tabIndex+', '+colIndex+', '+boxIndex+')">';
		html[html.length] = 			BOX_MENU_DROPDOWN_CHART_TEXT;
		html[html.length] = 		'</a>';
		html[html.length] = 		'<ul class="chartOptions" style="display:none;">';
		html[html.length] = 			'<li>';
		html[html.length] = 				'<a chartParam="'+BOX_MENU_CHART_OPTION1_VALUE+'" href="javascript:getUbpMarket().actionSetChartPeriod('+tabIndex+', '+colIndex+', '+boxIndex+', \''+BOX_MENU_CHART_OPTION1_VALUE+'\')">';
		html[html.length] = 					BOX_MENU_CHART_OPTION1_LABEL;
		html[html.length] = 				'</a>';
		html[html.length] = 			'</li>';
		html[html.length] = 			'<li>';
		html[html.length] = 				'<a chartParam="'+BOX_MENU_CHART_OPTION2_VALUE+'" href="javascript:getUbpMarket().actionSetChartPeriod('+tabIndex+', '+colIndex+', '+boxIndex+', \''+BOX_MENU_CHART_OPTION2_VALUE+'\')">';
		html[html.length] = 					BOX_MENU_CHART_OPTION2_LABEL;
		html[html.length] = 				'</a>';
		html[html.length] = 			'</li>';
		html[html.length] = 			'<li>';
		html[html.length] = 				'<a chartParam="'+BOX_MENU_CHART_OPTION3_VALUE+'" href="javascript:getUbpMarket().actionSetChartPeriod('+tabIndex+', '+colIndex+', '+boxIndex+', \''+BOX_MENU_CHART_OPTION3_VALUE+'\')">';
		html[html.length] = 					BOX_MENU_CHART_OPTION3_LABEL;
		html[html.length] = 				'</a>';
		html[html.length] = 			'</li>';
		html[html.length] = 			'<li>';
		html[html.length] = 				'<a chartParam="'+BOX_MENU_CHART_OPTION4_VALUE+'" href="javascript:getUbpMarket().actionSetChartPeriod('+tabIndex+', '+colIndex+', '+boxIndex+', \''+BOX_MENU_CHART_OPTION4_VALUE+'\')">';
		html[html.length] = 					BOX_MENU_CHART_OPTION4_LABEL;
		html[html.length] = 				'</a>';
		html[html.length] = 			'</li>';
		html[html.length] = 		'</ul>'
		html[html.length] = 	'</li>'
		html[html.length] = '</ul>';
		
		return html.join("");
	};
	
	
	this.actionToggleBox = function(tabIndex, colIndex, boxIndex) {
		// update profile (temporaty only local)
		if (this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].disp[0].state == "min") {
			this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].disp[0].state = "max";
		} else {
			this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].disp[0].state = "min";
		}
		
		// update dom
		var boxId = "#box" + this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].id;
		jQuery(boxId).removeClass("max").removeClass("min").addClass(this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].disp[0].state);
		this.refreshBox(tabIndex, colIndex, boxIndex);
		
		// update profile
		var id = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].id;
		UBPMAjax.updateBoxPropMinMax(id,
			function(profile){
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
			}
		);
	};
	
	this.actionMoveBox = function(boxId, colId, previousBoxId) {
		UBPMAjax.moveBox(boxId, colId, previousBoxId,
			function(profile){
				//getUbpMarket().callbackLoadProfile(profile);
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
				getUbpMarket().refreshTab();
				getUbpMarket().refreshBoxes();
			}
		);
	};
	
	this.actionRemoveBox = function(tabIndex, colIndex, boxIndex) {
		var id = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].id;
		
		UBPMAjax.removeBox(id,
			function(profile){
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
				getUbpMarket().refreshTab();
				getUbpMarket().refreshBoxes();
			}
		);
	};
	
	this.actionAddBox = function(tkvalor, title, tabid, colid) {
		UBPMAjax.addBoxToProfile(
			tkvalor,
			title,
			tabid,
			colid,
			'true',
			function(profile){
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
				getUbpMarket().refreshTab();
				getUbpMarket().refreshBoxes();
			}
		);
	}
	
	this.actionToggleData = function(tabIndex, colIndex, boxIndex) {
		var id = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].id;
		UBPMAjax.updateDataDisplay(id,
			function(profile){
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
				getUbpMarket().refreshBox(tabIndex, colIndex, boxIndex);
			}
		);
	};
	
	this.actionToggleQuotes = function(tabIndex, colIndex, boxIndex) {
		var id = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].id;
		UBPMAjax.updateQuotesDisplay(id,
			function(profile){
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
				getUbpMarket().refreshBox(tabIndex, colIndex, boxIndex);
			}
		);
	};
	
	this.actionToggleChart = function(tabIndex, colIndex, boxIndex) {
		var id = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].id;
		UBPMAjax.updateChartDisplay(id,
			function(profile){
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
				getUbpMarket().refreshBox(tabIndex, colIndex, boxIndex);
			}
		);
	};
	
	this.actionSetChartPeriod = function(tabIndex, colIndex, boxIndex, period) {
		var id = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex].id;
		UBPMAjax.updateChartPeriod(id, period,
			function(profile){
				getUbpMarket().profile = jQuery.secureEvalJSON(profile);
				getUbpMarket().refreshBox(tabIndex, colIndex, boxIndex);
			}
		);
	};
	
	this.refreshBoxes = function() {
		//console.log("refreshBoxes");
		var currentTab = this.profile.tabs[this.activeTab];
		for (var colIndex = 0; colIndex < currentTab.cols.length; colIndex++) {
			currentCol = currentTab.cols[colIndex];
			for (var boxIndex = 0; boxIndex < currentCol.boxes.length; boxIndex++) {
				currentBox = currentCol.boxes[boxIndex];
				if (currentBox.disp[0].state != "min") {
					this.refreshBox(this.activeTab, colIndex, boxIndex);
				}
			}
		}
	};
	
	this.refreshBox = function(tabIndex, colIndex, boxIndex) {
		//console.log("refreshBox");
		var currentBox = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex];
		jQuery.ajax({
			type: "GET",
			url: AJAX_URL,
			data: 'id=' + currentBox.id + '&ts=' + new Date().getTime(),
			cache: true,
			success: function(html) {
				getUbpMarket().callbackRefreshBox(tabIndex, colIndex, boxIndex, html);
			}
		});
	};
	
	this.callbackRefreshBox = function(tabIndex, colIndex, boxIndex, html) {
		//console.log("callbackRefreshBox");
		var currentBox = this.profile.tabs[tabIndex].cols[colIndex].boxes[boxIndex];
		var boxContent = jQuery("#box" + currentBox.id + " dd");
		boxContent.unbind(); // unbind oll event on old dom object
		boxContent.html(html);
		this.updateColsHeight();
	}
	
	this.updateTask = function() {
		//console.log("updateTask");
		this.refreshBoxes();
		setTimeout("getUbpMarket().updateTask()", REFRESH_DELAY);
	};
	
	this.updateColsHeight = function() {
		//console.log("updateColsHeight");
		jQuery('#cols div.col').equalHeight(COL_MIN_HEIGHT);
	};
}

//return single instance of ubp market (usefull from callback functions)
ubpMarket = "";
function getUbpMarket() {
	// create singleton if required
	if (ubpMarket == "") {
		ubpMarket = new UbpMarketClass();	
	}
	return ubpMarket;
}

jQuery(document).ready(function() {
	getUbpMarket().loadProfile();
});

function UbpMarketSearchClass() {
	this.init = function() {
		this.registerSearchEvent();
	}
	
	this.registerSearchEvent = function() {
		jQuery('#ubpmarket_form .btn_submit').click(function(){
			return getUbpMarketSearch().actionDoSearch();
		});
		jQuery('#searchinput').keypress(function(e){
			if(e.which==13) {
				getUbpMarketSearch().actionDoSearch();
				return false;
			}
		});
		jQuery('#ubpmarket_form .btn_reset').click(function(){
			return getUbpMarketSearch().actionHideSearchResult();
		});
		
		jQuery('#ubpmarket_form_result .btn_add').click(function(){
			return getUbpMarketSearch().actionAddBox();
		});
	}
	
	this.registerSearchResponseEvent = function() {
		jQuery('#ubpmarket_form_result #results > li').click(function() {
			jQuery('#ubpmarket_form_result #results > li').removeClass("selected");
			jQuery(this).addClass("selected");
		});
		jQuery('#ubpmarket_form_result #results > li').dblclick(function() {
			return getUbpMarketSearch().actionAddBox();
		});
	}
	
	this.actionDoSearch = function() {
		if (!jQuery('#search_form').valid()) return false;
		this.search(1);
	}
	
	this.actionShowSearch = function() {
		jQuery('#ubpmarket_form').show();
	}
	
	this.actionShowSearchResult = function() {
		jQuery('#ubpmarket_form').show();
		jQuery('#ubpmarket_form_result').show();
	}
	
	this.actionHideSearch = function() {
		jQuery('#ubpmarket_form').hide();
		jQuery('#ubpmarket_form_result').hide();
	}
	
	this.actionHideSearchResult = function() {
		jQuery('#ubpmarket_form_result').hide();
	}
	
	this.actionAddBox = function() {
		var selectedLi = jQuery('#ubpmarket_form_result #results > li.selected');
		if (selectedLi.length == 1){
			// add the new box
			
			var tkvalor = jQuery('td.tkvalor', selectedLi).html();
			var title = jQuery('td.col_Name', selectedLi).html();
			var tabid = getUbpMarket().profile.tabs[getUbpMarket().activeTab].tabid;			
			var colid = getUbpMarket().profile.tabs[getUbpMarket().activeTab].cols[0].colid;
			getUbpMarket().actionAddBox(tkvalor, title, tabid, colid);
		}
	}
	
	this.getSearch = function() {
		return jQuery('#searchinput').val();
	}
	
	this.getFormat = function() {
		// fix missing default value on ie after a form reset
		if (!jQuery("#format option:selected").length) {
			jQuery("#format option[value='all']").attr('selected', 'selected');
		}
		
		return jQuery('#format option:selected').val();
	}
	
	this.getSecurityCodes = function() {
		var securitycodes = '';
		var instruments = jQuery('#ubpmarket_form input[name="instruments"]:checked');	
		instruments.each(function(i){
			securitycodes += instruments[i].value+';';
		});
		return securitycodes;
	}
	
	this.getMarketCode = function() {
		// fix missing default value on ie after a form reset
		if (!jQuery("#boursecode option:selected").length) {
			jQuery("#boursecode option[value='all']").attr('selected', 'selected');
		}
		
		return jQuery('#boursecode option:selected').val();
	}
	
	this.search = function(page) {
		this.offset = (page - 1) * resultsPerPage;
		
		jQuery('#ubpmarket_form_result li:not(.spinner)').remove();
		jQuery('#ubpmarket_form_result li.spinner').show();
		jQuery('#ubpmarket_form_result form div.results').html("");
		jQuery('#ubpmarket_form_result form div.pagination').html("");
		
		jQuery('#ubpmarket_form_result').show();
		
		var format = this.getFormat();
		var search = this.getSearch();
		var securitycodes = this.getSecurityCodes();
		var marketCode = this.getMarketCode();
		var offset = this.offset;
		
		UBPMAjax.doSearch(format, search, securitycodes, marketCode, offset, 
			{
				callback: function(response){ 		
					getUbpMarketSearch().searchCallback(response);
				},
				errorHandler: function(message, exception) {
					getUbpMarketSearch().searchCallbackError(message, exception);
				}
			}
		);
	}
	
	this.searchCallback = function(response) {
		response = jQuery.secureEvalJSON(response);
		
		jQuery('#results').append(this.renderSearchResult(response));
		this.registerSearchResponseEvent();
		
		if (response.total == 1) {
			jQuery('#ubpmarket_form_result form div.results').html(response.total + ' result');
		} else if (response.total > 1) {
			jQuery('#ubpmarket_form_result form div.results').html(response.total + ' results');
		} else {
			jQuery('#ubpmarket_form_result form div.results').html('No result');
		}
		jQuery('#ubpmarket_form_result form div.pagination').html(this.renderPagination(this.offset, response.results.length, response.total, resultsPerPage));
		
		jQuery('#ubpmarket_form_result li.spinner').hide();
	}
	
	this.searchCallbackError = function(message, exception) {
		jQuery('#ubpmarket_form_result form div.results').html('Error');
		jQuery('#ubpmarket_form_result li.spinner').hide();
	}
	
	this.renderSearchResult = function(response) {
		var html = [];
		
		if (response.results.length > 0){	
			for (var resultIndex = 0; resultIndex < response.results.length; resultIndex++) {
				var result = response.results[resultIndex];
				
				html[html.length] = '<li>';
				html[html.length] = 	'<table cellpadding="0" cellspacing="0" width="100%">';
				html[html.length] = 		'<tr>';
				html[html.length] = 			'<td class="col_Name">';
				html[html.length] = 				result.Name;
				if (ubpmarketdebugenable) {
					html[html.length] = 				" (" + result.tkvalor + ")";
				}
				html[html.length] = 			'</td>';
				html[html.length] = 			'<td class="col_Market">';
				html[html.length] = 				result.BC;
				html[html.length] = 			'</td>';
				html[html.length] = 			'<td class="col_Type">';
				html[html.length] = 				result.SC;
				html[html.length] = 			'</td>';
				html[html.length] = 			'<td>';
				html[html.length] = 				result.ISIN;
				html[html.length] = 			'&nbsp;</td>';
				html[html.length] = 			'<td class="tkvalor" style="display:none;">';
				html[html.length] = 				result.tkvalor;
				html[html.length] = 			'</td>';
				html[html.length] = 		'</tr>';
				html[html.length] = 	'</table>';
				html[html.length] = '</li>';
			}
			
			//printPaginator(availableResults, totalResults, offset);			
			
		}
		
		return html.join("");
	}
	
	this.renderPagination = function(resultStart, resultCount, totalResult, resultPerPage) {
		var html = [];
		
		// print the paginator only if we have more than one page
		if (resultPerPage > totalResult) return "";
		
		var firstPage = 1;
		var lastPage = Math.ceil(totalResult / resultPerPage);
		var currentPage = Math.ceil(resultStart / resultPerPage) + 1;	
		
		if (currentPage > firstPage + 3) {
			html[html.length] = this.renderPaginationLink(1, "First&nbsp;", false);
		}
		
		if (currentPage != firstPage) {
			html[html.length] = this.renderPaginationLink(currentPage - 1, "Previous&nbsp;", false);
		}
		
		for (var page = currentPage - 3; page <= currentPage + 3; page++) {	
			if (page > 0 && page <= lastPage) {
				html[html.length] = this.renderPaginationLink(page, page, page == currentPage);
			}
		}
		
		if (currentPage != lastPage){
			html[html.length] = this.renderPaginationLink(currentPage + 1, "&nbsp;Next", false);
		}
		
		if (currentPage < lastPage - 3){
			html[html.length] = this.renderPaginationLink(lastPage, "&nbsp;Last", false);
		}
		
		return html.join("");
	}
	
	this.renderPaginationLink = function(pageNumber, pageLabel, isCurrent) {
	    var html = [];
	    
	    if (isCurrent) {
	        html[html.length] = '<strong> ';
	        html[html.length] =     pageLabel;
	        html[html.length] = '</strong>';
	    } else {
	        html[html.length] = '<a href="#'+pageLabel+'" onClick="getUbpMarketSearch().search('+pageNumber+');"> ';
	        html[html.length] =     pageLabel;
	        html[html.length] = '</a>';
	    }

	    return html.join("");
	}
	
}

//return single instance of ubp market (usefull from callback functions)
ubpMarketSearch = "";
function getUbpMarketSearch() {
	// create singleton if required
	if (ubpMarketSearch == "") {
		ubpMarketSearch = new UbpMarketSearchClass();	
	}
	return ubpMarketSearch;
}

jQuery(document).ready(function() {
	getUbpMarketSearch().init();
});

jQuery.fn.equalHeight = function(minHeight) {
    var height = 0, 
        maxHeight = 0;

    // Store the tallest element's height
    this.each(function() {
        var t = jQuery(this);
        t.height("");
        //height = t.height() + parseInt(t.css('paddingTop'), 10) + parseInt(t.css('paddingBottom'), 10) + parseInt(t.css('borderTopWidth'), 10) + parseInt(t.css('borderBottomWidth'), 10);
        
        var border_top = ( isNaN(parseInt(t.css('borderTopWidth'),10)) ? 0 : parseInt(t.css('borderTopWidth'),10) );
        var border_bottom = ( isNaN(parseInt(t.css('borderBottomWidth'),10)) ? 0 : parseInt(t.css('borderBottomWidth'),10) );
        height = t.height() + parseInt(t.css('paddingTop'), 10) + parseInt(t.css('paddingBottom'), 10) + border_top + border_bottom;
        
        maxHeight = (height > maxHeight) ? height : maxHeight;
    });
	
    // Set element's min-height to tallest element's height
    return this.each(function() {
        var t = jQuery(this);
            var border_top = ( isNaN(parseInt(t.css('borderTopWidth'),10)) ? 0 : parseInt(t.css('borderTopWidth'),10) );
            var border_bottom = ( isNaN(parseInt(t.css('borderBottomWidth'),10)) ? 0 : parseInt(t.css('borderBottomWidth'),10) );
        
            mh = maxHeight - (parseInt(t.css('paddingTop'), 10) + parseInt(t.css('paddingBottom'), 10) + border_top + border_bottom );
            //mh = maxHeight - (parseInt(t.css('padding-top'), 10) + parseInt(t.css('padding-bottom'), 10) + parseInt(t.css('border-top-width'), 10) + parseInt(t.css('border-bottom-width'), 10));
            if(mh > minHeight){
            	t.height(mh-4);
            }else{
            	t.height(minHeight);
            }
            //t.css({minHeight: mh +'px'});
    });
};

//Sortable config
var els = ['.col'];

/**
 * makeSortable
 */
var makeSortable = function(){    
	jQuery(els.toString()).sortable({ 
		items: '> dl',
		handle: 'dt',
		//cursor: 'move',
		connectWith: els,
		placeholder: "ui-selected",
		opacity: 0.8,      
		change: sortableChange,
		start: function(e,ui) {
			ui.helper.css("width", ui.item.width());
		},
		/*      
		update: function(){			 
			sortableUpdate();
		}
		*/	
		stop: function(e,ui){			
			var boxId = ui.item[0].id.replace("box","");
			var colId = ui.item[0].parentNode.id;
			var previousBoxId = -1;
			if (ui.item[0].previousSibling != null){
				previousBoxId = ui.item[0].previousSibling.id.replace("box","");
			}
			getUbpMarket().actionMoveBox(boxId, colId, previousBoxId);
		},
		appendTo: 'body'
    });        
};

/**
 * sortableChange
 */
var sortableChange = function(e, ui){
	if(ui.sender){
		var w = ui.element.width();
		ui.placeholder.width(w);
		ui.helper.css("width",ui.element.children().width());
	}
};

/**
 * Custom validator
 */
jQuery.validator.addMethod("instrument", function(value, element) {
	return this.optional(element) || /^[A-Za-z0-9\.\-_ ]*$/i.test(element.value);
}, "Contains invalid character");
jQuery.validator.addClassRules("instrument", {instrument: true});