跳轉到內容

事件處理

監聽事件

我們可以使用 v-on 指令,我們通常將其簡寫為 @ 符號,來監聽 DOM 事件並在它們被觸發時執行一些 JavaScript。用法為 v-on:click="handler" 或使用快捷方式,@click="handler"

處理器值可以是以下之一

  1. 內聯處理器:在事件被觸發時執行的內聯 JavaScript(類似於原生的 onclick 屬性)。

  2. 方法處理器:指向元件上定義的方法的屬性名或路徑。

內聯處理器

內聯處理器通常用於簡單情況,例如

js
const count = ref(0)
js
data() {
  return {
    count: 0
  }
}
template
<button @click="count++">Add 1</button>
<p>Count is: {{ count }}</p>

方法處理器

儘管許多事件處理器的邏輯會更復雜,可能無法使用內聯處理器實現。這就是為什麼 v-on 還可以接受您要呼叫的元件方法名稱或路徑。

例如

js
const name = ref('Vue.js')

function greet(event) {
  alert(`Hello ${name.value}!`)
  // `event` is the native DOM event
  if (event) {
    alert(event.target.tagName)
  }
}
js
data() {
  return {
    name: 'Vue.js'
  }
},
methods: {
  greet(event) {
    // `this` inside methods points to the current active instance
    alert(`Hello ${this.name}!`)
    // `event` is the native DOM event
    if (event) {
      alert(event.target.tagName)
    }
  }
}
template
<!-- `greet` is the name of the method defined above -->
<button @click="greet">Greet</button>

方法處理器自動接收觸發它的原生 DOM 事件物件 - 在上面的示例中,我們能夠透過 event.target 訪問觸發事件的元素。

