Vue组件间传值

1. 父组件向子组件传值 props

父组件

<template>
  <div>
    <h1>我是父组件</h1>
    <!-- 
        title2名称与子组件prop中的名称一致 ="title1" 与父组件中data数据中的title1名称一致 
    -->
    <children :title2="title1" :content2="content1"></children>
  </div>
</template>>
<script>
import Children from "./Children";
export default {
  data() {
    return {
      title1: "我是父组件的标题",
      content1: "我是内容"
    };
  },
  components: {
    Children
  }
};
</script>

子组件

<template>
  <div>
    <h1>children</h1>
    <span>{{title2}}</span>
    <br />
    <span>{{content2}}</span>
  </div>
</template>>
<script>
export default {
  props: {
    title2: String,
    content2: String
  }
};
</script>>

要点

  1. 父组件中引入子组件、注册子组件,template中使用子组件;import、components
  2. 子组件中props创建一个属性,接收父组件传的值,在template中使用 {{contents}}
  3. 父组件中的 title 与子组件中 prop 添加的属性名称一致;="title 与父组件中data数据的title一致

2. 子组件向父组件传值 $emit

子组件

<template>
  <div>
    <h1>children</h1>
      <button @click="sendTOParent">向父组件传值</button>
  </div>
</template>>
<script>
export default {
  data() {
    return {
      data: "子组件中的信息"
    };
  },
  methods:{
        sendTOParent(){
            this.$emit('listenToChildEvent',this.data)
        }
    }
};
</script>>

父组件

<template>
  <div>
    <h1>我是父组件</h1>
    <children @listenToChildEvent = 'showMsgfromChild'></children>
  </div>
</template>>
<script>
import Children from "./Children";
export default {
  data() {
    return {
    };
  },
   methods:{
        showMsgfromChild(data){
            console.log(data)
        }
    },
   components: {
    Children
  },
};
</script>

要点

  1. 子组件中需要以某种方式(如点击)来触发一个自定义事件
  2. 将需要传的值作为 $emit 的第二个参数,该值将作为实参传给响应自定义事件的方法
  3. 在父组件中注册子组件并在子组件标签上绑定对应自定义事件的监听
  4. 具体流程 sendTOParent => listenToChildEvent => showMsgfromChild

3. 总线机制bus

通过一个空的Vue实例作为中央事件总线,用它来触发事件和监听事件,巧妙而轻量的实现了任何组件之间的通信,包括父子、兄弟、跨级等。

公共bus.js文件

import Vue from 'vue'
export default new Vue()

组件A代码

<template>
  <div>
    A组件:
    <span>{{elementValue}}</span>
    <input type="button" value="点击触发" @click="elementByValue">
  </div>
</template>
<script>
  // 引入公共的bus,来做为中间传达的工具
  import Bus from './bus.js'
  export default {
    data () {
      return {
        elementValue: 4
      }
    },
    methods: {
      elementByValue() {
      	// 使用$emit来传递参数
        Bus.$emit('sendVal', this.elementValue)
      }
    }
  }
</script>

组件B代码

<template>
  <div>
    B组件:
    <input type="button" value="点击触发" @click="getData">
    <span>{{num}}</span>
  </div>
</template>
<script>
  import Bus from './bus.js'
  export default {
    data () {
      return {
        num: 0
      }
    },
    mounted() {
      var vm = this
      // 用$on事件来接收参数
      Bus.$on('sendVal', (data) => {
        console.log(data)
        vm.num= data
      })
    },
    methods: {
      getData() {
        this.num++
      }
    },
    destroyed () {
	   // 取消对bus事件的监听
	   // 事件订阅是通过Bus对象完成的 与组件无关
	   Bus.$off('sendVal')
	 }
  }
</script>

要点

  1. 在项目中定义 bus.js 文件,并注册一个 Vue 实例
  2. 页面A导入 Vue 实例,并通过 Bus.$emit('sendVal', this.elementValue) 方法进行传值
  3. 页面B导入 Vue 实例,并通过 Bus.$on('sendVal', (data) => { }) 方法监听其他组件的传值

4. vuex

当前方法写的不够完善,需要进一步的改进 \color{red}当前方法写的不够完善,需要进一步的改进 当前方法写的不够完善,需要进一步的改进

主要方法是使用store空间存储值并进行获取或监测

vuex中的store空间存值

// src/store/modules/home.js
const homeModule: any = {
		time: {
			change: 0,
		},
	},
	mutations: {},
	actions: {},
};

export default homeModule;

页面a修改store空间值

import { useStore } from '/@/store/index';
const store = useStore();
store.state.homeParams.time.change = 1;

页面b监听store空间值的修改并作出响应

import { useStore } from '/@/store/index';
const store = useStore();
<script lang="ts">
export default defineComponent({
	setup() {
		watch(
			() => store.state.homeParams.time.change,
			() => {
				getTime();
			}
		)
	}
});
<script>

5. $parent/$children && ref

代码待完善

  • $parent / $children: 访问父/子实例
  • ref: 如果在普通DOM元素上使用,引用指向的时DOM元素;如果在子组件上,引用指向组件实例。

两种都是直接得到组件实例,使用后可以直接调用组件的方法或访问数据

6. $attrs / $listeners

代码待实现

7. provide / inject

代码待实现

  • 成对出现:provide和inject是成对出现的
  • 作用:用于父组件向子孙组件传递数据
  • 使用方法:provide在父组件中返回要传给下级的数据,inject在需要使用这个数据的子孙辈组件中注入数据
  • 使用场景:由于vue有$parent属性可以让子组件访问父组件,但是孙组件想要访问祖先组件比较困难,通过provide/inject可以轻松实现跨级访问父组件的数据

参考:
https://blog.youkuaiyun.com/weixin_44834981/article/details/119797571
https://blog.youkuaiyun.com/weixin_42566993/article/details/127045794

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值