uni-app 封装下拉选择组件 标红指定项

javascript 复制代码
<template>
	<view class="uni-dropdown">
		<view class="trigger" @tap="toggleDropdown">{{ showlabel }}</view>
		<view class="dropdown-content" v-if="isOpen">
			<view class="" style="position: relative;">
				<text class="blk blk-a-xialakuang-xiala"></text>
			</view>
			<view style="max-height: 150px;overflow-y: auto;">
				<view v-for="(item, index) in options" :key="index" :class="['dropdown-item', item.isred ? 'red' : '']"
					@tap="selectOption(item)">
					{{ item[labelkey] }}
				</view>
			</view>
		</view>
	</view>
</template>

<script setup>
	import {
		ref,
		watch,
	} from 'vue';

	const props = defineProps({
		options: {
			type: Array,
			default: () => []
		},
		modelValue: {
			type: [String, Number],
			default: ''
		},
		valuekey: {
			type: String,
			default: 'id'
		},
		labelkey: {
			type: String,
			default: 'name'
		},
		isredkey: {
			type: String,
			default: 'isred'
		}
	});
	let emit = defineEmits(['update:modelValue', 'change'])

	const isOpen = ref(false);
	const showlabel = ref('请选择'); // 初始化显示文本  

	const toggleDropdown = () => {
		isOpen.value = !isOpen.value;
	};

	const selectOption = (item) => {
		emit('update:modelValue', item[props.valuekey]); // 发出更新事件  
		emit('change', item[props.valuekey])
		isOpen.value = false; // 关闭下拉  
		// 同时更新显示的标签(如果需要)  
		showlabel.value = item[props.labelkey];
	};

	watch(() => props.modelValue, (newVal) => {
		const selectedOption = props.options.find(opt => opt[props.valuekey] === newVal);
		if (selectedOption) {
			// 注意这里应该是selectedOption而不是selectOption  
			showlabel.value = selectedOption[props.labelkey];
		} else {
			// 如果找不到匹配的选项,可以重置为默认文本或其他逻辑  
			showlabel.value = '请选择';
		}
	},{
		immediate:true
	});
</script>

<style scoped>
	.uni-dropdown {
		position: relative;
	}

	.trigger {
		padding: 5rpx;
		border: 1px solid #ccc;
		cursor: pointer;
		overflow-x: scroll;
		width: 100%;
		border-radius: 4px;
	}

	.dropdown-content {
		box-sizing: border-box;
		position: absolute;
		top: calc(100% + 5px);
		left: 0;
		width: 100%;
		background-color: #fff;
		border: 1px solid #ebeef5;
		border-radius: 6px;
		box-shadow: 0 2px 12px 0 rgba(0, 0, 0, .1);
		z-index: 3;
		padding: 4px 0;
		font-size: 20rpx;
	}

	.blk-a-xialakuang-xiala {
		position: absolute;
		left: 20%;
		top: -14px;
		color: #fff;
		border-top-width: 0;
		border-bottom-color: #ebeef5;
	}

	.dropdown-item {
		padding: 5rpx;
		cursor: pointer;
	}

	.dropdown-item.red {
		color: red;
	}

	.dropdown-item:hover {
		background-color: #f0f0f0;
	}
</style>

使用方式

html 复制代码
<selectBom v-if="!isOnlyRead&&supplies_detail_item.type_biaoshi==3&&item?.bom_list?.length"
								v-model="item.bom_versions" :options="item.bom_list" labelkey='bom_versions'
								valuekey='bom_versions'
								@change="handle_change_boom($event,item,index,idx,item.bom_list)"></selectBom>
相关推荐
IT_陈寒8 小时前
Python+AI实战:用LangChain构建智能问答系统的5个核心技巧
前端·人工智能·后端
2501_916008898 小时前
iOS 发布全流程详解,从开发到上架的流程与跨平台使用 开心上架 发布实战
android·macos·ios·小程序·uni-app·cocoa·iphone
袁煦丞8 小时前
MoneyPrinterTurbo一键生成短视频:cpolar内网穿透实验室第644个成功挑战
前端·程序员·远程工作
代码小学僧8 小时前
让 AI 真正帮你开发:前端 MCP 实用技巧分享
前端
晴殇i8 小时前
前端鉴权新时代:告别 localStorage,拥抱更安全的 JWT 存储方案
前端·javascript·面试
Json____8 小时前
使用node Express 框架框架开发一个前后端分离的二手交易平台项目。
java·前端·express
since �8 小时前
前端转Java,从0到1学习教程
java·前端·学习
码农刚子9 小时前
ASP.NET Core Blazor简介和快速入门 二(组件基础)
javascript·后端
小奋斗9 小时前
面试官:[1] == '1'和[1] == 1结果是什么?
前端·面试
萌萌哒草头将军9 小时前
尤雨溪宣布 oxfmt 即将发布!比 Prettier 快45倍 🚀🚀🚀
前端·webpack·vite