Слушатель декоратора Javascript - PullRequest
0 голосов
/ 09 февраля 2019

Я немного поиграюсь с декораторами, имея угловой фон, я пытаюсь обернуть голову вокруг декоратора HostListener.

Вот как далеко я дошёл:

class Demo {
        counter = 0;

        @Listen("mousemove") onMouseMove(e?) {
            console.log(this);

            this.counter++;
        }
    }

    export function Listen(name) {
        return (target, key, descriptor) => {

            window.addEventListener(name, oldValue.bind(target));


            return descriptor;
        };
    }

    new Demo();

Это более или менее единственная проблема реализации - передача цели / этой ссылки, поскольку цель не инициализирована.

1 Ответ

0 голосов
/ 11 февраля 2019

Решено, я использую Vue, так что это может быть не всем ответом, в основном то, что я делаю, это вызов функции только один раз, когда вы можете добавить mixin, и внутри этого mixin будет вызываться хук beforeMount,таким образом, позволяя мне вызвать его один раз.

Обновленный код Decorator:

export function Listen(name) {
    return function (target, key, descriptor) {
        if (!target.subscriptions) target.subscriptions = [];


        add(target, "Listen", key);

        if (process.client) {
            const oldValue = descriptor.value;

            descriptor.value = function() {
                target.subscriptions.push(
                    target.$eventManager.add(window, name, oldValue.bind(this))
                );
            };

            return descriptor;
        }

        return descriptor;
    };
}

const add = (target, name, functionName) => {
    if(!target.decorators) target.decorators = {};
    if(!target.decorators[name]) target.decorators[name] = [];

    target.decorators[name].push(functionName);
};

Vue mixin:

Vue.mixin({
    beforeMount: function() {
        if(this.decorators && this.decorators.Listen) {
            this.decorators.Listen.forEach(key => this[key]());
        }
    },
    destroyed: function () {
        this.$subscriptionManager.remove(this.subscriptions);
    }
});
...