feat: tree-select add tag-render
parent
646fad2eda
commit
d46762c1d6
|
@ -27,9 +27,9 @@ Multiple and checkable.
|
|||
/>
|
||||
</template>
|
||||
<script lang="ts">
|
||||
import { TreeSelect } from 'ant-design-vue';
|
||||
import type { TreeSelectProps } from 'ant-design-vue';
|
||||
import { defineComponent, ref, watch } from 'vue';
|
||||
import { TreeSelect } from 'ant-design-vue';
|
||||
const SHOW_PARENT = TreeSelect.SHOW_PARENT;
|
||||
|
||||
const treeData: TreeSelectProps['treeData'] = [
|
||||
|
|
|
@ -0,0 +1,93 @@
|
|||
<docs>
|
||||
---
|
||||
order: 24
|
||||
title:
|
||||
zh-CN: 自定义选择标签
|
||||
en-US: Custom Tag Render
|
||||
---
|
||||
|
||||
## zh-CN
|
||||
|
||||
允许自定义选择标签的样式。仅支持多选模式,单选可直接使用 `title` 插槽
|
||||
|
||||
## en-US
|
||||
|
||||
Allows for custom rendering of tags.
|
||||
|
||||
</docs>
|
||||
|
||||
<template>
|
||||
<a-tree-select
|
||||
v-model:value="value"
|
||||
show-search
|
||||
style="width: 100%"
|
||||
:dropdown-style="{ maxHeight: '400px', overflow: 'auto' }"
|
||||
placeholder="Please select"
|
||||
allow-clear
|
||||
multiple
|
||||
:show-checked-strategy="SHOW_ALL"
|
||||
tree-default-expand-all
|
||||
:tree-data="treeData"
|
||||
>
|
||||
<template #tagRender="{ label, closable, onClose, option }">
|
||||
<a-tag :closable="closable" :color="option.color" style="margin-right: 3px" @close="onClose">
|
||||
{{ label }}
|
||||
</a-tag>
|
||||
</template>
|
||||
<template #title="{ value: val, title }">
|
||||
<b v-if="val === 'parent 1-1'" style="color: #08c">{{ val }}</b>
|
||||
<template v-else>{{ title }}</template>
|
||||
</template>
|
||||
</a-tree-select>
|
||||
</template>
|
||||
<script lang="ts">
|
||||
import type { TreeSelectProps } from 'ant-design-vue';
|
||||
import { defineComponent, ref, watch } from 'vue';
|
||||
import { TreeSelect } from 'ant-design-vue';
|
||||
const SHOW_ALL = TreeSelect.SHOW_ALL;
|
||||
export default defineComponent({
|
||||
setup() {
|
||||
const value = ref<string[]>(['parent 1', 'parent 1-0', 'leaf1']);
|
||||
const treeData = ref<TreeSelectProps['treeData']>([
|
||||
{
|
||||
title: 'parent 1',
|
||||
value: 'parent 1',
|
||||
color: 'pink',
|
||||
children: [
|
||||
{
|
||||
title: 'parent 1-0',
|
||||
value: 'parent 1-0',
|
||||
color: 'orange',
|
||||
children: [
|
||||
{
|
||||
title: 'my leaf',
|
||||
value: 'leaf1',
|
||||
color: 'green',
|
||||
},
|
||||
{
|
||||
title: 'your leaf',
|
||||
value: 'leaf2',
|
||||
color: 'cyan',
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: 'parent 1-1',
|
||||
value: 'parent 1-1',
|
||||
color: 'blue',
|
||||
},
|
||||
],
|
||||
},
|
||||
]);
|
||||
watch(value, () => {
|
||||
console.log('select', value.value);
|
||||
});
|
||||
|
||||
return {
|
||||
value,
|
||||
treeData,
|
||||
SHOW_ALL,
|
||||
};
|
||||
},
|
||||
});
|
||||
</script>
|
|
@ -7,6 +7,9 @@
|
|||
<suffix />
|
||||
<async />
|
||||
<Highlight />
|
||||
<treeLineVue />
|
||||
<virtualScrollVue />
|
||||
<customTagRenderVue />
|
||||
</demo-sort>
|
||||
</template>
|
||||
<script lang="ts">
|
||||
|
@ -17,6 +20,9 @@ import Checkable from './checkable.vue';
|
|||
import Suffix from './suffix.vue';
|
||||
import Async from './async.vue';
|
||||
import Highlight from './highlight.vue';
|
||||
import treeLineVue from './tree-line.vue';
|
||||
import virtualScrollVue from './virtual-scroll.vue';
|
||||
import customTagRenderVue from './custom-tag-render.vue';
|
||||
import CN from '../index.zh-CN.md';
|
||||
import US from '../index.en-US.md';
|
||||
import { defineComponent } from 'vue';
|
||||
|
@ -32,6 +38,9 @@ export default defineComponent({
|
|||
Suffix,
|
||||
Async,
|
||||
Highlight,
|
||||
treeLineVue,
|
||||
virtualScrollVue,
|
||||
customTagRenderVue,
|
||||
},
|
||||
setup() {
|
||||
return {};
|
||||
|
|
|
@ -17,6 +17,7 @@ Use `treeLine` to show the line style.
|
|||
</docs>
|
||||
|
||||
<template>
|
||||
<a-space direction="vertical">
|
||||
<a-switch
|
||||
v-model:checked="treeLine"
|
||||
checked-children="treeLine"
|
||||
|
@ -40,6 +41,7 @@ Use `treeLine` to show the line style.
|
|||
<template v-else>{{ title }}</template>
|
||||
</template>
|
||||
</a-tree-select>
|
||||
</a-space>
|
||||
</template>
|
||||
<script lang="ts">
|
||||
import type { TreeSelectProps } from 'ant-design-vue';
|
|
@ -1,74 +0,0 @@
|
|||
<docs>
|
||||
---
|
||||
order: 2
|
||||
title:
|
||||
zh-CN: 从数据直接生成
|
||||
en-US: Generate form tree data
|
||||
---
|
||||
|
||||
## zh-CN
|
||||
|
||||
使用 `treeData` 把 JSON 数据直接生成树结构。
|
||||
|
||||
## en-US
|
||||
|
||||
The tree structure can be populated using `treeData` property. This is a quick and easy way to provide the tree content.
|
||||
|
||||
</docs>
|
||||
<template>
|
||||
<a-tree-select
|
||||
v-model:value="value"
|
||||
style="width: 100%"
|
||||
:dropdown-style="{ maxHeight: '400px', overflow: 'auto' }"
|
||||
:tree-data="treeData"
|
||||
placeholder="Please select"
|
||||
tree-default-expand-all
|
||||
>
|
||||
<template #title="{ key, value: val, title }">
|
||||
<span v-if="key === '0-0-1'" style="color: #08c">Child Node1 {{ val }}</span>
|
||||
<template v-else>{{ title }}</template>
|
||||
</template>
|
||||
</a-tree-select>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import type { TreeSelectProps } from 'ant-design-vue';
|
||||
import { defineComponent, ref, watch } from 'vue';
|
||||
|
||||
const treeData: TreeSelectProps['treeData'] = [
|
||||
{
|
||||
title: 'Node1',
|
||||
value: '0-0',
|
||||
key: '0-0',
|
||||
children: [
|
||||
{
|
||||
value: '0-0-1',
|
||||
key: '0-0-1',
|
||||
},
|
||||
{
|
||||
title: 'Child Node2',
|
||||
value: '0-0-2',
|
||||
key: '0-0-2',
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: 'Node2',
|
||||
value: '0-1',
|
||||
key: '0-1',
|
||||
},
|
||||
];
|
||||
export default defineComponent({
|
||||
setup() {
|
||||
const value = ref<string>();
|
||||
|
||||
watch(value, () => {
|
||||
console.log(value.value);
|
||||
});
|
||||
return {
|
||||
value,
|
||||
treeData,
|
||||
};
|
||||
},
|
||||
});
|
||||
</script>
|
|
@ -0,0 +1,73 @@
|
|||
<docs>
|
||||
---
|
||||
order: 9
|
||||
title:
|
||||
zh-CN: 虚拟滚动
|
||||
en-US: Virtual scroll
|
||||
---
|
||||
|
||||
## zh-CN
|
||||
|
||||
使用 `height` 属性则切换为虚拟滚动。
|
||||
|
||||
## en-US
|
||||
|
||||
Use virtual list through `height` prop.
|
||||
|
||||
</docs>
|
||||
<template>
|
||||
<a-tree-select
|
||||
v-model:value="checkedKeys"
|
||||
style="width: 100%"
|
||||
tree-checkable
|
||||
tree-default-expand-all
|
||||
:show-checked-strategy="SHOW_PARENT"
|
||||
:height="233"
|
||||
:tree-data="treeData"
|
||||
:max-tag-count="10"
|
||||
>
|
||||
<template #title="{ title, value }">
|
||||
<span v-if="value === '0-0-1-0'" style="color: #1890ff">{{ title }}</span>
|
||||
<template v-else>{{ title }}</template>
|
||||
</template>
|
||||
</a-tree-select>
|
||||
</template>
|
||||
<script lang="ts">
|
||||
import type { TreeSelectProps } from 'ant-design-vue';
|
||||
import { TreeSelect } from 'ant-design-vue';
|
||||
import { defineComponent, ref, watch } from 'vue';
|
||||
const SHOW_PARENT = TreeSelect.SHOW_PARENT;
|
||||
|
||||
function dig(path = '0', level = 3) {
|
||||
const list: TreeSelectProps['treeData'] = [];
|
||||
for (let i = 0; i < 10; i += 1) {
|
||||
const value = `${path}-${i}`;
|
||||
const treeNode: TreeSelectProps['treeData'][number] = {
|
||||
title: value,
|
||||
value,
|
||||
};
|
||||
|
||||
if (level > 0) {
|
||||
treeNode.children = dig(value, level - 1);
|
||||
}
|
||||
|
||||
list.push(treeNode);
|
||||
}
|
||||
return list;
|
||||
}
|
||||
|
||||
export default defineComponent({
|
||||
setup() {
|
||||
const checkedKeys = ref<string[]>(['0-0-0', '0-0-1']);
|
||||
watch(checkedKeys, () => {
|
||||
console.log('checkedKeys', checkedKeys);
|
||||
});
|
||||
|
||||
return {
|
||||
treeData: dig(),
|
||||
checkedKeys,
|
||||
SHOW_PARENT,
|
||||
};
|
||||
},
|
||||
});
|
||||
</script>
|
|
@ -10,6 +10,7 @@ import type { VueNode } from '../../_util/type';
|
|||
import Overflow from '../../vc-overflow';
|
||||
import type { DisplayValueType, RenderNode, CustomTagProps, RawValueType } from '../BaseSelect';
|
||||
import type { BaseOptionType } from '../Select';
|
||||
import useInjectLegacySelectContext from '../../vc-tree-select/LegacyContext';
|
||||
|
||||
type SelectorProps = InnerSelectorProps & {
|
||||
// Icon
|
||||
|
@ -79,7 +80,7 @@ const SelectSelector = defineComponent<SelectorProps>({
|
|||
const measureRef = ref();
|
||||
const inputWidth = ref(0);
|
||||
const focused = ref(false);
|
||||
|
||||
const legacyTreeSelectContext = useInjectLegacySelectContext();
|
||||
const selectionPrefixCls = computed(() => `${props.prefixCls}-selection`);
|
||||
|
||||
// ===================== Search ======================
|
||||
|
@ -147,15 +148,20 @@ const SelectSelector = defineComponent<SelectorProps>({
|
|||
onPreventMouseDown(e);
|
||||
props.onToggleOpen(!open);
|
||||
};
|
||||
let originData = option;
|
||||
// For TreeSelect
|
||||
if (legacyTreeSelectContext.keyEntities) {
|
||||
originData = legacyTreeSelectContext.keyEntities[value]?.node || {};
|
||||
}
|
||||
return (
|
||||
<span onMousedown={onMouseDown}>
|
||||
<span key={value} onMousedown={onMouseDown}>
|
||||
{props.tagRender({
|
||||
label: content,
|
||||
value,
|
||||
disabled: itemDisabled,
|
||||
closable,
|
||||
onClose,
|
||||
option,
|
||||
option: originData,
|
||||
})}
|
||||
</span>
|
||||
);
|
||||
|
|
|
@ -109,6 +109,7 @@ const SingleSelector = defineComponent<SelectorProps>({
|
|||
let titleNode = null;
|
||||
// custom tree-select title by slot
|
||||
|
||||
// For TreeSelect
|
||||
if (item && legacyTreeSelectContext.customSlots) {
|
||||
const key = item.key ?? item.value;
|
||||
const originData = legacyTreeSelectContext.keyEntities[key]?.node || {};
|
||||
|
|
|
@ -727,6 +727,7 @@ export default defineComponent({
|
|||
OptionList={OptionList}
|
||||
emptyOptions={!mergedTreeData.value.length}
|
||||
onDropdownVisibleChange={onInternalDropdownVisibleChange}
|
||||
tagRender={props.tagRender || slots.tagRender}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue