// Miscellaneous Javascript Functions
function getElementsByClass(node,searchClass,tag) {
    var classElements = new Array();
    var els = node.getElementsByTagName(tag);
    var elsLen = els.length;
    var pattern = new RegExp("\\b"+searchClass+"\\b");
    for (var i = 0; i < elsLen; i++) {
        if ( pattern.test(els[i].className) ) {
            classElements[classElements.length] = els[i];
        }
    }
    return classElements;
}

function openPopupWindow(formFieldName, pageName) {
    var theSelect = document.getElementById(formFieldName);
    var thePage = document.getElementById(pageName).value;
    if (theSelect.options[theSelect.selectedIndex].value != '') {
        thePage += theSelect.options[theSelect.selectedIndex].value;
        var w = window.open(thePage,formFieldName,'width=700,height=500,scrollbars=1,resizable=yes,toolbar=no,menubar=yes'); 
        w.focus(); 
    }
    return false;
}

function CheckTextAreaLength(pobjChanged, pintMaxLength) {
    // First check for NaN
    var lintLength = Math.abs(pobjChanged.value.length);

    if(lintLength > pintMaxLength)
    {
        alert('Too many characters. Maximum allowable length is ' + pintMaxLength + ' characters.');
        pobjChanged.focus();
        pobjChanged.select();
        return false;
    }
    return true;
}

function textCounter(field, maxlimit) {
    var textArea = document.getElementById(field);
    var countField = document.getElementById(field + 'Count');
    if (textArea.value.length > maxlimit) {
        alert('Maximum character count of ' + maxlimit + ' exceeded. Truncating input.');
        textArea.value = textArea.value.substring(0, maxlimit);
    }
    countField.firstChild.nodeValue = "Max " + maxlimit + " Characters, " + (maxlimit - textArea.value.length) + " Remaining";
}

function setCountFields(field) {
    var countElement = document.getElementById(field);
    var dataElement = window.opener.document.getElementById(field);
    countElement.firstChild.nodeValue = dataElement.firstChild.nodeValue;
}

function ValidateDecimal(pobjField, pstrFieldDesc) {
    // Check for NaN
    lobjChanged = eval(pobjField);
    
    // Remove ',' so numbers will validate
    re = new RegExp(',', 'g');
    lobjChanged.value = lobjChanged.value.replace(re, '');
    
    if (isNaN(lobjChanged.value)) {
        alert(pstrFieldDesc + ' may contain numbers only.');
        lobjChanged.focus();
        lobjChanged.select();
        return false;
    }
    return true;
}

function ValidateInteger(pobjField, pstrFieldDesc) {
    // First check for NaN
    lobjChanged = eval(pobjField);
    if (isNaN(lobjChanged.value) || lobjChanged.value.indexOf(".") > -1) {
        alert(pstrFieldDesc + ' may contain integers only.');
        lobjChanged.focus();
        lobjChanged.select();
        return false;
    }
    return true;
}

/************************************************************
Name:		TrimString
Purpose:	To trim off any leading or trailing spaces
Input:		str - String that needs to be trimmed
Output:		Returns the string without leading/trailing spaces
************************************************************/      
function TrimString(str) {

    var whitespace = new String(" \t\n\r");
    var s = new String(str);
	
    if (whitespace.indexOf(s.charAt(0)) != -1) {
        // We have a string with leading blank(s)...
        var j=0, i = s.length;

        // Iterate from the far left of string until we
        // don't have any more whitespace...
        while (j < i && whitespace.indexOf(s.charAt(j)) != -1)
            j++;

        // Get the substring from the first non-whitespace
        // character to the end of the string...
        s = s.substring(j, i);
    }
    
    if (whitespace.indexOf(s.charAt(s.length-1)) != -1) {
        // We have a string with trailing blank(s)...
        var k = s.length - 1;       // Get length of string

        // Iterate from the far right of string until we
        // don't have any more whitespace...
        while (k >= 0 && whitespace.indexOf(s.charAt(k)) != -1)
            k--;

        // Get the substring from the front of the string to
        // where the last non-whitespace character is...
        s = s.substring(0, k+1);
    }

	return s;    
}

