热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

hookEventofVue

在Vue当中,hooks可以作为一种event,在Vue的源码当中,称之为hookEvent。

在Vue当中,hooks可以作为一种event,在Vue的源码当中,称之为hookEvent。

从一个场景出发

有一个来自第三方的复杂表格组件,表格进行数据更新的时候渲染时间需要1s,由于渲染时间较长,为了更好的用户体验,我希望在表格进行更新时显示一个loading动画。

有一个粗暴的办法是直接修改这个组件的源码,利用beforeUpdate和updated来显示loading,但是这种办法非常不好

  • 这是一个第三方的组件,作者发布组件的时候很可能对代码进行了压缩与构建,使得代码可读性很低,直接修改打包后的代码难度较高
  • 如果有源码的话,可以fork一份自己修改,不过作者不一定会发布源码
  • 无法享受开源社区对这个组件的升级与维护,你需要自己手动维护

总之,修改源码这个方案可行,但是不好,不优雅。
那么,有没有办法,可以声明式的在模板上直接给一个组件注入一个生命周期函数呢?其实是可以的,就是通过hookEvent。

生命周期函数是如何工作的

所谓生命周期函数,就是在某一个特定的时间点调用的函数,所以我们需要关注两件事:1、注册,2、调用。

我们首先从调用开始。

vm._self = vm
initLifecycle(vm)
initEvents(vm)
initRender(vm)
callHook(vm, 'beforeCreate')
initInjections(vm) // resolve injections before data/props
initState(vm)
initProvide(vm) // resolve provide after data/props
callHook(vm, 'created')

上面是一段Vue的源码,可以看出,生命周期函数是通过callHook这个函数去调用的,自然而然,我们去看看callHook函数的代码

export function callHook (vm: Component, hook: string) {
// #7573 disable dep collection when invoking lifecycle hooks
pushTarget()
const handlers = vm.$options[hook] // 选项当中的生命周期函数
const info = `${hook} hook`
if (handlers) {
for (let i = 0, j = handlers.length; i invokeWithErrorHandling(handlers[i], vm, null, vm, info)
}
}
if (vm._hasHookEvent) {
vm.$emit('hook:' + hook)
}
popTarget()
}

所以,callHook(‘created’)在vm._hasHookEvent为true的情况下,会执行$emit(‘hooks:created’),也就是说,一个有着 hook: 特殊前缀的事件,会在对应的生命周期当中执行。其实到这里,我们已经可以大胆推断了:只要使用类似@hooks:created这个形式,就可以从Vue的模板中声明式的注入一个生命周期函数,测试一下,it works.

hasHookEvent

之前的大胆推断,忽略了一个条件,那就是_hasHookEvent必需为true,接下来就去看看这个_hasHookEvent

const hookRE = /^hook:/ // 以hook:开头
Vue.prototype.$on = function (event: string | Array, fn: Function): Component {
const vm: CompOnent= this
if (Array.isArray(event)) {
for (let i = 0, l = event.length; i vm.$on(event[i], fn)
}
} else {
(vm._events[event] || (vm._events[event] = [])).push(fn)
// optimize hook:event cost by using a boolean flag marked at registration
// instead of a hash lookup
if (hookRE.test(event)) {
vm._hasHookEvent = true
}
}
return vm
}

当使用了$on方法监听事件时,如果事件名以 hooks: 作为前缀,那么这个事件会被当做hookEvent,注册事件回调的同时,vm._hasHookEvent会被置为true,当使用callHook调用生命周期函数时,由于_hasHookEvent为true,所以会$emit(‘hooks:xxx’),注册的生命周期函数就会执行。

所以,如果你想给一个Vue组件添加生命周期函数有3个办法:

  • 在Vue选项中添加
  • 在模板中通过@hooks:created这种形式
  • vm.$on(‘hooks:created’, cb)或者vm.$once(‘hooks:created’, cb)

推荐阅读
  • vue使用
    关键词: ... [详细]
  • [大整数乘法] java代码实现
    本文介绍了使用java代码实现大整数乘法的过程,同时也涉及到大整数加法和大整数减法的计算方法。通过分治算法来提高计算效率,并对算法的时间复杂度进行了研究。详细代码实现请参考文章链接。 ... [详细]
  • 模板引擎StringTemplate的使用方法和特点
    本文介绍了模板引擎StringTemplate的使用方法和特点,包括强制Model和View的分离、Lazy-Evaluation、Recursive enable等。同时,还介绍了StringTemplate语法中的属性和普通字符的使用方法,并提供了向模板填充属性的示例代码。 ... [详细]
  • VueCLI多页分目录打包的步骤记录
    本文介绍了使用VueCLI进行多页分目录打包的步骤,包括页面目录结构、安装依赖、获取Vue CLI需要的多页对象等内容。同时还提供了自定义不同模块页面标题的方法。 ... [详细]
  • GreenDAO快速入门
    前言之前在自己做项目的时候,用到了GreenDAO数据库,其实对于数据库辅助工具库从OrmLite,到litePal再到GreenDAO,总是在不停的切换,但是没有真正去了解他们的 ... [详细]
  • 单页面应用 VS 多页面应用的区别和适用场景
    本文主要介绍了单页面应用(SPA)和多页面应用(MPA)的区别和适用场景。单页面应用只有一个主页面,所有内容都包含在主页面中,页面切换快但需要做相关的调优;多页面应用有多个独立的页面,每个页面都要加载相关资源,页面切换慢但适用于对SEO要求较高的应用。文章还提到了两者在资源加载、过渡动画、路由模式和数据传递方面的差异。 ... [详细]
  • 用Vue实现的Demo商品管理效果图及实现代码
    本文介绍了一个使用Vue实现的Demo商品管理的效果图及实现代码。 ... [详细]
  • Ihaveaworkfolderdirectory.我有一个工作文件夹目录。holderDir.glob(*)>holder[ProjectOne, ... [详细]
  • VUE中引用路径的配置
    在vue项目开发中经常引用JS、CSS、IMG文件。当项目较大时文件层级很多,导致路径很长,我们可以通过在bulidwebpack.base.conf.js设置简便的引用路径一、 ... [详细]
  • 【Vue基础】监听属性watch
    Vue监听属性是watch,我们可以通过watch来响应数据的变化。代码示例: ... [详细]
  • 本文涉及源码版本为2.6.9准备工作down一份Vue源码,从package.json入手,找我们需要的代码1、package.json中的scripts,build:nodesc ... [详细]
  • 在Android开发中,使用Picasso库可以实现对网络图片的等比例缩放。本文介绍了使用Picasso库进行图片缩放的方法,并提供了具体的代码实现。通过获取图片的宽高,计算目标宽度和高度,并创建新图实现等比例缩放。 ... [详细]
  • 本文介绍了[从头学数学]中第101节关于比例的相关问题的研究和修炼过程。主要内容包括[机器小伟]和[工程师阿伟]一起研究比例的相关问题,并给出了一个求比例的函数scale的实现。 ... [详细]
  • Python正则表达式学习记录及常用方法
    本文记录了学习Python正则表达式的过程,介绍了re模块的常用方法re.search,并解释了rawstring的作用。正则表达式是一种方便检查字符串匹配模式的工具,通过本文的学习可以掌握Python中使用正则表达式的基本方法。 ... [详细]
  • python中安装并使用redis相关的知识
    本文介绍了在python中安装并使用redis的相关知识,包括redis的数据缓存系统和支持的数据类型,以及在pycharm中安装redis模块和常用的字符串操作。 ... [详细]
author-avatar
雪中磐石
人生只有走出来的美丽,没有等出来的辉煌。
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有