/**
  The following code is to support the TreeView Control with checboxes.
  Copyright by Information Refinery Inc.
**/

var LOADING_MESSAGE = "Loading, Please wait...";
var GETSUBNODES_AJAX_CONFIG = true;

///Callback function when the bullet is clicked to expand.
///
///p_ImageElement : image element clicked
///p_ControlID : name of the .net control that invoked this function.
///
function OnImageClicked( p_ImageElement , p_ControlID ) {

    if( GETSUBNODES_AJAX_CONFIG ) {

        //TargetNode is the UL tag that will have it's HTML dynamically written.
        var targetNode = p_ImageElement.name + '_branch';

	//since it may take a second or 2 to load output a message that something is happening
	WriteTextToID(targetNode, LOADING_MESSAGE);

        //Make an AJAX call to get the subnodes dynamically.
        //And set the callback to write to the targetNode, which is a UL tag.
        RunShortAjax("?ACID=" + p_ControlID + 
                     "&AOP=getsiccodes" +  
                     "&APARAMS=" + p_ImageElement.name ,
                     "WriteTextToID('" + targetNode + "', objHttpRequest.responseText)");



        //Reset the onclick handler so it does not continue to do AJAX calls.
        p_ImageElement.onclick = new Function("expandCollapse(this);");

    }

    //Call expandCollapse, which will expand/minimize the Image's subnodes sections
    expandCollapse(p_ImageElement);

    return true;
}


///Callback function when the checkbox is clicked/checked.
///
///     The subnodes are automatically checked or unchecked to reflect the state of the parent node.
///
///p_Node : checkbox that was clicked
///p_ControlID : 
///
function OnTreeItemClicked( p_Node, p_ControlID ) {

    //If the node invoking this is a checkbox 
    if( p_Node.type != null && p_Node.type == 'checkbox' ) {

        //Build the ajax url to record the checkbox's checkstate
        var ajaxURL = "?ACID=" + p_ControlID + 
                        "&AOP=checksiccodes" + 
                        "&APARAMS=" + p_Node.id + "," + p_Node.checked + 
                        "&ResponseXsl=/resource/sicBusinesses.simple.ajax.xslt";

        //run a short ajax , with no callback
        RunShortAjax( ajaxURL,  "WriteTextToID('ajax_SelectBusinessOutput', objHttpRequest.responseText)");

        //Set the state of the subnodes based on this node's state.
        checkSubNodes(p_Node, p_Node.checked);

        //Check siblings.
        setParent( p_Node );

    }
    return true;
}

///checkSubNodes recursively sets the state of child nodes equal to the parents state.
///
/// p_Node : the parent checkbox.  It's child boxes will be checked or unchecked base on the parent.
/// p_chkState : the check state of the parent.
function checkSubNodes( p_Node, p_chkState ) {

    //Get the current node's state data
    var objID = p_Node.id;

    //Get the current node's children branch
    // * This branch contains all the child nodes.
    var branchID = objID + '_branch';

    //Locate the branchNode element.
    var branchNode = document.getElementById(branchID);

    //Loop through the List-Items in the branchNode
    for( var i = 0; branchNode.childNodes != null && i < branchNode.childNodes.length; i++ ) {

        //For each List-Item loop through it's collection, and find the checkbox.
        for( var j = 0; branchNode.childNodes[i].id != null && j < branchNode.childNodes[i].childNodes.length; j++ ) {

            //Get the current element inside the LI.
            var el = branchNode.childNodes[i].childNodes[j];

            //If the element is a checkbox, then set it's checked state.
            if( el.type && el.type == "checkbox" ) {
                el.checked = p_chkState;

                //Recursively set the subnodes' state
                checkSubNodes( el, p_chkState );
            }
        }
    }
}


///getParent locates p_Node's parent checkbox and returns it.
///
/// p_Node : the child checkbox.  It's parent checkbox will be located by the function.
///
/// Note, if p_Node is a top level node, then the function returns FALSE.
function getParent( p_Node ) {
    //If the id's length is longer than 2 (then it is a child checkbox)
    if( p_Node.id.length > 2 ) {

        //Note, we have to get the parent by traversal instead of "document.getElementById(pID)"
        //because IE returns the first element that has the name equal to pID.

        //Get the id of the parent    
        var parentID = p_Node.id.substring(0, p_Node.id.length - 2);

        //The branch that contains the parent.  
        //  1st parentNode gets you to the LI that wraps the p_Node.
        //  2nd parentNode gets you to the UL (branch) where the LI exists.
        //  3rd parentNode gets you to the LI (parent) which wraps UL.
        var parentBranch = p_Node.parentNode.parentNode.parentNode;

        //Set the returnItem to false incase it cannot be found.
        var returnItem = false;


        //For each of the node in the parent branch ...
        for( var i = 0; i < parentBranch.childNodes.length && returnItem == false; i++ ){

            //Get the child element.
            var item = parentBranch.childNodes[i];

            //If the element is a checkbox and the ID equals parentID then return that element.
            if( item.type && item.type == "checkbox" && item.id == parentID ) {
                returnItem = item;
            }
        }

        return returnItem;
    }
    else {
        return false;
    }
}

///getSiblings locates the branch that contains all the sibling checkboxes.
///  * This branch will also contain p_Node in the collection of checkboxes.
///
/// p_Node : a checkbox item.  The branch that contains it will be returned because
///          it contains the siblings.
function getSiblings( p_Node ) {

    //If the node is a top level 
    if( p_Node.id.length == 2 ) {
        //  then there are no siblings
        return false;
    }
    //else 
    else {

        //  Get the parent node
        var parentalUnit = getParent( p_Node );

        //  return the branch of that parent node
        return document.getElementById( parentalUnit.id + '_branch' );
    }

}

///setParent sets p_Node's parent checkbox state to checked or unchecked.
///  * The state of the parent is checked if all of it's subnodes are checked, and unchecked otherwise.
///
/// p_Node : a checkbox item, who's parent will be checked/unchecked.
function setParent( p_Node ) {

    //Get the parent of this node.
    var parentalUnit = getParent(p_Node);

    //If p_Node does not have a parent then
    if( parentalUnit == false ) {
        //return immediately
        return;
    }               

    //If p_Node is FALSE then 
    if( p_Node.checked == false ) {
        //set the parent node to FALSE
        parentalUnit.checked = false;
    }
    //Else we need to look at the siblings check state
    else {

        //Get the sibling branch
        var siblingBranch = getSiblings( p_Node );

        //Assume they are all checked.    
        var isAllChecked = true;

        //Loop through the List-Items
        for( var i = 0; siblingBranch != null && 
                        siblingBranch.childNodes != null && 
                        i < siblingBranch.childNodes.length && 
                        isAllChecked; i++ ) {

            //Loop through each element in each List-Item
            for( var j = 0; siblingBranch.childNodes[i].id != null && 
                            j < siblingBranch.childNodes[i].childNodes.length && 
                            isAllChecked; j++ ){

                //Grab the current element
                var el = siblingBranch.childNodes[i].childNodes[j];

                //If it is a checkbox, then record it's state
                if( el.type && el.type == "checkbox" ) {
                    isAllChecked = el.checked && isAllChecked;
                }
            }
        }

        //Set the parent's state based on the siblings checked state.
        parentalUnit.checked = isAllChecked;
    }

    //Recursively call setParent with p_Node's parent as the parameter
    //This will check or uncheck the grand-parent.  (parent of the parent)
    setParent( parentalUnit );
}
