//
function _round(num, d)
{
  n = Math.pow(10, !d ? 2 : d);
  return Math.round(num*n) / n;
}

//Returns the selected button index of a group, given a pointer to a button group
function getselectedbutton(buttongroup) {
  for (var i=0; i<buttongroup.length; i++ ) {
    if (buttongroup[i].checked) {
	  return i
    }
  }
}

function getselectedname(buttongroup) {
  var index = getselectedbutton(buttongroup);
  return buttongroup[index].value;
}

// Returns true if a string contains only whitespace characters
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;
}

function isvaliddatetime(dateStr)
{
  return isvaliddate(dateStr,true);
}

function isvaliddate(dateStr,withTime)
{
  // Checks for the following valid date formats:
  // MM/DD/YY   MM/DD/YYYY   MM-DD-YY   MM-DD-YYYY
  // Also separates pieces into variables
  // Time formats are:
  // h:mm AM/PM hh:mm AM/PM h:mm:ss AM/PM hh:mm:ss AM/PM

  // TODO: 24 hour time support?

  var datePat;

  // To require a 4 digit year entry, use this line instead:
  // var datePat = /^(\d{1,2})(\/|-)(\d{1,2})\2(\d{4})$/;
  if (withTime)
	datePat = /^(\d{1,2})(\/|-)(\d{1,2})\2(\d{2}|\d{4})\s(\d{1,2}):(\d{2})(:(\d{2}))?\s*(AM|PM|am|pm)$/;
  else
    datePat = /^(\d{1,2})(\/|-)(\d{1,2})\2(\d{2}|\d{4})$/;

  var matchArray = dateStr.match(datePat); // is the format ok?
  if (matchArray == null) 
  {
    return false;
  }
  month = matchArray[1]; // parse date into variables
  day = matchArray[3];
  year = matchArray[4];

  if (withTime)
  {
    hours = matchArray[5];
	minutes = matchArray[6];
	seconds = matchArray[8]; // optional
	ampm = matchArray[9];

    // 0 is midnight according to SQL.  Let them put it in
    if (hours<0 || hours > 12)
    {
	  return false;
    }
	if (minutes <0 || minutes > 59)
	{
	  return false;
	}
	if (seconds!='' && (seconds<0 || seconds > 59) )
	{
	  return false;
	}
  }

  if (month < 1 || month > 12) 
  {
    return false;
  }
  if (day < 1 || day > 31) 
  {
    return false;
  }
  if ((month==4 || month==6 || month==9 || month==11) && day==31) 
  {
    return false
  } 
  if (month == 2) // check for leap year
  { 
    var isleap = (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
    if (day>29 || (day==29 && !isleap)) 
    {
      return false;
    }
  }
  return true;
}

// Safari has a bug just passing this string in to make a date obj, make it here instead
function getdateobj(dateStr,withTime)
{
    var datePat;
    var d;

  // To require a 4 digit year entry, use this line instead:
  // var datePat = /^(\d{1,2})(\/|-)(\d{1,2})\2(\d{4})$/;
  if (withTime)
  	datePat = /^(\d{1,2})(\/|-)(\d{1,2})\2(\d{2}|\d{4})\s(\d{1,2}):(\d{2})(:(\d{2}))?\s*(AM|PM|am|pm)$/;
  else
    datePat = /^(\d{1,2})(\/|-)(\d{1,2})\2(\d{2}|\d{4})$/;

  var matchArray = dateStr.match(datePat); // is the format ok?
  if (matchArray == null) 
  {
    return false;
  }
  var month = matchArray[1]; // parse date into variables
  var day = matchArray[3];
  var year = matchArray[4];

  d = new Date();

  if (year <1970)
    year = year + 100;  

  d.setFullYear(year,month-1,day);

  if (withTime)
  {
    var hours = Number(matchArray[5]);
	  var minutes = matchArray[6];
	  var seconds = matchArray[8]; // optional
    var ampm = matchArray[9];
    
    if (ampm=="PM" || ampm=="PM")
      hours += 12;
      
    if (hours==12 && (ampm=="AM" || ampm=="AM"))
      hours = 0;
    
    d.setHours(hours);
    d.setMinutes(minutes);
    if (seconds!='')
      d.setSeconds(seconds);
    else
      d.setSeconds(0);
  }

  return d;

}

function isvalidemail(emailstr)
{
  var valid    = true;
  var atsymbol = emailstr.indexOf('@');
  var dot      = emailstr.lastIndexOf('.');
  var space    = emailstr.indexOf(' ');
  var len      = emailstr.length - 1;

  if ((atsymbol < 1) ||            // '@' cannot be in first position
      (dot <= atsymbol+1) ||       // Must be atleast one valid char btwn '@' and '.'
      (dot == len ) ||             // Must be atleast one valid char after '.'
      (space != -1))               // No empty spaces permitted
     {  
       valid = false
     }
  return valid;
}

// override to add custom error checking after regular error checking
function customvalidate(f,errors)
{
  // example
  //if ( parseInt(f.start_date.value) >= parseInt(f.stop_date.value) )
  //  errors += "- The field stop_date must be greater than the field start_date.\n"

  return errors;
}

// override to set values before validating, passed form reference
function initvalidate(f)
{
  // Field options
  // optional, email, date, min, max, numeric, real, integer
  // * numeric is deprecated.  Please use real or integer
  
  // ex1) set a field to optional and validate e-mail
  // f.email.optional=true;
  // f.email.email=true;
  
  // ex2) set a field to numeric (real)
  // f.age.real=true;
  // f.age.min=1;
  // f.age.max=120;

  // ex4) check for valid date
  // f.startdate.date=true;
}

// Verifies if the form is filled out correctly and displays an error with what's wrong if it isn't
function validateform(f)
{
  var msg;
  var empty_fields = "";
  var errors = "";
  var fieldname = "";
  
  initvalidate(f);

  // any fields that have an "optional" property defined are allowed to be empty

  // loop through all "text" and "textarea" form components and if they are not "optional" add to the empty list
  for (var i=0; i < f.length; i++)
  {
    var e = f.elements[i];
    if (((e.type == "text") || (e.type == "textarea") || (e.type == "password")) && !e.optional)
    {
      // use common name if given, if not use regular name
	  if (e.common!="")
	  {
	    fieldname = e.common;
	  }
	  else
	    fieldname = e.name;
	  
	  // first check if the field is empty
      if ((e.value == null) || (e.value == "") || isblank(e.value))
      {
        empty_fields += "\n       " + fieldname;
        continue;
      }
      else
      {
        // Check minimum field length
		// Note: Maxlength is a property of the INPUT tag itself so no need for it here
		if (e.minlength != null && (e.value.length < e.minlength))
          errors += "- The field " + fieldname + " must be at least " + e.minlength + " chars long.\n";

        // any fields with a "min", "max", or "decplaces" defined are assumed to be real number fields if not designated integer
		if (!e.integer && (e.min!=null || e.max!=null || e.decplaces!=null))
          e.real = true;

        // Now check numeric fields
        if ( e.numeric || e.integer || e.real )
        {
          if (e.numeric || e.real)
		    var v = parseFloat(e.value);
		  else
		    var v = parseInt(e.value);

          // Check if it's a valid number
          if (isNaN(v) || e.value!=v)
          {
            if (e.numeric || e.real)
              errors += "- The field " + fieldname + " must be a valid real number.\n";
            else
              errors += "- The field " + fieldname + " must be a valid integer.\n";

            continue; // skip rest of checking on this field if we already know it's not a number
          }

          // Round if needed
		  if (e.decplaces!=null) {
		    e.value = _round(e.value,e.decplaces);
            v = parseFloat(e.value);
		  }

		  if ( ((e.min != null) && (v < e.min)) || ((e.max != null) && (v > e.max)) ) 
          {
            errors += "- The field " + fieldname + " must be a number";
            if (e.min != null)
              errors += " that is greater than or equal to " + e.min;
            if (e.max != null && e.min != null)
              errors += " and less than or equal to " + e.max;
            else if (e.max != null)
              errors += " that is less than or equal to " + e.max;
            errors += ".\n";
          }
        }

        if (e.email && !isvalidemail(e.value))
          errors += "- The field " + fieldname + " must be a valid email address.\n";

        if (e.date && !isvaliddate(e.value))
          errors += "- The field " + fieldname + " must be a valid date.\n";        

        if (e.datetime && !isvaliddatetime(e.value))
          errors += "- The field " + fieldname + " must be a valid date and time.\n";        
      }    
    }
  }

  errors = customvalidate(f,errors);
   
  // if there are any errors display them and return false so form is not submitted
  // otherwise return true and the form is sent
  if (!empty_fields && !errors) return true;
  
  msg  = "______________________________________________\n\n";
  msg += "Your request was not submitted because of the following error(s).\n";
  msg += "Please correct and resubmit.\n";
  msg += "______________________________________________\n\n";
  
  if (empty_fields)
  {
    msg += "- The following field(s) are empty:" + empty_fields +"\n";
    if (errors) msg += "\n";
  }
 
  msg += errors;
  alert(msg);
  return false;
}
