// JavaScript Document

// TODO JSS S'han de passar per traducció algunes funcions.
function obreURL(snom,surl,itop,ileft,iwidth,iheight,stoolbar,slocation,sstatus,smenubar,sscrollbars,sresizable){
	if(!snom){ snom = ' '; }
	if(!surl){ surl = 'error'; }
	if(!itop){ itop = '0'; }
	if(!ileft){ ileft = '0'; }
	if(!iwidth){ iwidth = '700'; }
	if(!iheight){ iheight = '500'; }
	if(!stoolbar){ stoolbar = 'no'; }
	if(!slocation){ slocation = 'no'; }
	if(!sstatus){ sstatus = 'no'; }
	if(!smenubar){ smenubar = 'no'; }
	if(!sscrollbars){ sscrollbars = 'no'; }
	if(!sresizable){ sresizable = 'yes'; }
	var sprop="top="+itop+ ",left="+ileft+",height="+iheight+",width="+iwidth+",toolbar="+stoolbar+",location="+slocation+",status="+sstatus+",menubar="+smenubar+",scrollbars="+sscrollbars+",resizable="+sresizable;
	var win = window.open(surl,null,sprop);
	win.focus();
	return win;
}

function enviar(nom_camps,excepcion,accion,formulario){
	var camposVacios=0;
	i = 0;
	campos = "";
	while(i < nom_camps.length){
		if(trimAll(document.getElementById(nom_camps[i]).value) == "" ) {
			camposVacios = camposVacios + 1;
			campos = campos + "\n    " + nom_camps[i];
		}
		i = i + 1;
	}
	if(camposVacios == 0){
		if(trimAll(accion) == ""){
			var des=true;
		}else{
			var des = confirm('Confirma que desitja '+accion+' el registre?');
		}
		if(des == true){
//			alert(formulario.name);
//			formulario.submit();
			document.getElementById(formulario).submit();
		}
	}else{
		alert("Existeixen " + camposVacios + " camps buits: " + campos + "\n" + excepcion);
	}
}

function getResposta(originalRequest)
{
	var jsonRet = originalRequest.responseText;

	jsonRet = jsonRet.parseJSON();

	if(jsonRet[2])
		eval(jsonRet[2]);

	if(jsonRet[1])
		alert(jsonRet[1]);

	if(jsonRet[0])
		if(typeof(jsonRet[0]) == "object")
			for(var i in jsonRet[0])
				if(i != 'toJSONString')
					switch(document.getElementById(i).type){
						case 'hidden':
						case 'text':
						case 'select-one':

							if(document.getElementById(i+'___Frame')){

								//pause(2000);

								var oEditor = FCKeditorAPI.GetInstance(i);
								//alert("S'esta carregant l'dioma "+i+"\n\n Confirmi l'acció.");
								if(oEditor.EditMode == FCK_EDITMODE_WYSIWYG){

									oEditor.SetHTML(jsonRet[0][i]);

									//oEditor.InsertHtml(jsonRet[0][i]);
								}else
									alert(wsIdioma['formulariFCKmodeEdicio']+i);


							}else
								document.getElementById(i).value=jsonRet[0][i];
							break;
						case 'checkbox':
							if(jsonRet[0][i] == 1)
								document.getElementById(i).checked = true;
							else
								document.getElementById(i).checked = false;
							break;
						case 'textarea':
							document.getElementById(i).innerHTML = jsonRet[0][i];
							break;
					}
}

function getError(){
	alert("Error Inespertat!");
}

/**
	* Genera una petició de registre Ajax al recuperador de la plataforma
	*
	* @param recuperadorAjax
	*	@param nomTaula
	*	@param index
	*	@param referencia
	* @param condicio
	* @param ordre
	*/
function peticioAjax(recuperadorAjax,pars,nomTaula,index,referencia,condicio,ordre) {
	var pars = pars+'taula='+nomTaula+'&index='+ucFirst(index)+'&manteniment=false&referencia='+referencia+'&condicio='+condicio+'&ordre='+ordre;
	var oAjax = new Ajax.Request(recuperadorAjax,
															{
															method: "post",
															parameters: pars,
															onComplete: getResposta,
															onFailure: getError
															});
}

/**
	* Genera una petició de registre Ajax - Contingut
	*
	* @param recuperadorAjax
	* @param idContingut
	*/
function getAjaxContingut(recuperadorAjax,pars) {
	peticioAjax(recuperadorAjax,pars,'modulContinguts','id','referencia','','');
//	peticioAjax(recuperadorAjax,pars,'modulContinguts','id','referencia',idContingut,'');
}

function ajaxFormParameters(form)
{
	var f=Form.getElements(form);
	var pars = '';
	f.length.times(function(index){
		sValue = new String(Form.Element.getValue(f[index]));
		sValue = sValue.replace(/&+/g,"#38#");
		sValue = sValue.replace(/\++/g,"#43#");
//JSS Proto 1.6		pars += Form.Element.getName(f[index]) +'='+ sValue + '&';
		pars += f[index].name +'='+ sValue + '&';
	});

	return pars;
}

function ajaxProcess(form,divMsg,bSet)
{
	if(bSet){
		Form.disable(form);
		Element.show(divMsg);
		document.getElementById(divMsg).focus();
		Element.scrollTo(divMsg);
	}else{
		Form.enable(form);
		document.getElementById(divMsg).focus();
		Element.hide(divMsg);
	}
}

function setFormCheckBoxes(form,bCheck)
{
	var f = Form.getElements(form);
	f.length.times(function(index){
		if(Form.Element.getType(f[index]) == 'checkbox')
			$(Form.Element.getId(f[index])).checked = bCheck;
	});
}

function confirmaBoto(wsl)
{
	return confirm(wsIdioma[wsl]);
}

function showlocaltime() {
	var today = new Date();
	var difftime = (today.getTimezoneOffset()+60) *60000;
	today.setTime(today.getTime()+difftime);
	return(today.toLocaleString());
}

