vue事件实现原理
Vue 事件实现原理
Vue 的事件系统基于发布-订阅模式,通过 $on、$emit、$off 等方法实现组件间通信。其核心原理可以分为以下几个部分:
事件注册与存储
Vue 实例内部通过 _events 对象存储事件监听器。当调用 $on 方法时,会将事件名作为键,监听器函数作为值存入 _events 对象。如果是多个监听器,则以数组形式存储。
// 伪代码示例
Vue.prototype.$on = function (event, fn) {
const vm = this
;(vm._events[event] || (vm._events[event] = [])).push(fn)
return vm
}
事件触发
调用 $emit 方法时,会根据事件名从 _events 中取出对应的监听器函数列表,依次执行。支持传递参数,这些参数会传递给监听器函数。
Vue.prototype.$emit = function (event, ...args) {
const vm = this
let cbs = vm._events[event]
if (cbs) {
cbs.forEach(fn => fn.apply(vm, args))
}
return vm
}
事件移除
$off 方法用于移除事件监听器。可以移除指定事件的某个监听器、所有监听器,或移除所有事件的所有监听器。
Vue.prototype.$off = function (event, fn) {
const vm = this
if (!arguments.length) {
vm._events = Object.create(null)
return vm
}
if (!fn) {
vm._events[event] = null
return vm
}
const cbs = vm._events[event]
if (cbs) {
vm._events[event] = cbs.filter(cb => cb !== fn)
}
return vm
}
自定义事件与原生事件
Vue 还区分自定义事件和原生 DOM 事件:
- 自定义事件通过
$emit和$on实现组件间通信。 - 原生 DOM 事件通过
v-on指令绑定,底层调用addEventListener。
事件修饰符
Vue 提供的事件修饰符(如 .stop、.prevent)在编译阶段会被解析为对应的原生 DOM 操作。例如:
.stop会调用event.stopPropagation().prevent会调用event.preventDefault()
总结
Vue 的事件系统通过 _events 对象管理监听器,利用发布-订阅模式实现高效的事件通信。其设计兼顾了灵活性和性能,同时通过修饰符简化了原生事件的处理。







