前言
我发现,很多select 选择器多选时,没有全选功能,就算有,它亦不能与模糊搜索共存!但需求又要求共存,真是两难全啊!
一、为 el-option 准备基础数据
src/assets/baseData.js
export const options = [
'黄金糕',
'双皮奶',
'蚵仔煎',
'龙须面',
'椰子鸡',
'周黑鸭'
]
二、为 el-option 渲染数据,同时塞一个“全部”
我记得请教导师时,他一如既往地选择了 table ,看来是对 table 情有独钟啊!但我好像不喜欢 table,唉......
App.vue
<template>
<div class="mySelect">
<el-select
v-model="value"
multiple
clearable
filterable
collapse-tags
style="margin-left: 20px;"
placeholder="请选择">
<el-option
v-for="item in options"
:key="item"
:label="item"
:value="item"
>
</el-option>
</el-select>
</div>
</template>
<script>
import { options } from '../src/assets/baseData'
export default {
data() {
return {
options: options,
value: []
};
},
mounted () {
// ◆既然没有全选,咱就给它头部塞一个
this.options.unshift('全部')
},
};
</script>
嘿嘿!全部出来啦!
三、实现全选影响小选、小选影响全选的效果
使用 watch 侦听 value 新旧值的变化,既而给 value 重新赋值
watch: {
value: {
handler(newVal,oldVal){
if(newVal.includes('全部') && !oldVal.includes('全部')){
// 1、如果新值包含 “全部”,旧值不含 “全部”
this.value = this.options
console.log(1);
}else if(!newVal.includes('全部') && oldVal.includes('全部')){
// 2、如果新值不包含 “全部”,旧值包含 “全部”,
this.value = []
console.log(2);
}else if(newVal.includes('全部') && oldVal.includes('全部') &&
newVal.length < oldVal.length){
// 4、如果新值包含 “全部”,旧值包含 “全部” ,但新值比旧值少
this.value.shift('全部')
console.log(3);
}else if(!newVal.includes('全部') && !oldVal.includes('全部') &&
newVal.length+1 == this.options.length){
// 5、如果新值不含 “全部”,旧值不含 “全部”,但新值长度+1 等于 options 的长度
this.value = this.options
console.log(4);
}
}
}
},
然而,这么做也留下了一个不尽如人意的地方,当你选择全部时,全部不应该展示,后面应当展示+5。额,我实在没有想到更好的办法了,暂且随它吧。
你不选全部的时候,还是正常的!
如果我们传给后台的值不能包含“全部”二字,你用 filter 把它筛选一下再传给后台就好了。
结语
当然,在实际开发中,很多公司内部组件的下拉框是有全选功能,没必要自己去写!比如我们公司就是,但尤为头疼的是,全选和模糊搜索又无法共存。我记得后来我们的解决方法是,全选就传个空数组给后台,也就是,当下拉框为必选值时,我不选,就会传空数组,此时后台返所有数据给我。