2025-05-20 16:34:38 +08:00
|
|
|
<template>
|
|
|
|
|
<div class="custom-select2">
|
2025-10-30 18:16:57 +08:00
|
|
|
<Select2 v-model="currentValue" :options="processedOptions" :settings="select2Settings"
|
|
|
|
|
@update:modelValue="handleChange" :disabled="isDisabled" />
|
2025-05-20 16:34:38 +08:00
|
|
|
</div>
|
|
|
|
|
</template>
|
|
|
|
|
|
|
|
|
|
<script setup>
|
|
|
|
|
//import { ref, computed, watch, defineProps, defineEmits } from 'vue';
|
|
|
|
|
import Select2 from 'vue3-select2-component';
|
|
|
|
|
import 'select2/dist/css/select2.min.css';
|
2025-10-30 18:16:57 +08:00
|
|
|
import { processOptions } from '@/utils/pinyin.js'; // 引入拼音处理工具
|
2025-05-20 16:34:38 +08:00
|
|
|
|
|
|
|
|
// 定义组件props
|
|
|
|
|
const props = defineProps({
|
|
|
|
|
options: {
|
|
|
|
|
type: Array,
|
|
|
|
|
default: () => []
|
|
|
|
|
},
|
|
|
|
|
value: {
|
|
|
|
|
type: [String, Number, Object],
|
|
|
|
|
default: null
|
|
|
|
|
},
|
|
|
|
|
placeholder: {
|
|
|
|
|
type: String,
|
|
|
|
|
default: '请选择'
|
|
|
|
|
},
|
|
|
|
|
disabled: {
|
|
|
|
|
type: Boolean,
|
|
|
|
|
default: false
|
|
|
|
|
},
|
|
|
|
|
width: {
|
|
|
|
|
type: String,
|
|
|
|
|
default: '200px'
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// 定义组件emits
|
|
|
|
|
const emits = defineEmits(['update:modelValue', 'change']);
|
|
|
|
|
|
|
|
|
|
// 处理选项数据
|
|
|
|
|
const processedOptions = computed(() => {
|
|
|
|
|
return processOptions(props.options);
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// 当前值
|
|
|
|
|
const currentValue = ref(props.value);
|
|
|
|
|
|
|
|
|
|
// Select2设置
|
|
|
|
|
const select2Settings = computed(() => ({
|
|
|
|
|
placeholder: props.placeholder,
|
|
|
|
|
allowClear: true,
|
|
|
|
|
width: props.width,
|
|
|
|
|
dropdownAutoWidth: false,
|
|
|
|
|
|
|
|
|
|
// 自定义搜索函数
|
|
|
|
|
matcher: (params, data) => {
|
|
|
|
|
if (!params.term || params.term.trim() === '') {
|
|
|
|
|
return data;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const term = params.term.toLowerCase();
|
|
|
|
|
|
|
|
|
|
// 检查文本、拼音或拼音首字母是否匹配
|
|
|
|
|
if (
|
2025-10-30 18:16:57 +08:00
|
|
|
data.text.toLowerCase().includes(term) ||
|
|
|
|
|
data.pinyin.toLowerCase().includes(term) ||
|
|
|
|
|
data.firstLetters.toLowerCase().includes(term)
|
2025-05-20 16:34:38 +08:00
|
|
|
) {
|
|
|
|
|
return data;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return null;
|
|
|
|
|
}
|
|
|
|
|
}));
|
|
|
|
|
|
|
|
|
|
// 跟踪禁用状态
|
|
|
|
|
const isDisabled = computed(() => props.disabled);
|
|
|
|
|
|
|
|
|
|
// 监听外部值变化
|
|
|
|
|
watch(() => props.value, (newVal) => {
|
|
|
|
|
currentValue.value = newVal;
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// 处理值变更
|
|
|
|
|
const handleChange = (value) => {
|
|
|
|
|
currentValue.value = value;
|
|
|
|
|
emits('update:modelValue', value);
|
|
|
|
|
emits('change', value);
|
|
|
|
|
};
|
|
|
|
|
</script>
|
|
|
|
|
|
|
|
|
|
<style scoped>
|
|
|
|
|
.custom-select2 {
|
|
|
|
|
width: 100%;
|
|
|
|
|
}
|
|
|
|
|
</style>
|