欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Vue.directive() 封装DOM操作

程序员文章站 2022-03-30 13:13:11
...

这篇文章是关于Vue Directive的介绍,后面会介绍一个使用的小例子。

1.Vue Directive的简介

directive在Vue中十分常见,Vue提供的许多指令如 v-on 、 v-show 使得Vue的功能更加强大,可是仍然有一些操作指令是Vue没有提供的,不过Vue提供了自定义directive的属性方法来满足这一需求。其实,Vue Directive就是一种特殊的HTML元素属性。

Vue提供了两中注册方法,一种是全局注册,在Vue.directive中定义组件的名字和相关指令操作

Vue.directive('指令的名字', {
        //一些option,提供许多hook function 定义directive的具体操作,如inserted、bind...
        inserted: function (el) {
            //指令插入元素后的操作
        }
    })

另一种是局部注册,在对应组件的directives属性里注册组件名,传入指令的option对象

directives: {
  name: {  //指令的名字
    // 指令的定义
  }
}

在定义时,Vue提供了许多hook function,例如 inserted 、bind等,bind是只会在绑定的对象节点被插入父节点时调用一次的函数,与unbind相对应,unbind将也只会在元素被解除绑定时调用。

Vue.directive('指令的名字', {
    bind: function(el, binding, vnode,oldVnode) {
        //绑定指令时调用
    },
    unbind: function() {
        //指令解除绑定时调用
    }
})

bind函数中的binding,是一个包含了众多属性的对象,关于它的所有的性质的介绍可以自行查看官方文档 ,比较常用的一个属性binding.value,与其对应的是在指令中传入的字符串,Vue会自动解析这个值并执行。与此相对应的另一个属性binding.expression里的值则就是原始值。

2.为什么要使用VueDirective

有同学可能会问,我在Vue实例的方法中写DOM操作不可以吗?那为什么使用Vue Directive来封装DOM操作呢?

这是因为,为了实现View和ViewModel的分离,我们必须封装DOM操作,View层负责页面上的显示,ViewModel层负责改变操作数据,由于Vue是数据驱动的,属于ViewModel层,那么其中就不应该出现View层上的DOM操作,而且,使用Vue Directive是和DOM元素的创建、销毁绑定的。Vue Directive的生命周期方法能让我们更优雅的去在合适的时机进行DOM的操作。而在ViewModel里则没有和DOM元素对应的方法。因为Vue Directive是属于View层面的,所以DOM操作应该被封装在Vue Directive里而不是出现在Vue实例中。

3. Demo:自制scroll指令

接下来看一个具体使用Vue Directive封装DOM操作的scroll事件的例子,在这个例子中需求是在用户滑动到页面的底端时请求更多数据。

3.1 首先将DOM操作封装到指令的option中

let scrollCallback = function(callback) {
    if (document.body.scrollHeight < 1000) {
        return
    }
    if (document.body.scrollHeight - window.scrollY - 100  document.body.clientHeight) {
        callback()
    }
}
let callBackWarpped // 新变量 保存引用
export default {
    bind: function(el, binding, vnode) {
        callBackWarpped =  scrollCallback.bind({}, binding.value)
        window.addEventListener("scroll", callBackWarpped)
    },
    unbind: function() {
        window.removeEventListener("scroll", callBackWarpped)
    }
}

首先需要监听页面的滚动,如果触发了scroll事件那么就要执行回调函数,由于在解除绑定的时候也要将监听事件从window上移除,所以必须给回调函数取一个名字,例如本例中的scrollCallback,并在unbind函数中将监听移除,因此scrollCallBack的具体定义应在对象外执行。

并且回调函数应该在页面滑动到底端时才执行,也就是说不能马上执行 binding.value,怎样实现这一点呢?可以将bind.value作为函数的参数传进scrollCallback,先判断,然后在满足条件时调用binding.value 。

3.2 在组件里import一个directive

import scrollDirective from '../../directives/scroll'
//import 指令的option的名字 from '指令option的位置'

使用import将directive引入组件。

3.3 在组件的directives属性中注册这个指令,值为scroll

directives: {
    scroll: scrollDirective
    //指令的名字:指令的option的名字
}

将引入的组件注册到scroll上。

3.4 在相应元素上加上directive指令

v-scroll = "onScroll"
//v-'指令的名字' = "回调函数"

用注册好的名字在相对应的元素上加入指令 。

3.5 编写directive指令中的函数

最后在method中编写onScroll函数,也就是上文中对应的binding.value,在这个函数中我们将会请求更多数据,而Vue就会执行相应v-scroll中的值。

具体的Demo请戳这里

相关标签: # vue全局API vue