前言
小伙伴们,大家好,我最近一直在使用vben(Vben Admin)框架,虽然我感觉他封装的不错,但是使用过程中,还是会出现很多很难解决的bug,为了大家在以后的开发中,少走弯路,节省时间,所以我把一些难以解决和不易发现的bug给大家总结出来,大家一起进步。
今天主要讲讲ApiCascader(动态级联选择器)的问题。主要有几点:
参数
vben在很多的动态选择器中的参数使用的都是params作为参数来展示(ApiSelect, ApiTreeSelect),例如
举例一个form表单的动态获取
export const addFormSchema: FormSchema[] = [
{
field: 'receiveType',
label: '业务类型',
component: 'ApiSelect',
defaultValue: '1',
componentProps: {
placeholder: '请选择业务类型',
api: dictDetailListByCode,
labelField: 'value',
valueField: 'code',
showSearch: true,
params: { dictType: 'receive_type' },
},
required: true,
colProps: { span: 12 },
}
]
但是ApiCascader不一样,他是initFetchParams:写法为
export const searchMoreFormSchema: FormSchema[] = [
{
field: 'storageIds',
label: '仓库名称',
component: 'ApiCascader',
componentProps: {
placeholder: '请选择仓库名称',
api: storageTree,
labelField: 'storageName',
valueField: 'id',
initFetchParams: { serviceType: 5 },
},
}
]
无限下级
删除的load-data,要不然会出现无限级的loading请求,如图。
如果不删的话,就会出现如图无限循环
但是实际数据呢只有两层,很尴尬
箭头的清除
删除load-data之后是不会请求无限下级了,但是每一个上面都有箭头怎么办,很丑啊,而已如果只有两级,没有下级元素的话会造成误导的啊,是个bug,要解决。
那么我们如何取消这个箭头呢,主要是他的isLeaf属性来决定的。
interface Option {
value: string;
label: string;
loading?: boolean;
isLeaf?: boolean;
children?: Option[];
}
主要是generatorOptions这个递归函数的方法有问题,iisLeaf一直是false导致的。
改掉他,咱们自己根据children来做判断。
function generatorOptions(options: any[]): Option[] {
const { labelField, valueField, numberToString, childrenField, isLeaf } = props;
return options.reduce((prev, next: Recordable) => {
if (next) {
const value = next[valueField];
const children = Reflect.get(next, childrenField);
const item = {
...omit(next, [labelField, valueField]),
label: next[labelField],
value: numberToString ? `${value}` : value,
// isLeaf: isLeaf && typeof isLeaf === 'function' ? isLeaf(next) : false,
isLeaf: children && children.length ? false : true,
};
if (children) {
Reflect.set(item, childrenField, generatorOptions(children));
}
prev.push(item);
}
return prev;
}, [] as Option[]);
}
效果出来了哦耶
这个问题困扰了我两天时间,其实还有个思路是在数据初始化的时候,把isleaf这个字段就加进去,但是那样就要写函数,就复杂了,代码量直线上升,后端也不愿意增加字段,人家说有children判断去就行了。
回显
如果只赋值那么是显示不出来的,例如这样,那么这样是不行了
setFieldsValue({
storageIds: data.record.storageIds
});
export const addFormSchema: FormSchema[] = [
{
field: 'storageIds',
label: '仓库名称',
component: 'ApiCascader',
componentProps: ({ formModel }) => {
return {
placeholder: '请选择仓库名称',
api: storageTree,
labelField: 'storageName',
valueField: 'id',
initFetchParams: { serviceType: 1 },
};
},
required: true,
colProps: { span: 12 },
},
]
会选中 但是不会展示出来,需要增加回显的数据
setFieldsValue({
storageIds: data.record.storageIds,
storageNames: data.record.storageNames,
});
export const addFormSchema: FormSchema[] = [
{
field: 'storageIds',
label: '仓库名称',
component: 'ApiCascader',
componentProps: ({ formModel }) => {
return {
placeholder: '请选择仓库名称',
api: storageTree,
labelField: 'storageName',
valueField: 'id',
displayRenderArray: formModel.storageNames,
initFetchParams: { serviceType: 1 },
};
},
required: true,
colProps: { span: 12 },
},
{
field: 'storageNames',
label: '仓库名称',
component: 'ApiCascader',
colProps: { span: 12 },
show: false,
},
]
这样就可以了,他的bug确实有点多
以上就是Vben框架中的ApiCascader在项目中遇到的问题,希望对大家有所帮助.