function confirmDelete(pstrMessage) {
   var varOK;
   varOK = window.confirm(pstrMessage);
   if (!varOK)
	  return false;
   else
	  return true;
}

function confirmDeleteLink(pstrMessage, pstrLink) {
    var varOK;
    varOK = window.confirm(pstrMessage);
    if (!varOK)
        return false;
    else
        window.location.href = pstrLink;
        return false;
}

function sessionExpireWarning() {
	// Display a warning that the session is about to expire
    var strFormattedTime = new String();
    strFormattedTime = getClientTime();
    alert('WARNING:\nYour user session on the web server will expire shortly due to inactivity.\nPlease save any pending data changes now or click any link to continue your session.\n(Issued at ' + strFormattedTime + ')');
}

function getClientTime() {
    var Digital = new Date();
    var hours = Digital.getHours();
    var minutes = Digital.getMinutes();
    var dn = "AM";
    var strFormattedTime = new String("");
    
    if (hours >= 12) { dn = "PM"; }
    if (hours > 12) { hours = hours - 12; }
    if (hours == 0) { hours = 12; }
    if (minutes <= 9) { minutes = "0" + minutes; }
    strFormattedTime = hours + ':' + minutes + ' ' + dn;
    return strFormattedTime;
}

/* This script is Copyright (c) Paul McFedries and 
Logophilia Limited (http://www.mcfedries.com/).
Permission is granted to use this script as long as 
this Copyright notice remains in place.*/
function RoundDecimals(original_number, decimals) {
    var result1 = original_number * Math.pow(10, decimals)
    var result2 = Math.round(result1)
    var result3 = result2 / Math.pow(10, decimals)
    return PadWithZeros(result3, decimals)
}

/* This script is Copyright (c) Paul McFedries and 
Logophilia Limited (http://www.mcfedries.com/).
Permission is granted to use this script as long as 
this Copyright notice remains in place.*/
function PadWithZeros(rounded_value, decimal_places) {
    // Convert the number to a string
    var value_string = rounded_value.toString()
    // Locate the decimal point
    var decimal_location = value_string.indexOf(".")

    // Is there a decimal point?
    if (decimal_location == -1) {
        // If no, then all decimal places will be padded with 0s
        decimal_part_length = 0
        
        // If decimal_places is greater than zero, tack on a decimal point
        value_string += decimal_places > 0 ? "." : ""
    }
    else {
        // If yes, then only the extra decimal places will be padded with 0s
        decimal_part_length = value_string.length - decimal_location - 1
    }
    
    // Calculate the number of decimal places that need to be padded with 0s
    var pad_total = decimal_places - decimal_part_length
    
    if (pad_total > 0) {
        // Pad the string with 0s
        for (var counter = 1; counter <= pad_total; counter++) 
            value_string += "0"
        }
    return value_string
}

function getArrayOfTextAreaFieldsOnPage() {
	var fieldsToCheckName = new Array();
   	var index = -1;
	var form;
	
	// Scan for all TextAreas and TextBoxes
	for (var i = 0; i < document.forms.length; i++) {
		form = document.forms[i];
		for (var j = 0; j < form.elements.length; j++) {
			// If the document element is a textArea or long text box ...
			if (form.elements[j].type == 'textarea') {
				// ... then add it to the Array
				index ++;
				fieldsToCheckName[index] = 'document.' + form.name + '.' + form.elements[j].name;
			}
		}
	}
	return fieldsToCheckName;
}

function disableAllElementsOnForm(formId) {
	var form = document.getElementById(formId);
	// Scan for all Elements on FORM
	for (var i = 0; i < form.elements.length; i++) {
	    form.elements[i].disabled = true;
	}
}

function enableAllElementsOnForm(formId) {
	var form = document.getElementById(formId);
	// Scan for all Elements on FORM
	for (var i = 0; i < form.elements.length; i++) {
	    form.elements[i].disabled = false;
	}
}

function showContent(tagId) {
	document.getElementById(tagId).style.display=''; 
}

function hideContent(tagId) {
	document.getElementById(tagId).style.display='none'; 
}

