//////////////////////////////////////////////////////////////////////
//
//  Functions for validating general form input
//

function validateUpload (fileWidget)
{
	var val = fileWidget.value;

	if (val.indexOf (',') != -1 ||
	    val.indexOf ('%') != -1 ||
			val.indexOf ('&') != -1 ||
			val.indexOf ('#') != -1 ||
			val.indexOf ('`') != -1 ||
			val.indexOf (String.fromCharCode(180)) != -1 ||
			val.indexOf ('+') != -1)
	{
		alert (STRING_Files_validateUpload2);
		fileWidget.focus ();
		return false;
	}
			
	return true;
}

// Check the text length of a field
function checkLengthOn (aField, aTitle, limit)
{
	if (! aField || aField.value == null)
		return true;
	
	n = aField.value.length;
	if (n > limit)
	{
		alert (parent.format (STRING_Edit_checkLengthOn, aTitle, n, limit));
  	aField.focus ();
		return false;
	}
	return true;
}

// Field must not be empty
function mustNotBeNull (aField, aTitle)
{
	if (aField.value.length != 0)
		return true;

	alert (parent.format (STRING_Edit_mustNotBeNull, aTitle));
 	aField.focus ();
	return false;
}

function removeWhiteSpaceFromTail (field)
{
	var val = field.value;
	var pos = val.length - 1;
	while (pos > 0 && isWhitespace (val.charAt (pos)))
		pos--;
	field.value = val.substr (0, pos + 1);
}
	
// Checks if c is a whitespace character
function isWhitespace (c)
{
	return c == ' ' || c == '\t' || c == '\n' || c == '\r' || c == '\f';
}

// Field must not contain only spaces
function notOnlySpaces (aField, aTitle)
{
	if (aField.value.length == 0) return true;
	var i;
	for (i = 0; i < aField.value.length; i++)
	{
		if (! isWhitespace (aField.value.charAt (i)))
			return true;
	}

	alert (parent.format (STRING_Edit_notOnlySpaces, aTitle));
 	aField.focus ();
	return false;
}

// Check for characters not in ISO-8859
function checkCharCodes (aField, aTitle)
{
	if (aField.value.length == 0) return true;
	var str = aField.value;
	for (i = 0; i < str.length; i++)
	{
		var j = str.charCodeAt (i);
		if ((j > 127 && j < 160) || j > 255)
		{
			alert (parent.format (STRING_Edit_illegalChars, aTitle, str.charAt (i)));
			aField.focus ();
			return false;
		}
	}
	return true;
}

// Check for forbidden characters
function mustNotContain (aField, aTitle, someChars)
{
	if (aField.value.length == 0) return true;
	var i;
	for (i = 0; i < someChars.length; i++)
	{
		if (aField.value.indexOf (someChars.charAt (i)) != -1)
		{
			alert (parent.format (STRING_Edit_mustNotContain, aTitle, someChars));
	  	aField.focus ();
			return false;
		}
	}

	return true;
}

// Checks if date1 is before date2: aFormat may contain only "dd", "MM" and "yyyy" !
function isDateBefore (date1, date2, aFormat)
{
	var d1 = parseDate (date1, aFormat);
	var d2 = parseDate (date2, aFormat);
	year1  = d1.getFullYear ();
	year2  = d2.getFullYear ();
	month1 = d1.getMonth ();
	month2 = d2.getMonth ();
	day1   = d1.getDate ();
	day2   = d2.getDate ();
	return !(year1 > year2 ||
			    (year1 == year2 && month1 > month2) ||
			    (year1 == year2 && month1 == month2 && day1 > day2));
}

// Helper function. Don't use it.
function readNumberFromStart (aString)
{
	var result = "";
	var pos = 0;
	while (pos < aString.length && !isNaN (Number (aString.charAt (pos))))
		result += aString.charAt (pos++);
	return result;
}

