diff --git a/packages/components/_private/checkable-list/src/CheckableList.tsx b/packages/components/_private/checkable-list/src/CheckableList.tsx index b1b656081..66dbb8c8f 100644 --- a/packages/components/_private/checkable-list/src/CheckableList.tsx +++ b/packages/components/_private/checkable-list/src/CheckableList.tsx @@ -21,6 +21,7 @@ export default defineComponent({ setup(props, { slots, expose }) { const common = useGlobalConfig('common') const mergedPrefixCls = computed(() => `${common.prefixCls}-checkable-list`) + const labelKey = computed(() => props.labelKey ?? 'label') const virtualScrollRef = ref() provide(checkableListContext, { @@ -33,7 +34,7 @@ export default defineComponent({ expose(checkableListApi) - const getRowKey = (item: CheckableListData) => (props.getRowKey?.(item) ?? item.key)! + const getKey = (item: CheckableListData) => (props.getKey?.(item) ?? item.key)! const handleScroll = (evt: Event) => { callEmit(props.onScroll, evt) @@ -46,7 +47,7 @@ export default defineComponent({ } const renderListItem: VirtualItemRenderFn = ({ item, index }) => { - const key = getRowKey(item) + const key = getKey(item) const onCheckChange = (checked: boolean) => { callEmit(props.onCheckChange, item, checked) } @@ -60,7 +61,7 @@ export default defineComponent({ (), - checkable: IxPropTypes.bool.def(true), - removable: IxPropTypes.bool.def(false), - checked: IxPropTypes.func<(item: CheckableListData) => boolean>(), + dataSource: Array as PropType, + checkable: { + type: Boolean, + default: true, + }, + removable: { + type: Boolean, + default: false, + }, + checked: Function as PropType<(item: CheckableListData) => boolean>, customAdditional: { type: Object as PropType, default: undefined }, - disabled: IxPropTypes.func<(item: CheckableListData) => boolean>(), - getRowKey: IxPropTypes.func<(item: CheckableListData) => VKey>(), - virtual: IxPropTypes.bool, - scroll: IxPropTypes.object(), - onCheckChange: IxPropTypes.emit<(item: CheckableListData, checked: boolean) => void>(), - onRemove: IxPropTypes.emit<(item: CheckableListData) => void>(), - onScroll: IxPropTypes.emit<(evt: Event) => void>(), - onScrolledChange: IxPropTypes.emit<(startIndex: number, endIndex: number, visibleData: unknown[]) => void>(), - onScrolledBottom: IxPropTypes.emit<() => void>(), + disabled: Function as PropType<(item: CheckableListData) => boolean>, + getKey: Function as PropType<(item: CheckableListData) => VKey>, + labelKey: String, + virtual: { + type: Boolean, + default: false, + }, + scroll: Object as PropType, + onCheckChange: [Function, Array] as PropType void>>, + onRemove: [Function, Array] as PropType void>>, + onScroll: [Function, Array] as PropType void>>, + onScrolledChange: [Function, Array] as PropType< + MaybeArray<(startIndex: number, endIndex: number, visibleData: unknown[]) => void> + >, + onScrolledBottom: [Function, Array] as PropType void>>, } export const checkableListItemProps = { - checked: IxPropTypes.bool.def(false), - checkable: IxPropTypes.bool.def(true), - removable: IxPropTypes.bool.def(false), - disabled: IxPropTypes.bool.def(false), - label: IxPropTypes.string, - value: IxPropTypes.oneOfType([String, Number, Symbol]).isRequired, - onCheckChange: IxPropTypes.emit<(checked: boolean) => void>(), - onRemove: IxPropTypes.emit<() => void>(), + checked: { + type: Boolean, + default: false, + }, + checkable: { + type: Boolean, + default: true, + }, + removable: { + type: Boolean, + default: false, + }, + disabled: { + type: Boolean, + default: false, + }, + label: String, + value: { + type: [String, Number, Symbol], + required: true, + }, + onCheckChange: [Function, Array] as PropType void>>, + onRemove: [Function, Array] as PropType void>>, } export interface CheckableListApi { diff --git a/packages/components/transfer/src/Transfer.tsx b/packages/components/transfer/src/Transfer.tsx index 58c19d588..1de0ced56 100644 --- a/packages/components/transfer/src/Transfer.tsx +++ b/packages/components/transfer/src/Transfer.tsx @@ -70,7 +70,7 @@ export default defineComponent({ sourceCheckableListRef, targetCheckableListRef, showSelectAll, - getRowKey: transferDataContext.getRowKey, + getKey: transferDataContext.getKey, }) provide(TRANSFER_SOURCE_TOKEN, sourceBindings) provide(TRANSFER_TARGET_TOKEN, targetBindings) diff --git a/packages/components/transfer/src/composables/useGetRowKey.ts b/packages/components/transfer/src/composables/useGetRowKey.ts deleted file mode 100644 index 31dcf42dd..000000000 --- a/packages/components/transfer/src/composables/useGetRowKey.ts +++ /dev/null @@ -1,36 +0,0 @@ -/** - * @license - * - * Use of this source code is governed by an MIT-style license that can be - * found in the LICENSE file at https://github.com/IDuxFE/idux/blob/main/LICENSE - */ - -import type { TransferData, TransferProps } from '../types' -import type { TransferConfig } from '@idux/components/config' - -import { computed } from 'vue' - -import { isString } from 'lodash-es' - -import { Logger, type VKey } from '@idux/cdk/utils' - -export type GetRowKey = (record: TransferData) => VKey - -export function useGetRowKey(props: TransferProps, config: TransferConfig): GetRowKey { - const getKey = computed(() => { - const getKey = props.getKey ?? config.getKey - if (isString(getKey)) { - return (record: TransferData) => { - // eslint-disable-next-line @typescript-eslint/no-explicit-any - const key = (record as any)[getKey] - if (__DEV__ && key === undefined) { - Logger.warn('components/transfer', 'Each record in transfer should have a unique `key` prop.') - } - return key - } - } - return getKey - }) - - return (record: TransferData) => getKey.value(record) -} diff --git a/packages/components/transfer/src/composables/useTransferBindings.ts b/packages/components/transfer/src/composables/useTransferBindings.ts index ec6cfe623..06cdf3bd7 100644 --- a/packages/components/transfer/src/composables/useTransferBindings.ts +++ b/packages/components/transfer/src/composables/useTransferBindings.ts @@ -46,7 +46,7 @@ export function useTransferBindings( setSourceSearchValue, targetSearchValue, setTargetSearchValue, - getRowKey, + getKey, } = transferDataContext const { sourceSelectedKeys, @@ -74,7 +74,7 @@ export function useTransferBindings( showSelectAll, triggerAppend, triggerRemove, - getRowKey, + getKey, } return { diff --git a/packages/components/transfer/src/composables/useTransferData.ts b/packages/components/transfer/src/composables/useTransferData.ts index 886f8e3a3..d19460157 100644 --- a/packages/components/transfer/src/composables/useTransferData.ts +++ b/packages/components/transfer/src/composables/useTransferData.ts @@ -13,8 +13,7 @@ import type { PaginationProps } from '@idux/components/pagination' import { type ComputedRef, computed } from 'vue' import { type VKey, callEmit, useControlledProp, useState } from '@idux/cdk/utils' - -import { type GetRowKey, useGetRowKey } from './useGetRowKey' +import { type GetKeyFn, useGetKey } from '@idux/components/utils' export interface TransferDataContext { dataSource: ComputedRef @@ -35,7 +34,7 @@ export interface TransferDataContext { remove: (keys: VKey[]) => void clear: () => void - getRowKey: GetRowKey + getKey: ComputedRef disabledKeys: ComputedRef> disabledSourceKeys: ComputedRef> @@ -54,7 +53,7 @@ export function useTransferData( transferDataStrategies: TransferDataStrategies, transferPaginationContext: TransferPaginationContext, ): TransferDataContext { - const getRowKey = useGetRowKey(props, config) + const getKey = useGetKey(props, config, 'transfer') const { genDataKeys, genDataKeyMap, @@ -66,7 +65,7 @@ export function useTransferData( } = transferDataStrategies const dataSource = computed(() => props.dataSource as T[]) - const dataKeyMap = computed(() => genDataKeyMap(dataSource.value, getRowKey)) + const dataKeyMap = computed(() => genDataKeyMap(dataSource.value, getKey.value)) const [targetKeys, setTargetKeys] = useControlledProp(props, 'value', () => []) const [sourceSearchValue, setSourceSearchValue] = useState('') @@ -80,13 +79,13 @@ export function useTransferData( } const separatedData = computed(() => - separateDataSource(dataSource.value, dataKeyMap.value, targetKeySet.value, getRowKey), + separateDataSource(dataSource.value, dataKeyMap.value, targetKeySet.value, getKey.value), ) const sourceData = computed(() => separatedData.value.sourceData) const targetData = computed(() => separatedData.value.targetData) - const sourceDataKeys = computed(() => genDataKeys(sourceData.value, getRowKey)) - const targetDataKeys = computed(() => genDataKeys(targetData.value, getRowKey)) + const sourceDataKeys = computed(() => genDataKeys(sourceData.value, getKey.value)) + const targetDataKeys = computed(() => genDataKeys(targetData.value, getKey.value)) const filteredDataSource = computed(() => dataFilter( @@ -121,19 +120,19 @@ export function useTransferData( ) const append = (keys: VKey[]) => { - _append(keys, targetKeySet.value, getRowKey, handleChange) + _append(keys, targetKeySet.value, getKey.value, handleChange) } const remove = (keys: VKey[]) => { - _remove(keys, targetKeySet.value, getRowKey, handleChange) + _remove(keys, targetKeySet.value, getKey.value, handleChange) } const clear = () => { handleChange(Array.from(disabledTargetKeys.value)) } - const disabledKeys = computed(() => genDisabledKeys(dataSource.value, getRowKey)) + const disabledKeys = computed(() => genDisabledKeys(dataSource.value, getKey.value)) const disabledTargetKeys = computed(() => { - const keys = genDisabledKeys(targetData.value, getRowKey) + const keys = genDisabledKeys(targetData.value, getKey.value) targetKeySet.value.forEach(key => { if (disabledKeys.value.has(key)) { @@ -142,7 +141,7 @@ export function useTransferData( }) return keys }) - const disabledSourceKeys = computed(() => genDisabledKeys(sourceData.value, getRowKey)) + const disabledSourceKeys = computed(() => genDisabledKeys(sourceData.value, getKey.value)) return { dataSource, @@ -163,7 +162,7 @@ export function useTransferData( remove, clear, - getRowKey, + getKey, disabledKeys, disabledSourceKeys, diff --git a/packages/components/transfer/src/composables/useTransferDataStrategies.ts b/packages/components/transfer/src/composables/useTransferDataStrategies.ts index 5198dad00..c7bf7373a 100644 --- a/packages/components/transfer/src/composables/useTransferDataStrategies.ts +++ b/packages/components/transfer/src/composables/useTransferDataStrategies.ts @@ -20,29 +20,29 @@ function createDefaultStrategies(): Trans }) return { - genDataKeys: (data, getRowKey) => { - return new Set(data.map(data => getRowKey(data))) + genDataKeys: (data, getKey) => { + return new Set(data.map(data => getKey(data))) }, - genDataKeyMap: (dataSource, getRowKey) => { + genDataKeyMap: (dataSource, getKey) => { const dataKeyMap = new Map() dataSource.forEach(item => { - dataKeyMap.set(getRowKey(item), item) + dataKeyMap.set(getKey(item), item) }) return dataKeyMap }, - genDisabledKeys: (data, getRowKey) => { + genDisabledKeys: (data, getKey) => { const keys = new Set() data.forEach(item => { if (item.disabled) { - keys.add(getRowKey(item)) + keys.add(getKey(item)) } }) return keys }, - separateDataSource: (dataSource, dataKeyMap, selectedKeySet, getRowKey) => { - const sourceData = dataSource.filter(data => !selectedKeySet.has(getRowKey(data))) + separateDataSource: (dataSource, dataKeyMap, selectedKeySet, getKey) => { + const sourceData = dataSource.filter(data => !selectedKeySet.has(getKey(data))) const targetData: T[] = [] selectedKeySet.forEach(key => { diff --git a/packages/components/transfer/src/composables/useTransferOperations.ts b/packages/components/transfer/src/composables/useTransferOperations.ts index 7fd999165..4f9b5939c 100644 --- a/packages/components/transfer/src/composables/useTransferOperations.ts +++ b/packages/components/transfer/src/composables/useTransferOperations.ts @@ -29,26 +29,17 @@ export function useTransferOperations( transferDataContext: TransferDataContext, transferSelectStateContext: TransferSelectStateContext, ): TransferOperationsContext { - const { - dataKeyMap, - sourceData, - targetData, - disabledSourceKeys, - disabledTargetKeys, - append, - remove, - clear, - getRowKey, - } = transferDataContext + const { dataKeyMap, sourceData, targetData, disabledSourceKeys, disabledTargetKeys, append, remove, clear, getKey } = + transferDataContext const { sourceSelectedKeys, targetSelectedKeys } = transferSelectStateContext const appendDisabled = computed(() => props.disabled || sourceSelectedKeys.value.length <= 0) const removeDisabled = computed(() => props.disabled || targetSelectedKeys.value.length <= 0) const appendAllDisabled = computed( - () => props.disabled || sourceData.value.every(item => disabledSourceKeys.value.has(getRowKey(item))), + () => props.disabled || sourceData.value.every(item => disabledSourceKeys.value.has(getKey.value(item))), ) const clearDisabled = computed( - () => props.disabled || targetData.value.every(item => disabledTargetKeys.value.has(getRowKey(item))), + () => props.disabled || targetData.value.every(item => disabledTargetKeys.value.has(getKey.value(item))), ) const triggerAppend = (keys?: VKey[]) => { diff --git a/packages/components/transfer/src/list/TransferListBody.tsx b/packages/components/transfer/src/list/TransferListBody.tsx index dd9263d31..bafdd1e02 100644 --- a/packages/components/transfer/src/list/TransferListBody.tsx +++ b/packages/components/transfer/src/list/TransferListBody.tsx @@ -24,7 +24,7 @@ export default defineComponent({ mergedPrefixCls, sourceCheckableListRef, targetCheckableListRef, - getRowKey, + getKey, } = inject(transferContext)! const transferBindings = props.isSource ? inject(TRANSFER_SOURCE_TOKEN)! : inject(TRANSFER_TARGET_TOKEN)! @@ -61,14 +61,14 @@ export default defineComponent({ } const onCheckChange = (item: TransferData, checked: boolean) => { - const key = getRowKey(item) + const key = getKey.value(item) const _checkedKeys = new Set(selectedKeySet.value) checked ? _checkedKeys.add(key) : _checkedKeys.delete(key) handleSelectChange(_checkedKeys) } const onRemove = (item: TransferData) => { - const key = getRowKey(item) + const key = getKey.value(item) triggerRemove([key]) } @@ -76,9 +76,9 @@ export default defineComponent({ <ɵCheckableList ref={checkableListRef} dataSource={checkListData.value} - getRowKey={getRowKey} - checked={item => selectedKeySet.value.has(getRowKey(item))} - disabled={item => transferProps.disabled || disabledDataSourceKeys.value.has(getRowKey(item))} + getKey={getKey.value} + checked={item => selectedKeySet.value.has(getKey.value(item))} + disabled={item => transferProps.disabled || disabledDataSourceKeys.value.has(getKey.value(item))} checkable={props.isSource || transferProps.mode === 'default'} removable={!props.isSource && transferProps.mode === 'immediate'} virtual={transferProps.virtual} diff --git a/packages/components/transfer/src/token.ts b/packages/components/transfer/src/token.ts index 2824515da..799336ea8 100644 --- a/packages/components/transfer/src/token.ts +++ b/packages/components/transfer/src/token.ts @@ -5,12 +5,12 @@ * found in the LICENSE file at https://github.com/IDuxFE/idux/blob/main/LICENSE */ -import type { GetRowKey } from './composables/useGetRowKey' import type { TransferOperationsContext } from './composables/useTransferOperations' import type { TransferBindings, TransferDataStrategiesConfig, TransferProps, TransferSlots } from './types' import type { ɵCheckableListInstance } from '@idux/components/_private/checkable-list' import type { TransferConfig } from '@idux/components/config' import type { TransferLocale } from '@idux/components/locales' +import type { GetKeyFn } from '@idux/components/utils' import type { ComputedRef, InjectionKey, Ref } from 'vue' interface TransferContext { @@ -22,7 +22,7 @@ interface TransferContext { sourceCheckableListRef: Ref<ɵCheckableListInstance | undefined> targetCheckableListRef: Ref<ɵCheckableListInstance | undefined> showSelectAll: ComputedRef - getRowKey: GetRowKey + getKey: ComputedRef } export const transferContext: InjectionKey = Symbol('transferContext') diff --git a/packages/components/transfer/src/types.ts b/packages/components/transfer/src/types.ts index 430f1c717..38cb8892e 100644 --- a/packages/components/transfer/src/types.ts +++ b/packages/components/transfer/src/types.ts @@ -5,34 +5,32 @@ * found in the LICENSE file at https://github.com/IDuxFE/idux/blob/main/LICENSE */ -import type { GetRowKey } from './composables/useGetRowKey' import type { TransferOperationsContext } from './composables/useTransferOperations' import type { ConvertToSlotParams } from './utils' import type { VirtualScrollToFn } from '@idux/cdk/scroll' -import type { ExtractInnerPropTypes, ExtractPublicPropTypes, VKey } from '@idux/cdk/utils' +import type { ExtractInnerPropTypes, ExtractPublicPropTypes, MaybeArray, VKey } from '@idux/cdk/utils' import type { EmptyProps } from '@idux/components/empty' import type { PaginationProps } from '@idux/components/pagination' +import type { GetKeyFn } from '@idux/components/utils' import type { ComputedRef, DefineComponent, HTMLAttributes, PropType, Slots, VNode } from 'vue' -import { IxPropTypes } from '@idux/cdk/utils' - export interface SeparatedData { sourceData: T[] targetData: T[] } export interface TransferDataStrategiesConfig { - genDataKeys?: (data: T[], getRowKey: GetRowKey) => Set - genDataKeyMap?: (dataSource: T[], getRowKey: GetRowKey) => Map - genDisabledKeys?: (data: T[], getRowKey: GetRowKey) => Set + genDataKeys?: (data: T[], getKey: GetKeyFn) => Set + genDataKeyMap?: (dataSource: T[], getKey: GetKeyFn) => Map + genDisabledKeys?: (data: T[], getKey: GetKeyFn) => Set separateDataSource?: ( dataSource: T[], dataKeyMap: Map, selectedKeySet: Set, - getRowKey: GetRowKey, + getKey: GetKeyFn, ) => SeparatedData dataFilter?: (data: T[], searchValue: string, searchFn: (item: T, searchValue: string) => boolean) => T[] - append?: (keys: VKey[], selectedKeySet: Set, getRowKey: GetRowKey, handleChange: (keys: VKey[]) => void) => void - remove?: (keys: VKey[], selectedKeySet: Set, getRowKey: GetRowKey, handleChange: (keys: VKey[]) => void) => void + append?: (keys: VKey[], selectedKeySet: Set, getKey: GetKeyFn, handleChange: (keys: VKey[]) => void) => void + remove?: (keys: VKey[], selectedKeySet: Set, getKey: GetKeyFn, handleChange: (keys: VKey[]) => void) => void } export type TransferDataStrategies = Required> @@ -61,7 +59,7 @@ export interface TransferBindings { triggerAppend: (keys: VKey[]) => void triggerRemove: (keys: VKey[]) => void - getRowKey: GetRowKey + getKey: ComputedRef handleSelectChange: (keys: Set | VKey[]) => void selectAll: (selected?: boolean) => void @@ -108,56 +106,102 @@ export type SearchFn = ( searchValue: string, ) => boolean export const transferProps = { - value: IxPropTypes.array(), - sourceSelectedKeys: IxPropTypes.array(), - targetSelectedKeys: IxPropTypes.array(), - - clearable: IxPropTypes.bool, - clearIcon: IxPropTypes.string, + value: Array as PropType, + sourceSelectedKeys: Array as PropType, + targetSelectedKeys: Array as PropType, + + clearable: { + type: Boolean, + default: undefined, + }, + clearIcon: String, customAdditional: { type: Object as PropType, default: undefined }, - dataSource: IxPropTypes.array().def(() => []), - disabled: IxPropTypes.bool.def(false), - empty: IxPropTypes.oneOfType([String, IxPropTypes.object()]), - getKey: IxPropTypes.oneOfType([String, IxPropTypes.func<(item: TransferData) => number | string>()]), - mode: IxPropTypes.oneOf(['default', 'immediate']).def('default'), - pagination: IxPropTypes.oneOfType([Boolean, IxPropTypes.object()]), - scroll: IxPropTypes.object(), - searchable: IxPropTypes.oneOfType([Boolean, IxPropTypes.object<{ source: boolean; target: boolean }>()]), - searchFn: IxPropTypes.func(), - spin: IxPropTypes.oneOfType([Boolean, IxPropTypes.object<{ source: boolean; target: boolean }>()]), - showSelectAll: IxPropTypes.bool, - virtual: IxPropTypes.bool.def(false), + dataSource: { + type: Array as PropType, + default: (): TransferData[] => [], + }, + disabled: { + type: Boolean, + default: false, + }, + empty: [String, Object] as PropType, + getKey: [String, Function] as PropType number | string)>, + mode: { + type: String as PropType, + default: 'default', + }, + pagination: { + type: [Boolean, Object] as PropType, + default: undefined, + }, + scroll: Object as PropType, + searchable: { + type: [Boolean, Object] as PropType, + default: undefined, + }, + searchFn: Function as PropType, + spin: { + type: [Boolean, Object] as PropType, + default: undefined, + }, + showSelectAll: { + type: Boolean, + default: undefined, + }, + virtual: { + type: Boolean, + default: false, + }, //Events - 'onUpdate:value': IxPropTypes.emit<(keys: VKey[]) => void>(), - 'onUpdate:sourceSelectedKeys': IxPropTypes.emit<(keys: VKey[]) => void>(), - 'onUpdate:targetSelectedKeys': IxPropTypes.emit<(keys: VKey[]) => void>(), - onChange: IxPropTypes.emit<(keys: VKey[], oldKeys: VKey[]) => void>(), - onSearch: IxPropTypes.emit<(isSource: boolean, searchValue: string) => void>(), - onSelectAll: IxPropTypes.emit<(isSource: boolean, selectAll: boolean) => void>(), - onClear: IxPropTypes.emit<() => void>(), - - onScroll: IxPropTypes.emit<(isSource: boolean, evt: Event) => void>(), - onScrolledChange: - IxPropTypes.emit<(isSource: boolean, startIndex: number, endIndex: number, visibleData: unknown[]) => void>(), - onScrolledBottom: IxPropTypes.emit<(isSource: boolean) => void>(), + 'onUpdate:value': [Function, Array] as PropType void>>, + 'onUpdate:sourceSelectedKeys': [Function, Array] as PropType void>>, + 'onUpdate:targetSelectedKeys': [Function, Array] as PropType void>>, + onChange: [Function, Array] as PropType void>>, + onSearch: [Function, Array] as PropType void>>, + onSelectAll: [Function, Array] as PropType void>>, + onClear: [Function, Array] as PropType void>>, + + onScroll: [Function, Array] as PropType void>>, + onScrolledChange: [Function, Array] as PropType< + MaybeArray<(isSource: boolean, startIndex: number, endIndex: number, visibleData: unknown[]) => void> + >, + onScrolledBottom: [Function, Array] as PropType void>>, } as const export const transferListProps = { - isSource: IxPropTypes.bool.isRequired, + isSource: { + type: Boolean, + required: true, + }, } export const transferListBodyProps = transferListProps export const transferListHeaderProps = transferListProps export const transferListFooterProps = transferListProps export const transferListItemProps = { - checked: IxPropTypes.bool.def(false), - checkable: IxPropTypes.bool.isRequired, - removable: IxPropTypes.bool.isRequired, - disabled: IxPropTypes.bool.def(false), - value: IxPropTypes.oneOfType([String, Number, Symbol]).isRequired, - onChange: IxPropTypes.emit<(value: boolean) => void>(), - onRemove: IxPropTypes.emit<() => void>(), + checked: { + type: Boolean, + default: false, + }, + checkable: { + type: Boolean, + required: true, + }, + removable: { + type: Boolean, + required: true, + }, + disabled: { + type: Boolean, + default: false, + }, + value: { + type: [String, Number, Symbol], + required: true, + }, + onChange: [Function, Array] as PropType void>>, + onRemove: [Function, Array] as PropType void>>, } export interface TransferApis { diff --git a/packages/components/tree/__tests__/__snapshots__/tree.spec.ts.snap b/packages/components/tree/__tests__/__snapshots__/tree.spec.ts.snap index 16999d675..e09ea578a 100644 --- a/packages/components/tree/__tests__/__snapshots__/tree.spec.ts.snap +++ b/packages/components/tree/__tests__/__snapshots__/tree.spec.ts.snap @@ -948,3 +948,45 @@ exports[`Tree > searchValue work 4`] = ` " `; + +exports[`Tree > searchValue work 5`] = ` +"
+ +
+
+
+
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+
+
+
+
" +`; diff --git a/packages/pro/transfer/src/ProTransfer.tsx b/packages/pro/transfer/src/ProTransfer.tsx index 9ba496d75..505875bc4 100644 --- a/packages/pro/transfer/src/ProTransfer.tsx +++ b/packages/pro/transfer/src/ProTransfer.tsx @@ -13,7 +13,12 @@ import { computed, defineComponent, provide, ref } from 'vue' import { type VKey, useControlledProp } from '@idux/cdk/utils' import { useGlobalConfig as useComponentGlobalConfig } from '@idux/components/config' -import { IxTransfer, TRANSFER_DATA_STRATEGIES, type TransferListSlotParams } from '@idux/components/transfer' +import { + IxTransfer, + TRANSFER_DATA_STRATEGIES, + type TransferDataStrategiesConfig, + type TransferListSlotParams, +} from '@idux/components/transfer' import { useGlobalConfig } from '@idux/pro/config' import { useTreeDataStrategies } from './composables/useTreeDataStrategy' @@ -22,7 +27,7 @@ import ProTransferList from './content/ProTransferList' import ProTransferTable from './content/ProTransferTable' import ProTransferTree from './content/ProTransferTree' import { type ProTransferContext, proTransferContext } from './token' -import { type ProTransferApis, type TreeTransferData, proTransferProps } from './types' +import { type ProTransferApis, type TransferData, type TreeTransferData, proTransferProps } from './types' export default defineComponent({ name: 'IxProTransfer', @@ -54,7 +59,7 @@ export default defineComponent({ dataKeyMap: _dataKeyMap, parentKeyMap, dataStrategies, - } = useTreeDataStrategies(childrenKey, props.defaultTargetData) + } = useTreeDataStrategies(childrenKey, props.defaultTargetData as TreeTransferData[] | undefined) const expandedKeysContext = useTreeExpandedKeys(props, targetKeys, parentKeyMap) dataKeyMap = _dataKeyMap @@ -65,7 +70,7 @@ export default defineComponent({ parentKeyMap, } - provide(TRANSFER_DATA_STRATEGIES, dataStrategies) + provide(TRANSFER_DATA_STRATEGIES, dataStrategies as unknown as TransferDataStrategiesConfig) } provide(proTransferContext, context) @@ -92,14 +97,14 @@ export default defineComponent({ let count = 0 if (isSource) { dataKeyMap.forEach((item, key) => { - if (!targetKeySet.value.has(key) && (!item[childrenKey.value] || item[childrenKey.value].length <= 0)) { + if (!targetKeySet.value.has(key) && (!item[childrenKey.value] || item[childrenKey.value]!.length <= 0)) { ++count } }) } else { targetKeys.value?.forEach(key => { const item = dataKeyMap.get(key) - if (item && (!item[childrenKey.value] || item[childrenKey.value].length <= 0)) { + if (item && (!item[childrenKey.value] || item[childrenKey.value]!.length <= 0)) { ++count } }) diff --git a/packages/pro/transfer/src/composables/useTransferTableProps.ts b/packages/pro/transfer/src/composables/useTransferTableProps.ts index be1540014..57e138f3f 100644 --- a/packages/pro/transfer/src/composables/useTransferTableProps.ts +++ b/packages/pro/transfer/src/composables/useTransferTableProps.ts @@ -24,7 +24,7 @@ export function useTransferTableProps( mergedPrefixCls: ComputedRef, isSource: boolean, ): ComputedRef { - const { paginatedData, paginatedDataSource, selectedKeys, getRowKey } = transferBindings + const { paginatedData, paginatedDataSource, selectedKeys, getKey } = transferBindings return computed(() => { const columns = isSource ? props.tableProps?.sourceColumns : props.tableProps?.targetColumns @@ -46,7 +46,7 @@ export function useTransferTableProps( pagination: false, selectedRowKeys: selectedKeys.value, virtual: props.virtual, - rowKey: getRowKey as (record: unknown) => number | string, + rowKey: getKey.value as (record: unknown) => number | string, onScroll: evt => { callEmit(props.onScroll, isSource, evt) }, @@ -68,14 +68,14 @@ function convertTableColumns( slots: Slots, isSource: boolean, ): TableColumn[] { - const { handleSelectChange, getRowKey, triggerRemove, disabledDataSourceKeys } = transferBindings + const { handleSelectChange, getKey, triggerRemove, disabledDataSourceKeys } = transferBindings const convertedColumns = (columns && [...columns]) ?? [] const selectableColumnIdx = convertedColumns.findIndex(col => 'type' in col && col.type === 'selectable') const defaultSelectableColumn: TableColumnSelectable = { type: 'selectable', - disabled: record => disabledDataSourceKeys.value.has(getRowKey(record)) || !!props.disabled, + disabled: record => disabledDataSourceKeys.value.has(getKey.value(record)) || !!props.disabled, multiple: true, trigger: 'click', onChange: selectedKeys => handleSelectChange(selectedKeys), @@ -99,7 +99,7 @@ function convertTableColumns( if ('type' in lastCol) { convertedColumns.push({ customCell: ({ record }) => { - const key = getRowKey(record) + const key = getKey.value(record) return renderRemovableLabel( key, disabledDataSourceKeys.value.has(key), @@ -127,7 +127,7 @@ function convertTableColumns( convertedColumns.splice(convertedColumns.length - 1, 1, { ...lastCol, customCell: data => { - const key = getRowKey(data.record) + const key = getKey.value(data.record) return renderRemovableLabel( key, disabledDataSourceKeys.value.has(key), diff --git a/packages/pro/transfer/src/composables/useTransferTreeProps.ts b/packages/pro/transfer/src/composables/useTransferTreeProps.ts index 99c7e1bea..e392a81f5 100644 --- a/packages/pro/transfer/src/composables/useTransferTreeProps.ts +++ b/packages/pro/transfer/src/composables/useTransferTreeProps.ts @@ -32,7 +32,7 @@ export function useTransferTreeProps( selectedKeySet, disabledKeys, disabledDataSourceKeys, - getRowKey, + getKey, handleSelectChange, } = transferBindings const { sourceExpandedKeys, targetExpandedKeys, handleSourceExpandedChange, handleTargetExpandedChange } = @@ -45,7 +45,10 @@ export function useTransferTreeProps( const tempKeySet = new Set(selectedKeySet.value) selectedKeys.value.forEach(key => { - if (dataKeyMap.value.get(key)?.[childrenKey.value] && dataKeyMap.value.get(key)?.[childrenKey.value].length > 0) { + if ( + dataKeyMap.value.get(key)?.[childrenKey.value] && + (dataKeyMap.value.get(key)?.[childrenKey.value] as TransferData[]).length > 0 + ) { return } @@ -57,7 +60,11 @@ export function useTransferTreeProps( } const item = dataKeyMap.value.get(currentKey)! - if (item[childrenKey.value].some((child: TransferData) => !tempKeySet.has(getRowKey(child)))) { + if ( + (item[childrenKey.value] as TransferData[]).some( + (child: TransferData) => !tempKeySet.has(getKey.value(child)), + ) + ) { tempKeySet.delete(currentKey) } } @@ -76,11 +83,11 @@ export function useTransferTreeProps( checkedKeys: checkedKeys.value, checkStrategy: 'all', dataSource: treeDataSource.value, - disabled: node => _disabledKeys.value.has(getRowKey(node as TransferData)) || !!props.disabled, + disabled: node => _disabledKeys.value.has(getKey.value(node as TransferData)) || !!props.disabled, draggable: false, expandedKeys: isSource ? sourceExpandedKeys.value : targetExpandedKeys.value, height: isNumber(props.scroll?.height) ? props.scroll?.height : undefined, - nodeKey: getRowKey as (node: TreeNode) => VKey, + getKey: getKey.value as (node: TreeNode) => VKey, selectable: true, virtual: props.virtual, 'onUpdate:checkedKeys': handleSelectChange, diff --git a/packages/pro/transfer/src/composables/useTreeDataStrategy.ts b/packages/pro/transfer/src/composables/useTreeDataStrategy.ts index efbf92e70..fc117a2de 100644 --- a/packages/pro/transfer/src/composables/useTreeDataStrategy.ts +++ b/packages/pro/transfer/src/composables/useTreeDataStrategy.ts @@ -53,8 +53,11 @@ export function useTreeDataStrategies( } if (item[childrenKey.value]) { - keys = genDisabledKeys(item[childrenKey.value], getRowKey, keys) - if (item[childrenKey.value].every((child: TreeTransferData) => keys.has(getRowKey(child)))) { + keys = genDisabledKeys(item[childrenKey.value]!, getRowKey, keys) + if ( + item[childrenKey.value]!.length > 0 && + item[childrenKey.value]!.every((child: TreeTransferData) => keys.has(getRowKey(child))) + ) { keys.add(key) } } diff --git a/packages/pro/transfer/src/content/ProTransferList.tsx b/packages/pro/transfer/src/content/ProTransferList.tsx index d8a772052..ef26a4d60 100644 --- a/packages/pro/transfer/src/content/ProTransferList.tsx +++ b/packages/pro/transfer/src/content/ProTransferList.tsx @@ -7,13 +7,13 @@ import { computed, defineComponent, inject } from 'vue' -import { callEmit } from '@idux/cdk/utils' +import { type VKey, callEmit } from '@idux/cdk/utils' import { ɵCheckableList } from '@idux/components/_private/checkable-list' import { ɵEmpty } from '@idux/components/_private/empty' import { TRANSFER_SOURCE_TOKEN, TRANSFER_TARGET_TOKEN } from '@idux/components/transfer' import { proTransferContext } from '../token' -import { type TransferData, proTransferListContentProps } from '../types' +import { type TreeTransferData, proTransferListContentProps } from '../types' import { flattenTree } from '../utils' export default defineComponent({ @@ -34,19 +34,19 @@ export default defineComponent({ paginatedDataSource, selectedKeySet, handleSelectChange, - getRowKey, + getKey, triggerRemove, } = transferBindings - const onCheckChange = (item: TransferData, checked: boolean) => { - const key = getRowKey(item) + const onCheckChange = (item: TreeTransferData, checked: boolean) => { + const key = getKey.value(item) const _checkedKeys = new Set(selectedKeySet.value) checked ? _checkedKeys.add(key) : _checkedKeys.delete(key) handleSelectChange(_checkedKeys) } - const onRemove = (item: TransferData) => { - const key = getRowKey(item) + const onRemove = (item: TreeTransferData) => { + const key = getKey.value(item) triggerRemove([key]) } @@ -64,7 +64,9 @@ export default defineComponent({ const data = props.isSource && proTransferProps.mode === 'immediate' ? paginatedDataSource.value : paginatedData.value - return proTransferProps.type === 'tree' ? flattenTree(data, childrenKey.value, true) : data + return proTransferProps.type === 'tree' + ? flattenTree(data as TreeTransferData[], childrenKey.value, true) + : data }) return () => { @@ -82,9 +84,10 @@ export default defineComponent({ <ɵCheckableList ref={contentRef} dataSource={dataSource.value} - getRowKey={getRowKey} - checked={item => selectedKeySet.value.has(getRowKey(item))} - disabled={item => proTransferProps.disabled || disabledKeys.value.has(getRowKey(item))} + getKey={getKey.value} + labelKey={proTransferProps.treeProps?.labelKey} + checked={item => selectedKeySet.value.has(getKey.value(item))} + disabled={item => proTransferProps.disabled || disabledKeys.value.has(getKey.value(item))} checkable={props.isSource || proTransferProps.mode === 'default'} removable={!props.isSource && proTransferProps.mode === 'immediate'} virtual={proTransferProps.virtual} diff --git a/packages/pro/transfer/src/content/ProTransferTree.tsx b/packages/pro/transfer/src/content/ProTransferTree.tsx index 21b7c3185..05f4df0fb 100644 --- a/packages/pro/transfer/src/content/ProTransferTree.tsx +++ b/packages/pro/transfer/src/content/ProTransferTree.tsx @@ -7,14 +7,14 @@ import { computed, defineComponent, inject, normalizeStyle } from 'vue' -import { convertCssPixel } from '@idux/cdk/utils' +import { type VKey, convertCssPixel } from '@idux/cdk/utils' import { ɵEmpty } from '@idux/components/_private/empty' import { TRANSFER_SOURCE_TOKEN, TRANSFER_TARGET_TOKEN } from '@idux/components/transfer' import { IxTree } from '@idux/components/tree' import { useTransferTreeProps } from '../composables/useTransferTreeProps' import { proTransferContext } from '../token' -import { type TransferData, proTransferTreeContentProps } from '../types' +import { type TreeTransferData, proTransferTreeContentProps } from '../types' import { genFlattenedTreeKeys } from '../utils' import { renderRemoveIcon } from './RenderRemovableLabel' @@ -35,7 +35,7 @@ export default defineComponent({ const proTransferTreeCls = computed(() => `${mergedPrefixCls.value}-tree-content`) const transferBindings = inject(props.isSource ? TRANSFER_SOURCE_TOKEN : TRANSFER_TARGET_TOKEN)! - const { disabledKeys, getRowKey, triggerRemove } = transferBindings + const { disabledKeys, getKey, triggerRemove } = transferBindings const treeProps = useTransferTreeProps( proTransferProps, transferBindings, @@ -45,12 +45,12 @@ export default defineComponent({ props.isSource, ) - const renderTreeRemovableSuffix = ({ node }: { node: TransferData }) => { + const renderTreeRemovableSuffix = ({ node }: { node: TreeTransferData }) => { const prefixCls = proTransferTreeCls.value - const key = getRowKey(node) + const key = getKey.value(node) const onClick = () => { - triggerRemove(genFlattenedTreeKeys([node], childrenKey.value, getRowKey)) + triggerRemove(genFlattenedTreeKeys([node], childrenKey.value, getKey.value)) } return (