321
This commit is contained in:
parent
2fae2b2bcf
commit
2c7a7940a0
|
|
@ -7,10 +7,10 @@
|
||||||
const development = {
|
const development = {
|
||||||
// API基础URL
|
// API基础URL
|
||||||
// baseUrl: 'https://ydsapi.zpc-xy.com',
|
// baseUrl: 'https://ydsapi.zpc-xy.com',
|
||||||
baseUrl: 'http://1.15.21.245:2401',
|
// baseUrl: 'http://1.15.21.245:2401',
|
||||||
host: ['http://1.15.21.245:2401'],
|
// host: ['http://1.15.21.245:2401'],
|
||||||
// baseUrl: 'http://localhost:2015',
|
baseUrl: 'http://localhost:2015',
|
||||||
// host: ['http://localhost:2015'],
|
host: ['http://localhost:2015'],
|
||||||
imageUrl: 'https://guyu-1308826010.cos.ap-shanghai.myqcloud.com',
|
imageUrl: 'https://guyu-1308826010.cos.ap-shanghai.myqcloud.com',
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -21,4 +21,38 @@ export const getConfigData = async () => {
|
||||||
await preloadConfigData();
|
await preloadConfigData();
|
||||||
}
|
}
|
||||||
return configData.value;
|
return configData.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取订阅消息模板ID列表
|
||||||
|
* @param {Number} depositFee 押金费用
|
||||||
|
* @returns {Array|null} 返回模板ID数组,失败时返回null
|
||||||
|
*/
|
||||||
|
export const getSubscribeMessage = async (depositFee) => {
|
||||||
|
try {
|
||||||
|
debugger
|
||||||
|
const config = await getConfigData();
|
||||||
|
if (!config || !config.config || !config.config.subscribeMessage) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
const templateIds = config.config.subscribeMessage
|
||||||
|
.filter(element => {
|
||||||
|
// 如果没有押金,过滤掉扣费通知和退款通知
|
||||||
|
if (element.type == "reservation_success" || element.type == "reservation_change" || element.type == "reservation_reminder") {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
// if (depositFee === 0) {
|
||||||
|
// return element.type !== "deduction_notice" && element.type !== "refund";
|
||||||
|
// }
|
||||||
|
// return true;
|
||||||
|
})
|
||||||
|
.map(element => element.templateId);
|
||||||
|
|
||||||
|
return templateIds;
|
||||||
|
} catch (error) {
|
||||||
|
console.error('获取订阅消息配置失败:', error);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -112,7 +112,75 @@ export const getReservationRoomList = async (startTime, endTime) => {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 用户创建预约接口
|
||||||
|
* @param {Object} reservationData 预约数据
|
||||||
|
* @param {number} reservationData.room_id 房间ID
|
||||||
|
* @param {number} reservationData.start_time 开始时间 时间戳(秒)
|
||||||
|
* @param {number} reservationData.end_time 结束时间 时间戳(秒)
|
||||||
|
* @param {string} reservationData.game_type 游戏类型
|
||||||
|
* @param {number} reservationData.deposit_fee 押金费用
|
||||||
|
* @param {string} reservationData.important_data 重要数据
|
||||||
|
* @returns {Promise<any>} 返回预约结果
|
||||||
|
*/
|
||||||
|
export const addSQReservation = async (reservationData) => {
|
||||||
|
const res = await request.post("sq/AddSQReservation", reservationData);
|
||||||
|
if (res.code == 0) {
|
||||||
|
return {
|
||||||
|
success: true,
|
||||||
|
data: res.data.reservation_id
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
success: false,
|
||||||
|
message: res.msg || '预约失败'
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 用户加入预约接口
|
||||||
|
* @param {Object} joinData 加入预约数据
|
||||||
|
* @param {number} joinData.ReservationsId 预约ID
|
||||||
|
* @param {string} joinData.important_data 重要数据
|
||||||
|
* @returns {Promise<any>} 返回加入结果
|
||||||
|
*/
|
||||||
|
export const joinReservation = async (joinData) => {
|
||||||
|
const res = await request.post("sq/JoinReservation", joinData);
|
||||||
|
if (res.code == 0) {
|
||||||
|
return {
|
||||||
|
success: true,
|
||||||
|
message: res.msg || '加入预约成功'
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
success: false,
|
||||||
|
message: res.msg || '加入预约失败'
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 取消预约接口
|
||||||
|
* @param {Object} cancelData 取消预约数据
|
||||||
|
* @param {number} cancelData.reservation_id 预约ID
|
||||||
|
* @param {string} cancelData.cancel_reason 取消原因(可选)
|
||||||
|
* @returns {Promise<any>} 返回取消结果
|
||||||
|
*/
|
||||||
|
export const cancelReservation = async (reservation_id, cancel_reason) => {
|
||||||
|
console.log("cancelReservation", reservation_id, cancel_reason);
|
||||||
|
const res = await request.post("sq/CancelReservation", { reservation_id: reservation_id, cancel_reason: cancel_reason });
|
||||||
|
if (res.code == 0) {
|
||||||
|
return {
|
||||||
|
success: true,
|
||||||
|
message: res.msg || '取消预约成功'
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
success: false,
|
||||||
|
message: res.msg || '取消预约失败'
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
export const sqInterface = {
|
export const sqInterface = {
|
||||||
|
|
@ -122,5 +190,8 @@ export const sqInterface = {
|
||||||
getEvaluateServices,
|
getEvaluateServices,
|
||||||
addEvaluateServices,
|
addEvaluateServices,
|
||||||
getReputationByUser,
|
getReputationByUser,
|
||||||
getReservationRoomList
|
getReservationRoomList,
|
||||||
|
addSQReservation,
|
||||||
|
joinReservation,
|
||||||
|
cancelReservation
|
||||||
}
|
}
|
||||||
|
|
@ -124,8 +124,20 @@ export const cancelUserBlack = async (userId) => {
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* 添加黑名单
|
||||||
|
* @param {*} userId 要拉黑的用户ID
|
||||||
|
* @returns {Promise<boolean>}
|
||||||
|
*/
|
||||||
|
export const usePay = async (money) => {
|
||||||
|
const res = await request.post("user/UsePay", { money: money });
|
||||||
|
if (res.code == 0) {
|
||||||
|
return res.data;
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
export const userInterface = {
|
export const userInterface = {
|
||||||
|
|
||||||
getAnonymousLogin,
|
getAnonymousLogin,
|
||||||
ueWxPhoneNumberLogin,
|
ueWxPhoneNumberLogin,
|
||||||
anonymousLogin,
|
anonymousLogin,
|
||||||
|
|
@ -134,7 +146,8 @@ export const userInterface = {
|
||||||
editUserInfo,
|
editUserInfo,
|
||||||
getMyBlackList,
|
getMyBlackList,
|
||||||
addUserBlack,
|
addUserBlack,
|
||||||
cancelUserBlack
|
cancelUserBlack,
|
||||||
|
usePay
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,7 @@ const throttledLoadUserInfo = throttle(_loadUserInfo, 2000, { leading: true, tra
|
||||||
/**
|
/**
|
||||||
* 清除用户相关存储
|
* 清除用户相关存储
|
||||||
*/
|
*/
|
||||||
const clearUserStorage = () => {
|
export const clearUserStorage = () => {
|
||||||
userInfo.value = null;
|
userInfo.value = null;
|
||||||
uni.removeStorageSync('tokenInfo');
|
uni.removeStorageSync('tokenInfo');
|
||||||
uni.removeStorageSync('userInfo');
|
uni.removeStorageSync('userInfo');
|
||||||
|
|
|
||||||
|
|
@ -7,6 +7,7 @@ import config from '@/common/env.js';
|
||||||
import md5 from 'js-md5';
|
import md5 from 'js-md5';
|
||||||
import { getLocalStorage, setLocalStorage } from './cacheService';
|
import { getLocalStorage, setLocalStorage } from './cacheService';
|
||||||
import qs from 'qs';
|
import qs from 'qs';
|
||||||
|
import { clearUserStorage } from '@/common/server/user'
|
||||||
class request {
|
class request {
|
||||||
/**
|
/**
|
||||||
* 生成唯一的nonce值
|
* 生成唯一的nonce值
|
||||||
|
|
@ -139,6 +140,10 @@ class request {
|
||||||
success: res => {
|
success: res => {
|
||||||
const endDate = Date.now();
|
const endDate = Date.now();
|
||||||
console.log(requestUrl, "请求消耗时间", endDate - startDate);
|
console.log(requestUrl, "请求消耗时间", endDate - startDate);
|
||||||
|
if (res.data.code == 14007) {
|
||||||
|
//登录失效
|
||||||
|
clearUserStorage();
|
||||||
|
}
|
||||||
resolve(res.data);
|
resolve(res.data);
|
||||||
},
|
},
|
||||||
fail: e => {
|
fail: e => {
|
||||||
|
|
|
||||||
|
|
@ -1,3 +1,4 @@
|
||||||
|
import { forEach } from "lodash";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 延迟执行
|
* 延迟执行
|
||||||
|
|
@ -139,6 +140,81 @@ export function hideLoading() {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 请求订阅消息
|
||||||
|
* @param {Array} tmplIds 模板ID数组
|
||||||
|
* @returns {Promise} 返回Promise对象,resolve中返回订阅结果对象
|
||||||
|
*/
|
||||||
|
export function requestSubscribeMessage(tmplIds) {
|
||||||
|
return new Promise((resolve) => {
|
||||||
|
uni.requestSubscribeMessage({
|
||||||
|
tmplIds: tmplIds || [],
|
||||||
|
success(res) {
|
||||||
|
console.log('订阅消息授权结果:', res);
|
||||||
|
// if(res[''])
|
||||||
|
var data = {};
|
||||||
|
for (let i = 0; i < tmplIds.length; i++) {
|
||||||
|
if (res[tmplIds[i]] != null && res[tmplIds[i]] == "accept") {
|
||||||
|
data[tmplIds[i]] = true;
|
||||||
|
} else {
|
||||||
|
data[tmplIds[i]] = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
console.log("订阅消息授权结果:", data);
|
||||||
|
|
||||||
|
resolve({
|
||||||
|
success: true,
|
||||||
|
result: data
|
||||||
|
});
|
||||||
|
},
|
||||||
|
fail(err) {
|
||||||
|
console.error('订阅消息授权失败:', err);
|
||||||
|
resolve({
|
||||||
|
success: false,
|
||||||
|
result: [],
|
||||||
|
error: err
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 微信支付
|
||||||
|
* @param {Object} orderInfo 支付订单信息对象
|
||||||
|
* @param {String} orderInfo.appid 微信开放平台应用AppId
|
||||||
|
* @param {String} orderInfo.noncestr 随机字符串
|
||||||
|
* @param {String} orderInfo.package 固定值 "Sign=WXPay"
|
||||||
|
* @param {String} orderInfo.partnerid 微信支付商户号
|
||||||
|
* @param {String} orderInfo.prepayid 统一下单订单号
|
||||||
|
* @param {Number} orderInfo.timestamp 时间戳(单位:秒)
|
||||||
|
* @param {String} orderInfo.sign 签名
|
||||||
|
* @returns {Promise} 返回Promise对象,resolve中返回支付结果对象
|
||||||
|
*/
|
||||||
|
export function requestPayment(orderInfo) {
|
||||||
|
return new Promise((resolve) => {
|
||||||
|
uni.requestPayment({
|
||||||
|
provider: "weixin",
|
||||||
|
...orderInfo,
|
||||||
|
success(res) {
|
||||||
|
console.log('微信支付成功:', res);
|
||||||
|
resolve({
|
||||||
|
success: true,
|
||||||
|
result: res
|
||||||
|
});
|
||||||
|
},
|
||||||
|
fail(err) {
|
||||||
|
console.error('微信支付失败:', err);
|
||||||
|
resolve({
|
||||||
|
success: false,
|
||||||
|
result: null,
|
||||||
|
error: err
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
let os = '';
|
let os = '';
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
|
|
|
||||||
|
|
@ -209,19 +209,20 @@ const getGenderText = (genderLimit) => {
|
||||||
|
|
||||||
// 处理加入组局
|
// 处理加入组局
|
||||||
const handleJoin = () => {
|
const handleJoin = () => {
|
||||||
// 触发父组件的加入事件
|
// 触发父组件的加入事件 reservationData.value
|
||||||
emit('join', reservationData.value)
|
console.log("reservationData.value", reservationData.value);
|
||||||
|
|
||||||
}
|
}
|
||||||
const cancelJoin = async () => {
|
const cancelJoin = async () => {
|
||||||
var res = await showModalConfirm('提示', '确定要取消组局吗?')
|
var res = await showModalConfirm('提示', '确定要取消组局吗?')
|
||||||
if (res) {
|
if (res) {
|
||||||
emit('cancelJoin', reservationData.value)
|
console.log("reservationData.value", reservationData.value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const exitJoin = async () => {
|
const exitJoin = async () => {
|
||||||
var res = await showModalConfirm('提示', '确定要退出组局吗?')
|
var res = await showModalConfirm('提示', '确定要退出组局吗?')
|
||||||
if (res) {
|
if (res) {
|
||||||
emit('exitJoin', reservationData.value)
|
console.log("reservationData.value", reservationData.value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// 打开用户信息弹窗
|
// 打开用户信息弹窗
|
||||||
|
|
@ -231,7 +232,7 @@ const openUserPop = (user) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
// 定义事件
|
// 定义事件
|
||||||
const emit = defineEmits(['join', 'openUserPop', 'cancelJoin', 'exitJoin'])
|
const emit = defineEmits(['openUserPop'])
|
||||||
|
|
||||||
// 暴露方法给父组件
|
// 暴露方法给父组件
|
||||||
defineExpose({
|
defineExpose({
|
||||||
|
|
|
||||||
|
|
@ -7,7 +7,7 @@
|
||||||
<view class="status-tag">
|
<view class="status-tag">
|
||||||
{{ statusName }}
|
{{ statusName }}
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<!-- 九宫格麻将桌 -->
|
<!-- 九宫格麻将桌 -->
|
||||||
<view class="nine-grid-container">
|
<view class="nine-grid-container">
|
||||||
<view></view>
|
<view></view>
|
||||||
|
|
@ -17,21 +17,21 @@
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
<view></view>
|
<view></view>
|
||||||
|
|
||||||
<view class="item">
|
<view class="item">
|
||||||
<view v-if="getJoinPlayerAtPosition(2)" class="item-avatar">
|
<view v-if="getJoinPlayerAtPosition(2)" class="item-avatar">
|
||||||
<image :src="getPlayerAtPosition(1)" class="avatar-img" mode="aspectFit"></image>
|
<image :src="getPlayerAtPosition(1)" class="avatar-img" mode="aspectFit"></image>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
<view></view>
|
<view></view>
|
||||||
|
|
||||||
<view class="item">
|
<view class="item">
|
||||||
<view v-if="getJoinPlayerAtPosition(3)" class="item-avatar">
|
<view v-if="getJoinPlayerAtPosition(3)" class="item-avatar">
|
||||||
<image :src="getPlayerAtPosition(2)" class="avatar-img" mode="aspectFit"></image>
|
<image :src="getPlayerAtPosition(2)" class="avatar-img" mode="aspectFit"></image>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
<view></view>
|
<view></view>
|
||||||
|
|
||||||
<view class="item">
|
<view class="item">
|
||||||
<view v-if="getJoinPlayerAtPosition(4)" class="item-avatar">
|
<view v-if="getJoinPlayerAtPosition(4)" class="item-avatar">
|
||||||
<image :src="getPlayerAtPosition(3)" class="avatar-img" mode="aspectFit"></image>
|
<image :src="getPlayerAtPosition(3)" class="avatar-img" mode="aspectFit"></image>
|
||||||
|
|
@ -40,7 +40,7 @@
|
||||||
<view></view>
|
<view></view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<!-- 信息区域 -->
|
<!-- 信息区域 -->
|
||||||
<view class="info-section">
|
<view class="info-section">
|
||||||
<view class="info-content">
|
<view class="info-content">
|
||||||
|
|
@ -68,7 +68,7 @@ const props = defineProps({
|
||||||
id: '',
|
id: '',
|
||||||
status: '',
|
status: '',
|
||||||
description: '',
|
description: '',
|
||||||
dateStr:'',
|
dateStr: '',
|
||||||
time: '',
|
time: '',
|
||||||
room: '',
|
room: '',
|
||||||
requirements: '',
|
requirements: '',
|
||||||
|
|
@ -135,7 +135,7 @@ const playerPositions = computed(() => {
|
||||||
const statusName = computed(() => {
|
const statusName = computed(() => {
|
||||||
const { status, personCount, joinPerson } = props.item
|
const { status, personCount, joinPerson } = props.item
|
||||||
const count = joinPerson.length
|
const count = joinPerson.length
|
||||||
|
|
||||||
if (status === 0) {
|
if (status === 0) {
|
||||||
return personCount === count ? "待开始" : "组局中..."
|
return personCount === count ? "待开始" : "组局中..."
|
||||||
} else if (status === 1) {
|
} else if (status === 1) {
|
||||||
|
|
@ -168,7 +168,7 @@ const getPlayerAtPosition = (position) => {
|
||||||
*/
|
*/
|
||||||
const getJoinPlayerAtPosition = (index) => {
|
const getJoinPlayerAtPosition = (index) => {
|
||||||
const personCount = props.item.personCount
|
const personCount = props.item.personCount
|
||||||
|
|
||||||
if (personCount === 2) {
|
if (personCount === 2) {
|
||||||
// 2人局:第二行左边和右边
|
// 2人局:第二行左边和右边
|
||||||
return [2, 3].includes(index)
|
return [2, 3].includes(index)
|
||||||
|
|
@ -255,7 +255,7 @@ const handleJoin = () => {
|
||||||
.status-tag {
|
.status-tag {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
left: 16rpx;
|
left: 16rpx;
|
||||||
top: 0;
|
top: 5px;
|
||||||
font-family: PingFang SC, PingFang SC;
|
font-family: PingFang SC, PingFang SC;
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
font-size: 26rpx;
|
font-size: 26rpx;
|
||||||
|
|
|
||||||
|
|
@ -10,11 +10,11 @@
|
||||||
</label-field>
|
</label-field>
|
||||||
<view :style="{ height: lineHeight }"></view>
|
<view :style="{ height: lineHeight }"></view>
|
||||||
<time-select-cell label="开始时间" icon="@@:app/static/time_start.png" @select="openUpDatesTimePicker">
|
<time-select-cell label="开始时间" icon="@@:app/static/time_start.png" @select="openUpDatesTimePicker">
|
||||||
{{ getDayDescription(startTimeStr) }}
|
{{ getDayDescription(reservationInfo.start_time * 1000) }}
|
||||||
</time-select-cell>
|
</time-select-cell>
|
||||||
<view :style="{ height: lineHeight }"></view>
|
<view :style="{ height: lineHeight }"></view>
|
||||||
<time-select-cell label="结束时间" icon="@@:app/static/time_end.png" @select="openUpDatesTimePickerEnd">
|
<time-select-cell label="结束时间" icon="@@:app/static/time_end.png" @select="openUpDatesTimePickerEnd">
|
||||||
{{ getDayDescription(endTimeStr) }}
|
{{ getDayDescription(reservationInfo.end_time * 1000) }}
|
||||||
</time-select-cell>
|
</time-select-cell>
|
||||||
<view :style="{ height: lineHeight }"></view>
|
<view :style="{ height: lineHeight }"></view>
|
||||||
<time-select-cell label="房间" @select="openRoomPicker">
|
<time-select-cell label="房间" @select="openRoomPicker">
|
||||||
|
|
@ -97,7 +97,7 @@
|
||||||
<text class="note-text">鸽子费(保证金),参与人需缴纳鸽子费。若有参与者在预约后没有赴约,其鸽子费由在场的所有人平分。组局成功或失败后鸽子费将全额返还。</text>
|
<text class="note-text">鸽子费(保证金),参与人需缴纳鸽子费。若有参与者在预约后没有赴约,其鸽子费由在场的所有人平分。组局成功或失败后鸽子费将全额返还。</text>
|
||||||
</card-container>
|
</card-container>
|
||||||
|
|
||||||
<view class="center submit-button">
|
<view class="center submit-button" @click="submitReservation">
|
||||||
<text style="margin: 20rpx; color: white;">发起预约</text>
|
<text style="margin: 20rpx; color: white;">发起预约</text>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
|
|
@ -121,12 +121,18 @@ import {
|
||||||
watch
|
watch
|
||||||
} from 'vue';
|
} from 'vue';
|
||||||
import {
|
import {
|
||||||
getConfigData
|
getConfigData, getSubscribeMessage
|
||||||
} from '@/common/server/config'
|
} from '@/common/server/config'
|
||||||
|
import { usePay } from '@/common/server/interface/user'
|
||||||
|
import {
|
||||||
|
requestSubscribeMessage,
|
||||||
|
requestPayment
|
||||||
|
} from '@/common/utils'
|
||||||
import {
|
import {
|
||||||
getDayDescription,
|
getDayDescription,
|
||||||
ceilMinuteToNext5
|
ceilMinuteToNext5
|
||||||
} from '@/common/system/timeUtile';
|
} from '@/common/system/timeUtile';
|
||||||
|
import { isLogin } from '@/common/server/user'
|
||||||
import {
|
import {
|
||||||
forEach,
|
forEach,
|
||||||
union
|
union
|
||||||
|
|
@ -139,15 +145,13 @@ import TagSelect from '@/components/com/appointment/tag-select.vue'
|
||||||
import ComAppointmentPickerData from '@/components/com/appointment/picker-data.vue'
|
import ComAppointmentPickerData from '@/components/com/appointment/picker-data.vue'
|
||||||
import ComAppointmentRadioSelect from '@/components/com/appointment/radio-select.vue'
|
import ComAppointmentRadioSelect from '@/components/com/appointment/radio-select.vue'
|
||||||
import {
|
import {
|
||||||
getReservationRoomList
|
getReservationRoomList, addSQReservation, cancelReservation
|
||||||
} from '@/common/server/interface/sq'
|
} from '@/common/server/interface/sq'
|
||||||
const _containerBase = ref(null)
|
const _containerBase = ref(null)
|
||||||
// 年龄选择器状态
|
// 年龄选择器状态
|
||||||
const agePickerVisible = ref(false)
|
const agePickerVisible = ref(false)
|
||||||
const agePickerColumns = ref([[], []])
|
const agePickerColumns = ref([[], []])
|
||||||
const agePickerDefaultIndex = ref([0, 0])
|
const agePickerDefaultIndex = ref([0, 0])
|
||||||
const startTimeStr = ref(0)
|
|
||||||
const endTimeStr = ref(0)
|
|
||||||
|
|
||||||
const lineHeight = ref("15rpx")
|
const lineHeight = ref("15rpx")
|
||||||
const timeRange = ref(["2小时", "3小时", "4小时", "自定义"])
|
const timeRange = ref(["2小时", "3小时", "4小时", "自定义"])
|
||||||
|
|
@ -157,17 +161,17 @@ const roomOptions = ref([])
|
||||||
const roomPickerRef = ref(null)
|
const roomPickerRef = ref(null)
|
||||||
//提交表单数据
|
//提交表单数据
|
||||||
const reservationInfo = ref({
|
const reservationInfo = ref({
|
||||||
room_id: 0, //房间id
|
room_id: 0, //房间id 非空
|
||||||
room_name: '请选择房间', //房间名称
|
room_name: '请选择房间', //房间名称
|
||||||
start_time: 0, //开始时间 时间戳
|
start_time: 0, //开始时间 时间戳 非空
|
||||||
end_time: 0, //结束时间 时间戳
|
end_time: 0, //结束时间 时间戳 非空
|
||||||
max_age: 0, //最大年龄
|
max_age: 0, //最大年龄 默认0
|
||||||
min_age: 0, //最小年龄
|
min_age: 0, //最小年龄 非空
|
||||||
title: '', //组局名称
|
title: '', //组局名称 非空
|
||||||
extra_info: '', //其它说明
|
extra_info: '', //其它说明 可为空
|
||||||
game_rule: '', //具体规则
|
game_rule: '', //具体规则 非空
|
||||||
game_type: '', //玩法类型
|
game_type: '', //玩法类型 非空
|
||||||
gender_limit: 0, //性别限制
|
gender_limit: 0, //性别限制
|
||||||
is_smoking: 2, //是否禁烟
|
is_smoking: 2, //是否禁烟
|
||||||
credit_limit: 0, //信誉限制
|
credit_limit: 0, //信誉限制
|
||||||
deposit_fee: 0, //鸽子费
|
deposit_fee: 0, //鸽子费
|
||||||
|
|
@ -179,14 +183,14 @@ const onTimeRangeChange = async (val) => {
|
||||||
console.log('timeRange change:', val)
|
console.log('timeRange change:', val)
|
||||||
if (val != "") {
|
if (val != "") {
|
||||||
await openUpDatesTimePicker(false);
|
await openUpDatesTimePicker(false);
|
||||||
if (startTimeStr.value > 0) {
|
if (reservationInfo.value.start_time > 0) {
|
||||||
var str = val;
|
var str = val;
|
||||||
if (str == "2小时") {
|
if (str == "2小时") {
|
||||||
endTimeStr.value = startTimeStr.value + 1000 * 60 * 60 * 2;
|
reservationInfo.value.end_time = reservationInfo.value.start_time + 2 * 60 * 60;
|
||||||
} else if (str == "3小时") {
|
} else if (str == "3小时") {
|
||||||
endTimeStr.value = startTimeStr.value + 1000 * 60 * 60 * 3;
|
reservationInfo.value.end_time = reservationInfo.value.start_time + 3 * 60 * 60;
|
||||||
} else if (str == "4小时") {
|
} else if (str == "4小时") {
|
||||||
endTimeStr.value = startTimeStr.value + 1000 * 60 * 60 * 4;
|
reservationInfo.value.end_time = reservationInfo.value.start_time + 4 * 60 * 60;
|
||||||
} else {
|
} else {
|
||||||
await openUpDatesTimePickerEnd(false);
|
await openUpDatesTimePickerEnd(false);
|
||||||
}
|
}
|
||||||
|
|
@ -198,43 +202,41 @@ const getRoomPickerName = () => {
|
||||||
}
|
}
|
||||||
|
|
||||||
const openUpDatesTimePicker = async (isManual = true) => {
|
const openUpDatesTimePicker = async (isManual = true) => {
|
||||||
var now = startTimeStr.value;
|
var now = reservationInfo.value.start_time * 1000;
|
||||||
var min = Date.now();
|
var min = Date.now();
|
||||||
min += 1000 * 60 * 30;
|
min += 1000 * 60 * 30;
|
||||||
min = ceilMinuteToNext5(min).valueOf();
|
min = ceilMinuteToNext5(min).valueOf();
|
||||||
if (startTimeStr.value == 0) {
|
if (reservationInfo.value.start_time == 0) {
|
||||||
now = Date.now();
|
now = Date.now();
|
||||||
now += 1000 * 60 * 30;
|
now += 1000 * 60 * 30;
|
||||||
now = ceilMinuteToNext5(now).valueOf();
|
now = ceilMinuteToNext5(now).valueOf();
|
||||||
}
|
}
|
||||||
const startTime = await _containerBase.value.openUpDatesTimePicker(now, min, "预约开始时间")
|
const startTime = await _containerBase.value.openUpDatesTimePicker(now, min, "预约开始时间")
|
||||||
startTimeStr.value = startTime
|
// 直接设置到表单对象,毫秒转秒
|
||||||
// 同步到表单对象,毫秒转秒
|
reservationInfo.value.start_time = Math.floor(startTime / 1000)
|
||||||
reservationInfo.value.start_time = Math.floor(startTimeStr.value / 1000)
|
// 手动选择时间则切换为"自定义"
|
||||||
// 手动选择时间则切换为“自定义”
|
|
||||||
if (isManual) {
|
if (isManual) {
|
||||||
timeRangeValue.value = "自定义"
|
timeRangeValue.value = "自定义"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const openUpDatesTimePickerEnd = async (isManual = true) => {
|
const openUpDatesTimePickerEnd = async (isManual = true) => {
|
||||||
if (startTimeStr.value == 0) {
|
if (reservationInfo.value.start_time == 0) {
|
||||||
uni.showToast({
|
uni.showToast({
|
||||||
title: '请先选择开始时间',
|
title: '请先选择开始时间',
|
||||||
icon: 'none'
|
icon: 'none'
|
||||||
})
|
})
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
var now = endTimeStr.value;
|
var now = reservationInfo.value.end_time * 1000;
|
||||||
var min = (startTimeStr.value + 1000 * 60 * 30);
|
var min = (reservationInfo.value.start_time * 1000 + 1000 * 60 * 30);
|
||||||
if (now == 0) {
|
if (now == 0) {
|
||||||
now = (startTimeStr.value + 1000 * 60 * 30);
|
now = (reservationInfo.value.start_time * 1000 + 1000 * 60 * 30);
|
||||||
}
|
}
|
||||||
//minDate+1000*60*30 最小间隔30分钟
|
//minDate+1000*60*30 最小间隔30分钟
|
||||||
const endTime = await _containerBase.value.openUpDatesTimePicker(now, min, "预约结束时间")
|
const endTime = await _containerBase.value.openUpDatesTimePicker(now, min, "预约结束时间")
|
||||||
endTimeStr.value = endTime
|
// 直接设置到表单对象,毫秒转秒
|
||||||
// 同步到表单对象,毫秒转秒
|
reservationInfo.value.end_time = Math.floor(endTime / 1000)
|
||||||
reservationInfo.value.end_time = Math.floor(endTimeStr.value / 1000)
|
// 手动选择时间则切换为"自定义"
|
||||||
// 手动选择时间则切换为“自定义”
|
|
||||||
if (isManual) {
|
if (isManual) {
|
||||||
timeRangeValue.value = "自定义"
|
timeRangeValue.value = "自定义"
|
||||||
}
|
}
|
||||||
|
|
@ -339,6 +341,8 @@ const increment = () => {
|
||||||
if (currentValue.value > 5) {
|
if (currentValue.value > 5) {
|
||||||
currentValue.value = 5
|
currentValue.value = 5
|
||||||
}
|
}
|
||||||
|
// 同步到表单对象
|
||||||
|
reservationInfo.value.credit_limit = currentValue.value
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -348,18 +352,227 @@ const decrement = () => {
|
||||||
if (currentValue.value < 0) {
|
if (currentValue.value < 0) {
|
||||||
currentValue.value = 0
|
currentValue.value = 0
|
||||||
}
|
}
|
||||||
|
// 同步到表单对象
|
||||||
|
reservationInfo.value.credit_limit = currentValue.value
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const changeLog = (e) => {
|
const changeLog = (e) => {
|
||||||
console.log('change事件:', e)
|
console.log('change事件:', e)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 当开始或结束时间变化(通过其它方式)时也自动刷新房间
|
// 表单验证方法
|
||||||
watch([startTimeStr, endTimeStr], async ([s, e]) => {
|
const validateForm = () => {
|
||||||
reservationInfo.value.start_time = s ? Math.floor(s / 1000) : 0
|
const info = reservationInfo.value
|
||||||
reservationInfo.value.end_time = e ? Math.floor(e / 1000) : 0
|
|
||||||
|
// 必填字段验证
|
||||||
|
if (!info.room_id || info.room_id === 0) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '请选择房间',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!info.start_time || info.start_time === 0) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '请选择开始时间',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!info.end_time || info.end_time === 0) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '请选择结束时间',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
if (info.end_time <= info.start_time) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '结束时间需晚于开始时间',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!info.title || info.title.trim() === '') {
|
||||||
|
uni.showToast({
|
||||||
|
title: '请输入组局名称',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!info.player_count || info.player_count === 0) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '请选择游玩人数',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!info.game_type || info.game_type === 0) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '请选择玩法类型',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!info.game_rule || info.game_rule === 0) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '请选择具体规则',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// 年龄范围验证(如果设置了年龄限制)
|
||||||
|
if (info.min_age > 0 && info.max_age > 0 && info.min_age > info.max_age) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '最小年龄不能大于最大年龄',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// 提交预约方法
|
||||||
|
const submitReservation = async () => {
|
||||||
|
var isLoginSucces = await isLogin();
|
||||||
|
if (!isLoginSucces) {
|
||||||
|
uni.navigateTo({
|
||||||
|
url: '/pages/me/login'
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// 验证表单
|
||||||
|
if (!validateForm()) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
try {
|
||||||
|
var messageId = await getSubscribeMessage(reservationInfo.value.deposit_fee);
|
||||||
|
console.log("messageId", messageId);
|
||||||
|
var subscribeMessage = await requestSubscribeMessage(messageId);
|
||||||
|
console.log("message", subscribeMessage);
|
||||||
|
|
||||||
|
// 显示加载状态
|
||||||
|
uni.showLoading({
|
||||||
|
title: '提交中...'
|
||||||
|
})
|
||||||
|
|
||||||
|
// 准备提交数据
|
||||||
|
const submitData = {
|
||||||
|
...reservationInfo.value,
|
||||||
|
// 确保信誉限制同步
|
||||||
|
credit_limit: currentValue.value,
|
||||||
|
important_data: {}
|
||||||
|
}
|
||||||
|
|
||||||
|
var resPay = null;
|
||||||
|
if (submitData.deposit_fee > 0) {
|
||||||
|
resPay = await usePay(submitData.deposit_fee);
|
||||||
|
if (resPay == null) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '鸽子费订单创建失败,请重新提交预约数据!',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
subscribeMessage.result.paymentId = resPay.paymentId;
|
||||||
|
}
|
||||||
|
console.log('提交预约数据:', submitData)
|
||||||
|
var important_data = "";
|
||||||
|
if (subscribeMessage.result != null) {
|
||||||
|
important_data = JSON.stringify(subscribeMessage.result);
|
||||||
|
}
|
||||||
|
submitData.important_data = important_data;
|
||||||
|
// TODO: 调用后端API提交预约
|
||||||
|
// 调用后端API提交预约
|
||||||
|
const result = await addSQReservation(submitData)
|
||||||
|
uni.hideLoading()
|
||||||
|
console.log("result", result);
|
||||||
|
if (!result.success) {
|
||||||
|
uni.showToast({
|
||||||
|
title: result.message,
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (submitData.deposit_fee > 0 && resPay != null) {
|
||||||
|
var payRes = await requestPayment(resPay);
|
||||||
|
if (payRes.success) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '鸽子费支付成功',
|
||||||
|
icon: 'success'
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
await cancelReservation(result.data, "鸽子费支付失败,请重新预约!");
|
||||||
|
uni.showToast({
|
||||||
|
title: '鸽子费支付失败,请重新预约!',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
console.log("payRes", payRes);
|
||||||
|
}
|
||||||
|
// 提交成功
|
||||||
|
uni.showToast({
|
||||||
|
title: '预约提交成功',
|
||||||
|
icon: 'success'
|
||||||
|
})
|
||||||
|
|
||||||
|
// 可以跳转到其他页面或重置表单
|
||||||
|
// uni.navigateBack() // 返回上一页
|
||||||
|
// 或者重置表单
|
||||||
|
resetForm()
|
||||||
|
|
||||||
|
} catch (error) {
|
||||||
|
uni.hideLoading()
|
||||||
|
console.error('提交预约失败:', error)
|
||||||
|
uni.showToast({
|
||||||
|
title: '提交失败,请重试',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 重置表单方法(可选)
|
||||||
|
const resetForm = () => {
|
||||||
|
reservationInfo.value = {
|
||||||
|
room_id: 0,
|
||||||
|
room_name: '请选择房间',
|
||||||
|
start_time: 0,
|
||||||
|
end_time: 0,
|
||||||
|
max_age: 0,
|
||||||
|
min_age: 0,
|
||||||
|
title: '',
|
||||||
|
extra_info: '',
|
||||||
|
game_rule: '',
|
||||||
|
game_type: '',
|
||||||
|
gender_limit: 0,
|
||||||
|
is_smoking: 2,
|
||||||
|
credit_limit: 0,
|
||||||
|
deposit_fee: 0,
|
||||||
|
player_count: 0,
|
||||||
|
}
|
||||||
|
currentValue.value = 0
|
||||||
|
timeRangeValue.value = ""
|
||||||
|
gameRuleRange.value = []
|
||||||
|
peopleRange.value = []
|
||||||
|
peopleText.value = "请先选择房间"
|
||||||
|
gameRuleText.value = "请先选择玩法类型"
|
||||||
|
}
|
||||||
|
|
||||||
|
// 当开始或结束时间变化时自动刷新房间
|
||||||
|
watch([() => reservationInfo.value.start_time, () => reservationInfo.value.end_time], async ([s, e]) => {
|
||||||
await tryLoadRooms()
|
await tryLoadRooms()
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
@ -412,6 +625,9 @@ onLoad(async () => {
|
||||||
gameTypeRange.value = [...config.config.playingMethodOptions];
|
gameTypeRange.value = [...config.config.playingMethodOptions];
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
onShow(async () => {
|
||||||
|
resetForm();
|
||||||
|
})
|
||||||
// 年龄列构建与显示/文案
|
// 年龄列构建与显示/文案
|
||||||
const buildAgeColumns = () => {
|
const buildAgeColumns = () => {
|
||||||
const minList = [{ value: 0, text: '不限' }]
|
const minList = [{ value: 0, text: '不限' }]
|
||||||
|
|
|
||||||
|
|
@ -38,7 +38,7 @@
|
||||||
|
|
||||||
|
|
||||||
<!-- 预约信息弹窗组件 -->
|
<!-- 预约信息弹窗组件 -->
|
||||||
<ReservationPopup ref="reservationPopup" @join="handleJoin" @openUserPop="openUserPop" />
|
<ReservationPopup ref="reservationPopup" @openUserPop="openUserPop" />
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user