var day;
var month;
var year;
var hour;
var minute;
var second;
var clock_set = 0;

/**
 * Opens calendar window.
 *
 * @param   string      calendar.php parameters
 * @param   string      form name
 * @param   string      field name
 * @param   string      edit type - date/timestamp
 */
function openCalendar(url, form, field, type) {
    window.open(url, "calendar", "width=300,height=250,status=yes");
    dateField = eval("document." + form + "." + field);
    dateType = type;
}

/**
 * Formats number to two digits.
 *
 * @param   int number to format.
 */
function formatNum2(i, valtype) {
    f = (i < 10 ? '0' : '') + i;
    if (valtype && valtype != '') {
        switch(valtype) {
            case 'month':
                f = (f > 12 ? 12 : f);
                break;

            case 'day':
                f = (f > 31 ? 31 : f);
                break;

            case 'hour':
                f = (f > 24 ? 24 : f);
                break;

            default:
            case 'second':
            case 'minute':
                f = (f > 59 ? 59 : f);
                break;
        }
    }

    return f;
}

/**
 * Formats number to four digits.
 *
 * @param   int number to format.
 */
function formatNum4(i) {
    return (i < 1000 ? i < 100 ? i < 10 ? '000' : '00' : '0' : '') + i;
}

/**
 * Initializes calendar window.
 */
function initCalendar() {
    if (!year && !month && !day) {
        /* Called for first time */
        if (window.opener.dateField.value) {
            value = window.opener.dateField.value;
            if (window.opener.dateType == 'datetime' || window.opener.dateType == 'date') {
                if (window.opener.dateType == 'datetime') {
                    parts   = value.split(' ');
                    value   = parts[0];

                    if (parts[1]) {
                        time    = parts[1].split(':');
                        hour    = parseInt(time[0],10);
                        minute  = parseInt(time[1],10);
                        second  = parseInt(time[2],10);
                    }
                }
                date        = value.split("-");
                day         = parseInt(date[2],10);
                month       = parseInt(date[1],10) - 1;
                year        = parseInt(date[0],10);
            } else {
                year        = parseInt(value.substr(0,4),10);
                month       = parseInt(value.substr(4,2),10) - 1;
                day         = parseInt(value.substr(6,2),10);
                hour        = parseInt(value.substr(8,2),10);
                minute      = parseInt(value.substr(10,2),10);
                second      = parseInt(value.substr(12,2),10);
            }
        }
        if (isNaN(year) || isNaN(month) || isNaN(day) || day == 0) {
            dt      = new Date();
            year    = dt.getFullYear();
            month   = dt.getMonth();
            day     = dt.getDate();
        }
        if (isNaN(hour) || isNaN(minute) || isNaN(second)) {
            dt      = new Date();
            hour    = dt.getHours();
            minute  = dt.getMinutes();
            second  = dt.getSeconds();
        }
    } else {
        /* Moving in calendar */
        if (month > 11) {
            month = 0;
            year++;
        }
        if (month < 0) {
            month = 11;
            year--;
        }
    }

    if (document.getElementById) {
        cnt = document.getElementById("calendar_data");
    } else if (document.all) {
        cnt = document.all["calendar_data"];
    }

    cnt.innerHTML = "";

    str = ""

    //heading table
    str += '<table class="calendar"><tr><th width="50%">';
    str += '<form method="NONE" onsubmit="return 0">';
    str += '<a href="javascript:month--; initCalendar();">&laquo;</a> ';
    str += '<select id="select_month" name="monthsel" onchange="month = parseInt(document.getElementById(\'select_month\').value); initCalendar();">';
    for (i =0; i < 12; i++) {
        if (i == month) selected = ' selected="selected"';
        else selected = '';
        str += '<option value="' + i + '" ' + selected + '>' + wsIdioma['nomMesosAny'][i] + '</option>';
    }
    str += '</select>';
    str += ' <a href="javascript:month++; initCalendar();">&raquo;</a>';
    str += '</form>';
    str += '</th><th width="50%">';
    str += '<form method="NONE" onsubmit="return 0">';
    str += '<a href="javascript:year--; initCalendar();">&laquo;</a> ';
    str += '<select id="select_year" name="yearsel" onchange="year = parseInt(document.getElementById(\'select_year\').value); initCalendar();">';
    for (i = year - 25; i < year + 25; i++) {
        if (i == year) selected = ' selected="selected"';
        else selected = '';
        str += '<option value="' + i + '" ' + selected + '>' + i + '</option>';
    }
    str += '</select>';
    str += ' <a href="javascript:year++; initCalendar();">&raquo;</a>';
    str += '</form>';
    str += '</th></tr></table>';

    str += '<table class="calendar"><tr>';
    for (i = 0; i < 7; i++) {
        str += "<th>" + wsIdioma['nomDiesSetmana'][i] + "</th>";
    }
    str += "</tr>";

    var firstDay = new Date(year, month, 1).getDay();
    var lastDay = new Date(year, month + 1, 0).getDate();

    str += "<tr>";

    dayInWeek = 0;
    for (i = 0; i < firstDay; i++) {
        str += "<td>&nbsp;</td>";
        dayInWeek++;
    }
    for (i = 1; i <= lastDay; i++) {
        if (dayInWeek == 7) {
            str += "</tr><tr>";
            dayInWeek = 0;
        }

        dispmonth = 1 + month;

        if (window.opener.dateType == 'datetime' || window.opener.dateType == 'date') {
            actVal = formatNum4(year) + "-" + formatNum2(dispmonth, 'month') + "-" + formatNum2(i, 'day');
        } else {
            actVal = "" + formatNum4(year) + formatNum2(dispmonth, 'month') + formatNum2(i, 'day');
        }
        if (i == day) {
            style = ' class="selected"';
        } else {
            style = '';
        }
        str += "<td" + style + "><a href=\"javascript:returnDate('" + actVal + "');\">" + i + "</a></td>"
        dayInWeek++;
    }
    for (i = dayInWeek; i < 7; i++) {
        str += "<td>&nbsp;</td>";
    }

    str += "</tr></table>";

    cnt.innerHTML = str;

    // Should we handle time also?
    if (window.opener.dateType != 'date' && !clock_set) {

        if (document.getElementById) {
            cnt = document.getElementById("clock_data");
        } else if (document.all) {
            cnt = document.all["clock_data"];
        }

        str = '';
        str += '<form class="clock">';
        str += '<input id="hour"    type="text" size="2" maxlength="2" onblur="this.value=formatNum2(this.value, \'hour\')" value="' + formatNum2(hour, 'hour') + '" />:';
        str += '<input id="minute"  type="text" size="2" maxlength="2" onblur="this.value=formatNum2(this.value, \'minute\')" value="' + formatNum2(minute, 'minute') + '" />:';
        str += '<input id="second"  type="text" size="2" maxlength="2" onblur="this.value=formatNum2(this.value, \'second\')" value="' + formatNum2(second, 'second') + '" />';
        str += '</form>';

        cnt.innerHTML = str;
        clock_set = 1;
    }

}

