自定义选择框

效果图展示:

在这里插入图片描述


需求场景及描述:

需求: 1.在车长选择时,可以选择多个,但限制3个以内 2.在选择不限时,取消其他车长的选择 3.在单个选择时,默认车长范围为0到所选项,需从小到大排序 4.在两个选择时,车长范围为当前两个值的范围,需从小到大排序 5.在三个选择时,车长范围为以最小和最大的值,作为范围取值,需从小到大排序 数据格式要求: 1.最小车长 carLengthMin 2.最大车长 carLengthMax 3.页面展示车长 carLength 4.后台传参车长 vehicleLength

逻辑分析:

分析:
1.通过elementUI框架的el-tag来对选项进行显示,控制其属性type,来呈现是否选中的样式
2.通过el-tag属性的改变,记录选中的下标,并存储进数组中,超过3个时,从数组里剔除,恢复第四个选中效果,并弹窗提示
3.在选中不限(即下标为0的选项)时,清空数组,将0存进数组,代表选中了不限,以便后续判断,并取消其他选中样式,并选中第一项(不限)
4.根据数组内容开始判断对应参数的数据格式:最小车长(carLengthMin)为单个的number类型;最大车长(carLengthMax)为单个的number类型;页面展示车长(carLength)为string类型;后台传参车长(vehicleLength)为string类型,并以’,'隔开.


代码及解析:

提示:这里填写该问题的具体解决方案:

<template>
	<div>
		<el-row>
			<el-col :span="24">
				<div class="fl_c_start w_700">
					<div>
						<p class="step_tips mar_b_10 mar_l_20"><span class="red_icon">*</span> 车长选择</p>
						<div class="mar_b_20 mar_l_20">
							<el-form-item label="" prop="carLength">
								<el-input placeholder="" v-model="goodsForm.carLength" class="w_400" @focus="goodsForm.dialogVisibleCarLength = true">
								</el-input>
							</el-form-item>
						</div>
					</div>
				</div>
			</el-col>
		</el-row>
		<!-- 车长选择 -->
		<el-dialog title="选择车长" :visible.sync="goodsForm.dialogVisibleCarLength" width="500px" center :before-close="handleClose"
		 :close-on-click-modal="false">
			<div style="width: 100%; height: 100%">
				<div class="fl_c_start mar_b_20">
					<span class="mar_l_10">车长:最多选择3个。</span>
				</div>
				<div class="body_box">
					<el-tag v-for="(item, index) in carLengthItems" :key="item.label" :type="item.type" effect="dark" size="big"
					 @click="changeCarLength(index)">
						{{ item.label }}
					</el-tag>
				</div>
				<div class="fl_c_end mar_t_20">
					<el-button type="primary" @click="handleClose">确定</el-button>
				</div>
			</div>
		</el-dialog>
	</div>
</template>

