/// <reference path="../Elements.ts" />
/// <reference path="../../World/Classes/Rulebook.ts" />
module Elements.HyperlinkHandler {
    export var linkedActionsTab = document.getElementById("linkActions");
    export var commonActionsTab = document.getElementById("commonActionsTab");

    var currentCommand = document.createTextNode("");
    document.getElementById("currentCommand").appendChild(currentCommand);

    var currentActionTarget = document.createTextNode("");
    document.getElementById("linkTarget").appendChild(currentActionTarget);

    var commonActions = [];
    var availableActions = [];

    export function resetCommonActions () {
        commonActions.splice(0, commonActions.length);
        while (commonActionsTab.firstChild) {
            commonActionsTab.removeChild(commonActionsTab.firstChild);
        }
    }

    export function addCommonAction (name : string, action : Action) {
        commonActions.push([name, action]);
    }

    function resetAvailableActions () {
        availableActions = [];
        currentActionTarget.nodeValue = "";
        while (linkedActionsTab.firstChild) {
            linkedActionsTab.removeChild(linkedActionsTab.firstChild);
        }
    }

    export function addAvailableAction (name : string, action : Action) {
        availableActions.push([name, action]);
    }

    export function hoverAction (action : Action) {
        currentCommand.nodeValue = action.getCommandText().toLowerCase();
    }

    export function unhoverAction () {
        currentCommand.nodeValue = "";
    }

    export async function hyperlinkObject (thing? : any) {
        resetAvailableActions();
        if (thing instanceof Thing && thing != WorldState.player) {
            await HyperlinkingRulebook.execute({noun: thing});

            currentActionTarget.nodeValue = thing.getPrintedName() + ": ";

            for (let i = 0, value = availableActions[i]; value != undefined; value = availableActions[++i]) {
                let link = createLink(value);
                link.classList.add("columnLink");
                Controls.KeyHandler.applyCode(link, Controls.KeyHandler.getSecondKeyCode());
                linkedActionsTab.appendChild(link);
            }
        }
    }

    function createLink (value : Array<any>) {
        let link = document.createElement("a");
        link.appendChild(document.createTextNode(value[0]));
        Controls.Links.makeLink(link, value[1]);
        return link;
    }

    export async function hyperlinkCommonActions () {
        resetCommonActions();

        await CommonActionsRulebook.execute({});

        for (let i = 0, value = commonActions[i]; value != undefined; value = commonActions[++i]) {
            let link = createLink(value);
            link.classList.add("lineLink");
            Controls.KeyHandler.applyCode(link, Controls.KeyHandler.getThirdKeyCode());
            commonActionsTab.appendChild(link);
        }
    }

    /**
     * The hyperlinking rulebook is ran over the last thing the player interacted with.
     *  It populates the hyperlinks tab with information on the thing that was interacted with.
     * @type {Rulebook}
     */
    export var HyperlinkingRulebook = new Rulebook<Thing>("Hyperlinking something");

    /**
     * The common actions rulebook serves to set up all the available common actions for the player.
     *  It should check the player's current state to see if a command is applicable and
     *    then ADD said command to the HyperlinkHandler.
     * @type {Rulebook}
     */
    export var CommonActionsRulebook = new Rulebook<void>("Common Actions Rulebook");
}