/**
 * Returns date from calendar.
 *
 * @param   string     date text
 */
function returnDate(d) {
    txt = d;
    if (window.opener.dateType != 'date') {
        // need to get time
        h = parseInt(document.getElementById('hour').value,10);
        m = parseInt(document.getElementById('minute').value,10);
        s = parseInt(document.getElementById('second').value,10);
        if (window.opener.dateType == 'datetime') {
            txt += ' ' + formatNum2(h, 'hour') + ':' + formatNum2(m, 'minute') + ':' + formatNum2(s, 'second');
        } else {
            // timestamp
            txt += formatNum2(h, 'hour') + formatNum2(m, 'minute') + formatNum2(s, 'second');
        }
    }

    window.opener.dateField.value = txt;

    window.close();
}

var DayNames= new Array("Mon","Tue","Wed","Thu","Fri","Sat","Sun");

/******************************
** Common Javascript routines
** Simon Mugan: Sep 2000
*******************************/

// convert a string to lowercase with 1st letter capitalised
function ucFirst(s)
{
	var c = s.charAt(0);

	if (parseInt(s.length)==1){
		return c.toUpperCase();
	}
	else
	{
		return c.toUpperCase() + s.slice(1).toLowerCase();
	}
}

// remove leading and trailing spaces JSS
function Trim(s) {
	var trimmed="";
	var leading = true;
	var trailing = true;

	// strip leading spaces
	for(var i = 0; i < s.length; i++){
		var c = s.charAt(i);
		if (c == ' '){
			if (!leading){
				trimmed +=c;
			}
		}else{
//JSS			leading=false;
			trimmed +=c;
		}
	}

	// strip trailing spaces
	for (var i = trimmed.length-1; i>0; i--){
		var c = trimmed.charAt(i);
		if (c != " ")
			return trimmed;
		else
			trimmed=trimmed.substr(0,trimmed.length-1);
	}

	return trimmed;
}

// A simple routine to strip HTML tags from supplied string
// It's not very clever but it's quite useful.
// Everything between each "<" and the subsequent ">" is ignored
// hence it could get confused with any javascript comparisons
// or comments that contain comparisons.
function stripHTMLTags(str)
{	var mystr="";
	var chr="";
	var skip=false;
	var skipcancel=false;

	for (x=0; x<str.length; x++)
	{
		if (skipcancel==true){skip=false;}
		chr=str.charAt(x);
		if (chr=="<"){skip=true;skipcancel=false;}
		else if (chr==">" && skip==true){skipcancel=true;}

		if (skip==false) mystr=mystr+chr;
	}
	return mystr;
}

// same as ucFirst, but repeated for all words in a string after
// converting all underscore characters to spaces
function ReadableName(s)
{
	var formatted = "";
	var c = "";
	var wStart = true;
    for(var i = 0; i < s.length; i++)
    {
        c = s.charAt(i);
        if (c == "_"){c=" ";}
        if (wStart==true){formatted=formatted+c.toUpperCase();wStart=false;}
        else {formatted=formatted+c.toLowerCase();}
        if (c == " "){wStart=true;}
    }
    return formatted;
}

// checks whether a field is empty
function isblank(s)
{
    for(var i = 0; i < s.length; i++) {
        var c = s.charAt(i);
        if ((c != ' ') && (c != '\n') && (c != '\t')) return false;
    }
    return true;
}


// validate an email address
function isValidEmail(e)
{
	// assume an email address cannot start with an @ or white space, but it
	// must contain the @ character followed by groups of alphanumerics and '-'
	// followed by the dot character '.'
	// It must end with 2 or 3 alphanumerics.
	//
	var alnum="a-zA-Z0-9";
	exp="^[^@\\s]+@(["+alnum+"+\\-]+\\.)+["+alnum+"]["+alnum+"]["+alnum+"]?$";
	emailregexp = new RegExp(exp);

	result = e.match(emailregexp);
	if (result != null)
	{
		return true;
	}
	else
	{
		return false;
	}
}

function isValidTime(strTime) {
	// Checks if time is in HH:MM:SS format.
	// The seconds are optional.

	var timePat = /^(\d{1,2}):(\d{2})(:(\d{2}))?$/;
	var matchArray = strTime.match(timePat);
	if (matchArray == null) {
		return false;
	}

	hour = matchArray[1];
	minute = matchArray[2];
	second = matchArray[4];

	if (second=="") { second = null; }

	if (hour < 0  || hour > 23) {
		return false;
	}

	if (minute<0 || minute > 59) {
		return false;
	}
	if (second != null && (second < 0 || second > 59)) {
		return false;
	}
	return true;
}

function isValidNumber(numval)
{
	if (numval==""){return false;}
	var myRegExp = new RegExp("^[/+|/-]?[0-9]*[/.]?[0-9]*$");
	return myRegExp.test(numval);
}

