vue组件间通信详解

组件间通信详解

1. 组件间多种通信方式:

props

vue自定义事件

事件总线

v-model

.sync 属性修饰符

attrs与listeners

children与parent

provide与inject

vuex

作用域插槽slot-scope

2. 组件间通信最基本方式: props

  • 用来实现父子之间相互通信的最基本方式, 也是用得最多的方式
    • 父 ==> 子, 传递的是非函数类型的属性
    • 子 ==> 父, 传递的是函数类型的属性

3. 组件间通信: vue自定义事件

vue自定义事件

  • 绑定vue自定义事件监听
    • 只能在组件标签上绑定
    • 事件名是任意的, 可以与原生DOM事件名相同
  • 只有当执行$emit('自定义事件名', data)时分发自定义事件, 才会触发自定义事件监听函数调用
  • $event: 就是分发自定义事件时指定的data数据
  • $event可以是任意类型, 甚至可以没有
  • 用来实现子向父组件通信, 功能相当于函数类型的props

4. 组件间通信: 事件总线

  • 定义:
    • Vue原型对象上有3个事件处理的方法: on() / emit() / $off()
    • 组件对象的原型对象的原型对象是Vue的原型对象: 组件对象可以直接访问Vue原型对象上的方法
  • 实现任意组件间通信

- 编码实现:

  • 将入口js中的vm作为全局事件总线对象:
    beforeCreate() {
    Vue.prototype.$bus = this
    }
  • 分发事件/传递数据的组件: this.bus.emit('eventName', data)
  • 处理事件/接收数据的组件: this.bus.on('eventName', (data) => {})

5. 组件间通信: v-model

1) 原生input上的本质:

动态的value属性与原生input事件监听

<input type="text" :value="name2" @input="name2=$event.target.value">

2) 组件标签上的本质:

动态的value属性与自定义input事件监听

// 父组件:

<CustomInput :value="name4" @input="name4= e v e n t " / > / / 子组件 p r o p s : [ ′ v a l u e ′ ] < i n p u t t y p e = " t e x t " : v a l u e = " v a l u e " @ i n p u t = " event"/> // 子组件 props: ['value'] <input type="text" :value="value" @input=" event"/>//子组件props:[′value′]<inputtype="text":value="value"@input="emit('input', $event.target.value)">

3) 利用v-model能做什么?

  • v-model不仅能实现原生标签上的双向数据绑定, 也能实现父子组件间数据双向通信(同步)
  • 应用
    • 一般用于封装带表单项的复用性组件
    • elment-ui中: Input/CheckBox/Radio/Select等表单项组件都封装了v-model

6. 组件间通信: sync 属性修饰符

1)定义:

绑定一个自定义事件监听, 用来接收子组件分发事件携带的最新数据来更新父组件的数据

2) 利用sync能做什么呢?

  • 在原有父向子的基础上加上子向父通信
  • 应用
    • 常用于封装可复用组件(需要更新父组件数据)
      • v-model一般用于带表单项的组件
      • sync一般用于不带表单项标签的组件
    • element-ui中: Dialog就利用sync来实现组件的隐藏

7. 组件间通信: attrs与listeners

1)定义:

  • $attrs: 排除props声明, class, style的所有组件标签属性组成的对象

  • $listeners: 级组件标签绑定的所有自定义事件监听的对象

  • v-bind: 的特别使用

  • v-on: 的特别使用:

    一般: v-bind与attrs配合使用, v-on与listeners配合使用

2) 使用它们能做什么呢?

  • 在封装可复用组件时: HintButton
    • 从父组件中接收不定数量/名称的属性或事件监听
    • 在组件内部, 传递给它的子组件
  • element-ui中: Input就使用了v-bind与$attrs来接收不定的属性传递给input

3) 扩展双击监听:

  • @dblclick="add2"
    绑定是自定义事件监听, 而el-button内部并没处理(没有绑定对应的原生监听, 没有分发自定义事件)
    双击时, 不会有响应
  • @dblclick.native="add2"
    绑定的是原生的DOM事件监听, 最终是给组件的根标签a绑定的原生监听
    当双击a内部的button能响应, 因为事件有冒泡

