整理的一些 Vue3 知識(shí)點(diǎn),初學(xué)者看完就能上手做項(xiàng)目
點(diǎn)擊上方關(guān)注?前端技術(shù)江湖,一起學(xué)習(xí),天天進(jìn)步
看完你就基本可以上手搞開發(fā)了,本文適合Vue初學(xué)者,或者Vue2遷移者,當(dāng)然還是建議Vue3官網(wǎng)完全過一遍。不適合精通原理,源碼的大佬們。
先推薦兩個(gè)vscode插件
Volar
首先推薦Volar,使用vscode開發(fā)Vue項(xiàng)目的小伙伴肯定都認(rèn)識(shí)Vetur這個(gè)神級(jí)插件,有了它可以讓我們得開發(fā)如魚得水。那么Volar可以理解為Vue3版本的Vetur,代碼高亮,語法提示,基本上Vetur有的它都有。
特色功能
當(dāng)然作為新的插件出山,肯定有它獨(dú)有的功能。
多個(gè)根節(jié)點(diǎn)編輯器不會(huì)報(bào)錯(cuò)
Vue3是允許我們有多個(gè)根節(jié)點(diǎn)的,但是我們?nèi)绻褂肰etur就會(huì)報(bào)錯(cuò),不會(huì)影響運(yùn)行,但是看起來就很煩。所以當(dāng)我們轉(zhuǎn)向Volar那么就不會(huì)出現(xiàn)這個(gè)問題了。

編輯器分隔
即便Vue的組件化開發(fā),可以將單文件的代碼長度大幅縮短,但還是動(dòng)輒幾百行甚是上千行。那么我們切換template,script和style的時(shí)候就要頻繁上下翻,雖然有的插件可以直接定位到css,但是你回不去??!所以這個(gè)功能簡直是太人性化了。
安裝完Volar以后,打開一個(gè).vue文件,看vscode的右上角,有這么一個(gè)圖標(biāo),點(diǎn)一下。

它就會(huì)自動(dòng)給你分隔成三個(gè)頁面,分別對(duì)應(yīng)template,script和style,這樣就太舒服了有沒有。

Vue 3 Snippets
推薦的第二個(gè)插件叫做Vue 3 Snippets,同樣的,他也有自己的Vue2版本。它是干什么的呢,可以看一下下面這張圖,我只輸入了“v3”,它有很多提示,我們就先選擇v3computed,選中回車即可。

然后它就給自動(dòng)給我們寫了如下代碼

