parent
c23153d82e
commit
2937530bef
@ -390,12 +390,12 @@ export function createPathGetter(ctx: any, path: string) {
|
||||
}
|
||||
}
|
||||
|
||||
function traverse(value: unknown, seen: Set<unknown> = new Set()) {
|
||||
if (
|
||||
!isObject(value) ||
|
||||
seen.has(value) ||
|
||||
(value as any)[ReactiveFlags.SKIP]
|
||||
) {
|
||||
export function traverse(value: unknown, seen: Set<unknown> = new Set()) {
|
||||
if (!isObject(value) || (value as any)[ReactiveFlags.SKIP]) {
|
||||
return value
|
||||
}
|
||||
seen = seen || new Set()
|
||||
if (seen.has(value)) {
|
||||
return value
|
||||
}
|
||||
seen.add(value)
|
||||
|
@ -20,6 +20,7 @@ import { callWithAsyncErrorHandling, ErrorCodes } from './errorHandling'
|
||||
import { ComponentPublicInstance } from './componentPublicInstance'
|
||||
import { mapCompatDirectiveHook } from './compat/customDirective'
|
||||
import { pauseTracking, resetTracking } from '@vue/reactivity'
|
||||
import { traverse } from './apiWatch'
|
||||
|
||||
export interface DirectiveBinding<V = any> {
|
||||
instance: ComponentPublicInstance | null
|
||||
@ -51,6 +52,7 @@ export interface ObjectDirective<T = any, V = any> {
|
||||
beforeUnmount?: DirectiveHook<T, null, V>
|
||||
unmounted?: DirectiveHook<T, null, V>
|
||||
getSSRProps?: SSRDirectiveHook
|
||||
deep?: boolean
|
||||
}
|
||||
|
||||
export type FunctionDirective<T = any, V = any> = DirectiveHook<T, any, V>
|
||||
@ -101,6 +103,9 @@ export function withDirectives<T extends VNode>(
|
||||
updated: dir
|
||||
} as ObjectDirective
|
||||
}
|
||||
if (dir.deep) {
|
||||
traverse(value)
|
||||
}
|
||||
bindings.push({
|
||||
dir,
|
||||
instance,
|
||||
|
@ -99,6 +99,8 @@ export const vModelText: ModelDirective<
|
||||
}
|
||||
|
||||
export const vModelCheckbox: ModelDirective<HTMLInputElement> = {
|
||||
// #4096 array checkboxes need to be deep traversed
|
||||
deep: true,
|
||||
created(el, _, vnode) {
|
||||
el._assign = getModelAssigner(vnode)
|
||||
addEventListener(el, 'change', () => {
|
||||
@ -171,6 +173,8 @@ export const vModelRadio: ModelDirective<HTMLInputElement> = {
|
||||
}
|
||||
|
||||
export const vModelSelect: ModelDirective<HTMLSelectElement> = {
|
||||
// <select multiple> value need to be deep traversed
|
||||
deep: true,
|
||||
created(el, { value, modifiers: { number } }, vnode) {
|
||||
const isSetModel = isSet(value)
|
||||
addEventListener(el, 'change', () => {
|
||||
|
Loading…
Reference in New Issue
Block a user