Vue3 响应式数据
ref 基本数据类型响应式
- 语法:
let xxx = ref(初始值)
。 - **返回值:**一个
RefImpl
的实例对象,简称ref对象
或ref
,ref
对象的value
属性是响应式的。 - 注意点:
TS
中操作数据需要:xxx.value
,但模板中不需要.value
,直接使用即可。- 对于
let name = ref('张三')
来说,name
不是响应式的,name.value
是响应式的。
<script lang="ts" setup name="Person">
import {ref} from 'vue';
// 数据 -- 此时不是响应式的
let name = ref('张三');
let age = ref(18);
let tel = '1234567890';
// 方法 -- 这样修改页面没有变化
function changName() {
name.value = '李四';
}
function changeAge() {
age.value = 20;
}
function showTel() {
alert(tel);
}
reactive 对象类型的响应式数据
- 作用:定义一个响应式对象(基本类型不要用它,要用
ref
,否则报错) - 语法:
let 响应式对象= reactive(源对象)
。 - **返回值:**一个
Proxy
的实例对象,简称:响应式对象。 - 注意点:
reactive
定义的响应式数据是**“深层次”**的。
<template>
<div class="person">
<h1>Person</h1>
<p>Name: {{ name }}</p>
<p>Age: {{ age }}</p>
<button @click="changName">修改名字</button>
<button @click="changeAge">修改年龄</button>
<button @click="showTel">查看联系方式</button>
<h1>一辆小汽车</h1>
<h3>品牌{{ car.brand }}</h3>
<h3>价格{{ car.price }}</h3>
<br>
<button @click="changeCarPrice">修改价格</button>
<br>
<h1>游戏列表</h1>
<ul>
<li v-for="game in games" :key="game.name">
<p>游戏名称: {{ game.name }}</p>
<p>游戏价格: {{ game.price }}</p>
</li>
</ul>
<button @click="changeFisrtGamePrice">修改第一个游戏价格</button>
</div>
</template>
<!-- <script lang="ts">
export default {
name: 'Person',
// setup() {
// // 数据 -- 此时不是响应式的
// let name = '张三';
// let age = 18;
// let tel = '1234567890';
// // 方法 -- 这样修改页面没有变化
// function changName() {
// name = '李四';
// }
// function changeAge() {
// age = 20;
// }
// function showTel() {
// alert(tel);
// }
// return {a:name, b:age, changName, changeAge, showTel}
// }
} -->
<!-- </script> -->
<script lang="ts" setup name="Person">
import {ref} from 'vue';
import { reactive } from 'vue';
// 数据 -- 此时不是响应式的
let name = ref('张三');
let age = ref(18);
let tel = '1234567890';
let car = reactive({brand: 'BMW', price: 1000000});
let games = reactive([
{name: 'LOL', price: 100},
{name: 'DNF', price: 200},
{name: 'CF', price: 300},
]);
// 方法 -- 这样修改页面没有变化
function changName() {
name.value = '李四';
}
function changeAge() {
age.value = 20;
}
function showTel() {
alert(tel);
}
function changeCarPrice() {
car.price += 10000;
}
function changeFisrtGamePrice() {
games[0].price += 100;
}
</script>
<style>
.person {
background-color: aqua;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
}
</style>
ref 再探
ref
接收的数据可以是:基本类型、对象类型。- 若
ref
接收的是对象类型,内部调用了reactive
函数。
<template>
<div class="person">
<h1>Person</h1>
<p>Name: {{ name }}</p>
<p>Age: {{ age }}</p>
<button @click="changName">修改名字</button>
<button @click="changeAge">修改年龄</button>
<button @click="showTel">查看联系方式</button>
<h1>一辆小汽车</h1>
<h3>品牌{{ car.brand }}</h3>
<h3>价格{{ car.price }}</h3>
<br>
<button @click="changeCarPrice">修改价格</button>
<br>
<h1>游戏列表</h1>
<ul>
<li v-for="game in games" :key="game.name">
<p>游戏名称: {{ game.name }}</p>
<p>游戏价格: {{ game.price }}</p>
</li>
</ul>
<button @click="changeFisrtGamePrice">修改第一个游戏价格</button>
</div>
</template>
<!-- <script lang="ts">
export default {
name: 'Person',
// setup() {
// // 数据 -- 此时不是响应式的
// let name = '张三';
// let age = 18;
// let tel = '1234567890';
// // 方法 -- 这样修改页面没有变化
// function changName() {
// name = '李四';
// }
// function changeAge() {
// age = 20;
// }
// function showTel() {
// alert(tel);
// }
// return {a:name, b:age, changName, changeAge, showTel}
// }
} -->
<!-- </script> -->
<script lang="ts" setup name="Person">
import {ref} from 'vue';
import { reactive } from 'vue';
// 数据 -- 此时不是响应式的
let name = ref('张三');
let age = ref(18);
let tel = '1234567890';
let car = ref({brand: 'BMW', price: 1000000});
let games = ref([
{name: 'LOL', price: 100},
{name: 'DNF', price: 200},
{name: 'CF', price: 300},
]);
// 方法 -- 这样修改页面没有变化
function changName() {
name.value = '李四';
}
function changeAge() {
age.value = 20;
}
function showTel() {
alert(tel);
}
function changeCarPrice() {
car.value.price += 10000;
}
function changeFisrtGamePrice() {
games.value[0].price += 100;
}
</script>
<style>
.person {
background-color: aqua;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
}
</style>
宏观角度看:
ref
用来定义:基本类型数据、对象类型数据;
reactive
用来定义:对象类型数据。
- 区别:
ref
创建的变量必须使用.value
(可以使用volar
插件自动添加.value
)。reactive
重新分配一个新对象,会失去响应式(可以使用**Object.assign
**去整体替换)。
// reactive
Object.assign(car, {brand:'dklsajf', price:333});
// ref
car.value = {brand:'3', price:3454};
- 使用原则:
- 若需要一个基本类型的响应式数据,必须使用
ref
。- 若需要一个响应式对象,层级不深,
ref
、reactive
都可以。- 若需要一个响应式对象,且层级较深,推荐使用
reactive
。
自动加value:
toRefs toRef
- 作用:将一个响应式对象中的每一个属性,转换为**
ref
对象**。 - 备注:
toRefs
与toRef
功能一致,但toRefs
可以批量转换。
import {toRefs} from 'vue'
let person = {
name:'glm',
age:211
};
// 解构 toRefs
let {name, age} = toRefs(pesrson);
// 解构 toRef
let age = toRef(person. 'age');