是不是超級(jí)省事,摸魚的時(shí)間又增加了!還有更多有趣的使用方式,小伙伴們自行探索吧。
創(chuàng)建Vue3項(xiàng)目
那么正式開始學(xué)習(xí)我們的Vue3,先從創(chuàng)建項(xiàng)目開始。
使用 vue-cli 創(chuàng)建
輸入下面的命令然后選擇配置項(xiàng)進(jìn)行安裝即可,這里注意vue-cli的版本一定要在4.5.0以上
//?安裝或者升級(jí)
npm?install?-g?@vue/cli
//查看版本?保證?vue?cli?版本在?4.5.0?以上
vue?--version
//?創(chuàng)建項(xiàng)目
vue?create?my-project
//然后根據(jù)提示一步一步傻瓜式操作就行了
...
復(fù)制代碼
使用 Vite 創(chuàng)建
都說Vue3.0和Vite2更配,各種優(yōu)化,各種快,但都不屬于本文的內(nèi)容,本文的目的我們只需要知道它特別好用,怎么用就行了。我這里是多選擇了TS,每行都有注釋,一目了然。
//?初始化viete項(xiàng)目
npm?init?vite-app?
//?進(jìn)入項(xiàng)目文件夾
cd?
//?安裝依賴
npm?install
//啟動(dòng)項(xiàng)目
npm?run?dev
復(fù)制代碼
創(chuàng)建完以后我們先來看看入口文件main.ts
//?引入createApp函數(shù),創(chuàng)建對(duì)應(yīng)的應(yīng)用,產(chǎn)生應(yīng)用的實(shí)例對(duì)象
import?{?createApp?}?from?'vue';
//?引入app組件(所有組件的父級(jí)組件)
import?App?from?'./App.vue';
//?創(chuàng)建app應(yīng)用返回對(duì)應(yīng)的實(shí)例對(duì)象,調(diào)用mount方法進(jìn)行掛載??掛載到#app節(jié)點(diǎn)上去
createApp(App).mount('#app');
復(fù)制代碼
然后看看根組件app.vue
//Vue2組件中的html模板中必須要有一對(duì)根標(biāo)簽,Vue3組件的html模板中可以沒有根標(biāo)簽
??<img?alt="Vue?logo"?src="./assets/logo.png">
??
??<HelloWorld?msg="Welcome?to?Your?Vue.js?+?TypeScript?App"?/>
template>
<script?lang="ts">
//?這里可以書寫TS代碼
//?defineComponent函數(shù),目的是定義一個(gè)組件?內(nèi)部可以傳入一個(gè)配置對(duì)象
import?{?defineComponent?}?from?'vue';
//引入子級(jí)組件
import?HelloWorld?from?'./components/HelloWorld.vue';
//?暴露出去一個(gè)定義好的組件
export?default?defineComponent({
??//?當(dāng)前組件的名字
??name:?'App',
??//?注冊組件
??components:?{
????//?注冊一個(gè)子級(jí)組件
????HelloWorld,
??},
});
script>
復(fù)制代碼
Composition API
接下來到了重頭戲,Vue3的招牌特性,Composition API
關(guān)于Composition API這里有大佬做的動(dòng)畫演示,極力推薦。
那個(gè)忙了一夜的Vue3動(dòng)畫很好,就是太短了
Composition API可以更方便的抽取共通邏輯,但是不要過于在意邏輯代碼復(fù)用,以功能提取代碼也是一種思路。
順便提一句,Vue3兼容大部分Vue2語法,所以在Vue3中書寫Vue2語法是沒有問題的(廢除的除外),但是既然我們已經(jīng)升級(jí)Vue3了,不建議混合使用,除非一些大型特殊項(xiàng)目需要兼容兩個(gè)版本。
setup
setup是組合Composition API中的入口函數(shù),也是第一個(gè)要使用的函數(shù)。
setup只在初始化時(shí)執(zhí)行一次,所有的Composition API函數(shù)都在此使用。
setup()?{
??console.log('我執(zhí)行了')?//我執(zhí)行了
},
復(fù)制代碼
可以通過console.log看到setup是在beforeCreate生命周期之前執(zhí)行的(只執(zhí)行一次)
??beforeCreate()?{
????console.log('beforeCreate執(zhí)行了');
??},
??setup()?{
????console.log('setup執(zhí)行了');
????return?{};
??},
??//setup執(zhí)行了
??//beforeCreate執(zhí)行了
復(fù)制代碼
由此可以推斷出setup執(zhí)行的時(shí)候,組件對(duì)象還沒有創(chuàng)建,組件實(shí)例對(duì)象this還不可用,此時(shí)this是undefined, 不能通過this來訪問data/computed/methods/props。
返回對(duì)象中的屬性會(huì)與data函數(shù)返回對(duì)象的屬性合并成為組件對(duì)象的屬性,返回對(duì)象中的方法會(huì)與methods中的方法合并成功組件對(duì)象的方法,如果有重名,?setup優(yōu)先。因?yàn)樵?code style="margin-right: 2px;margin-left: 2px;padding: 2px 4px;outline: 0px;max-width: 100%;font-size: 14px;font-family: "Operator Mono", Consolas, Monaco, Menlo, monospace;word-break: break-all;border-radius: 4px;color: rgb(233, 105, 0);background-color: rgb(248, 248, 248);box-sizing: border-box !important;overflow-wrap: break-word !important;">setup中this不可用,methods中可以訪問setup提供的屬性和方法, 但在setup方法中不能訪問data和methods里的內(nèi)容,所以還是不建議混合使用。
setup函數(shù)如果返回對(duì)象, 對(duì)象中的?屬性?或?方法?,?模板?中可以直接使用
//templete
{{number}}</div>
//JS
setup()?{
??const?number?=?18;
??return?{
????number,
??};
},
復(fù)制代碼
注意:setup不能是一個(gè)async函數(shù): 因?yàn)榉祷刂挡辉偈?code style="margin-right: 2px;margin-left: 2px;padding: 2px 4px;outline: 0px;max-width: 100%;font-size: 14px;font-family: "Operator Mono", Consolas, Monaco, Menlo, monospace;word-break: break-all;border-radius: 4px;color: rgb(233, 105, 0);background-color: rgb(248, 248, 248);box-sizing: border-box !important;overflow-wrap: break-word !important;">return的對(duì)象, 而是promise, 模板中就不可以使用return中返回對(duì)象的數(shù)據(jù)了。
setup的參數(shù)(props,context)`
props: 是一個(gè)對(duì)象,里面有父級(jí)組件向子級(jí)組件傳遞的數(shù)據(jù),并且是在子級(jí)組件中使用props接收到的所有的屬性
context:上下文對(duì)象,可以通過es6語法解構(gòu)?setup(props, {attrs, slots, emit})
attrs: 獲取當(dāng)前組件標(biāo)簽上所有沒有通過props接收的屬性的對(duì)象, 相當(dāng)于?this.$attrs slots: 包含所有傳入的插槽內(nèi)容的對(duì)象, 相當(dāng)于?this.$slots emit: 用來分發(fā)自定義事件的函數(shù), 相當(dāng)于?this.$emit
演示attrs和props
//父組件
??<child?:msg="msg"?msg2='哈哈哈'?/>
</template>
//子組件
??子組件
??msg:{{?msg?}}
復(fù)制代碼
演示emit
//父組件
??<child?@show="show"?/>
</template>
//子組件
??
????
????
?????????????????class="looklook">
????????看看我出現(xiàn)在了哪里
????????
??????
????
??
復(fù)制代碼
可以看到在子組件中的looklook元素跑到了body下面,而之前的位置默認(rèn)出現(xiàn)了兩行注釋

微信截圖_20210623170701.png Suspense(不確定的)
作用
它們允許我們的應(yīng)用程序在等待異步組件時(shí)渲染一些后備內(nèi)容,可以讓我們創(chuàng)建一個(gè)平滑的用戶體驗(yàn)
語法
?
????<template?v-slot:default>
??????
??????<AsyncComp?/>
????template>
????<template?v-slot:fallback>
??????
??????<h1>LOADING...h1>
????template>
??</Suspense>
復(fù)制代碼
vue3中引入異步組件的方式
const?AsyncComp?=?defineAsyncComponent(()?=>?import('./AsyncComp.vue'))
復(fù)制代碼
代碼演示
父組件
??<Suspense>
?????
????<template?v-slot:default>
??????<AsyncComp/>
????template>
????<template?v-slot:fallback>
??????<h1>LOADING...h1>
????template>
??Suspense>
</template>
復(fù)制代碼
子組件
??<h2>AsyncComp22h2>
??<p>{{msg}}p>
</template>
復(fù)制代碼
子組件
??<span?@click="sonClick">msg:?{{?props.msg?}}span>
</template>
復(fù)制代碼
子組件先不使用語法糖
??<div>
????我是子組件{{msg}}
??div>
</template>
復(fù)制代碼
子組件
??<div>
????我是子組件{{?msg?}}
??div>
??<button?@click="handleClick(1)">我是按鈕1button>
??<button?@click="handleClick(2)">我是按鈕2button>
</template>
復(fù)制代碼
子組件1
??<div>
????我是子組件1
????<h1>{{msg}}h1>
??div>
</template>
復(fù)制代碼
子組件2
??<div>
????我是子組件2
??div>
??<button?@click='changeMsg'>點(diǎn)擊修改msgbutton>
</template>
復(fù)制代碼
演示

1.gif 自定義指令
先看看Vue2自定義指令的鉤子
bind:當(dāng)指令綁定在對(duì)應(yīng)元素時(shí)觸發(fā)。只會(huì)觸發(fā)一次。 inserted:當(dāng)對(duì)應(yīng)元素被插入到?DOM?的父元素時(shí)觸發(fā)。 update:當(dāng)元素更新時(shí),這個(gè)鉤子會(huì)被觸發(fā)(此時(shí)元素的后代元素還沒有觸發(fā)更新)。 componentUpdated:當(dāng)整個(gè)組件(包括子組件)完成更新后,這個(gè)鉤子觸發(fā)。 unbind:當(dāng)指令被從元素上移除時(shí),這個(gè)鉤子會(huì)被觸發(fā)。也只觸發(fā)一次。
在?Vue3?中,官方為了更有助于代碼的可讀性和風(fēng)格統(tǒng)一,把自定義指令的鉤子名稱改的更像是組件生命周期,盡管他們是兩回事
bind?=>?beforeMount inserted?=>?mounted beforeUpdate:?新的鉤子,會(huì)在元素自身更新前觸發(fā) update?=>?移除! componentUpdated?=>?updated beforeUnmount:?新的鉤子,當(dāng)元素自身被卸載前觸發(fā) unbind?=>?unmounted
過渡動(dòng)畫
這個(gè)沒有什么大的改動(dòng),只是修改了兩個(gè)class名字,正是因?yàn)闆]有什么大的改動(dòng),導(dǎo)致我曾經(jīng)在這里栽了大跟頭,寫完了怎么都不對(duì),后來查官網(wǎng)才知道。
以下是直接引用?官網(wǎng)的原文
v-enter-from:定義進(jìn)入過渡的開始狀態(tài)。在元素被插入之前生效,在元素被插入之后的下一幀移除。
v-enter-active:定義進(jìn)入過渡生效時(shí)的狀態(tài)。在整個(gè)進(jìn)入過渡的階段中應(yīng)用,在元素被插入之前生效,在過渡/動(dòng)畫完成之后移除。這個(gè)類可以被用來定義進(jìn)入過渡的過程時(shí)間,延遲和曲線函數(shù)。
v-enter-to:定義進(jìn)入過渡的結(jié)束狀態(tài)。在元素被插入之后下一幀生效 (與此同時(shí) v-enter-from 被移除),在過渡/動(dòng)畫完成之后移除。
v-leave-from:定義離開過渡的開始狀態(tài)。在離開過渡被觸發(fā)時(shí)立刻生效,下一幀被移除。
v-leave-active:定義離開過渡生效時(shí)的狀態(tài)。在整個(gè)離開過渡的階段中應(yīng)用,在離開過渡被觸發(fā)時(shí)立刻生效,在過渡/動(dòng)畫完成之后移除。這個(gè)類可以被用來定義離開過渡的過程時(shí)間,延遲和曲線函數(shù)。
v-leave-to:離開過渡的結(jié)束狀態(tài)。在離開過渡被觸發(fā)之后下一幀生效 (與此同時(shí) v-leave-from 被刪除),在過渡/動(dòng)畫完成之后移除。
特別注意的是v-enter改成了v-enter-form,v-leave改成了v-leave-from。
其他小知識(shí)
Vue3移除了filter
獲取組件實(shí)例方法getCurrentInstance()
這個(gè)方法可以獲取到當(dāng)前組件的實(shí)例,相當(dāng)于Vue2中的this最后,畢竟是個(gè)人總結(jié),難免會(huì)出現(xiàn)紕漏和錯(cuò)誤,期待各路大神的補(bǔ)充和糾正。
我的開源項(xiàng)目:
https://juejin.cn/post/6963945204965441550"
參考資料
[1]https://github.com/vuejs/rfcs/pull/210
作者:一尾流鶯
https://juejin.cn/post/6977004323742220319
The End
歡迎自薦投稿到《前端技術(shù)江湖》,如果你覺得這篇內(nèi)容對(duì)你挺有啟發(fā),記得點(diǎn)個(gè)?「在看」哦
點(diǎn)個(gè)『在看』支持下?
