实现 VUE 中 MVVM - step7 - Event

栏目: 编程工具 · 发布时间: 7年前

内容简介:在标准浏览器中,我们经常使用:在我看来,一个事件是一种行为(或情况),当发生这种行为(或情况)时,我们要去做的事,比如今天下雨了,那我就得去找伞;闹钟响了,那我就得起床等等。仔细看这些情况,归结到代码中,无非就是一个行为(或情况)的名称,和一些列的动作,而在

在标准浏览器中,我们经常使用: addEventListener 来为一个 DOM 添加一个事件( clickmousemovetap 等)。

在我看来,一个事件是一种行为(或情况),当发生这种行为(或情况)时,我们要去做的事,比如今天下雨了,那我就得去找伞;闹钟响了,那我就得起床等等。

仔细看这些情况,归结到代码中,无非就是一个行为(或情况)的名称,和一些列的动作,而在 js 中动作就是 function ,一系列的动作就是一个函数的集合。

实现

如上所说,我们把事件抽象成一个类

类下属性 & 方法

  • _events 一个对象 {key: eventName, value: Array<Function,Function...>}
  • $on(eventName, func) 添加具体事件的处理函数
  • $off(eventName) 取消事件处理函数
  • $emit(eventName, data1, data2, ...) 用于触发事件
  • $once(eventName, func) 设置仅触发一次的事件

ok 根据我们的构想,在来看这个实现好的 Event

let uid = 0

export class Event {
    constructor() {
        this.id = ++uid
        this._events = {}
    }

    $on(eventName, fn) {
        let ctx = this;
        // 若 _events 对象下无对应事件名,则新建一个数组,然后将处理函数推入数组
        if(!ctx._events[eventName]){
            ctx._events[eventName] = []
        }
        ctx._events[eventName].push(fn)
        return ctx
    }

    $once(eventName, fn) {
        let ctx = this

        function on() {
            // 先取消,然后触发,确保仅触发一次
            ctx.$off(eventName, on)
            fn.apply(ctx, arguments)
        }

        on.fn = fn
        ctx.$on(eventName, on)
        return object
    }

    $off(eventName) {
        let ctx = this
        const cbs = ctx._events[eventName]
        if (cbs) {
            // 取消置空即可
            ctx._events[eventName] = null
        }
        return ctx
    }

    $emit(eventName, ...args) {
        let ctx = this
        let cbs = ctx._events[eventName]
        if (cbs) {
            cbs.forEach(func => func.apply(ctx, args))
        }
        return ctx
    }

}
复制代码

一个简单的事件管理的类便实现好了,让我们来测试一下:

import {Event} from "./Event";

let eventTest = new Event()

eventTest.$on('testEvent', function (event) {
    console.log('测试事件添加,传入参数为' + event)
})

eventTest.$emit('testEvent', '事件触发成功')
// 测试事件添加,传入参数为事件触发成功

eventTest.$emit('testEvent', '事件再次触发成功')
// 测试事件添加,传入参数为事件再次触发成功

eventTest.$off('testEvent')

eventTest.$emit('testEvent', '事件取消,不会有输出')
// 无输出

eventTest.$once('testOnce', function (event) {
    console.log('事件仅仅触发一次,传入参数为' + event)
})

eventTest.$emit('testOnce', '事件触发成功')
// 事件仅仅触发一次,传入参数为事件触发成功

eventTest.$emit('testOnce', '事件取消,不会有输出')
// 无输出
复制代码

ok 一个简易的事件管理实现了,由于这节内容与上几节关系不大,所以这里再次说下测试代码的运行方式:

  1. node 环境 8.11.1 往上,不然不能够支持 import 语法
  2. 为了不转码支持 import 语法,文件后缀为 .mjs
  3. 进入到 test.mjs 所在目录命令行运行: node --experimental-modules test.mjs 即可

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

Web Form Design

Web Form Design

Luke Wroblewski / Rosenfeld Media / 2008-5-2 / GBP 25.00

Forms make or break the most crucial online interactions: checkout, registration, and any task requiring information entry. In Web Form Design, Luke Wroblewski draws on original research, his consider......一起来看看 《Web Form Design》 这本书的介绍吧!

图片转BASE64编码
图片转BASE64编码

在线图片转Base64编码工具

MD5 加密
MD5 加密

MD5 加密工具