/*******************************************************************************
 Program:	Registration Library
 File:		regform.js
 Description:	Online Registration Client-side Validation (JavaScript)
 Author:	Jason_ZhuYX@hotmail.com
 Environment:	JavaScript1.2 IE4+/Opera/Netscape4+
 Revision:	Beta - 12/26/2001
		V1.0 - 11/26/2006
 Note:
 *******************************************************************************/

 var emailAddress = "reg@righthandeng.com";

 var countries = new Object; setCountries();
 var products = new Object; setProducts();
 var referTypes = new Object; setReferTypes();
 var regnames = new Object; setRegnames();
 var states = new Object; setStates();

 var strDOC = (document.all) ? "document.all." : "document.";
 var strSTYLE = (document.all) ? ".style" : "";

 deletecookie("product");    // ensure varied products; 9/16/2004

 if (top.location != self.location)
 {
	top.location = self.location;	// keep this page out of a frame
 }

 window.status = "Loading script ...";


/*******************************************************************************
 functions to populate properties of objects: countries[""] and states[""]
 *******************************************************************************/
 function setCountries()
 {
	var mdash = "&mdash;&mdash;&mdash;&mdash;&mdash;&mdash;&mdash;&mdash;";

	countries["US"] = "United States (USA)";
	countries["CN"] = "China, People's Republic Of";
	countries["CA"] = "Canada";
	countries["--"] = "" + mdash + mdash + mdash;	// special splitter
	countries["AF"] = "Afghanistan";
	countries["AL"] = "Albania";
	countries["DZ"] = "Algeria";
	countries["AS"] = "American Samoa";
	countries["AD"] = "Andorra";
	countries["AO"] = "Angola";
	countries["AI"] = "Anguilla";
	countries["AQ"] = "Antarctica";
	countries["AG"] = "Antigua and Barbuda";
	countries["AR"] = "Argentina";
	countries["AM"] = "Armenia";
	countries["AW"] = "Aruba";
	countries["AU"] = "Australia";
	countries["AT"] = "Austria";
	countries["AZ"] = "Azerbaijan";
	countries["BS"] = "Bahamas, The";
	countries["BH"] = "Bahrain";
	countries["BD"] = "Bangladesh";
	countries["BB"] = "Barbados";
	countries["BY"] = "Belarus";
	countries["BE"] = "Belgium";
	countries["BZ"] = "Belize";
	countries["BJ"] = "Benin";
	countries["BM"] = "Bermuda";
	countries["BT"] = "Bhutan";
	countries["BO"] = "Bolivia";
	countries["BA"] = "Bosnia and Herzegovina";
	countries["BW"] = "Botswana";
	countries["BV"] = "Bouvet Island (Norway)";
	countries["BR"] = "Brazil";
	countries["IO"] = "British Indian Ocean Territory";
	countries["BN"] = "Brunei Darussalam";
	countries["BG"] = "Bulgaria";
	countries["BF"] = "Burkina Faso";
	countries["BI"] = "Burundi";
	countries["KH"] = "Cambodia";
	countries["CM"] = "Cameroon";
	countries["CV"] = "Cape Verde";
	countries["KY"] = "Cayman Islands";
	countries["CF"] = "Central African Republic";
	countries["TD"] = "Chad";
	countries["CL"] = "Chile";
	countries["CX"] = "Christmas Island";
	countries["CC"] = "Cocos (Keeling) Islands";
	countries["CO"] = "Colombia";
	countries["KM"] = "Comoros";
	countries["CD"] = "Congo, Democratic Republic Of (Zaire)";
	countries["CG"] = "Congo, People's Republic Of";
	countries["CK"] = "Cook Islands";
	countries["CR"] = "Costa Rica";
	countries["CI"] = "Cote d'Ivoire (Ivory Coast)";
	countries["HR"] = "Croatia (Hrvatska)";
	countries["CU"] = "Cuba";
	countries["CY"] = "Cyprus";
	countries["CZ"] = "Czech Republic";
	countries["CS"] = "Czechoslovakia (CSFR, Czech and Slovak Federative Republic)";
	countries["DK"] = "Denmark";
	countries["DJ"] = "Djibouti";
	countries["DM"] = "Dominica";
	countries["DO"] = "Dominican Republic";
	countries["TL"] = "East Timor";
	countries["EC"] = "Ecuador";
	countries["EG"] = "Egypt";
	countries["SV"] = "El Salvador";
	countries["GQ"] = "Equatorial Guinea";
	countries["ER"] = "Eritrea";
	countries["EE"] = "Estonia";
	countries["ET"] = "Ethiopia";
	countries["FK"] = "Falkland Islands (Malvinas)";
	countries["FO"] = "Faroe Islands";
	countries["FJ"] = "Fiji";
	countries["FI"] = "Finland";
	countries["FR"] = "France";
	countries["FX"] = "France, Metropolitan";
	countries["GF"] = "French Guiana";
	countries["PF"] = "French Polynesia";
	countries["TF"] = "French Southern Territories";
	countries["GA"] = "Gabon";
	countries["GM"] = "Gambia, The";
	countries["GE"] = "Georgia";
	countries["DE"] = "Germany";
	countries["GH"] = "Ghana";
	countries["GI"] = "Gibraltar";
	countries["GB"] = "Great Britain, United Kingdom of";
	countries["GR"] = "Greece";
	countries["GL"] = "Greenland";
	countries["GD"] = "Grenada";
	countries["GP"] = "Guadeloupe";
	countries["GU"] = "Guam";
	countries["GT"] = "Guatemala";
	countries["GN"] = "Guinea";
	countries["GW"] = "Guinea-Bissau";
	countries["GY"] = "Guyana";
	countries["HT"] = "Haiti";
	countries["HM"] = "Heard Island and McDonald Islands";
	countries["HN"] = "Honduras";
	countries["HK"] = "Hong Kong (China)";
	countries["HU"] = "Hungary";
	countries["IS"] = "Iceland";
	countries["IN"] = "India";
	countries["ID"] = "Indonesia";
	countries["IR"] = "Iran, Islamic Republic Of";
	countries["IQ"] = "Iraq";
	countries["IE"] = "Ireland";
	countries["IM"] = "Isle of Man";
	countries["IL"] = "Israel";
	countries["IT"] = "Italy";
	countries["JM"] = "Jamaica";
	countries["JP"] = "Japan";
	countries["JO"] = "Jordan";
	countries["KZ"] = "Kazakhstan";
	countries["KE"] = "Kenya";
	countries["KI"] = "Kiribati";
	countries["KP"] = "Korea, Democratic People's Republic Of";
	countries["KR"] = "Korea, Republic of";
	countries["KW"] = "Kuwait";
	countries["KG"] = "Kyrgyzstan";
	countries["LA"] = "Lao People's Democratic Republic";
	countries["LV"] = "Latvia";
	countries["LB"] = "Lebanon";
	countries["LS"] = "Lesotho";
	countries["LR"] = "Liberia";
	countries["LY"] = "Libyan Arab Jamahiriya";
	countries["LI"] = "Liechtenstein";
	countries["LT"] = "Lithuania";
	countries["LU"] = "Luxembourg";
	countries["MO"] = "Macau (China)";
	countries["MK"] = "Macedonia, (former Yugoslav Republic Of)";
	countries["MG"] = "Madagascar";
	countries["MW"] = "Malawi";
	countries["MY"] = "Malaysia";
	countries["MV"] = "Maldives";
	countries["ML"] = "Mali";
	countries["MT"] = "Malta";
	countries["MH"] = "Marshall Islands";
	countries["MQ"] = "Martinique";
	countries["MR"] = "Mauritania";
	countries["MU"] = "Mauritius";
	countries["YT"] = "Mayotte";
	countries["MX"] = "Mexico";
	countries["FM"] = "Micronesia, Federated States Of";
	countries["MD"] = "Moldova, Republic Of";
	countries["MC"] = "Monaco";
	countries["MN"] = "Mongolia";
	countries["MS"] = "Montserrat";
	countries["MA"] = "Morocco";
	countries["MZ"] = "Mozambique";
	countries["MM"] = "Myanmar (Burma)";
	countries["NA"] = "Namibia";
	countries["NR"] = "Nauru";
	countries["NP"] = "Nepal";
	countries["NL"] = "Netherlands (Holland)";
	countries["AN"] = "Netherlands Antilles";
	countries["NN"] = "Neutral Zone (Unknown Area)";
	countries["NC"] = "New Caledonia";
	countries["NZ"] = "New Zealand";
	countries["NI"] = "Nicaragua";
	countries["NE"] = "Niger";
	countries["NG"] = "Nigeria";
	countries["NU"] = "Niue";
	countries["NF"] = "Norfolk Island";
	countries["MP"] = "Northern Mariana Islands";
	countries["NO"] = "Norway";
	countries["OM"] = "Oman";
	countries["PK"] = "Pakistan";
	countries["PW"] = "Palau";
	countries["PS"] = "Palestinian Territory, Occupied";
	countries["PA"] = "Panama";
	countries["PG"] = "Papua New Guinea";
	countries["PY"] = "Paraguay";
	countries["PE"] = "Peru";
	countries["PH"] = "Philippines";
	countries["PN"] = "Pitcairn Islands (British)";
	countries["PL"] = "Poland";
	countries["PT"] = "Portugal";
	countries["PR"] = "Puerto Rico";
	countries["QA"] = "Qatar";
	countries["RE"] = "Reunion (French)";
	countries["RO"] = "Romania";
	countries["RU"] = "Russian Federation";
	countries["RW"] = "Rwanda";
	countries["KN"] = "Saint Kitts and Nevis";
	countries["LC"] = "Saint Lucia";
	countries["VC"] = "Saint Vincent and the Grenadines";
	countries["SM"] = "San Marino";
	countries["ST"] = "Sao Tome and Principe";
	countries["SA"] = "Saudi Arabia";
	countries["SN"] = "Senegal";
	countries["SC"] = "Seychelles";
	countries["SL"] = "Sierra Leone";
	countries["SG"] = "Singapore";
	countries["SK"] = "Slovakia (Slovak Republic)";
	countries["SI"] = "Slovenia";
	countries["SB"] = "Solomon Islands";
	countries["SO"] = "Somalia";
	countries["ZA"] = "South Africa";
	countries["GS"] = "South Georgia and The South Sandwich Islands";
	countries["ES"] = "Spain";
	countries["LK"] = "Sri Lanka";
	countries["SH"] = "St. Helena (British)";
	countries["PM"] = "St. Pierre and Miquelon";
	countries["SD"] = "Sudan";
	countries["SR"] = "Suriname";
	countries["SJ"] = "Svalbard and Jan Mayen Islands (Norway)";
	countries["SZ"] = "Swaziland";
	countries["SE"] = "Sweden";
	countries["CH"] = "Switzerland";
	countries["SY"] = "Syrian Arab Republic";
	countries["TW"] = "Taiwan - Republic Of China";
	countries["TJ"] = "Tajikistan";
	countries["TZ"] = "Tanzania, United Republic Of";
	countries["TH"] = "Thailand";
	countries["TG"] = "Togo";
	countries["TK"] = "Tokelau (New Zealand)";
	countries["TO"] = "Tonga";
	countries["TT"] = "Trinidad and Tobago";
	countries["TN"] = "Tunisia";
	countries["TR"] = "Turkey";
	countries["TM"] = "Turkmenistan";
	countries["TC"] = "Turks and Caicos Islands";
	countries["TV"] = "Tuvalu";
	countries["UG"] = "Uganda";
	countries["UA"] = "Ukraine";
	countries["AE"] = "United Arab Emirates";
	countries["UK"] = "United Kingdom (UK)";
	countries["UM"] = "United States Minor Outlying Islands";
	countries["UY"] = "Uruguay";
	countries["UZ"] = "Uzbekistan";
	countries["VU"] = "Vanuatu";
	countries["VA"] = "Vatican City State (Holy See)";
	countries["VE"] = "Venezuela";
	countries["VN"] = "Viet Nam";
	countries["VG"] = "Virgin Islands (British)";
	countries["VI"] = "Virgin Islands (US)";
	countries["WF"] = "Wallis and Futuna Islands";
	countries["EH"] = "Western Sahara";
	countries["WS"] = "Western Samoa";
	countries["YE"] = "Yemen";
	countries["YU"] = "Yugoslavia";
	countries["ZM"] = "Zambia";
	countries["ZW"] = "Zimbabwe";

 }//end setCountries()


 function setProducts()
 {
	products["sku"] = new Object;
	products["sku_id"] = new Object;

	products["sku_id"]["2003010101"] = "WVCF";
	products["sku_id"]["2004072801"] = "WVMX";

	products["sku"]["WVMX"] = "WinVerter-Monitor FX-MX";
	products["sku"]["WVCF"] = "WinVerter-Control SW";
 }


 function setReferTypes()
 {
 	referTypes["0"] = "Click to select &rarr;";
	referTypes["1"] = "1. Magazine Ad";
	referTypes["11"] = "1.1 High Country News";
	referTypes["12"] = "1.2 Home Power";
	referTypes["2"] = "2. Industry Chat List";
	referTypes["3"] = "3. Referral";
	referTypes["4"] = "4. Reseller";
	referTypes["5"] = "5. Trade Show";
	referTypes["6"] = "6. Web Ad";
	referTypes["7"] = "7. Web Link";
	referTypes["8"] = "8. Web Search";
	referTypes["9"] = "9. Others";
	referTypes["Selected"] = "0";

 }//end setReferTypes()


 function setRegnames()
 {
	regnames["**"] = new Object;
	regnames["required"] = new Object;
	regnames["=="] = new Object;
	regnames["US"] = new Object;

 	regnames["required"]["RegFiName"] = true;
	regnames["required"]["RegLaName"] = true;
	regnames["required"]["RegMiInit"] = false;
	regnames["required"]["RegJTitle"] = false;
	regnames["required"]["RegOrName"] = false;
	regnames["required"]["RegAddrL1"] = false;
	regnames["required"]["RegAddrL2"] = false;
	regnames["required"]["RegCiTown"] = true;
	regnames["required"]["RegCounty"] = false;
	regnames["required"]["RegRegion"] = true;
	regnames["required"]["RegZIPost"] = false;
	regnames["required"]["RegNation"] = true;
	regnames["required"]["RegPhone1"] = true;
	regnames["required"]["RegPhone2"] = false;
	regnames["required"]["RegEmAddr"] = true;
	regnames["required"]["RegURLink"] = false;
	regnames["required"]["RegRefer1"] = true;
	regnames["required"]["RegRefer2"] = false;

 	regnames["=="]["RegFiName"] = "First Name  ";
	regnames["=="]["RegLaName"] = "Family Name ";
	regnames["=="]["RegMiInit"] = "Middle Name ";
	regnames["=="]["RegJTitle"] = "Job Title   ";
	regnames["=="]["RegOrName"] = "Organization";
	regnames["=="]["RegAddrL1"] = "Address 1   ";
	regnames["=="]["RegAddrL2"] = "Address 2   ";
	regnames["=="]["RegCiTown"] = "City/Town   ";
	regnames["=="]["RegCounty"] = "County      ";
	regnames["=="]["RegRegion"] = "State/Region";
	regnames["=="]["RegZIPost"] = "Postal ZIP  ";
	regnames["=="]["RegNation"] = "Country     ";
	regnames["=="]["RegPhone1"] = "Phone No.   ";
	regnames["=="]["RegPhone2"] = "Phone2/Fax  ";
	regnames["=="]["RegEmAddr"] = "E-mail ID   ";
	regnames["=="]["RegURLink"] = "Web Site    ";
	regnames["=="]["RegRefer1"] = "Refer Type  ";
	regnames["=="]["RegRefer2"] = "Referral    ";
	regnames["=="]["RegSWList"] = "Product     ";

 	regnames["**"]["RegFiName"] = "Your Name:      ";
	regnames["**"]["RegLaName"] = "Family Name:    ";
	regnames["**"]["RegMiInit"] = "M.I.            ";
	regnames["**"]["RegJTitle"] = "Title:          ";
	regnames["**"]["RegOrName"] = "Organization:   ";
	regnames["**"]["RegAddrL1"] = "Address line 1: ";
	regnames["**"]["RegAddrL2"] = "Address line 2: ";
	regnames["**"]["RegCiTown"] = "City/Town:      ";
	regnames["**"]["RegCounty"] = "County:         ";
	regnames["**"]["RegRegion"] = "Region/Province: ";
	regnames["**"]["RegZIPost"] = "Postcode:       ";
	regnames["**"]["RegNation"] = "Country:        ";
	regnames["**"]["RegPhone1"] = "Telephone No.   ";
	regnames["**"]["RegPhone2"] = "Cell/Fax/Other Contact: ";
	regnames["**"]["RegEmAddr"] = "E-mail:         ";
	regnames["**"]["RegURLink"] = "Web:            ";
	regnames["**"]["RegRefer1"] = "How did you hear about us? ";
	regnames["**"]["RegRefer2"] = "Referral info:  ";

 	regnames["US"]["RegFiName"] = "First Name:    ";
	regnames["US"]["RegLaName"] = "Last Name:     ";
	regnames["US"]["RegMiInit"] = "M.I.           ";
	regnames["US"]["RegJTitle"] = "Title:         ";
	regnames["US"]["RegOrName"] = "Organization:  ";
	regnames["US"]["RegAddrL1"] = "Street Address:";
	regnames["US"]["RegAddrL2"] = "Address (cont.)";
	regnames["US"]["RegCiTown"] = "City/Town:     ";
	regnames["US"]["RegCounty"] = "County:        ";
	regnames["US"]["RegRegion"] = "State (U.S.):  ";
	regnames["US"]["RegZIPost"] = "ZIP Code:      ";
	regnames["US"]["RegNation"] = "Country:       ";
	regnames["US"]["RegPhone1"] = "Primary Phone: ";
	regnames["US"]["RegPhone2"] = "2nd Phone/Fax No.: ";
	regnames["US"]["RegEmAddr"] = "E-mail:        ";
	regnames["US"]["RegURLink"] = "Web:           ";
	regnames["US"]["RegRefer1"] = "How did you hear about us?";
	regnames["US"]["RegRefer2"] = "Referral info: ";

 }//end setRegnames()


 function setStates()
 {
	states["CA"] = new Object;	// Canada
	states["CN"] = new Object;	// China, People's Republic Of
	states["US"] = new Object;	// The United States Of America
	states["AU"] = new Object;	// Australia
	states["BR"] = new Object;	// Brazil
	states["BS"] = new Object;	// Bahamas
	states["CF"] = new Object;	// Central African Republic
	states["CH"] = new Object;	// Switzerland
	states["DE"] = new Object;	// Germany
	states["DO"] = new Object;	// Dominican Republic
	states["ES"] = new Object;	// Spain
	states["GB"] = new Object;	// United Kingdom (UK) - Great Britain
	states["GY"] = new Object;	// Guyana
	states["IE"] = new Object;	// Ireland
	states["IN"] = new Object;	// India
	states["IT"] = new Object;	// Italy
	states["MX"] = new Object;	// Mexico
	states["NL"] = new Object;	// Netherlands (Holland)
	states["NZ"] = new Object;	// New Zealand
	states["PR"] = new Object;	// Puerto Rico
	states["PT"] = new Object;	// Portugal
	states["ZA"] = new Object;	// South Africa

	states["US"]["AL"] = "Alabama";
	states["US"]["AK"] = "Alaska";
	states["US"]["AZ"] = "Arizona";
	states["US"]["AR"] = "Arkansas";
	states["US"]["CA"] = "California";
	states["US"]["CO"] = "Colorado";
	states["US"]["CT"] = "Connecticut";
	states["US"]["DE"] = "Delaware";
	states["US"]["FL"] = "Florida";
	states["US"]["GA"] = "Georgia";
	states["US"]["HI"] = "Hawaii";
	states["US"]["ID"] = "Idaho";
	states["US"]["IL"] = "Illinois";
	states["US"]["IN"] = "Indiana";
	states["US"]["IA"] = "Iowa";
	states["US"]["KS"] = "Kansas";
	states["US"]["KY"] = "Kentucky";
	states["US"]["LA"] = "Louisiana";
	states["US"]["ME"] = "Maine";
	states["US"]["MD"] = "Maryland";
	states["US"]["MA"] = "Massachusetts";
	states["US"]["MI"] = "Michigan";
	states["US"]["MN"] = "Minnesota";
	states["US"]["MS"] = "Mississippi";
	states["US"]["MO"] = "Missouri";
	states["US"]["MT"] = "Montana";
	states["US"]["NE"] = "Nebraska";
	states["US"]["NV"] = "Nevada";
	states["US"]["NH"] = "New Hampshire";
	states["US"]["NJ"] = "New Jersey";
	states["US"]["NM"] = "New Mexico";
	states["US"]["NY"] = "New York";
	states["US"]["NC"] = "North Carolina";
	states["US"]["ND"] = "North Dakota";
	states["US"]["OH"] = "Ohio";
	states["US"]["OK"] = "Oklahoma";
	states["US"]["OR"] = "Oregon";
	states["US"]["PA"] = "Pennsylvania";
	states["US"]["RI"] = "Rhode Island";
	states["US"]["SC"] = "South Carolina";
	states["US"]["SD"] = "South Dakota";
	states["US"]["TN"] = "Tennessee";
	states["US"]["TX"] = "Texas";
	states["US"]["UT"] = "Utah";
	states["US"]["VT"] = "Vermont";
	states["US"]["VA"] = "Virginia";
	states["US"]["WA"] = "Washington";
	states["US"]["DC"] = "Washington, DC";
	states["US"]["WV"] = "West Virginia";
	states["US"]["WI"] = "Wisconsin";
	states["US"]["WY"] = "Wyoming";

	states["CA"]["AB"] = "Alberta";
	states["CA"]["BC"] = "British Columbia";
	states["CA"]["MB"] = "Manitoba";
	states["CA"]["NB"] = "New Brunswick";
	states["CA"]["NL"] = "Newfoundland and Labrador";
	states["CA"]["NS"] = "Nova Scotia";
	states["CA"]["NT"] = "Northwest Territories";
	states["CA"]["NU"] = "Nunavut";
	states["CA"]["ON"] = "Ontario";
	states["CA"]["PE"] = "Prince Edward Island";
	states["CA"]["QC"] = "Quebec";
	states["CA"]["SK"] = "Saskatchewan";
	states["CA"]["YT"] = "Yukon Territory";

	states["CN"]["AH"] = "Anhui (Wan)";
	states["CN"]["MO"] = "Aomen, SAR (Macau)";
	states["CN"]["BJ"] = "Beijing - the Capital";
	states["CN"]["CQ"] = "Chongqing, MC (Yu)";
	states["CN"]["FJ"] = "Fujian (Min)";
	states["CN"]["GS"] = "Gansu (Long)";
	states["CN"]["GD"] = "Guangdong (Yue - Canton)";
	states["CN"]["GX"] = "Guangxi, AR (Gui)";
	states["CN"]["GZ"] = "Guizhou (Qian)";
	states["CN"]["HI"] = "Hainan (Qiong)";
	states["CN"]["HE"] = "Hebei (Ji)";
	states["CN"]["HL"] = "Heilongjiang (Hei)";
	states["CN"]["HA"] = "Henan (Yu)";
	states["CN"]["HK"] = "Hongkong, SAR";
	states["CN"]["HB"] = "Hubei (E)";
	states["CN"]["HN"] = "Hunan (Xiang)";
	states["CN"]["JS"] = "Jiangsu (Su)";
	states["CN"]["JX"] = "Jiangxi (Gan)";
	states["CN"]["JL"] = "Jilin (Ji)";
	states["CN"]["LN"] = "Liaoning (Liao)";
	states["CN"]["NM"] = "Neimenggu, AR (Meng)";
	states["CN"]["NX"] = "Ningxia, AR (Ning)";
	states["CN"]["QH"] = "Qinghai (Qing)";
	states["CN"]["SD"] = "Shandong (Lu)";
	states["CN"]["SH"] = "Shanghai, MC (Hu)";
	states["CN"]["SX"] = "Shanxi (Jin)";
	states["CN"]["SN"] = "Shanxi (Qin)";
	states["CN"]["SC"] = "Sichuan (Shu)";
	states["CN"]["TW"] = "Taiwan (Tai)";
	states["CN"]["TJ"] = "Tianjin, MC (Jin)";
	states["CN"]["XJ"] = "Xinjiang, AR (Xin)";
	states["CN"]["XZ"] = "Xizang, AR (Tibet)";
	states["CN"]["YN"] = "Yunnan (Dian)";
	states["CN"]["ZJ"] = "Zhejiang (Zhe)";

	states["AU"]["CT"] = "Australian Capital Territory";
	states["AU"]["NS"] = "New South Wales";
	states["AU"]["NT"] = "Northern Territory";
	states["AU"]["QL"] = "Queensland";
	states["AU"]["SA"] = "South Australia";
	states["AU"]["TS"] = "Tasmania";
	states["AU"]["VI"] = "Victoria";
	states["AU"]["WA"] = "Western Australia";

	states["BR"]["AC"] = "Acre";
	states["BR"]["AL"] = "Alagoas";
	states["BR"]["AP"] = "Amapa";
	states["BR"]["AM"] = "Amazonas";
	states["BR"]["BA"] = "Bahia";
	states["BR"]["CE"] = "Ceara";
	states["BR"]["DF"] = "Distrito Federal";
	states["BR"]["ES"] = "Espirito Santo";
	states["BR"]["GO"] = "Goias";
	states["BR"]["MA"] = "Maranhao";
	states["BR"]["MT"] = "Mato Grosso";
	states["BR"]["MS"] = "Mato Grosso do Sul";
	states["BR"]["MG"] = "Minas Gerais";
	states["BR"]["PA"] = "Para";
	states["BR"]["PB"] = "Paraiba";
	states["BR"]["PR"] = "Parana";
	states["BR"]["PE"] = "Pernambuco";
	states["BR"]["PI"] = "Piaui";
	states["BR"]["RJ"] = "Rio de Janeiro";
	states["BR"]["RN"] = "Rio Grande do Norte";
	states["BR"]["RS"] = "Rio Grande do Sul";
	states["BR"]["RO"] = "Rondonia";
	states["BR"]["RR"] = "Roraima";
	states["BR"]["SC"] = "Santa Catarina";
	states["BR"]["SP"] = "Sao Paulo";
	states["BR"]["BR"] = "SE Sergipe";
	states["BR"]["TO"] = "Tocantins";

	states["BS"]["AC"] = "Acklins and Crooked Islands";
	states["BS"]["BI"] = "Bimini";
	states["BS"]["CI"] = "Cat Island";
	states["BS"]["EX"] = "Exuma";
	states["BS"]["FP"] = "Freeport";
	states["BS"]["FC"] = "Fresh Creek";
	states["BS"]["GH"] = "Governor's Harbour";
	states["BS"]["GT"] = "Green Turtle Cay";
	states["BS"]["HI"] = "Harbour Island";
	states["BS"]["HR"] = "High Rock";
	states["BS"]["IN"] = "Inagua";
	states["BS"]["KB"] = "Kemps Bay";
	states["BS"]["LI"] = "Long Island";
	states["BS"]["MH"] = "Marsh Harbour";
	states["BS"]["MG"] = "Mayaguana";
	states["BS"]["NP"] = "New Providence";
	states["BS"]["NB"] = "Nicholls Town and Berry Islands";
	states["BS"]["RI"] = "Ragged Island";
	states["BS"]["RS"] = "Rock Sound";
	states["BS"]["SR"] = "San Salvador and Rum Cay";
	states["BS"]["SP"] = "Sandy Point";

	states["CF"]["BK"] = "Baase-Kotto";
	states["CF"]["BB"] = "Bamingui-Bangoran";
	states["CF"]["BG"] = "Bangui";
	states["CF"]["HK"] = "Haute-Kotto";
	states["CF"]["HM"] = "Haut-Mbomou";
	states["CF"]["KG"] = "Kémo";
	states["CF"]["LB"] = "Lobaye";
	states["CF"]["HS"] = "Mambér?Kadéï";
	states["CF"]["MB"] = "Mbomou";
	states["CF"]["KB"] = "Nana-Grébizi";
	states["CF"]["NM"] = "Nana-Mambéré|";
	states["CF"]["MP"] = "Ombella-Mpoko";
	states["CF"]["UK"] = "Ouaka";
	states["CF"]["AC"] = "Ouham";
	states["CF"]["OP"] = "Ouham-Pendé|";
	states["CF"]["SE"] = "Sangha-Mbaéré|";
	states["CF"]["VR"] = "Vakaga";

	states["CH"]["AG"] = "Aargau";
	states["CH"]["AR"] = "Appenzell Innerrhoden";
	states["CH"]["BL"] = "Basel-Landschaft";
	states["CH"]["BS"] = "Basel-Stadt";
	states["CH"]["BE"] = "Bern";
	states["CH"]["FR"] = "Fribourg";
	states["CH"]["GE"] = "Geneva";
	states["CH"]["GL"] = "Glarus";
	states["CH"]["GR"] = "Graubünden";
	states["CH"]["JU"] = "Jura";
	states["CH"]["LU"] = "Lucerne";
	states["CH"]["NE"] = "Neuchatel";
	states["CH"]["NW"] = "Nidwalden";
	states["CH"]["OW"] = "Obwalden";
	states["CH"]["SH"] = "Schaffhausen";
	states["CH"]["SZ"] = "Schwyz";
	states["CH"]["SO"] = "Solothurn";
	states["CH"]["SG"] = "St. Gallen";
	states["CH"]["TG"] = "Thurgau";
	states["CH"]["TI"] = "Ticino";
	states["CH"]["UR"] = "Uri";
	states["CH"]["VS"] = "Valais";
	states["CH"]["VD"] = "Vaud";
	states["CH"]["ZG"] = "Zug";
	states["CH"]["ZH"] = "Zurich";

	states["DE"]["BW"] = "Baden-Württemberg";
	states["DE"]["BY"] = "Bavaria (Bayern)";
	states["DE"]["BE"] = "Berlin (city-state)";
	states["DE"]["BR"] = "Brandenburg";
	states["DE"]["HB"] = "Bremen (city-state)";
	states["DE"]["HH"] = "Hamburg (city-state)";
	states["DE"]["HE"] = "Hes (Hesn)";
	states["DE"]["NI"] = "Lower Saxony (Niedersachn)";
	states["DE"]["MV"] = "Mecklenburg-Western Pomerania (Mecklenburg-Vorpomm";
	states["DE"]["NW"] = "North Rhine-Westphalia (Nordrhein-Westfalen)";
	states["DE"]["RP"] = "Rhineland-Palatinate (Rheinland-Pfalz)";
	states["DE"]["SL"] = "Saarland";
	states["DE"]["SN"] = "Saxony (Sachn)";
	states["DE"]["ST"] = "Saxony-Anhalt (Sachn-Anhalt)";
	states["DE"]["SH"] = "Schleswig-Holstein";
	states["DE"]["TH"] = "Thuringia (Thüringen)";

	states["DO"]["AZ"] = "Azua";
	states["DO"]["BR"] = "Bahoruco";
	states["DO"]["BH"] = "Barahona";
	states["DO"]["DA"] = "Dajabon";
	states["DO"]["DN"] = "Distrito Nacional (Santo Domingo)";
	states["DO"]["DU"] = "Duarte";
	states["DO"]["SE"] = "El Seibo";
	states["DO"]["EP"] = "Espaillat";
	states["DO"]["HM"] = "Hato Mayor";
	states["DO"]["IN"] = "Independencia";
	states["DO"]["AL"] = "La Altagracia";
	states["DO"]["EP"] = "La Estrelleta";
	states["DO"]["RO"] = "La Romana";
	states["DO"]["VE"] = "La Vega";
	states["DO"]["MT"] = "María Trinidad Sánchez";
	states["DO"]["MN"] = "Monseñor Nouel";
	states["DO"]["MC"] = "Monte Cristi";
	states["DO"]["MP"] = "Monte Plata";
	states["DO"]["PN"] = "Pedernales";
	states["DO"]["PR"] = "Peravia";
	states["DO"]["PP"] = "Puerto Plata";
	states["DO"]["SC"] = "Salcedo";
	states["DO"]["SM"] = "Samaná|";
	states["DO"]["CR"] = "San Cristóbal";
	states["DO"]["JU"] = "San Juan";
	states["DO"]["PM"] = "San Pedro de Macorís";
	states["DO"]["SZ"] = "Sánchez Ramírez";
	states["DO"]["ST"] = "Santiago";
	states["DO"]["SR"] = "Santiago Rodríguez";
	states["DO"]["VA"] = "Valverde"

	states["ES"]["AB"] = "Albacete";
	states["ES"]["AC"] = "Alicante";
	states["ES"]["AL"] = "Alava";
	states["ES"]["AM"] = "Almeria";
	states["ES"]["AS"] = "Asturias";
	states["ES"]["AV"] = "Avila";
	states["ES"]["BR"] = "Barcelona";
	states["ES"]["BJ"] = "Badajoz";
	states["ES"]["BU"] = "Burgos";
	states["ES"]["CA"] = "A Coruna";
	states["ES"]["CC"] = "Caceres";
	states["ES"]["CD"] = "Cordoba";
	states["ES"]["CL"] = "Castellon";
	states["ES"]["CR"] = "Ciudad Real";
	states["ES"]["CT"] = "Cantabria";
	states["ES"]["CU"] = "Cuenca";
	states["ES"]["CZ"] = "Cadiz";
	states["ES"]["GD"] = "Granada";
	states["ES"]["GI"] = "Girona";
	states["ES"]["GJ"] = "Guadalajara";
	states["ES"]["GP"] = "Guipuzcoa";
	states["ES"]["HL"] = "Huelva";
	states["ES"]["HS"] = "Huesca";
	states["ES"]["IB"] = "Illes Balears";
	states["ES"]["JN"] = "Jaen";
	states["ES"]["LE"] = "Leon";
	states["ES"]["LG"] = "Lugo";
	states["ES"]["LL"] = "Lleida";
	states["ES"]["MD"] = "Madrid";
	states["ES"]["ML"] = "Malaga";
	states["ES"]["MU"] = "Mucria";
	states["ES"]["NV"] = "Navarra";
	states["ES"]["OU"] = "Ourense";
	states["ES"]["PL"] = "Palencia";
	states["ES"]["PM"] = "Las Palmas";
	states["ES"]["PO"] = "Pontevedra";
	states["ES"]["RJ"] = "La Rioja";
	states["ES"]["SC"] = "Santa Cruz de Tererife";
	states["ES"]["SG"] = "Segovia";
	states["ES"]["SL"] = "Salamanca";
	states["ES"]["SO"] = "Soria";
	states["ES"]["SV"] = "Sevilla";
	states["ES"]["TA"] = "Tarragona";
	states["ES"]["TE"] = "Teruel";
	states["ES"]["TO"] = "Toledo";
	states["ES"]["VC"] = "Valencia";
	states["ES"]["VD"] = "Valladolid";
	states["ES"]["VZ"] = "Vizcaya";
	states["ES"]["ZM"] = "Zamora";
	states["ES"]["ZR"] = "Zaragoza";

	states["GB"]["EN"] = "England";
	states["GB"]["NI"] = "Northern Ireland";
	states["GB"]["SC"] = "Scotland";
	states["GB"]["WS"] = "Wales";

	states["GY"]["BA"] = "Barima-Waini";
	states["GY"]["CU"] = "Cuyuni-Mazaruni";
	states["GY"]["DE"] = "Demerara-Mahaica";
	states["GY"]["EB"] = "East Berbice-Corentyne";
	states["GY"]["ES"] = "Essequibo Islands-West Demerara";
	states["GY"]["MA"] = "Mahaica-Berbice";
	states["GY"]["PM"] = "Pomeroon-Supenaam";
	states["GY"]["PT"] = "Potaro-Siparuni";
	states["GY"]["UD"] = "Upper Demerara-Berbice";
	states["GY"]["UT"] = "Upper Takutu-Upper Essequibo";

	states["IE"]["CW"] = "Carlow";
	states["IE"]["CN"] = "Cavan";
	states["IE"]["CE"] = "Clare";
	states["IE"]["CO"] = "Cork";
	states["IE"]["DL"] = "Donegal";
	states["IE"]["DU"] = "Dublin";
	states["IE"]["GA"] = "Galway";
	states["IE"]["KY"] = "Kerry";
	states["IE"]["KE"] = "Kildare";
	states["IE"]["KK"] = "Kilkenny";
	states["IE"]["LS"] = "Laois";
	states["IE"]["LM"] = "Leitrim";
	states["IE"]["LK"] = "Limerick";
	states["IE"]["LD"] = "Longford";
	states["IE"]["LH"] = "Louth";
	states["IE"]["MO"] = "Mayo";
	states["IE"]["MH"] = "Meath";
	states["IE"]["MN"] = "Monaghan";
	states["IE"]["OY"] = "Offaly";
	states["IE"]["RN"] = "Roscommon";
	states["IE"]["SO"] = "Sligo";
	states["IE"]["TA"] = "Tipperary";
	states["IE"]["WD"] = "Waterford";
	states["IE"]["WH"] = "Westmeath";
	states["IE"]["WX"] = "Wexford";
	states["IE"]["WW"] = "Wicklow";

	states["IN"]["AN"] = "Andaman and Nicobar Islands (UT)";
	states["IN"]["AP"] = "Andhra Pradesh";
	states["IN"]["AR"] = "Arunachal Pradesh";
	states["IN"]["AS"] = "Assam";
	states["IN"]["BR"] = "Bihar";
	states["IN"]["CH"] = "Chandigarh (UT)";
	states["IN"]["CT"] = "Chhattisgarh";
	states["IN"]["DN"] = "Dadra and Nagar Haveli (UT)";
	states["IN"]["DD"] = "Daman and Diu (UT)";
	states["IN"]["DL"] = "Delhi (UT)";
	states["IN"]["GA"] = "Goa";
	states["IN"]["GJ"] = "Gujarat";
	states["IN"]["HR"] = "Haryana";
	states["IN"]["HP"] = "Himachal Pradesh";
	states["IN"]["JK"] = "Jammu and Kashmir";
	states["IN"]["JH"] = "Jharkhand";
	states["IN"]["KA"] = "Karnataka";
	states["IN"]["KL"] = "Kerala";
	states["IN"]["LD"] = "Lakshadweep (UT)";
	states["IN"]["MP"] = "Madhya Pradesh";
	states["IN"]["MM"] = "Maharashtra";
	states["IN"]["MN"] = "Manipur";
	states["IN"]["ML"] = "Meghalaya";
	states["IN"]["MZ"] = "Mizoram";
	states["IN"]["NL"] = "Nagaland";
	states["IN"]["OR"] = "Orissa";
	states["IN"]["PY"] = "Pondicherry (UT)";
	states["IN"]["PB"] = "Punjab";
	states["IN"]["RJ"] = "Rajasthan";
	states["IN"]["SK"] = "Sikkim";
	states["IN"]["TN"] = "Tamil Nadu";
	states["IN"]["TR"] = "Tripura";
	states["IN"]["UP"] = "Uttar Pradesh";
	states["IN"]["UL"] = "Uttaranchal";
	states["IN"]["WB"] = "West Bengal";

	states["IT"]["AG"] = "Agrigento";
	states["IT"]["AL"] = "Alessandria";
	states["IT"]["AN"] = "Ancona";
	states["IT"]["AO"] = "Aosta";
	states["IT"]["AR"] = "Arezzo";
	states["IT"]["AP"] = "Ascoli Piceno";
	states["IT"]["AT"] = "Asti";
	states["IT"]["AV"] = "Avellino";
	states["IT"]["BA"] = "Bari";
	states["IT"]["BL"] = "Belluno";
	states["IT"]["BN"] = "Benevento";
	states["IT"]["BG"] = "Bergamo";
	states["IT"]["BI"] = "Biella";
	states["IT"]["BO"] = "Bologna";
	states["IT"]["BZ"] = "Bolzano";
	states["IT"]["BS"] = "Brescia";
	states["IT"]["BR"] = "Brindisi";
	states["IT"]["CA"] = "Cagliari";
	states["IT"]["CL"] = "Caltanissetta";
	states["IT"]["CB"] = "Campobasso";
	states["IT"]["CE"] = "Caserta";
	states["IT"]["CT"] = "Catania";
	states["IT"]["CZ"] = "Catanzaro";
	states["IT"]["CH"] = "Chieti";
	states["IT"]["CO"] = "Como";
	states["IT"]["CS"] = "Cosenza";
	states["IT"]["CR"] = "Cremona";
	states["IT"]["KR"] = "Crotone";
	states["IT"]["CN"] = "Cuneo";
	states["IT"]["EN"] = "Enna";
	states["IT"]["FE"] = "Ferrara";
	states["IT"]["FI"] = "Florence";
	states["IT"]["FG"] = "Foggia";
	states["IT"]["FO"] = "Forli";
	states["IT"]["FR"] = "Frosinone";
	states["IT"]["GE"] = "Genova";
	states["IT"]["GO"] = "Gorizia";
	states["IT"]["GR"] = "Grosseto";
	states["IT"]["IM"] = "Imperia";
	states["IT"]["IS"] = "Isernia";
	states["IT"]["SP"] = "La Spezia";
	states["IT"]["AQ"] = "L'Aquila";
	states["IT"]["LT"] = "Latina";
	states["IT"]["LE"] = "Lecce";
	states["IT"]["LC"] = "Lecco";
	states["IT"]["LI"] = "Livorno";
	states["IT"]["LO"] = "Lodi";
	states["IT"]["LU"] = "Lucca";
	states["IT"]["MC"] = "Macerata";
	states["IT"]["MN"] = "Mantua";
	states["IT"]["MS"] = "Massa-Carrara";
	states["IT"]["MT"] = "Matera";
	states["IT"]["ME"] = "Messina";
	states["IT"]["MI"] = "Milan";
	states["IT"]["MO"] = "Modena";
	states["IT"]["NA"] = "Napoli";
	states["IT"]["NO"] = "Novara";
	states["IT"]["NU"] = "Nuoro";
	states["IT"]["OR"] = "Oristano";
	states["IT"]["PD"] = "Padua";
	states["IT"]["PA"] = "Palermo";
	states["IT"]["PR"] = "Parma";
	states["IT"]["PV"] = "Pavia";
	states["IT"]["PG"] = "Perugia";
	states["IT"]["PS"] = "Pesaro e Urbino";
	states["IT"]["PE"] = "Pescara";
	states["IT"]["PC"] = "Piacenza";
	states["IT"]["PI"] = "Pisa";
	states["IT"]["PT"] = "Pistoia";
	states["IT"]["PN"] = "Pordenone";
	states["IT"]["PZ"] = "Potenza";
	states["IT"]["PO"] = "Prato";
	states["IT"]["RG"] = "Ragusa";
	states["IT"]["RA"] = "Ravenna";
	states["IT"]["RC"] = "Reggio di Calabria";
	states["IT"]["RE"] = "Reggio nell'Emilia";
	states["IT"]["RI"] = "Rieti";
	states["IT"]["RN"] = "Rimini";
	states["IT"]["RM"] = "Rome Roma";
	states["IT"]["RO"] = "Rovigo";
	states["IT"]["SA"] = "Salerno";
	states["IT"]["SS"] = "Sassari";
	states["IT"]["SV"] = "Savona";
	states["IT"]["SI"] = "Siena";
	states["IT"]["SO"] = "Sondrio";
	states["IT"]["SR"] = "Syracuse";
	states["IT"]["TA"] = "Taranto";
	states["IT"]["TE"] = "Teramo";
	states["IT"]["TR"] = "Terni";
	states["IT"]["TP"] = "Trapani";
	states["IT"]["TN"] = "Trento";
	states["IT"]["TV"] = "Treviso";
	states["IT"]["TS"] = "Trieste";
	states["IT"]["TO"] = "Turin";
	states["IT"]["UD"] = "Udine";
	states["IT"]["VA"] = "Varese";
	states["IT"]["VE"] = "Venice";
	states["IT"]["VB"] = "Verbano-Cusio-Ossola";
	states["IT"]["VC"] = "Vercelli";
	states["IT"]["VR"] = "Verona";
	states["IT"]["VV"] = "Vibo Valentia";
	states["IT"]["VI"] = "Vicenza";
	states["IT"]["VT"] = "Viterbo";

	states["MX"]["AG"] = "Aguascalientes";
	states["MX"]["BN"] = "Baja California";
	states["MX"]["BS"] = "Baja California Sur";
	states["MX"]["CM"] = "Campeche";
	states["MX"]["CP"] = "Chihuahua";
	states["MX"]["CH"] = "Chiapas";
	states["MX"]["CA"] = "Coahuila";
	states["MX"]["CL"] = "Colima";
	states["MX"]["DF"] = "Distrito Federal";
	states["MX"]["DU"] = "Durango";
	states["MX"]["GJ"] = "Guerrero";
	states["MX"]["GR"] = "Guanajuato";
	states["MX"]["HI"] = "Hidalgo";
	states["MX"]["JA"] = "Jalisco";
	states["MX"]["MX"] = "Mexico";
	states["MX"]["MC"] = "Michoacan";
	states["MX"]["MR"] = "Morelos";
	states["MX"]["NA"] = "Nayarit";
	states["MX"]["NL"] = "Nuevo Leon";
	states["MX"]["OA"] = "Oaxaca";
	states["MX"]["PU"] = "Puebla";
	states["MX"]["QE"] = "Queretaro";
	states["MX"]["QR"] = "Quintana Roo";
	states["MX"]["SL"] = "San Luis Potosi";
	states["MX"]["SI"] = "Sinaloa";
	states["MX"]["SO"] = "Sonora";
	states["MX"]["TB"] = "Tabasco";
	states["MX"]["TM"] = "Tamaulipas";
	states["MX"]["TL"] = "Tlaxcala";
	states["MX"]["VE"] = "Veracruz";
	states["MX"]["YU"] = "Yucatan";
	states["MX"]["ZA"] = "Zacatecas";
	states["NL"]["DR"] = "Drenthe";
	states["NL"]["FL"] = "Flevoland";
	states["NL"]["FR"] = "Friesland";
	states["NL"]["GE"] = "Gelderland";
	states["NL"]["GR"] = "Groningen";
	states["NL"]["LI"] = "Limburg";
	states["NL"]["NB"] = "Noord Brabant";
	states["NL"]["NH"] = "Noord Holland";
	states["NL"]["OV"] = "Overijsl";
	states["NL"]["UT"] = "Utrecht";
	states["NL"]["ZE"] = "Zeeland";
	states["NL"]["ZH"] = "Zuid Holland";

	states["NZ"]["AU"] = "Auckland";
	states["NZ"]["BP"] = "Bay of Plenty";
	states["NZ"]["CA"] = "Canterbury";
	states["NZ"]["CI"] = "Chatham Islands";
	states["NZ"]["GI"] = "Gisborne";
	states["NZ"]["HB"] = "Hawke's Bay";
	states["NZ"]["MW"] = "Manawatu-Wanganui";
	states["NZ"]["MA"] = "Marlborough";
	states["NZ"]["NE"] = "Nelson";
	states["NZ"]["NO"] = "Northland";
	states["NZ"]["OT"] = "Otago";
	states["NZ"]["SO"] = "Southland";
	states["NZ"]["TK"] = "Taranaki";
	states["NZ"]["TS"] = "Tasman";
	states["NZ"]["WK"] = "Waikato";
	states["NZ"]["WG"] = "Wellington";
	states["NZ"]["WC"] = "West Coast";

	states["PR"]["AJ"] = "Adjuntas";
	states["PR"]["AD"] = "Aguada";
	states["PR"]["AL"] = "Aguadilla";
	states["PR"]["AB"] = "Aguas Buenas";
	states["PR"]["AI"] = "Aibonito";
	states["PR"]["AN"] = "Anasco";
	states["PR"]["AC"] = "Arecibo";
	states["PR"]["AR"] = "Arroyo";
	states["PR"]["BC"] = "Barceloneta";
	states["PR"]["BQ"] = "Barranquitas";
	states["PR"]["BY"] = "Bayamon";
	states["PR"]["CR"] = "Cabo Rojo";
	states["PR"]["CG"] = "Caguas";
	states["PR"]["CA"] = "Camuy";
	states["PR"]["CV"] = "Canovanas";
	states["PR"]["CN"] = "Carolina";
	states["PR"]["CT"] = "Catano";
	states["PR"]["CY"] = "Cayey";
	states["PR"]["CB"] = "Ceiba";
	states["PR"]["CL"] = "Ciales";
	states["PR"]["CD"] = "Cidra";
	states["PR"]["CO"] = "Coamo";
	states["PR"]["CM"] = "Comerio";
	states["PR"]["CZ"] = "Corozal";
	states["PR"]["CU"] = "Culebra";
	states["PR"]["DO"] = "Dorado";
	states["PR"]["FJ"] = "Fajardo";
	states["PR"]["FL"] = "Florida";
	states["PR"]["GC"] = "Guanica";
	states["PR"]["GM"] = "Guayama";
	states["PR"]["GL"] = "Guayanilla";
	states["PR"]["GB"] = "Guaynabo";
	states["PR"]["GR"] = "Gurabo";
	states["PR"]["HA"] = "Hatillo";
	states["PR"]["HO"] = "Hormigueros";
	states["PR"]["HU"] = "Humacao";
	states["PR"]["IS"] = "Isabela";
	states["PR"]["JY"] = "Jayuya";
	states["PR"]["JD"] = "Juana Diaz";
	states["PR"]["JC"] = "Juncos";
	states["PR"]["LJ"] = "Lajas";
	states["PR"]["LR"] = "Lares";
	states["PR"]["LM"] = "Las Marias";
	states["PR"]["LP"] = "Las Piedras";
	states["PR"]["LZ"] = "Loiza";
	states["PR"]["LQ"] = "Luquillo";
	states["PR"]["MT"] = "Manati";
	states["PR"]["MR"] = "Maricao";
	states["PR"]["MB"] = "Maunabo";
	states["PR"]["MG"] = "Mayaguez";
	states["PR"]["MC"] = "Moca";
	states["PR"]["MV"] = "Morovis";
	states["PR"]["NG"] = "Naguabo";
	states["PR"]["NR"] = "Naranjito";
	states["PR"]["OR"] = "Orocovis";
	states["PR"]["PT"] = "Patillas";
	states["PR"]["PN"] = "Penuelas";
	states["PR"]["PO"] = "Ponce";
	states["PR"]["QB"] = "Quebradillas";
	states["PR"]["RC"] = "Rincon";
	states["PR"]["RG"] = "Rio Grande";
	states["PR"]["SB"] = "Sabana Grande";
	states["PR"]["SA"] = "Salinas";
	states["PR"]["SG"] = "San German";
	states["PR"]["SJ"] = "San Juan";
	states["PR"]["SL"] = "San Lorenzo";
	states["PR"]["SS"] = "San Sebastian";
	states["PR"]["SI"] = "Santa Isabel";
	states["PR"]["TA"] = "Toa Alta";
	states["PR"]["TB"] = "Toa Baja";
	states["PR"]["TJ"] = "Trujillo Alto";
	states["PR"]["UT"] = "Utuado";
	states["PR"]["VA"] = "Vega Alta";
	states["PR"]["VB"] = "Vega Baja";
	states["PR"]["VQ"] = "Vieques";
	states["PR"]["VL"] = "Villalba";
	states["PR"]["YB"] = "Yabucoa";
	states["PR"]["YU"] = "Yauco";

	states["PT"]["AR"] = "Acores (Azores)";
	states["PT"]["AV"] = "Aveiro";
	states["PT"]["BA"] = "Braga";
	states["PT"]["BJ"] = "Beja";
	states["PT"]["BN"] = "Braganca";
	states["PT"]["CB"] = "Castelo Branco";
	states["PT"]["CO"] = "Coimbra";
	states["PT"]["EV"] = "Evora";
	states["PT"]["FA"] = "Faro";
	states["PT"]["GU"] = "Guarda";
	states["PT"]["LE"] = "Leiria";
	states["PT"]["LI"] = "Lisboa";
	states["PT"]["MA"] = "Madeira";
	states["PT"]["PG"] = "Portalegre";
	states["PT"]["PO"] = "Porto";
	states["PT"]["SA"] = "Santarem";
	states["PT"]["SE"] = "Setubal";
	states["PT"]["VC"] = "Viana do Castelo";
	states["PT"]["VR"] = "Vila Real";
	states["PT"]["VS"] = "Viseu";

	states["ZA"]["EC"] = "Eastern Cape";
	states["ZA"]["FS"] = "Free State";
	states["ZA"]["GT"] = "Gauteng";
	states["ZA"]["NL"] = "Kwazulu-Natal";
	states["ZA"]["MP"] = "Mpumalanga";
	states["ZA"]["NC"] = "Northern Cape";
	states["ZA"]["NP"] = "Northern Province";
	states["ZA"]["NW"] = "North-West";
	states["ZA"]["WC"] = "Western Cape";

 }//end setStates()