// Parses a date from a string in a specific date format: aFormat may contain only "dd", "MM" and "yyyy" !
function parseDate (aText, aFormat)
{
  if (aText == null || aText.length == 0)
		return new Date ();
	var value = aText;
	var format = (typeof (aFormat) == "undefined" || aFormat == null) ? "dd.MM.yyyy" : aFormat;

	var day   = -1;
	var month = -1;
	var year  = -1;
	while (format.length > 0)
	{
		if (format.indexOf ("dd") == 0)
		{
			dayString = readNumberFromStart (value);
			if (dayString.length > 2) return null;
			day = parseInt (dayString, 10);
			if (isNaN (day)) return null;
			format = format.substring (2);
			value = value.substring (dayString.length);
		}
		else if (format.indexOf ("MM") == 0)
		{
			monthString = readNumberFromStart (value);
			if (monthString.length > 2) return null;
			month = parseInt (monthString, 10);
			if (isNaN (month)) return null;
			format = format.substring (2);
			value = value.substring (monthString.length);
		}
		else if (format.indexOf ("yyyy") == 0)
		{
			yearString = readNumberFromStart (value);
			if (yearString.length != 4) return null;
			year = parseInt (yearString, 10);
			if (isNaN (year)) return null;
			format = format.substring (4);
			value = value.substring (yearString.length);
		}
		else
		{
			if (value.length == 0 || format.charAt (0) != value.charAt (0))
				return null;
			format = format.substring (1);
			value = value.substring (1);
		}
	}

	if (day <= 0 || day > 31 || month <= 0 || month > 12 || year < 100)
		return null;

	return new Date (year, month - 1, day);
}

// Validate the date in a field: aFormat may contain only "dd", "MM" and "yyyy" !
function validateDateIn (aField, aTitle, aFormat)
{
	var aFormat = (typeof (aFormat) == "undefined" || aFormat == null) ? "dd.MM.yyyy" : aFormat;
  if (aField == null || aField.value.length == 0 || parseDate (aField.value, aFormat) != null)
		return true;
	alert (parent.format (STRING_Edit_reportInvalidDateIn + aFormat, aTitle));
	aField.focus ();
	return false;
}

// Parses a time from a string in a specific date format: aFormat may contain only "HH" and "mm" !
function parseTime (aText, aFormat)
{
  if (aText == null || aText.length == 0)
		return new Date ();
	var value = aText;
	var format = (typeof (aFormat) == "undefined" || aFormat == null) ? "HH:mm" : aFormat;

	var hour    = -1;
	var minutes = -1;
	while (format.length > 0)
	{
		if (format.indexOf ("HH") == 0)
		{
			hourString = readNumberFromStart (value);
			if (hourString.length > 2) return null;
			hour = parseInt (hourString, 10);
			if (isNaN (hour)) return null;
			format = format.substring (2);
			value = value.substring (hourString.length);
		}
		else if (format.indexOf ("mm") == 0)
		{
			minutesString = readNumberFromStart (value);
			if (minutesString.length > 2) return null;
			minutes = parseInt (minutesString, 10);
			if (isNaN (minutes)) return null;
			format = format.substring (2);
			value = value.substring (minutesString.length);
		}
		else
		{
			if (value.length == 0 || format.charAt (0) != value.charAt (0))
				return null;
			format = format.substring (1);
			value = value.substring (1);
		}
	}

	if (hour < 0 || hour > 23 || minutes < 0 || minutes > 59)
		return null;
	
	return new Date (0, 0, 0, hour, minutes, 0, 0);
}

// Validate the time in a field: aFormat may contain only "HH" and "mm" !
function validateTimeIn (aField, aTitle, aFormat)
{
	var aFormat = (typeof (aFormat) == "undefined" || aFormat == null) ? "HH:mm" : aFormat;
  if (aField == null || aField.value.length == 0 || parseTime (aField.value, aFormat) != null)
		return true;
	alert (parent.format (STRING_Edit_reportInvalidTimeIn + aFormat, aTitle));
	aField.focus ();
	return false;
}

// Returns the date of x months in the future
function inXMonths (months)
{
	var today = new Date ();
	var month = today.getMonth ();
	if (month >= 12 - months)
		today.setYear (today.getFullYear () + 1);
	today.setMonth ((month + months) % 12);
	return today;
}

// Formats a number as a two digit string
function twoDigits (number)
{
	return number < 10 ? ("0" + number) : number;
}

