这是我参与11月更文挑战的第14天,活动详情查看:2021最后一次更文挑战
一、先上一段vue3的代码
这是基本的展示数值,然后新增数字的例子:
<div id="app">
<p>{{state.count}}</p>
<p>doubleCounter:{{state.doubleCounter}}</p>
<button @click='handlerAdd'>add</button>
</div>
<script type="text/javascript">
const {createApp,reactive,computed,onMounted} = Vue;//引用所有需要的方法
createApp({
setup(props,{emit,slots,attrs}) {
//对象的响应式
const state = reactive({
count: 0,
doubleCounter: computed(()=> state.count * 2)
})
//新增方法
function handlerAdd() {
state.count++;
}
//生命周期钩子onMounted,onBeforeMount
onMounted(()=> {
console.log('onMounted')
})
//暴露给render,让外部HTML可以访问
return {
state,
add
}
}
}).mount('#app');
</script>
这段代码中没有任何this,在vue3中this没有任何意义,以前vue中是选项的模式,上面定义data下面写方法,现在可以在上面定义变量,就可以立马写方法,这样的话更方便阅读也可以把这段方法提取出来,可读性,复用性组织也更好。
当然,如果还是不习惯上面这样的代码, 还是可以使用下面的方式:
createApp({
data() {
return {
foo: 1
}
}
setup(props,{emit,slots,attrs}) {
const vm = getCurrentInstance();//获取上下文
console.log(vm.ctx.foo);//相当于this
}
}).mount('#app');
上面这个例子就是结合了vue2版本,用data选项,下面使用getCurrentInstance()获取上下文,得到的vm.ctx就相当于this,但是不建议这样写。
总结
Vue最初选项API中存在大量的this上下文,对TypeScript类型判断不友好,在composition-api中利用纯变量和函数,规避了对this的使用,就自然而然的有更好的类型判断能力。
三、整体流程
-
mount:实例挂载
-
render:渲染传入的vnode到指定的容器中
-
patch:初始化处理根组件
-
mountComponent:初始化走挂载流程,创建组件实例
-
setupComponent:安装组件,选项处理
-
setStatefulComponent:安装状态组件
-
finishComponentSetup:完成组件的安装
-
applyOptions:支持旧版本的选项方法,对data选项做响应式处理使用的是reactive函数
-
resolveData:数据响应式,获取数据对象
-
reactive:对data做响应式处理,无论是以vue2的方法写还是vue3的方式,最后都是走这个方法
其中最重要的setupRenderEffect:使当前组件渲染函数成为响应式数据依赖,从而数据发生变化,渲染函数还可以正常执行,也就是使用effect函数做依赖收集