var nbsp = 160;					// non-breaking space char
var node_text = 3;				// DOM text node-type
var emptyString = /^\s*$/ ;		// Empty character (except &nbsp;)
var global_valfield;			// retain valfield for timer thread

// --------------------------------------------
//                  trim
// Trim leading/trailing whitespace off string
// --------------------------------------------
function trim(str) {
	str = str.replace(/^\s+|\s+$/g, '');
	str = str.replace("&nbsp;", "");
	return  str;
}


// --------------------------------------------
//                  setfocus
// Delayed focus setting to get around IE bug
// --------------------------------------------
function setFocusDelayed() {
	global_valfield.focus();
}

function setfocus(valfield) {
	// save valfield in global variable so value retained when routine exits
	global_valfield = valfield;
	setTimeout( 'setFocusDelayed()', 100 );
}


// --------------------------------------------
//                  msg
// Display warn/error message in HTML element.
// commonCheck routine must have previously been called
// --------------------------------------------
function msg(fld,     // id of element to display message in
             msgtype, // class to give element ("warn" or "error")
             message) // string to display
{
	// setting an empty string can give problems if later set to a 
	// non-empty string, so ensure a space present. (For Mozilla and Opera one could 
	// simply use a space, but IE demands something more, like a non-breaking space.)
	var dispmessage;
  	if (emptyString.test(message)) {
		dispmessage = String.fromCharCode(nbsp);    
  	} else  {
		dispmessage = message;
	}
	if (fld)
	{
		var elem = document.getElementById(fld);
		if (!elem.firstChild){
			elem = $(fld);
		}
		elem.firstChild.nodeValue = dispmessage;  
		elem.className = msgtype;   // set the CSS class to adjust appearance of message
	}
	else
	{
		if(window.alert_box)
		{
			alert_box(dispmessage);
		}
		else
		{
			alert(dispmessage);
		}
	}
}

// --------------------------------------------
//            commonCheck
// Common code for all validation routines to:
// (a) check for older / less-equipped browsers
// (b) check if empty fields are required
// Returns true (validation passed), 
//         false (validation failed) or 
//         proceed (don't know yet)
// --------------------------------------------

var proceed = 2;  

function commonCheck    (valfield,   	// element to be validated
                         infofield,  	// id of element to receive info/error msg
                         required) 		// true if required
{

	if (!document.getElementById) return true;  // not available on this browser - leave validation to the server

	var elem = document.getElementById(infofield);
	if (!elem) return true;		// can't get the element!
	if (!elem.firstChild)  return true;  // not available on this browser 
	if (elem.firstChild.nodeType != node_text) return true;  // infofield is wrong type of node  

	if (emptyString.test(valfield.value) || (valfield.value == "")) 
	{
		if (required) 
		{
			msg (infofield, "error", "Error: required field");  
			setfocus(valfield);
			return false;
		}
		else 
		{
			msg (infofield, "warn", "");   // OK
			return true;  
		}
	}
	return proceed;
}

// --------------------------------------------
//            validatePresent
// Validate if something has been entered
// Returns true if so 
// --------------------------------------------
function validatePresent(valfield,   // element to be validated
                         infofield )  // id of element to receive info/error msg
{

  var stat = commonCheck (valfield, infofield, true);
  if (stat != proceed) return stat;
  msg (infofield, "warn", "");
  return true;
}

// --------------------------------------------
//               validateEmail
// Validate if e-mail address
// Returns true if so (and also if could not be executed because of old browser)
// --------------------------------------------
function validateEmail  (valfield,  // element to be validated
                         infofield,  // id of element to receive info/error msg
                         required)   // true if required
{
	var stat = commonCheck (valfield, infofield, required);
	if (stat != proceed) return stat;
	
	var tfld = trim(valfield.value);  // value of field with whitespace trimmed off
	var email = /^[^@]+@[^@.]+\.[^@]*\w\w$/  ;
	if (!email.test(tfld)) {
		msg (infofield, "error", "Error: not a valid e-mail address");
		setfocus(valfield);
		return false;
	}
	
/*	
	var email2 = /^[A-Za-z][\w.-]+@\w[\w.-]+\.[\w.-]*[A-Za-z][A-Za-z]$/  ;
	if (!email2.test(tfld)) 
		msg (infofield, "warn", "Unusual e-mail address - check if correct");
	else
		msg (infofield, "warn", "");
	return true;
*/
	return true;
}