/**
 * Set focus to specified field. If specified field not found, set focus to the first available field of 
 * the specified form. If the specified form is not found, default to setDefaultFocus()
 *
 * @param fieldId The id of the field to focus on.
 * @param formId The id of the form to focus on if the field could not be found.
 */
function setFocus(fieldId, formId) {
    var i = 0;
    
    //First attempt to focus on the field 
    var fieldObj = fieldId ? document.getElementById(fieldId) : null;
    if (fieldObj) {
        fieldObj.focus();
        return;
    }
    
    //Failing that, try the form
    var formObj = formId ? document.getElementById(formId) : null;
    if (formObj) {
        while (i < formObj.length) {
            if (formObj.elements[i].type != null) {
                if (formObj.elements[i].type != 'hidden' && formObj.elements[i].disabled != true) {
                    formObj.elements[i].focus();
                    return;
                }
            }
            i++;
        }
    } 
    
    //Fall through to use the default focus
    setDefaultFocus();
}

/**
 * Attempts to set the focus to the first select input field on the first form of the page.  
 * The google search form is ignored.
 */
function setDefaultFocus() {
    var f = 0;
    var i = 0;
    while (f < document.forms.length) {
        var formObj = document.forms[f];
        if (formObj.name.toLowerCase() != 'frmgooglesearch') {
            while (i < formObj.length) {
                if (formObj.elements[i].type != 'hidden' && formObj.elements[i].disabled != true) {
                    formObj.elements[i].focus();
                    return;
                }
                i++;
            }
        }
        f++;
    }
}


/**
 * Changes the styling on a section of content to display it as enabled or disabled,
 * depending on the parameters
 *   elementId 			The id of the element to enable
 *   enableFormFields 	true/false setting if the enabling should also be applied to contained 
 *  					form elements.  Defaults to false.
 */
function enableContent(elementId, enable, enableFormFields) {
	enable = (enable == undefined) ? true : enable;
	enableFormFields = (enableFormFields == undefined) ? true : enableFormFields;
	var element = document.getElementById(elementId);
	if (enable) {
		removeClassName(element, 'Disabled');
	} else {
		appendClassName(element, 'Disabled');
	}
	enableFormElements(element, enable);
}

/**
 * Enables or disabled all of the form fields that are descendents of the 
 * element.
 *   element 	The element to enable the fields in.
 *   enable 	true/false if the form elements should be enabled.
 */
function enableFormElements(element, enable) {
	for (var i = 0; i < element.childNodes.length; i++) {
		var childElement = element.childNodes[i];
		if ((childElement.tagName == 'INPUT') || (childElement.tagName == 'SELECT') || (childElement.tagName == 'TEXTAREA')) {
			childElement.disabled = !enable;
		} else {
			enableFormElements(childElement, enable);
		}
	}
}
/**
 * The appendClassName/removeClassName methods should be used instead of this
 * method since they allow multiple classes to be assigned to an element.  
 *
 * This method is maintained for backwards compatibility with existing code.
 */
function changeClass(tagId, newClass) {
	document.getElementById(tagId).className=newClass; 
}

function clearNameGuidFields(nameField, guidField) {
    document.getElementById(guidField).value = '';
    document.getElementById(nameField).value = '';
}

function toggleVisibility(searchClass) {
    var el = getElementsByClass(document,searchClass,'*');
    //alert(el.length);
    var pattern = new RegExp("\\bVisibleContent\\b");
    for (var i = 0; i < el.length; i++) {
        if ( pattern.test(el[i].className) ) {
            el[i].className = 'HiddenContent ' + searchClass;
        } else {
            el[i].className = 'VisibleContent ' + searchClass;
        }
    }
}

function selectOrg(nameValue, guidValue) {
	document.getElementById("txtOrgDisabled").value = nameValue;
	document.getElementById("hdnOrganization").value = guidValue;
	changeClass("searchResults", "HiddenContent");
	changeClass("orgSelected", "VisibleContent");
	activateSaveButton();
	setFocus('txtSearch');
}

