浅谈vue钩子函数自定义指令
Updated:
一、vue中自定义指令
1. 什么是自定义指令?
除了使用 Vue 提供的内置指令之外,我们可以自定义一些自己的指令,来实现业务操作。
2. 什么时候需要自定义指令?
当你需要不可避免的操作 DOM 的时候,使用自定义指令来解决
3. 如何注册和使用自定义指令?
1. 注册
- 全局注册,在任何组件中都可以使用全局注册自定义指令
- 局部注册,只能在当前组件使用该指令
如果需要在多个不同的组件中使用该指令,则把它定义为全局的
非通用的,不需要多次使用的指令我们定义到局部
2. 使用
例:注册一个自定义指令focus1
2
3
4
5
6
7
8// 注册一个全局自定义指令 `v-focus`
Vue.directive('focus', {
// 当被绑定的元素插入到 DOM 中时……
inserted: function (el) {
// 聚焦元素
el.focus()
}
})
注册一个全局自定义指令 v-focus
使用 声明Vue.directive()
参一是指令的名字
- 指令的名字随便起,但是在使用的时候务必加上 v- 前缀,所以我们在其名字的时候就不要加 v- 前缀
- 如果是驼峰命名法的名称,则在使用的时候需要把驼峰转为小写使用 - 连接起来(例:myFocus 为 v-my-focus)
参二是钩子函数
下面我们将简单介绍钩子函数
二、钩子函数
1. 简介钩子函数
vue中提供了5个钩子函数
- bind:只调用一次,指令第一次绑定到元素时调用。在这里可以进行一次性的初始化设置。(bind 中拿不到父元素)
- inserted:被绑定元素插入父节点时调用 (仅保证父节点存在,但不一定已被插入文档中)。如果你需要操作作用指令的父元素,则最起码写到这个 inserted 中
- update:所在组件的 VNode 更新时调用,但是可能发生在其子 VNode 更新之前。指令的值可能发生了改变,也可能没有。但是你可以通过比较更新前后的值来忽略不必要的模板更新 (详细的钩子函数参数见下)。
- componentUpdated:指令所在组件的 VNode 及其子 VNode 全部更新后调用。
- unbind:只调用一次,指令与元素解绑时调用。
每个钩子函数都可以接收两个参数:
- el 作用该指令的 DOM 对象
- binding 一个对象,可以获取指令的值等信息
注意:
- bind 和 inserted 的相同之处是一上来都执行一次,以后再也不会执行,异同之处在于,bind 拿不到父元素,inserted 可以拿到父元素
- update 和 componentUpdated 只有在指令的绑定的值发生更新的时候才会触发调用
- update 和 componentUpdated 的区别是:
update 中获取的是更新的之前的指令所在的 DOM 内容
componentUpdated 获取的是更新之后的最新 DOM 内容
update 拿到的是数据改变视图之前的视图内容
componentUpdated 拿到的是数据改变视图之后的视图内容
也就是说如果你需要获取数据改变视图之前的内容,则把代码写到 update 中
如果需要获取数据改变视图之后的内容,则把代码写到 componentUpdated 里面
例: 模拟v-show实现1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30<div id="app">
<!-- <input type="text" v-focus> -->
<div class="box" v-my-show="seen">{{ seen }}</div>
</div>
Vue.directive('my-show', {
bind (el, binding) {
inserted (el, binding) {
console.log('my-show inserted')
if (binding.value) {
el.style.display = 'block'
} else {
el.style.display = 'none'
}
},
update (el, binding) {
// console.log('my-show update', el, binding)
console.log('my-show update', el.innerHTML)
if (binding.value) {
el.style.display = 'block'
} else {
el.style.display = 'none'
}
},
componentUpdated (el, binding) {
console.log('my-show componentUpdated', el.innerHTML)
},
unbind () {
console.log('my-show unbind')
}
})
2. 函数简写
在很多时候,你可能想在 bind 和 update 时触发相同行为,而不关心其它的钩子。比如这样写:1
2
3Vue.directive('color-swatch', function (el, binding) {
el.style.backgroundColor = binding.value
})
我只关心 bind 和 inserted,所以可以这样简写1
2
3
4
5
6
7
8
9Vue.directive('my-show', function (el, binding) {
// console.log('my-show update', el, binding)
// console.log('my-show update', el.innerHTML)
if (binding.value) {
el.style.display = 'block'
} else {
el.style.display = 'none'
}
})
模拟v-bind动态绑定属性值
1 | <body> |
模拟v-bind绑定class
1 | <style> |