因为vue更新后与文中demo不兼容 ,再此说明一下, 本文的全部内容是基于3.0.0-alpha.1
版本编写,各位小伙伴在学习的时候注意下版本哦 javascript
首先,在GitHub上拉取最新代码html
$ git pull https://github.com/vuejs/vue-next.git $ cd vue-next && yarn 复制代码
下载完成以后打开代码, 开启sourceMap 一、tsconfig.json 把sourceMap字段修改成true
前端
rollup.config.js
中,手动键入
output.sourcemap = true
yarn dev
/demo/index.html
vue
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> <style> .container { text-align: center; font-size: 24px; padding: 32px; } </style> <script src="../packages/vue/dist/vue.global.js"></script> </head> <body> <div id="app"></div> </body> <script src="./index.js"></script> </html> 复制代码
/demo/index.js
java
const { reactive } = Vue var App = { template: ` <div class="container"> {{message}} </div>`, setup() { const state = reactive({message: "Hello World!!!"}) return { ...state } } } Vue.createApp().mount(App, '#app') 复制代码
在浏览器打开我们编写的html文件, react
serve
库来建立的,有兴趣的话能够看下
serve
anyway,我们接着看我们的/demo/index.js
文件,能够看到,我们用了setup, reactive
等函数,这就是Vue3的Composition API
,相对于Vue2的组件来讲 3 可让咱们很简单的经过组合API的方式建立一个 基于Vue3 响应式 Web 应用。 下边我会经过一个个的demo为你们详细解释这些API。git
接下来我们实现一个双向绑定的demo!!!github
const { reactive } = Vue let App = { template: ` <div class="container"> <input v-model="state.value"/>{{state.value}} </div>`, setup() { const state = reactive({ value: '' }) return { state } } } Vue.createApp().mount(App, '#app') 复制代码
beforeCreate
和
Created
这两个生命周期。
setup接受两个参数,第一个参数是props, 另外一个参数是context,因此你们在使用2.0时习惯的在this下获取属性的方式 ,在 vue3.0 中,变成了:shell
setup(props, ctx) { console.log(props, ctx) } 复制代码
不过在模板中仍然能够直接使用props的属性值,例如:npm
let Child = { template: `<div>{{title}}</div>`, setup(props, context) { console.log(props) } } let App = { template: ` <div class="container"> <Child title="test props"/> </div>`, components: { Child } } Vue.createApp().mount(App, '#app') 复制代码
那reactive???以前用的 data呢??? 在Vue3中,咱们能够把数据通过 reactive 加工变成响应式的对象,用于模版的渲染数据, 固然Vue的向下兼容 仍是容许咱们使用data的方式实现,但既然Vue3出新的写法了,何不尝试一波呢
const { reactive, toRefs } = Vue let App = { template: ` <div class="container"> count: {{count}} <button @click="handlerCountAdd"> Click ++ </button> </div>`, setup() { const state = reactive({ count: 0 }) const handlerCountAdd = () => { state.count++ } return { ...toRefs(state), handlerCountAdd } } } Vue.createApp().mount(App, '#app') 复制代码
const App = { template: ` <div class="container"> {{value}} </div>`, setup() { const value = ref(1) return { value } } } Vue.createApp().mount(App, '#app') 复制代码
reactive
建立的响应式对象 在模板中访问的话,则须要
state.xxx
, 例:
const App = { template: ` <div class="container"> {{state.value}} </div>`, setup() { const state = reactive({ value: 'reactive' }) return { state } } } Vue.createApp().mount(App, '#app') 复制代码
这样访问属性确实有点麻烦,vue3提供的toRefs
正是为咱们解决这个问题的,toRefs把一组的响应式对象拆成单个的响应式对象,就可以在模板中直接访问了,及:
const App = { template: ` <div class="container"> {{value}} </div>`, setup() { const state = reactive({ value: 'reactive' }) return toRefs(state) } } Vue.createApp().mount(App, '#app') 复制代码
let App = { template: ` <div class="container"> value: <input v-model="value"/> <br/> rvalue: {{rvalue}} </div>`, setup() { const state = reactive({ value: '', rvalue: computed(() => state.value .split('') .reverse() .join('') ) }) return toRefs(state) } } Vue.createApp().mount(App, '#app') 复制代码
computed
计算属性实现了反转字符串的功能,这个函数虽然简单,可是功能很强大,正如vue官网所说:对于任何复杂逻辑,你都应当使用计算属性。
你们都知道, 在Vue3中实现数据响应式的方案由Vue2中的Object.defineProperty 换成了 Proxy,关于数据响应式的Api上边说到了一些,还剩下effect和watch没有说起到,effect是数据响应式中重要的一部分,watch和computed都是基于 effect 的,下边来看下代码
let App = { template: ` <div class="container"> count: {{count}} <button @click="handlerCountAdd"> Click ++ </button> </div>`, setup() { const state = reactive({ count: 0, value: 1 }) const handlerCountAdd = () => { state.count++ } watch( () => state.count, val => { console.log('watch', state.count) console.log('watch', state.value) } ) effect(() => { console.log('effect', state.count) console.log('effect', state.value) }) return { ...toRefs(state), handlerCountAdd } } } Vue.createApp().mount(App, '#app') 复制代码
首先,effect 在响应式数据变化的时候就会执行,执行次数根据响应式数据的个数来决定,例如
let App = { template: ` <div class="container"> <button @click="handlerCountAdd"> Click ++ </button> </div>`, setup() { const r = ref(1) const s = ref(1) const t = ref(1) const handlerCountAdd = () => { r.value *= 1 s.value *= 2 t.value *= 3 } effect(() => { console.log('effect', [r.value, s.value, t.value]) }) return { handlerCountAdd } } } Vue.createApp().mount(App, '#app') 复制代码
而watch则点击一次 ,只会触发执行一次
let App = { template: ` <div class="container"> <button @click="handlerCountAdd"> Click ++ </button> </div>`, setup() { const state = reactive({ count: 0, value: 1 }) const r = ref(1) const s = ref(1) const t = ref(1) const handlerCountAdd = () => { r.value *= 1 s.value *= 2 t.value *= 3 } watch([r, s, t], val => { console.log('watch', val) }) return { handlerCountAdd } } } Vue.createApp().mount(App, '#app') 复制代码
好了,vue3Composition Api
中经常使用的一些函数在咱上边的demo中使用了,接下来我们对比一下2和3的生命周期函数有什么改变
Vue2 | Vue3 |
---|---|
beforeCreate | setup(替代) |
created | setup(替代) |
beforeMount | onBeforeMount |
mounted | onMounted |
beforeUpdate | onBeforeUpdate |
updated | onUpdated |
beforeDestroy | onBeforeUnmount |
destroyed | onUnmounted |
errorCaptured | onErrorCaptured |
虽然Vue官方说能够直接运行run dev 就能够对其进行调试,但是运行该命令后,是生成事后的代码,不能对其编写的ts源码进行调试。
篇幅很大,感谢你们耐心观看,文中若有错误欢迎指正。
我是
Colin
,能够扫描下方二维码加我微信,备注交流。
感谢H5兽超进化前端菜鸡兽指正文章中的问题