cascader add size & disabled

pull/2559/head
baiyaaaaa 2017-01-22 01:19:46 +08:00
parent 1a16fbb735
commit fc4fd4cd61
6 changed files with 352 additions and 25 deletions

View File

@ -32,18 +32,57 @@
}], }],
}], }],
}], }],
optionsWithDisabled: [{
value: 'zhejiang',
label: 'Zhejiang',
disabled: true,
children: [{
value: 'hangzhou',
label: 'Hangzhou',
children: [{
value: 'xihu',
label: 'West Lake',
}],
}, {
value: 'ningbo',
label: 'NingBo',
children: [{
value: 'jiangbei',
label: 'Jiang Bei',
}],
}],
}, {
value: 'jiangsu',
label: 'Jiangsu',
children: [{
value: 'nanjing',
label: 'Nanjing',
children: [{
value: 'zhonghuamen',
label: 'Zhong Hua Men',
}],
}],
}],
selectedOptions: [], selectedOptions: [],
selectedOptions2: ['jiangsu', 'nanjing', 'zhonghuamen'], selectedOptions2: ['jiangsu', 'nanjing', 'zhonghuamen']
selectedOptions3: [],
selectedOptions4: [],
selectedOptions5: []
}; };
}, },
methods: { methods: {
handleChange(value) {
console.log(value);
}
} }
}; };
</script> </script>
<style>
.demo-cascader {
.el-cascader {
width: 222px;
}
}
</style>
## 级联选择 ## 级联选择
需要从一组相关联的数据集合进行选择,例如省市区,公司层级,事物分类等。 需要从一组相关联的数据集合进行选择,例如省市区,公司层级,事物分类等。
@ -55,55 +94,329 @@
:::demo :::demo
```html ```html
<el-cascader <el-cascader
placeholder="请选择"
:options="options" :options="options"
v-model="selectedOptions" v-model="selectedOptions"
@change="handleChange"
></el-cascader> ></el-cascader>
<script>
module.exports = {
data() {
return {
options: [{
value: 'zhejiang',
label: 'Zhejiang',
children: [{
value: 'hangzhou',
label: 'Hangzhou',
children: [{
value: 'xihu',
label: 'West Lake',
}],
}, {
value: 'ningbo',
label: 'NingBo',
children: [{
value: 'jiangbei',
label: 'Jiang Bei',
}],
}],
}, {
value: 'jiangsu',
label: 'Jiangsu',
children: [{
value: 'nanjing',
label: 'Nanjing',
children: [{
value: 'zhonghuamen',
label: 'Zhong Hua Men',
}],
}],
}],
selectedOptions: []
};
},
methods: {
handleChange(value) {
console.log(value);
}
}
};
</script>
```
:::
### 禁用值
:::demo
```html
<el-cascader
placeholder="请选择"
:options="optionsWithDisabled"
></el-cascader>
<script>
module.exports = {
data() {
return {
optionsWithDisabled: [{
value: 'zhejiang',
label: 'Zhejiang',
disabled: true,
children: [{
value: 'hangzhou',
label: 'Hangzhou',
children: [{
value: 'xihu',
label: 'West Lake',
}],
}, {
value: 'ningbo',
label: 'NingBo',
children: [{
value: 'jiangbei',
label: 'Jiang Bei',
}],
}],
}, {
value: 'jiangsu',
label: 'Jiangsu',
children: [{
value: 'nanjing',
label: 'Nanjing',
children: [{
value: 'zhonghuamen',
label: 'Zhong Hua Men',
}],
}],
}]
};
}
};
</script>
``` ```
::: :::
### 默认值 ### 默认值
:::demo :::demo 默认值通过数组的方式指定。
```html ```html
<el-cascader <el-cascader
placeholder="请选择"
:options="options" :options="options"
v-model="selectedOptions2" v-model="selectedOptions2"
></el-cascader> ></el-cascader>
<script>
module.exports = {
data() {
return {
options: [{
value: 'zhejiang',
label: 'Zhejiang',
children: [{
value: 'hangzhou',
label: 'Hangzhou',
children: [{
value: 'xihu',
label: 'West Lake',
}],
}, {
value: 'ningbo',
label: 'NingBo',
children: [{
value: 'jiangbei',
label: 'Jiang Bei',
}],
}],
}, {
value: 'jiangsu',
label: 'Jiangsu',
children: [{
value: 'nanjing',
label: 'Nanjing',
children: [{
value: 'zhonghuamen',
label: 'Zhong Hua Men',
}],
}],
}],
selectedOptions2: ['jiangsu', 'nanjing', 'zhonghuamen']
};
}
};
</script>
``` ```
::: :::
### 移入展开 ### 移入展开
在鼠标移入时就展开下级菜单,完成选择仍需要进行点击。
:::demo :::demo
```html ```html
<el-cascader <el-cascader
placeholder="请选择"
:options="options" :options="options"
v-model="selectedOptions3"
expand-trigger="hover" expand-trigger="hover"
></el-cascader> ></el-cascader>
<script>
module.exports = {
data() {
return {
options: [{
value: 'zhejiang',
label: 'Zhejiang',
children: [{
value: 'hangzhou',
label: 'Hangzhou',
children: [{
value: 'xihu',
label: 'West Lake',
}],
}, {
value: 'ningbo',
label: 'NingBo',
children: [{
value: 'jiangbei',
label: 'Jiang Bei',
}],
}],
}, {
value: 'jiangsu',
label: 'Jiangsu',
children: [{
value: 'nanjing',
label: 'Nanjing',
children: [{
value: 'zhonghuamen',
label: 'Zhong Hua Men',
}],
}],
}]
};
}
};
</script>
``` ```
::: :::
### 选择即改变 ### 选择即改变
该模式下允许只选中父级选项。
:::demo :::demo
```html ```html
<el-cascader <el-cascader
placeholder="请选择"
:options="options" :options="options"
v-model="selectedOptions4"
change-on-select change-on-select
></el-cascader> ></el-cascader>
<script>
module.exports = {
data() {
return {
options: [{
value: 'zhejiang',
label: 'Zhejiang',
children: [{
value: 'hangzhou',
label: 'Hangzhou',
children: [{
value: 'xihu',
label: 'West Lake',
}],
}, {
value: 'ningbo',
label: 'NingBo',
children: [{
value: 'jiangbei',
label: 'Jiang Bei',
}],
}],
}, {
value: 'jiangsu',
label: 'Jiangsu',
children: [{
value: 'nanjing',
label: 'Nanjing',
children: [{
value: 'zhonghuamen',
label: 'Zhong Hua Men',
}],
}],
}]
};
}
};
</script>
``` ```
::: :::
### 可搜索 ### 可搜索
可以直接搜索选项并选择。
:::demo :::demo
```html ```html
<el-cascader <el-cascader
placeholder="请选择"
:options="options" :options="options"
v-model="selectedOptions5"
show-search show-search
></el-cascader> ></el-cascader>
<script>
module.exports = {
data() {
return {
options: [{
value: 'zhejiang',
label: 'Zhejiang',
children: [{
value: 'hangzhou',
label: 'Hangzhou',
children: [{
value: 'xihu',
label: 'West Lake',
}],
}, {
value: 'ningbo',
label: 'NingBo',
children: [{
value: 'jiangbei',
label: 'Jiang Bei',
}],
}],
}, {
value: 'jiangsu',
label: 'Jiangsu',
children: [{
value: 'nanjing',
label: 'Nanjing',
children: [{
value: 'zhonghuamen',
label: 'Zhong Hua Men',
}],
}],
}]
};
}
};
</script>
``` ```
::: :::
### Attributes
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|---------- |-------- |---------- |------------- |-------- |
| options | 可选项数据源 | array | — | — |
| value | 指定选中项 | array | — | — |
| popup-class | 自定义浮层类名 | string | — | — |
| placeholder | 输入框占位文本 | string | — | — |
| disabled | 是否禁用 | boolean | — | false |
| allowClear | 是否支持清除 | boolean | — | false |
| expand-trigger | 次级菜单的展开方式 | string | click / hover | 'click' |
| showSearch | 是否支持搜索选项 | boolean | — | — |
| size | 尺寸 | string | large / small / mini | — |
### Events
| 事件名称 | 说明 | 回调参数 |
|---------- |-------- |---------- |
| change | 当绑定值变化时触发的事件 | 当前值 |

