电脑知识|欧美黑人一区二区三区|软件|欧美黑人一级爽快片淫片高清|系统|欧美黑人狂野猛交老妇|数据库|服务器|编程开发|网络运营|知识问答|技术教程文章 - 好吧啦网

您的位置:首頁技術(shù)文章
文章詳情頁

詳解Vue自定義指令及使用

瀏覽:4日期:2022-09-30 08:13:20
一、什么是指令

學(xué)習(xí) vue 的時候肯定會接觸指令,那么什么是指令呢?

在 vue 中提供了一些對于頁面和數(shù)據(jù)更為方便的輸出,這些操作就叫做指令,以 v-xxx 表示,比如 html 頁面中的屬性 <div v-xxx ></div>

比如在 angular 中 以 ng-xxx 開頭的就叫做指令

指令中封裝了一些 DOM 行為,結(jié)合屬性作為一個暗號,暗號有對應(yīng)的值,根據(jù)不同的值,會進(jìn)行相關(guān) DOM 操作的綁定,即可以進(jìn)行一些模板的操作

vue 中常用的一些內(nèi)置 v- 指令 v-text:元素的 innerText 屬性,只能用在雙標(biāo)簽中, 和{{ }}效果是一樣的,使用較少 v-html:元素的 innerHTML,其實(shí)就是給元素的 innerHTML 賦值 v-show:元素的顯示與隱藏,基于 css 樣式的切換。如果確定要隱藏,會給元素的 style 加上display: none v-if:元素的插入和移除操作,相當(dāng)于對元素的銷毀和創(chuàng)建。如果表達(dá)式的值為 false,會留下一個 <!----> 作為標(biāo)記,若未來 v-if 的值是 true 了,就在這里插入元素(如果 if 有 else 就不要單獨(dú)留坑了)。 v-else-if:前一個相鄰元素必須有 v-if 或 v-else-if v-else:前一個相鄰元素必須有 v-if 或 v-else-if,如果 v-if 和 v-else-if 都有對應(yīng)的表達(dá)式,則 v-else 可以直接寫 v-for:用于循環(huán)渲染一組數(shù)據(jù)(數(shù)組或?qū)ο?。必須使用特定語法:v-for='alias in expression'。注:當(dāng) v-for 和 v-if 同處于一個節(jié)點(diǎn)時,v-for 的優(yōu)先級比 v-if 更高。即 v-if 將運(yùn)行在每個 v-for循環(huán)中 v-on:主要用來監(jiān)聽 dom 時間,然后執(zhí)行一些操作。簡寫為【@】 v-model:用于 input/textarea 等表單控件上創(chuàng)建雙向數(shù)據(jù)綁定。 v-bind:動態(tài)的綁定一個或多個屬性,常用于綁定 class,style,href 等。 v-once:組件和元素只渲染一次,當(dāng)數(shù)據(jù)發(fā)生變化,也不會重新渲染。v-if 和 v-show 的對比 v-if 是真正的條件渲染,因?yàn)樗鼤_保在切換過程中條件塊內(nèi)的事件監(jiān)聽器和子組件適當(dāng)?shù)谋讳N毀和重建。 v-if 也是惰性的,如果在初始渲染時條件為假,則什么也不做,直到條件第一次為真時,才會開始渲染條件塊。 相比之下 v-show 就簡單的多,不管初始條件是什么,元素總是會被渲染,并且只是簡單的基于 css 進(jìn)行切換。

一般來說,v-if 有更高的切換開銷,而 v-show 有更高的初始渲染開銷。因此,如果需要非常頻繁的切換,則使用 v-show 較好,如果在運(yùn)行時條件很少改變,則使用 v-if 較好。

在實(shí)際的開發(fā)過程中,可能這些內(nèi)置指令并不能滿足所有的需求,或者說想為元素附件一些特別的功能。這時候,就需要用到 Vue 給我們提供的一個強(qiáng)大又靈活的功能「 自定義指令 」。

官方api 文檔里有這么一句話:對普通 DOM 元素進(jìn)行底層操作,這時候就會用到自定義指令。也就是說自定義指令解決的問題或者說使用場景是對普通 DOM 元素進(jìn)行底層操作,所以我們不能盲目的胡亂的使用自定義指令。

二、自定義指令的鉤子函數(shù)

Vue 提供了自定義指令的5個鉤子函數(shù):

