vue中的事件綁定舉例詳解
1 事件處理
1.1 最簡(jiǎn)單的事件綁定例子
在vue當(dāng)中,要給元素綁定事件需要用到vue指令,指令一般以v-開(kāi)頭,例如綁定單擊事件的指令是v-on:click = “函數(shù)名”,簡(jiǎn)寫(xiě)為@click = “函數(shù)名”
例如以下例子:?jiǎn)螕鬮utton按鈕,執(zhí)行showInfo函數(shù),彈出alert窗口。
<body> <button class="btn" v-on:click = "showInfo">點(diǎn)擊彈出{{name}}窗口</button> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ data:{ name:"alert" }, methods:{ showInfo(){ alert('hello!'); } } }) vm.$mount('.btn') </script> </body>
以上是最簡(jiǎn)單的事件綁定例子,鼠標(biāo)懸停、鼠標(biāo)移出等事件可以參照以上例子。
vm.$mount(".btn")指定了可供vue操作的元素,與el關(guān)鍵字的作用類(lèi)似,但比el更加靈活。
methods記錄了所有的方法,凡事與vue所操作元素有關(guān)的方法都應(yīng)該寫(xiě)在method里面,否則無(wú)效。
在button屬性里面,使用v-on:click綁定了一個(gè)單擊事件,當(dāng)點(diǎn)擊此對(duì)象時(shí),就執(zhí)行showInfo函數(shù)。
1.2 默認(rèn)參數(shù)event
這一步是探究methods配置項(xiàng)中,函數(shù)的傳參問(wèn)題。在上一個(gè)例子當(dāng)中,設(shè)置了showInfo函數(shù),這是自定義的函數(shù),現(xiàn)在探究這個(gè)函數(shù)它默認(rèn)情況下怎么接收函數(shù)。首先,為showInfo設(shè)置三個(gè)參數(shù)的位置,分別為a,b,c,然后后臺(tái)輸出a,b,c這三個(gè)參數(shù),看看哪一個(gè)參數(shù)里面存的有東西。代碼如下所示:
<body> <button class="btn" v-on:click = "showInfo">點(diǎn)擊彈出{{name}}窗口</button> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ data:{ name:"alert" }, methods:{ showInfo(a,b,c){ alert('hello!'); console.log(a,b,c); } } }) vm.$mount('.btn') </script> </body>
可以發(fā)現(xiàn)輸出的a,b,c當(dāng)中只有a有東西,其他的全部為undefined??梢园l(fā)現(xiàn)a里面存放的是一個(gè)名為PointerEvent(百度翻譯:指針事件)的對(duì)象,其實(shí)就是事件對(duì)象event,有點(diǎn)像事件委托當(dāng)中的event??梢試L試以下代碼。
methods:{ showInfo(event){ alert('hello!'); console.log(event.target); console.log(event.target.innerHTML); } }
輸出結(jié)果:分別彈出被點(diǎn)擊的標(biāo)簽、被點(diǎn)擊標(biāo)簽的文本內(nèi)容。
1.3 其它自定義參數(shù)
先寫(xiě)好兩個(gè)按鈕,這兩個(gè)按鈕點(diǎn)擊之后會(huì)觸發(fā)相應(yīng)的函數(shù),btn1觸發(fā)showInfo1函數(shù),btn2觸發(fā)showInfo2函數(shù),showInfo1不傳參數(shù),showInfo2傳入一個(gè)參數(shù)。接著,在methods中配置好showInfo1與showInfo2函數(shù)。代碼如下所示:
<body> <button class="btn" v-on:click = "showInfo1">按鈕1</button> <button class="btn" v-on:click = "showInfo2(66)">按鈕2</button> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ methods:{ showInfo1(a){ console.log( `showInfo1:${a}`); }, showInfo2(a){ console.log( `showInfo2:${a}`); } } }) vm.$mount('.btn') </script> </body>
輸出結(jié)果:
showInfo1沒(méi)有傳入任何參數(shù),所以showInfo1的第一次參數(shù)位默認(rèn)為event ,showInfo2我們給它傳入了數(shù)字66作為第一個(gè)參數(shù),所以showInfo2輸出66 ,但這樣做之后,event消失了。解決辦法,再傳入一個(gè)$event參數(shù),$event是一個(gè)關(guān)鍵字,vue會(huì)自動(dòng)將其解析為event,這個(gè)參數(shù)無(wú)論作為第幾個(gè)參數(shù)都可以。代碼如下所示:
<body> <div class="btns"> <button v-on:click = "showInfo1">按鈕1</button> <button v-on:click = "showInfo2(66,$event)">按鈕2</button>//添加$evetn </div> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ methods:{ showInfo1(a){ console.log( `showInfo1:${a}`); }, showInfo2(a,b){//增加形參b console.log( `showInfo2:${a},$`); } } }) vm.$mount('.btns') </script>
輸出結(jié)果:
1.4 this
methods中的配置函數(shù),都是被vue所管理的函數(shù),this指向vm或組件實(shí)例對(duì)象,所以showInfo中的this指向vue實(shí)例(即例子當(dāng)中的vm),若showInfo使用箭頭函數(shù),則this指向window。箭頭函數(shù)的寫(xiě)法如下所示:
methods:{ showInfo:(event) => { alert('hello!'); console.log(event.target); console.log(event.target.innerHTML); } }
受vue所管理的函數(shù)最好寫(xiě)成普通函數(shù),而不是寫(xiě)成箭頭函數(shù),不然會(huì)影響this的指向。
2 事件修飾符
2.1 prevent阻止默認(rèn)事件(常用)
一般用在有默認(rèn)事件的標(biāo)簽上,例如點(diǎn)擊a標(biāo)簽時(shí)的默認(rèn)跳轉(zhuǎn)行為,寫(xiě)法是@click.prevent="函數(shù)名"
2.2 stop阻止事件冒泡(常用)
例如在以下代碼當(dāng)中,若先將button元素中的v-on:click.stop="showInfo1"改寫(xiě)為v-on:click="showInfo1",那么此時(shí)點(diǎn)擊button按鈕會(huì)彈出兩次alert窗口。為什么?因?yàn)閎utton元素和它的父級(jí)元素都有click事件,所以,如果點(diǎn)擊button按鈕不僅會(huì)觸發(fā)button的單擊事件,同時(shí)也會(huì)觸發(fā)div的click事件,這種行為叫做冒泡,若在button元素中的單擊事件中添加stop事件修飾符,那么會(huì)在button元素這一步停止冒泡行為。
<body> <div v-on:click="showInfo1" class="btns"> <button v-on:click.stop="showInfo1">按鈕1</button> </div> <script type="text/javascript"> const vm = new Vue({ methods: { showInfo1() { alert(`彈出信息!`); } } }) vm.$mount('.btns') </script> </body>
2.3 once事件只觸發(fā)一次(常用)
以上面的代碼為例,每一次點(diǎn)擊button都會(huì)出現(xiàn)alert彈窗,如果我想讓它在第一次點(diǎn)擊的時(shí)候出現(xiàn)彈窗,以后無(wú)論點(diǎn)多少?gòu)亩疾怀霈F(xiàn)彈窗,該怎么做。
只需將button的單擊事件改寫(xiě)為v-on:click.once='showInfo1'即可。
2.4 capture使用事件的捕獲模式
捕獲(由外往內(nèi)),冒泡(由內(nèi)往外),先捕獲再冒泡,程序默認(rèn)在冒泡階段處理事件。
capture可以使程序在捕獲階段就開(kāi)始處理事件。
首先觀察以下不加任何修飾符的代碼。
<body> <div v-on:click="showInfo1(1)" class="btns"> div1 <div v-on:click="showInfo1(2)"> div2 </div> </div> <script type="text/javascript"> const vm = new Vue({ methods: { showInfo1(number) { console.log(`${number}`); } } }) vm.$mount('.btns') </script> </body>
代碼的大致意思是:我點(diǎn)擊哪一個(gè)div元素就在控制臺(tái)輸出它的序號(hào),觀察它的輸出順序。若點(diǎn)擊div1,則后臺(tái)只輸出1,若點(diǎn)擊div2,則后臺(tái)就接著輸出2、1(有先后順序),為什么點(diǎn)擊div2的時(shí)候還要多輸出1呢?因?yàn)槟J(rèn)使用了事件的冒泡模式,事件處理函數(shù)默認(rèn)在冒泡階段被執(zhí)行?,F(xiàn)在我想讓div1在捕獲階段就被執(zhí)行,那么只需要在div的單擊事件上添加capture事件修飾符即可。代碼示例如下:
<body> <div v-on:click.capture="showInfo1(1)" class="btns"> div1 <div v-on:click="showInfo1(2)"> div2 </div> </div> <script type="text/javascript"> const vm = new Vue({ methods: { showInfo1(number) { console.log(`${number}`); } } }) vm.$mount('.btns') </script> </body>
此時(shí)若再來(lái)點(diǎn)擊div2,則控制臺(tái)彈出1、2(有先后順序),與剛才的截然相反。
但有一個(gè)誤區(qū)值得注意,div1的事件是在捕獲階段被觸發(fā)的,div2的事件仍然是在冒泡階段觸發(fā)的,簡(jiǎn)單總結(jié)就是有capture的事件才會(huì)在捕獲階段觸發(fā),沒(méi)有capture的事件仍然在冒泡階段被觸發(fā),這一點(diǎn)可以通過(guò)以下例子被證實(shí):
<body> <div v-on:click.capture="showInfo1(1)" class="btns"> div1 <div v-on:click="showInfo1(2)"> div2 <div v-on:click="showInfo1(3)"> div3 </div> </div> </div> <script type="text/javascript"> const vm = new Vue({ methods: { showInfo1(number) { console.log(`${number}`); } } }) vm.$mount('.btns') </script> </body>
觀察代碼發(fā)現(xiàn),只有div1有capture,所以當(dāng)點(diǎn)擊div3的時(shí)候,控制臺(tái)先后輸出1、3、2。
2.5 self只有event.target是當(dāng)前的操作元素時(shí)才出發(fā)事件
這個(gè)2.5的標(biāo)題可能有點(diǎn)難以理解,首先來(lái)看看event.target是什么。先來(lái)個(gè)例子:
<body> <div v-on:click="showInfo2" class="btns"> div <span v-on:click="showInfo1"> span </span> </div> <script type="text/javascript"> const vm = new Vue({ methods: { showInfo1(event) { console.log(`我是span我點(diǎn)擊的是${event.target}`); }, showInfo2(event) { console.log(`我是div我點(diǎn)擊的是${event.target}`); } } }) vm.$mount('.btns') </script> </body>
以上代碼大致意思是,若點(diǎn)擊div則執(zhí)行showInfo1,若點(diǎn)擊span則執(zhí)行showInfo2。
若點(diǎn)擊div,則后臺(tái)輸出情況如下:這一條結(jié)果對(duì)應(yīng)的是div標(biāo)簽的事件,且從語(yǔ)句中我們可得知被點(diǎn)擊的是div標(biāo)簽。
若點(diǎn)擊span,則后臺(tái)輸出情況如下:因?yàn)槊芭葺敵隽藘蓚€(gè)結(jié)果,但從兩條結(jié)果中都可獲知被點(diǎn)擊的是span標(biāo)簽。
所以,綜上所述,event.target代表被點(diǎn)擊的對(duì)象,無(wú)論當(dāng)前被捕獲(或冒泡)到哪一個(gè)元素,event.target的值都不變。
再次回到self事件修飾符,只有self的作用對(duì)象與event.target目標(biāo)對(duì)象是同一個(gè)時(shí),事件才被執(zhí)行。以下是示例代碼:(在第二行添加了self)
<body> <div v-on:click.self="showInfo2" class="btns"> div <span v-on:click="showInfo1"> span </span> </div> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ methods: { showInfo1(event) { console.log(`我是span我點(diǎn)擊的是${event.target}`); }, showInfo2(event) { console.log(`我是div我點(diǎn)擊的是${event.target}`); } } }) vm.$mount('.btns') </script> </body>
這時(shí)候點(diǎn)擊span就不會(huì)出現(xiàn)兩條結(jié)果了,而是只出現(xiàn)“我是span我點(diǎn)擊的是[objectHTMLSpanElement]”。
為什么這時(shí)候只有一條語(yǔ)句呢,因?yàn)辄c(diǎn)擊span后,代碼首先執(zhí)行span的事件,然后再冒泡到div,發(fā)現(xiàn)div有self,但event.target的并不是div,所以div的事件就沒(méi)有執(zhí)行。若直接點(diǎn)擊div,則div的事件正常執(zhí)行。
2.6 passive事件的默認(rèn)行為立即執(zhí)行,無(wú)需等待事件回調(diào)執(zhí)行完畢
事件的默認(rèn)行為就例如:a標(biāo)簽點(diǎn)擊會(huì)跳轉(zhuǎn)、鼠標(biāo)輪滾動(dòng)頁(yè)面也會(huì)滾動(dòng)等等。
@scroll是滾動(dòng)條滾動(dòng)事件,@wheel是鼠標(biāo)滾輪滾動(dòng)事件,兩者有區(qū)別。
passive一般用在什么情況?(如下)
以鼠標(biāo)滾動(dòng)事件為例,當(dāng)不考慮passive時(shí),并且設(shè)置了滾動(dòng)時(shí)需要執(zhí)行函數(shù)的機(jī)制時(shí),執(zhí)行順序是:
觸發(fā)滾動(dòng)事件——執(zhí)行滾動(dòng)時(shí)的函數(shù)——頁(yè)面滾動(dòng)
以上順序需要等待函數(shù)執(zhí)行完畢頁(yè)面才能滾動(dòng),若所執(zhí)行的函數(shù)耗時(shí)非常大,就會(huì)造成卡頓現(xiàn)象。
面對(duì)此現(xiàn)象,如果加上passive事件修飾符,那么函數(shù)和默認(rèn)事件就會(huì)同時(shí)執(zhí)行,且不會(huì)造成頁(yè)面卡頓現(xiàn)象。
2.7 事件修飾符的連續(xù)使用
如果既需要阻止冒泡,又需要阻止默認(rèn)跳轉(zhuǎn)行為,則寫(xiě)法應(yīng)如下:
@click.stop.prevent = "函數(shù)名"或者@click.prevent.stop = "函數(shù)名",兩種寫(xiě)法任選其一,效果一致。
3 鍵盤(pán)事件
3.1 Vue中常用的按鍵別名
- 回車(chē) => enter
- 刪除 => delete
- 退出 => esc
- 空格 => space
- 換行 => tab
- 上 => up
- 下 => down
- 左 => left
- 右 => right
Vue當(dāng)中未提供別名的按鍵,可以使用按鍵原始的key值去綁定,但注意要轉(zhuǎn)為kebab-case(短橫線(xiàn)命名)
3.2 最簡(jiǎn)單的綁定鍵盤(pán)事件的方法
鍵盤(pán)事件常用的有兩個(gè):keydown(鍵盤(pán)按下時(shí)執(zhí)行)和keyup(鍵盤(pán)按下后彈起時(shí)執(zhí)行)
綁定鍵盤(pán)事件的寫(xiě)法為@keyup="函數(shù)名"(v-on:keyup="函數(shù)名"),可參照以下代碼。
每一個(gè)按鍵都有自己的名字與編碼,以下代碼執(zhí)行的是 在按下任意鍵之后,控制臺(tái)顯示該按鍵的按鍵名(key)與按鍵編碼(keyCode)。keyCode在web標(biāo)準(zhǔn)中已經(jīng)被廢棄
<body> <div class="btns"> <input type="text" @keyup="keyEvent"> </div> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ methods: { keyEvent(event) { console.log(event.key,event.keyCode); } } }) vm.$mount('.btns') </script> </body>
以下例舉幾個(gè)按鍵:
注意:這里輸出的結(jié)果開(kāi)頭大寫(xiě),并非vue當(dāng)中所提供的別名,vue提供的別名一般用在形如@keyup.enter=“函數(shù)名” 上,后面會(huì)有詳細(xì)描述。
3.3 按下目標(biāo)鍵才觸發(fā)的鍵盤(pán)事件
假如現(xiàn)在有一個(gè)input標(biāo)簽,在input標(biāo)簽中輸入內(nèi)容,輸入完畢后,只有按回車(chē)鍵才能將輸入的內(nèi)容顯示在控制臺(tái)。有兩種實(shí)現(xiàn)方法:
第一種:使用if進(jìn)行原始的按鍵判斷方法
<body> <div class="btns"> <input type="text" @keyup="keyEvent"> </div> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ methods: { keyEvent(event) { if (event.key == 'Enter') { console.log(event.target.value); } } } }) vm.$mount('.btns') </script> </body>
第二種:使用vue提供的按鍵判斷(要用到vue提供的別名),只需在@keyup后添加別名即可。
<body> <div class="btns"> <input type="text" @keyup.enter="keyEvent"> </div> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ methods: { keyEvent(event) { console.log(event.target.value); } } }) vm.$mount('.btns') </script> </body>
但是有一類(lèi)按鍵比較特殊,這類(lèi)按鍵由多個(gè)單詞組成,例如CapsLock(大小寫(xiě)切換),它由Caps與Lock組成,寫(xiě)在@keyup后面就應(yīng)該這樣寫(xiě):
@keyup.caps-lock="函數(shù)名"
即:將兩個(gè)單詞拆分開(kāi)用短橫線(xiàn)連接,并且將大寫(xiě)字母變?yōu)樾?xiě)。
另外一個(gè)需要注意的點(diǎn)是,部分按鍵無(wú)法進(jìn)行鍵盤(pán)事件的綁定,例如音量鍵、亮度鍵等。
3.4 tab按鍵(特殊)
tab按鍵自身就有一個(gè)功能,就是把焦點(diǎn)從當(dāng)前元素身上移到另一個(gè)元素身上。tab鍵在按下但還沒(méi)有抬起來(lái)時(shí)就已經(jīng)被觸發(fā),所以@keyup對(duì)tab鍵無(wú)效,需要使用@keydown來(lái)控制tab鍵。
3.5 系統(tǒng)修飾鍵(特殊)
系統(tǒng)修飾鍵(用法特殊):ctrl、shift、alt、meta(也叫徽標(biāo)鍵或win鍵)。
以上按鍵需要配合keydowm按鍵才能正常的觸發(fā)鍵盤(pán)事件。若配合keyup按鍵,則需要再按下修飾鍵的同時(shí)再按下其他鍵,隨后釋放其他鍵,事件才被觸發(fā)。
若規(guī)定只能按下ctrl+y才能觸發(fā)鍵盤(pán)事件,應(yīng)該怎么寫(xiě)?
答案:@keyup.ctrl.y = "函數(shù)名"
3.6 自定義按鍵別名
例如將回車(chē)鍵的別名由enter改為huiche需要怎么改?
寫(xiě)法如下:
vue.config.keyCodes.huiche = 13;
數(shù)字13是回車(chē)鍵的編碼。huiche是新的別名。
一般不推薦自定義按鍵名。
總結(jié)
到此這篇關(guān)于vue中的事件綁定的文章就介紹到這了,更多相關(guān)vue事件綁定內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Vue3中Composition?API和Options?API的區(qū)別
Vue3的Composition API和Options API是Vue.js框架中的兩種不同的API,本文主要介紹了Vue3中Composition?API和Options?API的區(qū)別,文中通過(guò)示例代碼介紹的非常詳細(xì),需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2023-06-06解決vue數(shù)據(jù)更新但table內(nèi)容不更新的問(wèn)題
這篇文章主要給大家介紹了vue數(shù)據(jù)更新table內(nèi)容不更新解決方法,文中有詳細(xì)的代碼示例供大家作為參考,感興趣的同學(xué)可以參考閱讀一下2023-08-08vue中(el-button的五種類(lèi)型,三種css格式)
這篇文章主要介紹了vue中(el-button的五種類(lèi)型,三種css格式)具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-07-07vue中異步數(shù)據(jù)獲取方式(確保數(shù)據(jù)被獲取)
這篇文章主要介紹了vue中異步數(shù)據(jù)獲取方式(確保數(shù)據(jù)被獲取),具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-01-01Vue3.2.x中的小技巧及注意事項(xiàng)總結(jié)
Vue是一套用于構(gòu)建用戶(hù)界面的漸進(jìn)式JavaScript框架,是目前最火的前端框架之一,是前端工程師的必備技能,下面這篇文章主要給大家介紹了關(guān)于Vue3.2.x中的小技巧及注意事項(xiàng)的相關(guān)資料,需要的朋友可以參考下2022-04-04詳解windows下vue-cli及webpack 構(gòu)建網(wǎng)站(三)使用組件
本篇文章主要介紹了詳解windows下vue-cli及webpack 構(gòu)建網(wǎng)站(三)使用組件,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-06-06vue性能優(yōu)化之cdn引入vue-Router的問(wèn)題
這篇文章主要介紹了vue性能優(yōu)化之cdn引入vue-Router的問(wèn)題及解決,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-08-08