Как бы вы прослушали событие, созданное динамически созданным экземпляром компонента?
В примере верхний компонент добавляется в DOM, а второй динамически создается в javascript.
Vue.component("button-counter", {
data: function() {
return {
count: this.initial_count
}
},
props: ['initial_count'],
methods: {
add: function() {
this.count++
this.$emit('myevent', this.count)
}
},
template: '<button v-on:click = "add">You clicked me {{ count }} times.</button>'
})
let app = new Vue({
el: "#app",
data() {
return {
initial_count: 10,
}
},
mounted: function() {
let initial_count = this.initial_count
let ButtonCounterComponentClass = Vue.extend({
data: function() {
return {}
},
render(h) {
return h("button-counter", {
props: {
initial_count: initial_count
}
})
}
})
let button_counter_instance = new ButtonCounterComponentClass()
button_counter_instance.$mount()
button_counter_instance.$on('myevent', function(count) {
console.info('listened!')
this.say(count)
})
this.$refs.container.appendChild(button_counter_instance.$el)
},
methods: {
say: function(message) {
alert(message)
}
}
})
<script src = "https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js"></script>
<div id = "app">
<button-counter initial_count=20 v-on:myevent = "say"></button-counter>
<div ref='container'></div>
</div>
Если я понял, чего вы хотите, вам просто нужно прослушать событие на внутреннем компоненте и передать его.
Я использовал стрелочные функции в нескольких местах, чтобы избежать проблем с привязками this
. В противном случае я попытался оставить ваш код без изменений, насколько это возможно. Изменения отмечены ****
.
Vue.component("button-counter", {
data: function() {
return {
count: this.initial_count
}
},
props: ['initial_count'],
methods: {
add: function() {
this.count++
this.$emit('myevent', this.count)
}
},
template: '<button v-on:click = "add">You clicked me {{ count }} times.</button>'
})
let app = new Vue({
el: "#app",
data() {
return {
initial_count: 10,
}
},
mounted: function() {
let initial_count = this.initial_count
let ButtonCounterComponentClass = Vue.extend({
data: function() {
return {}
},
render(h) {
return h("button-counter", {
props: {
initial_count: initial_count
},
// **** Added this ****
on: {
myevent: count => {
this.$emit('myevent', count);
}
}
// ****
})
}
})
let button_counter_instance = new ButtonCounterComponentClass()
button_counter_instance.$mount()
// **** Changed the next line ****
button_counter_instance.$on('myevent', count => {
console.info('listened!')
this.say(count)
})
this.$refs.container.appendChild(button_counter_instance.$el)
},
methods: {
say: function(message) {
alert(message)
}
}
})
<script src = "https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js"></script>
<div id = "app">
<button-counter initial_count=20 v-on:myevent = "say"></button-counter>
<div ref='container'></div>
</div>
Важно понимать, что button_counter_instance
не является экземпляром вашего компонента button-counter
. Вы обернули его в другой компонент, хотя компонент, который не добавляет никаких дополнительных узлов DOM. Таким образом, прослушивание компонента-обертки — это не то же самое, что прослушивание button-counter
.
Документы, на которые можно перейти h
: https://vuejs.org/v2/guide/render-function.html#The-Data-Object-In-Depth