function isValidInterval(interval)
{
	var strIntervals = new Array("yrs","year","years","mos","month","months","day","days","week","weeks","hrs","hour","hours","mins","min","minutes","secs","sec","second","seconds");
	strArray = interval.split(" ");

	// need at least two items
	if (strArray.length < 2) {return false;}

	// check all pairs of values to be valid intervals (e.g 2 hrs 5 mins)
	for (i = 0;i<strArray.length-1;i=i+2) {
		if (isNaN(strArray[i])){return false;}
		found=false;
		for (var x = 0;x<strIntervals.length;x++) {
			if (strArray[i+1].toUpperCase() == strIntervals[x].toUpperCase()) {found=true;}
		}
		if (!found){return false;}
	}
	return true;
}

function isValidDate(d,convert) {
	//var strDatestyle = "US"; //United States date style
	var strDatestyle = "EU";  //European date style
	var strDate;
	var strDateArray;
	var strDay;
	var strMonth;
	var strYear;
	var intDay;
	var intMonth;
	var intYear;
	var booFound = false;
	var strSeparatorArray = new Array("-"," ","/",".");
	var intElementNr;
	var err = 0;
	var strMonthArray = new Array("Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec");
	strDate = d;
	if (strDate.length < 1) {
		return false;
	}
	if (strDate.toLowerCase()=="today" || strDate.toLowerCase()=="now"){return true;}

	for (intElementNr = 0; intElementNr < strSeparatorArray.length; intElementNr++) {
		if (strDate.indexOf(strSeparatorArray[intElementNr]) != -1) {
			strDateArray = strDate.split(strSeparatorArray[intElementNr]);
			if (strDateArray.length != 3)
			{
				err = 1;
				return false;
			}
			else
			{
				strDay = strDateArray[0];
				strMonth = strDateArray[1];
				strYear = strDateArray[2];
			}
			booFound = true;
		}
	}

	if (booFound == false) {
		if (strDate.length>5) {
			strDay = strDate.substr(0, 2);
			strMonth = strDate.substr(2, 2);
			strYear = strDate.substr(4);
		}
		else
			return false;
	}

	// verify year part	2 or 4 digits
	if (strYear.length != 2 && strYear.length != 4) {return false;}
	if (isNaN(strYear)){return false;}
	// US style (swap month and day)
	if (strDatestyle == "US") {
		strTemp = strDay;
		strDay = strMonth;
		strMonth = strTemp;
	}

	// verify 1 or 2 digit integer day
	if (strDay.length<1 || strDay.length>2) {return false;}
	if (isNaN(strDay)){return false;}

	// month may be digits of characters, hence following check
	intMonth = parseInt(strMonth, 10);
	if (isNaN(intMonth)) {
		for (i = 0;i<12;i++) {
			if (strMonth.toUpperCase() == strMonthArray[i].toUpperCase()) {
				intMonth = i+1;
				strMonth = strMonthArray[i];
				i = 12;
			}
		}
		if (isNaN(intMonth)) {
			err = 3;
			return false;
		}
	}

	intDay=parseInt(strDay,10);
	intYear = parseInt(strYear, 10);

	if (intMonth>12 || intMonth<1) {
		err = 5;
		return false;
	}

	// day in month check
	if (intDay < 1 || intDay > 31){return false;}

	if ((intMonth == 4 || intMonth == 6 || intMonth == 9 || intMonth == 11) && (intDay > 30)) {
		return false;
	}

	if (intMonth == 2) {
		if (LeapYear(intYear)) {
			if (intDay > 29) {return false;}
		}
		else
		{
			if (intDay > 28) {return false;}
		}
	}

	if (!convert)
		return true;
	else
	{
		if (intYear<=99){intYear=intYear+2000;}
		return intDay+"/"+intMonth+"/"+intYear;
	}
}

function ConvertToJscriptDate(mydate)
{
	if (!isValidDate(mydate)){return "";}
	var vdate=isValidDate(mydate,true);
	var dparts= vdate.split("/");
	var JDate = new Date(dparts[2]+"/"+dparts[1]+"/"+dparts[0]);
	return JDate;
}

// check a composite date/time field
// assume date is everything up to first space
// and time is everything after first space

function isValidDateTime(strDateTime)
{
	var dt = Trim(strDateTime);
	var intMatch;
	var intDateOnly = false;

	if (strDateTime.toLowerCase()=="today" || strDateTime.toLowerCase()=="now"){return true;}

	intMatch=dt.indexOf(":");
	if (intMatch < 0)
	{
		intDateOnly = true;
		intMatch=dt.length;
	}
	else
	{
		intMatch=dt.indexOf(" ");
	}
	if (intMatch < 0) {return false;}

	// check date
	if (!isValidDate(dt.substr(0,intMatch))){return false;}

	// check time
	if (!intDateOnly) {
		if (!isValidTime(dt.substr(intMatch+1,dt.length-intMatch))){return false;}
	}

	return true;
}


function LeapYear(intYear) {
	if (intYear % 100 == 0) {
		if (intYear % 400 == 0) { return true; }
	}
	else {
		if ((intYear % 4) == 0) { return true; }
	}
	return false;
}

function isEarlierOrEqual(start,end)
{
	// convert dates to dd/mm/yyyy
	var myStart = isValidDate(start,true);
	var myEnd = isValidDate(end,true);
	if (myStart=="" || myEnd=="") return false;

	var startparts= myStart.split("/");
	var endparts=myEnd.split("/");

	if (Date.UTC(startparts[2],startparts[1],startparts[0]) <= Date.UTC(endparts[2],endparts[1],endparts[0]))
		return true;
	else
		return false;
}

function isTimeEarlierOrEqual(start,end)
{
	// convert times to UTC dates
	if (start=="" || end=="") return false;

	var startparts= start.split(":");
	var endparts=end.split(":");

	if (Date.UTC(2000,1,1,startparts[0],startparts[1]) <= Date.UTC(2000,1,1,endparts[0],endparts[1]))
		return true;
	else
		return false;
}