function activateSaveButton(){
    var activate = false;
    var href = document.location.href.toLowerCase();
    
    if (href.indexOf('createneworganizationaffiliationenhanced') != -1) {
		var position = document.getElementById('cboPosition');
	    var orgDropDown = document.getElementById('cboOrganization');
	    var orgHidden = document.getElementById('hdnOrganization');
	    var orgText = document.getElementById('txtOrganization');
	    
	    var bPosition = (position.options.length > 1 && position.options[0].selected == false);
	    var bOrgDropDown = (orgDropDown.options.length > 1 && orgDropDown.options[0].selected == false);
	    var bOrgHidden = (orgHidden.value.length > 0);
	    var bOrgText = (orgText.value.length > 0);
	    
	    document.getElementById('cmdSave').disabled = (!(bPosition && (bOrgDropDown || bOrgHidden || bOrgText)));
	    activate = (bPosition && (bOrgDropDown || bOrgHidden || bOrgText));
    } else if (href.indexOf('secondaryreviewapplicationduplication') != -1) {
    	var oppGroup = document.getElementById('cboOpportunityGroup');
    	var oppPrimary = document.getElementById('cboPrimaryOpportunity');
    	var oppSecondary = document.getElementById('cboSecondaryOpportunity');
    	var scoreThreshold = document.getElementById('txtScoreThreshold');
    	
    	activate = (oppGroup.value.length > 0 && oppPrimary.value.length > 0 && oppSecondary.value.length > 0 && scoreThreshold.value.length > 0);
    	document.getElementById('cmdGetOppApps').disabled = !activate;
    }
    
	return activate;
}

function fixNewHallPassLinks() {
	if (document.getElementsByTagName) {
		var anchors = document.getElementsByTagName("a");
		for(var i=0; i < anchors.length; i++) {
			var a = anchors[i]; 
			var href = a.href.toLowerCase();
			if (href.indexOf("createnewhallpasssetup") != -1) {
				href = href + ((href.indexOf("?") == -1)? "?" : "&") + "ajax=1"; 
				a.setAttribute("href",href);
			} else if ((href.indexOf("createneworganizationaffiliation") != -1) && (href.indexOf("step=edit") == -1) && (href.indexOf("enhanced") == -1)) {
				href = href.replace("createneworganizationaffiliation", "CreateNewOrganizationAffiliationEnhanced");
				a.setAttribute("href",href); 
			}
		} 
	}
}

function selectAllNone(formName, selected) {
    if (document.getElementById) {
        var formObj = document.getElementById(formName);
        if (formObj != null) {
	        for (var i=0; i < formObj.elements.length; i++) {
	            var fldObj = formObj.elements[i];
	            if (fldObj.type != null && fldObj.type == 'checkbox') {
	                fldObj.checked = (selected);
	            }
	        }
	    }
    }
}

function getKey(oEvent) {
	if (oEvent.keyCode) {
		return oEvent.keyCode; 
	} else if (oEvent.which) {
		return oEvent.which; 
	} else {
		return null;
	}
}

function printThis() {
   $(".temp_print").remove();
   $("textarea").each(function() {
      var contents = $(this).val();
      contents = contents.replace(new RegExp("\\n","g"),"\<br/\>");
      $(this).after("<p class=\"print_block\">" + contents + "</p>");
   });
   window.print();
}

function removeSelectOptions(selectElement, beginIndex, numToDelete) {
	if (beginIndex < selectElement.options.length) {
		var numOptionsAfterBegin = selectElement.options.length - beginIndex;
		if (numToDelete == undefined) {
			numToDelete = numOptionsAfterBegin;
		} else {
			numToDelete = Math.min(numOptionsAfterBegin, numToDelete);
		}
	}
	
	for (i = 0; i < numToDelete; i++) {
		selectElement.remove(beginIndex);
	}
}

function addSelectOptions(fromListId, toListId) {
  	var fromList = document.getElementById(fromListId);
  	var toList = document.getElementById(toListId);
  	// step through all items in fromList
  	for (var i = 0; i < fromList.options.length; i++) {
  		if (fromList.options[i].selected) {
  			// add the item
  			newItem = toList.options.length;
  			toList.options[newItem] = new Option(fromList.options[i].text);
  			toList.options[newItem].value = fromList.options[i].value;
  			toList.options[newItem].selected = true;
  		}
  	}
}

