一、安装 mitt
sql
bashCopy Code
npm install mitt # :ml-citation{ref="1,2" data="citationList"}
pnpm install mitt # :ml-citation{ref="2" data="citationList"}
yarn add mitt # :ml-citation{ref="3" data="citationList"}
二、基本使用方式
-
局部使用(单文件内)
-
创建事件总线实例:
rubyjavascriptCopy Code import mitt from 'mitt'; const emitter = mitt(); // :ml-citation{ref="2,3" data="citationList"}
-
触发事件:
rubyjavascriptCopy Code emitter.emit('eventName', data); // :ml-citation{ref="1,2" data="citationList"}
-
监听事件:
rubyjavascriptCopy Code emitter.on('eventName', (data) => { console.log('接收数据:', data); }); // :ml-citation{ref="1,2" data="citationList"}
-
-
全局使用(跨组件通信)
-
在
main.ts
中注册全局事件总线:initypescriptCopy Code import { createApp } from 'vue'; import mitt from 'mitt'; const app = createApp(App); app.config.globalProperties.emitter = mitt(); // :ml-citation{ref="6,7" data="citationList"} app.mount('#app');
-
在组件中通过全局属性调用:
rubytypescriptCopy Code import { getCurrentInstance } from 'vue'; const { emitter } = getCurrentInstance()!.appContext.config.globalProperties; // :ml-citation{ref="2,7" data="citationList"}
-
三、事件监听与移除
操作 | 代码示例 | 作用说明 |
---|---|---|
移除单个事件监听 | emitter.off('eventName') |
解绑指定事件 |
清空所有事件监听 | emitter.all.clear() |
移除所有监听 |
批量监听/移除 | 结合 emitter.on 和 emitter.off 实现 |
动态管理事件 |
四、使用场景示例
-
组件间数据传递
-
子组件触发事件:
cssvueCopy Code <button @click="emitter.emit('send-data', { id: 1 })">发送数据</button> // :ml-citation{ref="5,8" data="citationList"}
-
父组件监听事件:
rubyjavascriptCopy Code emitter.on('send-data', (data) => { console.log('接收子组件数据:', data); }); // :ml-citation{ref="5,8" data="citationList"}
-
-
跨层级组件通信
- 非父子组件通过全局
emitter
实现交互,无需逐层传递props
。
- 非父子组件通过全局
五、注意事项
-
避免内存泄漏
- 组件销毁时需手动移除事件监听(如在
onUnmounted
生命周期中调用emitter.off
)。
- 组件销毁时需手动移除事件监听(如在
-
事件命名规范
- 使用唯一且明确的事件名称,防止命名冲突。
-
TypeScript 支持
- 全局使用时需扩展
ComponentCustomProperties
类型声明。
- 全局使用时需扩展
完整代码示例
typescript
typescriptCopy Code
// 全局注册(main.ts)
import { createApp } from 'vue';
import mitt from 'mitt';
declare module '@vue/runtime-core' {
interface ComponentCustomProperties {
emitter: ReturnType<typeof mitt>;
}
}
const app = createApp(App);
app.config.globalProperties.emitter = mitt(); // :ml-citation{ref="7" data="citationList"}
app.mount('#app');
// 组件中使用
import { getCurrentInstance } from 'vue';
const { emitter } = getCurrentInstance()!.appContext.config.globalProperties;
// 触发事件
emitter.emit('update-list', { items: [1, 2, 3] }); // :ml-citation{ref="1,2" data="citationList"}
// 监听事件
emitter.on('update-list', (data) => {
console.log('列表更新:', data);
}); // :ml-citation{ref="2,3" data="citationList"}
// 销毁时移除监听
onUnmounted(() => {
emitter.off('update-list'); // :ml-citation{ref="2,3" data="citationList"}
});