/*
File: lib_cart_jquery.js
Description: Miscellaneous functions shared by cart sites and cart admin

Now with 90% less prototype.js
*/


/*
*  "".htmlspecialchars() will aid in the elimination of XSS issues.
*/
String.prototype.htmlspecialchars = function ()	{
        return this.replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/"/g, '&quot;');
};


// -- browser detection
var strUserAgent = navigator.userAgent.toLowerCase();
	
var isIE = strUserAgent.indexOf("msie") > -1;
var isNS6 = strUserAgent.indexOf("netscape6") > -1;
var isNS4 = !isIE && !isNS6  && parseFloat(navigator.appVersion) < 5;
var isFirefox = strUserAgent.indexOf("firefox") > -1;
var isSafari = strUserAgent.indexOf("safari") > -1;
var isMac = strUserAgent.indexOf("mac") > -1;

var aryNavLinks = Array("/members/home.php",
					"/members/preferences.php",
					"/members/messages.php",
					"/members/media.php",
					"/members/blog.php",
					"/members/edit_friends.php",
					"/admin/members/"
				);

arrQuantity = new Array();

// ======= Form validation functions =======

/*
Function: valFormField
Contributors: Jordan Phillips
Description: Toggles validation message for form field if it is blank or fails the extra criteria check
Parameters:

objForm - Form object which containts the field
strFieldId - Id of field element
blnExtraCriteria - Boolean expression used to further validate the field
strErrorMsg - Optional, Will override existing error message for this field

Returns: True if field validates, false otherwise.
*/
function valFormField(objForm, strFieldId, blnExtraCriteria, strErrorMsg) {

	if ( blnExtraCriteria == undefined || blnExtraCriteria == null ) blnExtraCriteria = true;

	var objErrorMsg = $("#" + strFieldId + "Error");
	var objField = $(objForm).find('#' + strFieldId);

	if ( !objErrorMsg.length ) {

		alert("Error message container does not exist for field "+strFieldId);
		return;

	}

	if ( objField.type == "select-one" ) {

		strValue = objField.options[objField.selectedIndex].value;

	} else if ( objField.length > 0 ) {
	
		var opt = $(objField).find('option:checked');

		strValue = opt?opt.val():"";
		
	} else {		
		strValue = objField.value;
	}

	if ( strValue == "" || !blnExtraCriteria ) {
		
		if ( strErrorMsg != undefined && strErrorMsg != null ) {
			objErrorMsg.innerHTML = strErrorMsg;
		}

		objErrorMsg.show();

		$(objForm).data('blnValid', false);
		
		return false;

	} else {
		objErrorMsg.hide();

		return true;
	}

}

function checkDate(objField) {

	if (objField.value){
		if(!isValidDate(objField)){
			objField.focus();
			objField.value = "";
		}
	}
}

function isValidDate(dateField) {
	dateStr = dateField.value;
	// Checks for the following valid date formats:
	// MM/DD/YY   MM/DD/YYYY   MM-DD-YY   MM-DD-YYYY
	// Also separates date into month, day, and year variables
	
//	var datePat = /^(\d{2})(\/|-)(\d{2})\2(\d{2}|\d{4})$/;
	var datePat = /^(\d{2})(\/)(\d{2})\2(\d{2}|\d{4})$/;
	
	// To require a 4 digit year entry, use this line instead:
	// var datePat = /^(\d{1,2})(\/|-)(\d{1,2})\2(\d{4})$/;
	
	var matchArray = dateStr.match(datePat); // is the format ok?
	if (matchArray == null) {
	alert("Date is not in a valid format.");
	dateField.focus();
	return false;
	}
//	month = matchArray[1]; // parse date into variables
//	day = matchArray[3];
	day = matchArray[1];
	month = matchArray[3]; // parse date into variables
	year = matchArray[4];
	if (month < 1 || month > 12) { // check month range
	alert("Month must be between 1 and 12.");
	dateField.focus();
	return false;
	}
	if (day < 1 || day > 31) {
	alert("Day must be between 1 and 31.");
	dateField.focus();
	return false;
	}
	if ((month==4 || month==6 || month==9 || month==11) && day==31) {
	alert("Month "+month+" doesn't have 31 days!");
	dateField.focus();
	return false
	}
	if (month == 2) { // check for february 29th
	var isleap = (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
	if (day>29 || (day==29 && !isleap)) {
	alert("February " + year + " doesn't have " + day + " days!");
	dateField.focus();
	return false;
	   }
	}
	return true;  // date is valid
}

/*
Function: isValidEmail
Contributors: Jordan Phillips
Description: Tests for valid email address syntax
Parameters:

strEmail - Email address

Returns: True if valid, false otherwise.
*/
function isValidEmail(strEmail) {

	var emailfilter=/^\w+[\+\.\w-]*@([\w-]+\.)*\w+[\w-]*\.([a-z]{2,5}|\d+)$/i

	return emailfilter.test(strEmail);
}

function populateHidden(strValue, objField){
	var thisValue;
	if(strValue.search(/\\/)){
		arrValue=strValue.split("\\");
		thisValue = arrValue[arrValue.length-1];
	}else if(strValue.search(/\//)){
		arrValue=strValue.split("/");
		thisValue = arrValue[arrValue.length-1];
	}else{
		thisValue = strValue;
	}

	objField.value = thisValue;
}

function checkFileType(strValue, arrTypes){
	var goodFile = 0;
	var firstIndex = strValue.length-3;
	var strType = strValue.slice(firstIndex);
	for(var i = 0; i < arrTypes.length; i++){
		if(strType == arrTypes[i]){
			goodFile = 1;
		}
	}

	if(!goodFile){
		alert('not a valid file type');
	}

}

/*
Function: checkCharLength
Contributors: Jordan Phillips
Description: Enforces character limit on textarea fields
Parameters:

objEvent - event object
objField - textarea field being checked
intLimit - character limit

Returns: True if character limit hasn't been reach, False otherwise.
*/
function checkCharLength(objEvent, objField, intLimit) {

    if (objEvent.which)
        var intKeycode = objEvent.which; // mozilla
    else 
        var intKeycode = objEvent.keyCode; // ie

	if ( objField.value.length >= intLimit &&
			((intKeycode >= 48 && intKeycode <= 57)
			 || (intKeycode >= 65 && intKeycode <= 90)
			 || (intKeycode == 9)
			 || (intKeycode == 13)
			 ) ) {
		return false
	}
	
	return true;

}

// ==================================

function createSelectList(arrList, selectObj, strSelectedValue, strDefaultTxt, arrLeaveOut){
//alert(selectObj.name+" "+strSelectedValue);
	var j = 0;
	selectObj.options.length = 0;
//	selectObj.options[0] = new Option(strDefaultTxt, '');
	for (var k in arrList){
                var intAdd = 1;
		if(arrLeaveOut){
			for(var l in arrLeaveOut){
				if(l == k){
					intAdd = 0;
				}
			}
		}
                if(intAdd ==1){
                        selectObj.options[j] = new Option(arrList[k], k);
			if(k == strSelectedValue){
				selectObj.options[j].selected == true;
			}
                        j++;
                }

        }

}



function clearField(objField){
	objField.value = "";
}

function selectAll(objSelect){
        for(var i = objSelect.length-1; i >= 0; i--){
                objSelect[i].selected = true;
	}

}

function addToArray(arrOptions, strIndex, strValue){
	arrOptions[strIndex] = strValue;
}





function getSelectedValues (select) {
	var r = new Array();
	for (var i = 0; i < select.options.length; i++){
		if (select.options[i].selected)
			r[r.length] = select.options[i].value;
	}
	return r;
}

function getSelectVals (oField) {

	//oField = $(oField);

	if ( oField.type == "select-one" ) {

		return oField.options[oField.selectedIndex].value;

	} else {

		var aryVals = new Array();

		for (var i = 0; i < oField.options.length; i++){
			if (oField.options[i].selected) {
				aryVals[aryVals.length] = oField.options[i].value;
			}
		}

		return aryVals;

	}
}


function populateFieldFromSelect(select, objField){
	arrOptions = getSelectedValues(select);
	strOptions = arrOptions.join(",");
	objField.value = strOptions;
}

function formatDateField(objField){
	arrDate = objField.value.split("/");
	objField.value = arrDate[2]+arrDate[1]+arrDate[0]
}

function selectOptions(arrValues, objSelect){
        for(var i = objSelect.length-1; i >= 0; i--){
		for(var j = 0; j <= arrValues.length; j++){
			if(objSelect[i].value == arrValues[j]){
				objSelect[i].selected = true;
			}
		}
	}

}



function displayStatusMsg(strMsg, cssStyle) {

	if ( !strMsg ) {

		// -- hide message container
		$("#divStatusMsg").hide();

		// -- clear message container
		$("#divStatusMsg").html("");

	} else {

/*	disabled for now (jp)
		if ( $("divStatusMsg").style.display == "" ) {

			// -- add to existing message
			$("divStatusMsg").innerHTML += strMsg;

		} else {
*/
			// -- show message container
			$("#divStatusMsg").show();

			if ( cssStyle ) {
				// -- set css class if provided
				$("#divStatusMsg").className = cssStyle;
			}
		
			// -- display message
			$("#divStatusMsg").innerHTML = strMsg.replace("\\n", "<br />");

			$("#divStatusMsg").scrollIntoView(true);
		
			//alert($("divStatusMsg").innerHTML+"\n\n"+strMsg);

//		}

	}
	
}


// ====== Cart site functions ======

var shippingMethodSelected = false //	--	is toggled true when a shipping method is selected

var blnEmailCheck = false;
var blnSubmitting = false;

var blnExists;
var blnValidEmailHost;
var blnValidEmailSyntax = true;

function checkEmail(strEmail, fnCallback) {

	blnValidEmailSyntax = isValidEmail(strEmail);

	fnCallback = fnCallback != undefined ? fnCallback : cbCheckEmail;

	blnEmailCheck = false;

	if ( strEmail == "" ) return false;

	strURL = document.location.pathname;
	
//	alert(strURL);
	
	makeRequest(strURL+"?action=checkemail&email="+strEmail, "get", null, fnCallback);
//	document.location = "?action=checkemail&email="+strEmail;
	
}

function cbCheckEmail(objRequest) {


	if ( !callBack(objRequest) ) {
			return false;
	}

	objErrorMsg = $("#strEmailError");
	
	if ( blnValidEmailHost == false ) {

		objErrorMsg.html("* The email host for this address is not valid.");
		objErrorMsg.show();
		$("#frmAddEdit").blnValid = false;

	} else if ( blnExists ) {

		objErrorMsg.innerHTML = "* This <strong>Email Address<\/strong> is already being used.  Please choose another.";
		objErrorMsg.show();

		$("#frmAddEdit").blnValid = false;
		
	} else {

		objErrorMsg.innerHTML = "";
		objErrorMsg.show();

		blnEmailCheck = true;

		if ( blnSubmitting ) {
			$("#frmCreateNew").submit();
		}

	}
	
}

function cbCheckEmail_Checkout(objRequest) {

	// -- parse any js returned from ajax call
	// jquery evals response scripts by default @jalley
	//objRequest.responseText.evalScripts();

	blnEmailCheck = true;
	
	toggleConfirm();

}


// this is for action=signin
function valLoginForm_jquery (oForm) {
	$(oForm).data('blnValid', true);
	var strEmail = '', blnSubmitting = false;

	if ($(oForm).find(':input[name="strConfirm"]').length) {
		valFormField(oForm, 'strPassword', $(oForm).find(':input[name="strPassword"]').val() == $(oForm).find(':input[name="strConfirm"]').val(), '* Password and Confirm Password must match<br />');
		strEmail = $(oForm).find(':input[name="strEmail"]').val();

		if (!strEmail) {
			valFormField(oForm, 'strEmail', strEmail.indexOf('@') > -1 && strEmail.indexOf('.') > -1);
		}
		else if (!blnEmailCheck) {
			blnSubmitting = true;
			checkEmail(strEmail);
			return false;
		}
	}
	else {
		strEmail = $(oForm).find('#LoginName').val();
		valFormField(oForm, 'LoginName', strEmail.indexOf('@') > -1 && strEmail.indexOf('.') > -1);
		valFormField(oForm, 'Password');
	}

	return $(oForm).data('blnValid');
}

// this is for cart page login form
function valLoginForm(oForm) {

	oForm.blnValid = true;

//	alert(blnExists);

	if ( oForm.elements["strConfirm"] ) {

		valFormField(oForm, "strPassword", oForm.elements["strPassword"].value == oForm.elements["strConfirm"].value, "* Password and Confirm Password must match<br />");

		strEmail = oForm.elements["strEmail"].value;

		if ( !strEmail ) {

			valFormField(oForm, "strEmail", strEmail.indexOf("@") > -1 && strEmail.indexOf(".") > -1);

		} else if ( !blnEmailCheck ) {

			blnSubmitting = true;
			checkEmail(strEmail);
			return false;

		}


	} else {
		
		strEmail = oForm.elements["LoginName"].value;
		valFormField(oForm, "LoginName", strEmail.indexOf("@") > -1 && strEmail.indexOf(".") > -1);

		valFormField(oForm, "Password");
	}

//	alert($("frmLogin").blnValid);

	return oForm.blnValid;

}

function removeFromCart(intIndex) {

	strParams = "action=remove&index="+intIndex;
	strURL = document.location.pathname; //"removeFromCart.php";

	makeHTMLRequest(strURL+"?"+strParams, "get", "", null, "divCart");

}

function checkQuantityLimit(oQuantity, intLimit){
	if(oQuantity.value <=0){
		alert("Quantity must be greater than 0");
		oQuantity.focus();
		oQuantity.value=1;
	}
	if(intLimit > 0 && oQuantity.value > intLimit){
		alert("Quantity can not be greater than "+intLimit);
		oQuantity.focus();
		oQuantity.value=intLimit;
	}
}

function checkQuantity(oQuantity){
	if(oQuantity.value <=0){
		alert("Quantity must be greater than 0");
		oQuantity.focus();
		oQuantity.value=1;
	}
}

function verifyAndRecalc(oQuantity, oForm, intLimit){
	if(intLimit > 0 && oQuantity.value > intLimit){
		alert("Quantity can not be greater than "+intLimit);
		oQuantity.focus();
		oQuantity.value=intLimit;
		postForm(oForm, "shop.php", null, "divCart");
	}
	if(oQuantity.value <=0){
		alert("Quantity must be greater than 0");
		oQuantity.focus();
		oQuantity.value=1;
		postForm(oForm, "shop.php", null, "divCart");
	}else{
		postForm(oForm, "shop.php", null, "divCart");
	}
}

function recalcCart (oForm) {
	postForm(oForm, null, null, "divCart");
}

function redirectDiscounts(){
	window.location = "adminDiscountTable.php";
}

function buildSKUs(oForm) {

	arySKUs = Array();

	for ( i=0; i<oForm.elements.length; i++ ) {

		oField = oForm.elements[i];

if ( !oField.name ) continue;


		if ( oForm.elements[oField.name].options ) {
			strValue = getSelectVals(oField);
		} else {
			strValue = oField.value;
		}

		strValue = strValue.split('|')[0];

		regexps = /^Option_(\w+?)(\d*)$/;
		aryMatches = oField.name.match(regexps);

		if ( aryMatches ) {

			intOptGroup = aryMatches[2]?aryMatches[2]:1;

			if ( !arySKUs[intOptGroup-1] ) {
				arySKUs[intOptGroup-1] = "";
			}

			arySKUs[intOptGroup-1] += strValue;
//			alert("Option: "+aryMatches[0]+", "+aryMatches[1]+", "+aryMatches[2]);
		}

		regexps = /^SKU_(\w+?)(\d*)$/;
		aryMatches = oField.name.match(regexps);

		if ( aryMatches ) {

			arySKUs[arySKUs.length] = strValue;

		}

	}


	if ( oForm.elements.strSKUs.value ) {
//		arySKUs.unshift(oForm.elements.strSKUs.value);
		arySKUs.push(oForm.elements.strSKUs.value);
//		alert("static skus: "+oForm.elements.strSKUs.value);
	}

	strSKUs = arySKUs.join(",");

	return strSKUs;

}


// -- borrowed from http://evolt.org/node/24700
function isValidCC (cardNumber, cardType) {

  var isValid = false;
  var ccCheckRegExp = /[^\d ]/;
  isValid = !ccCheckRegExp.test(cardNumber);

  if (isValid)
  {
    var cardNumbersOnly = cardNumber.replace(/ /g,"");
    var cardNumberLength = cardNumbersOnly.length;
    var lengthIsValid = false;
    var prefixIsValid = false;
    var prefixRegExp;

    switch(cardType)
    {
      case "MC":
        lengthIsValid = (cardNumberLength == 16);
        prefixRegExp = /^5[1-5]/;
        break;

      case "VS":
        lengthIsValid = (cardNumberLength == 16 || cardNumberLength == 13);
        prefixRegExp = /^4/;
        break;

      case "AE":
        lengthIsValid = (cardNumberLength == 15);
        prefixRegExp = /^3(4|7)/;
        break;

	  case "DS":
        lengthIsValid = (cardNumberLength == 16);
        prefixRegExp = /^6011/;
        break;

      default:
        prefixRegExp = /^$/;
        alert("Card type not found");
    }

    prefixIsValid = prefixRegExp.test(cardNumbersOnly);
    isValid = prefixIsValid && lengthIsValid;
  }

  if (isValid)
  {
    var numberProduct;
    var numberProductDigitIndex;
    var checkSumTotal = 0;

    for (digitCounter = cardNumberLength - 1; 
      digitCounter >= 0; 
      digitCounter--)
    {
      checkSumTotal += parseInt (cardNumbersOnly.charAt(digitCounter));
      digitCounter--;
      numberProduct = String((cardNumbersOnly.charAt(digitCounter) * 2));
      for (var productDigitCounter = 0;
        productDigitCounter < numberProduct.length; 
        productDigitCounter++)
      {
        checkSumTotal += 
          parseInt(numberProduct.charAt(productDigitCounter));
      }
    }

    isValid = (checkSumTotal % 10 == 0);
  }

  return isValid;
}


function getCityState(postalcode) {
	//no need in searching if it's blank
	if (postalcode != "") {
		$("tip_strCust_BillingCity").style.visibility = "visible";
		$("tip_strCust_BillingCityCopy").innerHTML = "Looking up the corresponding city and state for postal code '" + postalcode + "', please wait...";

		var url = '?'; //'?'+pars; //'<?=$_SERVER["PHP_SELF"]?>';
		var pars = 'action=ZIP_LOOKUP&postalcode=' + postalcode;

		var myAjax = new Ajax.Request( url, { method: 'post', parameters: pars, onComplete: cbShowZipSearchResponse });	
	
//		document.location= url+"?"+pars;	
	}
}

function updateShippingOptions() {

	if (!$("#divCourierOptions")) return;	// -- do nothing if the container for this does not exist(ie. on profile form, signup pages etc)

	//check to see if shipping rates and/or couriers should be updated if shipping address is completed
	if ($("#strCust_ShippingAddress1").val() != "" && $("#strCust_ShippingCity").val() != "") {
		if ($("#strCust_ShippingCountry").val() == 'US' && !$("#strCust_ShippingZip").val().match(/^[0-9]{5}([- /]?[0-9]{4})?$/)) {
			$("#divCourierOptions").html("Please enter a valid Shipping Zip Code");
		} else	if ($("#strCust_ShippingCountry").val() == 'US' && !$("#strCust_ShippingState")) {
			$("#divCourierOptions").html("Please enter a valid State");
		} else {
			getShippingOptions();
			if (window.fnOnShippingOptionsUpdate) {
				fnOnShippingOptionsUpdate();
			}
		}
	} else {
		// -- incomplete shipping
	}
}

function getShippingOptions() {
	if ($("#strCust_ShippingCountry").val() != "Select Country") {
		$("#divCourierOptions").html("<img src=\"images/indicator_medium.gif\" width=\"32\" height=\"32\" border=\"0\" alt=\"Retrieving Shipping Quotes\" />");
		$.post("?", 
			{
				action:               "GET_SHIPPING_OPTIONS",
				format:               "JSON",
				ship_street_address1: encodeURIComponent($("#strCust_ShippingAddress1").val()),
				ship_street_address2: encodeURIComponent($("#strCust_ShippingAddress2").val()),
				ship_city:            $("#strCust_ShippingCity").val(),
				ship_state:           $("#strCust_ShippingState").val(),
				ship_postcode:        $("#strCust_ShippingZip").val(),
				ship_country:         $("#strCust_ShippingCountry").val()
			},
			function(data) {alert(data)} // Put results into shipping 
		);
	} else {
		$("#strCust_ShippingCountry").focus();
	}
}

function fnCheckName(objField, intID, intSiteID){
	if(objField.value){
		var url = "ajax_checkname.php";
		var pars = "strName="+objField.name+"&strValue="+objField.value+"&intID="+intID+"&intSiteID="+intSiteID;

		var myAjax = new Ajax.Request( url, { method: 'post', parameters: pars, onComplete: cbCheckNameResponse });
	}
}

//sends request to NetBilling to see if the credit card will go through
function getCCVerification() {
	var url = '<?=$oSite->strURL?>/includes/checkout_da_functions.php';
	var pars = 'action=PROCESS_CC&cc=' + $("#ccNum").val() + '&billingName=' + $("#strCust_BillingFirstName").val() + ' ' + $("#strCust_BillingLastName").val() + '&expMonth=' + $("#intExpMonth").options[$("#intExpMonth").attr("selectedIndex")].val() + '&expYear=' + $("#intExpYear").options[$("#intExpYear").attr("selectedIndex")].val() + '&cid=' + $("#cid").val();
	var myAjax = new Ajax.Request( url, { method: 'post', parameters: pars, onComplete: cbShowCCVerificationResponse });	
}

function cbShowZipSearchResponse (response) {

	var s = new String(response.responseText);
	//alert(s);
	if (s.indexOf("NO_RECORDS_FOUND") >= 0) {

		$("#tip_strCust_BillingCityCopy").html("We couldn't find a city and state to match '" + $("#strCust_BillingZip").val() + "', please enter your city,state & country.");

	} else {

		//parse out put into vars
		q = new String(response.responseText).parseQuery();
		
		//set city value
		$("#strCust_BillingCity").val(q["city"]);
		if ($("#blnCust_ShippingSame").checked) {
			$("#strCust_ShippingCity").val(q["city"]);
		}
		
		//set state value 
		$("#strCust_BillingState").val(q["state"]);
		if ($("#blnCust_ShippingSame").checked) {
			$("#strCust_ShippingState").val(q["state"]);
		}
		
		//hide tool tip
		$("#tip_strCust_BillingCity").hide();
		$("#tip_strCust_BillingCityCopy").val('Your city is used only for billing verification. <i><a href="javascript:showPrivacyPolicy()">View our privacy policy</a></i>');
		
		//set focus on phone field
		$("#strCust_BillingPhone").focus();
	}

	updateShippingOptions();
}

function cbCheckNameResponse(response) {
	var s = new String(response.responseText);
	if(s > 0){
		$("#attrname^enError").style.display='block';	
		$("#attrname^enError").html("There is already a product with that name");
		$("#attrname^en").val("");
		$("#attrname^en").focus();
	}
}

function cbShowCCVerificationResponse(response) {
	var s = new String(response.responseText);
	alert(s);
}

function cbShowConfirmResponse (response) {
	var s = new String(response.responseText);
	$("#divConfirmContent").html(s);
}


//This function brings the billing fields over to the shipping fields when the checkbox is checked, also makes fields uneditable when checked
//This function is run when the checkbox is checked. 
function fnSameShip(strFieldPrefix) {
	strFP = strFieldPrefix;

	if ($("#blnCust_ShippingSame").checked) {

		$("#"+strFP+"_ShippingFirstName").val($("#"+strFP+"_BillingFirstName").val());
		$("#"+strFP+"_ShippingLastName").val($("#"+strFP+"_BillingLastName").val());
		$("#"+strFP+"_ShippingAddress1").val($("#"+strFP+"_BillingAddress1").val());
		$("#"+strFP+"_ShippingAddress2").val($("#"+strFP+"_BillingAddress2").val());
		$("#"+strFP+"_ShippingCity").val($("#"+strFP+"_BillingCity").val());

		$("#"+strFP+"_ShippingStateSelect").attr("selectedIndex") = $("#"+strFP+"_BillingStateSelect").attr("selectedIndex");

		$("#"+strFP+"_ShippingCAProvinceSelect").attr("selectedIndex") = $("#"+strFP+"_BillingCAProvinceSelect").attr("selectedIndex");

		$("#"+strFP+"_ShippingState").val($("#"+strFP+"_BillingState").val());
		$("#"+strFP+"_ShippingZip").val($("#"+strFP+"_BillingZip").val());
		//$("#"+strFP+"_ShippingCountry").attr("selectedIndex") = $("#"+strFP+"_BillingCountry").attr("selectedIndex");
		//now that country lists are different between shipping and billing population must be done by value rather than indes. There are more country options for billing than shipping
		arrSelectVals = getSelectedValues($("#"+strFP+"_BillingCountry"));
		selectOptions(arrSelectVals, $("#"+strFP+"_ShippingCountry"));

		$("#"+strFP+"_ShippingFirstName").attr("readOnly", true);
		$("#"+strFP+"_ShippingLastName").attr("readOnly", true);
		$("#"+strFP+"_ShippingAddress1").attr("readOnly", true);
		$("#"+strFP+"_ShippingAddress2").attr("readOnly", true);
		$("#"+strFP+"_ShippingCity").attr("readOnly", true);
		$("#"+strFP+"_ShippingState").attr("readOnly", true);
		$("#"+strFP+"_ShippingStateSelect").attr("disabled", true);
		$("#"+strFP+"_ShippingCAProvinceSelect").attr("disabled", true);
		$("#"+strFP+"_ShippingZip").attr("readOnly", true);
		$("#"+strFP+"_ShippingCountry").attr("readOnly", true);

	} else {

		$("#"+strFP+"_ShippingFirstName").attr("readOnly", false);
		$("#"+strFP+"_ShippingLastName").attr("readOnly", false);
		$("#"+strFP+"_ShippingAddress1").attr("readOnly", false);
		$("#"+strFP+"_ShippingAddress2").attr("readOnly", false);
		$("#"+strFP+"_ShippingCity").attr("readOnly", false);
		$("#"+strFP+"_ShippingState").attr("readOnly", false);
		$("#"+strFP+"_ShippingStateSelect").attr("disabled", false);
		//$("#"+strFP+"_ShippingCAProvinceSelect").attr("disabled", false);
		$("#"+strFP+"_ShippingZip").attr("readOnly", false);
		$("#"+strFP+"_ShippingCountry").attr("readOnly", false);

	}

	if(strFieldPrefix == "strCust"){
		fnShowHideState();
	}

}

//This function updates the corresponding shipping field if a billing field is checked
//and "Same as billing address" is checked
function updateShipping(o) {

	if ($("#blnCust_ShippingSame").checked) {
		//alert('source id: '+o.id+', dest id: '+o.id.replace("Billing", "Shipping"));

		strShipFieldID = o.id.replace("Billing", "Shipping");
		oShipField = $(strShipFieldID);

		if ( oShipField ) {
			oShipField.value = o.value;
		} else {
			alert('missing: '+strShipFieldID);
		}
	}
}

//Shows select or text field for state depending on country selection
// jquery conversion note: straight-converting css manipulation 
// instead of doing show()/hide() until testing is done 
function fnShowHideState(){
	var strBillingCountry = $("#strCust_BillingCountry").val();

	if(strBillingCountry == "US") {
		$("#strCust_BillingStateSelect").css("display", "block");
		$("#strCust_BillingState").val($("strCust_BillingStateSelect").val());
		$("#strCust_BillingState").css("display", "none");
		$("#strCust_BillingCAProvinceSelect").css("display", "none");
	}else if(strBillingCountry == "CA"){
		$("#strCust_BillingCAProvinceSelect").css("display", "block");
		$("#strCust_BillingState").val($("strCust_BillingCAProvinceSelect").val());
		$("#strCust_BillingState").css("display", "none");
		$("#strCust_BillingStateSelect").css("display", "none");
	}else{
		$("#strCust_BillingStateSelect").css("display", "none");
		$("#strCust_BillingCAProvinceSelect").css("display", "none");

		$("#strCust_BillingState").css("display", "block");

	}

	var strShippingCountry = $("#strCust_ShippingCountry").val();
// if ($("#testcheck").attr("checked") == true) {
	if(strShippingCountry == "US" ||($("blnCust_ShippingSame").attr("checked") == true && strBillingCountry == "US")){
		$("#strCust_ShippingStateSelect").css("display", "block");
		$("#strCust_ShippingState").val($("#strCust_ShippingStateSelect").val());
		$("#strCust_ShippingState").css("display", "none");
		$("#strCust_ShippingCAProvinceSelect").css("display", "none");
	}else if(strShippingCountry == "CA" ||($("#blnCust_ShippingSame").attr("checked") == true && strBillingCountry == "CA")){
		$("#strCust_ShippingCAProvinceSelect").css("display", "block");
		$("#strCust_ShippingState").val($("#strCust_ShippingCAProvinceSelect").val());
		$("#strCust_ShippingState").css("display", "none");
		$("#strCust_ShippingStateSelect").css("display", "none");
	}else{
		$("#strCust_ShippingStateSelect").css("display", "none");
		$("#strCust_ShippingState").css("display", "block");
		$("#strCust_ShippingCAProvinceSelect").css("display", "none");
	}

}


function toggleConfirm() {

	//scroll to top of window
	window.scroll(0,0);
	
	if (!$("#divConfirm")) {
		return false;
	}

	if ($("#divConfirm").css("visibility", "hidden")) {

		// -- make sure dupe email check is performed before continuing any further
		if ( !blnEmailCheck && $("#strCust_Email") && $("#strCust_Email").val() ) {
			checkEmail($("#strCust_Email").val(), cbCheckEmail_Checkout);
			return false;
		}


		arrError = validateCheckout();

		if (arrError.length == 0) {
			
			if ( window.fnOnReviewOrder ) {
				fnOnReviewOrder();
			}

			getConfirm();

			trackPageView("/ga_goal_paymentmethod.php");

			$("#divIndicator").css("visibility", "hidden");
			$("#divConfirm").css("visibility", "visible");
			$("#frmCheckout :input").each(function (i, e) {
				$(e).attr("disabled", "true");
			});
			hideSelectLists();

		} else {
	
			hideSelectLists();
			var strError = "<ul><li>"+arrError.join("<li>")+"</ul>";	
			$("#strMissingFieldsMessage").html(strError);
			$("#divMissingFieldsForm").show();

			// failed validation
		}

	} else {
		$("#divConfirmContent").html("");
		$("#divConfirm").css("visibility", "hidden");
		$("#frmCheckout :input").each(function (i, e) {
			$(e).attr("disabled", "false");
		});
		showSelectLists();
	}

}

function hideSelectLists(){
	$("#strCust_BillingStateSelect").css("visibility", "hidden");
	$("#strCust_BillingCountry").css("visibility", "hidden");
	$("#strCust_ShippingStateSelect").css("visibility", "hidden");
	$("#strCust_ShippingCountry").css("visibility", "hidden");
	$("#strCust_CardType").css("visibility", "hidden");
	$("#strCust_CardExpireMonth").css("visibility", "hidden");
	$("#strCust_CardExpireYear").css("visibility", "hidden");
}

function showSelectLists(){
	$("#strCust_BillingStateSelect").css("visibility", "");
	$("#strCust_BillingCountry").css("visibility", "");
	$("#strCust_ShippingStateSelect").css("visibility", "");
	$("#strCust_ShippingCountry").css("visibility", "");
	$("#strCust_CardType").css("visibility", "");
	$("#strCust_CardExpireMonth").css("visibility", "");
	$("#strCust_CardExpireYear").css("visibility", "");
}

function activateForm(){
	$("#frmCheckout :input").each(function (i, e) {
		$(e).attr("disabled", "false");
	});
}


// -- form validation functions
var aryRequiredFields = Array();

function addRequiredField(strFieldName) {

	objLabel = $("#"+strFieldName+"Label");

	if ( !objLabel ) {
	
		//commented out because there's no need to display
		//this to site visitors
		
		// -- do not comment this out;  if you see this msg you have an error in your form.
		alert("Label not found for '"+strFieldName+"'.");
		
		return;
	}

	strFieldLabel = $("#"+strFieldName+"Label").innerHTML.replace(":","");
	
	aryRequiredFields[aryRequiredFields.length] = strFieldName+"|"+strFieldLabel;
}

function validateCheckout() {

	var blnValidate = true;

	aryRequiredFields = Array();
	arrError = new Array();

	addRequiredField("strCust_BillingFirstName");
	addRequiredField("strCust_BillingLastName");
	addRequiredField("strCust_BillingAddress1");
	addRequiredField("strCust_BillingCity");

	if ( $("#strCust_BillingCountry").val().match(/US|CA/) ) {
		addRequiredField("strCust_BillingState");
		addRequiredField("strCust_BillingZip");
	}

	addRequiredField("strCust_BillingCountry");
	addRequiredField("strCust_ShippingFirstName");
	addRequiredField("strCust_ShippingLastName");
	addRequiredField("strCust_ShippingAddress1");
	addRequiredField("strCust_ShippingCity");
	addRequiredField("strCust_ShippingCountry");

	if ( $("#strCust_ShippingCountry").val().match(/US|CA/) ) {
		addRequiredField("strCust_ShippingState");
		addRequiredField("strCust_ShippingZip");
	}
	
	if ( !$("#strCust_ShippingCountry").val().match(/US/) ) {
		// -- phone is required for non-us customers
		addRequiredField("strCust_BillingPhone");
	}

	if ( $("#strCust_Email") ) {
		// -- email is required for non-logged in users
		addRequiredField("strCust_Email");
		
		if ( $("#strCust_Email").val() && !blnValidEmailSyntax ) {
			arrError.push("Email: The address you entered is not valid");
		}

	}

	if ($("#CreatePassword") && $("#CreatePassword").val() != "" ) {

		if ( blnExists ) {
			arrError.push("Email: Can not create user account with this email. The address you entered is already in use.");
		}

		addRequiredField("strCust_Email");
		addRequiredField("CreatePassword2");

	}
	

	if ( $("#over18verified_cb") ) {
		// -- over18 checkbox is required for non-logged in users
		addRequiredField("over18verified_cb");
	}

	addRequiredField("shippingMeth");

	if ( $("#PayTypeOC").attr("checked") ) {

		addRequiredField("strCust_CheckBankRoutingNum");
		addRequiredField("strCust_CheckAccountNum");
		addRequiredField("strCust_CheckNumber");

	} else if ( $("#PayTypeCC").attr("checked") ) {

		addRequiredField("strCust_CardType");
		addRequiredField("intCust_CardNumber");
		addRequiredField("strCust_CardExpireDate");
		 
		if ( !$("#blnCust_CardSecurityCodeUnavail").attr("checked") ) {
			addRequiredField("intCust_CardSecurityCode");
		}
		
	} else if ( $("#PayTypeMO").attr("checked") ) {

		// -- no required fields for this payment type

	} else if ( $("#PayTypeBT").attr("checked") ) {

		// -- no required fields for this payment type

	} else if ( $("#PayTypeOP").attr("checked") ) {
        // -- no required fields for this payment type

    }

	
	/* jQuery conversion - stuff in this loop should be looked at */
	for(var i=0; i < aryRequiredFields.length; i++){

		strFieldName = aryRequiredFields[i].split('|')[0];
		strFieldLabel = aryRequiredFields[i].split('|')[1];

		objField = $("#frmCheckout").elements[strFieldName];

		if ( objField ) {

			if ( objField.type == "select-one" ) {
		
				strValue = objField.options[objField.selectedIndex].value;
		
			} else if ( objField.length > 0 ) {
			
				aryOptions = $A(objField);
				var opt = aryOptions.find( function(objOption){
					return (objOption.checked == true);
				});
				
				strValue = opt?opt.value:"";
		
			} else if ( objField.type.match(/checkbox|radio/) ) {
			
				if ( objField.checked ) {
					strValue = objField.value;
				} else {
					strValue = "";
				}

			} else {

				strValue = objField.value;

			}
			

		} else {
			strValue = "";
		}

		if ( !strValue ) {
			
			//Commenting out the following line because it's producing errors and is not necessary and 
			//we honestly can't find a solution right now 12/20/2007 9:46 ...David Ashley
			//if ( objField && objField.id ) objField.focus();
			
			blnValidate = false;

			arrError.push(strFieldLabel);

			// -- disabled for now (jp, 5/16)
			//$(strFieldName+"Label").className = "cssCOLabelRequired";
			//$(strFieldName).className = "cssCOFieldRequired";

		} else {

			//$(strFieldName+"Label").className = "cssCOLabel";
			//$(strFieldName).className = "cssCOInput";

		}

	}

	return arrError;
}

function showCheckoutError(strMessage, strHeading) {
	
	if ( strHeading != undefined ) {
		$("#divCheckoutErrorHeading").html(strHeading);
	}

	$("#divCheckoutErrorMsg").html(strMessage);
	$("#divCheckoutError").show();

}

function constructConfirmPars() {

	var pars = '&strCust_BillingFirstName='  + encodeURIComponent($("#strCust_BillingFirstName").val()) + 
          '&strCust_BillingLastName='   + encodeURIComponent($("#strCust_BillingLastName").val())   + 
          '&strCust_BillingAddress1='   + encodeURIComponent($("#strCust_BillingAddress1").val())   + 
          '&strCust_BillingAddress2='   + encodeURIComponent($("#strCust_BillingAddress2").val())   + 
          '&strCust_BillingCity='       + encodeURIComponent($("#strCust_BillingCity").val())       + 
          '&strCust_BillingState='      + encodeURIComponent($("#strCust_BillingState").val())      + 
          '&strCust_BillingZip='        + encodeURIComponent($("#strCust_BillingZip").val())        + 
          '&strCust_BillingCountry='    + encodeURIComponent($("#strCust_BillingCountry").val())    + 
          '&strCust_ShippingFirstName=' + encodeURIComponent($("#strCust_ShippingFirstName").val()) +
          '&strCust_ShippingLastName='  + encodeURIComponent($("#strCust_ShippingLastName").val())  +
          '&strCust_ShippingAddress1='  + encodeURIComponent($("#strCust_ShippingAddress1").val())  + 
          '&strCust_ShippingAddress2='  + encodeURIComponent($("#strCust_ShippingAddress2").val())  + 
          '&strCust_ShippingCity='      + encodeURIComponent($("#strCust_ShippingCity").val())      + 
          '&strCust_ShippingState='     + encodeURIComponent($("#strCust_ShippingState").val())     + 
          '&strCust_ShippingZip='       + encodeURIComponent($("#strCust_ShippingZip").val())       + 
          '&strCust_ShippingCountry='   + encodeURIComponent($("#strCust_ShippingCountry").val()); 

	pars += '&shippingMeth='	+ getCheckedValue($("#frmCheckout").shippingMeth); 

	pars += '&intCust_PaymentType='	+ getCheckedValue($("#frmCheckout").intCust_PaymentType); 

	if ($("#PayTypeCC").val()) {

		pars += '&strCust_CardType='		+ escape($("#strCust_CardType").val())       + 
            '&intCust_CardNumber='			+ escape($("#intCust_CardNumber").val())     + 
            '&strCust_CardExpireDate='		+ escape($("#strCust_CardExpireDate").val()) + 
            '&intCust_CardSecurityCode='	+ escape($("#intCust_CardSecurityCode").val());

   } else if ($("#PayTypeOC").val()) {

		pars += '&strCust_CheckBankRoutingNum='	+ escape($("#strCust_CheckBankRoutingNum").val()) + 
            '&strCust_CheckAccountNum='			+ escape($("#strCust_CheckAccountNum").val()) + 
            '&strCust_CheckNumber='				+ escape($("#strCust_CheckNumber").val());
    }

	pars += '&intCouponCode=' + encodeURIComponent($("#intCouponCode").val()) +
			'&curOrder_FleshBucks=' + escape($("#curOrder_FleshBucks").val()) +
			'&blnApplyFleshBucks=' + escape($("#blnApplyFleshBucks").val()) +
			'&strPurchaseOrder=' + escape($("#strPurchaseOrder").val()) +
			'&strComments=' + encodeURIComponent($("#strComments").val());

	return pars;
	
}

function getConfirm() {
	var url = "?";
	var pars = 'action=GET_CONFIRM_DIALOG&' + constructConfirmPars();
	makeRequest(url, "post", pars, cbShowConfirmResponse)

}

//This function makes the focus jump to postal code if there's nothing already in the city field
function Address2Blur() {
	if ($("#strCust_BillingCity").val() == "") {
		$("#strCust_BillingZip").focus();
	} else {
		$("#strCust_BillingCity").focus();
	}
}

//this function toggles the shipping method 
function setShippingMethod(o) {

	shippingMethodSelected = o.value;

	trackPageView("/ga_goal_shipping.php");
}


/**************************************************************************
PAYMENT FIELDS FUNCTIONS

These functions handle interaction with the billing fields.  Most of these 
faciliated hiding or showing fields and or tip bubbles.
***************************************************************************/

function switchPaymentMethod(method) {

	//hide all
	$("#ccForm").hide();
	$("#ocForm").hide();
	$("#moForm").hide();
	$("#ppForm").hide();
	$("#btForm").hide();
	$("#opForm").hide();
	
	aryforms = ["ccForm", "ocForm", "moForm","ppForm","btForm", "opForm"];
	Element.show(aryforms[method-1]);

}


//This function updates the image and the instructions that show beneath the payment fields
function updateCodeInstructions(cardType) {

	switch (cardType) {
		case "AE" :
			$("#amexCodeInstructions").show();
			$("#visamcCodeInstructions").hide();
			$("#cardImage").css("top", "0px");
			break;

		default:
			$("#amexCodeInstructions").hide();
			$("#visamcCodeInstructions").show();
			$("#cardImage").css("top", "-100px");
			break;

	}

}


function submitOrder() {

	$("#cellSubmitOrder").html("<img src=\"images/indicator_medium.gif\" width=\"32\" height=\"32\" border=\"0\" alt=\"Retrieving Shipping Quotes\" />");
	$("#cellUpdateOrder").html("");
	activateForm();	

	$("#frmCheckout").submit();

}

//shows state as mandatory field if country is US

function mandatoryState(){
	if($("strCust_BillingCountry").value == "US"){
//		$("spanStateRequired").style.visibility = "visible";
	}else{
//		$("spanStateRequired").style.visibility = "hidden";
	}

}


function getCheckedValue(radioObj) {
	if(!radioObj)
		return "";
	var radioLength = radioObj.length;
	if(radioLength == undefined)
		if(radioObj.checked)
			return radioObj.value;
		else
			return "";
	for(var i = 0; i < radioLength; i++) {
		if(radioObj[i].checked) {
			return radioObj[i].value;
		}
	}
	return "";
}

// calculate the ASCII code of the given character
function CalcKeyCode(aChar) {
  var character = aChar.substring(0,1);
  var code = aChar.charCodeAt(0);
  return code;
}

function checkNumber(val) {
  var strPass = val.value;
  var strLength = strPass.length;
  var lchar = val.value.charAt((strLength) - 1);
  var cCode = CalcKeyCode(lchar);

  /* Check if the keyed in character is a number
     do you want alphabetic UPPERCASE only ?
     or lower case only just check their respective
     codes and replace the 48 and 57 */

  if (cCode < 48 || cCode > 57 ) {
    var myNumber = val.value.substring(0, (strLength) - 1);
    val.value = myNumber;
  }
  return false;
}

function BillingTypes(obj){
	if(obj.value == "IL"){
		$("#OCcell").hide();
		$("#BTcell").show();
	}else{
		$("#OCcell").show();
		$("#BTcell").hide();
	}
}

// -- selects first closest match to strValue
function selectFirstMatch(objField, strValue) {

	for ( i=0; i<objField.length; i++) {
	
		if ( objField.options[i].text.match(strValue) ) {

			objField.selectedIndex = i;
			return;
		}

	}

}

// -- Google Analytics functions
function trackPageView(strPage) {

	if ( window.pageTracker ) {

		pageTracker._trackPageview(strPage);

	} else if ( window.urchinTracker ) {
		
		urchinTracker(strPage);
	}

}

// ================ AJAX functions =================

function makeRequest (strURL, strType, strParams, fnCallback, blnEvalJS) {
	// deprecating blnEvalJS.  that should go in the callback function if anything.
	$.ajax({
		url: strURL,
		type: strType,
		data: strParams,
		success: fnCallback
	});
}

// NOTE: evalScripts/evalJS options will only work if the response contains just JS with no <script> tags.  (JP 8/31/09)
/*
function makeRequest(strURL, strType, strParams, fnCallback, blnEvalJS) {

	if ( blnEvalJS == undefined ) {
		blnEvalJS = true;
	}

	var myAjax = new Ajax.Request(
		strURL, 
		{
			method: strType, 
			evalScripts: blnEvalJS,
			evalJS: blnEvalJS,
			parameters: strParams?strParams:"", 
			onComplete: fnCallback?fnCallback:callBack,
			onFailure: onFailure
		});
}
*/

function postForm(objForm, strURL, fnCallback, strTargetID, blnEvalJS) {

	if ( blnEvalJS == undefined ) {
		blnEvalJS = true;
	}
	
	strQueryString = "";
	for(i=0;i<objForm.elements.length;i++) {

		// fix to default the type to text
		if (!objForm.elements[i].type)
			objForm.elements[i].type = 'text';

		// -- skip unchecked checkboxes
		if ( objForm.elements[i].type.match(/checkbox|radio/) && objForm.elements[i].checked == false) {
			continue;
		} else if ( objForm.elements[i].type == "select-multiple" ) { 
			objSel = objForm.elements[i];
			for(x=0;x<objSel.options.length;x++) {
				if (objSel.options[x].selected) {
					strQueryString += strQueryString?"&":"";
					strQueryString += objForm.elements[i].name + "=" + escape(objSel.options[x].value);
				}
			}

		} else {

			strQueryString += strQueryString?"&":"";
			strQueryString += objForm.elements[i].name + "=" + escape(objForm.elements[i].value);
		}
	}

	if ( strTargetID ) {
		makeHTMLRequest(
			strURL?strURL:objForm.attr("action"), 
			objForm.method, 
			strQueryString, 
			fnCallback?fnCallback:null, 
			strTargetID,
			blnEvalJS);
	} else {
//		makeRequest(strURL, objForm.method, strQueryString, callback?callback:null);
//			alert(strQueryString);

		makeHTMLRequest(
			strURL?strURL:objForm.attr("action"),
			false,
			strQueryString?strQueryString:"",
			fnCallback?fnCallback:callBack,
			false,
			false
		);
	}
}

// is this a generic callback?  turning off for jquery conversion @jalley
function callBack(objRequest) {
	// objRequest.responseText.evalScripts();
	return true;
}

// potentially antiquated: strType, blnEvalJS
function makeHTMLRequest(strURL, strType, strParams, fnCallback, strDestDivID, blnEvalJS) {
	$.post(strURL, strParams, function (ret) {
		if (strDestDivID) $('#' + strDestDivID).html(ret);

		if (fnCallback) fnCallback(ret);
		else callBack(ret);
	});
}

function onFailure(objRequest) {
	alert("Http Request FAILED");
}

// -- this function needs to be moved out of this library (JP 8/31/09)
function postPoll (strPollID, strSuccess)
{
	postForm(
		$('#'+strPollID),
		$('#'+strPollID).attr('action'),
		function () {
			$('#'+strPollID).replaceWith(strSuccess ? strSuccess : 'Thanks for voting!');
		}
	);

	return false; // prevent default action on forms
}


// =========================================


/**
* Insert a tab at the current text position in a textarea
* Jan Dittmer, jdittmer@ppp0.net, 2005-05-28
* Inspired by http://www.forum4designers.com/archive22-2004-9-127735.html
* Tested on: 
*   Mozilla Firefox 1.0.3 (Linux)
*   Mozilla 1.7.8 (Linux)
*   Epiphany 1.4.8 (Linux)
*   Internet Explorer 6.0 (Linux)
* Does not work in: 
*   Konqueror (no tab inserted, but focus stays)
*/
function insertTab(event,obj) {
    var tabKeyCode = 9;
    if (event.which) // mozilla
        var keycode = event.which;
    else // ie
        var keycode = event.keyCode;
    if (keycode == tabKeyCode) {
        if (event.type == "keydown") {
            if (obj.setSelectionRange) {
                // mozilla
                var s = obj.selectionStart;
                var e = obj.selectionEnd;
                var startPos = obj.selectionStart;
                
                obj.value = obj.value.substring(0, s) + 
                    "\t" + obj.value.substr(e);
                obj.focus();
                obj.setSelectionRange(s + 1, s + 1);
                
				obj.selectionStart = startPos+1;
				obj.selectionEnd = startPos+1;

            } else if (obj.createTextRange) {
                // ie
                document.selection.createRange().text="\t"
                obj.onblur = function() { this.focus(); this.onblur = null; };
            } else {
                // unsupported browsers
            }
        }
        if (event.returnValue) // ie ?
            event.returnValue = false;
        if (event.preventDefault) // dom
            event.preventDefault();
        return false; // should work in all browsers
    }
    return true;
}

// === cookie functions lifted from:
// http://techpatterns.com/downloads/javascript_cookies.php
function setCookie( name, value, expires, path, domain, secure ) {

	// set time, it's in milliseconds
	var today = new Date();
	today.setTime( today.getTime() );
	
	/*
	if the expires variable is set, make the correct 
	expires time, the current script below will set 
	it for x number of days, to make it for hours, 
	delete * 24, for minutes, delete * 60 * 24
	*/
	if ( expires )
	{
	expires = expires * 1000 * 60 * 60 * 24;
	}
	var expires_date = new Date( today.getTime() + (expires) );
	
	document.cookie = name + "=" +escape( value ) +
	( ( expires ) ? ";expires=" + expires_date.toGMTString() : "" ) + 
	( ( path ) ? ";path=" + path : "" ) + 
	( ( domain ) ? ";domain=" + domain : "" ) +
	( ( secure ) ? ";secure" : "" );

}

function getCookie( check_name ) {

	// first we'll split this cookie up into name/value pairs
	// note: document.cookie only returns name=value, not the other components
	var a_all_cookies = document.cookie.split( ';' );
	var a_temp_cookie = '';
	var cookie_name = '';
	var cookie_value = '';
	var b_cookie_found = false; // set boolean t/f default f
	
	for ( i = 0; i < a_all_cookies.length; i++ )
	{
		// now we'll split apart each name=value pair
		a_temp_cookie = a_all_cookies[i].split( '=' );
		
		
		// and trim left/right whitespace while we're at it
		cookie_name = a_temp_cookie[0].replace(/^\s+|\s+$/g, '');
	
		// if the extracted name matches passed check_name
		if ( cookie_name == check_name )
		{
			b_cookie_found = true;
			// we need to handle case where cookie has no value but exists (no = sign, that is):
			if ( a_temp_cookie.length > 1 )
			{
				cookie_value = unescape( a_temp_cookie[1].replace(/^\s+|\s+$/g, '') );
			}
			// note that in cases where cookie is initialized but no value, null is returned
			return cookie_value;
			break;
		}
		a_temp_cookie = null;
		cookie_name = '';
	}
	if ( !b_cookie_found )
	{
		return null;
	}
}

function deleteCookie( name, path, domain ) {

	if ( Get_Cookie( name ) ) 
		document.cookie = name + "=" +
			( ( path ) ? ";path=" + path : "") +
			( ( domain ) ? ";domain=" + domain : "" ) +
			";expires=Thu, 01-Jan-1970 00:00:01 GMT";
}

// ====================

function validateFleshBuck(objFleshBucks, intTotalFleshBucks){
	//alert(intTotalFleshBucks+" here "+objFleshBucks.value);
	var intFleshBucks = objFleshBucks.value;
	intFleshBucks = intFleshBucks.replace(/[^0-9]/g, ''); 
	if(objFleshBucks.value > intTotalFleshBucks){
		intFleshBucks = intTotalFleshBucks;
	}
	objFleshBucks.value = intFleshBucks;
}


/*
Function: debug
Contributors: Jordan Phillips
Description: write to firebug console
Parameters:

strMessage - test to send to console

Returns: None
*/
function debug(strMessage) {
	if (typeof console !== 'undefined') console.debug(strMessage);
}

function printStackTrace() {

	if (typeof console === 'undefined') return;

	var callstack = [];
	var isCallstackPopulated = false;
	try {
	  i.dont.exist+=0; //doesn't exist- that's the point
	} catch(e) {
	  if (e.stack) { //Firefox
		var lines = e.stack.split("\n");
		for (var i=0, len=lines.length; i<len; i++) {
		  if (lines[i].match(/^\s*[A-Za-z0-9\-_\$]+\(/)) {
			callstack.push(lines[i]);
		  }
		}
		//Remove call to printStackTrace()
		callstack.shift();
		isCallstackPopulated = true;
	  }
	  else if (window.opera && e.message) { //Opera
		var lines = e.message.split("\n");
		for (var i=0, len=lines.length; i<len; i++) {
		  if (lines[i].match(/^\s*[A-Za-z0-9\-_\$]+\(/)) {
			var entry = lines[i];
			//Append next line also since it has the file info
			if (lines[i+1]) {
			  entry += " at " + lines[i+1];
			  i++;
			}
			callstack.push(entry);
		  }
		}
		//Remove call to printStackTrace()
		callstack.shift();
		isCallstackPopulated = true;
	  }
	}
	
	if (!isCallstackPopulated) { //IE and Safari
	  var currentFunction = arguments.callee.caller;
	  while (currentFunction) {
		var fn = currentFunction.toString();
		var fname = fn.substring(fn.indexOf("function") + 8, fn.indexOf("(")) || "anonymous";
		callstack.push(fname);
		currentFunction = currentFunction.caller;
	  }
	}

	console.debug( "=== BEGIN CALLSTACK ===" );
	for ( i=0; i<callstack.length; i++ ) {
		console.debug(callstack[i]);
	}
	console.debug ( "=== END CALLSTACK ===" );

}

/* Cross browser JSON parsing */
function parse_json(data) {
	var JSON = JSON || {};
	JSON.parse = JSON.parse || function (data) {
		if (data === "") data = '""';
		eval('var p=' + data + ';');
		return p;
	}
	retval = JSON.parse(data);
	return retval;
}

