Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions examples/cascader/cascader.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
:: BASE_DOC ::

## API

### Cascader Props

名称 | 类型 | 默认值 | 说明 | 必传
Expand All @@ -22,14 +21,15 @@ max | Number | 0 | 用于控制多选数量,值为 0 则不限制 | N
minCollapsedNum | Number | 0 | 最小折叠数量,用于多选情况下折叠选中项,超出该数值的选中项折叠。值为 0 则表示不折叠 | N
multiple | Boolean | false | 是否允许多选 | N
options | Array | [] | 可选项数据源。TS 类型:`Array<CascaderOption>` | N
placeholder | String | - | 占位符 | N
placeholder | String | undefined | 占位符 | N
popupProps | Object | - | 参考 popup 组件 API。TS 类型:`PopupProps`。[详细类型定义](https://github.com/Tencent/tdesign-vue/tree/develop/src/cascader/type.ts) | N
showAllLevels | Boolean | true | 输入框中是否显示选中值的完整路径 | N
showAllLevels | Boolean | true | 选中值使用完整路径,输入框在单选时也显示完整路径 | N
size | String | medium | 组件尺寸。可选项:large/medium/small。TS 类型:`SizeEnum`。[通用类型定义](https://github.com/Tencent/tdesign-vue/blob/develop/src/common.ts) | N
trigger | String | click | 展开下一层级的方式。可选项:click/hover | N
value | String / Number / Array | [] | 选中项的值。支持语法糖。TS 类型:`CascaderValue<CascaderOption>`。[通用类型定义](https://github.com/Tencent/tdesign-vue/blob/develop/src/common.ts)。[详细类型定义](https://github.com/Tencent/tdesign-vue/tree/develop/src/cascader/type.ts) | N
defaultValue | String / Number / Array | [] | 选中项的值。非受控属性。TS 类型:`CascaderValue<CascaderOption>`。[通用类型定义](https://github.com/Tencent/tdesign-vue/blob/develop/src/common.ts)。[详细类型定义](https://github.com/Tencent/tdesign-vue/tree/develop/src/cascader/type.ts) | N
valueMode | String | onlyLeaf | 选中值模式。all 表示父节点和子节点全部会出现在选中值里面;parentFirst 表示当子节点全部选中时,仅父节点在选中值里面;onlyLeaft 表示无论什么情况,选中值仅呈现叶子节点。可选项:onlyLeaf/parentFirst/all | N
valueType | String | single | 用于控制选中值的类型。single 表示输入输出值为 叶子结点值, full 表示输入输出值为全路径。可选项:single/full | N
onBlur | Function | | 当输入框失去焦点时触发。`(context: { value: CascaderValue<CascaderOption>; e: FocusEvent }) => {}` | N
onChange | Function | | 选中值发生变化时触发。TreeNodeModel 从树组件中导出。`context.node` 表示触发事件的节点,`context.source` 表示触发事件的来源。[详细类型定义](https://github.com/Tencent/tdesign-vue/tree/develop/src/cascader/type.ts)。`(value: CascaderValue<CascaderOption>, context: CascaderChangeContext<CascaderOption>) => {}` | N
onFocus | Function | | 获得焦点时触发。`(context: { value: CascaderValue<CascaderOption>; e: FocusEvent }) => {}` | N
Expand Down
66 changes: 66 additions & 0 deletions examples/cascader/demos/value-type.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
<template>
<div>
<t-cascader v-model="value" class="t-demo-cascader" :options="options" value-type="full" placeholder="请选择" />

<t-cascader
v-model="value2"
class="t-demo-cascader"
multiple
:options="options"
value-type="full"
placeholder="请选择"
/>
</div>
</template>
<script>
export default {
data() {
return {
options: [
{
label: '选项一',
value: '1',
children: [
{
label: '子选项一',
value: '1.1',
},
{
label: '子选项二',
value: '1.2',
},
{
label: '子选项三',
value: '1.3',
},
],
},
{
label: '选项二',
value: '2',
children: [
{
label: '子选项一',
value: '2.1',
},
{
label: '子选项二',
value: '2.2',
},
],
},
],
value: ['1', '1.1'],
value2: [
['1', '1.1'],
['1', '1.2'],
],
};
},
};
</script>
<style scoped>
.t-demo-cascader + .t-demo-cascader {
margin-top: 16px;
}
</style>
66 changes: 34 additions & 32 deletions src/cascader/cascader.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import { prefix } from '../config';
import TreeStore from '../_common/js/tree/tree-store';
import { emitEvent } from '../utils/event';
import { getPropsApiByEvent } from '../utils/helper';
import { getTreeValue } from './utils/helper';
import { getTreeValue, getValue } from './utils/helper';

// common logic
import { treeNodesEffect, treeStoreExpendEffect } from './utils/cascader';
Expand Down Expand Up @@ -105,13 +105,15 @@ export default Vue.extend({
showAllLevels = true,
minCollapsedNum = 0,
loading,
valueType = 'single',
} = this;

const {
visible, treeStore, treeNodes, filterActive, inputVal, inputWidth,
} = this;

return {
valueType,
loading,
size,
disabled,
Expand Down Expand Up @@ -140,8 +142,9 @@ export default Vue.extend({
// 处理外部传进来的value
value: {
handler(val) {
const { valueType, multiple } = this;
if (isEqual(val, this.scopeVal)) return;
this.scopeVal = val;
this.scopeVal = getValue(val, valueType, multiple);
this.updateExpend();
this.updatedTreeNodes();
},
Expand Down Expand Up @@ -169,15 +172,16 @@ export default Vue.extend({
const {
value,
multiple,
cascaderContext: { setValue },
cascaderContext: { setValue, showAllLevels },
valueType,
} = this;
if ((multiple && !Array.isArray(value)) || (!multiple && Array.isArray(value))) {
if ((multiple && !Array.isArray(value)) || (!multiple && Array.isArray(value) && !showAllLevels)) {
const val: CascaderValue = multiple ? [] : '';
setValue(val, 'invalid-value');
console.warn('TDesign Cascader Warn:', 'cascader props value invalid, v-model automatic calibration');
}
if (!isEmpty(value)) {
this.scopeVal = value;
this.scopeVal = getValue(value, valueType, multiple);
}

this.init();
Expand Down Expand Up @@ -259,34 +263,32 @@ export default Vue.extend({
});

return (
<div ref="cascader">
<Popup
ref="popup"
overlayClassName={`${name}__dropdown`}
placement="bottom-left"
visible={visible}
trigger={popupProps?.trigger || 'click'}
expandAnimation={true}
{...popupProps}
content={() => (
<panel
empty={empty}
trigger={trigger}
cascaderContext={cascaderContext}
scopedSlots={{ empty: $scopedSlots.empty }}
></panel>
)}
>
<InputContent
{...$attrs}
<Popup
class={`${name}__popup`}
overlayClassName={`${name}__dropdown`}
placement="bottom-left"
visible={visible}
trigger={popupProps?.trigger || 'click'}
expandAnimation={true}
{...popupProps}
content={() => (
<panel
empty={empty}
trigger={trigger}
cascaderContext={cascaderContext}
placeholder={placeholder}
listeners={listeners}
collapsedItems={collapsedItems}
scopedSlots={{ collapsedItems: $scopedSlots.collapsedItems }}
></InputContent>
</Popup>
</div>
scopedSlots={{ empty: $scopedSlots.empty }}
></panel>
)}
>
<InputContent
{...$attrs}
cascaderContext={cascaderContext}
placeholder={placeholder}
listeners={listeners}
collapsedItems={collapsedItems}
scopedSlots={{ collapsedItems: $scopedSlots.collapsedItems }}
></InputContent>
</Popup>
);
},
});
Loading