210 lines
5.5 KiB
Vue
210 lines
5.5 KiB
Vue
|
|
<template>
|
|||
|
|
<uni-popup
|
|||
|
|
ref="popup"
|
|||
|
|
type="bottom"
|
|||
|
|
border-radius="20rpx"
|
|||
|
|
style="z-index: 20000"
|
|||
|
|
>
|
|||
|
|
<!-- 时间选择滚轮 -->
|
|||
|
|
<view class="region-body">
|
|||
|
|
<image class="region-body__close" @click="close" src="/static/images/shop/close.png"></image>
|
|||
|
|
<view class="region-body__header"> 请选择时间段 </view>
|
|||
|
|
<picker-view
|
|||
|
|
:value="pickerValue"
|
|||
|
|
@change="handleTimeChange"
|
|||
|
|
class="picker-scroll"
|
|||
|
|
:indicator-style="indicatorStyle"
|
|||
|
|
>
|
|||
|
|
<picker-view-column>
|
|||
|
|
<view class="picker-item" v-for="(hour, index) in hours" :key="index">
|
|||
|
|
{{ hour }}时
|
|||
|
|
</view>
|
|||
|
|
</picker-view-column>
|
|||
|
|
<picker-view-column>
|
|||
|
|
<view
|
|||
|
|
class="picker-item"
|
|||
|
|
v-for="(minute, index) in minutes"
|
|||
|
|
:key="index"
|
|||
|
|
>
|
|||
|
|
{{ minute }}分
|
|||
|
|
</view>
|
|||
|
|
</picker-view-column>
|
|||
|
|
<picker-view-column>
|
|||
|
|
<view class="picker-item"> - </view>
|
|||
|
|
</picker-view-column>
|
|||
|
|
<picker-view-column>
|
|||
|
|
<view class="picker-item" v-for="(hour, index) in hours" :key="index">
|
|||
|
|
{{ hour }}时
|
|||
|
|
</view>
|
|||
|
|
</picker-view-column>
|
|||
|
|
<picker-view-column>
|
|||
|
|
<view
|
|||
|
|
class="picker-item"
|
|||
|
|
v-for="(minute, index) in minutes"
|
|||
|
|
:key="index"
|
|||
|
|
>
|
|||
|
|
{{ minute }}分
|
|||
|
|
</view>
|
|||
|
|
</picker-view-column>
|
|||
|
|
</picker-view>
|
|||
|
|
<view class="region-body__btn" @tap="confirmTime"
|
|||
|
|
>确认
|
|||
|
|
{{
|
|||
|
|
`(${this.formatTime(this.startTime)}-${this.formatTime(
|
|||
|
|
this.endTime
|
|||
|
|
)})`
|
|||
|
|
}}</view
|
|||
|
|
>
|
|||
|
|
</view>
|
|||
|
|
</uni-popup>
|
|||
|
|
</template>
|
|||
|
|
|
|||
|
|
<script>
|
|||
|
|
export default {
|
|||
|
|
data() {
|
|||
|
|
return {
|
|||
|
|
default_times: "",
|
|||
|
|
business_time: "",
|
|||
|
|
indicatorStyle: "height: 68rpx;",
|
|||
|
|
pickerValue: [8, 0, 0, 18, 0],
|
|||
|
|
// 小时数组直接用数字字符串,确保parseInt转换无歧义
|
|||
|
|
hours: Array.from({ length: 24 }, (_, i) => `${i}`),
|
|||
|
|
// 分钟数组使用数字字符串,避免格式问题
|
|||
|
|
minutes: ["0", "10", "20", "30", "40", "50", "59"],
|
|||
|
|
};
|
|||
|
|
},
|
|||
|
|
computed: {
|
|||
|
|
startTime() {
|
|||
|
|
return {
|
|||
|
|
hour: this.hours[this.pickerValue[0]],
|
|||
|
|
minute: this.minutes[this.pickerValue[1]],
|
|||
|
|
};
|
|||
|
|
},
|
|||
|
|
endTime() {
|
|||
|
|
return {
|
|||
|
|
hour: this.hours[this.pickerValue[3]],
|
|||
|
|
minute: this.minutes[this.pickerValue[4]],
|
|||
|
|
};
|
|||
|
|
},
|
|||
|
|
},
|
|||
|
|
methods: {
|
|||
|
|
// 处理时间变化,确保开始时间小于结束时间
|
|||
|
|
handleTimeChange(e) {
|
|||
|
|
const values = e.detail.value;
|
|||
|
|
// 转换为数值计算(避免字符串比较问题)
|
|||
|
|
const startHour = parseInt(this.hours[values[0]], 10);
|
|||
|
|
const startMinute = parseInt(this.minutes[values[1]], 10);
|
|||
|
|
const endHour = parseInt(this.hours[values[3]], 10);
|
|||
|
|
const endMinute = parseInt(this.minutes[values[4]], 10);
|
|||
|
|
|
|||
|
|
// 计算总分钟数进行比较
|
|||
|
|
const startTotalMinutes = startHour * 60 + startMinute;
|
|||
|
|
const endTotalMinutes = endHour * 60 + endMinute;
|
|||
|
|
|
|||
|
|
if (startTotalMinutes >= endTotalMinutes) {
|
|||
|
|
// 自动调整结束时间为开始时间后1小时(处理跨天情况)
|
|||
|
|
let newEndHour = startHour + 1;
|
|||
|
|
if (newEndHour >= 24) newEndHour = 0; // 超过24点则重置为0点
|
|||
|
|
// 找到新结束小时在数组中的索引
|
|||
|
|
const newEndHourIndex = this.hours.findIndex(h => parseInt(h, 10) === newEndHour);
|
|||
|
|
// 保持分钟与开始时间一致
|
|||
|
|
values[3] = newEndHourIndex;
|
|||
|
|
values[4] = values[1];
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
this.pickerValue = values;
|
|||
|
|
},
|
|||
|
|
openTimePopup() {
|
|||
|
|
this.$refs.popup.open();
|
|||
|
|
},
|
|||
|
|
// 格式化时间显示(保持":""分隔,iOS兼容)
|
|||
|
|
formatTime(time) {
|
|||
|
|
// 确保分钟为两位数显示(可选,根据需求调整)
|
|||
|
|
const minute = time.minute.padStart(2, '0');
|
|||
|
|
return `${time.hour}:${minute}`;
|
|||
|
|
},
|
|||
|
|
close(){
|
|||
|
|
this.$refs.popup.close();
|
|||
|
|
},
|
|||
|
|
// 确认选择,发射标准化的时间字符串
|
|||
|
|
confirmTime() {
|
|||
|
|
const startTimeStr = this.formatTime(this.startTime);
|
|||
|
|
const endTimeStr = this.formatTime(this.endTime);
|
|||
|
|
this.$emit("confirmTime", `${startTimeStr}-${endTimeStr}`);
|
|||
|
|
this.$refs.popup.close();
|
|||
|
|
},
|
|||
|
|
},
|
|||
|
|
};
|
|||
|
|
</script>
|
|||
|
|
|
|||
|
|
<style scoped lang="less">
|
|||
|
|
/* 样式部分不变 */
|
|||
|
|
.region-body {
|
|||
|
|
flex: 1;
|
|||
|
|
overflow: hidden;
|
|||
|
|
background: #fff;
|
|||
|
|
border-radius: 20rpx 20rpx 0 0;
|
|||
|
|
&__close{
|
|||
|
|
width: 22rpx;
|
|||
|
|
height: 22rpx;
|
|||
|
|
position: absolute;
|
|||
|
|
top: 44rpx;
|
|||
|
|
right: 30rpx;
|
|||
|
|
}
|
|||
|
|
&__header {
|
|||
|
|
padding: 40rpx 0;
|
|||
|
|
font-weight: 500;
|
|||
|
|
font-size: 32rpx;
|
|||
|
|
color: #333333;
|
|||
|
|
line-height: 45rpx;
|
|||
|
|
text-align: left;
|
|||
|
|
font-style: normal;
|
|||
|
|
display: flex;
|
|||
|
|
justify-content: center;
|
|||
|
|
|
|||
|
|
}
|
|||
|
|
&__btn {
|
|||
|
|
display: flex;
|
|||
|
|
align-items: center;
|
|||
|
|
justify-content: center;
|
|||
|
|
width: 690rpx;
|
|||
|
|
height: 80rpx;
|
|||
|
|
background: #E8101E;
|
|||
|
|
border-radius: 38rpx;
|
|||
|
|
font-weight: 400;
|
|||
|
|
font-size: 30rpx;
|
|||
|
|
color: #ffffff;
|
|||
|
|
line-height: 39rpx;
|
|||
|
|
text-align: right;
|
|||
|
|
font-style: normal;
|
|||
|
|
margin: 0 30rpx;
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
.region-scroll {
|
|||
|
|
height: 100%;
|
|||
|
|
}
|
|||
|
|
.picker-scroll {
|
|||
|
|
height: 400rpx;
|
|||
|
|
}
|
|||
|
|
.picker-item {
|
|||
|
|
height: 68rpx;
|
|||
|
|
line-height: 68rpx;
|
|||
|
|
text-align: center;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
.region-item {
|
|||
|
|
display: flex;
|
|||
|
|
align-items: center;
|
|||
|
|
justify-content: space-between;
|
|||
|
|
padding: 24rpx 0;
|
|||
|
|
border-bottom: 1rpx solid #eeeeee;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
.region-item.checkbox-item {
|
|||
|
|
padding: 20rpx 0;
|
|||
|
|
width: 100%;
|
|||
|
|
justify-content: flex-start !important;
|
|||
|
|
align-items: center !important;
|
|||
|
|
}
|
|||
|
|
</style>
|