bind:指令第一次綁定到元素時調(diào)用,只執(zhí)行一次。在這里可以進(jìn)行一次性的初始化設(shè)置。 inserted:被綁定的元素,插入到父節(jié)點(diǎn)的 DOM 中時調(diào)用(僅保證父節(jié)點(diǎn)存在)。 update:組件更新時調(diào)用。 componentUpdated:組件與子組件更新時調(diào)用。 unbind:指令與元素解綁時調(diào)用,只執(zhí)行一次。

注意:

1.除 update 與 componentUpdated 鉤子函數(shù)之外,每個鉤子函數(shù)都含有 el、binding、vnode 這三個參數(shù)

2.在每個函數(shù)中,第一個參數(shù)永遠(yuǎn)是 el, 表示被綁定了指令的那個 dom 元素,這個el 參數(shù),是一個原生的 JS 對象,所以 Vue 自定義指令可以用來直接和 DOM 打交道

3.binding 是一個對象,它包含以下屬性:name、value、oldValue、expression、arg、modifiers

4.oldVnode 只有在 update 與 componentUpdated 鉤子中生效

5.除了 el 之外,binding、vnode 屬性都是只讀的

鉤子函數(shù)說白了也就是生命周期,即當(dāng)一個指令綁定到一個元素上時,這個指令內(nèi)部有5個生命周期事件函數(shù)。接下來創(chuàng)建一個案例來看看這幾個鉤子函數(shù)的觸發(fā)情況:

<p v-test>這是一段文字</p>​export default { ... ... directives: {test: { bind () {console.log(’bind’) }, inserted () {console.log(’inserted’) }, update () {console.log(’update’) }, componentUpdated () {console.log(’componentUpdated’) }, unbind () {console.log(’unbind’) }} }}

結(jié)果:

詳解Vue自定義指令及使用

頁面渲染時,觸發(fā)了 bind 和inserted 函數(shù)。那么另外三個鉤子函數(shù)什么時候會觸發(fā)呢?

關(guān)于 update 的官方解釋:

update:所在組件的 VNode 更新時調(diào)用,但是可能發(fā)生在其子 VNode 更新之前。指令的值可能發(fā)生了改變,也可能沒有。但是你可以通過比較更新前后的值來忽略不必要的模板更新 (詳細(xì)的鉤子函數(shù)參數(shù)見下)。

有點(diǎn)疑惑,‘ 所在組件的 VNode ’ 是指當(dāng)前綁定了該指令的 dom 元素嗎?如果是的話,是不是只要當(dāng)前元素的狀態(tài)發(fā)生了變化就會觸發(fā) update 呢?如下通過 v-show 來切換元素顯示隱藏:

<p v-test v-show='show'>這是另外一段文字</p><button @click='show = !show'>toggle</button>export default { data () { return { show: true } }}

默認(rèn)還是觸發(fā) bind 和inserted ,當(dāng)點(diǎn)擊按鈕切換元素的 display 時,結(jié)果如下:

詳解Vue自定義指令及使用

即:改變元素的樣式的時候觸發(fā)了 update 和componentUpdated 函數(shù)。如果使用 v-if 會觸發(fā)哪個事件呢?

<p v-test v-if='show'>這是另外一段文字</p><button @click='show = !show'>toggle</button>

結(jié)果:

詳解Vue自定義指令及使用

發(fā)現(xiàn) unbind 被觸發(fā),因?yàn)?v-if 是刪除或者重建 dom 元素,當(dāng)指令綁定的元素被銷毀時,會觸發(fā)指令的 unbind 事件,新建顯示仍是觸發(fā) bind 和inserted 。

總結(jié):

bind():當(dāng)指令綁定在 HTML 元素上時觸發(fā) inserted():當(dāng)指令綁定的元素插入到父節(jié)點(diǎn)中的時候觸發(fā) update():當(dāng)指令綁定的元素狀態(tài)/樣式、內(nèi)容(這里指元素綁定的 vue 數(shù)據(jù)) 發(fā)生改變時觸發(fā) componentUpdated():當(dāng) update() 執(zhí)行完畢之后觸發(fā) unbind():當(dāng)指令綁定的元素從 dom 中刪除時觸發(fā)

舉幾個應(yīng)用場景的栗子

1、輸入框自動獲取焦點(diǎn)(官方示例)。

2、點(diǎn)擊下拉菜單以外的區(qū)域隱藏菜單。

3、輸入的郵箱、電話的校驗(yàn)。

上面這幾個場合,在做項(xiàng)目的時候可以用其他方法代替,但是 vue 自定義指令能做到一處定義,全局調(diào)用,使得代碼簡潔高效,更便于維護(hù)。