function removeAllSelectOptions(fromListId) {
	var i = 0;
	var j;
	var k = 0;
  	var fromList = document.getElementById(fromListId);
  
  	while (i < (fromList.options.length - k)) {
  		if (fromList.options[i].selected) {
  			// remove the item
  			for (j = i; j < (fromList.options.length - 1); j++) {
  				fromList.options[j].text = fromList.options[j+1].text;
  				fromList.options[j].value = fromList.options[j+1].value;
  				fromList.options[j].selected = fromList.options[j+1].selected;
  			}
  			k++;
  		} else {
  			i++;
  		}
  	}
  	for (i = 0; i < k; i++) {
  		fromList.options[fromList.options.length - 1] = null;
  	}
}

function moveSelectOptions(fromListId, toListId) {
	addSelectOptions(fromListId, toListId);
	removeAllSelectOptions(fromListId);
}

function toggleAllCheckBoxes(formId, allNoneCheckBoxId) {
    var form = document.getElementById(formId)
    var allNoneCheckBox = document.getElementById(allNoneCheckBoxId)
    for (var i = 0; i < form.elements.length; i++) {
    var element = form.elements[i];
    if ((element != allNoneCheckBox) && (element.type == 'checkbox') && (!element.disabled) ) {
        element.checked = allNoneCheckBox.checked;
    }
  }
}

function toggleCheckBoxes(formId, allNoneCheckBoxId, checkBoxName) {
    var form = document.getElementById(formId)
    var allNoneCheckBox = document.getElementById(allNoneCheckBoxId)
    for (var i = 0; i < form.elements.length; i++) {
    	var element = form.elements[i];
    	if (element.name == checkBoxName) {
        	element.checked = allNoneCheckBox.checked;
       	}
    }
}

/**
 * Retrieves an array of all of the checked values in the specified 
 * checkbox group
 */
function getSelectedCheckBoxValues(checkBoxGroup) {
    var values = new Array();
    if (checkBoxGroup) {
        if (checkBoxGroup.length) {
            for (var i = 0; i < checkBoxGroup.length; i++) {
                if (checkBoxGroup[i].checked) {
                    values[values.length] = checkBoxGroup[i].value
                }
            }
        } else {
            if (checkBoxGroup.checked) {
                values[values.length] = checkBoxGroup.value
            }
        }
    }
    
    return values;
}


/**
 * Retrieves the checked radio button from the specified group.
 */
function getSelectedRadioButton(radioButtonGroup) {
	if (radioButtonGroup) {
		if (radioButtonGroup.length) {
			for (var i = 0; i < radioButtonGroup.length; i++) {
				if (radioButtonGroup[i].checked) {
					return radioButtonGroup[i];
				}
			}
		} else {
			if (radioButtonGroup.checked) {
				return radioButtonGroup; 
			}
		}
	}

	return null;
}

/**
 * Retrieves the value of the checked radio button from the specified group.
 */
function getSelectedRadioButtonValue(radioButtonGroup) {
	if (radioButtonGroup) {
		if (radioButtonGroup.length) {
			for (var i = 0; i < radioButtonGroup.length; i++) {
				if (radioButtonGroup[i].checked) {
					return radioButtonGroup[i].value;
				}
			}
		} else {
			if (radioButtonGroup.checked) {
				return radioButtonGroup.value; 
			}
		}
	}

	return null;
}

/**
 * Enables or Disables all of the elements of a radio button or checkbox group.
 */
function enableButtonGroup(group, enable) {
	if (group) {
		if (group.length) {
			for (var i = 0; i < group.length; i++) {
				group[i].disabled = !enable; 
			}
		} else {
			group.disabled = !enable; 
		}
	}

	return null;
}


/**
 * Removes all of the rows in the table starting with the begin index
 * and proceeding until either the end of the table is reached or numToDelete
 * is hit.  If numToDelete is omitted, all rows from the beginIndex on are
 * deleted.
 */