// --------------------------------------------
//            validateTelnr
// Validate telephone number
// Returns true if so (and also if could not be executed because of old browser)
// Permits spaces, hyphens, brackets and leading +
// --------------------------------------------
function validateTelnr  (valfield,   // element to be validated
                         infofield,  // id of element to receive info/error msg
                         required)   // true if required
{
	var stat = commonCheck (valfield, infofield, required);
	if (stat != proceed) return stat;
	
	var tfld = trim(valfield.value);  // value of field with whitespace trimmed off
	var telnr = /^\+?[0-9 ()-]+[0-9]$/  ;
	if (!telnr.test(tfld)) {
		msg (infofield, "error", "Error: not a valid telephone number. Characters permitted are digits, space ()- and leading +");
		setfocus(valfield);
		return false;
	}
	
	var numdigits = 0;
	for (var j=0; j<tfld.length; j++)
		if (tfld.charAt(j)>='0' && tfld.charAt(j)<='9') numdigits++;
	
	if (numdigits<6) {
		msg (infofield, "error", "Error: " + numdigits + " digits - too short");
		setfocus(valfield);
		return false;
	}
	
	if (numdigits>14)
		msg (infofield, "warn", numdigits + " digits - check if correct");
	else { 
		if (numdigits<10)
			msg (infofield, "warn", "Only " + numdigits + " digits - check if correct");
		else
			msg (infofield, "warn", "");
	}
	return true;
}

function checkLength  (valfield,   // element to be validated
                         infofield,  // id of element to receive info/error msg
						 minLength,  // Min length
                         maxLength)   // Max length
{
	var tfld = trim(valfield.value);
	
	if (tfld.length < minLength) {
		msg (infofield, "error", "Error: ID field must be longer then " + minLength + " character. It has "+tfld.length );
		setfocus(valfield);
		return false;
	}

	if (tfld.length > maxLength) {
		msg (infofield, "error", "Error: ID field must be shorter then " + maxLength + " character. It has "+tfld.length );
//		valfield.value = valfield.value.substring(0, maxLength)
		setfocus(valfield);
		return false;
	}

	return true;
}

function checkAlphaNumSpec (valfield,   // element to be validated
                         infofield)  // id of element to receive info/error msg
{
	var tfld = trim(valfield.value);
	if(!isAlphaNumSpec(tfld)){
		msg (infofield, "error", "Error: Must be english character!");
		setfocus(valfield);
		return false;
	}
	return true;
}


function checkIP (valfield,   // element to be validated
                         infofield)
{
	var tfld	= trim(valfield.value);

	var ipPattern = /^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$/;
	var ipArray = tfld.match(ipPattern);

/*
	if (tfld == "0.0.0.0")
	{
		msg (infofield, "error", "Error: "+tfld+" is a special IP address and cannot be used here.");
		setfocus(valfield);
		return false;
	}

	if (tfld == "255.255.255.255")
	{
		msg (infofield, "error", "Error: "+tfld+" is a special IP address and cannot be used here.");
		setfocus(valfield);
		return false;
	}
*/
		
	if (ipArray == null)
	{
		msg (infofield, "error", "Error: "+tfld+" is not a valid IP address.");
		setfocus(valfield);
		return false;
	}
	else
	{
		for (i = 0; i < 4; i++)
		{
			thisSegment = ipArray[i];
			if (thisSegment > 255)
			{
				msg (infofield, "error", "Error: "+tfld+" is not a valid IP address.");
				setfocus(valfield);
				return false;
			}
			
			if ((i == 0) && (thisSegment > 255))
			{
				msg (infofield, "error", "Error: "+tfld+" is a special IP address and cannot be used here.");
				setfocus(valfield);
				return false;
		    }
	   	}
	}
	return true;
}

function getCheckedValue(radioObj)
{
    if(!radioObj)
        return "";
		
    var radioLength = radioObj.length;
	
    if(radioLength == undefined)
        if(radioObj.checked)
            return radioObj.value;
        else
            return "";
			
    for(var i = 0; i < radioLength; i++)
	{
        if(radioObj[i].checked)
		{
            return radioObj[i].value;
        }
    }
	
    return "";
}


<!-- ****************************** 共用測試程式碼 : 開始 ******************************//-->
// 測試輸入格式 : 開始 ********************
var strValid_Number = '0123456789';
var strValid_Lower_Case = 'abcdefghijklmnopqrstuvwxyz';
var strValid_Upper_Case = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ';
var strValid_Special = '_@.-';
var strValid_Space = ' 　';
 
function isValid(strTest_Data, strValid_Data) {
    if (strTest_Data == "") return true;
    for (intLoop = 0; intLoop < strTest_Data.length; intLoop++) {
       if (strValid_Data.indexOf(strTest_Data.charAt(intLoop),0) == -1) return false;
    }
    return true;
}
 
function isNum(strTest_Data) {return isValid(strTest_Data, strValid_Number);}
function isLower(strTest_Data) {return isValid(strTest_Data, strValid_Lower_Case);}
function isUpper(strTest_Data) {return isValid(strTest_Data, strValid_Upper_Case);}
function isAlpha(strTest_Data) {return isValid(strTest_Data, strValid_Lower_Case + strValid_Upper_Case);}
function isAlphaNum(strTest_Data) {return isValid(strTest_Data, strValid_Lower_Case + strValid_Upper_Case + strValid_Number);}
function isAlphaNumSpec(strTest_Data) {return isValid(strTest_Data, strValid_Lower_Case + strValid_Upper_Case + strValid_Number + strValid_Special);}
function isAlphaNumSpecSpace(strTest_Data) {return isValid(strTest_Data, strValid_Lower_Case + strValid_Upper_Case + strValid_Number + strValid_Special + " ");}
function isSpace(strTest_Data) {return isValid(strTest_Data, strValid_Space);}  // 測試空白字元

// 測試輸入格式 : 結束 ********************
function isChinese(strTest_Data){
    if (strTest_Data == "") return true;
	if (escape(strTest_Data).indexOf("%u")!=-1) return true;
	return (/[^\x00-\xff]/g.test(strTest_Data));
}

function chkCharacters(str)  
{  
       var  s  =  str.replace(/\*/g,  "");  
       var  b  =  s.replace(/[^\x00-\xff]/g,"**").length;  
       var  cn=  b  -  s.length;  
       var  en=  s.length  -  cn  +  str.length  -  s.length;  
		if(window.alert_box)
		{
			alert_box("Chinese character = "+  cn  +"  and\r\n English character = "+  en);
		}
		else
		{
		      alert("Chinese character = "+  cn  +"  and\r\n English character = "+  en);
		}
}

function isURL(strTest_Data)
{
	if(strTest_Data.length != 0)
	{
		var j = new RegExp();
		j.compile("^[A-Za-z]+://[A-Za-z0-9-]+\.[A-Za-z0-9]+"); 
		if (!j.test(strTest_Data))
		{ 
			return false;
		}
		else
		{
			return true;
		}
	}
	else
	{
		return false;
	}
}

function isSqlAttack(strTest_Data)
{
	if(strTest_Data.length != 0)
	{
		var objRegExp = new RegExp();
		
		// SQL Meta Data Character
		objRegExp.compile("/((\%3D)|(=))[^\n]*((\%27)|(\')|(\-\-)|(\%3B)|(;))/i"); 
		if (objRegExp.test(strTest_Data))	return true;
		
		// Typical SQL attack
		objRegExp.compile("/\w*((\%27)|(\'))((\%6F)|o|(\%4F))((\%72)|r|(\%52))/ix"); 
		if (objRegExp.test(strTest_Data))	return true;

		// MS SQL attack
		objRegExp.compile("/exec(\s)+(s|x)p\w+/ix"); 
		if (objRegExp.test(strTest_Data))	return true;
	}
	return false;
}

function isCssAttack(strTest_Data)
{
	if(strTest_Data.length != 0)
	{
		var objRegExp = new RegExp();

		// Simple CSS attack
		objRegExp.compile("/((\%3C)|<)((\%2F)|\/)*[a-z0-9\%]+((\%3E)|>)/ix"); 
		if (objRegExp.test(strTest_Data))	return true;
	
		// Image Attack
		objRegExp.compile("/((\%3C)|<)((\%69)|i|(\%49))((\%6D)|m|(\%4D))((\%67)|g|(\%47))[^\n]+((\%3E)|>)/I"); 
		if (objRegExp.test(strTest_Data))	return true;

		// Paranoid Method (Can give false positive response)
		objRegExp.compile("/((\%3C)|<)[^\n]+((\%3E)|>)/I"); 
		if (objRegExp.test(strTest_Data))	return true;
	}
	return false;
}

// *** A simple code to prevent un-authorized access to our site!
// If not from our site.. (Check window opener url first then current page)
var blnSite_Safe = false;
var strLocation = "";
if (window.opener)
{
	strLocation = window.opener.location.toString().toLowerCase();
	if (strLocation.indexOf("http://192.168.1.13") == 0) blnSite_Safe = true;			// Dev Server
	if (strLocation.indexOf("http://192.168.1.103") == 0) blnSite_Safe = true;			// Andre
	if (strLocation.indexOf("http://192.168.1.107") == 0) blnSite_Safe = true;			// Franky
	if (strLocation.indexOf("http://192.168.1.112") == 0) blnSite_Safe = true;			// Alan
	if (strLocation.indexOf("http://www.yougotphoto.com") == 0) blnSite_Safe = true;
	if (strLocation.indexOf("http://yougotphoto.com") == 0) blnSite_Safe = true;
	if (strLocation.indexOf("http://linux.huveur.com") == 0) blnSite_Safe = true;
	if(!blnSite_Safe) window.opener.location="http://www.yougotphoto.com/";
}
strLocation = parent.location.toString().toLowerCase();
if (strLocation.indexOf("http://192.168.1.13") == 0) blnSite_Safe = true;
if (strLocation.indexOf("http://192.168.1.103") == 0) blnSite_Safe = true;
if (strLocation.indexOf("http://192.168.1.107") == 0) blnSite_Safe = true;
if (strLocation.indexOf("http://192.168.1.112") == 0) blnSite_Safe = true;
if (strLocation.indexOf("http://www.yougotphoto.com") == 0) blnSite_Safe = true;
if (strLocation.indexOf("http://yougotphoto.com") == 0) blnSite_Safe = true;
if (strLocation.indexOf("http://linux.huveur.com") == 0) blnSite_Safe = true;
if(!blnSite_Safe) parent.location="http://www.yougotphoto.com/";
<!-- ****************************** 共用測試程式碼 : 結束 ******************************//-->
