У меня есть директива, которая обновляет внешний вид элементов при изменении их содержимого. Таким образом, мне нужно, чтобы он запускался как при срабатывании собственного события change
, так и при первой настройке элемента. Поэтому я запускаю свою функцию в хуке bind
и в хуке componentUpdated
.
Таким образом, структура этого выглядит примерно так:
directives: {
demo: {
bind(el) {
el.addEventListener('change', () => {
alert('i am a directive function');
});
},
componentUpdated(el) {
alert('i am a directive function');
}
}
}
Он отлично работает, но мне пришлось скопировать и вставить функцию в оба объявления ловушек, и я хотел бы избавиться от этого.
Я подумал, что, возможно, объявление директивы может иметь свои локальные свойства, доступные через this
, поэтому я попытался решить это следующим образом:
directives: {
demo: {
myFunction: () => {
alert('i am a directive function');
},
bind(el) {
el.addEventListener('keyup', () => this.myFunction());
},
componentUpdated(el) {
this.myFunction();
}
}
}
Но это не сработало, говоря, что this.myFunction
не является функцией.
Как мне заставить это работать?
Это не очень похоже на разделение интересов. В идеале я хотел бы, чтобы директивы были своего рода plug & play и легко могли использоваться повторно.
Хм, я должен что-то упустить. Почему внешняя функция препятствует использованию plug&play или повторному использованию? Мой ответ ниже (вариант 2) демонстрирует то, что я предлагал.
Определите директиву в собственной переменной, на которую можно было бы ссылаться по имени вместо this
:
// MyComponent.vue
const myDirective = {
myFunction(msg) {
console.info(msg)
},
bind(el, { value }) {
el.addEventListener('keyup', () => myDirective.myFunction(value))
},
componentUpdated(el, { value }) {
myDirective.myFunction(value)
}
}
export default {
directives: {
myDirective
}
}
Определите общую функцию вне директивы и используйте ее там, где это необходимо:
// MyComponent.vue
function myFunction(msg) {
console.info(msg)
}
export default {
directives: {
myDirective: {
bind(el, { value }) {
el.addEventListener('keyup', () => myFunction(value))
},
componentUpdated(el, { value }) {
myFunction(value)
}
}
}
}
В обоих приведенных выше примерах директивы можно было бы переместить в отдельный файл, что повысило бы их тестируемость и улучшило бы читаемость компонента.
Да, вариант 2 — это тот, который я имел в виду, я не хотел, потому что он объявлял глобальную функцию (я нахожусь в банкомате приложения, отличного от cli). Вариант 1 — это именно то, что я хотел и пробовал, но я не знал, как правильно получить доступ к функции (я пытался с this
). Так что это работает. Спасибо!
Я бы просто переместил
myFunction
за пределы директивы в отдельную функцию, которую можно было бы вызывать где угодно. например,function myFunction() { ... }
, а затем просто используйтеmyFunction()
там, где это необходимо.