Merge pull request '⚔ refactor(pulldownSelecter): 优化并修复部分一直bug' (#406) from jasondom/Admin.NET.Pro:v2-1 into v2

Reviewed-on: https://code.adminnet.top/Admin.NET/Admin.NET.Pro/pulls/406
This commit is contained in:
zuohuaijun 2025-08-18 19:25:48 +08:00
commit 405b019969

View File

@ -91,7 +91,7 @@ const props = defineProps({
*/
labelFormat: {
type: Function,
default: (item: any) => {},
default: (item: any) => undefined,
},
/**
* 默认查询条件值绑定的属性名
@ -231,7 +231,7 @@ const resetQuery = () => {
};
//
const remoteMethod = debounce((query) => {
const remoteMethod = debounce((query: any) => {
if (query) {
state.loading = true;
if (typeof query === 'string') {
@ -258,37 +258,42 @@ const handleQuery = () => {
//
const handleChange = (row: any) => {
state.tableQuery = Object.assign(state.tableQuery, props.queryParams);
state.defaultOptions = props.defaultOptions ?? [];
state.defaultOptions.push(row);
//
if (props.multiple && !state.selectedValues) state.selectedValues = [];
// ,
if (typeof row[props.valueProp] === 'string') row[props.valueProp] = row[props.valueProp]?.trim();
setDefaultOptions([row]);
//
state.selectedValues = props.multiple ? Array.from(new Set([...state.selectedValues, row[props.valueProp]])) : row[props.valueProp];
emit('update:modelValue', state.selectedValues);
emit('change', state.selectedValues, row);
//
if (!props.multiple || state.selectedValues) selectRef.value?.blur();
tableRef.value?.setCurrentRow(row);
emit('update:modelValue', state.selectedValues);
emit('change', state.selectedValues, row);
};
watch(
() => props.modelValue,
(val: any) => {
state.selectedValues = val;
},
{ immediate: true }
);
//
const selectVisibleChange = (visible: boolean) => {
if (visible) {
state.tableQuery[props.keywordProp] = undefined;
handleQuery();
}
};
watch(
() => props.defaultOptions,
(val: any) => {
state.defaultOptions = val;
},
{ immediate: true }
);
//
//
const setDefaultOptions = (options: any[]) => {
state.defaultOptions = options;
const list = [] as any[];
for(const item of [...options ?? [], ...state.defaultOptions]) {
const value = item?.[props.valueProp];
const label = props.labelFormat?.(item) || item?.[props.labelProp];
if (value && label) list.push({ [props.valueProp]: value, [props.labelProp]: label })
}
state.defaultOptions = Array.from(new Set(list));
};
//
@ -314,6 +319,9 @@ const setValue = (option: any | any[], row: any) => {
emit('change', state.selectedValues, row);
};
watch(() => props.modelValue, (val: any) => state.selectedValues = val, { immediate: true });
watch(() => props.defaultOptions, (val: any) => setDefaultOptions(val), { immediate: true });
defineExpose({
setValue,
handleQuery,
@ -324,32 +332,26 @@ defineExpose({
<template>
<el-select
v-model="state.selectedValues"
:clearable="clearable"
:multiple="multiple"
:disabled="disabled"
:placeholder="placeholder"
:allow-create="allowCreate"
:remote-method="remoteMethod"
:default-first-option="allowCreate"
@visible-change="(val: boolean) => (val ? handleQuery() : null)"
popper-class="popper-class"
ref="selectRef"
remote-show-suffix
filterable
remote
v-model="state.selectedValues"
:clearable="clearable"
:multiple="multiple"
:disabled="disabled"
:placeholder="placeholder"
:allow-create="allowCreate"
:remote-method="remoteMethod"
:default-first-option="allowCreate"
@visible-change="selectVisibleChange"
popper-class="popper-class"
ref="selectRef"
remote-show-suffix
filterable
remote
>
<!-- 隐藏的选项用于占位 -->
<el-option style="width: 0; height: 0" />
<!-- 默认选项用于回显数据 -->
<el-option
v-for="item in (state.defaultOptions ?? []).filter((e) => !state.tableData?.items?.find((e2) => e2[valueProp] === e[valueProp]))"
:key="item[valueProp]"
:label="labelFormat(item) || item[labelProp]"
:value="item[valueProp]"
style="width: 0; height: 0"
/>
<el-option v-for="item in state.defaultOptions ?? []" :key="item[valueProp]" :label="labelFormat(item) || item[labelProp]" :value="item[valueProp]" style="width: 0; height: 0" />
<!-- 下拉框内容区域 -->
<div class="w100" v-loading="state.loading">
@ -367,12 +369,12 @@ defineExpose({
<!-- 数据表格 -->
<el-table
ref="tableRef"
@row-click="handleChange"
:data="state.tableData?.items ?? []"
:height="`calc(${dropdownHeight} - 175px${$slots.queryForm ? ' - 35px' : ''})`"
:style="{ width: dropdownWidth }"
highlight-current-row
ref="tableRef"
@row-click="handleChange"
:data="state.tableData?.items ?? []"
:height="`calc(${dropdownHeight} - 175px${$slots.queryForm ? ' - 35px' : ''}${state.tableQuery[keywordProp] && allowCreate ? ' - 35px' : ''})`"
:style="{ width: dropdownWidth }"
highlight-current-row
>
<template #empty><el-empty :image-size="25" /></template>
<slot name="columns"></slot>
@ -380,17 +382,17 @@ defineExpose({
<!-- 分页组件 -->
<el-pagination
v-if="props.pagination"
:disabled="state.loading"
:currentPage="state.tableQuery.page"
:page-size="state.tableQuery.pageSize"
:total="state.tableData.total"
:pager-count="4"
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
layout="prev, pager, next"
size="small"
background
v-if="props.pagination"
:disabled="state.loading"
:currentPage="state.tableQuery.page"
:page-size="state.tableQuery.pageSize"
:total="state.tableData.total"
:pager-count="4"
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
layout="prev, pager, next"
size="small"
background
/>
</div>
</el-select>
@ -407,4 +409,4 @@ defineExpose({
.popper-class {
min-width: 400px !important;
}
</style>
</style>