vue的自定义指令

235 阅读2分钟

这是我参与8月更文挑战的第19天,活动详情查看:8月更文挑战

是什么?

除了核心功能默认内置的指令,Vue也允许注册自定义指令

为什么用?

在 Vue 中,代码复用和抽象的主要形式是组件。然而,有的情况下,你仍然需要对普通 DOM 元素进行底层操作,这时候就会用到自定义指令。\

怎么用?

就像官网举的这个例子,每次进入页面时,我们就需要让某个输入框获取焦点,可以直接用指令去实现它

注册

首先我们得要先进行注册

Vue 自定义指令有全局注册和局部注册两种方式。

全局

这个是全局注册方式:

// 注册一个全局自定义指令 `v-focus` 
Vue.directive('focus', 
    { 
        // 当被绑定的元素插入到 DOM 中时…… 
        inserted: function (el) { 
            // 聚焦元素 
            el.focus() 
        } 
    }
)
局部

这个是局部注册方式:

directives: { 
    focus: { 
        // 指令的定义 
        inserted: function (el) { 
        el.focus() } 
    }
}
使用

可以在模板中任何元素上使用新的 v-focus 属性

<input v-focus>

实现图片懒加载

很多时候,我们需要对图片进行处理,比较多的处理就是图片的懒加载,一个页面如果有很多图片的话,我们可能需要很多计算,对页面的可视区域、图片大小,滚动区域,图片位置等等

这样有点太复杂,而且很多时候我们使用vue的话,都是用v-for循环出来的,对计算这些东西会更复杂,如果我们直接使用自定义指令的话,可以非常方便的对这个图片进行懒加载操作

下面我们就用vue2.x的实现一个简单的。

我这边使用的是全局绑定
directive.js

const lazy = {
    // 利用IntersectionObserver监听el
    observe(el) {
        const io = new IntersectionObserver((entries) => {
            const realSrc = el.dataset.src;
            if (entries[0].isIntersecting) {
                if (realSrc) {
                    el.src = realSrc;
                    el.removeAttribute('data-src');
                }
            }
        });
        io.observe(el);
    }, 
};
const lazyLoad = {
    bind(el,binding) {
        el.setAttribute('data-src', binding.value, width);
    }
    inserted(el) {
        lazy.observe(el);
    }
}

Vue.directive('lazyLoad', lazyLoad);

index文件引入这个文件
index.js

import './directive';

.vue文件
使用的时候直接在dom上设置v-lazyLoad就好了,直接传一个图片的链接

<img v-for="item in imgData" :key="item.id" v-lazyLoad="item.imgUrl"/>

这样,在其他组件上也有类似图片加载的时候,我们就可以不用在写各种计算了,直接一个自定义指令完事。
vue3中指令的函数都变了
在 Vue 3 中

  • created - 新的!在元素的 attribute 或事件侦听器应用之前调用。
  • bind → beforeMount
  • inserted → mounted
  • beforeUpdate:新的!这是在元素本身更新之前调用的,很像组件生命周期钩子。
  • update → 移除!有太多的相似之处要更新,所以这是多余的,请改用 updated
  • componentUpdated → updated
  • beforeUnmount:新的!与组件生命周期钩子类似,它将在卸载元素之前调用。
  • unbind -> unmounted