/*******************************************************************************
 functions to get html for <select></select> options
 *******************************************************************************/
 function getCountryOptions(cSelected)
 {
	if (countries == null) return "";
	if (cSelected == null) cSelected == "";

	if (countries["Selected"] == null && cSelected != "")
	{
		countries["Selected"] = cSelected;
	}

	var html = "\n\t<option value=\"__\"></option>\n";
	var option = "";

	for(var name in countries)
	{
		if (name != "Selected")
		{
			option = (name != cSelected)? "":" SELECTED=\"SELECTED\"";
			html += "\t<option value=\""+name+"\""+option+">"+
					countries[name]+"</option>\n";
		}
	}
	return html+"\n";
 }


 function getProduct()
 {
	var def = products["sku"]["WVCF"];
	var sku = getProductSKU();

	return ((sku!="" && products["sku"][sku])? products["sku"][sku] : def);
 }

 function getProductHTML(product)
 {
	var sku = (product)?product:getProductSKU();

	var html = "\n";
	var option = "";

	if (sku == "" && products["sku"][sku] == undefined)
	{
		sku = "WVCF";

		html = "\n"+
		"\t<select \n"+
		"\t	tabindex=\"1\" id=\"RegSWList\"\n"+
		"\t	name=\"RegSWList\" class=\"menu\" value=\""+sku+"\"\n"+
		"\t	style=\"width:100%\"\n"+
		"\t	onBlur=\"this.className='menu';\" \n"+
		"\t	onFocus=\"this.className='mark';\" \n"+
		"\t	size=\"1\" \n"+
		"\t>\n";

		for(var name in products["sku"])
		{
			option = (name != sku)? "":" SELECTED=\"SELECTED\"";
			html += "\t\t<option value=\""+name+"\""+option+">"+
				products["sku"][name]+"</option>\n";
		}

		html += "\t</select>\n";
	}
	else // specified product SKU
	{
		html += "\t<input id=\"product\" name=\"product\" type=\"hidden\" ";
		html += "value=\""+sku+"\" />";
	}

	return html;
 }

 function getProductSKU()
 {
	var arrQueries = new Array(
		"product","ProductId","product_id","RegSWList","RegProdId","sku","swlist"
	);

	for(var x in arrQueries)
	{
		var o = getObject(arrQueries[x]);
		var q = getQuery(arrQueries[x]);

		if (q == "" && o != null) q = o.value;
		if (q == "" || q == null) continue;

		for(var sku in products["sku"])
		{
			var val = products["sku"][sku];

			if (gmatch(val,q) || gmatch(q,sku))
			{
				return sku;
			}
		}
		for(var sid in products["sku_id"])
		{
			var val = products["sku"][sid];

			if (gmatch(val,q) || gmatch(q,sid))
			{
				return products["sku_id"][sid];
			}
		}
	}

	return "";
 }


 function getReferOptions(defaultKey)
 {
	if (referTypes == null) return "";
	if (defaultKey == null || defaultKey == "") defaultKey = referTypes["Selected"];

	referTypes["Selected"] = defaultKey;

	var html = "\n";
	var option = "";

	for(var key in referTypes)
	{
		if (key != "Selected")
		{
			option = (key != defaultKey)? "":" SELECTED=\"SELECTED\"";
			html += "\t<option value=\""+key+"\""+option+">"+
				referTypes[key]+"</option>\n";
		}
	}
	return html+"\n";
 }

 function getStateOptions(country, selState)
 {
	if (country == null) return "";
	if (countries == null) return "";
	if (selState == null) selState == "";
	if (states[country] == null) return "";

	if (states[country]["Selected"] == null && selState != "")
	{
		states[country]["Selected"] = selState;
	}

	var html = "\n\t<option value=\"__\"></option>\n";
	var option = "";

	for(var name in states[country])
	{
		if (name != "Selected")
		{
			option = (name != selState)? "":" SELECTED=\"SELECTED\"";
			html += "\t<option value=\""+name+"\""+option+">"+
					states[country][name]+"</option>\n";
		}
	}
	return html+"\n";
 }


 function chkCountry(field)
 {
	var value = field.value;

	return (value != null && value != "" && states[value.toUpperCase()] != null);
 }



/*******************************************************************************
 * checkFocus:	check if the field can be focused, or clear the flag object
 *******************************************************************************/

 function checkFocus(field, chkRequired)
 {
	if (typeof field == 'undefined' || field == null) return false;
	if (typeof chkRequired == 'undefined') chkRequired = false;

	if (chkRequired)
	{
		try
		{
		//	field.focus(); // this could cause looping in RegNation
		}
		catch(e)
		{
			return false;
		}
	}

	return true;
 }


/*******************************************************************************
 function check_all: use checkform's to correspond with HTML codes in the form.
 !caution: any changes to the field onBlur codes should also be reflected here.
 *******************************************************************************/

 function check_all(theForm)
 {
	if (checkform(theForm.RegFiName, "name",   2)
	 && checkform(theForm.RegMiInit, "M.I.",   1)
	 && checkform(theForm.RegLaName, "name",   2)
	 && checkform(theForm.RegJTitle, "title",  2)
	 && checkform(theForm.RegOrName, "organization",3)
	 && checkform(theForm.RegAddrL1, "address",6)
	 && checkform(theForm.RegAddrL2, "address",6)
	 && checkform(theForm.RegCiTown, "city",   2)
	 && checkform(theForm.RegCounty, "county", 2)
	 && checkform(theForm.RegRegion, "state/region",2)
	 && checkform(theForm.RegZIPost, "ZIP",    5)
	 && checkform(theForm.RegNation, "country",2)
	 && checkform(theForm.RegPhone1, "phone", 10)
	 && checkform(theForm.RegPhone2, "phone#",10)
	 && checkform(theForm.RegEmAddr, "email",  7)
	 && checkform(theForm.RegURLink, "URL",   10)
	 && checkform(theForm.RegRefer1, "refer",  1)
	 && checkform(theForm.RegRefer2, "referral")) { return true;
	}

	return false;
 }


/*******************************************************************************
 * checkform:	main function to validate form data
 * arguments:   field - input filed object,
 *		title - title for the input field
 *		nsize - the minimum required length
 *		required - if this is a required field
 * ret value:	valid (true) or invalid (false) field
 *******************************************************************************/
 function checkform(field, title, nsize, required)
 {
	if (field == null) return false;
	if (title == null) title = "input";
	if (nsize == null) nsize = 1;

	var regname = field.name;
	var objText = getObject("err_"+regname); // get the error object.
	var errText = "";

	if (typeof field == 'undefined') return false;

	if (typeof required == 'undefined' || required==null)
	{
		if (regnames["required"])
		{
			required = regnames["required"][regname];
		}
		else	// not defined
		{
			required = false;
		}
	}

	if (required && (isVacant(field)||field.value=="__")) // field value has been trimmed.
	{
		checkFocus(field, required);
		dispError(objText, "&lt;&lt; blank "+title+".");
		return false;
	}
	else	// safe to clear the focus flag
	{
		checkFocus(field, false);
	}

	var regvalue = field.value; // get value with no preceding & extra blanks.

	if (objText && field.form["RegLoaded"]) dispError(objText, " ");  // clear the previous error.

	if (regvalue.length && regvalue.length < nsize)
	{
		errText = "&lt;&lt; Invalid length for "+title+".";
	}
	else	// at least valid length
	{
	    switch(field.name)
	    {
		case "RegFiName":
		case "RegMiInit":
		case "RegLaName":
			if (chkEnglishName(regvalue)) return true; break;

		case "RegAddrL1":
		case "RegAddrL2":
		case "RegOrName":
		case "RegJTitle":
			if (chkWebName(regvalue)) return true; break;

		case "RegCiTown":
		case "RegCounty":
		case "RegRegion":
		case "RegNation":
			if (chkUnicodeName(regvalue)) return true; break;

		case "RegZIPost":
			if (chkPostalCode(regvalue)) return true; break;

		case "RegPhone1":
		case "RegPhone2":
			if (chkPhoneNumber(regvalue)) return true;
			errText = "&lt;&lt; Format:<font color='green'><i>(###) ###-####</font></i> ";
			break;

		case "RegEmAddr":
			field.value = regvalue = regvalue.toLowerCase();
			field.value = regvalue = regvalue.replace(" ","");
			if (regvalue.indexOf("righthandeng") >=0) break;
			if (chkEmailAddress(regvalue)) return true;
			errText = "&lt;&lt; Format:<font color='green'><i> "+
					  "name@domain.com  </i></font> "
			break;

		case "RegURLink":
			field.value = regvalue = regvalue.replace(" ","");
			if (chkUrlAddress(regvalue)) return true;
			errText = "&lt;&lt; http://www.domain.com ";
			break;

		case "RegRefer1":
			var error2 = getObject("err_RegRefer2");
			var field2 = field.form["RegRefer2"];
			var value2 = field2.value;

			if (regvalue == "0" )
			{
				errText = "choose one!"; break;
			}
			if (value2=="Which one?" || isBlanks(regvalue))
			{
				field2.value = "Which one?";
				errText = "<font color=green>&lt;&lt; your referral:</font>";
				dispError(error2, " ");
				break;
			}
			field2.className = "field";
			field2.disabled = false;
			checkFocus(field2);
			return true;
			break;

		 case "RegRefer2":
			var error1 = getObject("err_RegRefer1");
			var field1 = field.form["RegRefer1"];
			var value1 = field1.value;

			if (chkWebName(regvalue) && !isBlanks(regvalue))
			{
				if (regvalue=="Which one?") field.value="";
				dispError(objText, " ");
				return true;
			}
			field.value = "N/A";
			errText = "&lt;&lt; Referral information is not completed!";
			checkFocus(field);
			break;

		default: break;
	    }
	}

	if (errText=="")
	{
		errText = "&lt;&lt; Invalid "+title+".";
	}
	if (field.value != "")
	{
		dispError(objText, errText);
		checkFocus(field, required);
	}

	return (required)?false:true;

 }//end checkform()




/*******************************************************************************
 function confirm_all: collects and confirms the form data before submit
 *******************************************************************************/
 function confirm_all(theForm, relocation)
 {
	var hasRedir = (relocation==null || relocation=="")? false : true;
	var numField = theForm.elements.length;

	if (check_all(theForm))
	{
		var theDate = new Date();
		var theData = "!!!For serial code request, please reply within 30 hours!!!\n\n";
		var thePrompt =
			"To receive the serial number for download, \n"+
			"you are about to submit the following information:\n\n";
		var theHeader = "Registration: ";
		var theAppend = (navigator.cookieEnabled) ? "Cookie enabled on " : "";
		var theProduct = getProduct();

		if (!isBlanks(theProduct))
		{
			theHeader += theProduct + "\n";
		}
		theData += theHeader;

		for(var i=0; i < numField; i++)
		{
			var field = theForm.elements[i];
			var fname = theForm.elements[i].name;
			var ftype = theForm.elements[i].type;
			var value = theForm.elements[i].value;
			var vtext = value;

			var title = regnames["=="][fname] + " ";

			if (title == null || title == 'undefined ') continue;
			if (fname.substr(0,3)!="Reg" || ftype=="button" || ftype=="reset") continue;

			if (fname == "RegNation") vtext = countries[value];
			if (fname == "RegRefer1") vtext = referTypes[value];

			if (vtext != null && vtext != "")
			{
				savecookie(fname, value);
				theData += " \n&" + fname;
				theData += " \t=" + value;
				thePrompt += title + "\t=  ";
				thePrompt += vtext + "\n";
			}
		}
		theAppend += navigator.cpuClass+":"+navigator.platform+" ("+
				navigator.systemLanguage+"):"+
				navigator.appCodeName+"/"+
				navigator.appVersion+navigator.appMinorVersion+" \n";
		theAppend += theDate.toGMTString();

		theData += " \n\n" + theAppend;

		thePrompt += "--------------------------------------------------";
		thePrompt += "\n\nClick OK to confirm:\n";

	//	if (confirm(thePrompt))
		{
			desubmit(theForm);
		//	saveform(theForm);	// could be too large to be saved...

			if (hasRedir)
			{
				sendmail(theForm, theData, emailAddress);
				document.location = relocation+"?product="+getProduct();
			}
			return true;
		}
	}
	return false;

 }//end confirm_all()




/*******************************************************************************
 * function concatenateQueryString - generate query string registration form
 *******************************************************************************/
 function concatenateQueryString(theForm, bUseList)
 {
	if (typeof theForm == 'undefined') return "";
	if (typeof bUseList == 'undefined') bUseList = false;

	var query = "";

	for(var i=0; i < theForm.elements.length; i++)
	{
		var vname = theForm.elements[i].name;
		var vtype = theForm.elements[i].type;
		var value = theForm.elements[i].value;

		if (vtype=="button"||vtype=="reset"||vtype=="submit") continue;

		if (value != null && value != "")
		{
			if (bUseList)	// Listing all queries
			{
				query += "\n";
			}
			query += "&" + vname;
			query += "=" + value;
		}
	}

	return query;
 }




/*******************************************************************************
 * function desubmit: to gray the reset/submit buttons after submit form inputs
 *******************************************************************************/
 function desubmit(theForm)
 {
	if (document.all || document.getElementById)
	{
		for(var i=0; i< theForm.length; i++)
		{
			var elem = theForm.elements[i];
			var type = elem.type.toLowerCase();

			if (type=="submit"||type=="reset")
			{
				elem.disabled = true;
			}
		}
	}
 }




/*******************************************************************************
 * sendmail: using 'mailto:name@domain?cc=CC&subject="Subject"&body="Bodytext"'
 *******************************************************************************/
 function sendmail(theForm, theData, email)
 {
	var account = "Info"+"@"+"RightHandEng"+".com";
	var address = (chkEmailAddress(email))? email : account;
	var subject = "Registration: "+getProduct();
	var strMail = "mailto:"+address+"?subject="+subject;

//	strMail += "&body="+theData;	// this is not needed
//	theForm.Email.value = theData;	// extra email data for server-side
	theForm.action = strMail;
	return strMail;
 }




/*******************************************************************************
 * dispError: function to display error messages
 * arguments: error as object name to render the error message string in msgs
 *******************************************************************************/
 var errRender;		// global object handle to render the error message.
 var idTimeout;
 var setRender = 1;

 function dispError(error, msgs)
 {
	errRender = getObject("lbl_RegPrompt");
	thePrompt = "<font color='red'>*</font>: These fields must be completed. ";
	strRender = "* <font color='deeppink'>&lt;&lt;</font>: These fields require non-blank input before submit. ";

	if (!error)
	{
		window.status = "Invalid value! Check your input before submit!";
	}
	else if (!msgs)
	{
		error.innerHTML = "&lt;&lt; blank!<br/>";
		errRender.innerHTML = strRender;
	}
	else if (errRender)
	{
		errRender.innerHTML = thePrompt;
		error.innerHTML = msgs + "<br/>";
	}

	return true;

 }//end dispError


 function renderBlink(errRender, setRender)	// called by dispError() to render colors
 {
	return;	// stop using this for now

	var rgboff = 0xC000C0;
	var rgbmin = 0x008080;
	var rgbmax = 0xF0F0F0;

	var rgbval = Math.round(Math.random()*(rgbmin)) + rgboff;

	if (setRender>1)
	{
		idTimeout = setTimeout("renderBlink(errRender, --setRender)", 500);
	}
	else
	{
		clearTimeout(idTimeout);
		rgbval = 0x4169E1;	// restore color:royalblue;
	}

	if (errRender)
	{
		errRender.style.color = rgbval;
	}
 }




