完善茶艺师接口对接

This commit is contained in:
wangxiaowei
2026-01-05 00:39:06 +08:00
parent 237df8d039
commit 39c64a2504
29 changed files with 1204 additions and 651 deletions

View File

@ -17,7 +17,7 @@
<view>
<view>
<view class="flex items-center mx-36rpx">
<view class="text-30rpx leading-42rpx text-#303133 mr-60rpx w-100rpx">联系人</view>
<view class="text-30rpx leading-42rpx text-#303133 mr-60rpx w-150rpx">联系人</view>
<view>
<wd-input v-model="form.contact" size="large" placeholder="请填写联系人" no-border placeholderStyle="font-size: 30rpx; line-height: 42rpx; color: #c9c9c9;"></wd-input>
</view>
@ -27,7 +27,7 @@
<view>
<view class="flex items-center mx-36rpx">
<view class="text-30rpx leading-42rpx text-#303133 mr-60rpx w-100rpx">电话</view>
<view class="text-30rpx leading-42rpx text-#303133 mr-60rpx w-150rpx">电话</view>
<view>
<wd-input v-model="form.telephone" size="large" placeholder="请填写联系电话" no-border placeholderStyle="font-size: 30rpx; line-height: 42rpx; color: #c9c9c9;"></wd-input>
</view>
@ -35,21 +35,22 @@
<view class="h-2rpx bg-#F2F2F2"></view>
</view>
<!-- <view>
<view class="flex items-center mx-36rpx">
<view class="text-30rpx leading-42rpx text-#303133 mr-60rpx w-100rpx">省市区</view>
<view class="add-address">
<wd-col-picker v-model="address" :columns="area" :column-change="columnChange" auto-complete @confirm="Add.handleConfirmAddress" placeholder="请选择省市区"> </wd-col-picker>
<!-- <view class="flex items-center mx-36rpx">
<view class="text-30rpx leading-42rpx text-[#303133] w-150rpx mr-60rpx">选择地区</view>
<wd-picker :columns="cityColumns" v-model="form.city_id" use-default-slot @confirm="Add.handleConfirmAddress">
<view class="flex items-center">
<wd-input readonly v-model="city" size="large" placeholder="请选择地区" no-border placeholderStyle="font-size: 30rpx; line-height: 42rpx; color: #c9c9c9;"></wd-input>
<wd-icon name="chevron-right" size="32rpx" color="#909399"></wd-icon>
</view>
</view>
</wd-picker>
<view class="h-2rpx bg-#F2F2F2"></view>
</view> -->
<view>
<view class="flex items-center mx-36rpx" @click="Add.handleChooseLocation">
<view class="text-30rpx leading-42rpx text-#303133 mr-60rpx w-100rpx">地址</view>
<view class="text-30rpx leading-42rpx text-#303133 mr-60rpx w-150rpx">地址</view>
<view>
<wd-input readonly v-model="form.address" size="large" placeholder="请填写具体地址" no-border placeholderStyle="font-size: 30rpx; line-height: 42rpx; color: #c9c9c9;"></wd-input>
<wd-input readonly v-model="form.address" size="large" placeholder="请选择地址" no-border placeholderStyle="font-size: 30rpx; line-height: 42rpx; color: #c9c9c9;"></wd-input>
</view>
</view>
</view>
@ -57,12 +58,12 @@
<view class="h-12rpx bg-#F7F7F7"></view>
<view class="flex justify-between items-center mx-36rpx mt-32rpx">
<!-- <view class="flex justify-between items-center mx-36rpx mt-32rpx">
<view class="text-30rpx leading-42rpx text-#303133">设为默认地址</view>
<view class="">
<wd-switch v-model="isDefaultAddress" active-color="#4C9F44"/>
</view>
</view>
</view> -->
<view class="fixed bottom-70rpx left-0 right-0">
<view
@ -85,12 +86,12 @@
<script lang="ts" setup>
import { useMessage } from 'wot-design-uni'
import { useColPickerData } from '@/hooks/useColPickerData'
import { addUserAddress, IAddUserAddressParams, deleteUserAddress, userAddressDetails, editUserAddress } from '@/api/user'
import { getOpenCityList } from '@/api/tea-specialist'
import { toast } from '@/utils/toast'
import { mobile } from '@/utils/test'
import { router } from '@/utils/tools'
const OSS = inject('OSS')
// 弹出框
@ -102,44 +103,21 @@
// 地址id
const addressId = ref<number>(0)
// 获取已开通城市
const cityColumns = ref<Array<{ label: string, value: number }>>([])
// 表单信息
const form = reactive<IAddUserAddressParams>({
contact: '',
telephone: '',
// province: '',
// province_id: 0,
// city: '',
// city_id: 0,
// district: '',
// district_id: 0,
city_id: 0,
longitude: 0,
latitude: 0,
address: '',
is_default: 0,
// is_default: 0,
id: 0
})
// 省市区数据
const { colPickerData, findChildrenByCode } = useColPickerData()
const address = ref<string[]>([])
const area = ref<any[]>([])
const columnChange = async ({ selectedItem, resolve, finish }) => {
await Add.handleSleep(0)
const areaData = findChildrenByCode(colPickerData, selectedItem.value)
if (areaData && areaData.length) {
resolve(
areaData.map((item) => {
return {
value: item.value,
label: item.text
}
})
)
} else {
finish()
}
}
const city = ref<string>('')
// 是否默认地址
const isDefaultAddress = ref<boolean>(false)
@ -151,41 +129,50 @@
addressId.value = Number(args.id)
Add.handleGetAddressDetails()
}
Add.handleGetCity()
})
const Add = {
// 确认省市区
// handleConfirmAddress: (e) => {
// form.province = e.selectedItems[0]?.label || ''
// form.province_id = Number(e.selectedItems[0]?.value) || 0
// form.city = e.selectedItems[1]?.label || ''
// form.city_id = Number(e.selectedItems[1]?.value) || 0
// form.district = e.selectedItems[2]?.label || ''
// form.district_id = Number(e.selectedItems[2]?.value) || 0
// },
/**
* 获取已开通城市
*/
handleGetCity: async () => {
const res = await getOpenCityList()
cityColumns.value = res.list.map((item: any) => ({
label: item.name,
value: item.id
}))
},
/**
* 确认选择的地址
*/
handleConfirmAddress: (e: any) => {
form.city_id = Number(e.value)
city.value = e.selectedItems.label || ''
},
// 获取地址详情
handleGetAddressDetails: async () => {
const res = await userAddressDetails({
id: addressId.value
})
console.log("🚀 ~ res:", res)
form.contact = res.address_details.contact
form.telephone = res.address_details.telephone
form.address = res.address_details.address
// form.city_id = res.address_details.city_id,
// form.province = res.address_details.province
// form.province_id = res.address_details.province_id
// form.city = res.address_details.city
// form.city_id = res.address_details.city_id
// form.district = res.address_details.district
// form.district_id = res.address_details.district_id
form.address = res.address_details.address
form.is_default = res.address_details.is_default
isDefaultAddress.value = res.address_details.is_default === 1 ? true : false
address.value = [
String(res.address_details.province_id),
String(res.address_details.city_id),
String(res.address_details.district_id)
]
console.log("🚀 ~ address.value:", address.value)
// form.is_default = res.address_details.is_default
},
// 删除地址
@ -210,14 +197,14 @@
})
toast.info('删除成功')
uni.$emit('refreshAddressList')
router.navigateBack(500)
router.navigateBack(1, 500)
}).catch((res) => {
console.log("🚀 ~ res2:", res)
// 点击取消按钮回调事件
})
},
/**
/**
* 选择地址
*/
handleChooseLocation: async () => {
@ -250,8 +237,8 @@
return
}
// if (!form.province || !form.city || !form.district) {
// toast.info('请选择省市区')
// if (!form.city_id) {
// toast.info('请选择城市')
// return
// }
@ -260,18 +247,20 @@
return
}
form.is_default = isDefaultAddress.value ? 1 : 0
// form.is_default = isDefaultAddress.value ? 1 : 0
if (addressId.value > 0 ) {
// 编辑地址
form.id = addressId.value
await editUserAddress(form)
} else {
delete form.id
await addUserAddress(form)
}
uni.$emit('refreshAddressList')
router.navigateBack(500)
router.navigateBack(1, 500)
},
handleSleep: async (second: number = 1) => {

View File

@ -270,19 +270,17 @@
</view>
</view>
<view class="mt-24rpx">
<view class="font-bold text-28rpx leading-48rpx text-[#303133]">对饮八式</view>
<view class="font-bold text-28rpx leading-48rpx text-[#303133]">茶品介绍</view>
<view class="mt-24rpx font-500 text-[#303133] text-26rpx leading-48rpx">
<view>
<text class="mr-20rpx"> 洗尘</text>
<text class="mr-20rpx"> 坦呈</text>
<text class="mr-20rpx"> 苏酲</text>
<text class="mr-20rpx"> 法度</text>
<text class="mr-20rpx">1. 产地介绍</text>
<text class="mr-20rpx">2. 基础属性</text>
<text class="mr-20rpx">3. 外形品相</text>
<text class="mr-20rpx">4. 色香表现</text>
</view>
<view>
<text class="mr-20rpx"> 养成</text>
<text class="mr-20rpx"> 身受</text>
<text class="mr-20rpx"> 分享</text>
<text class="mr-20rpx"> 放下</text>
<text class="mr-20rpx">5.工艺特点</text>
<text class="mr-20rpx">6. 滋味口感</text>
</view>
</view>
</view>
@ -413,8 +411,8 @@
// 获取茶艺师详情
const res = await getTeaSpecialistDetail({
team_user_id: args.id,
latitude: uni.getStorageSync('latitude'),
longitude: uni.getStorageSync('longitude'),
latitude: uni.getStorageSync('latitude') || import.meta.env.VITE_DEFAULT_LATITUDE,
longitude: uni.getStorageSync('longitude') || import.meta.env.VITE_DEFAULT_LONGITUDE,
})
info.value = res.teamaster
console.log("🚀 ~ res:", res)

View File

@ -33,7 +33,7 @@
</view>
<!-- 团体茶艺师预购 -->
<view class="">
<!-- <view class="">
<view class="mx-30rpx flex items-center">
<view class="flex items-center mr-14rpx">
<wd-img width="160rpx" height="36rpx" :src="`${OSS}images/h5/home/home_image1.png`" />
@ -50,17 +50,17 @@
</view>
<view class="font-400 text-22rpx leading-32rpx text-#818CA9">定制方案</view>
</view>
</view>
</view> -->
<view class="mt-16rpx relative w-690rpx h-260rpx mx-30rpx">
<!-- <view class="mt-16rpx relative w-690rpx h-260rpx mx-30rpx"> -->
<!-- <view class="mt-16rpx relative w-690rpx h-260rpx mx-30rpx" @click="router.navigateTo('/pages/reserve/group-tea-specialist')"> -->
<wd-img width="690rpx" height="260rpx" :src="`${OSS}images/h5/home/home_image2.png`" mode="scaleToFill" />
<!-- <wd-img width="690rpx" height="260rpx" :src="`${OSS}images/h5/home/home_image2.png`" mode="scaleToFill" />
<view class="h-64rpx absolute bottom-0 right-0 bg-[#4C9F44] text-[#fff] flex items-center px-26rpx rounded">
<text class="mr-8rpx">一键约</text>
<wd-img width="22rpx" height="18.06rpx" :src="`${OSS}icon/icon_arrow_right.png`" mode="aspectFit" />
</view>
</view>
</view>
</view> -->
<!-- 茶艺师列表 -->
<view class="">
@ -104,13 +104,13 @@
</view>
<view class="flex items-center">
<!-- 到店服务 -->
<view class="mr-12rpx" v-if="item.server_type == 1">
<!-- 到店服务标签 -->
<view class="mr-12rpx" v-if="item.server_type == 1 || item.server_type == 3">
<wd-tag color="#F55726" bg-color="#F55726" plain custom-class="!rounded-4rpx">到店服务</wd-tag>
</view>
<!-- 上门服务 -->
<view class="mr-12rpx" v-if="item.server_type == 2">
<!-- 上门服务标签 -->
<view class="mr-12rpx" v-if="item.server_type == 2 || item.server_type == 3">
<wd-tag color="#40AE36" bg-color="#40AE36" plain custom-class="!rounded-4rpx">上门服务</wd-tag>
</view>
@ -227,11 +227,6 @@
* @param state 茶艺师状态: 0可约 1工作中
*/
handleReserveTeaSpecialist: (id: number, state: number) => {
if (state === 1) {
toast.show('茶艺师工作中,暂不可预约')
return
}
router.navigateTo(`/bundle_b/pages/tea-specialist/detail?id=${id}`)
},

View File

@ -47,7 +47,7 @@
</view>
<view class="" v-if="currentTimePicker == 'end'">
<wd-datetime-picker-view
:minDate='minTimestamp'
:minDate='futureTimestamp'
:maxDate='maxTimestamp'
type="datetime"
v-model="endTimeValue"
@ -76,12 +76,12 @@
<view>
<view class="flex justify-between items-center text-30rpx text-[#303133] leading-42rpx">
<view>服务费</view>
<view>¥{{ bill.service.total }}</view>
<view>¥{{ costBill.server_all_price }}</view>
</view>
<view class="flex justify-between items-center text-24rpx text-[#909399] leading-34rpx mt-16rpx">
<view>服务费(¥{{ bill.service.unitPrice }}元/小时)</view>
<view>x{{ bill.service.num }}</view>
<view>服务费(¥{{ costBill.server_price }}元/小时)</view>
<view>x{{ costParams.hours }}</view>
</view>
</view>
@ -89,12 +89,12 @@
<view>
<view class="flex justify-between items-center text-30rpx text-[#303133] leading-42rpx mt-52rpx">
<view>车马费</view>
<view>¥{{ bill.travel.total }}</view>
<view>¥{{ costBill.mileage_server_price }}</view>
</view>
<view class="flex justify-between items-center text-24rpx text-[#909399] leading-34rpx mt-16rpx">
<view>车马费(¥{{ bill.travel.unitPrice }}元/小时)</view>
<view>{{ bill.travel.num }}公里</view>
<view>车马费(¥{{ costBill.mileage_price }}元/小时)</view>
<view>{{ costBill.team_user_distance }}公里</view>
</view>
</view>
@ -102,23 +102,28 @@
<view>
<view class="flex justify-between items-center text-30rpx text-[#303133] leading-42rpx mt-52rpx">
<view>茶艺服务</view>
<view>¥{{ bill.teaService.total }}</view>
<view>¥{{ costBill.leaf_tea_all_price }}</view>
</view>
<view class="flex justify-between items-center text-24rpx text-[#909399] leading-34rpx mt-16rpx">
<view class="flex justify-between items-center text-24rpx text-[#909399] leading-34rpx mt-16rpx" v-if="selectedTeaTxt.length > 0">
<view class='w-400rpx'>{{ selectedTeaTxt.join('/') }}</view>
<view>¥{{ bill.teaService.total }}</view>
<view>¥{{ costBill.leaf_amount }}</view>
</view>
<view class="flex justify-between items-center text-24rpx text-[#909399] leading-34rpx mt-16rpx" v-if="teaUsageValue > 0">
<view class='w-400rpx'>茶具使用</view>
<view>{{ costBill.teacup_price }}</view>
</view>
</view>
<view class="mt-52rpx">
<view class="flex justify-between items-center text-30rpx text-[#303133] leading-42rpx">
<view>优惠</view>
<view class="text-[#4C9F44]">-¥{{ bill.coupon }}</view>
<view class="text-[#4C9F44]">-¥{{ costBill.coupon_price }}</view>
</view>
<view class="flex justify-between items-center text-24rpx text-[#909399] leading-34rpx mt-16rpx">
<view>优惠券</view>
<view>-¥{{ bill.coupon }}</view>
<view>-¥{{ costBill.coupon_price }}</view>
</view>
</view>
@ -128,7 +133,7 @@
<view class="flex justify-between items-center text-30rpx text-[#303133] leading-42rpx">
<view>实付金额</view>
<view>¥{{ bill.total }}</view>
<view>¥{{ costBill.order_amount }}</view>
</view>
</view>
</view>
@ -154,26 +159,6 @@
</view>
</view>
<!-- 预定茶叶 -->
<view class="mx-60rpx mb-50rpx">
<view class="text-32rpx leading-44rpx text-#303133">
<text class="mr-20rpx">预定茶叶</text>
<text class="text-26rpx leading-36rpx text-#909399">支持多选</text>
</view>
<view class="mt-28rpx">
<view class="grid grid-cols-3 gap-x-16rpx gap-y-16rpx">
<view
v-for="(item, index) in teaList" :key="index"
class="text-28rpx leading-40rpx rounded-8rpx text-center py-14rpx"
:class="selectedTea.includes(item.id) ? 'bg-#4C9F44 text-#fff' : 'bg-#F7F7F7 text-#606266'"
@click="Reserve.handleToggleTea(item.id, item.name, item.price)">
<view>{{item.name}}</view>
<view>¥{{item.price}}</view>
</view>
</view>
</view>
</view>
<!-- 茶具使用 -->
<view class="mx-60rpx mb-70rpx">
<view class="text-32rpx leading-44rpx text-#303133">茶具使用</view>
@ -193,6 +178,26 @@
</view>
</view>
<!-- 预定茶叶 -->
<view class="mx-60rpx mb-50rpx">
<view class="text-32rpx leading-44rpx text-#303133">
<text class="mr-20rpx">预定茶叶</text>
<text class="text-26rpx leading-36rpx text-#909399">支持多选</text>
</view>
<view class="mt-28rpx">
<view class="grid grid-cols-3 gap-x-16rpx gap-y-16rpx">
<view
v-for="(item, index) in teaList" :key="index"
class="text-28rpx leading-40rpx rounded-8rpx text-center py-14rpx"
:class="selectedTea.includes(item.id) ? 'bg-#4C9F44 text-#fff' : 'bg-#F7F7F7 text-#606266'"
@click="Reserve.handleToggleTea(item.id, item.name, item.price)">
<view>{{item.name}}</view>
<view>¥{{item.price}}</view>
</view>
</view>
</view>
</view>
<view class="h-2rpx bg-#EFF0F2"></view>
<!-- 按钮 -->
@ -200,7 +205,7 @@
<view class="">
<view class="text-24rpx leading-34rpx text-#303133">已选 {{selectedTea.length}} 项</view>
<view class="">
<price-format color="#FF5951" :first-size="40" :second-size="40" :subscript-size="28" :price="totalSelectedTeaPrice"></price-format>
<price-format color="#FF5951" :first-size="40" :second-size="40" :subscript-size="28" :price="costBill.order_amount"></price-format>
</view>
</view>
@ -225,7 +230,7 @@
<!-- 茶艺师信息 -->
<view class="flex items-center bg-white p-20rpx rounded-10rpx mb-20rpx mt-20rpx">
<view class="mr-28rpx relative">
<wd-img width="200rpx" height="200rpx" :src="`${OSS}images/home/home_image5.png`"></wd-img>
<wd-img width="200rpx" height="200rpx" :src="info.image"></wd-img>
</view>
<view class="">
<view class="font-bold text-[#303133] text-30rpx leading-42rpx mr-14rpx">
@ -269,7 +274,7 @@
<view class="flex items-center">
<view class="text-28rpx leading-40rpx text-#303133 w-430rpx line-1 text-right">
<template v-if="address && address.id > 0">
{{address.contact}} {{ address.telephone }} {{ address.province }}{{ address.city }}{{ address.district }}{{ address.address }}
{{address.contact}} {{ address.telephone }} {{ address.address }}
</template>
<template v-else>
请选择地址
@ -288,10 +293,7 @@
<view class="text-[26rpx] text-[#606266] leading-36rpx">{{ sevenDay.minimum_time }}小时起订</view>
<view class="flex items-center">
<view class="text-[28rpx] text-[#909399] leading-40rpx w-430rpx line-1 text-right">
<template v-if="serviceTypeValue == 1 && dayHours">
{{ dayTime }} {{ dayHours }}
</template>
<template v-else-if="serviceTypeValue == 2 && startTimeLayout && endTimeLayout">
<template v-if="startTimeLayout && endTimeLayout">
{{ startTimeLayout }} {{ endTimeLayout }}
</template>
<template v-else>
@ -326,15 +328,6 @@
</view>
</view>
<!-- 订单备注 -->
<view class="bg-white py-26rpx px-30rpx mt-20rpx">
<view class="text-32rpx leading-44rpx text-#303133 mb-28rpx">
<text class="mr-20rpx">订单备注 </text>
<text class="text-26rpx leading-36rpx text-#909399">(选填)</text>
</view>
<wd-textarea placeholder="有想说的可以在这里写哦!" v-model="orderRemarks" custom-class='!rounded-18rpx !border-2rpx !border-[#EFF0EF] !bg-[#F8F9FA]' custom-textarea-class='!bg-[#F8F9FA]' />
</view>
<!-- 优惠券 -->
<view class="bg-white py-26rpx px-30rpx mt-20rpx" @click="Reserve.handleToCoupon(CouponType.Discount)">
<view class="text-[#303133] text-32rpx leading-44rpx font-bold mb-24rpx">优惠券</view>
@ -356,6 +349,22 @@
</view>
</view>
<!-- 订单备注 -->
<view class="bg-white py-26rpx px-30rpx mt-20rpx">
<view class="text-32rpx leading-44rpx text-#303133 mb-28rpx">
<text class="mr-20rpx">订单备注 </text>
<text class="text-26rpx leading-36rpx text-#909399">(选填)</text>
</view>
<wd-textarea v-model="orderRemarks"
:auto-height="true"
no-border
placeholder="有想说的可以在这里写哦!"
custom-class='!rounded-18rpx !border-2rpx !border-[#EFF0EF] !bg-[#F8F9FA]'
custom-textarea-class='!bg-[#F8F9FA] !min-h-[100rpx] !px-24rpx' />
</view>
<!-- 支付方式 -->
<!-- <view class="bg-white py-26rpx px-30rpx mt-20rpx">
<pay hide-store-balance @pay="Reserve.handleGetPayValue"></pay>
@ -367,7 +376,7 @@
<view class="flex items-center ml-40rpx mr-20rpx" @click="showCostPopup = true">
<view class="text-24rpx text-[#303133] leading-34rpx w-50rpx whitespace-nowrap mr-10rpx">合计</view>
<view class="flex items-center h-56rpx mr-16rpx">
<price-format color="#FF5951" :first-size="40" :second-size="40" :subscript-size="28" :price="bill.total"></price-format>
<price-format color="#FF5951" :first-size="40" :second-size="40" :subscript-size="28" :price="costBill.order_amount"></price-format>
</view>
<view class="flex items-center text-[#4C9F44] w-100rpx whitespace-nowrap">
<view class="text-24rpx mr-10rpx">费用明细</view>
@ -375,7 +384,7 @@
</view>
</view>
<view class="mr-30rpx">
<wd-button custom-class='!bg-[#4C9F44] !rounded-8rpx !h-70rpx' @click="Reserve.handleSubmitOrder">立即预定</wd-button>
<wd-button custom-class='!bg-[#4C9F44] !rounded-8rpx !h-70rpx' :disabled="isSubmitting" @click="Reserve.handleSubmitOrder">立即预定</wd-button>
</view>
</view>
</view>
@ -396,12 +405,15 @@
import type { IUserAddressListResult } from '@/api/types/user'
import BookingTime from '@/components/BookingTime.vue'
import { CouponType } from '@/utils/coupon'
import { getTeaSpecialistDetail } from '@/api/tea-specialist'
import { getTeaSpecialistDetail, getTeaSpecialistFeeDetails } from '@/api/tea-specialist'
const OSS = inject('OSS')
const toast = useToast()
const message = useMessage('wd-message-box-slot')
// 防止重复提交
const isSubmitting = ref(false)
// 服务方式
const serviceType = ref<Array<any>>([
{type: 1, name: '到店服务'},
@ -434,8 +446,9 @@
const startTimeValue = ref<string>('') // 开始时间
const endTimeValue = ref<string>('') // 结束时间
const now = new Date()
const minTimestamp = Date.now()
// 允许选择今天及未来六天的日期
const minTimestamp = Date.now() + 0.5 * 60 * 60 * 1000
// 允许选择今天及未来六天的日期
const futureTimestamp = minTimestamp + 2 * 60 * 60 * 1000
const maxTimestamp = new Date(now.getFullYear(), now.getMonth(), now.getDate() + 6, 23, 59, 59, 999).getTime()
const startTimeLayout = ref<string>('')
const endTimeLayout = ref<string>('')
@ -453,7 +466,6 @@
})
// 茶艺服务
const teaService = ref<{id: number, name: string}>({id: 0, name: ''})
const showTeaServicePopup = ref<boolean>(false) // 显示门店列表弹窗
const servicePeople = ref<number>(1) // 服务人数
const teaList = ref<ITeaTypeListResult[]>([]) // 茶叶列表
@ -464,10 +476,10 @@
// 茶具使用
const teaUsageList = ref<Array<any>>([
{type: 1, name: '客户自备'},
{type: 2, name: '茶艺师提供'},
{type: 0, name: '客户自备'},
{type: 1, name: '茶艺师提供'},
])
const teaUsageValue = ref<number>(1)
const teaUsageValue = ref<number>(0)
// 订单备注
const orderRemarks = ref<string>('')
@ -479,6 +491,7 @@
const id = ref<number>(0)
const info = ref({
id: 0,
image: '',
image_arr: [], // 轮播图
name: '', // 茶艺师名字
star: 0, // 茶艺师评分
@ -494,6 +507,7 @@
hobby_introduce: '', // 兴趣爱好介绍
price: 0, // 服务费
mileage_price: 0, // 车马费
state: 0, // 茶艺师状态哦
})
// 选择的优惠券
@ -524,25 +538,44 @@
coupon: 0,
total: 0
})
// 费用明细
const costBill = ref<any>({
order_amount: 0, // 订单实付价格
server_price: 0, // 服务费单价
server_all_price: 0, // 服务费总价
mileage_price: 0, // 车马费单价
team_user_distance: 0, // 车马费公里数
mileage_server_price: 0, //车马费总价
leaf_tea_all_price: 0, // 茶艺服务费
leaf_amount: 0, // 茶叶金额
teacup_price: 0, // 茶具金额
coupon_price: 0, // 优惠券金额
})
// 计算费用明细参数
const costParams = ref({
hours: 0, // 预定小时数
tea_id: '', // 茶叶id
longitude: 0, // 经度
latitude: 0, // 纬度
user_coupon_id: 0, // 优惠券id
is_teacup: 0, // 是否需要茶具 0客户自备 1茶艺师提供
team_user_id: 0, // 茶艺师id
})
onLoad(async (args) => {
if (args.id) {
id.value = Number(args.id)
costParams.value.team_user_id = Number(args.id)
// 获取茶艺师详情
const res = await getTeaSpecialistDetail({
team_user_id: args.id,
latitude: uni.getStorageSync('latitude'),
longitude: uni.getStorageSync('longitude'),
latitude: uni.getStorageSync('latitude') || import.meta.env.VITE_DEFAULT_LATITUDE,
longitude: uni.getStorageSync('longitude') || import.meta.env.VITE_DEFAULT_LONGITUDE,
})
info.value = res.teamaster
// bill.value.travel = {
// total: toTimes(info.fare_price, info.distance),
// unitPrice: info.fare_price,
// num: info.distance
// }
}
// 初始化数据
@ -550,11 +583,12 @@
})
const Reserve = {
/**
* 初始化-获取茶叶列表
*/
handleInit: async () => {
// 获取茶叶列表
const tea = await getTeaTypeList()
teaList.value = tea as ITeaTypeListResult[]
console.log("🚀 ~ teaList.value:", teaList.value)
},
/**
@ -585,39 +619,37 @@
dayHours.value = ''
sevenDay.minimum_time = MINIMUMTIME
sevenDay.time = []
teaHouse.value = {id: 0, name: ''}
}
teaHouse.value = {id: 0, name: ''}
},
/**
* 选择预订时间
*/
handleChooseTime: async () => {
if (info.value.state === 1) {
toast.show('茶艺师工作中,暂不可预约')
return
}
if (serviceTypeValue.value === 1 && teaHouse.value.id === 0) {
// 到店服务必须要选择门店
toast.show('请先选择门店')
return false
}
if (serviceTypeValue.value === 1) {
const storeId = teaHouse.value.id || 0
const next7 = await getNext7Days(storeId, getCurrentDate())
// disabled = 0 可预约 1不可逾越
Object.assign(sevenDay, next7.data)
Object.assign(sevenDay, {minimum_time: MINIMUMTIME})
showBookTimePopup.value = true
} else if (serviceTypeValue.value === 2) {
// 上门服务
showReservePopup.value = true
}
showReservePopup.value = true
},
/**
* 切换预定茶叶选择
*/
handleToggleTea: (id: number, name: string, price: number) => {
console.log("🚀 ~ id:", id)
const index = selectedTea.value.indexOf(id)
if (index > -1) {
console.log("🚀 ~ index:", index)
if (index >= 0) {
// 已选择,取消选择
selectedTea.value.splice(index, 1)
selectedTeaTxt.value.splice(index, 1)
@ -628,9 +660,14 @@
selectedTeaTxt.value.push(name)
selectedTeaPrice.value.push(price)
}
console.log("🚀 ~ selectedTea.value:", selectedTea.value)
totalSelectedTeaPrice.value = toPlus(selectedTeaPrice.value)
bill.value.teaService.total = Number(totalSelectedTeaPrice.value) // 更新茶艺服务费用
// 计算费用明细
costParams.value.tea_id = selectedTea.value.join(',')
Reserve.handleCost()
},
/**
@ -639,8 +676,14 @@
handleToChooseStore: () => {
uni.$on('chooseTeaHouse', params => {
console.log("🚀 ~ params:", params)
uni.$off('chooseTeaHouse')
teaHouse.value = params
// 计算费用明细
costParams.value.longitude = params.longitude
costParams.value.latitude = params.latitude
// Reserve.handleCost()
})
router.navigateTo('/bundle_b/pages/tea-specialist/store?from=reserve')
},
@ -650,8 +693,13 @@
*/
handleToAddress: () => {
uni.$on('chooseAddress', params => {
console.log("🚀 ~ params:", params)
uni.$off('chooseAddress')
address.value = params
costParams.value.longitude = params.longitude
costParams.value.latitude = params.latitude
// Reserve.handleCost()
})
router.navigateTo('/bundle_b/pages/tea-specialist/address/list?from=reserve')
},
@ -660,21 +708,20 @@
* 选中预定时间
*/
handleChooseReserveTime: (params: any) => {
console.log("🚀 ~ params:", params)
reserveTime.value = params
if (!digits(params.countSelectedTime)) {
message.alert({
title: '提示',
msg: '选择时间段不满一小时按一小时算请合理选择时间',
confirmButtonText: '确定',
cancelButtonProps: {
customClass: '!bg-[#F6F7F8] !text-[#303133] !text-32rpx !leading-44rpx !rounded-8rpx',
},
confirmButtonProps: {
customClass: '!bg-[#4C9F44] !text-[#fff] !text-32rpx !leading-44rpx !rounded-8rpx',
},
})
}
// if (!digits(params.countSelectedTime)) {
// message.alert({
// title: '提示',
// msg: '选择时间段不满一小时按一小时算请合理选择时间',
// confirmButtonText: '确定',
// cancelButtonProps: {
// customClass: '!bg-[#F6F7F8] !text-[#303133] !text-32rpx !leading-44rpx !rounded-8rpx',
// },
// confirmButtonProps: {
// customClass: '!bg-[#4C9F44] !text-[#fff] !text-32rpx !leading-44rpx !rounded-8rpx',
// },
// })
// }
timeSlots.value = params.selectedTimestamps
dayTitle.value = params.dayTitle
@ -684,10 +731,9 @@
}).join(',')
dayHours.value = times
startTime.value = params.selectedTimestamps[0]
console.log("🚀 ~ startTime.value:", startTime.value)
endTime.value = params.selectedTimestamps[params.selectedTimestamps.length - 1]
console.log("🚀 ~ endTime.value:", endTime.value)
// 预定了几个小时
countHours.value = params.countSelectedTime
bill.value.service = {
@ -698,14 +744,16 @@
endHour: params.selectedTime[params.selectedTime.length - 1].time
}
// Detail.handleCalculateTeaRoomPrice()
// 计算费用明细
costParams.value.hours = params.countSelectedTime
Reserve.handleCost()
},
/**
* 跳转优惠券页面
*/
handleToCoupon(type) {
if (reserveTime.value.length == 0) {
if (totalHour.value == 0) {
toast.info('请选择预定时间')
return
}
@ -716,10 +764,13 @@
selectedCoupon.value = {id: params.coupon.id, name: params.coupon.name}
bill.value.coupon = params.coupon.coupon_price
selectCouponId.value = params.coupon.id // 这里的ID是在数据表自增的ID保存下来是为了回显列表的,没有其他作用
// 计算费用明细
costParams.value.user_coupon_id = params.coupon.id
Reserve.handleCost()
})
// 获取预定了几个小时
const count = bill.value.service.num
router.navigateTo(`/bundle_b/pages/tea-specialist/coupon?couponId=${selectCouponId.value}`)
},
@ -729,7 +780,7 @@
handleResetTeaService: () => {
servicePeople.value = 1
selectedTea.value = []
teaUsageValue.value = 1
teaUsageValue.value = 0
},
/**
@ -740,60 +791,82 @@
toast.info('请选择预定茶叶')
return
}
teaService.value = { id: 1, name: '茶艺服务' }
showTeaServicePopup.value = false
// 计算费用明细
costParams.value.is_teacup = teaUsageValue.value
Reserve.handleCost()
},
/**
* 提交订单数据
*/
handleSubmitOrder: async () => {
if (serviceTypeValue.value == 1 && teaHouse.value.id == 0) {
toast.info('请选择门店地址')
if (isSubmitting.value) return
if (costParams.value.longitude == 0 && costParams.value.latitude == 0) {
toast.info('请选择地址')
return false
}
if (info.value.state === 1) {
toast.show('茶艺师工作中,暂不可预约')
return
}
if (serviceTypeValue.value == 2 && address.value.id == 0) {
toast.info('请选择上门服务地址')
return
}
if (bill.value.service.num == 0) {
if (totalHour.value == 0) {
toast.info('请选择预定时间')
return
return false
}
if (selectedTea.value.length == 0) {
toast.info('请选择茶艺时服务')
return
toast.info('请选择茶')
return false
}
// if (teaUsageValue.value == -1) {
// toast.info('请选择茶具需求')
// showTeaServicePopup.value = true
// return false
// }
isSubmitting.value = true
// uni.showLoading({
// title: '提交中...'
// })
toast.loading('提交中...')
// 提交的订单数据
const params = {
team_user_id: id.value, // 茶艺师ID
server_type: serviceTypeValue.value, // 服务方式 1到店服务 2上门服务
longitude: uni.getStorageSync('longitude'), // 经度
latitude: uni.getStorageSync('latitude'), // 纬度
longitude: costParams.value.longitude, // 经度
latitude: costParams.value.latitude, // 纬度
store_id: serviceTypeValue.value == 1 ? teaHouse.value.id : 0, // 茶室Id如果是上门服务则传0
address: serviceTypeValue.value == 1 ? teaHouse.value.name : address.value.address, // 地址: 到店传茶室名称 上门则传地址
start_time: serviceTypeValue.value == 1 ? startTime.value : Math.floor(Door.startTimeTimestamp / 1000), // 预约开始时间
end_time: serviceTypeValue.value == 1 ? endTime.value : Math.floor(Door.endTimeTimestamp / 1000), // 预约结束时间
hours: serviceTypeValue.value == 1 ? countHours.value : totalHour.value, // 预约小时数
start_time: Math.floor(Door.startTimeTimestamp / 1000), // 预约开始时间
end_time: Math.floor(Door.endTimeTimestamp / 1000), // 预约结束时间
hours: totalHour.value, // 预约小时数
remrk: orderRemarks.value, // 订单备注
is_teacup: teaUsageValue.value, // 是否需要茶具 1客户自备 2茶艺师提供
is_teacup: teaUsageValue.value, // 是否需要茶具 0客户自备 1茶艺师提供
tea_id: selectedTea.value.join(','), // 茶叶商品ids 多个逗号隔开
user_coupon_id: selectedCoupon.value.id, // 优惠券id默认传0
server_number: servicePeople.value
}
try {
const res = await createTeaSpecialistOrder(params)
toast.close()
uni.$on('payment', params => {
console.log("🚀 ~ params:", params)
setTimeout(() => {
uni.$off("payment")
isSubmitting.value = false
if (params.result) {
uni.redirectTo({
url: `/pages/notice/reserve?type=teaSpecialist&orderId=${params.orderId}`
url: `/pages/notice/reserve?type=${OrderType.TeaSpecialist}&orderId=${params.orderId}`
})
} else {
uni.redirectTo({
@ -804,12 +877,23 @@
})
setTimeout(() => {
router.navigateTo(`/pages/cashier/cashier?from=${OrderType.TeaSpecialist}&orderId=${res.id}&teaSpecialistId=${info.id}&teaSpecialistName=${info.name}`)
router.navigateTo(`/pages/cashier/cashier?from=${OrderType.TeaSpecialist}&orderId=${res.order_id}&teaSpecialistName=${info.value.name}&teaSpecialistOrderAmount=${res.order_amount}`)
}, 800)
} catch (error) {
toast.info('订单提交失败,请稍后重试')
toast.close()
isSubmitting.value = false
return
}
},
/**
* 计算费用明细
*/
handleCost: async () => {
toast.loading('计费中...')
const res = await getTeaSpecialistFeeDetails(costParams.value)
toast.close()
costBill.value = res
}
}
@ -819,8 +903,12 @@
endTimeTimestamp: 0, // 记录结束时间戳
handleStartTimePicker: (e: {value: number}) => {
console.log("🚀 ~ e:", e)
Door.startTimeTimestamp = e.value
startTimeLayout.value = Door.handleFormatDate(e.value)
endTimeLayout.value = Door.handleFormatDate(Number(e.value) + Number(2 * 60 * 60 * 1000)) // 初始化结束时间是未来2个小时
Door.endTimeTimestamp = Number(e.value) + Number(2 * 60 * 60 * 1000) // 初始化结束时间是未来2个小时
endTimeValue.value = String(Door.endTimeTimestamp)
Door.handleTotalTimestamp()
},
@ -831,8 +919,6 @@
},
handleFormatTime: (type: string, values: string) => {
const now = new Date();
if (type === 'year') {
return `${values}`
}
@ -898,25 +984,29 @@
* 确定时间
*/
handleConfirmHour: () => {
if (totalHour.value <= sevenDay.minimum_time) {
if (totalHour.value < sevenDay.minimum_time) {
toast.info(`起订时间${sevenDay.minimum_time}小时`)
return
}
if (!digits(totalHour.value)) {
message.alert({
title: '提示',
msg: '选择时间段不满一小时按一小时算请合理选择时间',
confirmButtonText: '确定',
cancelButtonProps: {
customClass: '!bg-[#F6F7F8] !text-[#303133] !text-32rpx !leading-44rpx !rounded-8rpx',
},
confirmButtonProps: {
customClass: '!bg-[#4C9F44] !text-[#fff] !text-32rpx !leading-44rpx !rounded-8rpx',
},
})
}
// if (!digits(totalHour.value)) {
// message.alert({
// title: '提示',
// msg: '选择时间段不满一小时按一小时算请合理选择时间',
// confirmButtonText: '确定',
// cancelButtonProps: {
// customClass: '!bg-[#F6F7F8] !text-[#303133] !text-32rpx !leading-44rpx !rounded-8rpx',
// },
// confirmButtonProps: {
// customClass: '!bg-[#4C9F44] !text-[#fff] !text-32rpx !leading-44rpx !rounded-8rpx',
// },
// })
// }
showReservePopup.value = false
// 计算费用明细
costParams.value.hours = totalHour.value
Reserve.handleCost()
},
}

View File

@ -91,8 +91,8 @@
const filter = {
page: mescroll.num,
size: mescroll.size,
latitude: uni.getStorageSync('latitude'),
longitude: uni.getStorageSync('longitude'),
latitude: uni.getStorageSync('latitude') || import.meta.env.VITE_DEFAULT_LATITUDE,
longitude: uni.getStorageSync('longitude') || import.meta.env.VITE_DEFAULT_LONGITUDE,
search: storeName.value
}