|
@@ -20,7 +20,7 @@ import {
|
|
|
validateProps,
|
|
validateProps,
|
|
|
warn,
|
|
warn,
|
|
|
} from '@vue/runtime-dom'
|
|
} from '@vue/runtime-dom'
|
|
|
-import { ReactiveFlags } from '@vue/reactivity'
|
|
|
|
|
|
|
+import { type ComputedRef, ReactiveFlags, computed } from '@vue/reactivity'
|
|
|
import { normalizeEmitsOptions } from './componentEmits'
|
|
import { normalizeEmitsOptions } from './componentEmits'
|
|
|
import { renderEffect } from './renderEffect'
|
|
import { renderEffect } from './renderEffect'
|
|
|
import { pauseTracking, resetTracking } from '@vue/reactivity'
|
|
import { pauseTracking, resetTracking } from '@vue/reactivity'
|
|
@@ -35,11 +35,24 @@ export type DynamicPropsSource =
|
|
|
| (() => Record<string, unknown>)
|
|
| (() => Record<string, unknown>)
|
|
|
| Record<string, () => unknown>
|
|
| Record<string, () => unknown>
|
|
|
|
|
|
|
|
-// TODO optimization: maybe convert functions into computeds
|
|
|
|
|
export function resolveSource(
|
|
export function resolveSource(
|
|
|
source: Record<string, any> | (() => Record<string, any>),
|
|
source: Record<string, any> | (() => Record<string, any>),
|
|
|
): Record<string, any> {
|
|
): Record<string, any> {
|
|
|
- return isFunction(source) ? source() : source
|
|
|
|
|
|
|
+ return isFunction(source)
|
|
|
|
|
+ ? resolveFunctionSource(source as () => Record<string, any>)
|
|
|
|
|
+ : source
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+/**
|
|
|
|
|
+ * Resolve a function source with computed caching.
|
|
|
|
|
+ */
|
|
|
|
|
+export function resolveFunctionSource<T>(
|
|
|
|
|
+ source: (() => T) & { _cache?: ComputedRef<T> },
|
|
|
|
|
+): T {
|
|
|
|
|
+ if (!source._cache) {
|
|
|
|
|
+ source._cache = computed(source)
|
|
|
|
|
+ }
|
|
|
|
|
+ return source._cache.value
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
export function getPropsProxyHandlers(
|
|
export function getPropsProxyHandlers(
|
|
@@ -78,7 +91,11 @@ export function getPropsProxyHandlers(
|
|
|
while (i--) {
|
|
while (i--) {
|
|
|
source = dynamicSources[i]
|
|
source = dynamicSources[i]
|
|
|
isDynamic = isFunction(source)
|
|
isDynamic = isFunction(source)
|
|
|
- source = isDynamic ? (source as Function)() : source
|
|
|
|
|
|
|
+ source = isDynamic
|
|
|
|
|
+ ? (resolveFunctionSource(
|
|
|
|
|
+ source as () => Record<string, unknown>,
|
|
|
|
|
+ ) as any)
|
|
|
|
|
+ : source
|
|
|
for (rawKey in source) {
|
|
for (rawKey in source) {
|
|
|
if (camelize(rawKey) === key) {
|
|
if (camelize(rawKey) === key) {
|
|
|
return resolvePropValue(
|
|
return resolvePropValue(
|
|
@@ -205,7 +222,11 @@ export function getAttrFromRawProps(rawProps: RawProps, key: string): unknown {
|
|
|
while (i--) {
|
|
while (i--) {
|
|
|
source = dynamicSources[i]
|
|
source = dynamicSources[i]
|
|
|
isDynamic = isFunction(source)
|
|
isDynamic = isFunction(source)
|
|
|
- source = isDynamic ? (source as Function)() : source
|
|
|
|
|
|
|
+ source = isDynamic
|
|
|
|
|
+ ? (resolveFunctionSource(
|
|
|
|
|
+ source as () => Record<string, unknown>,
|
|
|
|
|
+ ) as any)
|
|
|
|
|
+ : source
|
|
|
if (source && hasOwn(source, key)) {
|
|
if (source && hasOwn(source, key)) {
|
|
|
const value = isDynamic ? source[key] : source[key]()
|
|
const value = isDynamic ? source[key] : source[key]()
|
|
|
if (merged) {
|
|
if (merged) {
|
|
@@ -337,7 +358,7 @@ export function resolveDynamicProps(props: RawProps): Record<string, unknown> {
|
|
|
if (props.$) {
|
|
if (props.$) {
|
|
|
for (const source of props.$) {
|
|
for (const source of props.$) {
|
|
|
const isDynamic = isFunction(source)
|
|
const isDynamic = isFunction(source)
|
|
|
- const resolved = isDynamic ? source() : source
|
|
|
|
|
|
|
+ const resolved = isDynamic ? resolveFunctionSource(source) : source
|
|
|
for (const key in resolved) {
|
|
for (const key in resolved) {
|
|
|
const value = isDynamic ? resolved[key] : (resolved[key] as Function)()
|
|
const value = isDynamic ? resolved[key] : (resolved[key] as Function)()
|
|
|
if (key === 'class' || key === 'style') {
|
|
if (key === 'class' || key === 'style') {
|