// This is the function that performs form verification.  It will be invoked
// from the onSubmit() event handler.  The handler should return whatever
// value this function returns.
function frmValidateCommon(f)
{
    var msg;
    var empty_fields = "";
    var errors = "";
    var mylen = parseInt(f.length);
    var errOne = false;

    // Loop through the elements of the form, looking for all
    // text and textarea elements that don't have an "optional" property
    // defined.  Then, check for fields that are empty and make a list of them.
    // Also, if any of these elements have a "min" or a "max" property defined,
    // then verify that they are numbers and that they are in the right range.
    // Put together error messages for fields that are wrong.
    for(var i = 0; i < mylen; i++) {
        var e = f.elements[i];

        if (((e.type == "text") || (e.type == "textarea")) && !e.optional)
        {
            // first check if the field is empty
            if ((e.value == null) || (e.value == "") || isblank(e.value))
            {
                empty_fields += "\n          " + ReadableName(e.name);
                if (!errOne)
                {
					errOne=true;e.focus();
				}
                continue;
            }
        }

	    // now validate email addresses
	    if (e.email) {
			if ((e.value == null) || (e.value == "") || isblank(e.value)) continue;
			if (!isValidEmail(e.value)) {
				errors += "\n- The value in field " +ReadableName(e.name)+" does not appear to be a valid email address\n"
				if (!errOne){errOne=true;e.focus();}
			}
		}

	    // now validate date fields
	    if (e.date) {
			if ((e.value == null) || (e.value == "") || isblank(e.value)) continue;
			if (!isValidDate(e.value)) {
				errors += "\n- The field " +ReadableName(e.name)+" does not contain a recognised\ndate value (try dd-mmm-yyyy) \n"
				if (!errOne){errOne=true;e.focus();}
			}
		}

	    // now validate time fields
	    if (e.time) {
			if ((e.value == null) || (e.value == "") || isblank(e.value)) continue;
			if (!isValidTime(e.value)) {
				errors += "\n- The field " +ReadableName(e.name)+" does not contain a recognised\ntime value (try hh:mm[:ss]) \n"
				if (!errOne){errOne=true;e.focus();}
			}
		}

	    // now validate date/time fields
	    if (e.datetime) {
			if ((e.value == null) || (e.value == "") || isblank(e.value)) continue;
			if (!isValidDateTime(e.value)) {
				errors += "\n- The field "+ReadableName(e.name)+ " does not contain a recognised\ndate/time value (try dd-mmm-yyyy hh:mm[:ss]) \n"
				if (!errOne){errOne=true;e.focus();}
			}
		}

	    // now validate interval fields
	    if (e.interval) {
			if ((e.value == null) || (e.value == "") || isblank(e.value)) continue;
			if (!isValidInterval(e.value)) {
				errors += "\n- The field "+ReadableName(e.name)+ " does not contain a recognised\ninterval value (try nn hours or nn days) \n"
				if (!errOne){errOne=true;e.focus();}
			}
		}

        // Now check for fields that are supposed to be numeric.
        if (e.numeric || (e.min != null) || (e.max != null))
        {
			if ((e.value == null) || (e.value == "") || isblank(e.value)) continue;
			var v = parseFloat(e.value);
			if (isNaN(v) || !isValidNumber(e.value) || ((e.min != null) && (v < e.min)) || ((e.max != null) && (v > e.max)))
			{
					if (!errOne){errOne=true;e.focus();}
					errors += "\n- The field " + ucFirst(e.name) + " must be a number";
                    if (e.min != null)
                        errors += " that is greater than " + e.min;
                    if (e.max != null && e.min != null)
                        errors += " and less than " + e.max;
                    else if (e.max != null)
                        errors += " that is less than " + e.max;
                    errors += ".\n";
            }
        }
    }

    // Now, if there were any errors, then display the messages, and
    // return true to prevent the form from being submitted.  Otherwise
    // return false
    if (!empty_fields && !errors) return true;

    msg  = "Sorry, but we cannot process your request because of the\n";
    msg += "following error(s). Please correct the problem and try again\n";

    if (empty_fields) {
        msg += "\n- The following fields are mandatory:"
                + empty_fields + "\n";
        if (errors) msg += "\n";
    }
    msg += errors;
    alert(msg);
    return false;
}

// this function sets the fields in the combo that exist in the values string
// multiple values should be comma delimited
// e.g. SetSelection(myCombo,"fred,harry");
//    will highlight the combo entries that have the value harry and/or fred
function SetSelections(Combo,Values)
{
	var lvals = Values.split(",");
	var strval = "";

	for (var x=0; x<Combo.length; x++)
	{
		strval=Combo.options[x].value.toLowerCase();

		for (var i=0; i<lvals.length; i++)
				if (strval==Trim(lvals[i].toLowerCase()))
					Combo.options[x].selected=true;
	}
}


// Insert new item into a combo in alhpabetcial order or at specified pos
function InsertIntoList(Combo, itemText, itemVal, Pos)
{
	var inserted=false;
	var insertpos=-1;

	// add blank row
	Combo.length++;

	if (Pos==-1)
	{
		// find alpha pos for insert
		for (var x=0; x<Combo.length-1; x++)
		{	if (Combo.options[x].text.toLowerCase()>itemText.toLowerCase())
				{insertpos=x;break;}
		}
	}
	else
		{insertpos=Pos;}

	// shift part of array down one then insert new row
	if (insertpos!=-1)
	{	for (var y=Combo.length-1; y>insertpos; y--)
		{
			Combo.options[y].value=Combo.options[y-1].value;
			Combo.options[y].text=Combo.options[y-1].text;
		}
		Combo.options[insertpos].text=itemText;
		Combo.options[insertpos].value=itemVal;
	}
	else
	// append new row
	{
		insertpos=Combo.length-1;
		Combo.options[insertpos].text=itemText;
		Combo.options[insertpos].value=itemVal;
	}

	return insertpos;
}

// Append a new item into a combo (assume no ordering)
function AppendToList(Combo, itemText, itemVal)
{
	// add blank row
	Combo.length++;
	Combo.options[Combo.length-1].text=itemText;
	Combo.options[Combo.length-1].value=itemVal;
	return true;
}

