A modern vue admin. It is based on Vue3, vite and TypeScript. It's fast!
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

47 lines
1.3 KiB

import type { Ref } from 'vue';
import { computed, getCurrentInstance, useAttrs, useSlots } from 'vue';
import {
getFirstNonNullOrUndefined,
kebabToCamelCase,
} from '@vben-core/shared';
/**
* 依次从插槽、attrs、props、state 中获取值
* @param key
* @param props
* @param state
*/
export function usePriorityValue<
T extends Record<string, any>,
S extends Record<string, any>,
K extends keyof T = keyof T,
>(key: K, props: T, state: Readonly<Ref<NoInfer<S>>> | undefined) {
const instance = getCurrentInstance();
const slots = useSlots();
const attrs = useAttrs() as T;
const value = computed((): T[K] => {
// props不管有没有传,都会有默认值,会影响这里的顺序,
// 通过判断原始props是否有值来判断是否传入
const rawProps = (instance?.vnode?.props || {}) as T;
const standardRawProps = {} as T;
for (const [key, value] of Object.entries(rawProps)) {
standardRawProps[kebabToCamelCase(key) as K] = value;
}
const propsKey =
standardRawProps?.[key] === undefined ? undefined : props[key];
// slot可以关闭
return getFirstNonNullOrUndefined(
slots[key as string],
attrs[key],
propsKey,
state?.value?.[key as keyof S],
) as T[K];
});
return value;
}