指令的注冊方式和「過濾器」「混入」「組件」注冊的方式一樣都分為兩種:一是全局注冊,二是局部注冊。

三、全局指令

// 給元素添加隨機(jī)背景<div v-bgcolor></div> Vue.directive(’bgcolor’, { bind: function(el, binding, vnode) {el.style.backgroundColor = '#' + Math.random().toString(16).slice(2,8); }})

注意:在定義的時候,指令的名稱前面不需要加 v- 前綴,在調(diào)用的時候,必須在指定的名稱前加上 v-前綴來進(jìn)行調(diào)用

四、局部指令

// 和data, methods同級methods: {},directives: { bgcolor: { bind: function(el, binding) { el.style.backgroundColor = '#' + Math.random().toString(16).slice(2,8);} }}

我個人更傾向于使用全局注冊的方式,因?yàn)榧热灰呀?jīng)使用了自定義指令,應(yīng)該是通用的可復(fù)用的。所以提供整個項(xiàng)目使用的指令才更有價值,而不僅僅只限于某個組件內(nèi)部。如果單一地方使用直接把功能摟出來就行了,何必費(fèi)這力氣。

五、帶參數(shù)的自定義指令

<div v-bgcolor=’{color: ’orange’}’></div>Vue.directive(’bgcolor’, { bind: function(el, binding) {el.style.backgroundColor = binding.value.color; }})六、函數(shù)簡寫

如果想在 bind 和 update 時觸發(fā)相同行為,而不關(guān)心其它的鉤子,可以這樣寫:

// 全局Vue.directive(’bgcolor’, function (el, binding) { el.style.backgroundColor = binding.value})// 局部directives: { bgcolor: (el, binding) => {el.style.backgroundColor = binding.value }}七、應(yīng)用實(shí)例

熟悉指令的創(chuàng)建方式與參數(shù)之后,我們就用它來創(chuàng)建兩個實(shí)際案例。

通過指令來實(shí)現(xiàn)點(diǎn)擊空白處子菜單隱藏的功能,具體代碼如下:

// clickOutside.jsexport default { bind (el, binding) {const self = {} // 定義一個私有變量,方便在unbind中可以解除事件監(jiān)聽self.documentHandler = (e) => { if (el.contains(e.target)) { // 這里判斷綁定的元素是否包含點(diǎn)擊元素,如果包含則返回return false } if (binding.value) { // 判斷指令中是否綁定了值binding.value(e) // 如果綁定了函數(shù)則調(diào)用那個函數(shù),此處 binding.value就是handleClose方法 } return true}document.addEventListener(’click’, self.documentHandler) }, unbind (el) {// 解除事件監(jiān)聽document.removeEventListener(’click’, self.documentHandler)delete self.documentHandler }}

在組件中使用:

<template> <div><div v-show='isShow' v-clickoutside='handleClickOutside' @click='showOrHide'> 子菜單 ... </div> </div></template>​<script> import clickoutside from ’./js/clickOutside’export default {... ...directives: { clickoutside},data() { return {isShow: true, };},methods: { handleOutsideClick () {this.isShow = false }} }</script>

自定義指令來優(yōu)化圖片的加載:圖片在加載過程中,未加載完成時使用灰色背景占位,圖片加載完后直接顯示

<template> <div><!-- 參數(shù)不可以直接填寫url地址--><img v-imgUrl=’url’ /> </div></template>​<script> export default {data () { return {url: ’../src/assets/logo.png’ }} }</script>// 全局注冊Vue.directive(’imgUrl’, function (el, binding) { el.style.backgroundColor = ’#FEFEFE’ //設(shè)置背景顏色 var img = new Image() img.src = binding.value // binding.value 指令后的參數(shù) img.onload = function () {el.style.backgroundColor = ’’el.src = binding.value }})

以上就是詳解Vue自定義指令及使用的詳細(xì)內(nèi)容,更多關(guān)于Vue的資料請關(guān)注好吧啦網(wǎng)其它相關(guān)文章!