function removeTableRows(tableElement, beginIndex, numToDelete) {
	if (beginIndex < tableElement.rows.length) {
		var numRowsAfterBegin = tableElement.rows.length - beginIndex;
		if (numToDelete == undefined) {
			numToDelete = numRowsAfterBegin;
		} else {
			numToDelete = Math.min(numRowsAfterBegin, numToDelete);
		}
	}
	
	for (i = 0; i < numToDelete; i++) {
		tableElement.deleteRow(beginIndex);
	}
}

/**
 * Removes a table row by searching the row collection for a row
 * with the specified id.
 */
function removeTableRow(tableElement, rowId) {
	for (var i = 0; i < tableElement.rows.length; i++) {
		if (tableElement.rows[i].id == rowId) {
			tableElement.deleteRow(i);
			break;
		}
	}
}

//------------------------------------------------------------------------------
//  Class Manipulation Methods
//------------------------------------------------------------------------------

/**
 * Appends the indicated newClassName to the objects class if it is not already present.
 */
function appendClassName(obj, newClassName) {
    if (!containsClassName(obj, newClassName)) {
	    if (!obj.className) {
            obj.className = newClassName;
        } else {
	        obj.className = obj.className + " " + newClassName;
        }
    }
}

/**
 * Removes a class name from an object.
 */
function removeClassName(obj, classNameToRemove) {
    if (obj.className) {
    	var re = new RegExp("\\b" + classNameToRemove + "\\s");
    	obj.className = re.replace(re, '');
    }
}

/**
 * Determines if a class name is present on an object.
 */
function containsClassName(obj, className) {
    if (obj.className) {
        var classNames = obj.className.split(' ');
        for (var i = 0; i < classNames.length; i++) {
            if (classNames[i] == className) {
                return true;
            }
        }
    }

    return false;
}

/**
 * Replaces an existing class name on an element with a new value.  If the old
 * value is not present, the new value is simply added to the end of the class string.
 *
 * Returns true is the old value was present; otherwise, false.
 */
function replaceClassName(obj, oldClassName, newClassName) {
    if (!obj.className) {
    	obj.className = newClassName;
    	return false;
    } else {
    	var re = new RegExp("\\b" + oldClassName + "\\b");
    	if (obj.className.match(re)) {
    		obj.className = re.replace(re, newClassName);
    		return true;
    	} else {
    		obj.className = obj.className + ' ' + newClassName;
    		return false; 
    	}
   	}
}

/**
 * JavaScript Namespace for OSIC specific functions
 */
var OSIC = {
	CONTENT_AREA : 'content_area',
	STANDARD : 'standard',
	GRADE_BAND : 'grade_band',
	BENCHMARK : 'benchmark',
	GRADE_LEVEL : 'grade_level',
	INDICATOR : 'indicator',

	/**
	 * Determines the level of an OSIC value, returning one of the above constants.
	 */
	getLevel: function(osicValue) {
		var osicPartCount = osicValue.split('.').length;
        switch (osicPartCount) {
            case 2 :
                return this.CONTENT_AREA;
            case 3 :
                return this.STANDARD;
            case 4 :
                return this.GRADE_BAND;
            case 5 :
                return this.BENCHMARK;
            case 6 :
                return this.GRADE_LEVEL;
            case 7 :
                return this.INDICATOR;
		}
	},

	/**
	 * Comparison function for OSICs.  Useful when sorting
	 * arrays of OSICs
	 */
	compareOsics: function(osic1, osic2) {
		var compare = osic1.length - osic2.length;
		if (0 != compare) {
			return compare;
		} else {
			return ((osic1 > osic2) ? 1 : -1);
		}
	}
}

//TODO: This is no longer needed once the menus go away
var sfHover = function() {
	if (document.getElementById('Menu') != null) {
	    var sfEls = document.getElementById("Menu").getElementsByTagName("li");
	    for (var i=0; i<sfEls.length; i++) {
	        sfEls[i].onmouseover=function() {
	            this.className+=" sfhover";
	        }
	        sfEls[i].onmouseout=function() {
	            this.className=this.className.replace(new RegExp(" sfhover\\b"), "");
	        }
	    }
	}
}
if (window.attachEvent) window.attachEvent("onload", sfHover);