8. 组件间通信: children与parent

1) 定义:

  • $children: 所有直接子组件对象的数组, 利用它可以更新多个子组件的数据
  • $parent: 父组件对象, 从而可以更新父组件的数据
  • $refs: 包含所有有ref属性的标签对象或组件对象的容器对象

2) 利用它们能做什么?

  • 能方便的得到子组件/后代组件/父组件/祖辈组件对象, 从而更新其data或调用其方法
  • 官方建议不要大量使用, 优先使用props和event
  • 在一些UI组件库定义高复用组件时会使用children和parent, 如Carousel组件

3) 扩展: mixin

  • 多个组件有部分相同的js代码如何复用 ?
  • 答: 利用vue的mixin技术实现
  • 本质: 实现Vue组件的JS代码复用, 简化编码的一种技术

9. 组件间通信: provide与inject
1) 定义:

用来实现祖孙组件直接通信
在祖组件中通过provide配置向后代组件提供数据
在后代组件中通过inject配置来读取数据

2) 注意:

不太建议在应用开发中使用, 一般用来封装vue插件
provide提供的数据本身不是响应式的 ==> 父组件更新了数据, 后代组件不会变化
provide提供的数据对象内部是响应式的 ==> 父组件更新了数据, 后代组件也会变化

3) 应用:

element-ui中的Form组件中使用了provide和inject

10. 组件间通信: vuex

  1. 实现任意组件间通信
  2. Vuex 是一个专为 Vue 应用程序设计的管理多组件共享状态数据的 Vue 插件
    任意组件都可以读取到Vuex中store的state对象中的数据
    任意组件都可以通过dispatch()或commit()来触发store去更新state中的数据
    一旦state中的数据发生变化, 依赖于这些数据的组件就会自动更新

11. 作用域插槽slot-scope

1) 什么情况下使用作用域插槽?

  • 父组件需要向子组件传递标签结构内容
  • 但决定父组件传递怎样标签结构的数据在子组件中

2) 编码

<!: 子组件: >
<slot :row="item" :$index="index"></slot>

<!: 父组件: >
<template slot-scope="{row, $index}">
	<span>{{$index+1}}</span> &nbsp;&nbsp;
	<span :style="{color: $index%2===1 ? 'blue' : 'green'}" >{{row.text}}</span>
</template>

3) 应用

  • 对于封装列表之类的组件特别需要
  • element-ui中: Table组件中就用到了slot-scope
相关推荐
Мартин.2 分钟前
[Meachines] [Easy] Sea WonderCMS-XSS-RCE+System Monitor 命令注入
前端·xss
一 乐1 小时前
学籍管理平台|在线学籍管理平台系统|基于Springboot+VUE的在线学籍管理平台系统设计与实现(源码+数据库+文档)
java·数据库·vue.js·spring boot·后端·学习
昨天;明天。今天。1 小时前
案例-表白墙简单实现
前端·javascript·css
数云界1 小时前
如何在 DAX 中计算多个周期的移动平均线
java·服务器·前端
风清扬_jd2 小时前
Chromium 如何定义一个chrome.settingsPrivate接口给前端调用c++
前端·c++·chrome
安冬的码畜日常2 小时前
【玩转 JS 函数式编程_006】2.2 小试牛刀:用函数式编程(FP)实现事件只触发一次
开发语言·前端·javascript·函数式编程·tdd·fp·jasmine
ChinaDragonDreamer2 小时前
Vite:为什么选 Vite
前端
小御姐@stella2 小时前
Vue 之组件插槽Slot用法(组件间通信一种方式)
前端·javascript·vue.js
GISer_Jing2 小时前
【React】增量传输与渲染
前端·javascript·面试
eHackyd2 小时前
前端知识汇总(持续更新)
前端