refactor: tree-select

pull/4577/head
tangjinzhou 2021-08-22 22:22:22 +08:00
parent 8bf14f40ac
commit 8e38ed883c
10 changed files with 43 additions and 21 deletions

View File

@ -70,6 +70,7 @@ const TreeSelect = defineComponent({
}),
slots: [
'title',
'titleRender',
'placeholder',
'maxTagPlaceholder',
'treeIcon',

View File

@ -42,7 +42,7 @@ export default defineComponent({
showIcon: true,
expandAction: 'click',
}),
slots: ['icon', 'title', 'switcherIcon'],
slots: ['icon', 'title', 'switcherIcon', 'titleRender'],
emits: [
'update:selectedKeys',
'update:checkedKeys',

View File

@ -141,7 +141,7 @@ export default defineComponent({
showIcon: false,
blockNode: false,
}),
slots: ['icon', 'title', 'switcherIcon'],
slots: ['icon', 'title', 'switcherIcon', 'titleRender'],
emits: [
'update:selectedKeys',
'update:checkedKeys',

View File

@ -1,7 +1,7 @@
import pickAttrs from '../../_util/pickAttrs';
import Input from './Input';
import type { InnerSelectorProps } from './interface';
import type { VNodeChild } from 'vue';
import { Fragment, Suspense, VNodeChild } from 'vue';
import { computed, defineComponent, ref, watch } from 'vue';
import PropTypes from '../../_util/vue-types';
import { useInjectTreeSelectContext } from 'ant-design-vue/es/vc-tree-select/Context';
@ -96,11 +96,21 @@ const SingleSelector = defineComponent<SelectorProps>({
onInputCompositionEnd,
} = props;
const item = values[0];
let slotTitle = null;
if (treeSelectContext.value.slots) {
slotTitle =
let titleNode = null;
// custom tree-select title by slot
if (item && treeSelectContext.value.slots) {
titleNode =
item.label ||
treeSelectContext.value.slots[item?.option?.data?.slots?.title] ||
treeSelectContext.value.slots.title;
if (typeof titleNode === 'function') {
titleNode = titleNode(item.option?.data || {});
} else if (treeSelectContext.value.slots.titleRender) {
// title titleRender title titleRender
titleNode = treeSelectContext.value.slots.titleRender(item.option?.data || {});
}
} else {
titleNode = item?.label;
}
return (
<>
@ -134,8 +144,7 @@ const SingleSelector = defineComponent<SelectorProps>({
{/* Display value */}
{!combobox.value && item && !hasTextInput.value && (
<span class={`${prefixCls}-selection-item`} title={title.value}>
{/* <Fragment key={item.key || item.value}>{item.label}</Fragment> */}
{slotTitle?.(item.option?.data) || item.label}
<Fragment key={item.key || item.value}>{titleNode}</Fragment>
</span>
)}

View File

@ -1,4 +1,10 @@
import type { FlattenDataNode, Key, LegacyDataNode, RawValueType } from './interface';
import type {
FlattenDataNode,
InternalDataEntity,
Key,
LegacyDataNode,
RawValueType,
} from './interface';
import type { SkipType } from './hooks/useKeyValueMapping';
import type { ComputedRef, InjectionKey, PropType } from 'vue';
import { computed, defineComponent, inject, provide } from 'vue';
@ -31,7 +37,11 @@ interface ContextProps {
ignoreDisabledCheck?: boolean,
) => FlattenDataNode;
slots: Record<string, any>;
slots: {
title?: (data: InternalDataEntity) => any;
titleRender?: (data: InternalDataEntity) => any;
[key: string]: (d: any) => any | undefined;
};
}
const SelectContextKey: InjectionKey<ComputedRef<ContextProps>> = Symbol('SelectContextKey');

View File

@ -34,7 +34,7 @@ import classNames from '../_util/classNames';
export default defineComponent({
name: 'Tree',
inheritAttrs: false,
slots: ['checkable', 'title', 'icon'],
slots: ['checkable', 'title', 'icon', 'titleRender'],
props: initDefaultProps(treeProps(), {
prefixCls: 'vc-tree',
showLine: false,
@ -1023,8 +1023,6 @@ export default defineComponent({
loadData,
filterTreeNode,
titleRender: slots.title,
onNodeClick,
onNodeDoubleClick,
onNodeExpand,

View File

@ -362,7 +362,7 @@ export default defineComponent({
icon: treeIcon,
draggable,
loadData,
titleRender,
slots: contextSlots,
} = context.value;
const disabled = isDisabled.value;
const mergedDraggable = typeof draggable === 'function' ? draggable(data) : draggable;
@ -390,11 +390,12 @@ export default defineComponent({
let titleNode: any;
if (typeof title === 'function') {
titleNode = title(data);
} else if (titleRender) {
titleNode = titleRender(data);
} else if (contextSlots.titleRender) {
titleNode = contextSlots.titleRender(data);
} else {
titleNode = title === undefined ? defaultTitle : title;
titleNode = title;
}
titleNode = titleNode === undefined ? defaultTitle : titleNode;
const $title = <span class={`${prefixCls}-title`}>{titleNode}</span>;

View File

@ -64,7 +64,6 @@ export interface TreeContextProps {
loadData: (treeNode: EventDataNode) => Promise<void>;
filterTreeNode: (treeNode: EventDataNode) => boolean;
titleRender?: (node: DataNode) => VueNode;
onNodeClick: NodeMouseEventHandler;
onNodeDoubleClick: NodeMouseEventHandler;
@ -81,7 +80,11 @@ export interface TreeContextProps {
onNodeDragLeave: NodeDragEventHandler;
onNodeDragEnd: NodeDragEventHandler;
onNodeDrop: NodeDragEventHandler;
slots: Record<string, any>;
slots: {
title?: (data: DataNode) => any;
titleRender?: (data: DataNode) => any;
[key: string]: (d: any) => any | undefined;
};
}
const TreeContextKey: InjectionKey<ComputedRef<TreeContextProps>> = Symbol('TreeContextKey');

View File

@ -132,7 +132,7 @@ export const treeProps = () => ({
defaultSelectedKeys: { type: Array as PropType<Key[]> },
selectedKeys: { type: Array as PropType<Key[]> },
allowDrop: { type: Function as PropType<AllowDrop> },
// titleRender: { type: Function as PropType<(node: DataNode) => any> },
dropIndicatorRender: {
type: Function as PropType<
(props: {

View File

@ -7,7 +7,7 @@
placeholder="Please select"
tree-default-expand-all
>
<template #title1="{ key, value }">
<template #title="{ key, value }">
<span v-if="key === '0-0-1'" style="color: #08c">Child Node1 {{ value }}</span>
</template>
</a-tree-select>