Vue 的事件处理系统不仅语法优雅,还能显著减少模板中的样板代码。本篇文章将从基础用法s说起,逐步深入到事件修饰符、键盘事件、组合键监听等高阶特性。每一小节都通过真实开发场景切入,配合代码、原理剖析与注意事项,希望可以帮助你更好的学习vue。
一、基础事件绑定:从原生到 Vue
💡 使用背景
在原生 JS 中绑定事件常见如下写法:
js
document.querySelector('button').addEventListener('click', function () {
console.log('按钮被点击')
})
而在 Vue 中,可以直接在模板中使用 @事件名 或 v-on:事件名 来绑定:
js
<template>
<button @click="handleClick">点击我</button>
</template>
<script setup>
function handleClick() {
console.log('按钮被点击')
}
</script>
✅ 优势总结
- 更符合 HTML 语义,不需操作 DOM
- 与响应式数据天然集成
- 语法更简洁:@click 是 v-on:click 的简写
二、传参与事件对象
💡 使用背景
有时候你不仅要知道事件发生了,还需要传递额外的参数,例如列表索引、ID。
🧪 示例代码
js
<template>
<ul>
<li v-for="(item, index) in items" :key="item.id">
<button @click="handleClick(item, index, $event)">删除</button>
</li>
</ul>
</template>
<script setup>
const items = [
{ id: 1, name: '苹果' },
{ id: 2, name: '香蕉' },
]
function handleClick(item, index, event) {
console.log('删除:', item.name, '位置:', index)
console.log('原始事件对象:', event)
}
</script>
✅ 说明
- 你可以同时传自定义参数和 $event
- $event 是 Vue 提供的事件对象别名,指向原生 DOM 事件对象
三、事件修饰符:让模板更干净
💡 使用背景
在原生事件中,event.stopPropagation() 和 event.preventDefault() 很常见,但会让模板和逻辑耦合。
Vue 提供一系列修饰符,专注于事件行为控制:.stop
, .prevent
, .self
, .once
, .capture
, .passive
等。
🧪 示例代码
js
<template>
<form @submit.prevent="submit">
<button type="submit">提交</button>
</form>
<div @click="parentClick">
<button @click.stop="childClick">阻止冒泡</button>
</div>
</template>
<script setup>
function submit() {
console.log('提交表单,无页面刷新')
}
function parentClick() {
console.log('父容器被点击')
}
function childClick() {
console.log('按钮点击,不冒泡')
}
</script>
✅ 深入解析
-
.prevent 阻止默认行为,如 form 自动提交
-
.stop 阻止事件冒泡
-
.once 只触发一次,自动解绑
-
.self 限制事件只在自身元素触发时响应
⚠️ 注意事项
修饰符顺序会影响执行逻辑:.stop.prevent ≠ .prevent.stop
四、键盘事件与修饰符
💡 使用背景
表单输入时,我们常常需要监听 Enter 键提交,或组合键快捷操作。
Vue 支持多种键盘修饰符,如 @keyup.enter
、@keydown.esc
。
🧪 示例代码
js
<template>
<input @keyup.enter="search" placeholder="按回车搜索" />
</template>
<script setup>
function search() {
console.log('触发搜索')
}
</script>
✅ 常用键名
键名 | 修饰符写法 |
---|---|
Enter | .enter |
Esc | .esc |
Tab | .tab |
Delete | .delete |
Space | .space |
⚠️ 自定义键名
js
<input @keyup.page-down="nextPage" />
- 支持 kebab-case 和标准名称,如 page-down, arrow-up
五、组合键监听
💡 使用背景
如 Ctrl + S 保存,Ctrl + Enter 发送信息。
🧪 示例代码
js
<template>
<input @keydown.ctrl.enter="send" placeholder="Ctrl + Enter 发送" />
</template>
<script setup>
function send() {
console.log('消息已发送')
}
</script>
✅ 支持的组合键
-
.ctrl
-
.alt
-
.shift
-
.meta(Mac 上代表 Command 键)
组合顺序不影响结果,如 .ctrl.enter 和 .enter.ctrl 都可用。
六、事件绑定函数的多种写法
💡 使用背景
事件绑定可以传参,也可以绑定多个函数。Vue 支持如下写法:
🧪 多种写法对比
js
<!-- 直接绑定方法 -->
<button @click="submit" />
<!-- 使用箭头函数传参 -->
<button @click="() => submit(id)" />
<!-- 使用方法调用语法传参 -->
<button @click="submit(id)" />
⚠️ 注意事项
- 如果方法调用语法不加箭头函数,会在渲染阶段就执行!
ini
<button @click="submit(id)"> ❌ 不推荐
- 改为:
js
<button @click="() => submit(id)"> ✅
七、Vue 相比传统事件处理的优势总结
对比项 | 原生 JS | Vue |
---|---|---|
绑定方式 | 手动 DOM 查询 + addEventListener | 模板中用 @ 直接绑定 |
传参 | 不直观,需封装闭包 | 直接支持 $event 与任意参数 |
阻止行为 | 需手动调用事件 API | 一行 .stop / .prevent 即可 |
键盘组合 | 手动判断 event.key | .enter .ctrl.enter 内置支持 |
解耦性 | 模板与逻辑混杂 | 更关注"做什么",而非"怎么做" |