Vue.js:
Vue它是什么
是一套用于構建用戶界面的漸進式框架,在使用Vue的時候,可以只使用Vue里面的一部分去配合其他前端框架一起開發,也可以整個項目從頭到尾,從搭建項目,路由系統,全局的狀態管理等全部使用Vue,非常靈活。Vue2學習資料可以看歷史文章哦
一、初識Vue3
1.引入js文件,以開發版本來學習,下載到本地,首先引入Vue.js文件。
<!-- Vue2 -->
<!-- <script src="https://cdn.jsdelivr.net/npm/vue@2.6.14"></script> -->
<!-- Vue3 -->
<script src="https://unpkg.com/vue@next"></script>
2.Vue3創建一個Vue實例與Vue2創建一個實例的區別,在Vue3里面Vue是一個對象,通過該對象的createApp()方法,創建一個Vue實例,注意:在Vue3中,取消了el選項,在Vue3中,無論論是組件和Vue實例,data選項都必須是一個方法,由方法返回對象。
<!DOCTYPE html>
<html>
<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>初識Vue3</title>
<div id="app">
<p>name:{{name}}</p>
<p>age:{{age}}</p>
</div>
</head>
<body>
<!-- Vue2 -->
<!-- <script src="https://cdn.jsdelivr.net/npm/vue@2.6.14"></script> -->
<!-- Vue3 -->
<script src="https://unpkg.com/vue@next"></script>
<script>
// Vue2創建一個Vue實例
// 在Vue2里面的Vue是一個構造函數,通過該構造函數創建一個Vue實例
// new Vue({
// //指定當前Vue對象操作的DOM容器
// el:'#app',
// 在Vue2中,data選項可以是對象,也可以是方法返回一個對象
// //定義當前Vue對象管理的數據
// data:{
// name:'Vue2',
// age:'3'
// }.$mount('#app')
// Vue2可以通過el選項指定一個掛載的容器,也可以通過$mount()方法置頂掛載的容器
// })
// Vue3創建一個Vue實例
// 在Vue3里面Vue是一個對象,通過該對象的createApp()方法,創建一個Vue實例
Vue.createApp({
// 注意:在Vue3中,取消了el選項
// 注意:在Vue3中,無論是組件和Vue實例,data選項都必須是一個方法,由方法返回對象
data() {
return {
name:'Vue3',
age:2
}
},
}).mount('#app')
</script>
</body>
</html>
二、響應式
1.Vue3修復了Vue2中響應式的所有缺陷。什么是響應式?當數據變化,頁面也會隨之變化,例如Vue2的響應式:不能直接給對象添加屬性,刪除對象的屬性,不能直接操作數組的下標,但是,Vue2同時也提供了解決這些問題的方案。
<!DOCTYPE html>
<html>
<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>初識Vue2和Vue3的響應式</title>
<div id="app">
<p>{{student}}</p>
<button @click='reviseName'>修改name</button>
<button @click='reviseAge'>修改age</button>
<button @click='addSex'>添加sex</button>
<button @click='delSex'>刪除sex</button>
</div>
</head>
<body>
<!-- Vue2 -->
<!-- <script src="https://cdn.jsdelivr.net/npm/vue@2.6.14"></script> -->
<!-- Vue3 -->
<script src="https://unpkg.com/vue@next"></script>
<script>
// Vue2
// new Vue({
// el: "#app",
// data: {
// student: {
// name: '萌新',
// age: 3
// }
// },
// methods: {
// reviseName(){
// this.student.name = 'Vue3'
// },
// reviseAge(){
// this.student.age = '30'
// },
// addSex(){
// // 直接給對象添加的屬性,不具備響應式
// // this.student.sex = '男'
// // 如果要給對象添加屬性,并且添加的屬性也要具備響應式,要使用$set方法
// // 方法的第一個參數是指定的對象,第二個參數是屬性名,第三個參數是屬性值。
// // this.$set(this.student,'sex','男')
// // console.log(this.student);
// 也可以通過$forceUpdate()強制更新頁面一次 不推薦
// this.$forceUpdate()
// },
// delSex(){
// // 直接刪除對象身上的屬性,是不具備響應式的
// // delete this.student.sex
// // 如果要刪除對象身上的屬性,并且還要具備響應式,要使用$delete方法
// // 方法的第一個參數是指定的對象,第二個參數是屬性名
// // this.$delete(this.student,'sex')
// // console.log(this.student);
// }
// },
// })
// Vue3
Vue.createApp({
data() {
return {
student:{
name:'萌新',
age:3
}
}
},
methods: {
reviseName(){
this.student.name = 'Vue3'
},
reviseAge(){
this.student.age = '30'
},
addSex(){
// 在Vue3中,直接給對象添加屬性,新的屬性依然具備響應式
this.student.sex = '男'
},
delSex(){
// 在Vue3中,直接刪除對象的屬性,依然具備響應式
delete this.student.sex
}
},
}).mount('#app')
</script>
</body>
</html>
三、響應式原理
1.vue2在實例化時,會將data里面的所有數據采用Object.defineProperty進行處理,實現實現響應式功能。
2.但是你之后往data里面添加的數據,由于沒有來用 object.defineProperty進行處理,所以不具備響應式。
3.$set()方法,內部就是對單個屬性重新采用 0bject.defineProperty進行處理,從而具備響應式。
<!DOCTYPE html>
<html>
<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>Vue2和Vue3的響應式原理</title>
<div id="app">
<h2 id="name"></h2>
<h2 id="age"></h2>
</div>
</head>
<body>
<!-- Vue2 -->
<!-- <script src="https://cdn.jsdelivr.net/npm/vue@2.6.14"></script> -->
<!-- Vue3 -->
<!-- <script src="https://unpkg.com/vue@next"></script> -->
<script>
// Vue2的響應式原理:
// 這里的obj是源對象
let obj = {
name: 'Vue2',
age: 3
}
// 在頁面中顯示姓名和年齡
document.getElementById('name').innerText = obj.name
document.getElementById('age').innerText = obj.age
// 這里的obj2代理對象---由obj2代理obj
let obj2 = {}
// 通過Object.defineProperty方法,給obj2添加屬性
Object.defineProperty(obj2, 'name', {
// 讀取屬性的值,調用get方法
get() {
return obj.name
},
// 設置屬性的值,調用set方法
set(value) {
obj.name = value
document.getElementById('name').innerText = obj.name
}
})
// 給obj2定義age屬性
Object.defineProperty(obj2, 'age', {
get() {
return obj.age
},
set(value) {
obj.age = value
document.getElementById('age').innerText = obj.age
}
})
// vue2在實例化時,會將data里面的所有數據采用Object.defineProperty進行處理,實現實現響應式功能。
// 但是你之后往data里面添加的數據,由于沒有來用 object.defineProperty進行處理,所以不具備響應式。
// $set()方法,內部就是對單個屬性重新采用 0bject.defineProperty進行處理,從而具備響應式。
</script>
</body>
</html>
2.在Vue3中響應式,無論是代碼量還是性能,Proxy更加有優勢。
// Vue3的響應式原理:
// 這里的obj是源對象
let obj = {
name:'Vue3',
age:3
}
// 在頁面中顯示姓名和年齡
document.getElementById('name').innerText = obj.name
document.getElementById('age').innerText = obj.age
// 這里的obj2代理對象---由obj2代理obj
// new Proxy(源對象,{...})的方式,創建代理對象
let obj2 = new Proxy(obj,{
//讀取屬性,參數分別是:源對象,屬性名
get(target, property){
// 直接根據源對象返回源對象身上的屬性
// return target[property]
// 通過發射對象,發射輸出源對象身上的屬性
return Reflect.get(target,property)
},
//設置屬性,參數分別是:源對象,屬性名,屬性值
set(target, property,value){
// target[property] = value
if(Reflect.has(target,property)){
Reflect.set(target, property,value)
document.getElementById(`${property}`).innerText = value
}
},
//刪除屬性,參數分別是:源對象,屬性名
deleteProperty(target, property){
// return delete target[property]
//官方說,用這個方式發射,性能更好,更快
Reflect.deleteProperty(target, property)
}
})
四、引出Vue3新推出的組合式API
Vue3引入了全新的功能,叫組合式api,它是什么,可以理解為Vue新推出的一些方法,作用是:講原來分散開來定義的數據,方法,計算屬性,監聽器,組合起來定義一個完整的業務,統一在setup中使用,在setup中,直接定義的數據是不具備響應式的,如果要使數據具備響應式,需要使用ref組合式API對數據進行包裝,包裝后返回的是ref對象。
<div id="app">
<div>
<h2>學生信息</h2>
<!-- 注意:ref對象在模板只不需要.value的方式獲取里面的值 -->
<h4>姓名:{{stuName}}</h4>
<h4>年齡:{{stuAge}}</h4>
<button @click="updateStu">修改學生信息</button>
</div>
<div>
<h2>汽車信息</h2>
<h4>車名:{{carName}}</h4>
<h4>車價:{{carPrice}}</h4>
<button @click="updateCar">修改汽車信息</button>
</div>
<div>
<h2>手機信息</h2>
<h4>名稱:{{phoneName}}</h4>
<h4>顏色:{{phoneColor}}</h4>
<button @click="updatePhone">修改手機信息</button>
</div>
<div>
<h2>食物信息</h2>
<h4>名稱:{{foodName}}</h4>
<h4>價格:{{foodPrice}}</h4>
<button @click="updateFood">修改食物信息</button>
</div>
</div>
// 什么是組合式API(Composition API),就是Vue推出的一些新的方法,這個方法在setup中使用
// 從Vue身上獲取ref組合式API函數
let {ref} = Vue
Vue.createApp({
// 注意:Vue2中,Vue實例的data選項可以是一個對象,也可以是一個方法,由方法返回一個對象
// 但是,組件中data選項必須是一個方法。
// Vue3中,無論是Vue實例,還是組件,data選項都必須是一個方法。
// 我們之前習慣將所有的數據放在data選項中定義,所有的方法放在methods選項中定義,
// 所有的計算屬性放在computed選項中定義,所有的偵聽器放在watch選項中定義,
// 這樣就會導致一個業務的代碼會拆分到多個結構中去寫,如果一個頁面中要操作很多個業務,代碼后期維護成本會很高。
// 所以,Vue3引入了組合式API,簡化之前繁瑣的過程,將相同業務的代碼靠在一起寫。
/* data: function () {
return {
//定義學生數據
stuName: '張三',
stuAge: '20',
//汽車信息
carName: '奔馳',
carPrice: '50W',
//手機信息
phoneName: 'iphone',
phoneColor: '白色',
//食物信息
foodName: '漢堡',
foodPrice: '¥20'
}
},
methods: {
//修改學生的方法
updateStu(){
this.stuName = '李四'
this.stuAge = 30
},
//修改汽車的方法
updateCar(){
this.carName = '寶馬'
this.carPrice = '40W'
},
//修改手機的方法
updatePhone(){
this.phoneName = '華為'
this.phoneColor = '藍色'
},
updateFood(){
this.foodName = '蛋糕'
this.foodPrice = '¥30'
}
}, */
// setup方法是所有組合式API的入口
setup() {
// 定義學生的信息
// 在setup中,直接定義的數據是不具備響應式的,
// 如果要使數據具備響應式,需要使用ref組合式API對數據進行包裝,包裝后返回的是ref對象
let stuName = ref('張三')
let stuAge = ref('20')
let updateStu = () => {
//ref對象的value屬性保存的是值
stuName.value = '李四'
stuAge.value = 30
}
// 定義汽車的信息
let carName = ref('奔馳')
let carPrice = ref('50W')
let updateCar = () => {
carName.value = '寶馬'
carPrice.value = '40W'
}
// 定義手機的信息
let phoneName = ref('iphone')
let phoneColor = ref('白色')
let updatePhone = () => {
phoneName.value = '華為'
phoneColor.value = '藍色'
}
// 定義食物的信息
let foodName = ref('漢堡')
let foodPrice = ref('¥20')
let updateFood = () => {
foodName.value = '蛋糕'
foodPrice.value = '¥30'
}
//返回模板中需要使用的數據
return{
stuName,
stuAge,
updateStu,
carName,
carPrice,
updateCar,
phoneName,
phoneColor,
updatePhone,
foodName,
foodPrice,
updateFood
}
}
}).mount('#app')