一、 生命周期方法详解
钩子函数 | 详情 | 场景 | 备注 |
---|---|---|---|
beforeCreate | 实例初始化之后,组件被创建时期,这个时候的 el,data,message 都是 underfined | 可以加入 loading 事件;在服务器端的应用场景中,这个时候发送数据请求比较多一些 | |
created | 实例创建完成后,data、methods 被初始化 | 结束 loading 事件;推荐这个时候发送请求数据,尤其是返回的数据与绑定事件有关时 | |
beforeMount | 挂载初始之前,完成 el 初始化,render 被初次调用 | 也可以发送数据请求 | 在服务器端渲染期间不会被调用 |
mounted | 完成挂载 | 获取 el 中 DOM 元素,进行 DOM 操作;如果返回的数据操作依赖 DOM 完成,推荐这个时候发送数据请求 | 在服务器端渲染期间不会被调用 |
beofreUpdate | 挂载开始之前调用 | 挂载完成之前访问现有 DOM ,比如手动移除已添加的事件监听器;也可以进一步修改数据 | 在服务器渲染期间不会被调用,只有初次渲染会在服务端调用 |
updated | 由于数据更改,重新渲染界面时调用 | 可执行依赖于 DOM 的操作 | 服务器端渲染期间不会被调用 |
activated | keep-alive 组件激活时调用 | 服务器端渲染期间不会被调用 | |
deactivated | 组件停用时调用 | 服务器端渲染期间不会被调用 | |
beforeDestroy | 实例销毁之前调用 | 删除钱发出确认信息;清理定时器 | 服务器端渲染期间不会被调用 |
destroyed | 实例销毁后调有。调用后,所有东西都会被解绑,所有的事件监听器会被移动,子实例也会被销毁 | 提示已删除 | 服务器端渲染期间不会被调用 |
二、生命周期执行流程
1.创建
1.我们在new Vue()新建Vue实例后会先初始化数据、事件、生命周期函数。然后执行beforeCreate()函数:组件创建之前(此时没有数据)。在进行对初始化数据的注入和校验后执行created():组件创建完成。
2.然后判断是否有el元素,如果有el元素就直接判断是否有template模板元素。如果没有el元素就会先判断是否调用vm.$mounted(el)函数,然后在判断是否有template模板元素。
3.如果有template模板元素就直接render()进行渲染。 没有的话就会把el外部的HTML(就是你绑定的el元素)作为template编译。
4.然后执行beforeMount():即将挂载、Dom挂载之前。在创建vm.$el并用其替换el。 (这部分是虚拟Dom)
5.然后执行mounted():DOM挂载完成。
2.运行
1.如果data数据发生改变,会到beforeUpdate():更新之前的Dom,然后再次虚拟Dom重新渲染并应用更新。再执行updated():更新之后的Dom,进行再次挂载完成。
3.销毁
1.比如当组件使用v-if进行销毁时,会到beforeDestroy():销毁之前,进行解除绑定、销毁子组件以及事件监听器。然后destroyed():销毁完成。
三、代码
activated()和deactivated()要配合<keep-alive></keep-alive>使用 keep-alive将目前状态放入缓存,下次获取在到缓存中获取使用。
<!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>
</head>
<style>
.active{
color: red;
}
</style>
<body>
<div id="app">
<!-- 使用子组件 -->
<App></App>
</div>
<script src="vue .js"></script>
<script>
// beforeCreate
// created
// beforeMount
// mounted
// beforeUpdate
// updated
// activated
// deactivated
// beforeDestroy
// destroyed
Vue.component('Test',{
data(){
return{
msg:'小张同学',
isRed:false
}
},
methods: {
handleClick() {
this.msg = '学习vue生命周期'
this.isRed = !this.isRed;
},
},
template:`
<div>
<button @click='handleClick'>改变</button>
<h3 :class='{active:isRed}'>{{msg}}</h3>
</div>
`,
beforeCreate(){
console.log('组件创建之前',this.$data);
},
created () {
// 再这个方法中请求发送ajax,请求后端的数据
console.log('组件创建完成',this.$data);
},
beforeMount () {
// 即将挂载
console.log('Dom挂载之前',document.getElementById('app'));
},
mounted () {
console.log('DOM挂载完成',document.getElementById('app'));
},
beforeUpdate () {
// 获取更新之前的Dom
console.log('更新之前的Dom',document.getElementById('app').innerHTML);
},
updated () {
// 获取最新的Dom
console.log('更新之后的Dom',document.getElementById('app').innerHTML);
},
beforeDestroy () {
console.log('销毁之前');
},
destroyed () {
console.log('销毁完成');
},
activated () {
console.log('组件被激活了');
},
deactivated () {
console.log('组件被停用了');
},
})
const App = {
data(){
return{
isShow:true
}
},
methods: {
myClick() {
this.isShow = !this.isShow;
}
},
components:{
},
template:`
<div>
<keep-alive>
<Test v-if='isShow'></Test>
</keep-alive>
<button @click='myClick'>创建销毁</button>
</div>
`,
}
new Vue({
el:'#app',
data:{
},
components:{
//挂载子组件
App
}
})
</script>
</body>
</html>