Vue 2 和 Vue 3 事件修饰符对比(Vue3移除了.native修饰符,简化了组件事件处理逻辑)

Vue2和Vue3在事件修饰符上的主要区别在于.native修饰符的处理。


Vue2需要通过.native修饰符监听组件根元素的原生事件,而Vue3默认监听原生事件,只有当组件使用emits选项声明时才转为自定义事件。


其他常用修饰符(如.stop、.prevent等)在两个版本中功能一致。


Vue3移除了.native修饰符,简化了组件事件处理逻辑,使默认行为更符合直觉。


修饰符的链式调用方式在Vue2和Vue3中都保持相同。


Vue 2 和 Vue 3 事件修饰符对比


.native 修饰符

.native 修饰符用于在组件上直接监听原生 DOM 事件


为什么需要它?

默认情况下,在 Vue 组件上使用 @click 等事件监听的是组件自定义事件 (通过 $emit 触发),而不是原生 DOM 事件。

html 复制代码
<!-- 这样写,监听的是组件内部 $emit('click') 触发的自定义事件 -->
<MyComponent @click="handleClick" />

使用 .native

添加 .native 修饰符后,会直接监听组件根元素的原生事件:

html 复制代码
<!-- 现在监听的是组件根元素的原生 click 事件 -->
<MyComponent @click.native="handleClick" />

实际示例

html 复制代码
<!-- 父组件 -->
<template>
  <div>
    <!-- 不会触发:Button 组件没有 $emit('click') -->
    <Button @click="handleClick1" />
    
    <!-- 会触发:监听 Button 根元素的原生 click -->
    <Button @click.native="handleClick2" />
  </div>
</template>

<script>
import Button from './Button.vue'
export default {
  components: { Button },
  methods: {
    handleClick1() { console.log('不会执行') },
    handleClick2() { console.log('原生点击触发') }
  }
}
</script>

Vue 3 的变化

Vue 3 中移除了 .native 修饰符 。现在组件上所有事件监听都被视为原生事件,除非组件内部使用 emits 选项显式声明为自定义事件:

html 复制代码
<!-- Vue 3:默认就是原生事件 -->
<MyComponent @click="handleClick" />

<!-- 如果组件声明了 emits: ['click'],则 click 变为自定义事件 -->
<script setup>
// 声明后,@click 变为监听自定义事件
const emit = defineEmits(['click'])
</script>

总结

版本 用法 说明
Vue 2 @click.native 需要显式添加修饰符
Vue 3 @click 默认原生,声明 emits 后变自定义

Vue 2 和 Vue 3 事件修饰符对比

修饰符 Vue 2 Vue 3 说明
.stop 阻止事件冒泡,调用 event.stopPropagation()
.prevent 阻止默认行为,调用 event.preventDefault()
.capture 使用事件捕获模式
.self 仅当事件目标为元素本身时触发
.once 事件只触发一次
.passive 提升滚动性能,不调用 preventDefault()
.native Vue 2 中监听组件根元素原生事件;Vue 3 中移除,默认即为原生
.left 鼠标左键触发(鼠标事件)
.right 鼠标右键触发(鼠标事件)
.middle 鼠标中键触发(鼠标事件)
.ctrl Ctrl 键按下时触发
.alt Alt 键按下时触发
.shift Shift 键按下时触发
.meta Meta 键(Win 键/Command 键)按下时触发
.exact 精确控制系统修饰符组合(Vue 2.5.0+)

示例对比

Vue 2
html 复制代码
<template>
  <!-- 基本修饰符 -->
  <button @click.stop="handleClick">阻止冒泡</button>
  <form @submit.prevent="onSubmit">阻止提交</form>
  
  <!-- 组件原生事件 -->
  <MyComponent @click.native="onNativeClick" />
  
  <!-- 按键修饰符 -->
  <input @keyup.enter="submit" />
  <input @keyup.ctrl.enter="submit" />
  
  <!-- 精确组合 -->
  <button @click.ctrl.exact="onCtrlClick">仅 Ctrl 按下时触发</button>
</template>
Vue 3
html 复制代码
<template>
  <!-- 基本修饰符(相同) -->
  <button @click.stop="handleClick">阻止冒泡</button>
  <form @submit.prevent="onSubmit">阻止提交</form>
  
  <!-- 组件原生事件(无需 .native) -->
  <MyComponent @click="onNativeClick" />
  
  <!-- 按键修饰符(相同) -->
  <input @keyup.enter="submit" />
  <input @keyup.ctrl.enter="submit" />
  
  <!-- 精确组合(相同) -->
  <button @click.ctrl.exact="onCtrlClick">仅 Ctrl 按下时触发</button>
</template>

主要变化总结

变化点 说明
移除 .native Vue 3 中组件事件默认为原生事件,需用 emits 选项声明自定义事件
其他修饰符 功能和使用方式完全一致,无变化

修饰符链式调用

两个版本都支持修饰符链式组合:

html 复制代码
<!-- 阻止冒泡 + 阻止默认行为 + 只触发一次 -->
<a @click.stop.prevent.once="handleClick">链接</a>
相关推荐
daols883 小时前
vue甘特图vxe-gantt实现点击任务条弹出编辑表单
前端·vue.js·甘特图·vxe-gantt
予你@。3 小时前
vue 使用html2canvas + jsPDF 将html导出为pdf (延伸问题)
vue.js·pdf·html
Mintopia3 小时前
React vs Vue 优势对比Demo(证明React更具优势)
前端·vue.js·react.js
三*一3 小时前
mapbox 基于 Turf.js 实现高精度多边形分割(支持带空洞 / 坐标无损)
开发语言·前端·javascript·vue.js·mapbox gl
polaris06304 小时前
Docker部署Spring Boot + Vue项目
vue.js·spring boot·docker
ai产品老杨4 小时前
源码级赋能:基于Spring Boot/Vue的企业级AI视频平台二次开发实战与架构解析(GB28181/边缘计算/算法商城)
vue.js·人工智能·spring boot
wuhen_n4 小时前
终局之战:全链路性能体检与监控
前端·javascript·vue.js
AI服务老曹4 小时前
源码级解耦:基于 Spring Boot/Vue 的 AI 视频平台二次开发指南与私有化部署实践
vue.js·人工智能·spring boot
wuhen_n5 小时前
案例分析:从“慢”到“快”,一个后台管理页面的优化全记录
前端·javascript·vue.js