/****************************************************************************************************
제목 : Form 검사 Ver 2.0
----------------------------------------------------------------------------------------------------
목적 : Form 검사를 편리하게 하기 위한 함수
----------------------------------------------------------------------------------------------------
주의 :
	1. UTIL.js 가 미리 로드되어 있어야 함.

	2. Form 검사가 완료되면, Form Tag 내에 Textarea Tag 를 추가 ( name="formCheckInformation" ) 하여,
	   Form 검사 속성 ( just , min , max , regular 등 ) 을 함께 전송하게 된다.
	   이렇게 수집된 정보는 osForm.class 에 의하여 데이터 검사가 이뤄지도록 설계되어 있다.

	   이 때 수집되는 정보는 Form Tag 내에 존재하는 모든 Input Tag 의 정보가 되는데,
	   Checkbox 및 Radio 버튼 등과 같이 동일한 name Attribute 를 가지는 Input Tag 의 경우,
	   처음 만나는 Input Tag 의 정보를 참조하도록 설계되어 있다.

	   그러므로, Checkbox 및 Radio 버튼 등과 같은 Input Tag 의 검사 속성 ( just , min , max ) 은
	   맨 처음 출력되는 Input Tag 에 설정해야 정상적으로 처리된다.

	   반대로 모든 Checkbox 와 Radio 버튼에 동일한 검사 속성을 설정해도 프로그램 처리에는 문제가 없으나,
	   Checkbox 및 Radio 버튼의 수 만큼 검사를 하게 되므로, 비 효율적이다.
----------------------------------------------------------------------------------------------------
용법 :
	본 자바스크립트 파일을 Form Tag 이전에 호출 한 뒤, Form Tag 의 Attribute 값을 다음과 같이 설정한다.

	<form name="폼 명칭" method="메소드" action="액션" target="창 이름" onSubmit="return FORM.check ( this )">

	위와 같이 Form Tag 에 onSubmit 의 핸들러 설정을 해야 한다.
	만약, Form Tag 가 아닌, 다른 함수에 의해 Form 을 submit 해야 하는 경우에는 다음과 같이 설정한다.

	FORM.check ( 폼 객체 ) ;

	FORM.check () 함수는 지정 된 Form 을 검사 한 후, 조건에 맞으면 true 맞지 않으면 false 값을 리턴 한다.
----------------------------------------------------------------------------------------------------
속성 : 모든 속성 값은 선택적으로 사용 할 수 있다.

	[ 입력 폼 검사 선택 ]
	just : 1 혹은 0 ( 기본값 : 0 )
		1 : 필수 입력사항으로 공백을 제외한 문자가 입력되어야 한다.
			※ 라디오, 체크박스, 셀렉트의 경우 선택을 해야 한다.
		0 : 일반 입력으로 검사를 진행하지 않는다.
			0 대신에 just 자체를 입력하지 않아도 된다.
		※ just 값은 min , max , regular 에 어떠한 영향도 주지 않는다.

	[ 조건에 의한 검사 여부 ]
	maybe : 해당 Form 내의 checkbox 의 name
		지정된 checkbox 가 checked ( true ) 되어 있으면, 검사를 진행 하며, checked 되어 있지 않다면, 검사를 무시 한다.
		다른 입력 폼의 입력 혹은 수정에 따른 특정 조건에 의하여 검사 여부를 변경해야 하는 경우에 사용 함.

	[ 최소 입력 / 선택 제한 ]
	min : 1 보다 큰 정수 값.
		min 보다 작은 값을 입력 혹은 선택 할 수 없도록 제한 한다.
		checkbox 버튼에 min 값이 지정되면 min 값 만큼 선택을 해야 한다.
		checkbox 버튼에 min , max 값을 모두 입력하면 오류가 발생 할 수 있다.
		radio 버튼에는 사용 할 수 없다.

	[ 최대 입력 / 선택 제한 ]
	max : min 보다 큰 값
		max 보다 큰 값을 입력 혹은 선택 할 수 없도록 제한 한다. ( min 의 기능과 동일 )

	[ 숫자 입력 최대/최소 값 제한 ]
	numMin : 숫자 입력 최소 값.
	numMax : 숫자 입력 최대 값.

	[ 입력 폼 명칭 지정 ]
	nick : 입력 폼 명칭
		입력 폼에 설정된 형식과 맞지 않은경우, 경고창을 통해 안내되는 입력 폼의 이름.

	[ 입력 폼 명칭 접미어 제어 ]
	is : 0 혹은 1 ( 기본값 : 0 )
		0 : 는/를/가/와 ex) 입력 폼 명칭 : "자동차" 인 경우 : 자동차는, 자동차를, 자동차가, 자동차와
		1 : 은/을/이/과 ex) 입력 폼 명칭 : "이름" 인 경우 : 이름은, 이름을, 이름이, 이름과
		nick 에 지정된 입력 폼 명칭과 함께 사용되며, 입력 값 검사 후 오류 메세지를 출력 할 때,
		입력 폼 명칭에 따라 접미를 자동으로 선택하도록 하는 기능을 구현 한다.

	[ 포커스 지정 ]
	leave : Form 내의 입력 폼 name
		해당 입력값을 검사 후, Form Tag 내의 지정한 name 값을 가진 입력폼에 포커스를 준다.
		단 leave 속성을 지정하지 않을 경우에는 자동으로 자신에게 포커스가 지정된다.
		만약, 어디에도 포커스를 지정하지 않고자 하는 경우에는 off 로 설정한다.

	[안내 문구 지정]
	comment : 안내 문구
		안내 문구 값이 존재 하는 경우, 지정된 오류 메세지를 대신하여 안내 문구가 출력된다.

	[ 정규식 검사 ]
	regular : 지정된 정규식 명칭
		지정된 정규식에 따라 타당성 검사를 진행 한다.
		미리 지정되어 있는 명칭을 입력해야 하며, 그 이외의 값을 입력하면 에러가 발생 한다.

		PROTOCOL	: 인터넷 프로토콜	예) http , https , mms
		IP			: IPv4				예) 127.0.0.1
		DOMAIN		: 웹 서버 도메인	예) www.akanaka.com
		PORT		: 웹 서버 포트		예) :12345
		URI			: Query String		예) /home/ver1/index.html?val=1
		EMAIL		: 이메일			예) akanaka@hanmail.net
		URL			: URL				예) http://www.akanaka.com/home/ver1/index.html?val=1
		TEL			: 일반전화			예) 02-1234-1234~1234
		PHONE		: 핸드폰			예) 010-1234-1234
		FAX			: 팩스				예) 02-1234-1234~1234
		ID			: 아이디
		PASSWORD	: 비밀번호
		PID			: 주민 등록 번호	예) 123456-1234567
		BID			: 사업자 등록 번호	예) 123-12-12345
		CID			: 법인 등록 번호	예) 123456-1234567
		POSTAL		: 우편 번호			예) 123-123
		DATE		: 날짜				예) 1234-12-12
		NUMBER		: 숫자				예) 123456
		DECIMAL		: 정수				예) +123,456
		FLOAT		: 실수				예) -123,456.123
		MONEY		: 금액				예) \+123,456.123 , $-123,123
		HANGULE		: 한글
		ENGLISH		: 영문
		SPECIAL		: 특수문자
		STRING		: 한글 , 영문 , 숫자를 포함 ( 공백 , 특수문자 제외 ) 한다.


	예)

	<input type="text" name="id" size="12" maxlength="20" nick="아이디" just="1" min="5" max="20" regular="id">
	필수 검사이며, 최소 5자리 최대 20자리 내의 문자열을 허용하고 id 정규식 검사를 따른다.
	※ regular 속성이 있는 경우에는 just, min, max 값을 생략 할 수 있다.

	<input type="text" name="id" size="12" maxlength="20" nick="아이디" regular="id">
	필수 검사가 아니며, 입력 값이 있는 경우 id 정규식 검사를 따른다.
	※ just, min, max 를 제외한 경우

----------------------------------------------------------------------------------------------------
POST
----------------------------------------------------------------------------------------------------
GET
----------------------------------------------------------------------------------------------------
REQUEST
----------------------------------------------------------------------------------------------------
작성자 : 고광진 (akanaka)
작성일 : 2007년 11월 22일
수정일 : 2009년 06월 12일
연락처 : akanaka@hanmail.net
****************************************************************************************************/