// Move selected items up or down one pos in combo list
function ShiftListSelections(Combo, Down)
{
	var prevtext="";
	var prevval=""
	var swappos;
	if (!Down==true) Down=false;

	if (Down==true)
	{
		for (var x=Combo.length-1; x>=0; x--)
		{
			if (Combo[x].selected==true)
			{
				if (x<Combo.length-1 && Combo[x+1].selected==false)
				{
					//swap cur entry for previous entry
					prevtext=Combo[x+1].text;
					prevval=Combo[x+1].value;
					Combo[x+1].text=Combo[x].text;
					Combo[x+1].value=Combo[x].value;
					Combo[x+1].selected=true;
					Combo[x].text=prevtext;
					Combo[x].value=prevval;
					Combo[x].selected=false;
				}
			}
		}
	}
	else
	{
		for (var x=0; x<Combo.length; x++)
		{
			if (Combo[x].selected==true)
			{
				if (x>0 && Combo[x-1].selected==false)
				{
					//swap cur entry for previous entry
					prevtext=Combo[x-1].text;
					prevval=Combo[x-1].value;
					Combo[x-1].text=Combo[x].text;
					Combo[x-1].value=Combo[x].value;
					Combo[x-1].selected=true;
					Combo[x].text=prevtext;
					Combo[x].value=prevval;
					Combo[x].selected=false;
				}
			}
		}
	}
}

function DeleteFromList(Combo, Pos)
{
	if (Pos>=0 && Pos <= Combo.length)
	{
		Combo[Pos]=null;
	}
}

// function to do a bulk move from one list to another
// quicker than doing individual inserts/appends etc
function MoveSelectedListItems(srcCombo, destCombo, doSort, intSort, useVals)
{
	var numItems = 0;
	var curPos = destCombo.options.length;
	var srcLen = srcCombo.options.length;

	for (var x=0; x<srcCombo.options.length; x++)
		if (srcCombo.options[x].selected) numItems++;

	destCombo.options.length+=numItems;
	for (var x=0; x<srcCombo.options.length; x++)
		if (srcCombo.options[x].selected==true)
		{
			destCombo.options[curPos].text=srcCombo.options[x].text;
			destCombo.options[curPos].value=srcCombo.options[x].value;
			curPos++;
		}
	if (doSort) SortList(destCombo, intSort, useVals);

	/* now remove the selected items from the source listbox */
	/* This can be very slow for big lists, but I'm not sure how else to do it */
	for (var x=srcLen-1; x>=0; x--)
		if (srcCombo.options[x].selected) srcCombo.options[x]=null;
}

// Compare functions used internally by the SortList routine,
function ListCompareNums(a,b)
{
	var la = parseInt(a.split("{")[0]);
	var lb = parseInt(b.split("{")[0]);
	if (la < lb) return -1;
	if (la > lb) return 1
	return 0;
}
function ListCompareText(a,b)
{	var la = a.toLowerCase();
	var lb = b.toLowerCase();
	if (la < lb) return -1;
	if (la > lb) return 1
	return 0;
}

// Quite Fast way of sorting big option lists
function SortList(Combo, IntSort, UseVals)
{
	var cmbText = new Array(Combo.options.length);
	var cmbItems;

	// get copy of
	for (x=0; x<cmbText.length; x++)
		cmbText[x]=(UseVals)?Combo.options[x].value + "{" + Combo.options[x].text:Combo.options[x].text + "{" + Combo.options[x].value;

	if (IntSort)
		cmbText.sort(ListCompareNums);
	else
		cmbText.sort(ListCompareText);

	//rebuild main list, but don't redimension it
	for (x=0; x<cmbText.length; x++){
		cmbItems = cmbText[x].split("{");
		Combo.options[x].text=(UseVals)?cmbItems[1]:cmbItems[0];
		Combo.options[x].value=(UseVals)?cmbItems[0]:cmbItems[1];
	}
}

function NewWindow(url, title, w, h, scroll, resize) {
if (scroll==true || scroll=='yes') scroll='yes'; else scroll='no';
if (resize==true || resize=='yes') resize=', resizable'; else resize='';
var winl = (screen.width - w) / 2;
var wint = (screen.height - h) / 2;
winprops = 'height='+h+',width='+w+',top='+wint+',left='+winl+',scrollbars='+scroll+resize
win = window.open(url, title, winprops)
}

/* Function that displays status bar messages. */
function MM_displayStatusMsg(msgStr)  { //v3.0
	status=msgStr; document.MM_returnValue = true;
}

function MM_findObj(n, d) { //v3.0
  var p,i,x;  if(!d) d=document; if((p=n.indexOf("?"))>0&&parent.frames.length) {
    d=parent.frames[n.substring(p+1)].document; n=n.substring(0,p);}
  if(!(x=d[n])&&d.all) x=d.all[n]; for (i=0;!x&&i<d.forms.length;i++) x=d.forms[i][n];
  for(i=0;!x&&d.layers&&i<d.layers.length;i++) x=MM_findObj(n,d.layers[i].document); return x;
}
/* Functions that swaps images. */
function MM_swapImage() { //v3.0
  var i,j=0,x,a=MM_swapImage.arguments; document.MM_sr=new Array; for(i=0;i<(a.length-2);i+=3)
   if ((x=MM_findObj(a[i]))!=null){document.MM_sr[j++]=x; if(!x.oSrc) x.oSrc=x.src; x.src=a[i+2];}
}
function MM_swapImgRestore() { //v3.0
  var i,x,a=document.MM_sr; for(i=0;a&&i<a.length&&(x=a[i])&&x.oSrc;i++) x.src=x.oSrc;
}

/* Functions that handle preload. */
function MM_preloadImages() { //v3.0
 var d=document; if(d.images){ if(!d.MM_p) d.MM_p=new Array();
   var i,j=d.MM_p.length,a=MM_preloadImages.arguments; for(i=0; i<a.length; i++)
   if (a[i].indexOf("#")!=0){ d.MM_p[j]=new Image; d.MM_p[j++].src=a[i];}}
}

