赞
踩
EventHub是个全局对象,用于多个组件之间的通讯
就是发布订阅模式
比如:
EventHub.on
注册事件on(“xxx”, fn)EventHub.emit
触发事件emit(“xxx”)EventHub.off
删除事件off(“xxx”, fn)类实现
class EventHub{
on(eventName, fn){};
emit(eventName){};
}
export default EventHub;
简单的发布与订阅
class EventHub { /* { "楚天都市报": [fn1, fn2, fn3, fn4] , "羊城晚报": [fn1, fn2, fn3] } */ cache = {}; on(eventName, fn) { if (this.cache[eventName] === undefined) { // 初始化事件名 this.cache[eventName] = []; } const arry = this.cache[eventName]; arry.push(fn); } emit(eventName) { let arr = this.cache[eventName]; if (arr === undefined) { arr = []; } arr.forEach(fn => { fn(); }); } } export default EventHub;
测试
import EventHub from "../src/index";
// on emit
let called = false;
eventHub.on("xxx", () => {
called = true;
console.log("called: ", called);
})
eventHub.emit("xxx");
class EventHub {
cache = {};
on(eventName, fn) {
// api on 把函数推进cache数组
this.cache[eventName] = this.cache[eventName] || [];
this.cache[eventName].push(fn);
}
emit(eventName) {
// emit 把cache里面的fn依次调用
(this.cache[eventName] || []).forEach(fn => fn());
}
}
export default EventHub;
class EventHub {
cache = {};
on(eventName, fn) {
// api on 把函数推进cache数组
this.cache[eventName] = this.cache[eventName] || [];
this.cache[eventName].push(fn);
}
emit(eventName, data) {
// emit 把cache里面的fn依次调用
(this.cache[eventName] || []).forEach(fn => fn(data));
}
}
export default EventHub;
import EventHub from "../src/index";
const eventHub = new EventHub();
// on emit
let called = false;
eventHub.on("xxx", (data?) => {
called = true;
console.log("called: ", called);
console.log("data: ", data === "今天吃了泡面");
})
eventHub.emit("xxx", "今天吃了泡面");
class EventHub { ... off(eventName, fn) { // 删除cache中的事件fn let index = indexOf(this.cache[eventName], fn); if (index === -1) return; this.cache[eventName].splice(index, 1); } } function indexOf(arr, item) { if (arr === undefined ) return -1; let index = -1; for (let i = 0; i < arr.length; i++) { if (arr[i] === item) { index = i; break; } } return index; }
function indexOf(arr, item) { if (arr === undefined) return -1; let index = -1; for (let i = 0; i < arr.length; i++) { if (arr[i] === item) { index = i; break; } } return index; } class EventHub { cache = {}; on(eventName, fn) { // api on 把函数推进cache数组 this.cache[eventName] = this.cache[eventName] || []; this.cache[eventName].push(fn); } emit(eventName, data) { // emit 把cache里面的fn依次调用 (this.cache[eventName] || []).forEach(fn => fn(data)); } off(eventName, fn) { // 删除cache中的事件fn let index = indexOf(this.cache[eventName], fn); if (index === -1) return; this.cache[eventName].splice(index, 1); } } const eventHub = new EventHub(); function fn1() { console.log(1); } function fn2() { console.log(2); } function fn3() { console.log(3); eventHub.off("init", fn1); eventHub.off("init", fn2); eventHub.off("init", fn3); } function fn4() { console.log(4); } function fn5() { console.log(5); } function fn6() { console.log(6); } eventHub.on("init", fn1); eventHub.on("init", fn2); eventHub.on("init", fn3); eventHub.on("init", fn4); eventHub.on("init", fn5); eventHub.on("init", fn6); eventHub.emit("init"); eventHub.emit("init");
因为每次都是使用splice来切割数组的,所以off之后的事件直接消失,后面的事件就往前补空缺,使得下标index改变
const eventHub = new EventHub(); function fn1() { console.log(1); } function fn2() { console.log(2); } function fn3() { console.log(3); eventHub.off("init", fn1); eventHub.off("init", fn2); eventHub.off("init", fn3); } function fn4() { console.log(4); } function fn5() { console.log(5); } function fn6() { console.log(6); } eventHub.on("init", fn1); eventHub.on("init", fn2); eventHub.on("init", fn3); eventHub.on("init", fn4); eventHub.on("init", fn5); eventHub.on("init", fn6); console.log("第一次执行事件"); eventHub.emit("init"); console.log("第二次执行事件"); eventHub.emit("init");
如果有off取消事件,就先将off的事件指向null
在下一次emit触发事件的时候再重构事件数组
function indexOf(arr, item) { if (arr === undefined) return -1; let index = -1; for (let i = 0; i < arr.length; i++) { if (arr[i] === item) { index = i; break; } } return index; } class EventHub { cache = {}; on(eventName, fn) { // api on 把函数推进cache数组 this.cache[eventName] = this.cache[eventName] || []; this.cache[eventName].push(fn); } emit(eventName, data) { // console.log(this.cache[eventName]); // 删除数组中的无效事件 this.cache[eventName] = this.cache[eventName].filter(fn => fn != null); // console.log(this.cache[eventName]); // emit 把cache里面的fn依次调用 (this.cache[eventName] || []).forEach(fn => fn && fn(data)); } off(eventName, fn) { // 删除cache中的事件fn let index = indexOf(this.cache[eventName], fn); if (index === -1) return; this.cache[eventName][index] = null; } }
class EventHub { private cache: { [key: string]: Array<(data: unknown) => void> } = {}; // 订阅 on(eventName: string, fn: (data: unknown) => void) { // api on 把函数推进cache数组 this.cache[eventName] = this.cache[eventName] || []; this.cache[eventName].push(fn); } // 发布 emit(eventName: string, data?: unknown) { // emit 把cache里面的fn依次调用 (this.cache[eventName] || []).forEach(fn => fn(data)); } remove(eventName: string, fn: (data: unknown) => void) { // 删除cache中的事件fn let index = indexOf(this.cache[eventName], fn); if (index === -1) return; this.cache[eventName].splice(index, 1); } } function indexOf(arr, item) { if (arr === undefined) return -1; let index = -1; for (let i = 0; i < arr.length; i++) { if (arr[i] === item) { index = i; break; } } return index; } export default EventHub;
测试
import EventHub from "../src/index"; type TestCase = (message: string) => void; const test1: TestCase = message => { const eventHub = new EventHub(); console.assert(eventHub instanceof Object === true, "eventHub 是个对象"); console.log(message); }; const test2: TestCase = message => { const eventHub = new EventHub(); // on emit let called = false; eventHub.on("xxx", y => { called = true; console.assert(y[0] === "点了份外卖"); console.assert(y[1] === "晚上吃了泡面"); }); eventHub.emit("xxx", ["点了份外卖", "晚上吃了泡面"]); console.assert(called); console.log(message); }; const test3: TestCase = message => { const eventHub = new EventHub(); let called = false; const fn1 = () => { called = true; }; eventHub.on("yyy", fn1); eventHub.remove("yyy", fn1); eventHub.emit("yyy"); console.assert(called === false); console.log(message); }; test1("EventHub 可以创建对象"); test2(".on 了之后 .emit,会触发 .on 的函数"); test3(".off 有用");
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。