/// <reference path="../../../Functions.ts" />
class BranchingOption {
    public say : Say;
    public appearCondition : (() => boolean) | boolean;
    public previouslyPicked : boolean = false;

    public constructor (say : Say, appearCondition? : (() => boolean) | boolean) {
        this.say = say;
        this.appearCondition = appearCondition;
    }
}

class BranchingDialogue {
    private options : Array<BranchingOption> = [];
    private resolve : Function;

    public constructor (...options : Array<BranchingOption>) {
        this.addOptions(...options);
    }

    public addOptions (...options : Array<BranchingOption>) {
        this.options.push(...options);
        arrayUnique(this.options);
    }

    public async getChosenOption () : Promise<BranchingOption> {
        let validOptions = [];

        for (let i = 0, value = this.options[i]; value != undefined; value = this.options[++i]) {
            if (value.appearCondition == undefined || (typeof value.appearCondition == "function" && value.appearCondition()) || value.appearCondition) {
                validOptions.push(value);
            }
        }

        let choiceButtons : Array<HTMLElement> = [];

        for (let i = 0; i < validOptions.length; i++) {
            let value = validOptions[i];
            let classes = ["choice"];
            if (value.previouslyPicked) {
                classes.push("picked");
            }
            choiceButtons.push((await value.say.getHTML("p", classes))[0]);
        }

        let PlayerInput : Promise<BranchingOption> = new Promise((resolve, reject) => {
            this.resolve = resolve;
        });

        Controls.KeyHandler.reset();

        for (let index = 0, value = choiceButtons[index]; value != undefined; value = choiceButtons[++index]) {
            Controls.KeyHandler.applyCode(value, Controls.KeyHandler.getFirstKeyCode());
            value.addEventListener("click", (e) => {
                validOptions[index].previouslyPicked = true;
                this.resolve(validOptions[index]);
                e.preventDefault();
            });
        }

        await Elements.CurrentTurnHandler.print(...choiceButtons);

        let choice = await PlayerInput;

        await Elements.CurrentTurnHandler.unprint(...choiceButtons);

        return choice;
    }
}