/**
 * @class SurveySelector Class for the Selector of surveys which
 *        includes describing the originizational unit of the
 *        survyes.
 * 
 * @author ktyra (10/30/2008)
 */
 

isc.defineClass("OPINIATOR_UserTree", isc.TreeGrid);
OPINIATOR_UserTree.addProperties({

    //  Busy 
    showBusy: OPINIATOR_ShowBusy,
    destroyBusy: OPINIATOR_DestroyBusy,

    // Superclass properties
    loadDataOnDemand: false,
    selectionType: "single",
    styleName:"defaultCanvas",
    bodyStyleName:"surveySelectorBody",
    baseStyle:"surveySelectorCell",
    bodyBackgroundColor:null,
    showHeaderContextMenu:false, 
    showHeader:false, 
    showShadow:false, 
    shadowSize:0,
    iconSize:16,
    folderIcon:null,
    showOpenIcons:false,
    showDropIcons:false,
    openIconSuffix:"",
    closedIconSuffix:"",
    border:"0px",

    initWidget : function ()
        { this.Super("initWidget", arguments); },

    destroy: function()
        {
        this.destroyBusy();
        this.data.data = null;
        this.Super("destroy", arguments);
        },

    _isDeactive: function ( node )
        {
        if ( !node.active ) 
            { return true; }
        if ( node.parentId === 0 ) 
            { return false; }
        return this._isDeactive(this.data.data.find("id", node.parentId));
        },

    getIcon: function( node )
        {
        var isfolder = new Boolean(node.isFolder).valueOf();
        var isroot = new Boolean(node.isRootOrg).valueOf();
        var isdomain = new Boolean(node.isDomainOrg).valueOf();

        if ( isfolder )
            {
            if ( isroot )
                { return "icons/16/system.png"; }
            else if ( isdomain )
                {
                if ( this._isDeactive(node) )
                    { return "icons/16/domain1_black.png"; }
                else
                    { return "icons/16/domain1.png"; }
                }
            else
                {
                if ( this._isDeactive(node) )
                    { return "icons/16/group_black.png"; }
                else
                    { return "icons/16/group.png"; }
                }
            }
        else
            {
            if ( this._isDeactive(node) )
                { return "icons/16/user_black.png"; }
            else
                { return "icons/16/user.png"; }
            }
        return null;
        }

    });


