vue3 ts setup封装Autocomplete,支持插入suffixIcon和prefixIcon
![效果图](https://img-blog.csdnimg.cn/a58e2479c8564b65808999bf6374a165.png)
<template>
<el-autocomplete
v-model="state"
:fetch-suggestions="props.fetchSuggestions ?? querySearch"
:popper-class="props.popperClass"
:placeholder="props.placeholder"
:clearable="props.clearable"
@select="handleSelect"
@clear="clear"
>
<template #suffix v-if="props.suffixIconComponent">
<el-icon class="el-input__icon" @click="handleSuffixIconClick">
<component :is="props.suffixIconComponent"></component>
</el-icon>
</template>
<template #prefix v-if="props.prefixIconComponent">
<el-icon class="el-input__icon" @click="handlePrefixIconClick">
<component :is="props.prefixIconComponent"></component>
</el-icon>
</template>
<template #default="{ item }">
<div class="label">{{ item.label }}</div>
<span class="value">{{ item.value }}</span>
</template>
</el-autocomplete>
</template>
<script lang="ts" setup>
interface propsInterface {
fetchSuggestions?: (queryString: string, cb: (results: any[]) => void) => void
placeholder?: string
popperClass?: string
suffixIconComponent?: Component
prefixIconComponent?: Component
suggestions?: any[]
clearable?: boolean
data: dataInterface[]
}
let props = defineProps<propsInterface>()
interface dataInterface {
label: string
value: string
}
const state = ref('')
const localData = ref<dataInterface[]>([])
const querySearch = (queryString: string, cb) => {
const results = queryString
? localData.value.filter(createFilter(queryString))
: localData.value
cb(results)
}
const createFilter = (queryString) => {
return (restaurant) => {
return (
restaurant.value.toLowerCase().indexOf(queryString.toLowerCase()) !== -1
)
}
}
const emits = defineEmits(['select', 'clear', 'suffixIconClick', 'prefixIconClick'])
const clear = () => {
emits('clear')
state.value = ''
}
const handleSelect = (item: dataInterface) => {
emits('select', item)
}
const handleSuffixIconClick = (ev: Event) => {
emits('suffixIconClick', ev)
}
const handlePrefixIconClick = (ev: Event) => {
emits('prefixIconClick', ev)
}
onMounted(() => {
localData.value = props.data
})
</script>
<style>
.el-autocomplete{
width: 100%;
}
.label {
color: #409EFF;
font-weight: bold;
}
.value {
color: #cccccc;
font-weight: bold;
}
</style>
引用组件
<template>
<Autocomplete
:suffixIconComponent="Edit"
:clearable="true"
:data="autoCompleteData"
:placeholder="`请输入内容`"
@clear="onClear"
@select="onSelect"
@suffixIconClick="onSuffixIconClick"
@prefixIconClick="onPrefixIconClick"
/>
</template>
<script setup lang="ts">
import Autocomplete from "@/components/autocomplete/index.vue";
const autoCompleteData = [
{label: 'vue', value: 'https://github.com/vuejs/vue'},
{label: 'element', value: 'https://github.com/ElemeFE/element'},
{label: 'cooking', value: 'https://github.com/ElemeFE/cooking'},
{label: 'mint-ui', value: 'https://github.com/ElemeFE/mint-ui'},
{label: 'vuex', value: 'https://github.com/vuejs/vuex'},
{label: 'vue-router', value: 'https://github.com/vuejs/vue-router'},
{label: 'babel', value: 'https://github.com/babel/babel'},
]
const onSelect = (item: any) => {
ElNotification({
title: 'Success',
message: 'onSelect',
type: 'success',
})
}
const onClear = (val) => {
ElNotification({
title: 'Success',
message: 'onClear',
type: 'success',
})
}
const onSuffixIconClick = (val) => {
ElNotification({
title: 'Success',
message: 'onSuffixIconClick',
type: 'success',
})
}
const onPrefixIconClick = (val) => {
ElNotification({
title: 'Success',
message: 'onPrefixIconClick',
type: 'success',
})
}
</script>