jiangchengfeiyi-xiaochengxu/pages/workshop/component/timeSelect.vue
2025-03-17 18:10:19 +08:00

542 lines
14 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<view class="flex-col page" :style="{ backgroundImage: 'url(' + bkgUrl + ')' }">
<view class="flex-col group">
<view class="flex-row self-stretch group_2">
<image
class="image_2"
:src="productObject.goodImg"
/>
<view class="flex-col flex-1 self-start ml-15">
<image
class="self-end image"
@click="close()"
:src="workshopUrl + '/component/cha.png'"
/>
<view class="flex-col items-start self-stretch mt-58">
<text class="text">{{ productObject.price }}</text>
<text class="font text_2 mt-14">请选择</text>
</view>
</view>
</view>
<text class="self-start font_2 text_3 mt-20">当前日期{{appointmentDateVOList[appIdx].specificDate}}</text>
<view class="flex-row justify-between items-center self-stretch mt-20">
<text class="font_2">剩余预约人数{{ restNumber }}</text>
<view class="flex-row items-center group_3" @click="openyyxzTip()">
<image
class="shrink-0 image"
:src="bookUrl + '/photoProductsOrder/yyxz.png'"
/>
<text class="font text_4 ml-3">预约须知</text>
</view>
</view>
</view>
<view class="flex-row equal-division group_4">
<view class="flex-col items-center section equal-division-item" :style="selectObj[index]" v-for="(item, index) in appointmentDateVOList" :key="index" @click="isSelected(index)">
<text class="font" :style="fontColor[index]">{{ getWeekday(item.specificDate) }}</text>
<text class="font_3 mt-12" :style="fontColor[index]">{{item.specificDate.substring(5)}}</text>
</view>
</view>
<view class="flex-col group_5">
<view class="flex-row list_2 my_grid">
<view class="flex-col justify-start items-center text-wrapper"
v-for="(item, index) in appointmentDateVOList[appIdx].timePeriodVOList" :key="index" @click="itemIsSelected(index)" :style="itemSelectObj[appIdx][index]">
<text class="font_3 text_5" :style="itemFontColor[appIdx][index]">{{item.timeSlot}}</text>
</view>
</view>
<view style="height: 1.88rpx; background-color: #d9d9d9; margin-top: 30rpx; margin-bottom: 20rpx;"></view>
<view class="flex-row justify-between items-center group_7">
<text class="font_2 text_6">数量</text>
<view class="flex-row">
<image
@click="sub"
class="image_3"
:src="workshopUrl + '/component/sub.png'"
/>
<view class="flex-col justify-start items-center text-wrapper_2 ml-4">
<text class="font_3 text_7">{{cnt}}</text>
</view>
<image
@click="add"
class="image_4 ml-4"
:src="workshopUrl + '/component/add.png'"
/>
</view>
</view>
</view>
<view class="flex-col justify-start items-center text-wrapper_3" @click="selectStatus()"><text class="font text_8">{{ btnText }}</text></view>
</view>
<uni-popup ref="tip" :animation="false">
<view class="pop">
<tipVue></tipVue>
</view>
</uni-popup>
</template>
<script setup>
import tipVue from './tip.vue';
import {nextTick, onMounted, onUnmounted, ref} from 'vue'
import emitter from '../../../utils/emitter';
import { baseUrl } from '../../../api/request';
import { workshopUrl } from '../../../common/globalImagesUrl';
import { dealResult } from '../../../common/globalFunction';
import { onLoad } from "@dcloudio/uni-app";
import { getFonts } from '../../../common/globalFont';
import { bookUrl } from '../../../common/globalImagesUrl';
const bkgUrl = ref(bookUrl + '/component/bkg.png')
let selectObj = ref([])
let fontColor = ref([])
let itemSelectObj = ref([])
let itemFontColor = ref([])
const cookie = wx.getStorageSync("cookie") //请求头
const appIdx = ref(0)
const tIdx = ref(0)
const cnt = ref(1)
const productObject = ref()
const appointmentDateVOList = ref([])
let appointmentDate = ''
let timeSlot = ''
const restNumber = ref('请选择时间段')
let countMap = new Map()
const getGoodDataHandler = (val) => {
productObject.value = val
appointmentDateVOList.value = val.appointmentDateVOList
selectObj.value = new Array(appointmentDateVOList.value.length).fill(null).map(() => ({
backgroundColor: '#fff',
borderColor: '#C35C5D'
}));
fontColor.value = new Array(appointmentDateVOList.value.length).fill(null).map(() => ({
color: '#323233'
}))
selectObj.value[0] = {backgroundColor: '#FBDEDF', borderColor: '#FBDEDF'}
fontColor.value[0] = {color: '#C35C5D'}
for (var i = 0; i < appointmentDateVOList.value.length; i ++ ) {
var col = appointmentDateVOList.value[i].timePeriodVOList.length
itemSelectObj.value[i] = new Array(col).fill(null).map(() => ({
backgroundColor: '#F3F3F3'
}))
itemFontColor.value[i] = new Array(col).fill(null).map(() => ({
color: '#323233'
}))
}
}
const getBookingNumberMapHandler = (val) => {
countMap = val
console.log("val==============>", val)
appointmentDate = appointmentDateVOList.value[appIdx.value].specificDate;
}
const countHandler = (val) => {
nowSelected.value = val
console.log('现在选择的是---->',nowSelected.value);
statusChange() //更改按钮文字
}
const closeyyxzTipHandler = () => {
nextTick(() => {
if (tip.value) {
tip.value.close()
}
})
}
onLoad(() => {
getFonts()
})
onMounted(() => {
emitter.on('closeyyxzTip', closeyyxzTipHandler)
emitter.on('getGoodData', getGoodDataHandler)
emitter.on('getBookingNumberMap', getBookingNumberMapHandler)
emitter.on('count', countHandler)
})
onUnmounted(() => {
emitter.off('closeyyxzTip', closeyyxzTipHandler)
emitter.off('getGoodData', getGoodDataHandler)
emitter.off('getBookingNumberMap', getBookingNumberMapHandler)
emitter.off('count', countHandler)
})
const addCart = async () =>{ //加入购物车方法
console.log('日期--->',appointmentDate,'时间段--->',timeSlot,'数量--->',cnt.value,'商品id---->',productObject.value.id);
if(appointmentDate === '' || timeSlot === '' ) {
uni.showToast({
icon: 'error',
title: "字段不能为空"
})
return;
}
const res = await uni.request({
url: baseUrl + '/cartExperience/add',
method: 'POST',
header: {
cookie
},
data: {
goodId : productObject.value.id,
reservationDate : appointmentDate,
timeSlot : timeSlot,
quantity : cnt.value
}
})
if (!dealResult(res)) return
console.log('加入购物车结果',res);
if(res.data.code === 1) {
uni.showToast({
icon: 'success',
title: "加入购物车成功"
})
close() //关闭弹窗
} else {
uni.showToast({
icon: 'error',
title: "服务错误"
})
}
}
const tip = ref(null)
const openyyxzTip = () => {
tip.value.open()
}
const add = () => { //添加商品方法
if (restNumber.value === '请选择时间段') {
uni.showToast({
title: '请选择时间段',
icon: 'error'
})
return ;
}
if (cnt.value < Number(restNumber.value)) {
cnt.value ++
}
}
const sub = () => { //减少商品方法
if (cnt.value > 1) {
cnt.value --
}
}
const close = () => { //关闭弹窗
emitter.emit('closeTimeDialog')
}
const isSelected = (index) => { //选择预约日期方法
if (appIdx.value === index) return
appIdx.value = index
restNumber.value = '请选择时间段'
appointmentDate = appointmentDateVOList.value[appIdx.value].specificDate;
timeSlot = ''
console.log('appointmentDate===================================>', appointmentDate)
for (var i = 0; i < appointmentDateVOList.value.length; i ++ ) {
if (i == index) {
selectObj.value[i].backgroundColor = '#FBDEDF'
selectObj.value[i].borderColor = '#FBDEDF'
fontColor.value[i].color = '#C35C5D'
} else {
selectObj.value[i].backgroundColor = '#fff'
selectObj.value[i].borderColor = '#C35C5D'
fontColor.value[i].color = '#323233'
}
}
var col = appointmentDateVOList.value[appIdx.value].timePeriodVOList.length
for (var i = 0; i < col; i ++ ) {
itemSelectObj.value[appIdx.value][i].backgroundColor = '#F3F3F3'
itemFontColor.value[appIdx.value][i].color = '#323233'
}
}
const itemIsSelected = (index) => { //选择时间段方法
timeSlot = appointmentDateVOList.value[appIdx.value].timePeriodVOList[index].timeSlot
restNumber.value = countMap[appointmentDate + '&' + timeSlot]
console.log('timeSlot====================================>', timeSlot)
var col = appointmentDateVOList.value[appIdx.value].timePeriodVOList.length
for (var i = 0; i < col; i ++ ) {
if (i == index) {
itemSelectObj.value[appIdx.value][i].backgroundColor = '#FBDEDF'
itemFontColor.value[appIdx.value][i].color = '#C35C5D'
} else {
itemSelectObj.value[appIdx.value][i].backgroundColor = '#F3F3F3'
itemFontColor.value[appIdx.value][i].color = '#323233'
}
}
}
const nowSelected = ref(0) //区别于加入购物车弹窗和立即预约弹窗
const btnText = ref('加入购物车')
const statusChange = () => {
if(nowSelected.value === 2) {
btnText.value = '立即预约'
} else {
btnText.value = '加入购物车'
}
}
const selectStatus = () => {
if(btnText.value === '加入购物车') {
addCart()
} else {
goToBook()
}
}
const goToBook = async () => { //去预约方法
console.log('日期--->',appointmentDate,'时间段--->',timeSlot,'数量--->',cnt.value,'商品id---->',productObject.value.id);
if(appointmentDate === '' || timeSlot === '' ) {
uni.showToast({
icon: 'error',
title: "字段不能为空"
})
return;
}
console.log('id---------------------------->',productObject.value.id);
const res = await uni.request({
url: baseUrl + '/goods/checkServiceGood',
method: 'POST',
header: {
cookie
},
data: {
goodId: productObject.value.id,
reservationDate: appointmentDate,
timeSlot: timeSlot,
quantity: cnt.value
}
})
console.log(res)
if (!dealResult(res)) return ;
console.log('==============================>', productObject.value)
uni.navigateTo({ //跳转到待支付页面
//商品信息+数量
url: '/pages/order/singleServiceWait/singleServiceWait?id='
+ productObject.value.id + '&cnt=' + cnt.value + '&rest=' + restNumber.value
+ '&appointmentDate=' + appointmentDate + '&timeSlot=' + timeSlot
})
}
function getWeekday(dateStr) {
const date = new Date(dateStr);
const weekdays = ["星期日", "星期一", "星期二", "星期三", "星期四", "星期五", "星期六"];
return weekdays[date.getDay()];
}
</script>
<style lang="scss" scoped>
.ml-15 {
margin-left: 28.13rpx;
}
.ml-3 {
margin-left: 5.63rpx;
}
.mt-91 {
margin-top: 170.63rpx;
}
.page {
padding: 0 20.63rpx 48.75rpx;
background-color: #ffffff;
border-radius: 37.5rpx 37.5rpx 0rpx 0rpx;
width: 100%;
overflow-y: auto;
overflow-x: hidden;
height: 100%;
}
.group {
padding: 30rpx 0 22.5rpx;
border-bottom: solid 1.88rpx #d9d9d9;
}
.group_2 {
padding-left: 18.75rpx;
padding-right: 16.88rpx;
}
.image_2 {
margin-top: 7.5rpx;
border-radius: 5.63rpx;
width: 221.25rpx;
height: 232.5rpx;
}
.image {
width: 37.5rpx;
height: 37.5rpx;
}
.text {
margin-left: 6.92rpx;
color: #c35c5d;
font-size: 37.5rpx;
font-family: FZSongKeBenXiuKaiS-R-GB;
line-height: 27.52rpx;
}
.font {
font-size: 26.25rpx;
font-family: FZSongKeBenXiuKaiS-R-GB;
line-height: 23.94rpx;
color: #323233;
}
.text_2 {
line-height: 24.21rpx;
}
.font_2 {
font-size: 30rpx;
font-family: FZSongKeBenXiuKaiS-R-GB;
line-height: 27.71rpx;
color: #323233;
}
.text_3 {
margin-left: 3.45rpx;
line-height: 27.86rpx;
}
.group_3 {
margin-right: 20.57rpx;
}
.text_4 {
color: #000000;
line-height: 24.23rpx;
}
.equal-division {
margin-top: 43.13rpx;
}
.group_4 {
border-bottom: solid 1.88rpx #d9d9d9;
padding-bottom: 40rpx;
-webkit-overflow-scrolling: touch; /* 使滚动更加平滑 */
margin: 30rpx auto;
width: 100%;
overflow-x: auto;
}
.group_4::-webkit-scrollbar {
display: none; /* 隐藏滚动条 */
}
.section {
width: 150rpx;
margin: 0 15rpx;
}
.equal-division-item {
padding: 17.51rpx 0 20.49rpx;
background-color: #ffffff;
border-radius: 5.63rpx;
height: 106.88rpx;
border: solid 1.88rpx #c35c5d;
}
.font_3 {
font-size: 26.25rpx;
font-family: FZSongKeBenXiuKaiS-R-GB;
line-height: 19.29rpx;
color: #323233;
}
.group_5 {
padding: 0 0 58.13rpx;
}
.list_2 {
margin-right: 3.77rpx;
// border-bottom: solid 1.88rpx #d9d9d9;
}
.list_2::-webkit-scrollbar {
display: none; /* 隐藏滚动条 */
}
.my_grid{
margin: 0 auto;
display: grid;
grid-template-columns: repeat(3, 1fr);
grid-template-rows: repeat(3, 1fr);
row-gap: 20rpx;
column-gap: 40rpx;
overflow-y: auto;
height: 350rpx;
}
.text-wrapper {
padding: 39.09rpx 0 35.25rpx;
background-color: #f3f3f3;
border-radius: 5.63rpx;
height: 93.75rpx;
width: 200rpx;
margin-bottom: 20rpx;
}
.text_5 {
line-height: 19.41rpx;
}
.group_7 {
padding: 28.13rpx 3.75rpx 0 11.32rpx;
position: fixed;
bottom: 180rpx;
left: 30rpx;
right: 30rpx;
}
.text_6 {
color: #323232;
}
.image_3 {
border-radius: 9.38rpx 0rpx 0rpx 9.38rpx;
width: 46.88rpx;
height: 46.88rpx;
}
.text-wrapper_2 {
padding: 15.02rpx 0 13.13rpx;
background-color: #f3f3f3;
width: 46.88rpx;
height: 46.88rpx;
}
.text_7 {
color: #323232;
line-height: 18.73rpx;
}
.image_4 {
border-radius: 0rpx 9.38rpx 9.38rpx 0rpx;
width: 46.88rpx;
height: 46.88rpx;
}
.text-wrapper_3 {
width: 600rpx;
padding: 24.82rpx 0 27.84rpx;
background-color: #fbdedf;
border-radius: 37.5rpx;
position: fixed;
bottom: 50rpx;
left: 0;
right: 0;
margin: 0 auto;
}
.text_8 {
color: #c35c5d;
line-height: 24.21rpx;
}
@import url(../../../common/css/global.css);
</style>