组件通信的方式
1. Props(父传子)
父组件的数据
子组件
使用方法
2.$emit(子传父)
子组件
父组件
3.provide/inject(父传子孙后代)
provide 选项应该是一个对象或返回一个对象的函数。该对象包含可注入其子孙的属性。 子孙组件通过 inject 注入获取到祖级和父级 provide 的数据。
父组件
所有的子孙后代组件都可以用inject接收传值
使用
4.vuex(父传子孙后代)
步骤:
1. 装vuex包
2. 创建目录vuex,创建store.js文件
3. 在store.js文件里引入vue,引入vuex
4. vue使用vuex
5. 实例一个store对象
6. 配置vuex相关项--四大核心state getters mutations actions
7. 导出store对象
8. 在根组件里导入store
9. 在根组件里挂载store
10. 在所有组件的template模板里使用$store对象去插值或者别的操作
在src文件夹下建一个store文件夹,在store文件夹下创建index.js, (也可以在创建vue项目时把vuex选上)
在index.js里设置如下代码
import Vue from 'vue'
import Vuex from 'vuex'
import axios from 'axios'
// 引入msgModule
import MsgModule from './msgModule.js'
Vue.use(Vuex)
// 实例化vuex对象,导出vuex对象
export default new Vuex.Store({
// 全局都可以使用的数据
state:{
msg: '我是vuex里的数据',
num: 1,
isContactShow: false
},
// getters,相对于对state里的数据进行运算 类似于computed对于data的处理
getters:{
numDouble (state) {
return state.num * 2}},
// mutations,定义修改state里面数据的方法
mutations:{
updateMutationMsg (state) {
state.msg = '修改之后的msg数据'
},
updateMutationNum (state, info) {
state.num += info
},
actionCunt (state) {
++state.num
},
mutationContact (state) {
state.isContactShow = !state.isContactShow
}},
// actions用法--action中的方法触发mutations中的方法从而改变statei的数据;除此之外,如果需要异步操作,就必须在action中执行
actions:{
// actions方法中触发mutations中的方法
async actionUpdateNum (c, val) {
// console.log(c)
const res = await axios.get('http://47.100.227.25:3000/books/queryall')
console.log(res.data[0].id)
// 触发vuex实例mutations中的指定方法updateMutationNum
c.commit('updateMutationNum', res.data[0].id)
},
actionCunt (context) {
context.commit('actionCunt')
}},
modules:{
hh: MsgModule
}})
在子组件里设置一个点击事件
5.$parent/$children(获取父元素/获取子组件)
使用范围:
该属性只针对vue组件,与js中childNodes还是有区别的。
$children: 获取子组件实例集合。
childNodes: 获取子节点集合。
作用:获取父组件下的所有子组件实例,返回的是一个数组。
$children
输出
$parent
父组件
子组件通过this.$parent.num接收值
输出
6.兄弟组件之间传值
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width,
initial-scale=1.0">
<title>Document</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<div id="app">
<naruto></naruto>
<sasike></sasike>
</div>
<script>
// 1.定义一个新的vue实例作为事件中心,利用它来监听本身的自定义事件
let tmpCom = new Vue()
const app = new Vue({
el: "#app",
data:{},
methods:{},
components:{
'naruto':{
template: `<div>
<p>鸣人</p>
<p>{{skill}}</p>
<input type="button" value="给佐助传递skill" @click="sendSkill">
</div> `,
data: function() {
return{
skill: '螺旋丸'
}},
methods:{
sendSkill() {
// 2.触发事件中心的handle-n-skill事件
tmpCom.$emit('handle-n-skill', this.skill)
}}},
'sasike':{
template: ` <div>
<p>佐助</p>
<p>{{jineng}}</p>
<input type="button" value="给鸣人传递skill">
</div> `,
data: function() {
return{
jineng: '千鸟'
}},
mounted() {
// 3.监听事件中心的handle-n-skill事件
// 这里的第二个参数必须使用箭头函数
tmpCom.$on('handle-n-skill', val =>{
console.log(val)
console.log(this) // 如果不适用箭头函数,这里指向的是tmpCom实例
// console.log(app)
this.jineng = val
})}}}})
</script>
</body>
</html>
7.eventBus(子传父或兄弟组件)
在main.js中创建一个空的vue实例作为全局事件总线,同时,将其绑定在vue原型上。
子组件或兄弟组件,通过$emit来触发事件。
父组件或兄弟组件,通过$on来监听事件。
输出