# ref() 原始类型包装
使通过值传递的 string
和 number
等原始类型也能变得响应式。
<script setup>
const count = ref(1)
const obj = reactive({ count })
// ref 会被解包
console.log(count.value) // 1
console.log(obj.count === count.value) // true
</script>
1
2
3
4
5
6
7
8
2
3
4
5
6
7
8
# 解析$ref
//html
<div ref='divRef'>
myDiv
</div>
//js
<script setup>
const divRef=ref(null)
console.log(divRef.value.innerHtml) //'myDiv'
</script>
1
2
3
4
5
6
7
8
9
10
2
3
4
5
6
7
8
9
10
# isRef()
检查某个值是否为 ref。
let foo: unknown
if (isRef(foo)) {
// foo 的类型被收窄为了 Ref<unknown>
foo.value
}
1
2
3
4
5
2
3
4
5
# unref()
如果参数是 ref,则返回内部值,否则返回参数本身。
这是 val = isRef(val) ? val.value : val
计算的一个语法糖。
function useFoo(x: number | Ref<number>) {
const unwrapped = unref(x)
// unwrapped 现在保证为 number 类型
}
1
2
3
4
2
3
4
# toRef()
基于一个响应式数据,创建新的 ref ,并与原响应式属性保持双向数据同步。
使用场景:将 Props 转化为 ref ,然后传递给一个组合式函数。
const state = reactive({
foo: 1,
bar: 2
})
const fooRef = toRef(state, 'foo')
// 更改该 ref 会更新源属性
fooRef.value++
console.log(state.foo) // 2
// 更改源属性也会更新该 ref
state.foo++
console.log(fooRef.value) // 3
1
2
3
4
5
6
7
8
9
10
11
12
13
14
2
3
4
5
6
7
8
9
10
11
12
13
14
# reactive() 对象类型包装
- reactive 只能用于对象包装(数组也是对象)。
- 响应式是深层次的。
- 直接替换掉响应式对象或使用解构赋值将会失去响应式。
<script setup>
import { reactive } from 'vue'
const state = reactive({ count: 0 })
state.count++ //1
</script>
1
2
3
4
5
6
7
2
3
4
5
6
7
# toRefs()
将一个响应式对象转换为一个普通对象,这个普通对象的每个属性都是指向源对象相应属性的 ref(使用解构也不会失去响应式了)。
使用场景:当从组合式函数中返回响应式对象时,使用toRefs
进行包装,可以防止使用解构/展开返回对失去响应性。
const state = reactive({
foo: 1,
bar: 2
})
const stateAsRefs = toRefs(state)
/*
stateAsRefs 的类型:{
foo: Ref<number>,
bar: Ref<number>
}
*/
// 这个 ref 和源属性已经“链接上了”
state.foo++
console.log(stateAsRefs.foo.value) // 2
stateAsRefs.foo.value++
console.log(state.foo) // 3
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# isReactive()
检查一个对象是否是由 reactive()
(opens new window) 或 shallowReactive()
(opens new window) 创建的代理。
类型
function isReactive(value: unknown): boolean
1
# readonly() 返回只读数据
接受一个对象 (不论是响应式还是普通的) 或是一个 ref (opens new window),返回一个原值的只读代理。
const original = reactive({ count: 0 })
const copy = readonly(original)
watchEffect(() => {
// 用来做响应性追踪
console.log(copy.count)
})
// 更改源属性会触发其依赖的侦听器
original.count++
// 更改该只读副本将会失败,并会得到s一个警告
copy.count++ // warning!
1
2
3
4
5
6
7
8
9
10
11
12
13
14
2
3
4
5
6
7
8
9
10
11
12
13
14
# isReadonly()
检查一个对象是否是由 readonly()
(opens new window) 或 shallowReadonly()
(opens new window) 创建的代理。
类型
function isReadonly(value: unknown): boolean
1
# isProxy() 判断是否是响应式代理
检查一个对象是否是由 reactive()
(opens new window)、readonly()
(opens new window)、shallowReactive()
(opens new window) 或 shallowReadonly()
(opens new window) 创建的代理。
类型
function isProxy(value: unknown): boolean
1