feat(ref): 实现 ref 值变化检测和依赖触发功能

- 在 shared 包中新增 hasChanged 函数用于比较值是否发生变化
- 修改 RefImpl 类添加 _rawValue 属性存储原始值
- 实现 ref setter 中的值变化检测逻辑
- 添加 triggerRefValue 函数用于触发 ref 依赖更新
- 优化 ref 的 getter 和 setter 方法实现响应式更新
This commit is contained in:
dj
2026-02-05 22:36:15 +08:00
parent 9aad0f6c74
commit 6b7b452a56
2 changed files with 27 additions and 2 deletions

View File

@@ -1,6 +1,7 @@
import { createDep, Dep } from './dep' import { createDep, Dep } from './dep'
import { toReactive } from './reactive' import { toReactive } from './reactive'
import { activeEffect, track, trackEffects } from './effect' import { activeEffect, triggerEffects, trackEffects } from './effect'
import { hasChanged } from '@vue/shared'
export interface Ref<T = any> { export interface Ref<T = any> {
value: T value: T
@@ -17,20 +18,36 @@ function createRef(rawValue: unknown, shallow: boolean) {
} }
class RefImpl<T> { class RefImpl<T> {
private _value: T private _value: T
private _rawValue: T
public dep?: Dep = undefined public dep?: Dep = undefined
public readonly __v_isRef = true public readonly __v_isRef = true
constructor( constructor(
value: T, value: T,
public readonly __v_isShallow: boolean public readonly __v_isShallow: boolean
) { ) {
this._rawValue = value
this._value = __v_isShallow ? value : toReactive(value) this._value = __v_isShallow ? value : toReactive(value)
} }
get value() { get value() {
trackRefValue(this) trackRefValue(this)
return this._value return this._value
} }
set value(newValue) {} set value(newValue) {
if (hasChanged(newValue, this._rawValue)) {
this._rawValue = newValue
this._value = toReactive(newValue)
triggerRefValue(this)
}
}
} }
//触发依赖
export function triggerRefValue(ref) {
if (ref.dep) {
triggerEffects(ref.dep)
}
}
//收集依赖
export function trackRefValue(ref) { export function trackRefValue(ref) {
if (activeEffect) { if (activeEffect) {
trackEffects(ref.dep || (ref.dep = createDep())) trackEffects(ref.dep || (ref.dep = createDep()))

View File

@@ -3,3 +3,11 @@ export const isArray = Array.isArray
export const isObject = (val: unknown) => export const isObject = (val: unknown) =>
val !== null && typeof val === 'object' val !== null && typeof val === 'object'
/**
* 对比两个数据是否发生改变
* @param value
* @param oldValue
*/
export const hasChanged = (value: any, oldValue: any): boolean =>
!Object.is(value, oldValue)