Vue3由於完全由TS進行重寫,在應用中對類型判斷的定義和使用有很強的表現。同一對象的多個鍵返回值必須通過定義對應的接口(interface)來進行類型定義。要不然在ESLint檢測和檢測時都會報錯。
實踐中的問題:
1. Vue2中的this指向在Vue3中使用同樣的方法進行代碼書寫,比如:
methods: { increase() { this.count++ } }
此時的 count 在 data 已經正常定義了。但是在Vue3中直接這樣書寫會直接報錯。
此時需要替換書寫規則,需要重vue中引入 defineComponent 對象進行包裹。
import { defineComponent } from 'vue'; export default definedComponent({ name: 'App' })
2. 響應式數據在Vue3中變得更加靈活和友善。Vue2中 data 里沒有定義的屬性在后續無法正常的進行響應操作,必須通過 Vue.set 這個 API 向響應式對象中添加一個 property,並確保這個新 property 同樣是響應式的,且觸發視圖更新。它必須用於向響應式對象上添加新 property,因為 Vue 無法探測普通的新增 property (比如 this.myObject.newProperty = 'hi'
); 然而在 Vue3 中我們可以通過引入 ref 來操作響應值。ref 是一個實例方法,接受一個內部值並返回一個響應式且可變的 ref 對象。ref 對象具有指向內部值的單個 property.value。
const count = ref(0) console.log(count.value) // 0 count.value++ console.log(count.value) // 1
如果將對象分配為 ref 值,則可以通過 reactive 方法使該對象具有高度的響應式。
Vue3 采用了 ES6的一項新特性:Proxy 來實現Vue3中數據響應式的設計。通過下面的偽代碼我們可以對比一下:
Object.defineProperty 要修改 data 中的屬性必須要明確的知道 key 值(count), Proxy 在使用中是讀取或者設置data中任意的 key,所以不管是修改已有的屬性還是新增屬性,都可以實現響應式的要求。
3. 關於生命周期鈎子函數
Vue2 | Vue3 |
beforeCreate() | use setup() |
created() | use setup() |
beforeMount() | onBeforeMount |
mounted() | onMounted |
beforeUpdate() | onBeforeUpdate |
updated() | onUpdated |
beforeDestory() | onBeforeUnmount |
destoryed() | onUnmounted |
activated() | onActivated |
deactivated() | onDeactivated |
errorCaptured() | onErrorCaptured |
onRenderTracked(新增) — DebuggerEvent 調試用 | |
onRenderTriggered(新增) — DebuggerEvent 調試用 |
Vue3中的鈎子函數都在 setup() 中調用。
4. computed,watch 可直接調用
const count = ref(0) const double = computed(() => { return count.value * 2 })
watch 接收兩個參數,第一個參數是監聽的屬性,多個屬性可傳入數組, 第二個參數是一個回調函數,回調函數有兩個參數(newVal, oldVal);當 watch 的第一個參數是一個數組時,newVal 與 oldVal 對應的也是數組形式,一一對應。
// 監聽count watch('count', (newVal, oldVal) => { console.log('newVal:', newVal) console.log('oldVal:', oldVal) }) // 監聽多個屬性值 watch(['count', 'name'], (newVal, oldVal) => { console.log('newVal:', newVal) // 數組 console.log('oldVal:', oldVal) // 數組 })
如果是需要監聽定義在 reacitive 對象中的單一屬性,需要通過函數返回值來進行監聽。
watch(() => data.count, (newVal, oldVal) => { console.log('newVal:', newVal) console.log('oldVal:', oldVal) })