var __importDefault = (this && this.__importDefault) || function (mod) {
    return (mod && mod.__esModule) ? mod : { "default": mod };
};
define(["require", "exports", "jquery", "rxjs", "../key-constants"], function (require, exports, jquery_1, rxjs_1, key_constants_1) {
    "use strict";
    Object.defineProperty(exports, "__esModule", { value: true });
    jquery_1 = __importDefault(jquery_1);
    /**
     * A minibuffer is a kind of single line prompt that allows the user to enter
     * data. As the name suggests, this is inspired from Emacs.
     */
    class Minibuffer {
        constructor(top) {
            this._enabled = false;
            /**
             * The object on which this class and subclasses may push new events.
             */
            this._events = new rxjs_1.Subject();
            /**
             * The observable on which clients can listen for events.
             */
            this.events = this._events.asObservable();
            this.$top = jquery_1.default(top);
            this.$top.append("\
<label></label>&nbsp;<input type='text'>");
            this.promptEl = top.getElementsByTagName("label")[0];
            this.input = top.getElementsByTagName("input")[0];
            const $input = this.$input = jquery_1.default(this.input);
            $input.on("input", this.onInput.bind(this));
            $input.on("keypress", this.onKeypress.bind(this));
            $input.on("keydown", this.onKeydown.bind(this));
            this.disable();
        }
        get enabled() {
            return this._enabled;
        }
        enable() {
            this._enabled = true;
            this.input.disabled = false;
            this.input.style.display = "";
            this.input.focus();
        }
        disable() {
            this._enabled = false;
            this.input.disabled = true;
            this.input.value = "";
            this.input.style.display = "none";
        }
        installClient(client) {
            this.client = client;
            this.keydownHandler = client.onMinibufferKeydown.bind(client);
            this.clientSubscription =
                this.events.subscribe(client.onMinibufferChange.bind(client));
            this.enable();
        }
        uninstallClient() {
            const client = this.client;
            if (client === undefined) {
                return;
            }
            this.client = undefined;
            this.keydownHandler = undefined;
            this.clientSubscription.unsubscribe();
            this.disable();
            this.prompt = "";
            this.previous = undefined;
            client.onUninstall();
        }
        get prompt() {
            return this.promptEl.textContent;
        }
        set prompt(value) {
            this.promptEl.textContent = value;
        }
        forwardEvent(ev) {
            // For keypress events, we have to fill the input ourselves.
            if (ev.type === "keypress") {
                this.input.value += String.fromCharCode(ev.which);
            }
            this.$input.trigger(ev);
        }
        onKeydown(ev) {
            if (key_constants_1.ESCAPE.matchesEvent(ev)) {
                this.uninstallClient();
                return false;
            }
            if (this.keydownHandler != null && this.keydownHandler(ev) === false) {
                return false;
            }
            return undefined;
        }
        onKeypress(_ev) {
            const value = this.input.value;
            if (value !== this.previous) {
                this.previous = value;
                this._events.next({ name: "ChangeEvent", value });
            }
        }
        onInput(_ev) {
            const value = this.input.value;
            if (value !== this.previous) {
                this.previous = value;
                this._events.next({ name: "ChangeEvent", value });
            }
        }
    }
    exports.Minibuffer = Minibuffer;
});
//# sourceMappingURL=minibuffer.js.map