实现一个自定义event事件,包括on ,off,trigger,once
on监听事件,off取消事件 ,trigger触发事件,once只执行一次
class Event { constructor() { this.handlers = {};//记录所有的事件以及处理函数 /* { click:[fn1,fn2], mouseover: [fn3,fn4] } */ } /** * on 添加事件监听 * @param {事件类型} type * @param {事件处理函数} handler */ on(type, handler, once = false) { if (!this.handlers[type]) { this.handlers[type] = []; } if (!this.handlers[type].includes(handler)) { this.handlers[type].push(handler); handler.once = once; } } /** * off 取消事件监听 * @param {要取消的事件类型} type * @param {要取消的事件函数,如果不传则清除所有} handler */ off(type, handler) { if (this.handlers[type]) { if (handler === undefined) { this.handlers[type] = []; } else { this.handlers[type] = this.handlers[type].filter(f => f != handler); } } } /** * trigger 执行函数 * @param {要执行哪个类型的函数} type * @param {事件对象} eventData * @param {this执行} point */ trigger(type, eventData = {}, point = this) { if (this.handlers[type]) { this.handlers[type].forEach(f => { f.call(point, eventData); if (f.once) { this.off(type, f); } }); } } /** * once 只执行一次 * @param {事件类型} type * @param {要执行的函数} handler */ once(type, handler) { this.on(type, handler, true); } }
测试脚本
let e = new Event; e.on("click", () => { console.log(1); }) e.on("click", () => { console.log(2); }) function fn3() { console.log(3); } e.on("click", fn3); console.log(e);
或者可以使用上一章节的内容进行测试https://www.cnblogs.com/yinping/p/10697083.html
在function函数添加监听函数
(function () { let box = document.querySelector("#box"); let dragbox = new Drag(box); dragbox.on("dragstart", function (e) { //这里不可以使用箭头函数,否则trigger的call方法无效 console.log(e, this); console.log("开始拖拽"); this.style.background = "yellow"; }) dragbox.on("dragend", function (e) { console.log(e, this); this.style.background = "red"; }) dragbox.once("drag", function () { console.log("drag"); }) })()
同时在move,start中添加触发函数
class Drag extends Event { //构造函数 constructor(el) { super(); this.el = el; //鼠标摁下时的元素位置 this.startOffset = {}; //鼠标摁下时的鼠标位置 this.startPoint = {}; let move = (e) => { this.move(e); }; let end = (e) => { document.removeEventListener("mousemove", move); document.removeEventListener("mouseup", end); this.trigger("dragend", e, this.el); }; el.addEventListener("mousedown", (e) => { this.start(e); document.addEventListener("mousemove", move); document.addEventListener("mouseup", end); }) } //摁下时的处理函数 start(e) { let { el } = this; this.startOffset = { x: el.offsetLeft, y: el.offsetTop } this.startPoint = { x: e.clientX, y: e.clientY } this.trigger("dragstart", e, el); } //鼠标移动时的处理函数 move(e) { let { el, startOffset, startPoint } = this; let newPoint = { x: e.clientX, y: e.clientY } let dis = { x: newPoint.x - startPoint.x, y: newPoint.y - startPoint.y, } el.style.left = dis.x + startOffset.x + "px"; el.style.top = dis.y + startOffset.y + "px"; this.trigger('drag', e, el); } }