/*******************************************************************************
 functions to rollover classes for the buttons
 *******************************************************************************/
 function normalIt(field, classname)
 {
	if (!(field && field.className)) return;
	if (classname) field.className = classname;

	window.status = "Tips: Move mouse pointer over the button to see the help.";
 }

 function hiliteIt(field, classname)
 {
	if (!(field && field.className)) return;
	if (classname) field.className = classname;

	msgCancel = "Leave for the homepage without submitting the registration.";
	msgChange = "You need to click here to confirm your registration change request.";
	msgDirect = "Start to download the specified product ...";
	msgFinish = "Just one more click to submit your registration for the product.";
	msgGoBack = "Back to the previous page and rework the registration form.";
	msgRecall = "Recall Data: Reload your previous form data in cookies.";
	msgResets = "Reset Form: Clear all inputs but leave default values.";
	msgSubmit = "Save & Submit: Save all input for future use and submit the form.";
	msgStatus = "Tips: Move mouse pointer over the button to see the help ";

	switch(field.name)
	{
		case "Cannel": message = msgCancel; break;
		case "Change": message = msgChange; break;
		case "Direct": message = msgDirect; break;
		case "Finish": message = msgFinish; break;
		case "GoBack": message = msgGoBack; break;
		case "Recall": message = msgRecall; break;
		case "Resets": message = msgResets; break;
		case "Submit": message = msgSubmit; break;

		default: message = msgStatus + "when it is available";
	}
	window.status = message;
 }




/*******************************************************************************
 function isVacant: check and as well truncate extra blanks, repeats, and noises
 *******************************************************************************/
 function isVacant(field)
 {
	var isInetAddr = (field.name=="RegEmAddr"||field.name=="RegURLink")?true:false;
	var strtrunc = "";
	var start = 0, end = 0, noises = 0, repeats = 0, limit = 4;
	var thelast = ' ', hasTooManyNoisesOrRepeats = false;

	for(var i=0; i < field.value.length; i++)
	{
		thechar = field.value.charAt(i);
		if (isNotBlank(thechar))
		{
			// find the first non-blank char
			if (!start) start = end = i+1;

			// find the noise in repeats and a unsyllabic joint
			if (thechar == thelast)
			{
				if (i == end) repeats ++;
			}
			else
			{
				if (i == end && isNoises(thechar, thelast))
				{
					noises ++;
				}
				else
				{
					noises = 0;
				}
				thelast = thechar;
				repeats = 0;
			}
			// quit if noise repeats over the limit
			if (noises >= limit || repeats > limit) hasTooManyNoisesOrRepeats = true;

			// keep only one blank space
			if (i > end) strtrunc += " ";

			// start appending to a new truncated string
			strtrunc += thechar;

			// index after the last non-blank char so far
			end = i + 1;

			// uppercase the first letter, but not for url & email addresses
			if (!isInetAddr && start == end) strtrunc = strtrunc.toUpperCase();
		}
	}
	if (hasTooManyNoisesOrRepeats)
	{
		var strAlert = "You are not allowed to input something like this!\n";
		if (confirm(strAlert)) strtrunc = ""; // delete all if noises confirmed
	}
	// sets the truncated str back to field
	field.value = (strtrunc.toUpperCase()!= "N/A")? strtrunc : "";

	return (field.value.length > 0)? false : true;

 }//end isVacant()




/*******************************************************************************
 * sub routines to check valid tokens (eg. blank, vowels, digits, etc...)
 *******************************************************************************/
 function isBlanks(str)
 {
	for(var i=0; i< str.length; i++)
	{
		if (isNotBlank(str.charAt(i))) return false;
	}
	return true;
 }

 function isNotBlank(chr)
 {
	return ((chr>unescape("%20") && chr<unescape("%FF"))? true:false);
 }

 function isNumber(chr)
 {
	return ((chr<'0'||chr>'9')? false:true);
 }

 function isSymbol(chr)
 {
	if((chr>=unescape("%21")&&chr<=unescape("%2F")) // ASCII !"#$%&'()*+,-./
	 ||(chr>=unescape("%3A")&&chr<=unescape("%40")) // ASCII :;<=>?@
	 ||(chr>=unescape("%5B")&&chr<=unescape("%60")) // ASCII [\]^_`
	 ||(chr>=unescape("%7B")&&chr<=unescape("%7E")) // ASCII {|}~
	 ) return true;
	return false;
 }

 function isLetter(chr)
 {
	return ((chr>='a'&&chr<='z') || (chr>='A'&&chr<='Z')? true:false);
 }

 function isVowels(chr)
 {
	strVowels = "AEIOUaeiouÀÁÂÃÄÅÈÉÊËÌÍÎÏÒÓÔÕÖÙÚÛÜàáâãäåèéêëìíîïòóôõöùúûü";
	for(var i=0; i< strVowels.length; i++)
	{
		if (chr == strVowels.charAt(i)) return true;
	}
	return false;
 }

 function isConsnt(chr) // the English consonants, letters except vowels.
 {
	return ((isLetter(chr) && !isVowels(chr))? true:false);
 }

 function isDuplex(chr)
 {
	strDuplex = "hjlmnywxHJLMNYWX";	// the English semivowel letters
	for(var i=0; i< strDuplex.length; i++)
	{
		if (chr == strDuplex.charAt(i)) return true;
	}
	return false;
 }

 function isNoises(ch1, ch2)
 {
	var strMess1 = "DdFfGgHhJjKkLl";
	var strMess2 = "ZzXxCcVvBbNnMm";

	var hasMess1 = ((strMess1.indexOf(ch1) != -1) &&
			(strMess1.indexOf(ch2) != -1))? true : false;

	var hasMess2 = ((strMess2.indexOf(ch1) != -1) &&
			(strMess2.indexOf(ch2) != -1))? true : false;

	var hasNoises = (hasMess1 || hasMess2
		 ||((isDuplex(ch1) == isDuplex(ch2))
		 && (isConsnt(ch1) && isConsnt(ch2)))
		 || (isVowels(ch1) && isVowels(ch2))
		 || (isSymbol(ch1) && isSymbol(ch2)) ) ? true : false;

	return hasNoises;
 }




/*******************************************************************************
 * sub routines to check valid name, numbers, address, etc...
 *******************************************************************************/
 function chkEnglishName(str)   // a normal English name without digits:
 {
	if (!str.length) return false;

	strValid = "&'(),-./ abcdefghijklmnopqrstuvwxyz"; // not started with...

	for(var i=0; i < strValid.length; i++)
	{
		if (str.charAt(0) == strValid.charAt(i)) return false;
	}

	strValid += "ABCDEFGHIJKLMNOPQRSTUVWXYZ";	// valid started with...

	for(var j=1; j < str.length; j++)
	{
		for(var k=0; k < strValid.length; k++)
		{
			if (str.charAt(j) == strValid.charAt(k)) break;
		}
		if (k == strValid.length) return false
	}

	return true;
 }

 function chkPhoneNumber(str)
 {
	if (!str.length) return false;

	var numbers = 0, minLength = 8, maxLength = 18;
	var bracket = 0;

	if (str == "" || str.length < minLength) return false;

	for(var i=0; i < str.length; i++)
	{
		ch = str.charAt(i)
		if (ch >= '0' && ch <= '9') numbers++;
		else if (ch == '(') bracket++;
		else if (ch == ')') bracket--;
		else if (!(ch=='-'||ch=='.'||ch==' '||ch=='x'||ch=="+")) return false;
	}

	if (bracket!=0 || numbers<minLength || numbers>maxLength) return false;

	return true;
 }

 function chkPostalCode(str)	// valide in letters, digit, some chars
 {
	if (!str) return false;

	strValid = "ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz";
	strValid+= "0123456789()-./:;#@";

	for(var i=0; i < str.length; i++)
	{
		for(var j=0; j < strValid.length; j++)
		{
			if (str.charAt(i) == strValid.charAt(j)) break;
		}
		if (j == strValid.length) return false
	}
	return true;
 }

 function chkUnicodeName(str)   // name without digit and special chars
 {
	if (!str.length) return false;

	for(var i=0; i < str.length; i++)
	{
		ch = str.charAt(i);
		if((ch!=" ")&&(ch!="-")&&(ch!=".")&&(ch!=",")	// hypen, space
		&&!(ch>=unescape("%41")&&ch<=unescape("%5A"))	// ASCII 'A'-'Z'
		&&!(ch>=unescape("%61")&&ch<=unescape("%7A"))	// ASCII 'a'-'z'
		&&!(ch>=unescape("%80")&&ch<=unescape("%FF"))	// non-English chars
		) return false;
	}
	return true;
 }

 function chkUrlAddress(str)
 {
	str = str.toLowerCase();

	if (str=="" || str.substring(-2) == "//" || str.indexOf("www.domain.com")!= -1 ||
		str.indexOf(' ')!= -1 || str.indexOf('.')== -1 || str.length< 10 ||
	 !((str.indexOf('mailto:')==0 || str.indexOf('news:')==0) && str.indexOf('//')== -1)
	 && str.indexOf('http://')!=0 && str.indexOf('ftp://')!=0
	 && str.indexOf('nntp://')!=0 && str.indexOf('telnet://')!=0
	 && str.indexOf('gopher://')!=0 && str.indexOf('wais://')!=0
	 && str.indexOf('prospero://')!=0 && str.indexOf('file://')!=0 )
	{
		return false;
	}
	return true;
 }

 function chkWebName(str)   // digit and some special chars in name
 {
	if (!str.length) return false;

	strValid = "ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz";
	strValid+= "ƒŠŒŽšœžŸÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõöøùúûüý?";
	strValid+= "0123456789 ";

	for(var i=0; i < str.length; i++)
	{
		if (isSymbol(str.charAt(i))) continue;
		for(var j=0; j < strValid.length; j++)
		{
			if (str.charAt(i) == strValid.charAt(j)) break;
		}
		if (j == strValid.length) return false
	}
	return true;
 }




/*******************************************************************************
 * sub functions to check valid email address, using regular expression...
 * a regex script originated by Sandeep V. Tamhankar<stamhankar@hotmail.com>
 * available free online at http://javascript.internet.com
 *******************************************************************************/
 function chkEmailAddress(strInput)
 {
	var ValidAddressLength = 8;

	if (strInput == null || strInput == ""		/* a brief check */
	 || strInput.length < ValidAddressLength
	 || strInput.indexOf('@') == -1
	 || strInput.indexOf('.') == -1
	 || strInput.indexOf(' ') != -1) return false;

	/* start regex */
	var specials = "\\(\\)<>@,;:\\\\\\\"\\.\\[\\]"	/* special chars */
	var strValid = "\[^\\s" + specials + "\]"	/* pattern valid chars */

	var patEmail = /^(.+)@(.+)$/	/* pattern for "user@domain" format */
	var patQuoted = "(\"[^\"]*\")"	/* pattern for quoted "user"@domain */
	var atom = strValid + '+'
	/*  atom to represent a series of non-special chars
	 */
	var word = "(" + atom + "|" + patQuoted + ")"
	/*  word to represent one word in the typical username.
		could be either an atom or quoted string.
	 */
	var patUser = new RegExp("^" + word + "(\\." + word + ")*$")
	/*  pattern for the structure of the user
	 */
	var patDomain = new RegExp("^" + atom + "(\\." + atom + ")*$")
	/*  pattern for the structure of a normal symbolic domain
	 */
	var patIpdomain = /^\[(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})\]$/
	/*  pattern for IP address domain: user@[nnn.nnn.nnn.nnn],
		square brackets are required, number between 1~254.
	 */

	var arrayMatch = strInput.match(patEmail);
	/* a coarse pattern to break up username@domain into different pieces
	 */
	if (arrayMatch == null)
	{
		return false;	// failed to check @ and .'s in a general mould.
	}
	var strUser = arrayMatch[1];
	var strDomain = arrayMatch[2];

	if (strUser.match(patUser) == null)
	{
		return false	// not a valid username
	}
	var arrayIpdomain = strDomain.match(patIpdomain);
	/*  check valid pattern of IP address as domain in an email address
	 */
	if (arrayIpdomain != null)
	{
		for(var i=1; i <= 4; i++)
		{
			if (arrayIpdomain[i] > 255)
			{
				return false;
			}
		}
		return true;
	}
	var arrayDomain = strDomain.match(patDomain);
	/*  check valid pattern of a symbolic domain name
	 */
	if (arrayDomain == null)
	{
		return false;
	}
	/* domain name seems valid so far;
	   going to check the three-letter (com|edu|gov|org|...) domain
	   or a two-letter (cn|fr|uk|us|...) country code.
	 */
	var patAtom = new RegExp(atom,"g");
	var arrayNames = strDomain.match(patAtom);
	var max = arrayNames.length;
	/*  split the domain name to atoms in arrayNames
	 */
	if (arrayNames[max-1].length < 2
	 || arrayNames[max-1].length > 3)
	{
		return false;	// not end in a two letter or three letter word.
	}
	if (max < 2)
	{
		return false;	 // no hostname preceding the domain
	}

	return true;

 /* [Ref]: msdn version -
	var expEmail = /^[a-z][a-z_0-9\.]+@[a-z_0-9\.]+\.[a-z]{3}$/i
	if (expEmail.test(strInput)) return true;
 */
 }//end chkEmailAddress()