// Formats a date as "yyyy-MM-dd'T'HH:mm:ss.SS"
function formatDate (date)
{
	var offset = date.getTimezoneOffset () * (-1);
	return date.getFullYear () + "-" + twoDigits (date.getMonth () + 1) + "-" + twoDigits (date.getDate ()) + "T" + 
	       twoDigits (date.getHours ()) + ":" + twoDigits (date.getMinutes ()) + ":" + twoDigits (date.getSeconds ()) + "." + date.getMilliseconds ();
}

// Get a date from a field which is formatted as "yyyy-MM-dd'T'HH:mm:ss.SS".
function getFormattedDate (aField, aFormat)
{
	var date = parseDate (aField.value, aFormat);
	return date == null ? null : formatDate (date);
}

// Get a date/time from a date field and a time field which is formatted as "yyyy-MM-dd'T'HH:mm:ss.SS".
function getFormattedDateTime (aDateField, aTimeField, aDateFormat, aTimeFormat)
{
	var date = parseDate (aDateField.value, aDateFormat);
	var time = parseTime (aTimeField.value, aTimeFormat);
	if (date == null || time == null)
		return null;
	date.setHours (time.getHours ());
	date.setMinutes (time.getMinutes ());
	date.setSeconds (time.getSeconds ());
	date.setMilliseconds (time.getMilliseconds ());
	return formatDate (date);
}

//////////////////////////////////////////////////////////////////////
//
//  Validation of input in the edit forms.
//

// Validates on submit	
function submitForm (form)
{
	if (!form) form = document.forms[0];
	if (validate (form))
		form.submit ();
}

// Confirm dialog for deleting a layout file
function areYouSure ()
{
	if (confirm (STRING_Edit_areYouSure))
	  location.href='?command=deleteDisplayPage';
}

// Focus to the first element in the form	
function focusFirstElement (form)
{
	if (!form) form = document.forms[0];
	for (i = 0; i < form.length; i++)
	{ 
		if (form.elements[i].type != 'hidden')
		{ 	
			form.elements[i].focus();
			break;
		}
	}
}
	
// Function validate: Validate the user-input
var moreValidations = new Array ();
function validate (form)
{
	if (!form) form = document.forms[0];

	if (parseInt (form.category.value) != 8)	// Links have no name
	{
		if (! mustNotBeNull (form.name, STRING_Edit_validate_Name)) return false;
		if (! notOnlySpaces (form.name, STRING_Edit_validate_Name)) return false;
		if (! checkLengthOn (form.name, STRING_Edit_validate_Name, 24)) return false;
		if (! mustNotContain (form.name, STRING_Edit_validate_Name, "\\/*?\"<>|")) return false;
	}
	if (! checkLengthOn (form.title, STRING_Edit_validate_Title, 255))  return false;
	if (! notOnlySpaces (form.title, STRING_Edit_validate_Title)) return false;
	if (! checkLengthOn (form.comment, STRING_Edit_validate_Comment, 600))  return false;
	if (! checkLengthOn (form.Abstract, STRING_Edit_validate_Abstract, 4000))  return false;
	if (! checkLengthOn (form.extraDescriptors, STRING_Edit_validate_Descritors, 255))  return false;

	if (form.descriptors)
	{
		var descs = "";
		for (i = 0; i < form.descriptors.length; i++)
			descs += form.descriptors.options[i].value + ",";
		form.allDescriptors.value = descs;
	}
	
	if (form.attachment)
	{
		if (form.attachment[0].checked)
			form.int1.value = 0;
		else if (form.attachment[1].checked)
			form.int1.value = -1;
		else if (isNaN (form.int1.value))
		{
			alert (STRING_Edit_validate_Limit);
	 		form.int1.focus ();
			return false;
		}
	}
	
	for (mvals = 0; mvals < moreValidations.length; mvals++)
	{
		if (! moreValidations[mvals]())
			return false;
	}
	
	return true;
}

function registerValidation (aValidationFunction)
{
	moreValidations[moreValidations.length] = aValidationFunction;
}

function addDescriptor (id, term, form)
{
	if (!form) form = document.forms[0];
	var descsSX = new SelectX (form.descriptors);
	if (! descsSX.contains (id))
		descsSX.add (term, id);
}

// Removes a descriptor from the list
function removeDescriptors (form)
{
	if (!form) form = document.forms[0];
	var descs = form.descriptors;
	for (i = descs.length; i > 0; i--)
		if (descs.options[i - 1].selected) descs.options[i - 1] = null;
}