var FORM = new Object () ;


/**************************************************
실행 : 기본형
--------------------------------------------------
**************************************************/
FORM.run = function ()
{
	FORM.set.variable () ;
}


FORM.set = new Object () ;


/**************************************************
변수 선언
--------------------------------------------------
**************************************************/
FORM.set.variable = function ()
{
	try
	{
		FORM.v							= new Object () ;
		FORM.v.pattern					= new Array () ;
		FORM.v.pattern["PROTOCOL"]		= /^(HTTPS?|FTPS?|FILE|TELNET|NEWS|GOPHER|MMS|SVN)(?:\:\/\/|%3A%2F%2F)?$/i ;
		FORM.v.pattern["IP"]			= /^[0-9]{2,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$/ ;
		FORM.v.pattern["DOMAIN"]		= /^(?:[a-z0-9]{1}[a-z0-9\_\-]*\.)*(?:[a-z0-9]{1}[a-z0-9\_\-]{1,62})\.(?:[a-z]{2}\.)?(?:[a-z]{2,4})$/i ;
		FORM.v.pattern["PORT"]			= /^(?:\:|%3A)([0-9]{1,5})$/ ;
		FORM.v.pattern["URI"]			= /^((?:(?:[\%|\/|\?|\#|\&|\~|\!|\@]{1}|\%[a-f0-9]{2})(?:[0-9a-z가-힝\%|\/|\?|\#|\&|\~|\!|\@\$\(\)\*\+\-\,\.\_\:\;\=\[\]\^])+)*)+$/i ;
		FORM.v.pattern["EMAIL"]			= /^([a-z0-9_\-]+)@((?:[a-z0-9]{1}[a-z0-9\_\-]*\.)*(?:[a-z0-9]{1}[a-z0-9\_\-]{1,62})\.(?:[a-z]{2}\.)?(?:[a-z]{2,4}))$/i ;
		FORM.v.pattern["URL"]			= /^(?:(HTTPS?|FTPS?|FILE|TELNET|NEWS|GOPHER|MMS|SVN)(?:\:\/\/|%3A%2F%2F))([0-9]{2,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}|(?:[a-z0-9]{1}[a-z0-9\_\-]*\.)*(?:[a-z0-9]{1}[a-z0-9\_\-]{1,62})\.(?:[a-z]{2}\.)?(?:[a-z]{2,4}))(?:(?:\:|%3A)([0-9]{1,5}))?((?:(?:[\%|\/|\?|\#|\&|\~|\!|\@]{1}|\%[a-f0-9]{2})(?:[0-9a-z가-힝\%|\/|\?|\#|\&|\~|\!|\@\$\(\)\*\+\-\,\.\_\:\;\=\[\]\^])+)*)?$/i ;
		FORM.v.pattern["TEL"]			= /^(?:(0[0-9]{1,2})\-(?:[1-9]{1}[0-9]{1,3})|(?:15|16)[0-9]{2})\-(?:[0-9]{4})(?:[\-|~]?[0-9]{1,5})?$/ ;
		FORM.v.pattern["FAX"]			= /^(?:(0[0-9]{1,2})\-(?:[1-9]{1}[0-9]{1,3})|(?:15|16)[0-9]{2})\-(?:[0-9]{4})$/ ;
		FORM.v.pattern["PHONE"]			= /^(?:010|011|016|017|018|019)\-(?:[1-9]{1}[0-9]{2,4})\-(?:[0-9]{4})$/ ;
		FORM.v.pattern["ID"]			= /^[a-zA-Z]{1}[a-zA-Z0-9_\-]{3,19}$/ ;
		FORM.v.pattern["PASSWORD"]		= /^[a-zA-Z0-9]{1}[a-zA-Z0-9_\-\!\@\#\$\%\^\&\*\(\)\=>\+\,\.\/\:]{5,19}$/ ;
		FORM.v.pattern["PID"]			= /^([0-9]{2}[0-1]{1}[0-9]{1}[0-3]{1}[0-9]{1})\-?([1-4]{1}[0-9]{6})$/ ;
		FORM.v.pattern["BID"]			= /^([0-9]{3})-?([0-9]{2})-?([0-9]{5})$/ ;
		FORM.v.pattern["CID"]			= /^([0-9]{6})\-([0-9]{7})$/ ;
		FORM.v.pattern["POSTAL"]		= /^([0-9]{3})\-([0-9]{3})$/ ;
		FORM.v.pattern["DATE"]			= /^([0-9]{3}[0-9]{1})\-([0-1]{1}[0-9]{1})\-([0-3]{1}[0-9]{1})$/ ;
		FORM.v.pattern["NUMBER"]		= /^([0-9]+)$/ ;
		FORM.v.pattern["DECIMAL"]		= /^(\+|\-)?([0-9\,]+)$/ ;
		FORM.v.pattern["FLOAT"]			= /^(\+|\-)?([0-9\,]+)(?:\.([0-9]+))$/ ;
		FORM.v.pattern["MONEY"]			= /^([\\\|\$|￦|＄|￡|￥|€]?)(\+|\-)?([0-9\,]+)(?:\.([0-9]+))?$/ ;
		FORM.v.pattern["HANGULE"]		= /^[가-힝]+$/ ;
		FORM.v.pattern["ENGLISH"]		= /^[a-zA-Z]+$/ ;
		FORM.v.pattern["SPECIAL"]		= /^[\~\`\!\@\#\$\%\^\&\*\(\)\-\_\=\+\{\}\[\]\|\\\;\:\'\"\,\.\<\>\/\?]+$/ ;
		FORM.v.pattern["STRING"]		= /^[가-힝a-zA-Z0-9]+$/ ;
		FORM.v.message					= new Array () ;
		FORM.v.message["PROTOCOL"]		= "[name][is:2] 형식에 맞지 않습니다.\n\n알려지지 않은 [name][is:0] 지원하지 않습니다." ;
		FORM.v.message["IP"]			= "[name][is:2] 형식에 맞지 않습니다.\n\n[name][is:1] 확인 후, 다시 시도하여 주십시오." ;
		FORM.v.message["DOMAIN"]		= "[name][is:2] 형식 ( HTTP:// 제외 ) 에 맞지 않습니다.\n\n[name][is:1] 확인 후, 다시 시도하여 주십시오." ;
		FORM.v.message["PORT"]			= "[name][is:2] 형식에 맞지 않습니다.\n\n[name][is:1] 확인 후, 다시 시도하여 주십시오." ;
		FORM.v.message["URI"]			= "[name][is:2] 형식에 맞지 않습니다.\n\n[name][is:1] 확인 후, 다시 시도하여 주십시오." ;
		FORM.v.message["EMAIL"]			= "[name][is:2] 형식에 맞지 않습니다.\n\n영문자와 숫자로 구성된 [name][is:1] 입력하여 주십시오." ;
		FORM.v.message["URL"]			= "[name][is:2] 형식에 맞지 않습니다.\n\n알려지지 않은 [name][is:0] 지원하지 않습니다." ;
		FORM.v.message["TEL"]			= "[name][is:0] 숫자와 특수문자 ( - ~ 공백 불가 ) 만으로 입력해야 합니다.\n\n형식 ( 123-1234-1234~1 ) 에 맞게 [name][is:1] 입력하여 주십시요." ;
		FORM.v.message["FAX"]			= "[name][is:0] 숫자와 특수문자 ( - 공백 불가 ) 만으로 입력해야 합니다.\n\n형식에 맞게 [name][is:1] 입력하여 주십시요." ;
		FORM.v.message["PHONE"]			= "[name][is:0] 숫자와 특수문자 ( - 공백 불가 ) 만으로 입력해야 합니다.\n\n형식에 맞게 [name][is:1] 입력하여 주십시요." ;
		FORM.v.message["ID"]			= "[name][is:0] 영문자와 숫자, 그리고 특수문자 ( - _ ) 만 사용이 가능합니다.\n\n첫 시작 글자는 영문자이어야 하며 한글은 사용하실 수 없습니다.\n\n최소 4글자 이상, 최대 20글자 이내로 입력하여 주십시오." ;
		FORM.v.message["PASSWORD"]		= "[name][is:0] 영문자와 숫자, 그리고 특수문자 ( - _ 외 다수 ) 만 사용이 가능합니다.\n\n최소 6글자 이상, 최대 20글자 이내로 입력하여 주십시오." ;
		FORM.v.message["PID"]			= "[name][is:0] 숫자와 특수문자 ( - ) 만으로 입력해야 합니다.\n\n형식 ( 예 : 123456-1234567 ) 에 맞게 입력하여 주십시오." ;
		FORM.v.message["BID"]			= "[name][is:0] 숫자와 특수문자 ( - ) 만으로 입력해야 합니다.\n\n형식 ( 예 : 123-12-12345 ) 에 맞게 입력하여 주십시오." ;
		FORM.v.message["POSTAL"]		= "[name][is:0] 숫자와 특수문자 ( - ) 만으로 입력해야 합니다.\n\n형식 ( 예 123-123 ) 에 맞게 입력하여 주십시오." ;
		FORM.v.message["DATE"]			= "[name][is:0] 숫자와 특수문자 ( - ) 만으로 입력해야 합니다.\n\n형식 ( 예 : 1234-12-12 ) 에 맞게 입력하여 주십시오." ;
		FORM.v.message["NUMBER"]		= "[name][is:0] 숫자만 입력이 가능합니다." ;
		FORM.v.message["DECIMAL"]		= "[name][is:0] 숫자와 특수문자 ( + - , ) 만 입력이 가능합니다." ;
		FORM.v.message["FLOAT"]			= "[name][is:0] 숫자와 특수문자 ( + - , . ) 만 입력이 가능합니다." ;
		FORM.v.message["MONEY"]			= "[name][is:0] 금액을 표기하기 위하여 숫자와 특수문자 ( + - , . ) 만으로 입력하셔야 합니다." ;
		FORM.v.message["HANGULE"]		= "[name][is:0] 한글만 입력 하실 수 있습니다.\n\n공백도 허용되지 않으므로, 입력 사항을 확인하여 주십시오." ;
		FORM.v.message["ENGLISH"]		= "[name][is:0] 영문만 입력 하실 수 있습니다.\n\n공백도 허용되지 않으므로, 입력 사항을 확인하여 주십시오." ;
		FORM.v.message["SPECIAL"]		= "[name][is:0] 특수문자 ( 예 : % & ^ # : ; { } [ ] - _ + = 등 )에 한하여 입력이 가능합니다.\n\n공백도 허용되지 않으므로, 입력 사항을 확인하여 주십시오." ;
		FORM.v.message["STRING"]		= "[name][is:0] 특수문자 ( 예 : @ # . - 등 ) 를 제외한 한글, 영어, 숫자만 입력이 가능합니다.\n\n공백도 허용되지 않으므로, 입력 사항을 확인하여 주십시오." ;
		FORM.v.is						= new Array ( new Array ( '는' , '를' , '가' , '와' ) , new Array ( '은' , '을' , '이' , '과' ) ) ;
		FORM.v.code						= new Array () ;
		FORM.v.code["telephone"]		= new Array ( '070' , '080' , '02' , '031' , '032' , '033' , '041' , '042' , '043' , '051' , '052' , '053' , '054' , '055' , '061' , '062' , '063' , '064' ) ;
		FORM.v.code["handphone"]		= new Array ( '010' , '011' , '016' , '017' , '018' , '019' ) ;
		FORM.v.submit					= new Array () ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , 'FORM 객체 초기화에 실패하였습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


FORM.justness = new Object () ;


/**************************************************
타당성 검사 : 전화번호
--------------------------------------------------
input	: 입력 폼 객체
**************************************************/
FORM.justness.TEL = function ( input )
{
	try
	{
		var inputSplit = input.value.split ( '-' ) ;
		for ( i in FORM.v.code["telephone"] )
		{
			if ( inputSplit[0] == FORM.v.code["telephone"][i] ) return true ;
		}
		for ( i in FORM.v.code["handphone"] )
		{
			if ( inputSplit[0] == FORM.v.code["handphone"][i] ) return true ;
		}
		return false ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '타당성 검사 ( TEL ) 에서 오류가 발생되었습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


/**************************************************
타당성 검사 : 주민등록번호
--------------------------------------------------
input	: 입력 폼 객체
**************************************************/
FORM.justness.PID = function ( input )
{
	try
	{
		var i , pid , sum = 0 , multiply = new Array ( 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 2 , 3 , 4 , 5 ) ;
		var pid	= UTIL.convert.trim ( input.value ) ;
		if ( ! FORM.v.pattern["PID"].test ( pid ) ) return false ;
		if ( ( RegExp.$1 + RegExp.$2 ) == '1111111111118' ) return false ;
		pid = ( RegExp.$1 + RegExp.$2 ).split ( '' ) ;
		for ( i = 0 ; i < 12 ; i ++ )
		{
			if ( isNaN ( pid[i] ) == true ) return false ;
			sum	= sum + ( parseInt ( pid[i] , 10 ) * multiply[i] ) ;
		}
		if ( ( 11 - ( sum % 11 ) ) % 10 != parseInt ( pid[12] , 10 ) ) return false ;
		input.value	= RegExp.$1 + '-' + RegExp.$2 ;
		return true ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '타당성 검사 ( PID ) 에서 오류가 발생되었습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


/**************************************************
타당성 검사 : 사업자 등록번호 검사
--------------------------------------------------
input	: 입력 폼 객체
**************************************************/
FORM.justness.BID = function ( input )
{
	try
	{
		var i , bid , sum = 0 , multiply = new Array ( 1 , 3 , 7 , 1 , 3 , 7 , 1 , 3 , 5 ) ;
		var bid	= UTIL.convert.trim ( input.value ) ;
		if ( ! FORM.v.pattern["BID"].test ( bid ) ) return false ;
		if ( ( RegExp.$1 + RegExp.$2 + RegExp.$3 ) == '1231212345' ) return false ;
		bid = ( RegExp.$1 + RegExp.$2 + RegExp.$3 ).split ( '' ) ;
		for ( i = 0 ; i < 9 ; i ++ )
		{
			if ( isNaN ( bid[i] ) == true ) return false ;
			sum	= sum + ( parseInt ( bid[i] , 10 ) * multiply[i] ) ;
		}
		sum	= ( 10 - ( ( ( bid[8] / 2 ) + sum ) % 10 ) ) % 10 ;
		if ( parseInt ( bid[9] , 10 ) != sum ) return false ;
		input.value	= RegExp.$1 + '-' + RegExp.$2 + '-' + RegExp.$3 ;
		return true ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '타당성 검사 ( BID ) 에서 오류가 발생되었습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


/**************************************************
타당성 검사 : 법인 등록번호 검사
--------------------------------------------------
**************************************************/
FORM.justness.CID = function ( input )
{
	try
	{
		var i , j = 0 , cid , sum = 0 ;
		var cid	= UTIL.convert.trim ( input.value ) ;
		if ( ! FORM.v.pattern["CID"].test ( cid ) ) return false
		cid = ( RegExp.$1 + RegExp.$2 ).split ( '' ) ;
		for ( i = 0 ; i < 12 ; i ++ )
		{
			if ( isNaN ( cid[i] ) == true ) return false ;
			sum = sum + ( parseInt ( cid[i] , 10 ) * j ) ;
			j ++ ;
		}
		sum	= ( 10 - ( sum % 10 ) ) %10 ;
		if ( parseInt ( cid[12] , 10 ) != sum ) return false ;
		input.value	= RegExp.$1 + '-' + RegExp.$2 + '-' + RegExp.$3 ;
		return true ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '타당성 검사 ( CID ) 에서 오류가 발생되었습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


FORM.get = new Object () ;


/**************************************************
패턴 반환
--------------------------------------------------
regular	: 정규식 검사 패턴 이름
**************************************************/
FORM.get.pattern = function ( regular )
{
	try
	{
		if ( ! FORM.v.pattern[regular] )
			UTIL.echo.error ( errorCode , '존재하지 않는 패턴 ( ' + regular + ' ) 입니다.' ) ;
		return FORM.v.pattern[regular] ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '정규식 패턴 정보 반환에 실패하였습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


/**************************************************
오류 메세지
--------------------------------------------------
input	: 입력 폼 객체
**************************************************/
FORM.get.message = function ( input )
{
	try
	{
		var i , message , temp ;
		if ( ! FORM.v.message[input.regular] )
			UTIL.echo.error ( errorCode , '존재하지 않는 오류 메세지 ( ' + input.regular + ' ) 입니다.' ) ;
		message	= FORM.v.message[input.regular].split ( '[name]' ).join ( input.nick ) ;
		for ( i = 0 ; i < FORM.v.is[input.is].length ; i ++ )
		{
			temp	= message.split ( '[is:' + i + ']' ) ;
			if ( temp.length == 1 ) continue ;
			message	= temp.join ( FORM.v.is[input.is][i] ) ;
		}
		return message ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '오류 안내 메세지 반환에 실패하였습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


/**************************************************
Input 객체 Attribute 반환
--------------------------------------------------
input	: 입력 폼 객체
**************************************************/
FORM.get.attribute = function ( input )
{
	try
	{
		input.nick		= UTIL.get.attribute ( input , 'nick' ) ;
		input.leave		= UTIL.get.attribute ( input , 'leave' ) ;
		input.comment	= UTIL.get.attribute ( input , 'comment' ) ;
		input.min		= UTIL.get.attribute ( input , 'min' ) ;
		input.max		= UTIL.get.attribute ( input , 'max' ) ;
		input.numMin	= UTIL.get.attribute ( input , 'numMin' ) ;
		input.numMax	= UTIL.get.attribute ( input , 'numMax' ) ;
		input.name		= UTIL.get.attribute ( input , 'name' ) ;
		input.maybe		= UTIL.get.attribute ( input , 'maybe' ) ;
		input.just		= UTIL.get.attribute ( input , 'just' ) ;
		input.is		= ( UTIL.get.attribute ( input , 'is' ) ) ? 1 : 0 ;
		input.regular	= UTIL.get.attribute ( input , 'regular' ) ;
		input.value		= UTIL.convert.trim ( input.value ) ;
		input.bytes		= UTIL.get.bytes ( input.value ) ;		
		input.just		= ( ( input.just && input.just != '0' ) || ( input.maybe && input.form[input.maybe].checked == true ) ) ? true : false ;
		if ( input.regular )
			input.regular	= input.regular.toUpperCase () ;
		if ( ! input.nick )
		{
			input.nick	= '본 입력 사항' ;
			input.is	= 1 ;
		}
		return input ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , "입력 폼 정보 수집에 실패하였습니다.\n\n관리자에게 문의하여 주십시오." ) ;
	}
}


FORM.count = new Object () ;


/**************************************************
Radio 혹은 Checkbox 의 Checked 수 확인
--------------------------------------------------
input	: 입력 폼 객체
**************************************************/
FORM.count.check = function ( input )
{
	try
	{
		var i , name , counter	= 0 ;
		var index	= input.name.indexOf ( "[" ) ;
		if ( index >= 0 )
		{
			name	= input.name.substr ( 0 , index ) ;
		}
		else
		{
			index	= input.name.length ;
			name	= input.name ;
		}
		for ( i = 0 ; i < input.form.length ; i ++ )
		{
			if ( input.form[i].tagName == 'FIELDSET' ) continue ;
			if ( input.form[i].type == input.type && input.form[i].name.substr ( 0 , index ) == name && input.form[i].checked == true ) counter ++ ;
		}
		return counter ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '입력 폼 선택 수 확인에 실패하였습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


FORM.focus = new Object () ;


/**************************************************
포커스 변경
--------------------------------------------------
input	: 입력 폼 객체
**************************************************/
FORM.focus.leave = function ( input , message )
{
	try
	{
		var target	= input ;
		if ( input.leave )
		{
			if ( input.leave.toUpperCase () == 'OFF' ) return FORM.failure () ;
			target		= input.form[input.leave] ;
		}
		FORM.failure ( ( input.comment ) ? input.comment : message ) ;
		if ( target.disabled == true ) return false ;
		( target.type == 'text' ) ? target.select () : target.focus () ;
		return false ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '포커스 전환에 실패하였습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


/**************************************************
폼 검사 실패 처리
--------------------------------------------------
message	: 안내 메세지
**************************************************/
FORM.failure = function ( message )
{
	try
	{
		var i , obj ;
		for ( i in FORM.v.submit )
			FORM.v.submit[i].disabled = false ;
		UTIL.curtain.off () ;
		if ( message )
			alert ( message ) ;
		return false ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , '폼 검사 실패 처리에 오류가 발생하였습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


/**************************************************
폼 검사
--------------------------------------------------
obj					: 폼 객체 ( this )
userFunctionFirst	: 사용자 함수. 검사를 진행 전, 사용자 함수를 실행하여 결과 값이 true 인 경우 폼 전송을 시도한다.
userFunctionEnd		: 사용자 함수. 검사를 진행 후, 사용자 함수를 실행하여 결과 값이 true 인 경우 폼 전송을 시도한다.
curtain				: 커텐 출력 여부 ( 기본값 : 출력 , true : 출력 , false : 제외 )
tag					: 폼 체크 결과 Textarea 생성 여부 ( 기본값 : 생성 , true : 생성 , false : 제외 )
**************************************************/
FORM.check = function ( obj , userFunctionFirst , userFunctionEnd , curtain , tag )
{
	try
	{
		var i , temp , input , checkBoxCount , information = new Array () ;
		if ( curtain != false )
		{
			FORM.v.submit	= new Array () ;
			for ( i = 0 ; i < obj.length ; i ++ )
			{
				if ( obj[i].tagName == 'FIELDSET' ) continue ;
				temp = obj[i].type.toUpperCase () ;
				if ( temp != 'SUBMIT' && temp != 'IMAGE' ) continue ;
				FORM.v.submit.push ( obj[i] ) ;
				obj[i].disabled = true ;
			}
		}
		if ( userFunctionFirst && ! userFunctionFirst ( obj ) ) return FORM.failure () ;
		for ( i = 0 ; i < obj.length ; i ++ )
		{
			if ( obj[i].tagName == 'FIELDSET' || obj[i].tagName == 'OBJECT' || obj[i].tagName == 'EMBED' || obj[i].type == 'submit' || obj[i].type == 'file' ) continue ;
			input	= FORM.get.attribute ( obj[i] ) ;
			switch ( input.type )
			{
				case 'text' :
				case 'hidden' :
				case 'textarea' :
				case 'password' :
				case 'file' :
					if ( input.just && ! input.value )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][0] + ' 필수 입력 항목입니다.' ) ;
					if ( input.min && input.bytes < input.min )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][0] + ' 최소 ' + input.min + ' 글자 이상 입력해야 합니다.' ) ;
					if ( input.max && input.bytes > input.max )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][0] + ' 최대 ' + input.max + ' 글자 이내로 입력해야 합니다.' ) ;
					if ( input.numMin && parseInt ( input.value , 10 ) < input.numMin )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][0] + ' 최소 ' + input.numMin + ' 이하로 입력 될 수 없습니다.' ) ;
					if ( input.numMax && parseInt ( input.value , 10 ) > input.numMax )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][0] + ' 최대 ' + input.numMax + ' 이상 입력 될 수 없습니다.' ) ;
					if ( input.regular && input.value && ! FORM.get.pattern ( input.regular ).test ( input.value ) )
						return FORM.focus.leave ( input , FORM.get.message ( input ) ) ;
					switch ( input.regular )
					{
						case 'TEL' :
						case 'FAX' :
							if ( ! FORM.justness["TEL"] ( input ) )
								return FORM.focus.leave ( input , FORM.get.message ( input ) ) ;
							break ;
						default :
							if ( UTIL.get.type ( FORM.justness[input.regular] ) == 'function' && ! FORM.justness[input.regular] ( input ) )
								return FORM.focus.leave ( input , FORM.get.message ( input ) ) ;
							break ;
					}
					break ;

				case 'checkbox' :
					checkBoxCount = FORM.count.check ( input ) ;
					if ( input.just && ! checkBoxCount )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][1] + ' 선택하여 주십시요.' ) ;
					if ( input.min && checkBoxCount < input.min )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][0] + ' 최소 ' + input.min + ' 개 이상 선택해야 합니다.' ) ;
					if ( input.max && checkBoxCount > input.max )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][0] + ' 최대 ' + input.max + ' 개 이내로 선택해야 합니다.' ) ;
					break ;

				case 'radio' :
					if ( input.just && ! FORM.count.check ( input ) )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][1] + ' 선택하여 주십시요.' ) ;
					break ;

				case 'select-one' :
					if ( ! input.just ) continue ;
					if ( ! input.options[input.selectedIndex].value )
						return FORM.focus.leave ( input , input.nick + FORM.v.is[input.is][1] + ' 선택하여 주십시요.' ) ;
					break ;
			}
			if ( tag != false && input.name.indexOf ( '[' ) == -1 && ! information[input.name] )
				information[input.name] = input.name + ',' + input.type + ',' + input.nick + ',' + input.is + ',' + input.just + ',' + input.min + ',' + input.max + ',' + input.numMin + ',' + input.numMax + ',' + input.regular ;
		}		
		if ( userFunctionEnd && ! userFunctionEnd ( obj ) ) return FORM.failure () ;		
		if ( curtain != false ) UTIL.curtain.on () ;
		if ( tag != false )
		{
			temp	= new Array () ;
			for ( i in information )
				temp.push ( information[i] ) ;
			obj.appendChild ( UTIL.create.tag ( 'textarea' , 'name=formCheckInformation' , 'position:absolute;display:none' , temp.join ( '|' ) , false ) ) ;
		}
		if ( ! obj.getAttribute ( 'target' ) )
			obj.setAttribute ( 'target' , 'formSubmitTarget' ) ;
		return true ;
	}
	catch ( errorCode )
	{
		UTIL.echo.error ( errorCode , 'FORM 검사에 실패하였습니다.\n\n관리자에게 문의하여 주십시오.' ) ;
	}
}


FORM.run () ;