View File

@ -215,7 +215,7 @@
value: '选项5', value: '选项5',
label: '北京烤鸭' label: '北京烤鸭'
}], }],
value2: '' value2: '选项2'
} }
} }
} }

View File

@ -12,9 +12,11 @@
> >
<el-input <el-input
:readonly="!showSearch" :readonly="!showSearch"
:placeholder="placeholder" :placeholder="displayValue ? undefined : placeholder"
v-model="inputValue" v-model="inputValue"
@change="handleInputChange" @change="handleInputChange"
:validate-event="false"
:size="size"
> >
<template slot="icon"> <template slot="icon">
<i <i
@ -41,6 +43,7 @@ import ElCascaderMenu from './menu';
import ElInput from 'element-ui/packages/input'; import ElInput from 'element-ui/packages/input';
import Popper from 'element-ui/src/utils/vue-popper'; import Popper from 'element-ui/src/utils/vue-popper';
import Clickoutside from 'element-ui/src/utils/clickoutside'; import Clickoutside from 'element-ui/src/utils/clickoutside';
import emitter from 'element-ui/src/mixins/emitter';
const popperMixin = { const popperMixin = {
props: { props: {
@ -63,7 +66,7 @@ export default {
directives: { Clickoutside }, directives: { Clickoutside },
mixins: [popperMixin], mixins: [popperMixin, emitter],
components: { components: {
ElInput ElInput
@ -92,7 +95,8 @@ export default {
type: String, type: String,
default: 'click' default: 'click'
}, },
showSearch: Boolean showSearch: Boolean,
size: String
}, },
data() { data() {
@ -115,6 +119,7 @@ export default {
}, },
currentValue(value) { currentValue(value) {
this.displayValue = value.join('/'); this.displayValue = value.join('/');
this.dispatch('ElFormItem', 'el.form.change', [value]);
} }
}, },
@ -125,12 +130,13 @@ export default {
this.menu.options = this.options; this.menu.options = this.options;
this.menu.expandTrigger = this.expandTrigger; this.menu.expandTrigger = this.expandTrigger;
this.menu.changeOnSelect = this.changeOnSelect; this.menu.changeOnSelect = this.changeOnSelect;
this.menu.popperClass = this.popperClass;
this.popperElm = this.menu.$el; this.popperElm = this.menu.$el;
} }
this.menu.value = this.currentValue.slice(0); this.menu.value = this.currentValue.slice(0);
this.menu.visible = true; this.menu.visible = true;
this.menu.$on('change', this.handlePick); this.menu.$on('pick', this.handlePick);
this.updatePopper(); this.updatePopper();
}, },
hideMenu() { hideMenu() {
@ -140,6 +146,7 @@ export default {
handlePick(value, close = true) { handlePick(value, close = true) {
this.currentValue = value; this.currentValue = value;
this.$emit('input', value); this.$emit('input', value);
this.$emit('change', value);
if (close) { if (close) {
this.menuVisible = false; this.menuVisible = false;
} }
@ -165,7 +172,7 @@ export default {
}; };
}); });
} else { } else {
return [{ label: 'notFoundContent', value: 'ANT_CASCADER_NOT_FOUND', disabled: true }]; return [{ label: 'not found content', value: '', disabled: true }];
} }
}, },
renderRenderFilteredOption(inputValue, optionsStack) { renderRenderFilteredOption(inputValue, optionsStack) {

View File

@ -9,7 +9,8 @@
activeValue: [], activeValue: [],
value: [], value: [],
expandTrigger: 'click', expandTrigger: 'click',
changeOnSelect: false changeOnSelect: false,
popperClass: ''
}; };
}, },
@ -66,7 +67,7 @@
} }
if (this.changeOnSelect) { if (this.changeOnSelect) {
this.$emit('change', this.activeValue, closeMenu); this.$emit('pick', this.activeValue, closeMenu);
} }
}, },
expandItem(item, menuIndex) { expandItem(item, menuIndex) {
@ -81,7 +82,7 @@
this.selectItem(item, menuIndex); this.selectItem(item, menuIndex);
if (!item.children && !this.changeOnSelect) { if (!item.children && !this.changeOnSelect) {
this.$emit('change', this.activeValue); this.$emit('pick', this.activeValue);
} }
} }
}, },
@ -91,7 +92,8 @@
activeValue, activeValue,
activeOptions, activeOptions,
visible, visible,
expandTrigger expandTrigger,
popperClass
} = this; } = this;
const menus = this._l(activeOptions, (menu, index) => { const menus = this._l(activeOptions, (menu, index) => {
@ -100,10 +102,12 @@
on: {} on: {}
}; };
if (expandTrigger === 'click' || !item.children) { if (!item.disabled) {
events.on['click'] = () => { this.handleItemClick(item, index); }; if (expandTrigger === 'click' || !item.children) {
} else { events.on['click'] = () => { this.handleItemClick(item, index); };
events.on['mouseenter'] = () => { this.expandItem(item, index); }; } else {
events.on['mouseenter'] = () => { this.expandItem(item, index); };
}
} }
return ( return (
@ -111,7 +115,8 @@
class={{ class={{
'el-cascader-menu__item': true, 'el-cascader-menu__item': true,
'el-cascader-menu__item--extensible': item.children, 'el-cascader-menu__item--extensible': item.children,
'is-active': item.value === activeValue[index] 'is-active': item.value === activeValue[index],
'is-disabled': item.disabled
}} }}
{...events} {...events}
> >
@ -123,7 +128,7 @@
}); });
return ( return (
<transition name="el-zoom-in-top"> <transition name="el-zoom-in-top">
<div class="el-cascader-menus" v-show={visible}> <div class={['el-cascader-menus', popperClass]} v-show={visible}>
{menus} {menus}
</div> </div>
</transition> </transition>

View File

@ -106,6 +106,7 @@
@when disabled { @when disabled {
color: var(--select-option-disabled-color); color: var(--select-option-disabled-color);
background-color: var(--select-option-disabled-background);
cursor: not-allowed; cursor: not-allowed;
&:hover { &:hover {

View File

@ -161,6 +161,7 @@
--select-option-color: var(--link-color); --select-option-color: var(--link-color);
--select-option-disabled-color: var(--color-extra-light-silver); --select-option-disabled-color: var(--color-extra-light-silver);
--select-option-disabled-background: var(--color-white);
--select-option-height: 36px; --select-option-height: 36px;
--select-option-hover-background: var(--color-light-gray); --select-option-hover-background: var(--color-light-gray);
--select-option-selected: var(--color-primary); --select-option-selected: var(--color-primary);