function MM_showHideLayers() { //v3.0
  var i,p,v,obj,args=MM_showHideLayers.arguments;
  for (i=0; i<(args.length-2); i+=3) if ((obj=MM_findObj(args[i]))!=null) { v=args[i+2];
    if (obj.style) { obj=obj.style; v=(v=='show')?'visible':(v='hide')?'hidden':v; }
    obj.visibility=v; }
}

/* Funció que mostra i oculta capes fent servir l'atribut display.*/
function mostrarOcultar(nombreCapa) {
	if(document.getElementById(nombreCapa).style.display=="none")
		document.getElementById(nombreCapa).style.display="block";
	else
		document.getElementById(nombreCapa).style.display="none";
}

/* Google Maps */
var map;
var geocoder;
var nom; //nom de l'empresa que estem buscant amb el googlemaps

function load() {
	if(document.getElementById("map")) {
		map = new GMap2(document.getElementById("map"));

		map.addControl(new GSmallMapControl());
		map.addControl(new GMapTypeControl());
		map.setCenter(new GLatLng(41.543646,2.453127), 15);
		geocoder = new GClientGeocoder();
	}
}

/*
	addAddressToMap() is called when the geocoder returns an
	answer.  It adds a marker to the map with an open info window
	showing the nicely formatted version of the address and the country code.
*/
function addAddressToMap(response) {
	if(map==null) {load();}
	map.clearOverlays();
	if (!response || response.Status.code != 200) {
		alert("No se encuentra la dirección.");
	}else{
		place = response.Placemark[0];
		point = new GLatLng(place.Point.coordinates[1],
		place.Point.coordinates[0]);
		marker = new GMarker(point);
		map.addOverlay(marker);
		marker.openInfoWindowHtml("<strong>"+nom+"</strong><br>"+place.address + '<br>');
	}
}

/*
	showLocation() is called when you click on the Search button
	in the form.  It geocodes the address entered into the form
	and adds a marker to the map at that location.
*/
function showLocation(address,nomE) {
	nom=nomE;
	if(geocoder==null)
		geocoder = new GClientGeocoder();
	geocoder.getLocations(address, addAddressToMap);
}

/* Fi google maps */

// @todo el tamany de la imatge també hauria de ser per parametre
function mostrarImg(i,c) {
	document.getElementById(c).innerHTML="<img src='"+i+"' width='200px' height='200px'/>";
}

// @todo si la funció es especifica d'un modul, millor que estigui al modul
function mostrarOcultar2(nombreCapa,numCapes)
{
	for(i=0; i<numCapes; i++) {
		document.getElementById("gal"+i).style.display="none";
	}
	if(document.getElementById(nombreCapa).style.display=="none")
		document.getElementById(nombreCapa).style.display="block";
	else
		document.getElementById(nombreCapa).style.display="none";
}

// @todo falta persistencia. La mida no es manté al recarregar/canviar de pagina
function canviMidaFontI(opcio)
{
	switch(opcio)
	{
		case 'aa':
		document.body.style.fontSize="16px";
		//document.getElementById('navegacioCentral').style.width="75%";
		canviEtiquetes(16);
		SetCookie("tamanyLletra","16");
		break;
		
		case 'aaa':
		document.body.style.fontSize="18px";
		//document.getElementById('navegacioCentral').style.width="70%";
		canviEtiquetes(18);
		SetCookie("tamanyLletra","18");
		break;
		
		default:
		document.body.style.fontSize="12px";
		//document.getElementById('navegacioCentral').style.width="80%";
		canviEtiquetes(12);
		SetCookie("tamanyLletra","12");
		break;
	}
	if(document.getElementById('mycustomscroll_mcontentwrapper')){
		document.getElementById('mycustomscroll_mcontentwrapper').style.fontSize="16px";
	}
}


function canviEtiquetes(mida){
	var Fs = document.getElementsByTagName("font");
	for (var i = 0; i < Fs.length; i ++){
		if(Fs[i].id != 'letra'){
			if(Fs[i].style.fontSize != ""){
				Fs[i].style.fontSize = mida+"px";
			}
		}
	}
	
	var Ps = document.getElementsByTagName("p");
	for (var i = 0; i < Ps.length; i ++){
		if(Ps[i].style.fontSize != ""){
			Ps[i].style.fontSize = mida+"px";
		}
	}
	
	var Ss = document.getElementsByTagName("span");
	for (var i = 0; i < Ss.length; i ++){
		if(Ss[i].id != 'letraMenu'){
			if(Fs[i].style.fontSize != ""){
				Ss[i].style.fontSize = mida+"px";	
			}
		}
	}
}

/*FUNCIONS DE COOKIES*/

function GetCookie(name) {
	foobar = document.cookie.split(name + '=');
	
	if (foobar.length < 2) {
		return null;
	}
	tempString = foobar[1];
	if (tempString.indexOf(';') == -1) {
		return tempString;
	}
	yafoobar = tempString.split(';');
	return yafoobar[0];
}

function SetCookie(name, value) {
	document.cookie = name + "=" + value + "; path = /";
}

function getCookieVal (offset) {
	var endstr = document.cookie.indexOf (";", offset);
	if (endstr == -1)endstr = document.cookie.length;
	return unescape(document.cookie.substring(offset, endstr));
}
/*FI COOKIES*/




function MM_jumpMenu(targ,selObj,restore){ //v3.0
  eval(targ+".location='"+selObj.options[selObj.selectedIndex].value+"'");
  if (restore) selObj.selectedIndex=0;
}

/**
*
*  UTF-8 data encode / decode
*  http://www.webtoolkit.info/
*
**/

var Utf8 = {
	// public method for url encoding
	encode : function (string) {
		string = string.replace(/\r\n/g,"\n");
		var utftext = "";

		for (var n = 0; n < string.length; n++) {

			var c = string.charCodeAt(n);

			if (c < 128) {
				utftext += String.fromCharCode(c);
			}
			else if((c > 127) && (c < 2048)) {
				utftext += String.fromCharCode((c >> 6) | 192);
				utftext += String.fromCharCode((c & 63) | 128);
			}
			else {
				utftext += String.fromCharCode((c >> 12) | 224);
				utftext += String.fromCharCode(((c >> 6) & 63) | 128);
				utftext += String.fromCharCode((c & 63) | 128);
			}

		}

		return utftext;
	},

	// public method for url decoding
	decode : function (utftext) {
		var string = "";
		var i = 0;
		var c = c1 = c2 = 0;

		while ( i < utftext.length ) {

			c = utftext.charCodeAt(i);

			if (c < 128) {
				string += String.fromCharCode(c);
				i++;
			}
			else if((c > 191) && (c < 224)) {
				c2 = utftext.charCodeAt(i+1);
				string += String.fromCharCode(((c & 31) << 6) | (c2 & 63));
				i += 2;
			}
			else {
				c2 = utftext.charCodeAt(i+1);
				c3 = utftext.charCodeAt(i+2);
				string += String.fromCharCode(((c & 15) << 12) | ((c2 & 63) << 6) | (c3 & 63));
				i += 3;
			}

		}

		return string;
	}
}

//pausa
function pause(millis)
{

	var date = new Date();
	var curDate = null;

	do { curDate = new Date(); }
	while(curDate-date < millis);

}

/*Degradado del fondo */
//SCRIPT PARA CREAR UN DEGRADADO VARIABLE
//COPYRIGHT DESARROLLOWEB.COM
//
//Se puede utilizar siempre que se mantengan los creditos. Gracias.


//VARIABLES PARA CONFIGURAR EL DEGRADADO. Configurar desde aqui
//color que se presenta al principio
color_inicio = new Array(0,0,0)
//color al que se tiende
color_fin = new Array(253,146,7)
//los pasos que se utilizaran para pasar de un color al otro
pasos = 50
//comportamiento 1=bucle_infinito 2=una_pasada_de_inicio_a_fin 3=una_pasada_de_inicio_a_fin_a_inicio 4=bucle_infinito_con_interrupcion
comportamiento = 2



//VARIABLES INTERNAS Y PROGRAMACION.
//No tocar a no ser que se sepa lo que se hace
hexadecimal = new Array("0","1","2","3","4","5","6","7","8","9","A","B","C","D","E","F")
var iteracion = 0
var color_actual = new Array(3)
//calculo el incremento en los que se tiene que hacer el degradado, para el numero de pasos determinado
diferencia = new Array(3)
for (i=0;i<3;i++)
	diferencia[i] = (color_fin[i] - color_inicio[i]) / pasos

function convierteHexadecimal(num){
	//alert (num)
	var hexaDec = Math.floor(num/16)
	var hexaUni = num - (hexaDec * 16)
	return hexadecimal[hexaDec] + hexadecimal[hexaUni]
}

function degradado(){
	iteracion += 1
	//miro si estoy en el inicio > fin o en el fin > inicio
	if (iteracion < pasos) {
		//estoy al principo
		for (i=0;i<3;i++)
			color_actual[i] = (iteracion * diferencia[i]) + color_inicio[i]
	}else{
		//estoy volviendo
		for (i=0;i<3;i++)
			color_actual[i] = color_fin[i] - ((iteracion - pasos) * diferencia[i])
	}
	//alert(convierteHexadecimal(Math.round(color_actual[0])) + convierteHexadecimal(Math.round(color_actual[1])) + convierteHexadecimal(Math.round(color_actual[2])))

	document.bgColor = convierteHexadecimal(Math.round(color_actual[0])) + convierteHexadecimal(Math.round(color_actual[1])) + convierteHexadecimal(Math.round(color_actual[2]))

	//la llamo con un retardo
	switch (comportamiento){
		case 1:
			if (iteracion == pasos * 2)
				iteracion = 0
			setTimeout("degradado()",1)
			break;
		case 2:
			if(iteracion < pasos)
				setTimeout("degradado()",1)
			break;
		case 3:
			if(iteracion < pasos * 2)
				setTimeout("degradado()",1)
			break;
		case 4:
			if (iteracion == pasos * 2){
				iteracion = 0
				setTimeout("degradado()",10000)
			}else{
				setTimeout("degradado()",1)
			}
			break;
	}
}

/*Fin degradado del fondo*/
//Nifty corners
function nifty()
{
   // Nifty("div.contenidorSuperior","normal");
	Nifty("div#navegacioCentral","big transparent");
	//Nifty("div.contenidorDreta","big");
}

/* Creació d'un manual horitzontal manual*/
navHover = function() {
	if(!document.getElementById("navmenu"))
		return;
	var lis = document.getElementById("navmenu").getElementsByTagName("LI");

	for (var i=0; i<lis.length; i++) {
		lis[i].onmouseover=function() {
			this.className+=" iehover";
		}
		lis[i].onmouseout=function() {
			this.className=this.className.replace(new RegExp(" iehover\\b"), "");
		}
	}
}
if (window.attachEvent) window.attachEvent("onload", navHover);
/*Fi de la creació del menu horitzontal manual*/



/*Funció CANVILLIBRERIA que canvia una llibreria javascript per una altra, per problemes de versions, utitlitzat per al lightwindow*/
function canviLlibreria(antiga,nova)
{
var script = document.getElementsByTagName('script');
for(var i=0; i<script.length ; i++) 
	{
		
		var lib = script[i].src.substring(script[i].src.lastIndexOf('/')+1);
    	if(lib==antiga)
		{
			var caracters = script[i].src.length - lib.length;
			var srcNova = script[i].src.substring(0,caracters) + nova;
			
			script[i].parentNode.removeChild(script[i]);
			var proto = document.createElement("script");
			proto.src = srcNova;
			script[i].parentNode.appendChild(proto);

		}
	 }
}
/*Fi CANVILLIBRERIA*/