Vue组件间通信
vue组件间通信分为以下几种:
- 父向子传递数据,用自定义属性
- 子向父传递数据,用自定义事件
- 兄弟(任意)组件间传递数据,用全局事件总线或者消息订阅与发布
背吧,面试题要是说让你简述一下,就上面这段话拿过来回答呗。下面就介绍一下这几种通信方式的简单用法
1.父向子传递数据
前面已经说了,父向子传递数据用的是自定义属性
,接下来就让我们看下代码是怎么写的
- //这是父组件,Father.vue
- <template>
- <div class="father">
- <!-- 父组件向子组件传递person对象 -->
- <Son :person="person"/>
- </div>
- </template>
- <script>
- export default {
- data (){
- return {
- person:{name:'张三',age:18,sex:'男'}
- }
- }
- }
- </script>
- //这是子组件,Son.vue
- <template>
- <div class="son">
- <h2>我是子组件</h2>
- <div>
- <h4>个人信息展示</h4>
- <ul>
- <li><label>姓名:</label><span>{{person.name}}</span></li>
- <li><label>年龄:</label><span>{{person.age}}</span></li>
- <li><label>性别:</label><span>{{person.sex}}</span></li>
- </ul>
- </div>
- </div>
- </template>
- <script>
- export default {
- //子组件通过props接收父组件传递过来的数据
- props:['person']
- }
- </script>
这里题外话,简单的介绍下props
1.props的大小写
当我们使用自定义属性传递数据的时候,自定属性的名称
可能不会简单的是一个单词,那这个时候我们该如何书写呢?请看如下代码
- //父组件 父组件传递了 company-name
- <Son company-name = "Microsoft"></Son>
- //子组件 子组件接收时的写法
- <script>
- export default {
- props:['companyName']
- }
- </script>
2.props的两种写法
第一种是简单的写法
- props:['name','age','sex']
第二种是对象形式的写法
- props:{
- name:{
- type:String,
- required:true,
- default:''
- },
- age:{
- type:Number,
- required:true,
- default:0
- },
- sex:String
- }
这两种写法根据实际情况来决定,一般的使用第一种就可以满足需求
3.传递动态props
通过v-bind
为组件传递动态数据类型
- <Son :categoryList="categoryList"></Son>
- <script>
- export default {
- data (){
- return {
- //购物车列表数据
- categoryList:[]
- }
- }
- }
- </script>
2.子向父传递数据
前面讲到,子向父传递数据需要用到自定义事件
,但是这里通过自定义属性
也可以实现,我们一起来看一下
- //子组件 Son.vue
- <template>
- <div class="son">
- <button @click="sendMsgForFather">发送信息</button>
- </div>
- </template>
- <script>
- export default {
- props:['getSonMessage'],
- methods:{
- sendMsgForFather(){
- this.getSonMessage(`我是子组件,你好啊`)
- }
- }
- }
- </script>
- //父组件 Father.vue
- <template>
- <div class="father">
- <h1>我是父组件</h1>
- <Son :getSonMessage="getSonMessage"/>
- </div>
- </template>
- <script>
- import Son from '@/components/Son.vue'
- export default {
- components : {
- Son
- },
- methods:{
- getSonMessage(msg){
- console.log(`我收到了子组件传递过来的信息:${msg}`);
- }
- }
- }
- </script>
下面这段代码是通过自定义事件
实现的
- //子组件 Son.vue
- <template>
- <div class="son">
- <button @click="sendMsgForFather">发送信息</button>
- </div>
- </template>
- <script>
- export default {
- props:['getSonMessage'],
- methods:{
- //发送信息给父组件
- sendMsgForFather(){
- this.$emit('eventN',`我是子组件,hello`)
- }
- }
- }
- </script>
- //父组件 Father.vue
- <template>
- <div class="father">
- <h1>我是父组件</h1>
- <Son @eventN="demo"/>
- </div>
- </template>
- <script>
- import Son from '@/components/Son.vue'
- export default {
- components : {
- Son
- },
- methods:{
- demo(msg){
- console.log(`触发了demo函数,${msg}`);
- }
- }
- }
- </script>
其实理解起来还是很简单的,给子组件上绑定一个自定义事件,子组件上的自定义事件通过$emit
触发,而$emit
通过子组件上的按钮点击事件来触发,最终将数据发送给父组件,父组件通过demo函数拿到并展示数据,估计听完我说的,肯定蒙了。研究一下代码,自己敲一下就明白了
3.兄弟(任意)组件间的传值
兄弟组件间的传值方法比较多,包括我们甚至可以通过逐层使用自定义属性
和自定义事件
来实现,但代码看起来可能不是那么舒服,甚至把自己都给绕晕了,我自己也试过,想想这种方法知道就行,效率太低了。接下来就讲讲目前主流的几种兄弟组件间传值的方法
3.1全局事件总线
- //main.js中安装全局事件总线
- new Vue({
- render: h => h(App),
- beforeCreate(){
- Vue.prototype.$bus = this //安装全局事件总线
- }
- }).$mount('#app')
- //消息发送方 SendCom.vue
- <template>
- <div class="send-container">
- <!-- SendCom 向组件 GetMsg 发送信息,通过$emit触发自定义事件-->
- <button @click="sendMsg">发送消息</button>
- </div>
- </template>
- <script>
- export default {
- methods:{
- sendMsg(){
- this.$bus.$emit('eventB','hello')
- }
- }
- }
- </script>
- //消息接收方 GetMsg.vue
- <template>
- <div class="get-msg-container">
- </div>
- </template>
- <script>
- export default {
- mounted() {
- console.log(this);
- this.$bus.$on('eventB', (data) => {
- console.log(`我是事件接受方Demo2,我收到了数据${data}`);
- });
- },
- beforeDestroy() {
- this.$bus.$off('eventB') //在使用完后将事件解绑
- }
- };
- </script>
3.2消息订阅与发布
消息订阅与发布在原生js下实现比较复杂,这里使用第三方库pubsub-js
,通过npm i pubsub-js
安装。
- //消息订阅者(接收方) Subscribe.vue
- <template>
- <div class="subscribe">
- </div>
- </template>
- <script>
- import pubsub from 'pubsub-js'
- export default {
- mounted(){
- this.pubId = pubsub.subscribe('message',(msgName,data)=>{
- console.log(`我收到了消息${msgName},内容是${data}`);
- })
- },
- beforeDestroy(){
- pubsub.unsubscribe(this.pubId)
- }
- }
- </script
- //消息发布者(发送方) Publish.vue
- <template>
- <div class="publish">
- <button @click="sendMsg">点击发送</button>
- </div>
- </template>
- <script>
- import pubsub from 'pubsub-js'
- export default {
- methods:{
- sendMsg(){
- pubsub.publish('message','这是订阅的消息')
- }
- }
- }
- </script>
总结
本篇文章就到这里了,希望能够给你带来帮助,也希望您能够多多关注w3xue的更多内容!