Files
h5-meike/pages/ticket/ordersure.vue
T
jacobxu666andClaude Opus 4.8 77e5cb9510 feat: 全站 UI 按 Minimalist Modern 重设计,新增返回悬浮钮
- 设计令牌层:mm-* CSS 变量与工具类、uView 换肤、优设标题黑字体
- 九个页面全部重写为新风格(列表/详情/下单/出行人/订单/支付成功/登录)
- 补齐 H5 运行时缺失的基础样式(uni-view/scroll-view/toast/swiper 等,App.vue 全局)
- 修复:详情头图轮播、预订须知弹层滚动、出行人数量按购买数限制、订单详情去箭头
- 新增 gmy-back-touch 返回悬浮钮,除首页外全页接入,点击返回上一页

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-08-05 12:48:45 +08:00

988 lines
23 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 v-if="skuObj" class="page mm-page">
<gmy-back-touch></gmy-back-touch>
<!-- xuchao: 商品与日期/时段/数量选择卡 -->
<view class="sec mm-card mm-fade-up">
<view class="sku__name">{{skuObj.sku.skuName}}</view>
<view class="sku__age">适用年龄:{{skuObj.sku.typeInfo}}</view>
<view class="divider"></view>
<view class="label">使用日期</view>
<view class="dates">
<view v-for="(item,index) in cList" :key="index" v-if="index<3"
:class="['date', item.isSelect?'date--on':'', (!item.isEnabled&&!item.isSelect)?'date--off':'']"
@click="selectDate(item)">
{{getDayName(item.enableDate)}}<br />
{{formatToMonthDay(item.enableDate)}}
<view class="date__tag">{{item.isSelect?'√':item.isEnabled?'可订':'不可订'}}</view>
</view>
<view class="date date--more" @tap="show=true">更多<br />日期
<u-icon name="arrow-right" color="#64748B" size="22"></u-icon>
</view>
</view>
<template v-if="!skuObj.sku.stockDateType">
<view class="label">适用时段</view>
<view class="slots">
<view :class="['slot', item.isSelect?'slot--on':'']" v-for="(item,index) in timeSlotList"
:key="index" @click="selectSlot(index)">{{item.name}}
<view class="slot__tag">余{{item.stock}}张</view>
</view>
</view>
</template>
<view class="divider"></view>
<!-- xuchao: 购买数量 —— 自定义步进器:数字居中,加减号点击即加减,上限取当前日期/时段库存 -->
<view class="qty">
<text class="qty__label">购买数量</text>
<view class="stepper">
<view :class="['stepper__btn', value<=1?'stepper__btn--off':'']" @click="minusNum">
<u-icon name="minus" :color="value<=1?'#CBD5E1':'#0052FF'" size="26"></u-icon>
</view>
<text class="stepper__val mm-display">{{value}}</text>
<view :class="['stepper__btn', value>=getMaxStock()?'stepper__btn--off':'']" @click="plusNum">
<u-icon name="plus" :color="value>=getMaxStock()?'#CBD5E1':'#0052FF'" size="26"></u-icon>
</view>
</view>
</view>
</view>
<!-- xuchao: 游客信息卡(需实名入园时) -->
<view class="sec mm-card mm-fade-up" v-if="skuObj.sku.enterDemand=='2'">
<view class="sec__head">
<view class="mm-sec-title">游客信息</view>
<view class="sec__hint">需要 <text class="sec__hint-num">{{value}}位</text> 出行游客信息,用于入园身份验证</view>
</view>
<view class="persons">
<view class="p_on mm-grad" v-for="(item,index) in personList" :key="index">{{item.name}}</view>
<view class="p_add" @tap="addPerson">新增/更换
<u-icon name="arrow-right" color="#64748B" size="20"></u-icon>
</view>
</view>
<view class="p_row" v-for="(item,index) in personList" :key="index">
<view class="p_row__del" @click="deletePerson(index)">
<u-icon name="close-circle" color="#CBD5E1" size="36"></u-icon>
</view>
<text class="p_row__label">游客{{index+1}}</text>
<view class="p_row__info">
<view class="p_row__name">{{item.name}}</view>
<view class="p_row__id">{{item.identityNo}}</view>
</view>
</view>
<view class="c_row">
<text class="c_row__label">联系手机</text>
<text class="c_row__val">{{createInfo.mobile}}</text>
</view>
</view>
<!-- xuchao: 联系人信息卡(无需实名时) -->
<view class="sec mm-card mm-fade-up" v-else>
<view class="mm-sec-title">联系人信息</view>
<view class="c_row">
<text class="c_row__label">联系人</text>
<input class="c_row__input" :adjust-position="false" type="text" v-model="createInfo.contactName"
placeholder="请输入联系人姓名" placeholder-class="mm-ph" />
</view>
<view class="c_row">
<text class="c_row__label">手机号</text>
<text class="c_row__val">{{createInfo.mobile}}</text>
</view>
</view>
<!-- xuchao: 更多日期日历(选中色随主题) -->
<u-calendar v-model="show" :mode="mode" activeBgColor="#0052FF" :calendarList="calendarList"
@change="change"></u-calendar>
<!-- xuchao: 底部结算栏 —— 总价 + 明细 + 立即购买 -->
<view class="bar">
<view class="bar__sum">
<view class="bar__label">总价</view>
<view class="bar__price" @tap="show1=true">
<text class="bar__cur">¥</text>
<text class="bar__num mm-display mm-grad-text">{{salesPriceSum}}</text>
<view class="bar__detail">明细
<u-icon name="arrow-down-fill" color="#0052FF" size="20"></u-icon>
</view>
</view>
</view>
<view class="bar__buy mm-grad" @tap="buy">立即购买</view>
</view>
<!-- xuchao: 费用明细弹层 -->
<u-popup v-model="show1" border-radius="20" mode="bottom">
<view class="pp mm-safe-bottom">
<view class="mm-sec-title">费用明细</view>
<view class="pp__sub">景区/场馆</view>
<view class="pp__row">
<text class="pp__row-label">门票</text>
<text class="pp__row-val">¥{{salesPrice}} x{{value}}</text>
</view>
<view class="pp__total">
<text class="pp__total-label">总价</text>
<view class="pp__total-price">
<text class="pp__total-cur">¥</text>
<text class="pp__total-num mm-display mm-grad-text">{{salesPriceSum}}</text>
</view>
</view>
<view class="mm-btn" @click="show1=false">确定</view>
</view>
</u-popup>
</view>
</template>
<script>
// xuchao: 确认订单页 —— 支付统一走 common/pay.js 支付层
import pay from '@/common/pay.js'
var that = ''
import gmyBackTouch from "@/components/gmy-back-touch/gmy-back-touch.vue"
export default {
components: {
'gmy-back-touch': gmyBackTouch
},
data() {
return {
show1: false,
show: false,
mode: 'date',
sf: `**** **** **** *1918`,
mz: `李富贵`,
value: 1,
hday: '',
whday: '',
skuObj: '',
calendarList: [],
mobile: '',
personList: [],
objInfo: '',
createInfo: {
"ticketsId": 0,
"skuId": 0,
"buyNum": 0,
"calendarId": 0,
"timeSlot": 0,
"touristIdList": [],
"contactMobile": "",
"contactName": "",
"price": "",
"orderSource": "Channel_XGH",
"mobile": ""
}
}
},
computed: {
salesPrice() {
let price = 0
if (this.skuObj) {
if (this.skuObj.sku.stockDateType) {
this.calendarList.forEach(item => {
if (item.isSelect) {
price = (item.salePrice / 100).toFixed(2)
}
})
} else {
this.timeSlotList.forEach(item => {
if (item.isSelect) {
price = (item.salePrice / 100).toFixed(2)
}
})
}
}
return price
},
salesPriceSum() {
let priceSum = 0
if (this.skuObj) {
if (this.skuObj.sku.stockDateType) {
this.calendarList.forEach(item => {
if (item.isSelect) {
priceSum = (item.salePrice * this.value / 100).toFixed(2)
}
})
} else {
this.timeSlotList.forEach(item => {
if (item.isSelect) {
priceSum = (item.salePrice * this.value / 100).toFixed(2)
}
})
}
}
return priceSum
},
cList() {
let arr = []
console.log(this.calendarList,12312);
if (this.calendarList.length != 0) {
this.calendarList.forEach((item, index) => {
if (item.isSelect && index < 3) {
if(this.calendarList.length==1){
arr.push(this.calendarList[0])
}else if(this.calendarList.length==2){
arr.push(this.calendarList[0])
arr.push(this.calendarList[1])
}else if(this.calendarList.length>=3){
arr.push(this.calendarList[0])
arr.push(this.calendarList[1])
arr.push(this.calendarList[2])
}
} else if (item.isSelect && index >= 3) {
arr.push(this.calendarList[0])
arr.push(this.calendarList[1])
arr.push(item)
}
})
}
console.log(arr);
return arr
},
timeSlotList() {
let arr = []
if (this.calendarList.length != 0) {
this.calendarList.forEach((item, index) => {
if (item.isSelect) {
arr = item.timeSlotList
}
})
if (arr) {
arr.forEach((item1, index1) => {
if (index1 == 0) {
this.$set(item1, 'isSelect', true)
} else {
this.$set(item1, 'isSelect', false)
}
})
}
}
return arr
}
},
onLoad() {
that = this
this.createInfo.mobile = uni.getStorageSync('phone')
this.createInfo.contactMobile = uni.getStorageSync('phone')
this.skuObj = uni.getStorageSync('scenicDetail')
this.createInfo.ticketsId = this.skuObj.tickets.id
this.createInfo.skuId = this.skuObj.sku.id
if (this.skuObj.sku.stockDateType) {
for (var i = 0; i < this.skuObj.calendarList.length; i++) {
this.skuObj.calendarList[i].enableDate = this.formatDateTime(this.skuObj.calendarList[i].enableDate)
if (this.skuObj.sku.bookType == 1) {
if (i == 0) {
this.$set(this.skuObj.calendarList[i], 'isSelect', true)
} else {
this.$set(this.skuObj.calendarList[i], 'isSelect', false)
}
} else {
if (i == 1) {
this.$set(this.skuObj.calendarList[i], 'isSelect', true)
this.skuObj.calendarList[0].isEnabled = false
} else {
this.$set(this.skuObj.calendarList[i], 'isSelect', false)
}
}
this.calendarList.push(this.skuObj.calendarList[i])
}
} else {
for (var i = 0; i < this.skuObj.timeSlotData.length; i++) {
this.$set(this.skuObj.timeSlotData[i], 'isEnabled', true)
this.$set(this.skuObj.timeSlotData[i], 'enableDate', this.formatDateTime(this.skuObj.timeSlotData[i]
.date))
if (this.skuObj.sku.bookType == 1) {
if (i == 0) {
this.$set(this.skuObj.timeSlotData[i], 'isSelect', true)
} else {
this.$set(this.skuObj.timeSlotData[i], 'isSelect', false)
}
} else {
if (i == 1) {
this.$set(this.skuObj.timeSlotData[i], 'isSelect', true)
this.skuObj.timeSlotData[0].isEnabled = false
} else {
this.$set(this.skuObj.timeSlotData[i], 'isSelect', false)
}
}
this.calendarList.push(this.skuObj.timeSlotData[i])
}
}
console.log(this.calendarList);
},
onShow() {
var pages = getCurrentPages();
var prevPage = pages[pages.length - 1];
if (prevPage.objitem != undefined) {
that.isshow = true
that.personList = JSON.parse(prevPage.objitem);
}
},
methods: {
formatDateTime(isoString) {
// const date = new Date(isoString);
// const year = date.getFullYear();
// const month = String(date.getMonth() + 1).padStart(2, '0');
// const day = String(date.getDate()).padStart(2, '0');
// const hours = String(date.getHours()).padStart(2, '0');
// const minutes = String(date.getMinutes()).padStart(2, '0');
// const seconds = String(date.getSeconds()).padStart(2, '0');
return isoString.replace(/-/g, "/");;
},
getMaxStock() {
let stock = 0
if (this.skuObj.sku.stockNumType) {
stock = 99999
} else {
if (this.skuObj.sku.stockDateType) {
this.calendarList.forEach(item => {
if (item.isSelect) {
stock = item.stock
}
})
} else {
this.timeSlotList.forEach(item => {
if (item.isSelect) {
stock = item.stock
}
})
}
}
return stock
},
deletePerson(e) {
this.personList.splice(e, 1)
},
selectDate(e) {
if (e.isEnabled) {
this.cList.forEach(item => {
if (item.enableDate == e.enableDate) {
item.isSelect = true
} else {
item.isSelect = false
}
})
}
this.value = 1
},
selectSlot(e) {
this.timeSlotList.forEach((item, index) => {
if (e == index) {
this.timeSlotList[index].isSelect = true
} else {
this.timeSlotList[index].isSelect = false
}
})
this.value = 1
},
formatToMonthDay(dateStr) {
const date = new Date(dateStr)
const month = (date.getMonth() + 1).toString().padStart(2, '0');
const day = date.getDate().toString().padStart(2, '0');
return `${month}月${day}日`;
},
// xuchao: 数量步进 —— 减到下限 1 为止,加到当前库存上限并提示
minusNum() {
if (this.value > 1) this.value--
},
plusNum() {
if (this.value < this.getMaxStock()) {
this.value++
} else {
uni.showToast({
icon: 'none',
title: '库存不足了',
duration: 1500
})
}
},
change(e) {
this.calendarList.forEach((item, index) => {
if (new Date(item.enableDate).getTime() == new Date(e.result + ' 00:00:00').getTime()) {
item.isSelect = true
} else {
item.isSelect = false
}
})
this.value = 1
},
formatDateToMMDD(dateStr) {
const [year, month, day] = dateStr.split('-');
return `${month.padStart(2, '0')}月${day.padStart(2, '0')}日`;
},
buy() {
// uni.showModal({
// title: '提示',
// content: '预订人同一证件号1天内,最多可购买1份,当前超限制的证件号尾号为0514',
// showCancel: false
// })
if (this.skuObj.sku.enterDemand == '2') {
if (this.value > this.personList.length) {
uni.showToast({
icon: 'none',
title: '还需填写' + (this.value - this.personList.length) + '位游客信息',
duration: 2000
});
return
}
// xuchao: 出行人多于购买数量也拦截(如先选多人后减量),提示移除多余位
if (this.personList.length > this.value) {
uni.showToast({
icon: 'none',
title: '只需' + this.value + '位出行人,请移除多余' + (this.personList.length - this.value) + '位',
duration: 2000
});
return
}
} else {
if (this.createInfo.contactName == '') {
uni.showToast({
icon: 'none',
title: '请填写联系人姓名',
duration: 2000
});
return
}
}
this.createInfo.buyNum = this.value
if (this.skuObj.sku.stockDateType) {
this.createInfo.calendarId = this.cList.filter(item => {
return item.isSelect
})[0].id
} else {
this.createInfo.timeSlot = this.timeSlotList.filter(item => {
return item.isSelect
})[0].id
}
this.createInfo.price = this.salesPriceSum
this.createInfo.touristIdList = this.personList.map(item => {
return item.id
})
console.log(this.createInfo);
this.$u.api.createTicketsOrder(this.createInfo).then(res => {
if (res.errcode == 0) {
// xuchao: 支付层 —— 开发模式模拟成功,正式模式唤起微信支付
pay.pay(this, {
orderId: res.data,
onSuccess: () => {
uni.redirectTo({
url: 'paysuccess?id=' + res.data
})
},
onFail: () => {
uni.showToast({
icon: 'none',
title: '支付未完成,可在订单中继续支付',
duration: 2000
})
setTimeout(() => {
uni.redirectTo({
url: 'orderlist'
})
}, 1500)
}
})
}
})
},
addPerson() {
uni.navigateTo({
url: 'select?value=' + this.value
})
},
getFormattedDate(offset = 0) {
const date = new Date();
date.setDate(date.getDate() + offset);
const month = (date.getMonth() + 1).toString().padStart(2, '0');
const day = date.getDate().toString().padStart(2, '0');
return `${month}月${day}日`;
},
getDayName(date) {
const today = new Date();
today.setHours(0, 0, 0, 0);
const inputDate = new Date(date);
inputDate.setHours(0, 0, 0, 0);
const diffDays = Math.round((inputDate - today) / (1000 * 60 * 60 * 24));
// 处理今天/明天/后天
if (diffDays === 0) return "今天";
if (diffDays === 1) return "明天";
if (diffDays === 2) return "后天";
// 其他日期返回星期几
const weekDays = ["星期日", "星期一", "星期二", "星期三", "星期四", "星期五", "星期六"];
return weekDays[inputDate.getDay()];
}
}
}
</script>
<style scoped lang="less">
/* xuchao: 底部预留 200rpx,避免内容被固定结算栏遮挡 */
.page {
padding: 32rpx 32rpx 200rpx;
}
.sec {
margin-top: 24rpx;
padding: 32rpx 24rpx;
&:first-child {
margin-top: 0;
}
}
.divider {
margin: 28rpx 0;
border-top: 2rpx dashed var(--mm-border);
}
.label {
font-size: 24rpx;
color: var(--mm-muted-fg);
margin-top: 4rpx;
}
/* ---------- 商品摘要 ---------- */
.sku__name {
font-size: 32rpx;
font-weight: 600;
line-height: 1.4;
color: var(--mm-fg);
}
.sku__age {
margin-top: 8rpx;
font-size: 22rpx;
color: var(--mm-muted-fg);
}
/* ---------- 日期 chips ---------- */
.dates {
display: flex;
gap: 8rpx;
margin-top: 16rpx;
}
.date {
flex: 1;
height: 170rpx;
border: 2rpx solid var(--mm-border);
border-radius: 16rpx;
background: var(--mm-card);
color: var(--mm-muted-fg);
position: relative;
font-size: 26rpx;
line-height: 1.5;
padding: 40rpx 0 0 24rpx;
box-sizing: border-box;
}
.date--off {
background: var(--mm-muted);
color: #CBD5E1;
}
.date--on {
border-color: var(--mm-accent);
background: rgba(0, 82, 255, 0.04);
color: var(--mm-accent);
}
.date__tag {
position: absolute;
top: 0;
right: 0;
height: 34rpx;
padding: 0 12rpx;
display: flex;
align-items: center;
font-size: 18rpx;
background: var(--mm-muted);
color: var(--mm-muted-fg);
border-radius: 0 14rpx 0 14rpx;
}
.date--on .date__tag {
background: var(--mm-grad);
color: #fff;
}
.date--more {
flex: none;
width: 96rpx;
padding: 0;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
font-size: 22rpx;
line-height: 1.6;
}
/* ---------- 时段 chips ---------- */
.slots {
display: flex;
flex-wrap: wrap;
gap: 12rpx;
margin-top: 16rpx;
}
.slot {
width: 210rpx;
height: 110rpx;
border: 2rpx solid var(--mm-border);
border-radius: 16rpx;
color: var(--mm-muted-fg);
font-size: 26rpx;
display: flex;
align-items: center;
justify-content: center;
position: relative;
box-sizing: border-box;
}
.slot--on {
border-color: var(--mm-accent);
background: rgba(0, 82, 255, 0.04);
color: var(--mm-accent);
}
.slot__tag {
position: absolute;
top: 0;
right: 0;
height: 34rpx;
padding: 0 12rpx;
display: flex;
align-items: center;
font-size: 18rpx;
background: var(--mm-muted);
color: var(--mm-muted-fg);
border-radius: 0 14rpx 0 14rpx;
}
.slot--on .slot__tag {
background: var(--mm-grad);
color: #fff;
}
/* ---------- 购买数量 ---------- */
.qty {
display: flex;
align-items: center;
justify-content: space-between;
}
.qty__label {
font-size: 32rpx;
font-weight: 600;
color: var(--mm-fg);
}
/* xuchao: 数量步进器 —— 两端描边按钮、中间数字居中 */
.stepper {
display: flex;
align-items: center;
}
.stepper__btn {
width: 64rpx;
height: 64rpx;
border-radius: 16rpx;
border: 2rpx solid var(--mm-border);
background: var(--mm-card);
display: flex;
align-items: center;
justify-content: center;
transition: transform 0.15s ease;
}
.stepper__btn:active {
transform: scale(0.92);
background: var(--mm-muted);
}
.stepper__btn--off {
border-color: var(--mm-muted);
background: var(--mm-muted);
}
.stepper__val {
width: 110rpx;
text-align: center;
font-size: 36rpx;
color: var(--mm-fg);
}
/* ---------- 游客/联系人 ---------- */
.sec__head {
display: flex;
align-items: flex-end;
}
.sec__hint {
margin-left: 16rpx;
font-size: 20rpx;
color: var(--mm-muted-fg);
}
.sec__hint-num {
font-size: 24rpx;
font-weight: 600;
color: var(--mm-fg);
}
.persons {
display: flex;
flex-wrap: wrap;
gap: 16rpx;
margin-top: 24rpx;
}
/* xuchao: 已选游客徽章 —— 渐变胶囊(保持原有识别度) */
.p_on {
height: 60rpx;
padding: 0 24rpx;
display: flex;
align-items: center;
border-radius: 999rpx;
color: #fff;
font-size: 26rpx;
box-shadow: var(--mm-shadow-accent);
}
.p_add {
height: 60rpx;
padding: 0 24rpx;
display: flex;
align-items: center;
gap: 4rpx;
border-radius: 999rpx;
border: 2rpx dashed var(--mm-border);
color: var(--mm-muted-fg);
font-size: 26rpx;
}
.p_row {
display: flex;
align-items: center;
padding: 24rpx 0;
border-bottom: 2rpx solid var(--mm-border);
}
.p_row__del {
flex: none;
display: flex;
align-items: center;
}
.p_row__label {
flex: none;
margin-left: 20rpx;
font-size: 26rpx;
color: var(--mm-muted-fg);
}
.p_row__info {
flex: 1;
min-width: 0;
display: flex;
flex-direction: column;
align-items: flex-end;
}
.p_row__name {
font-size: 30rpx;
font-weight: 600;
color: var(--mm-fg);
}
.p_row__id {
margin-top: 4rpx;
font-size: 22rpx;
letter-spacing: 0.04em;
color: var(--mm-muted-fg);
}
.c_row {
display: flex;
align-items: center;
padding: 24rpx 0 0;
}
.c_row__label {
flex: none;
width: 140rpx;
font-size: 28rpx;
color: var(--mm-muted-fg);
}
.c_row__val {
font-size: 28rpx;
color: var(--mm-fg);
}
.c_row__input {
flex: 1;
font-size: 28rpx;
color: var(--mm-fg);
}
/* ---------- 底部结算栏 ---------- */
.bar {
position: fixed;
left: 0;
right: 0;
margin: 0 auto;
width: 750rpx;
bottom: 0;
z-index: 99;
display: flex;
align-items: center;
background: var(--mm-card);
border-top: 2rpx solid var(--mm-border);
box-shadow: 0 -8rpx 24rpx rgba(15, 23, 42, 0.05);
padding: 16rpx 32rpx;
/* xuchao: 全面屏底部安全区 */
padding-bottom: calc(16rpx + constant(safe-area-inset-bottom));
padding-bottom: calc(16rpx + env(safe-area-inset-bottom));
}
.bar__sum {
flex: 1;
min-width: 0;
}
.bar__label {
font-size: 20rpx;
color: var(--mm-muted-fg);
}
.bar__price {
display: flex;
align-items: baseline;
gap: 16rpx;
}
.bar__cur {
font-size: 28rpx;
font-weight: 600;
color: var(--mm-accent);
}
.bar__num {
font-size: 52rpx;
line-height: 1.1;
}
.bar__detail {
display: flex;
align-items: center;
gap: 4rpx;
font-size: 22rpx;
color: var(--mm-accent);
}
.bar__buy {
flex: none;
width: 288rpx;
height: 96rpx;
border-radius: 999rpx;
display: flex;
align-items: center;
justify-content: center;
color: #fff;
font-size: 32rpx;
font-weight: 600;
box-shadow: var(--mm-shadow-accent);
transition: transform 0.15s ease;
}
.bar__buy:active {
transform: scale(0.96);
}
/* ---------- 费用明细弹层 ---------- */
.pp {
padding: 48rpx;
display: flex;
flex-direction: column;
}
.pp__sub {
margin-top: 24rpx;
font-size: 28rpx;
font-weight: 600;
color: var(--mm-fg);
}
.pp__row {
height: 88rpx;
display: flex;
align-items: center;
justify-content: space-between;
border-bottom: 2rpx dashed var(--mm-border);
}
.pp__row-label {
font-size: 26rpx;
color: var(--mm-muted-fg);
}
.pp__row-val {
font-size: 26rpx;
color: var(--mm-fg);
}
.pp__total {
display: flex;
align-items: baseline;
justify-content: flex-end;
gap: 12rpx;
margin: 24rpx 0 40rpx;
}
.pp__total-label {
font-size: 22rpx;
color: var(--mm-muted-fg);
}
.pp__total-price {
display: flex;
align-items: baseline;
}
.pp__total-cur {
font-size: 26rpx;
font-weight: 600;
color: var(--mm-accent);
}
.pp__total-num {
font-size: 44rpx;
line-height: 1;
}
</style>