isc.defineClass("OPINIATOR_OrgUserSelector", isc.Canvas);
isc.OPINIATOR_OrgUserSelector.addProperties({

    // Constructor properties

    /**
     *  If defined then then buttons will be added to the tool strip
     *  to add and delete surveys
     */
    toolstrip: null,

    /**
     *  Called when a survey has been selected or a new survey is
     *  created.
     *  
     *  @param survey   May either be a survey object or a survey
     *  id. Check type to determine what to do with the function
     */
    onUserOpen: function ( user ) {},

    /**
     *   Called when an orgunit has been selected
     * 
     *   @param orgid   The orgunit id
     */
    onOrgOpen: function ( orgid ) {},

    /**
     * Called when there is not currently a selection
     */
    onNothingOpen: function () {},

    onUserAdded: function () {},

    onOrgAdded: function () {},


    // Superclass properties
    showResizeBar:true,
    styleName:"defaultCanvas",


    // Private Properties
    _treegrid: null,
    _userTree: null,
    _newUserButton: null,
    _delUserButton: null,
    _newOrgButton: null,
    _delOrgButton: null,

    initWidget : function ()
        {
        if ( isc.isAn.Object(this.toolstrip) )
            {
            this._newUserButton = OPINIATOR_Button.create({
                target: this,
                layoutAlign:"center",
                visibility: "hidden",
                title: "New User",
                icon: "icons/16/user.png",
                click: function ()
                    {
                    this.target.newUser();
                    return true;
                    }
                });

            this._deleteUserButton = OPINIATOR_Button.create({
                target: this,
                layoutAlign:"center",
                visibility: "hidden",
                title: "Delete",
                icon: "icons/16/delete.png",
                click: function ()
                    {
                    this.target.deleteUser();
                    return true;
                    }
                });


            this._newOrgButton = OPINIATOR_Button.create({
                target: this,
                layoutAlign:"center",
                visibility: "hidden",
                title: "New Org",
                icon: "icons/16/group.png",
                click: function ()
                    {
                    this.target.newOrg();
                    return true;
                    }
                });

            this._deleteOrgButton = OPINIATOR_Button.create({
                target: this,
                layoutAlign:"center",
                visibility: "hidden",
                title: "Delete",
                icon: "icons/16/delete.png",
                click: function ()
                    {
                    this.target.deleteOrg();
                    return true;
                    }
                });


            this._eraseOrgButton = OPINIATOR_Button.create({
                target: this,
                layoutAlign:"center",
                visibility: "hidden",
                title: "Erase Data",
                icon: "icons/16/erase.png",
                click: function ()
                    {
                    this.target.eraseOrg();
                    return true;
                    }
                });


            this.toolstrip.addMember(this._eraseOrgButton, 0);
            this.toolstrip.addMember(this._deleteOrgButton, 0);
            this.toolstrip.addMember(this._deleteUserButton, 0);
            this.toolstrip.addMember(this._newOrgButton, 0);
            this.toolstrip.addMember(this._newUserButton, 0);
            }

        this._treegrid = OPINIATOR_UserTree.create({
            width:"100%",
            height:"100%",
            target:this,
            nodeClick: function( tree, node, recordNum )     
                { this.target._openNode(node); }
            });

        this.children = [this._treegrid];
        this.Super("initWidget", arguments);
        //this.delayCall("refresh");
        },
	
	// override hide method
	hide:function() {
		_hide(this);
	},
	
	// override show method
	show:function() {
		_show(this);
	},
	
    destroy: function()
        {
        delete this._userTree;
        delete this._treegrid.target;
        delete this._treegrid;
        delete this._newUserButton;
        delete this._deleteUserButton;
        delete this._newOrgButton;
        delete this._deleteOrgButton;
        delete this._eraseOrgButton;
        delete this.toolstrip;
        this.Super("destroy", arguments);
        },

    /**
     * Show the busy indicator in the tree grid
     */
    showBusy: function ( state, delay )
        { this._treegrid.showBusy(state, delay); },

    _disableAllButtons: function ()
        {
        this._newUserButton.hide();
        this._deleteUserButton.hide();
        this._newOrgButton.hide();
        this._deleteOrgButton.hide();
        this._eraseOrgButton.hide();
        },

    _enableOrgButtons: function ( isDomainOrg )
        {
        this._newUserButton.show();
        this._deleteUserButton.hide();
        this._newOrgButton.show();
        this._deleteOrgButton.show();
        if ( isDomainOrg )
            { this._eraseOrgButton.show(); }
        else
            { this._eraseOrgButton.hide(); }
        },

    _enableUserButtons: function ()
        {
        this._newUserButton.hide();
        this._deleteUserButton.show();
        this._newOrgButton.hide();
        this._deleteOrgButton.hide();
        this._eraseOrgButton.hide();
        },

    refreshUserNode : function( user )
        {
        var node = this._findUserNode(user);
        if ( node === null  )
            { this._addUserNode(user); }
        else
            {
            node.name = user.firstName + " " + user.lastName;
            node.active = user.active;
            this._treegrid.refreshRow(this._treegrid.getRecordIndex(node));
            }
        },

    refreshOrgNode : function( org )
        {
        var node = this._findOrgNode(org);
        if ( node === null  )
            { this._addOrgNode(org); }
        else
            {
            node.name = org.levelName;
            var refchildren = (node.active != org.active);
            node.active = org.active;
            this._treegrid.refreshRow(this._treegrid.getRecordIndex(node));            
            if ( refchildren )
                { this._refreshChildren(node.id); }
            }
        },
        
    _refreshChildren : function( id )
        {
        var nodes = this._userTree.nodes;
        var children = nodes.findAll("parentId", id);
        if ( isc.isA.Array(children) )
            {
            var len = children.getLength();
            for ( var i = 0; i < len; i++ )
                {
                var child = children[i];
                this._treegrid.refreshRow(this._treegrid.getRecordIndex(child));
                this._refreshChildren(child.id);
                }
            }
        },

    /**
     *  Re-loads the entire from the server
     */
    refresh : function()
        {
        this.showBusy(true, OPINIATOR.BUSY_DELAY);
        WebClientSvc.getUserTree(this.callback("_setUserTree"), this.callback("error"));
        },

	setUserTree: function() {
		this._userTree = globalTreeAdmin;
		this._userTree.nodes = globalDataAdmin;
	},

	_getTreeGrid: function() {
		return this._treegrid;	
	},

    /**
     *  Sets a survey tree 
     */
    _setUserTree: function ( userTree )
        {
        this.showBusy(false);
        this._userTree = isc.isAn.Object(userTree) ? userTree : {nodes:[]};
        this._userTree.nodes = OPINIATOR.toArray(this._userTree.nodes);

        var tree = isc.Tree.create({
            modelType: "parent",
            rootValue: 0,
            nameProperty: "name",
            titleProperty: "name",
            idField: "id",
            parentIdField: "parentId",
            showRoot: false,            
            data: userTree.nodes
            });		
        this._treegrid.setData(tree);
		
		globalTreeAdmin = tree;		
		globalDataAdmin = this._userTree.nodes;
		
		// expand all, then collapse on so that all icon will be loaded correctly.
		tree.openAll();
		tree.closeAll();
		
		// open again with level 1
		tree.openFolder(tree.data[0]);
		
        },

    _findUserNode: function( user )
        { return this._findNode(user.id, false); },

    _findOrgNode: function( org )
        { return this._findNode(org.id, true); },

    _findNode: function( id, isFolder )
        {
        var nodes = this._userTree.nodes;
        for ( var i = 0; i < nodes.length; i++ )
            {
            var node = nodes[i];
            if ( (node.isFolder == isFolder) && (node.recordId == id) )
                { return node; }
            }
        return null;
        },

    _nextFreeId: function ( user )
        {
        var nodes = this._userTree.nodes;
        // Find the next id
        var nextid = 0;
        var len = nodes.getLength();
        for ( var i = 0; i < len; i++ )
            {
            var node = nodes[i];
            if ( nextid <= node.id )
                { nextid = node.id + 1; }
            }
        return nextid;
        },

    _findParentNode: function ( id )
        {
        var nodes = this._userTree.nodes;
        var parentnode = null;
        var len = nodes.getLength();
        for ( i = 0; i < len; i++ )
            {
            parentnode = nodes[i];
            if ( parentnode.isFolder && (parentnode.recordId == id) )
                { break; }
            }
        return parentnode;
        },

    _addUserNode: function ( user )
        {
        parentnode = this._findParentNode(user.orgUnitRef.id);
        parentnode.isOpen = true;

        // Create a new node and add it to the tree
        var newnode = {
            id:this._nextFreeId(), 
            parentId:parentnode.id, 
            name:user.firstName + " " + user.lastName, 
            recordId:user.id, 
            active:user.active, 
            enabled:true, 
            isOpen:true, 
            isFolder:false
            }; 

        this._addNode(newnode);
        this._enableUserButtons();
        this.onUserAdded(user);
        },

    _addOrgNode: function ( org )
        {
        var nodes = this._userTree.nodes;

        parentnode = this._findParentNode(org.parentId);
        parentnode.isOpen = true;

        // Create a new node and add it to the tree
        var newnode = {
            id:this._nextFreeId(), 
            parentId:parentnode.id, 
            name:org.levelName,
            isDomainOrg:org.isDomainOrg,
            recordId:org.id, 
            active:org.active, 
            enabled:true, 
            isOpen:true, 
            isFolder:true
            };

        this._addNode(newnode);
        this._enableOrgButtons(org.isDomainOrg);
        this.onOrgAdded(org);
        },

    _addNode: function ( newnode )
        {
        var nodes = this._userTree.nodes;
        nodes.add(newnode);
        this._treegrid.getData().linkNodes([newnode]);
        this._treegrid.deselectAllRecords();
        this._treegrid.selectRecord(newnode);
        },

    _removeUserNode: function ( id )
        { return this._removeNode(id, false); },

    _removeOrgNode: function ( id, isFolder )
        { return this._removeNode(id, true); },

    _removeNode: function ( id, isFolder )
        {
        var node = null;
        var nodes = this._userTree.nodes;

        // Find the node
        var len = nodes.getLength();
        for ( var i = 0; i < len; i++ )
            {
            node = nodes[i];
            if ( (node.isFolder == isFolder) && (node.recordId == id) )
                { break; }
            }

        if ( node !== null )
            { this._treegrid.getData().remove(node); }

        len = nodes.getLength();
        if ( i < len )
            { return nodes[i]; }

        return ( len > 0 ) ? nodes[len-1] : null;
        },

    _selectNode: function( node )
        {
        if ( isc.isAn.Object(node) )
            {
            this._treegrid.deselectAllRecords();
            this._treegrid.selectRecord(node);
            }
        },

    /**
     *  Opens the node.  If the node is not specified the selection
     *  will be used.
     */
    _openNode: function ( node )
        {
        if ( !isc.isAn.Object(node) )
            { node = this._treegrid.getSelectedRecord(); }

        if ( isc.isAn.Object(node) )
            {
            if ( node.isFolder )
                { 
                this._enableOrgButtons(node.isDomainOrg);
                this.onOrgOpen(node.recordId); 
                }
            else
                { 
                this._enableUserButtons();
                this.onUserOpen(node.recordId); 
                }
            }
        else
            { this.onNothingOpen(); }
        },

    deleteUser: function ()
        {
        var usernode = this._treegrid.getSelectedRecord();
        if ( !usernode.isFolder )
            {
            if ( OPINIATOR_MAIN.user.id == usernode.recoredId )
                {
                OPINIATOR.warn("You cannot not delete your self");
                return;
                }
            this._pendingDelete = usernode.recordId;
            OPINIATOR.askOk("Delete the user <b>"+usernode.name+"</b>?<br>", this.callback("_deleteUserReply"));
            }
        },

    _deleteUserReply: function ( ok )
        { 
        if ( ok )
            { 
            WebClientSvc.deleteUser(this._pendingDelete, this.callback("_deleteUser"), this.callback("error") ); 
            delete this._pendingDelete;
            }
        },

    _deleteUser: function ( userid )
        {
        this.showBusy(false);
        this._removeUserNode(userid);
        this._openNode();
        },

    newUser: function ()
        {
        this.showBusy(true, OPINIATOR.BUSY_DELAY);
        var orgnode = this._treegrid.getSelectedRecord();
        if ( orgnode.isFolder )
            { WebClientSvc.newUser(orgnode.recordId, this.callback("_newUser"), this.callback("error") ); }
        },

    _newUser: function( user )
        {
        this.showBusy(false);
        this._disableAllButtons();
        this.onUserOpen(user);
        },

    selectUser: function( user )
        { this._selectNode(this._findUserNode(user)); },


    deleteOrg: function ()
        {
        var orgnode = this._treegrid.getSelectedRecord();
        if ( orgnode.isFolder )
            {
            this._pendingDelete = orgnode.recordId;
            OPINIATOR.askOk("Delete the org <b>"+orgnode.name+"</b>?<br>Note: This will delete all Surveys, Users and Analytics associated with this orginization", this.callback("_deleteOrgReply"));
            }
        },

    _deleteOrgReply: function ( ok )
        { 
        if ( ok )
            { 
            WebClientSvc.deleteOrgUnit(this._pendingDelete, this.callback("_deleteOrg"), this.callback("error") ); 
            delete this._pendingDelete;
            }
        },

    _deleteOrg: function ( orgid )
        {
        this.showBusy(false);
        this._removeOrgNode(orgid);
        this._openNode();
        },

    eraseOrg: function ()
        {
        var orgnode = this._treegrid.getSelectedRecord();
        if ( orgnode.isFolder )
            {
            this._pendingErase = orgnode.recordId;
            OPINIATOR.askOk("Erase the org <b>"+orgnode.name+"</b>?<br>Note: This will erase all Survey Responses & Analytic Results associated with this orginization", this.callback("_eraseOrgReply"));
            }
        },


    _eraseOrgReply: function ( ok )
        { 
        if ( ok )
            { 
            WebClientSvc.eraseOrg(this._pendingErase, this.callback("_eraseOrg"), this.callback("error") ); 
            delete this._pendingErase;
            }
        },

    _eraseOrg: function ( orgid )
        { this.showBusy(false); },


    newOrg: function ()
        {
        this.showBusy(true, OPINIATOR.BUSY_DELAY);
        var orgnode = this._treegrid.getSelectedRecord();
        if ( orgnode.isFolder )
            { WebClientSvc.newOrgUnit(orgnode.recordId, this.callback("_newOrg"), this.callback("error") ); }
        },

    _newOrg: function( org )
        {
        this.showBusy(false);
        this._disableAllButtons();
        this.onOrgOpen(org);
        },

    selectOrg: function( org )
        { this._selectNode(this._findOrgNode(org)); },

    error : function( code, msg )
        {
        this._treegrid.showBusy(false);
        switch ( msg )
            {
            case "DeletedState":
                OPINIATOR.warn("This survey has been deleted by another user.");
                this.refresh();
                break;

            default:
                OPINIATOR.warn(msg);
                break;
            }
        },

    callback: function (methodName)
        { return {target:this, methodName:methodName}; }

    });