另請參閱:[事件處理器的型別化](/guide/typescript/composition-api#typing-event-handlers)

另請參閱:[事件處理器的型別化](/guide/typescript/options-api#typing-event-handlers)

方法與內聯檢測

模板編譯器透過檢查 v-on 值字串是否是有效的 JavaScript 識別符號或屬性訪問路徑來檢測方法處理器。例如,foofoo.barfoo['bar'] 被視為方法處理器,而 foo()count++ 被視為內聯處理器。

在內聯處理器中呼叫方法

除了直接繫結到方法名之外,我們還可以在內聯處理器中呼叫方法。這允許我們傳遞方法的自定義引數而不是原生事件

js
function say(message) {
  alert(message)
}
js
methods: {
  say(message) {
    alert(message)
  }
}
template
<button @click="say('hello')">Say hello</button>
<button @click="say('bye')">Say bye</button>

內聯處理程式中訪問事件引數

有時我們還需要在內聯處理程式中訪問原始DOM事件。您可以使用特殊變數 $event 將其傳遞到方法中,或者使用內聯箭頭函式。

template
<!-- using $event special variable -->
<button @click="warn('Form cannot be submitted yet.', $event)">
  Submit
</button>

<!-- using inline arrow function -->
<button @click="(event) => warn('Form cannot be submitted yet.', event)">
  Submit
</button>
js
function warn(message, event) {
  // now we have access to the native event
  if (event) {
    event.preventDefault()
  }
  alert(message)
}
js
methods: {
  warn(message, event) {
    // now we have access to the native event
    if (event) {
      event.preventDefault()
    }
    alert(message)
  }
}

事件修飾符

在事件處理程式中呼叫 event.preventDefault()event.stopPropagation() 是一個非常常見的需求。儘管我們可以在方法中輕鬆完成此操作,但最好是方法只關注資料邏輯,而不是處理DOM事件細節。

為了解決這個問題,Vue為v-on提供了事件修飾符。回想一下,修飾符是以點表示的指令字尾。

  • .stop
  • .prevent
  • .self
  • .capture
  • .once
  • .passive
template
<!-- the click event's propagation will be stopped -->
<a @click.stop="doThis"></a>

<!-- the submit event will no longer reload the page -->
<form @submit.prevent="onSubmit"></form>

<!-- modifiers can be chained -->
<a @click.stop.prevent="doThat"></a>

<!-- just the modifier -->
<form @submit.prevent></form>

<!-- only trigger handler if event.target is the element itself -->
<!-- i.e. not from a child element -->
<div @click.self="doThat">...</div>

提示

使用修飾符時順序很重要,因為相關程式碼是按相同順序生成的。因此,使用 @click.prevent.self 將阻止元素及其子元素的 click 的預設行為,而 @click.self.prevent 只會阻止元素本身的點選預設行為。

.capture.once.passive 修飾符與原生 addEventListener 方法的選項相對應。

template
<!-- use capture mode when adding the event listener     -->
<!-- i.e. an event targeting an inner element is handled -->
<!-- here before being handled by that element           -->
<div @click.capture="doThis">...</div>

<!-- the click event will be triggered at most once -->
<a @click.once="doThis"></a>

<!-- the scroll event's default behavior (scrolling) will happen -->
<!-- immediately, instead of waiting for `onScroll` to complete  -->
<!-- in case it contains `event.preventDefault()`                -->
<div @scroll.passive="onScroll">...</div>

.passive 修飾符通常與觸控事件監聽器一起使用,以在 提高移動裝置的效能

提示

不要同時使用 .passive.prevent,因為 .passive 已經向瀏覽器表明您 想阻止事件的預設行為,如果您這樣做,瀏覽器可能會顯示警告。

鍵修飾符

當監聽鍵盤事件時,我們經常需要檢查特定鍵。Vue允許在監聽鍵盤事件時為 v-on@ 新增鍵修飾符。

template
<!-- only call `submit` when the `key` is `Enter` -->
<input @keyup.enter="submit" />

您可以直接使用透過 KeyboardEvent.key 提供的任何有效鍵名作為修飾符,只需將它們轉換為短橫線命名法即可。

template
<input @keyup.page-down="onPageDown" />

在上面的示例中,只有當 $event.key 等於 'PageDown' 時,處理程式才會被呼叫。

鍵別名

Vue為最常用的鍵提供了別名

  • .enter
  • .tab
  • .delete(捕獲“Delete”和“Backspace”鍵)
  • .esc
  • .space
  • .up
  • .down
  • .left
  • .right

系統修飾鍵

您可以使用以下修飾符來觸發僅在按下相應的修飾鍵時才觸發的滑鼠或鍵盤事件監聽器

  • .ctrl
  • .alt
  • .shift
  • .meta

注意

在Macintosh鍵盤上,meta鍵是命令鍵(⌘)。在Windows鍵盤上,meta鍵是Windows鍵(⊞)。在Sun Microsystems鍵盤上,meta鍵標記為一個實心菱形(◆)。在某些鍵盤上,特別是MIT和Lisp機器鍵盤及其後繼產品,例如Knight鍵盤、space-cadet鍵盤,meta鍵被標記為“META”。在Symbolics鍵盤上,meta鍵被標記為“META”或“Meta”。

例如

template
<!-- Alt + Enter -->
<input @keyup.alt.enter="clear" />

<!-- Ctrl + Click -->
<div @click.ctrl="doSomething">Do something</div>

提示

請注意,修飾鍵與普通鍵不同,並且在使用keyup事件時,它們必須在事件發生時按下。換句話說,keyup.ctrl只有在您在按下ctrl鍵的同時釋放一個鍵時才會觸發。如果單獨釋放ctrl鍵,它不會觸發。

.exact 修飾符

.exact 修飾符允許控制觸發事件所需的精確系統修飾符組合。

template
<!-- this will fire even if Alt or Shift is also pressed -->
<button @click.ctrl="onClick">A</button>

<!-- this will only fire when Ctrl and no other keys are pressed -->
<button @click.ctrl.exact="onCtrlClick">A</button>

<!-- this will only fire when no system modifiers are pressed -->
<button @click.exact="onClick">A</button>

滑鼠按鈕修飾符

  • .left
  • .right
  • .middle

這些修飾符將處理程式限制為由特定滑鼠按鈕觸發的事件。

事件處理已載入