77 lines
2.7 KiB
JavaScript
77 lines
2.7 KiB
JavaScript
|
export default { reactive }
|
||
|
|
||
|
export function reactive(target, prism = new Map()) {
|
||
|
if (Array.isArray(target)) {
|
||
|
const items = target.map(item => {
|
||
|
if (item instanceof HTMLElement) {
|
||
|
return item
|
||
|
}
|
||
|
return reactive(item, prism)
|
||
|
})
|
||
|
return new Proxy(items, {
|
||
|
get(target, prop) {
|
||
|
if (prop === "map") {
|
||
|
return function (...args) {
|
||
|
return reactive(target[prop](...args).map((item, index) => {
|
||
|
if (item === target[index]) {
|
||
|
return item
|
||
|
}
|
||
|
if (item instanceof HTMLElement) {
|
||
|
const arr = prism.get(target[index]) ?? []
|
||
|
arr.push(item)
|
||
|
prism.set(target[index], arr)
|
||
|
return item
|
||
|
}
|
||
|
return reactive(item, prism)
|
||
|
}))
|
||
|
}
|
||
|
}
|
||
|
if (prop === "pop") {
|
||
|
console.log("调用了 pop 方法", target)
|
||
|
return function (...args) {
|
||
|
const item = target[prop](...args)
|
||
|
const arr = prism.get(item) ?? []
|
||
|
arr.forEach(element => element.remove()) // 移除映射的DOM
|
||
|
return item
|
||
|
}
|
||
|
}
|
||
|
if (prop === "splice") {
|
||
|
console.log("调用了 splice 方法", target)
|
||
|
return function (...args) {
|
||
|
const items = target[prop](...args)
|
||
|
items.map(item => {
|
||
|
const arr = prism.get(item) ?? []
|
||
|
arr.forEach(element => element.remove()) // 移除映射的DOM
|
||
|
})
|
||
|
return items
|
||
|
}
|
||
|
}
|
||
|
return target[prop]
|
||
|
},
|
||
|
set(target, prop, value) {
|
||
|
target[prop] = reactive(value, prism)
|
||
|
return true
|
||
|
}
|
||
|
})
|
||
|
}
|
||
|
|
||
|
if (typeof target === "object" && target !== null) {
|
||
|
const proxiedObject = {}
|
||
|
for (const key in target) {
|
||
|
proxiedObject[key] = reactive(target[key], prism)
|
||
|
}
|
||
|
|
||
|
return new Proxy(proxiedObject, {
|
||
|
get(target, prop) {
|
||
|
return target[prop]
|
||
|
},
|
||
|
set(target, prop, value) {
|
||
|
target[prop] = value
|
||
|
return true
|
||
|
}
|
||
|
})
|
||
|
}
|
||
|
|
||
|
return target
|
||
|
}
|