標(biāo)簽: Vue
相關(guān)文章:
主站蜘蛛池模板: 百方网-百方电气网,电工电气行业专业的B2B电子商务平台 | 东莞市踏板石餐饮管理有限公司_正宗桂林米粉_正宗桂林米粉加盟_桂林米粉加盟费-东莞市棒子桂林米粉 | 包装设计公司,产品包装设计|包装制作,包装盒定制厂家-汇包装【官方网站】 | 精密机械零件加工_CNC加工_精密加工_数控车床加工_精密机械加工_机械零部件加工厂 | 天然气分析仪-液化气二甲醚分析仪|传昊仪器 | 美能达分光测色仪_爱色丽分光测色仪-苏州方特电子科技有限公司 | 机构创新组合设计实验台_液压实验台_气动实训台-戴育教仪厂 | 打包钢带,铁皮打包带,烤蓝打包带-高密市金和金属制品厂 | 交流伺服电机|直流伺服|伺服驱动器|伺服电机-深圳市华科星电气有限公司 | LED太阳能中国结|发光红灯笼|灯杆造型灯|节日灯|太阳能灯笼|LED路灯杆装饰造型灯-北京中海轩光电 | 集装箱展厅-住人集装箱住宿|建筑|房屋|集装箱售楼处-山东锐嘉科技工程有限公司 | 大立教育官网-一级建造师培训-二级建造师培训-造价工程师-安全工程师-监理工程师考试培训 | 智慧消防-消防物联网系统云平台 智能化的检漏仪_气密性测试仪_流量测试仪_流阻阻力测试仪_呼吸管快速检漏仪_连接器防水测试仪_车载镜头测试仪_奥图自动化科技 | 浙江筋膜枪-按摩仪厂家-制造商-肩颈按摩仪哪家好-温州市合喜电子科技有限公司 | 深圳办公室装修,办公楼/写字楼装修设计,一级资质 - ADD写艺 | 双舌接地线-PC68数字式高阻计-ZC36|苏海百科 | 特种阀门-调节阀门-高温熔盐阀-镍合金截止阀-钛阀门-高温阀门-高性能蝶阀-蒙乃尔合金阀门-福建捷斯特阀门制造有限公司 | Q361F全焊接球阀,200X减压稳压阀,ZJHP气动单座调节阀-上海戎钛 | 光纤测温-荧光光纤测温系统-福州华光天锐光电科技有限公司 | 青海电动密集架_智能密集架_密集架价格-盛隆柜业青海档案密集架厂家 | 山东led显示屏,山东led全彩显示屏,山东LED小间距屏,临沂全彩电子屏-山东亚泰视讯传媒有限公司 | 深圳宣传片制作_产品视频制作_深圳3D动画制作公司_深圳短视频拍摄-深圳市西典映画传媒有限公司 | 上海APP开发-APP制作-APP定制开发-上海APP开发制作公司-咏熠科技 | 真空干燥烘箱_鼓风干燥箱 _高低温恒温恒湿试验箱_光照二氧化碳恒温培养箱-上海航佩仪器 | 鑫铭东办公家具一站式定制采购-深圳办公家具厂家直销 | 青州开防盗门锁-配汽车芯片钥匙-保险箱钥匙-吉祥修锁店 | 高压负荷开关-苏州雷尔沃电器有限公司| 土壤养分检测仪|土壤水分|土壤紧实度测定仪|土壤墒情监测系统-土壤仪器网 | 东莞喷砂机-喷砂机-喷砂机配件-喷砂器材-喷砂加工-东莞市协帆喷砂机械设备有限公司 | 整车VOC采样环境舱-甲醛VOC预处理舱-多舱法VOC检测环境仓-上海科绿特科技仪器有限公司 | 脉冲除尘器,除尘器厂家-淄博机械 | 成都治疗尖锐湿疣比较好的医院-成都治疗尖锐湿疣那家医院好-成都西南皮肤病医院 | 深圳快餐店设计-餐饮设计公司-餐饮空间品牌全案设计-深圳市勤蜂装饰工程 | 风电变桨伺服驱动器-风电偏航变桨系统-深圳众城卓越科技有限公司 | 铝合金风口-玻璃钢轴流风机-玻璃钢屋顶风机-德州东润空调设备有限公司 | 学校用栓剂模,玻璃瓶轧盖钳,小型安瓿熔封机,实验室安瓿熔封机-长沙中亚制药设备有限公司 | 广州企亚 - 数码直喷、白墨印花、源头厂家、透气无手感方案服务商! | 老城街小面官网_正宗重庆小面加盟技术培训_特色面馆加盟|牛肉拉面|招商加盟代理费用多少钱 | 交变/复合盐雾试验箱-高低温冲击试验箱_安奈设备产品供应杭州/江苏南京/安徽马鞍山合肥等全国各地 | 广州番禺搬家公司_天河黄埔搬家公司_企业工厂搬迁_日式搬家_广州搬家公司_厚道搬迁搬家公司 | 热闷罐-高温罐-钢渣热闷罐-山东鑫泰鑫智能热闷罐厂家 |