vue自定義指令

1.Vue自定義指令

除了核心功能默認(rèn)內(nèi)置的指令 (v-modelv-show等),Vue允許我們注冊(cè)自定義指令用于元素上。

當(dāng)我們需要對(duì)普通 DOM 元素進(jìn)行底層操作時(shí),就可以用到用到自定義指令。

2. 鉤子函數(shù):

配置對(duì)象中包含一下幾個(gè)鉤子函數(shù)(均為可選值):

鉤子函數(shù) 描述

  • bind: 只調(diào)用一次,指令第一次綁定到元素時(shí)調(diào)用。在這里可以進(jìn)行一次性的初始化設(shè)置。
  • inserted(常用): 被綁定元素插入父節(jié)點(diǎn)時(shí)調(diào)用 (僅保證父節(jié)點(diǎn)存在,但不一定已被插入文檔中)。
  • update: 所在組件的 VNode 更新時(shí)調(diào)用,但是可能發(fā)生在其子 VNode 更新之前。指令的值可能發(fā)生了改變,也可能沒有。但是你可以通過比較更新前后的值來忽略不必要的模板更新 (詳細(xì)的鉤子函數(shù)參數(shù)見下)。
  • componentUpdated: 指令所在組件的 VNode 及其子 VNode 全部更新后調(diào)用。
  • unbind: 只調(diào)用一次,指令與元素解綁時(shí)調(diào)用。

3. 鉤子函數(shù)參數(shù):

指令鉤子函數(shù)會(huì)被傳入以下參數(shù):

  • el:指令所綁定的元素,可以用來直接操作 DOM。

  • binding:一個(gè)對(duì)象,包含以下 property:

    • name:指令名,不包括 v- 前綴。

    • value:指令的綁定值,例如:v-my-directive="1 + 1" 中,綁定值為 2。

    • oldValue:指令綁定的前一個(gè)值,僅在 update 和 componentUpdated 鉤子中可用。無論值是否改變都可用。

    • expression:字符串形式的指令表達(dá)式。例如 v-my-

      directive="1 + 1" 中,表達(dá)式為 "1 + 1"。

    • arg:傳給指令的參數(shù),可選。例如 v-my-directive:foo 中,參數(shù)為 "foo"。

    • modifiers:一個(gè)包含修飾符的對(duì)象。例如:v-my-directive.foo.bar 中,修飾符對(duì)象為 { foo: true, bar: true }。

  • vnode:Vue 編譯生成的虛擬節(jié)點(diǎn)(這個(gè)參數(shù)本人沒有用過,有用過的大佬請(qǐng)指點(diǎn)一下)

  • oldVnode:上一個(gè)虛擬節(jié)點(diǎn),僅在 update 和componentUpdated 鉤子中可用。

4.全局注冊(cè)

全局注冊(cè)自定義指令是將我們的自定義指令掛載到vue實(shí)例上的,在項(xiàng)目中都可以使用。

  • 全局指令注冊(cè)方法為:Vue.directive(dName, options) 傳入兩個(gè)參數(shù)
  • 分別是 指令名配置對(duì)象
  • 創(chuàng)建完之后,我們就可以使用 v-指令名 的方式加在元素上,以使自定義指令生效

4.1使 input 進(jìn)入獲取焦點(diǎn)

import Vue from 'vue'
// 注冊(cè)一個(gè)全局自定義指令 `v-focus`
Vue.directive('focus', {
  // 當(dāng)被綁定的元素插入到 DOM 中時(shí)……
  inserted: function (el) {
    // 聚焦元素
    el.focus()
  }
})

  • 使用
<input v-focus />

5.局部注冊(cè)

用法與 全局 注冊(cè)是一樣的, 只是寫法稍有不同

進(jìn)行局部注冊(cè)時(shí), 我們的組件中可以接收一個(gè)directives選項(xiàng),

其中,鍵為指令名 值為配置對(duì)象
  • 注冊(cè)
export default{
  data(){
    return { ... }
  },
  directives:{
        focus:{
        inserted: function (el) {
          //element-ui中 el-input外層是div, 里面包裹的才是input, 因此用在 el-input上的話,要讓el-input里的子元素聚焦
          //增加判斷可以使我們的v-focus通用性更強(qiáng)
          el.tagName == 'INPUT' ? el.focus() : el.children[0].focus
        }
      }
  }
}

  • 使用
<input v-focus></input>

6.項(xiàng)目用到的自定義指令

6.1 防抖函數(shù):

點(diǎn)擊按鈕過快可能多次請(qǐng)求接口,用自定義指令做全局的函數(shù)防抖

  • 在main.js中 全局注冊(cè)一個(gè)自定義指令:
/**防抖函數(shù)
 * @el :指令所綁定的元素,可以用來直接操作 DOM。
 * @binding :綁定的事件或者值
 */
Vue.directive('debounce', {
  inserted(el, binding) {
    let timer = null
    el.addEventListener('click', () => {
      if (timer) {
        clearTimeout(timer)
      }
      timer = setTimeout(() => {
        binding.value();
        timer = null;
      }, 500)
    })
  }
})
  • 使用
<button v-debounce="send">發(fā)送</button>

6.2節(jié)流函數(shù)

觸發(fā)高頻事件后,n秒內(nèi)函數(shù)函數(shù)只會(huì)執(zhí)行一次。

應(yīng)用場(chǎng)景: search搜索聯(lián)想,用戶在不斷輸入值時(shí)

  • 在main.js中 全局注冊(cè)一個(gè)自定義指令
/**節(jié)流函數(shù)
 * @el :指令所綁定的元素,可以用來直接操作 DOM。
 * @binding :綁定的事件或者值
 */
Vue.directive('throttle', {
  inserted(el, binding) {
    let timer = null
    el.addEventListener('change', () => {
      if (!timer) {
        timer = setTimeout(() => {
          clearTimeout(timer)
          binding.value();
          timer = null;
        }, 100)
      }
    })

  }
})
  • 使用
<input v-throttle="changeSearch" />
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容