组件间的通讯方式

一、父传子

在Vue.component(){}中,加入与template、data同级的props用来接受传值

//接受传值  利用props
      props:{
        // 自定义接受
        //定义数据类型
        type : String,
        size:Number,
        pageSize:{
          //定义多种数据类型,用数组形式
          type:[Number,String],
           //设置默认值,若为基本数据类型不存在深拷贝的问题则可以写成对象的形式
           //(也可以写成函数形式),复杂数据类型写为函数形式,目的也是为了数据隔离,
          default(){
            return 5
          }
        }
      },

 然后再vue实例(即父级)控制区内加入组件标签,给标签的属性加冒号(:)即可获取到父级的data中的数据

二、子传父

 (一)子组件调用父组件的方法

1.在父组件中给引用的子组件注册一个事件(这个事件的名字是自定义的)

<div id='app'>
      <div class="container">
        <!-- 1.在父组件中给引用的子组件注册一个事件(这个事件的名字是自定义的) -->
        <!-- 可以传入$event(在这里只能写$event来获取子组件的参数)也可以拿到子组件传递的数据 -->
        <son @comment="comment($event,'hello')"></son>
        <ul class="list-group">
          <li v-for="(item,index) in list " :key="index" class="list-group-item">{{item.content}} 
          <span class="badge">{{item.name}}</span>
          </li>
        </ul>
      </div>
  </div>



--------------------js中
 methods: {
      // 1.在父组件中给引用的子组件注册一个事件(这个事件的名字是自定义的)
      // 父组件这个方法没有自定参数,在父组件的方法直接加这个参数就可以拿到子组件给父组件传递的数据
       comment(data){
         console.log(data);
         this.list.push(data)
        sessionStorage.setItem('list',JSON.stringify(this.list))
       }
    },

2.子组件可以触发这个事件$emit('事件名字')

(1)$emit方法第二个参数可以定义子组件给父组件传递的内容

 Vue.component('son',{
     template:"#son",
     data(){
      return {
        name:'',
        content:''
      }
     } ,
     methods:{
      issue(){
        if(this.name != '' && this.content != '') {
          // 2.子组件可以触发这个事件$emit('事件名字')
          // 1.$emit方法第二个参数可以定义子组件给父组件传递的内容
          this.$emit('comment',{
            name:this.name,content:this.content
          })
          this.name = ''
          this.content = ''
        } else {
          window.alert('请输入评论人及评论内容')
        }
      }
     }
    })

(二)在父组件中怎么拿到这内容

 1.父组件这个方法没有自定参数,在父组件的方法直接加这个参数就可以拿到

const vm = new Vue({
    el: '#app',
    data: {
      list:[]
    },
    methods: {
      // 1.在父组件中给引用的子组件注册一个事件(这个事件的名字是自定义的)
      // 父组件这个方法没有自定参数,在父组件的方法直接加这个参数就可以拿到子组件给父组件传递的数据
       comment(data){
//data就是子组件传来的数据
         console.log(data);
         this.list.push(data)
         sessionStorage.setItem('list',JSON.stringify(this.list))
       }
    },
  })

2.父组件有自定义参数,可以传入$event也可以拿到子组件传递的数据。通过$event只能传递第一个参数

  <div id='app'>
      <div class="container">
        <!-- 可以传入$event(在这里只能写$event来获取子组件的参数)也可以拿到子组件传递的数据 -->
        <son @comment="comment($event,'hello')"></son>
      </div>
  </div>

data即为标签中的$event,也就是子组件传来的值,data为标签中调用方法时传的参 

  const vm = new Vue({
    el: '#app',
    data: {
      list:[]
    },
    methods: {
      //父组件有自定义参数,可以传入$event也可以拿到子组件传递的数据。通过$event只能传递第一个参数。
      comment(data,data2){
//data即为标签中的$event,也就是子组件传来的值,data为标签中调用方法时传的参
        console.log(data);
        console.log(data2);
        this.list.push(data)
        sessionStorage.setItem('list',JSON.stringify(this.list))
      }
    },
  })

三、vuex

        1.定义:

        Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储,管理应用中所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。

        2.vuex解决的问题

                (1)行统一的状态管理,解决不同组件共享数据的问题。

                (2)不同视图需要变更同一状态的问题。

                (3)使用vuex之后,状态变化更加清晰。

        3.uvex的五大核心模块

(1)state

        state是什么? 是一个单一状态树,是vuex中为一个的数据源,我们的数据都是放在state中的。
组件中去取state的值,通过this.$store.state,
(2)getters

对state中的数据进行加工(派生)
取getters中的值,通过this.$store.getters,
(3)mutation

修改state中的值,我们state每次变化,都应该由mutation去修改,方便追踪数据的流转。

        ①this.$store.commit('mutation类型(函数名)',"参数,参数一般是对象形式")

        ②this.$store.commit({type:'mutation类型(函数名)'},...其他参数)

(4)action

        action类似于mutation,不同的是

        action可以包含异步操作

        action不能直接修改state,如果想修改state的话,需要触发mutation

(5)module

        由于使用单一的状态树,项目中的状态会集中在一起,导致难以维护,这个时候可以通过module对store进行拆分。
        使用module之后,每个模块都有自己的state、mutation等内容,方便维护
 

import Vuex from 'vuex'

Vue.use(Vuex)