/*******************************************************************************
 * Generic JavaScript library
 *******************************************************************************
 */
/*=============================================================================*
 ** class Hash
 *=============================================================================*
 */
 function Hash()
 {
	this.length = 0;
	this.elements = new Array();
	this.items = this.elements;

	for(var i=0; i < arguments.length; i += 2)
	{
		if (typeof(arguments[i + 1]) != 'undefined')
		{
			this.items[arguments[i]] = arguments[i + 1];
			this.length++;
		}
	}

	this.remove = function(in_key)
	{
		var tmp_value;
		if (typeof(this.items[in_key]) != 'undefined')
		{
			this.length--;
			tmp_value = this.items[in_key];
			delete this.items[in_key];
		}
		return tmp_value;
	}

	this.get = function(in_key)
	{
		return this.items[in_key];
	}

	this.set = function(in_key, in_value)
	{
		if (typeof(in_value) != 'undefined')
		{
			if (typeof(this.items[in_key]) == 'undefined')
			{
				this.length++;
			}
			this.items[in_key] = in_value;
		}
		return in_value;
	}

	this.has = function(in_key)
	{
		return (typeof(this.items[in_key]) != 'undefined');
	}

}// class Hash




/*=============================================================================*
 * general string functions
 *=============================================================================*
 */
 function gmatch(str1, str2)
 {
	if (str1 == null || typeof str1 != "string") return false;
	if (str2 == null || typeof str2 != "string") return false;

	return (trim(str1).toLowerCase() == trim(str2).toLowerCase());
 }

 function trim(str)
 {
	return trimHead(trimTail(str));
 }

 function trimHead(str)
 {
	if (str == null || typeof str != "string") return false;
	var blanks = " \t\n\r\f";
	for(var x = 0; x < str.length && blanks.indexOf(str.charAt(x)) >= 0; x++);
	return str.substring(x, str.length);
 }

 function trimTail(str)
 {
	if (str == null || typeof str != "string") return false;
	var blanks = " \t\n\r\f";
	for(var x = str.length; x>0 && blanks.indexOf(str.charAt(x-1)) >= 0; x--);
	return str.substring(0, x);
 }


/*=============================================================================*
 * getColorHTML
 *=============================================================================*
 */
 function getColorHTML(text, color)
 {
	if (text == null) text = "";
	if (color == null) color = "teal";

	return ("<font color='"+color+"'>"+text+"</font>");
 }


/*=============================================================================*
 * getObject
 *=============================================================================*
 */
 function getObject(id)
 {
	if (id==""||id==null) return null;

	if (document.getElementById)
	{
		this.obj = document.getElementById(id);

		if (this.obj)
		{
			this.style = document.getElementById(id).style;
		}

	}
	else if (document.all)
	{
		this.obj = document.all[id];

		if (this.obj)
		{
			this.style = document.all[id].style;
		}
	}
	else if (document.layers)
	{
		this.obj = getObjNS4(document, id);

		if (this.obj)
		{
			this.style = this.obj;
		}
	}
	return this.obj;
 }


/*=============================================================================*
 * getObjectNS4
 *=============================================================================*
 */
 function getObjectNS4(obj, id)
 {
	var x = obj.layers;
	var foundLayer;

	for(var i=0; i<x.length; i++)
	{
		if (x[i].id == id)
		{
			foundLayer = x[i];
		}
		else if (x[i].layers.length)
		{
			var tmp = getObjNS4(x[i],id);
		}
		if (tmp) foundLayer = tmp;
	}
	return foundLayer;
 }




/*=============================================================================*
 function getQueryString(): return the QUERY_STRING part in HTTP URL
 *=============================================================================*
 */
 function getQueryString()
 {
	var strURL = unescape(location.href);
	var arrURL = new Array();
	var strQue = new String;

	if (strURL.indexOf('?'))
	{
		arrURL = strURL.split("?");
		for(var i=0; i<arrURL.length; ++i)
		{
			strQue = arrURL[i];	// skip extra question marks
		}
	}
	return strQue;
 }


/*=============================================================================*
 function getQuery(name): query by name in HTTP URL and return the value
 *=============================================================================*
 */
 function getQuery(name)
 {
	var arrURL = new Array();
	var arrQue = new Array();
	var strURL = unescape(window.location.href);
	var strQue = new String;
	var strVal = new String;

	if (strURL.indexOf('?'))
	{
		arrURL = strURL.split("?");
		for(var i=0; i<arrURL.length; ++i)
		{
			strQue = arrURL[i];	// skip extra question marks
		}
		if (strQue.indexOf('&')==-1) strQue += "&";

		arrQue = strQue.split("&");

		for(var j=0; j<arrQue.length; ++j)
		{
			var arrNew = new Array();
			arrNew = arrQue[j].split("=");

			if (arrNew[0].toLowerCase() == name)
			{
				strVal = arrNew[1];
			}
		}
	}
	var pat_lt = /</g
	var pat_gt = />/g

	strVal.replace(pat_lt, "&lt;");
	strVal.replace(pat_gt, "&gt;");

	return strVal;
 }


/*=============================================================================*
 * func : getXMLHttpRequest()
 *=============================================================================*
 */
 function getXMLHttpRequest()
 {
    var http_request = null;

    if (window.XMLHttpRequest) // Mozilla, Safari, IE6 ...
    {
    	try {
            http_request = new XMLHttpRequest();

            if (http_request.overrideMimeType)
            {
                http_request.overrideMimeType('text/xml');
            }
	}
	catch(e) {}
    }
    else if (window.ActiveXObject) // IE 6 and below
    {
        var server_typenames=[
            "Microsoft.XMLHTTP",
            "MSXML2.XMLHTTP",
            "MSXML2.XMLHTTP.5.0",
            "MSXML2.XMLHTTP.4.0",
            "MSXML2.XMLHTTP.3.0"
        ];

        for(var n=0; n < server_typenames.length; n++)
        {
            try {
                return new ActiveXObject(server_typenames[n]);
            }
            catch(e) {}
        }
    }
    return http_request;
 }


/*=============================================================================*
 * hidVisible
 *=============================================================================*
 */
 function hidVisible(objId)
 {
	objdom = new getObject(objId);
	objdom.style.visibility = "hidden";
	objdom.style.display = "none";
 }


/*=============================================================================*
 * setVisible
 *=============================================================================*
 */
 function setVisible(objId)
 {
	objdom = new getObject(objId);
	objdom.style.visibility = "visible";
	objdom.style.display = "block"
 }


/*=============================================================================*
 * sub routines to manipulate the cookies on client-side
 *=============================================================================*
 */
 function checkcookie(theForm)
 {
	if (!navigator.cookieEnabled) return false;

	if (typeof theForm == 'undefined') return false;
	if (theForm == null || theForm.elements == null) return false;
	if (theForm.elements.length == null) return false;
	if (theForm.elements[0] == null) return false;

	for(var i=0; i < theForm.elements.length; i++)
	{
		var field = theForm.elements[i];
		var fname = theForm.elements[i].name;
		var ftype = theForm.elements[i].type;

		if (ftype=="button"||ftype=="reset"||ftype=="submit") continue;
		if (null != getcookie(fname)) return true;
	}

	return false;
 }

 function deletecookie(cookiename)
 {
	if (typeof cookiename == 'undefined') return;
	var cookievalue = getcookie(cookiename);
	var expirations = new Date();
	expirations.setTime(expirations.getTime() - 1);
	document.cookie = name + "=" + cookievalue + "; expires=" + expirations.toGMTString();
 }

 function evalcookie(cookiename)
 {
	if (!navigator.cookieEnabled) return null;
	if (typeof cookiename == 'undefined') return null;

	var thisCookie = window.document.cookie.split("; ");

	for(var i=0; i<thisCookie.length; i++)
	{
		var cname = thisCookie[i].split("=")[0];
		var value = thisCookie[i].split("=")[1];
		if (cookiename == cname) { return value; }
	}
	return null;
 }

 function getcookie(cookiename)
 {
	if (typeof cookiename == 'undefined') return null;

	var args = cookiename + "=";
	var alen = args.length;
	var i = 0;

	while (i < document.cookie.length)
	{
		var j = i + alen;
		if (document.cookie.substring(i, j) == args)
		{
			var endstr = document.cookie.indexOf (";", j);
			if (endstr == -1) endstr = document.cookie.length;
			return unescape(document.cookie.substring(j, endstr));
		}
		i = document.cookie.indexOf(" ", i) + 1;
		if (i == 0) break;
	}
	return null;
 }

 function savecookie(cookiename, value)
 {
	if (!navigator.cookieEnabled) return false;

	var currDate=new Date;
	var nextDate=new Date;

	nextDate.setMonth(nextDate.getMonth()+6);

	document.cookie=cookiename+"="+value+";expires="+nextDate.toGMTString();
 }


/*=============================================================================*
 * sub routines to retrieve/save form data from the cookies on client-side
 *=============================================================================*
 */
 function loadform(theForm, replace)
 {
	if (typeof theForm == 'undefined') return;

	var hasCookie = navigator.cookieEnabled;
	var iElements = theForm.elements.length;

	/* JavaScript note:
		Since (0 == false == undefined == null), only
		using (typeof arg == "undefined") can test missing parameter.
	 */

	if (typeof replace == "undefined") replace = false;

	deletecookie("product");	// ensure varied products; 9/16/2004

	for(var i=0; hasCookie && i < iElements; i++)
	{
		var field = theForm.elements[i];
		var fname = field.name;
		var ftype = field.type;
		var value = field.value;

		if (value=="__"|| value=="--"|| !value) value = "";

		if (value && !replace) continue;
		if (ftype=="button"||ftype=="reset"||ftype=="submit") continue;
		if (fname=="RegSubject"||fname=="RegProduct") continue;
		if (fname=="product") continue;

		var cookievalue = getcookie(fname);

		if (cookievalue)
		{
			field.value = cookievalue;
			field.blur();
		}
	}

 }

 function saveform(theForm)
 {
	if (!navigator.cookieEnabled) return false;

	var hasCookie = navigator.cookieEnabled;
	var nElements = theForm.elements.length;

	for(var i=0; hasCookie && i < nElements; i++)
	{
		var field = theForm.elements[i].name;
		var value = theForm.elements[i].value;
		savecookie(field, value);
	}
 }




/*******************************************************************************
 * Programmed by jason_zhuyx@hotmail.com; (c)2006, Lin Zhou
 *******************************************************************************/
// End

