vue之封装预约类组件

vue之封装预约类组件

0. 展示所有数据,【禁用】的展示【灰色】,【没选中】的展示【白色】,【选中的】时间范围展示【红色】
1. 点击两次,锁定时间范围。
2. 如果有跨越了禁用时间段的话,则重新选择。
3. 【禁用的时间范围】 和  【全部的时间范围】,后端会返回。
4. 插件会返回选择的时间。
<template>

	<view class="item" v-bind:class="{active:item.active,disabled:item.disabled}" v-for="(item, index) in list"
		:key="index" v-on:click="clickItem(item,index)">
		<view style="display: flex;justify-content: space-between;">
			<view>
				{{item.time}}
			</view>
			<view v-if="item.disabled">
				该条已被<text style="color: white;">{{item.bookedBy}}</text>预约
			</view>
		</view>
	</view>

</template>
<!-- 预约类时间段选择组件的开发思路:
	0.  展示所有数据,【禁用】的展示【灰色】,【没选中】的展示【白色】,【选中的】时间范围展示【红色】
	1. 点击两次,锁定时间范围。
	2. 如果有跨越了禁用时间段的话,则重新选择。
	3. 【禁用的时间范围】 和  【全部的时间范围】,后端会返回。
	4. 插件会返回选择的时间。

 -->
<script>
	export default {
		// props接收两个值,禁用的时间段和全部的时间段
		props: {
			// 禁用的时间
			checkTime: {
				type: Array
			},
			// 所有的时间
			allTime: {
				type: Array
			},

		},
		data() {
			return {
				// 用data接收props传来的值,不要直接操作props 
				
				
				// list用于存储传来的【全部的时间】,以下是传来数据的格式
				// "time": "08:00-08:30", "disabled": false, "active": false
				list: this.allTime,
				// 【禁用的时间】
				disabledList: this.checkTime,
				
				
				// item 点击的次数
				clickNumber: 0,
				// 点击item,把下标存到数组。
				indexArr: [],
			}
		},
		created() {
			this.initTime();
		},
		computed: {
			// 计算属性,用于返回给父组件,选值的范围。
			timeList() {
				let list = []
				this.list.forEach(item => {
					if (item.active) {
						list.push(item)
					}
				})
				let obj = {
					start: '',
					end: ''
				}
				if (list.length) {
					obj.start = list[0].time.split('-')[0]
					obj.end = list[list.length - 1].time.split('-')[1];
				}
				//console.log("computed监听",obj)
				return obj;
			}
		},
		methods: {
			// 通过传来的数据构建时间数组
			initTime() {
				// 根据【所有时间】和【禁用时间】,确定列表
				this.list.forEach(item => {
					this.disabledList.forEach(vitem => {
						// 判断是否有list的time和disabled的time一致
						// 有的话,则需要禁用掉
						const hasTime = item.time == vitem.time
						if (hasTime) {
							item.disabled = true
						}
					})
				})
			},
			clickItem(item, index) {
				// 如果是disable状态,直接不让点击
				if (item.disabled) {
					return
				}
				
				// 点击次数增加,用于记录点击的次数
				this.clickNumber++;
				// 记录第一次点击,且把数组的index值,存到indexArr 里面
				if (this.clickNumber == 1) {
					this.indexArr.push(index)
				}
				// 记录第二次点击,且把数组的index值,存到indexArr 里面
				if (this.clickNumber == 2) {
					this.indexArr.push(index)
				}

				console.log(this.indexArr)

				// 记录第三次点击,且把数组的index值,存到indexArr 里面
				// 记录第三次的值,是为了下面重置第三次为第一次。
				// 用于接下来的循环
				if (this.clickNumber == 3) {
					this.indexArr = [index]
				}
				
				// 给index排序
				this.indexArr = this.indexArr.sort((a, b) => a - b);
				
				
				// 如果点击的次数正好是第三次的时候
				// 点击次数重置为1
				// 我们的目的是点击两次,锁定时间范围,所以三次以上的,可以重置上面的步骤。
				if (this.clickNumber % 3 == 0) {
					// 重置成点击一次的状态。
					this.clickNumber = 1;
					// list中的active设置成false
					this.list.forEach(v => v.active = false);
					// 当前点击的item,设置active是true
					item.active = true
				}
				// 验证,如果选择多个的时候,跨着disabled,则不让选择。
				// 如果选择的,没有跨着disabled,则都给选择上。
				this.getCheckList(item)
			},
			getCheckList(vitem) {
				try {
					console.log("getCheckList", this.list, this.indexArr)
					this.list.forEach((item, idx) => {
						// this.indexArr 存两个值
						const [start, end] = this.indexArr
						if (idx >= start && idx <= end) {
							// 遍历List,如果有disabled的抛出异常。
							// 如果没有,则把区间内的赋值active
							if (item.disabled) {
								throw new Error("包含disabled状态数据")
							}
							item.active = true
						}
					})
				} catch (err) {
					// 抛出异常----选中的区间内有disabled的item的时候。
					
					// list 重置
					this.list.forEach(v => v.active = false);
					// 当前item为选中状态
					vitem.active = true;
				}
				vitem.active = true;
				// 返回给父组件
				this.$emit('getTime', this.timeList)
			}
		}
	}
</script>

<style>
	.item {
		line-height: 40px;
		background: #fff;
		border-bottom: 1px solid #D2D2D2;
	}

	.item.active {
		background: darkred;
		color: black;
	}

	.item.disabled {
		background: #888888;
		color: white;
	}
</style>

<TimeSelection @getTime='getTime' ref="child" :allTime="timeSelectList"
				:checkTime="timeSelectDisabledList" />



getTime(val) {
				console.log("getTime组件选择后的结果", val)
			},



// 后端返回所有的时间段列表
timeSelectList: [],
// 已选时间段列表
timeSelectDisabledList: [],
09-16 18:56