Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
107 lines
4.0 KiB
Vue
107 lines
4.0 KiB
Vue
<template>
|
||
<view class="page">
|
||
<!-- 订单信息卡片 -->
|
||
<view class="order-card">
|
||
<text class="card-title">订单信息</text>
|
||
<view class="order-row">
|
||
<text class="label">年卡名称</text>
|
||
<text class="value">{{ cardName }}</text>
|
||
</view>
|
||
<view class="order-row">
|
||
<text class="label">有效期</text>
|
||
<text class="value">365天</text>
|
||
</view>
|
||
<view class="order-row">
|
||
<text class="label">价格</text>
|
||
<text class="value price">¥{{ price }}</text>
|
||
</view>
|
||
</view>
|
||
<!-- 支付方式 -->
|
||
<view class="pay-card">
|
||
<text class="card-title">支付方式</text>
|
||
<view class="pay-option active">
|
||
<text class="pay-icon">💳</text>
|
||
<text class="pay-name">模拟支付(测试)</text>
|
||
<text class="pay-check">✓</text>
|
||
</view>
|
||
</view>
|
||
<!-- 底部支付栏 -->
|
||
<view class="bottom-bar">
|
||
<view class="bottom-price">
|
||
<text class="label">应付金额</text>
|
||
<text class="value">¥{{ price }}</text>
|
||
</view>
|
||
<button class="btn-pay" @click="handlePay" :disabled="paying">
|
||
{{ paying ? '支付中...' : '确认支付' }}
|
||
</button>
|
||
</view>
|
||
</view>
|
||
</template>
|
||
|
||
<script setup lang="ts">
|
||
import { ref } from 'vue'
|
||
import { onLoad } from '@dcloudio/uni-app'
|
||
import { createOrder, mockPay } from '../../../../api/order'
|
||
import { showToast } from '../../../../utils'
|
||
|
||
const cardId = ref('')
|
||
const cardName = ref('')
|
||
const price = ref(0)
|
||
const paying = ref(false)
|
||
|
||
/** 页面加载时解析路由参数 */
|
||
onLoad((options) => {
|
||
cardId.value = options?.id || ''
|
||
cardName.value = decodeURIComponent(options?.name || '')
|
||
price.value = Number(options?.price || 0)
|
||
})
|
||
|
||
/** 执行支付流程 */
|
||
async function handlePay() {
|
||
if (!cardId.value) return
|
||
paying.value = true
|
||
try {
|
||
// 1. 创建订单
|
||
const order = await createOrder({ cardId: cardId.value })
|
||
// 2. 模拟支付
|
||
const payResult = await mockPay(order.id)
|
||
if (payResult.success) {
|
||
showToast('支付成功', 'success')
|
||
// 3. 支付成功后跳转激活页
|
||
setTimeout(() => {
|
||
uni.redirectTo({
|
||
url: `/packages/user/pages/card/activate?cardId=${cardId.value}&name=${encodeURIComponent(cardName.value)}`
|
||
})
|
||
}, 1500)
|
||
} else {
|
||
showToast('支付失败')
|
||
}
|
||
} catch (err: any) {
|
||
showToast(err.message || '支付失败')
|
||
} finally {
|
||
paying.value = false
|
||
}
|
||
}
|
||
</script>
|
||
|
||
<style scoped>
|
||
.page { min-height: 100vh; background: #f5f5f5; padding: 20rpx; padding-bottom: 140rpx; box-sizing: border-box; }
|
||
.order-card, .pay-card { background: #fff; border-radius: 16rpx; padding: 24rpx 30rpx; margin-bottom: 20rpx; }
|
||
.card-title { font-size: 30rpx; font-weight: bold; color: #333; display: block; margin-bottom: 20rpx; padding-bottom: 16rpx; border-bottom: 1rpx solid #f0f0f0; }
|
||
.order-row { display: flex; justify-content: space-between; align-items: center; padding: 16rpx 0; }
|
||
.label { font-size: 28rpx; color: #666; }
|
||
.value { font-size: 28rpx; color: #333; }
|
||
.value.price { color: #E74C3C; font-weight: bold; font-size: 36rpx; }
|
||
.pay-option { display: flex; align-items: center; padding: 20rpx 0; }
|
||
.pay-option.active { color: #4A90D9; }
|
||
.pay-icon { font-size: 36rpx; margin-right: 16rpx; }
|
||
.pay-name { flex: 1; font-size: 28rpx; }
|
||
.pay-check { font-size: 32rpx; color: #4A90D9; font-weight: bold; }
|
||
.bottom-bar { position: fixed; bottom: 0; left: 0; right: 0; background: #fff; display: flex; align-items: center; padding: 16rpx 30rpx; padding-bottom: calc(16rpx + env(safe-area-inset-bottom)); border-top: 1rpx solid #eee; }
|
||
.bottom-price { flex: 1; display: flex; flex-direction: column; }
|
||
.bottom-price .label { font-size: 22rpx; color: #999; }
|
||
.bottom-price .value { font-size: 40rpx; color: #E74C3C; font-weight: bold; }
|
||
.btn-pay { background: #E74C3C; color: #fff; font-size: 30rpx; padding: 20rpx 60rpx; border-radius: 44rpx; border: none; }
|
||
.btn-pay[disabled] { background: #F5A8A3; }
|
||
</style>
|