<script>
	export default {
		data() {
			return {
				goodsForm: {
					vehicleLength: '', //车长(str)提交字段
					carLengthMin: 0,
					carLengthMax: 20,
					carLengthArr: [0, 20],
					carLength: '', // 车长(str)展示
					dialogVisibleCarLength: false,
				},
				carLengthItems: [{
						type: 'info',
						label: '不限'
					},
					{
						type: 'info',
						label: '4.2'
					},
					{
						type: 'info',
						label: '4.5'
					},
					{
						type: 'info',
						label: '5'
					},
					{
						type: 'info',
						label: '5.2'
					},
					{
						type: 'info',
						label: '6.2'
					},
					{
						type: 'info',
						label: '6.8'
					},
					{
						type: 'info',
						label: '7.2'
					},
					{
						type: 'info',
						label: '7.6'
					},
					{
						type: 'info',
						label: '8.2'
					},
					{
						type: 'info',
						label: '8.6'
					},
					{
						type: 'info',
						label: '9.6'
					},
					{
						type: 'info',
						label: '11.7'
					},
					{
						type: 'info',
						label: '12.5'
					},
					{
						type: 'info',
						label: '13'
					},
					{
						type: 'info',
						label: '13.5'
					},
					{
						type: 'info',
						label: '14'
					},
					{
						type: 'info',
						label: '15'
					},
					{
						type: 'info',
						label: '16'
					},
					{
						type: 'info',
						label: '17'
					},
					{
						type: 'info',
						label: '17.5'
					},
					{
						type: 'info',
						label: '18'
					}
				],
			};
		},
		created() {},
		mounted() {},
		method: {
			// 车长选择
			changeCarLength(k) {
				let continueState = true;
				let num = 0;
				let arr = [];
				this.carLengthItems.forEach((item, index) => {
					if (index == k && this.carLengthItems[k].type == '' && continueState) {
						this.carLengthItems[k].type = 'info';
						continueState = false;
					}
					if (index == k && this.carLengthItems[k].type == 'info' && continueState) {
						this.carLengthItems[k].type = '';
						continueState = false;
					}
					if (item.type == '') {
						num++;
					}
				});
				//push arr
				this.carLengthItems.forEach((item, index) => {
					if (item.type == '') {
						arr.push(index);
					}
				});
				// length>0排除0
				if (arr.indexOf(0) !== -1 && arr.length > 1) {
					this.carLengthItems[0].type = 'info';
					arr.splice(arr.indexOf(0), 1);
				}
				// 不限时,置空
				if (this.carLengthItems[0].type == 'info' && k == 0) {
					this.carLengthItems[0].type = '';
					arr.forEach((item) => {
						this.carLengthItems[item].type = 'info';
					});
					arr = [0];
				}
				//限制个数为3
				if (arr.length > 3) {
					this.carLengthItems[k].type = 'info';
					arr.splice(arr.indexOf(k), 1);
					this.alert_info('车长最多选择3个');
				}
				// 车长范围定义
				// 不限
				if (arr.length == 1 && arr.indexOf(0) == 0) {
					this.goodsForm.carLengthArr = [0, 20];
					this.goodsForm.carLength = '车长不限';
					this.goodsForm.vehicleLength = '';
				}
				// 选择1个
				if (arr.length == 1 && arr.indexOf(0) == -1) {
					this.goodsForm.carLengthArr = [Number(this.carLengthItems[arr[0]].label), 20];
					this.goodsForm.carLength = this.carLengthItems[arr[0]].label + '米';
					this.goodsForm.vehicleLength = this.carLengthItems[arr[0]].label;
				}
				// 选择2或3个
				if (arr.length >= 2) {
					// 排序
					arr = this.bubbleSort(arr);
					// 车长范围(str)
					let carLengtLabel = '';
					let vehicleLength = '';
					arr.forEach((item, index) => {
						if (index < arr.length - 1) {
							carLengtLabel += this.carLengthItems[arr[index]].label + '米 , ';
							vehicleLength += this.carLengthItems[arr[index]].label + ',';
						} else {
							carLengtLabel += this.carLengthItems[arr[index]].label + '米 ';
							vehicleLength += this.carLengthItems[arr[index]].label;
						}
					});
					this.goodsForm.vehicleLength = vehicleLength;
					this.goodsForm.carLength = carLengtLabel;
					// 最大最小车长
					this.goodsForm.carLengthArr = [
						Number(this.carLengthItems[arr[0]].label),
						Number(this.carLengthItems[arr[arr.length - 1]].label)
					];
				}
				this.goodsForm.carLengthMin = this.goodsForm.carLengthArr[0];
				this.goodsForm.carLengthMax = this.goodsForm.carLengthArr[1];
				let nums = 0;
				this.carLengthItems.forEach((item) => {
					if (item.type == '') {
						nums++;
					}
				});
				if (nums == 0) {
					this.goodsForm.carLength = '';
				}
			},
			// 冒泡排序
			bubbleSort(arr) {
				if (Array.isArray(arr)) {
					for (var i = arr.length - 1; i > 0; i--) {
						for (var j = 0; j < i; j++) {
							if (arr[j] > arr[j + 1]) {
								[arr[j], arr[j + 1]] = [arr[j + 1], arr[j]];
							}
						}
					}
					return arr;
				}
			},
			alert_info(val) {
				this.$alert(`${val}`, '提示', {
					confirmButtonText: '确定'
				});
			}
		}
	};
</script>


结语

代码量有点大,已有相关备注,我就不一一说明了,如果有疑问或愿意专研者,没看明白的可以私信或评论,我将在24内回复(每天必逛CSDN),请留言,我再完善和说明!


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值