export default new Vuex.Store({
  state: {
    // number:5,
    visible: false,
    userInfo:{},
  },
  getters: {

  },
  mutations: {
    changeVisible(state,payload){
      state.visible = payload
    },
    changeUserInfo(state,payload){
      state.userInfo = payload
    }
  },
  actions: {
  },
  modules: {
  }
})

四、ref

 (一)获取dom节点

1.给dom节点记上ref属性,可以理解为给dom节点起了个名字。

<!-- 给dom节点记上ref属性,可以理解为给dom节点起了个名字。 -->

    <h1 ref="h11" id="h11">h1标签</h1>

2.加上ref之后,在$refs属性中多了这个元素的引用。

3.通过vue实例的$refs属性拿到这个dom元素。

const vm = new Vue({
      el: '#app',
      data: {
        
      },
      methods: {
        changeSon(){
          
          this.$refs.myson.sonMsg = '被父组件的按钮改变'
        }
      },
      mounted(){
        console.log(document.getElementById('h11'));
        console.log(this.$refs);
        // 加上ref之后,在$refs属性中多了这个元素的引用。
        // 通过vue实例的$refs属性拿到这个dom元素,可以对dom元素进行操作
        this.$refs.h11.style.color = 'red'
      },
    })

 (二)获取组件

1.给组件记上ref属性,可以理解为给组件起了个名字。

 <!-- 给组件记上ref属性,可以理解为给组件起了个名字。 -->

    <son id="myson" ref="myson"></son>

2.加上ref之后,在$refs属性中多了这个组件的引用。

3.通过vue实例的$refs属性拿到这个组件的引用,之后可以通过这个引用调用子组件的方法,或者获取子组件的数据。

    const vm = new Vue({
      el: '#app',
      data: {
        
      },
      methods: {
        changeSon(){
          
          this.$refs.myson.sonMsg = '被父组件的按钮改变'
        }
      },
      mounted(){
        // 加上ref之后,在$refs属性中多了这个组件的引用
        // 通过vue实例的$refs属性拿到这个组件的引用,之后可以通过这个引用调用子组件的方法,或者获取子组件的数据
        // 获取子组件的数据
        console.log(this.$refs.myson.sonMsg);
        //可以通过这个引用调用子组件的方法
        console.log(this.$refs.myson.log1());
      },
    })

五、本地缓存

1.localStorage

(1)保存数据:localStorage.setItem(key,value)

(2)读取数据:localStorage.getItem(key)

(3)删除单个数据:localStorage.removeItem(key)

(4)删除所有数据:localStorage.clear()

(5)得到某个索引的key:localStorage.key(index)

2.sessionStorage

(1)保存数据:sessionStorage.setItem(key,value)

(2)读取数据:sessionStorage.getItem(key)

(3)删除单个数据:sessionStorage.removeItem(key)

(4)删除所有数据:sessionStorage.clear()

(5)得到某个索引的key:sessionStorage.key(index)

六、事件总线

 6.1定义事件总线对象


import Vue from 'vue'
import App from './App.vue'
 
Vue.config.productionTip = false
 
//给Vue绑定属性
Vue.prototype.xyz=100;
// Vue.prototype.$EventBus=vm
 
new Vue({
  beforeCreate(){
  //安装事件总线
  Vue.prototype.abc=900;
  Vue.prototype.$EventBus=this
 },
  render: h => h(App),
}).$mount('#app')

6.2  向总线发送事件

语法:this.$EventBus.$emit(发送的事件名,传递的参数)

<!--  -->
<template>
  <div id="demo01">
    <h1>Demo01组件</h1>
    <h2>从Demo02接受的收据:{{msg}}</h2>
    <button @click="fasong">发送数据给Demo02</button>
  </div>
</template>
 
<script>
export default {
  name: "Demo01",
  data () {
    return {
      msg: ''
    }
  },
  methods: {
    test01 (data) {
      console.log(data);
      this.msg = data
    },
    fasong () {
      this.$EventBus.$emit("send", "我是Demo01页面");
    }
  },
  mounted () {
    // console.log(this);
    // 2.接受全局的haha事件
    this.$EventBus.$on('haha', this.test01)
  }
}
</script>
<style scoped>
#demo01 {
  background-color: red;
  padding: 20px;
  margin-bottom: 20px;
}
</style>

6.3接收总线事件

    语法:this.$EventBus.$on(监听的事件名, 回调函数)

<!--  -->
<template>
  <div id="demo02">
    <h1>Demo02组件</h1>
    <button @click="sendData">发送事件给Demo01</button>
    <h2>从Demo01接受的收据:{{msg}}</h2>
  </div>
</template>
 
<script>
export default {
  name: "Demo02",
  data () {
    return {
      msg: ''
    }
  },
  methods: {
    sendData () {
      // 触发全局的haha事件
      this.$EventBus.$emit("haha", '老王')
    },
    display (data) {
      console.log(data);
      this.msg = data
    }
  },
  mounted () {
    // console.log(this.abc);
    console.log(this.$EventBus);
    this.$EventBus.$on("send", this.display)
  }
}
</script>
<style scoped>
#demo02 {
  background-color: blue;
  padding: 20px;
}
</style>

 6.3总线事件解绑

   语法:this.$EventBus.$off(要移除事件名)

   在组件离开,也就是被销毁前,要将该监听事件给移除,以免下次再重复创建监听。

  beforeDestory () {
    //移除事件监听send
    this.$EventBus.off("send")
  }
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

前端小菜凯

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值