Vue2 生命周期与数据共享

3个月前 (11-02) 502次浏览 已收录 1个评论

生命周期

生命周期是指一个组件从创建->运行->销毁的整个阶段,强调的是一个时间段

生命周期函数

生命周期函数(比如beforeCreate)是由vue提供的内置函数,会伴随着组件的生命周期,自动按次序执行。强调的是一个时间点

它有三个阶段,分别包含以下生命周期函数。

创建阶段

  • beforeCreate
  • created
  • beforeMount
  • mounted

运行阶段

  • beforeUpdate
  • updated

销毁阶段

  • beforeDestroy
  • destroyed

声明周期图

下图是vue官方给的生命周期参考图。

methods:{
show(){
    console.log('调用了life组件')
}
},
created(){
//在created生命周期函数阶段下,methods都已经创建好,且是可用状态,故可以进行调用。
    this.show()
}
}
created生命周期函数经常用在ajax中请求数据,即当执行到created阶段,立马去调用请求数据的方法,并且把请求到的数据,转存到data中,供template模版渲染的时候使用。


当数据发生变化之后,未来能够操作到最新的dom结构,必须把操作代码写到updated生命周期函数中,因为这个生命周期函数下的dom结构是同步于最新的数据。相反beforeUpdate就不是,它只是有了最新数据,并没有同步到dom结构中。


数据共享

父向子传值

父组件向子组件共享数据需要使用自定义属性。即子组件通过自定义属性props来接收父组件传过来的数据

简单类型数据是复制一份值再传过去;复杂数据类型是把它的引用给传过去。

父组件

<left :mes:"message"></left>
...
export default{
  data(){
         return{
               message:'zzl'
}
}
  components:{
    'left': left,//键值相同,可以省略 
    right,
    life
  }
}

子组件

<p>mes={{mes}}</p>
export default{
      props:['mes']
}

子向父传值

子组件向父组件共享数据使用自定义事件,也就是@click的写法与理解。

子组件

export default{
  data(){
    return {count:0}
  },
  methods:{
    add(){
      this.count+=1
      //修改数据时,通过调用$emit()触发自定义事件numchange
      this.$emit('numchange',this.count)
    }
  }
}

父组件

<biaoqian @numchange="getNewCount">
<!--如果指定的方法不带有小括号,则它默认自带事件对象numchange传过来的值,
如果带有小括号,即里面是该方法自己接收除事件对象传过来的值,即覆盖了默认值。
但是此时方法里面传入$event的话,
一样还是会拿到事件对象传过来的值,即方法有了两个值。
也可根据前面写的Vue初始文章的事件对象来理解上面的内容。-->
  </biaoqian>
export default{
  data(){
    return{
      countFromLeft:0
    }
  },
  methods:{
    //自定义getNewCount事件处理函数,接收子组件传过来的值
    getNewCount(val){
      console.log('dd')
      this.countFromLeft=val
    }
  }
}

兄弟组件之间的数据共享

在vue2中,兄弟组件之间的数据共享用EventBus。

  • 创建eventBus.js模块,并向外共享一个Vue的实例对象
  • 在数据发送方,调用bus.$emit(‘事件名称’,要发送的数据)方法触发自定义事件
  • 在数据接收方,调用bus.$on(‘事件名称’,事件处理函数)方法注册一个自定义事件

兄弟组件A(数据发送方)

<button @click="send">发送</button>
...
<script>
import bus from './eventBus.js'
export default{
  data(){
    return {
      str:'zzl'
    }
  },
  methods:{
    send(){
      bus.$emit('fenxiang',this.str)
    }
  }
}
</script>

eventBus.js

import Vue from 'vue'
//向外共享Vue的实例对象
export default new Vue()

兄弟组件C(数据接收方)

<script>
import bus from './eventBus.js'
export default{
  data(){
    return{
      msgFromLeft:''
    }
  },
//在这个created生命周期函数
  created(){
    bus.$on('fenxiang',valstr=>{
      this.msgFromLeft=valstr
      //console.log(this.msgFromLeft)
    })
  }
}
</script>
on是用来声明事件的,emit是用来触发事件的。

ref引用

引用dom

ref可以在不依赖于jQuery的情况下,获取和操作dom元素或组件的引用。

<template>
<div class="rootbox">
  <h1 ref="myh1">App根组件</h1>
  <button @click="showThis">打印</button>
</div>
</template>
<script>
export default{
  methods:{
    showThis(){
      // console.log(this.$refs.myh1)
      this.$refs.myh1.style.color="red"
    }
}
}
</script>

引用组件

ref也可以引用页面上的组件实例。

<button @click="onrel">重置left</button>
comLeft是组件的实例
<left ref="comLeft"></left>
...
export default{
  methods:{
    onrel(){
      //直接操作子组件的属性值
      // this.$refs.comLeft.count=0
      
      //直接操作子组件的方法
      this.$refs.comLeft.rel()
    }
  },
  components:{
    'left': left,//键值相同,可以省略 
    right,
    life
  }
}

this.$nextTick(callback)方法

当dom根据渲染好的数据重新更新好了dom,才会调用这个回调函数,相当于延迟了。

也可以这样理解,即等组件的dom元素更新完之后,再去执行回调函数。

  <input type="text" v-if="inputflag" @blur="showbutton" ref="iptRef"/>
methods:{
      showinput(){
        //切换布尔值,展示输入框
        this.inputflag=true//将要把文本框展示出来,但是此时只是把布尔值改为true而已,页面还没来得及更新,所以页面上还是按钮,并没有文本框,所以拿不到文本框的引用,又所以下面的iptRef拿不到,
        //this.$refs.iptRef.focus()此时这样会报错,因为此时的iptRef拿不到,
        //此时会根据上面的布尔值重新渲染完页面(有了文本框)之后再去执行这个回调函数。
        this.$nextTick(()=>{
          this.$refs.iptRef.focus()//自动获得焦点
        })
      }
}

渣渣龙, 版权所有丨如未注明 , 均为原创丨本网站采用BY-NC-SA协议进行授权
转载请注明原文链接:Vue2 生命周期与数据共享
喜欢 (4)

您必须 登录 才能发表评论!

(1)个小伙伴在吐槽
  1. this.$nextTick(()=>{}) 一旦完成界面更新就调用回调函数,它要写在数据更新之后
    厚积薄发2021-11-24 22:20