547 lines
14 KiB
Vue
547 lines
14 KiB
Vue
<template>
|
||
<scroll-view scroll-y>
|
||
<view class='content'>
|
||
<view class='c-flex-row'>
|
||
<view class='tab c-flex-row' :class='{"tab-active": tabIndex === 0}' @click.stop='tabIndex=0'>
|
||
<image :src='assetsUrl("ic_order_dd.png")' />
|
||
<text>到店</text>
|
||
</view>
|
||
<view class='tab c-flex-row' :class='{"tab-active": tabIndex === 1}' @click.stop='tabIndex=1'>
|
||
<image :src='assetsUrl("ic_order_yj.png")' />
|
||
<text>邮寄</text>
|
||
</view>
|
||
</view>
|
||
|
||
<view v-show='tabIndex==1' class='address-view c-flex-column'
|
||
@click.stop='goPath("/pages/mine/subs/address/index")'>
|
||
|
||
<view v-if='deliveryAddress?.addrid'>
|
||
<view class='user-info c-flex-row'>
|
||
<text class='status' v-if='deliveryAddress?.defaultstatus==1'>默认</text>
|
||
<text>{{ deliveryAddress?.name }}</text>
|
||
<text>{{ deliveryAddress?.mobile }}</text>
|
||
<view style='flex: 1' />
|
||
<image :src='assetsUrl("ic_arrow_right_gray.png")' />
|
||
</view>
|
||
|
||
<view class='addr c-flex-row'>
|
||
<image :src='assetsUrl("ic_location.png")' />
|
||
<text>{{ deliveryAddress?.addr }}</text>
|
||
</view>
|
||
</view>
|
||
<view v-else class='user-info c-flex-row'>
|
||
<text style='flex: 1'>请选择收货地址</text>
|
||
<image :src='assetsUrl("ic_arrow_right_gray.png")' />
|
||
</view>
|
||
<image class='dashed-line' :src='assetsUrl("ic_address_dashed_line.png")' />
|
||
</view>
|
||
|
||
<view class='goods-info-view c-flex-column'>
|
||
<view class='c-flex-row' style='margin-bottom: 20rpx' v-for='(item,index) in orderBean?.orderGoods'
|
||
:key='index'>
|
||
<image class='goods-image' :src='item.images||defaultImage' />
|
||
<view class='c-flex-column' style='flex: 1;'>
|
||
<view class='c-flex-row'>
|
||
<text class='goods-name'>{{ item.name || '未知' }}</text>
|
||
</view>
|
||
<text style='color: #999999;margin-top: 30rpx'>
|
||
{{ item.code }}
|
||
</text>
|
||
<view class='bottom-sku-view c-flex-row'>
|
||
<text>
|
||
{{ item.checkedStock.colorName||'均色' }},{{ item.checkedStock.sizeName||'均码' }} x{{ item.checkedStock.count }}
|
||
</text>
|
||
<text>¥{{ item.price }}</text>
|
||
</view>
|
||
</view>
|
||
</view>
|
||
<view class='divider' />
|
||
|
||
<view class='remark-view c-flex-row'>
|
||
<text>备注</text>
|
||
<input placeholder='请填写订单备注' @input='orderBean!.remark = $event.detail.value' />
|
||
</view>
|
||
</view>
|
||
|
||
<view class='card-view'>
|
||
<view class='c-flex-row'>
|
||
<text class='card-view-title'>商品总价</text>
|
||
<text class='card-view-value'>¥{{ orderBean?.totalPrice || 0 }}</text>
|
||
</view>
|
||
<view class='c-flex-row' style='display: none'>
|
||
<text class='card-view-title'>运费</text>
|
||
<text class='card-view-value'>¥0</text>
|
||
</view>
|
||
<view class='c-flex-row' @click.stop='showCouponDialog'>
|
||
<text class='card-view-title'>优惠券
|
||
<text style='font-size: 22rpx;color: #F32B2B;'>已选最大优惠</text>
|
||
</text>
|
||
<view class='card-view-value' style='color: #F32B2B;margin: 0'>-¥{{ checkedCoupon?.reduce || 0 }}
|
||
<image :src='assetsUrl("ic_arrow_right_gray.png")' />
|
||
</view>
|
||
</view>
|
||
<view class='divider' />
|
||
<view class='c-flex-row'>
|
||
<view style='flex: 1' />
|
||
<view class='c-flex-row'>
|
||
<text class='card-view-value'>共1件商品 合计:
|
||
<text style='font-size: 34rpx;color:#F32B2B'>¥{{ totalPrice || 0 }}</text>
|
||
</text>
|
||
</view>
|
||
</view>
|
||
</view>
|
||
|
||
<view class='payment-way c-flex-row' @click.stop='changePayment'>
|
||
<text>支付方式</text>
|
||
<view>{{ paymentType === 0 ? '微信支付' : '余额' }}
|
||
<image style='display: none' :src='assetsUrl("ic_arrow_right_gray.png")' />
|
||
</view>
|
||
</view>
|
||
|
||
<view class='bottom-view c-flex-row'>
|
||
<text>合计</text>
|
||
<text>¥{{ totalPrice || 0 }}</text>
|
||
<sqb-pay @navigateTo='navigateTo'
|
||
:return_url='buildSqbParams.return_url'
|
||
:total_amount='buildSqbParams.total_amount'
|
||
:terminal_sn='buildSqbParams.terminal_sn'
|
||
:client_sn='buildSqbParams.client_sn'
|
||
:subject='buildSqbParams.subject'
|
||
:subject_img='buildSqbParams.subject_img '
|
||
:merchant_name='buildSqbParams.merchant_name'
|
||
:notify_url='buildSqbParams.notify_url'
|
||
:sign='buildSqbParams.sign'>
|
||
<button class='confirm-order' @click='createOrder'>确认订单</button>
|
||
</sqb-pay>
|
||
</view>
|
||
</view>
|
||
</scroll-view>
|
||
<payment-dialog ref='paymentDialogRef' @change='args => paymentType=args' />
|
||
<coupon-dialog ref='couponDialogRef' @confirm='confirmCoupon' :order-price='orderBean?.totalPrice' />
|
||
</template>
|
||
|
||
<script lang='ts' setup>
|
||
import { assetsUrl, defaultImage } from '@/utils/assets';
|
||
import PaymentDialog from '@/components/payment-dialog.vue';
|
||
import CouponDialog from '@/pages/mall/subs/components/coupon-dialog.vue';
|
||
import { goPath, parseParameter, showToast, sortASCII } from '@/utils';
|
||
import { hexMD5 } from '@/utils/common/md5';
|
||
import { getPaymentList, orderCreate, overPayment } from '@/api/order';
|
||
import { CouponBean } from '@/api/user/types';
|
||
import { OrderBean } from '@/api/order/types';
|
||
import { useUserStore } from '@/store';
|
||
import { handlePayResult } from '@/utils/order';
|
||
import useShoppingCartStore from '@/store/modules/shoppingcart';
|
||
|
||
const userStore = useUserStore();
|
||
const { userInfo, terminalInfo, deliveryAddress } = storeToRefs(userStore);
|
||
const shoppingCartStore = useShoppingCartStore();
|
||
|
||
const couponDialogRef = ref();
|
||
const paymentDialogRef = ref();
|
||
const paymentType = ref(0);
|
||
const tabIndex = ref(0);
|
||
|
||
const checkedCoupon = ref<CouponBean>();
|
||
|
||
const orderBean = ref<OrderBean>();
|
||
|
||
onLoad((e) => {
|
||
orderBean.value = JSON.parse(decodeURIComponent(e?.orderBean));
|
||
createOrder();
|
||
});
|
||
|
||
const totalPrice = computed(() => {
|
||
return (orderBean?.value?.totalPrice || 0) - (checkedCoupon.value?.reduce || 0);
|
||
});
|
||
|
||
const buildSqbParams = computed(() => {
|
||
const params = sortASCII({
|
||
client_sn: orderBean.value?.id || '',
|
||
return_url: '/pages/common/payresult/index',
|
||
total_amount: Number(((totalPrice.value || 0) * 100).toFixed(2)),
|
||
terminal_sn: terminalInfo.value.terminalSn,
|
||
subject: orderBean?.value?.orderGoods[0].name||'未知',
|
||
subject_img: orderBean?.value?.orderGoods[0].images || '',
|
||
merchant_name: terminalInfo.value.companyName,
|
||
notify_url: 'https://www.baidu.com'
|
||
}, true);
|
||
|
||
return {
|
||
...params,
|
||
sign: hexMD5(parseParameter(params) + '&key=' + terminalInfo.value.terminalKey).toUpperCase()
|
||
};
|
||
});
|
||
|
||
const changePayment = () => {
|
||
// paymentDialogRef.value.show();
|
||
};
|
||
|
||
const showCouponDialog = () => {
|
||
couponDialogRef.value.show();
|
||
};
|
||
|
||
const confirmCoupon = (item: CouponBean) => {
|
||
checkedCoupon.value = item;
|
||
createOrder();
|
||
};
|
||
const navigateTo = (e: any) => {
|
||
handlePayResult(orderBean.value?.id, e, {
|
||
onSuccess: () => {
|
||
console.log('pay success');
|
||
payment();
|
||
},
|
||
onFailure: () => {
|
||
console.error('pay onFailure');
|
||
if(orderBean.value?.id) {
|
||
orderBean.value.id = '';
|
||
}
|
||
createOrder();
|
||
}
|
||
});
|
||
};
|
||
|
||
const createOrder = async () => {
|
||
|
||
//邮寄
|
||
if(tabIndex.value == 1 && !deliveryAddress.value.addrid) {
|
||
showToast('请选择收货地址');
|
||
return;
|
||
}
|
||
const params = {
|
||
// 'discount': 0,
|
||
// 'freePrice': 0,
|
||
'reducePrice': checkedCoupon.value == undefined ? 0 : checkedCoupon.value?.reduce,
|
||
'totalPrice': totalPrice.value,
|
||
// 'integral': 0,
|
||
// 'allowIntegral': 0,
|
||
// 'produceIntegralNumber': 0,
|
||
'couponIds': checkedCoupon.value?.id,
|
||
'remark': orderBean.value?.remark,
|
||
'address': tabIndex.value == 0 ? undefined : JSON.stringify(deliveryAddress.value),
|
||
'orderGoods': orderBean?.value?.orderGoods?.map(item => (
|
||
{
|
||
'goodsId': item.id,
|
||
'goodsCode': item.code,
|
||
'goodsNum': item.checkedStock.count,
|
||
'stockId': item.checkedStock.stockId,
|
||
'originPrice': item.price,
|
||
// 'consumePrice': item.price * ((userInfo.value?.levelEntity?.discount || 0) / 100),
|
||
'consumePrice': item.consumePrice,
|
||
'discount': userInfo.value?.levelEntity?.discount || 0
|
||
// 'discountOriginPrice': 0,
|
||
// 'produceIntegral': 0,
|
||
// 'priceModify': [0],
|
||
// 'offset': 0
|
||
}
|
||
))
|
||
};
|
||
|
||
if(orderBean.value?.id == undefined || orderBean.value?.id == '') {
|
||
await uni.showLoading();
|
||
const result = await orderCreate(params);
|
||
orderBean.value!.id = result.id;
|
||
uni.hideLoading();
|
||
}
|
||
|
||
//删除购物车已存在商品
|
||
orderBean?.value?.orderGoods?.forEach(item => {
|
||
const index = shoppingCartStore.getSameGoodsIndex(item.id, item.checkedStock.colorId, item.checkedStock.sizeId);
|
||
if(index >= 0) {
|
||
shoppingCartStore.delete(index);
|
||
}
|
||
});
|
||
};
|
||
|
||
const payment = async () => {
|
||
await uni.showLoading();
|
||
const paymentList = await getPaymentList(orderBean.value?.id || '');
|
||
const paymentParams = {
|
||
orderId: orderBean?.value?.id,
|
||
produceIntegralNumber: Math.round((orderBean?.value?.totalPrice || 0) + (orderBean?.value?.useGold || 0)),
|
||
transactionPrice: orderBean?.value?.totalPrice,
|
||
useGold: orderBean.value?.useGold || 0,
|
||
detailBos: [{
|
||
integralNumber: Math.floor(orderBean?.value?.totalPrice || 0),
|
||
onlinePayResult: '',
|
||
payName: '收钱吧',
|
||
payTypeId: paymentList.find((res: any) => res.type === 'ShouQianBa')?.id,
|
||
transactionPrice: Number(orderBean?.value?.totalPrice)
|
||
}]
|
||
};
|
||
await overPayment(paymentParams);
|
||
showToast('支付成功', {
|
||
icon: 'success',
|
||
complete: () => {
|
||
uni.navigateBack();
|
||
uni.hideLoading();
|
||
}
|
||
});
|
||
};
|
||
</script>
|
||
|
||
<style lang='scss' scoped>
|
||
.content {
|
||
padding: 20rpx 30rpx 200rpx 30rpx;
|
||
}
|
||
|
||
.tab {
|
||
height: 63rpx;
|
||
background: #E8E8E8;
|
||
border-radius: 10rpx 0 10rpx 0;
|
||
align-items: center;
|
||
justify-content: center;
|
||
margin-top: 17rpx;
|
||
flex: 1;
|
||
|
||
text {
|
||
font-weight: bold;
|
||
font-size: 30rpx;
|
||
color: #333333;
|
||
margin-left: 10rpx;
|
||
}
|
||
}
|
||
|
||
.tab:nth-of-type(1) {
|
||
border-radius: 10rpx 0 0 0;
|
||
}
|
||
|
||
.tab:nth-of-type(2) {
|
||
border-radius: 0 10rpx 0 0;
|
||
}
|
||
|
||
.tab-active {
|
||
background: #FFFFFF;
|
||
}
|
||
|
||
.tab:nth-of-type(1) image {
|
||
width: 42rpx;
|
||
height: 42rpx;
|
||
}
|
||
|
||
.tab:nth-of-type(2) image {
|
||
width: 38rpx;
|
||
height: 29rpx;
|
||
}
|
||
|
||
.address-view {
|
||
padding-top: 38rpx;
|
||
background: #FFFFFF;
|
||
|
||
.user-info {
|
||
margin-left: 20rpx;
|
||
margin-right: 20rpx;
|
||
|
||
.status {
|
||
padding: 2rpx 10rpx;
|
||
font-size: 24rpx;
|
||
color: #F32B2B;
|
||
border-radius: 5rpx;
|
||
border: 1rpx solid #F32B2B;
|
||
margin-right: 12rpx;
|
||
}
|
||
|
||
text:nth-of-type(n+2) {
|
||
font-weight: bold;
|
||
font-size: 30rpx;
|
||
color: #333333;
|
||
margin-left: 10rpx;
|
||
}
|
||
|
||
image {
|
||
width: 8rpx;
|
||
height: 16rpx;
|
||
}
|
||
}
|
||
|
||
.addr {
|
||
margin-top: 15rpx;
|
||
margin-left: 20rpx;
|
||
|
||
image {
|
||
width: 30rpx;
|
||
height: 37rpx;
|
||
}
|
||
|
||
text {
|
||
font-weight: 400;
|
||
font-size: 26rpx;
|
||
color: #999999;
|
||
margin-left: 16rpx;
|
||
}
|
||
}
|
||
|
||
.dashed-line {
|
||
width: 100%;
|
||
height: 8rpx;
|
||
margin-top: 37rpx;
|
||
}
|
||
}
|
||
|
||
.goods-info-view {
|
||
display: flex;
|
||
position: relative;
|
||
background: #FFFFFF;
|
||
margin-top: 20rpx;
|
||
border-radius: 10rpx;
|
||
padding: 30rpx 20rpx;
|
||
|
||
.goods-image {
|
||
width: 180rpx;
|
||
height: 180rpx;
|
||
border-radius: 10rpx;
|
||
margin-right: 20rpx;
|
||
}
|
||
|
||
.goods-name {
|
||
font-size: 30rpx;
|
||
font-weight: 400;
|
||
-webkit-line-clamp: 2;
|
||
text-overflow: ellipsis;
|
||
overflow: hidden;
|
||
margin-right: 20rpx;
|
||
color: #333333;
|
||
flex: 1;
|
||
}
|
||
|
||
.bottom-sku-view {
|
||
display: flex;
|
||
justify-content: space-between;
|
||
margin-top: 10rpx;
|
||
|
||
text:nth-of-type(1) {
|
||
font-size: 26rpx;
|
||
font-weight: 400;
|
||
flex: 1;
|
||
color: #999999;
|
||
}
|
||
|
||
text:nth-of-type(2) {
|
||
font-size: 30rpx;
|
||
color: #333333;
|
||
font-weight: bold;
|
||
margin-right: 5rpx;
|
||
}
|
||
|
||
text:nth-of-type(3) {
|
||
font-size: 34rpx;
|
||
color: #333333;
|
||
font-weight: bold;
|
||
}
|
||
}
|
||
|
||
.divider {
|
||
margin: 30rpx 0;
|
||
}
|
||
|
||
.remark-view {
|
||
text {
|
||
font-weight: 400;
|
||
font-size: 28rpx;
|
||
color: #333333;
|
||
flex: 1;
|
||
}
|
||
|
||
input {
|
||
min-width: 200rpx;
|
||
font-weight: 400;
|
||
text-align: right;
|
||
font-size: 28rpx;
|
||
color: #333333;
|
||
z-index: 0;
|
||
}
|
||
}
|
||
}
|
||
|
||
.card-view {
|
||
margin-top: 20rpx;
|
||
padding: 0 25rpx 0 23rpx;
|
||
|
||
view:not(.divider):nth-of-type(n+1) {
|
||
margin: 20rpx 0;
|
||
|
||
.card-view-title {
|
||
font-weight: 400;
|
||
font-size: 30rpx;
|
||
color: #333333;
|
||
flex: 1;
|
||
}
|
||
|
||
.card-view-value {
|
||
font-weight: 400;
|
||
font-size: 26rpx;
|
||
color: #333333;
|
||
|
||
image {
|
||
width: 8rpx;
|
||
height: 16rpx;
|
||
margin-left: 16rpx;
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
.payment-way {
|
||
background: #FFFFFF;
|
||
border-radius: 10rpx;
|
||
padding: 22rpx 23rpx;
|
||
margin-top: 20rpx;
|
||
|
||
text:nth-of-type(1) {
|
||
font-weight: bold;
|
||
font-size: 30rpx;
|
||
color: #333333;
|
||
flex: 1;
|
||
}
|
||
|
||
view:nth-of-type(1) {
|
||
font-weight: 400;
|
||
font-size: 28rpx;
|
||
color: #333333;
|
||
|
||
image {
|
||
width: 8rpx;
|
||
height: 16rpx;
|
||
margin-left: 13rpx;
|
||
}
|
||
}
|
||
}
|
||
|
||
.bottom-view {
|
||
background: #FFFFFF;
|
||
position: fixed;
|
||
bottom: 0;
|
||
left: 0;
|
||
right: 0;
|
||
padding: 20rpx 30rpx 78rpx 30rpx;
|
||
|
||
text:nth-of-type(1) {
|
||
font-weight: 400;
|
||
font-size: 30rpx;
|
||
color: #333333;
|
||
}
|
||
|
||
text:nth-of-type(2) {
|
||
font-weight: bold;
|
||
font-size: 36rpx;
|
||
color: #F32B2B;
|
||
margin-left: 14rpx;
|
||
flex: 1;
|
||
}
|
||
|
||
sqb-pay .confirm-order {
|
||
display: flex;
|
||
padding: 0 45rpx;
|
||
height: 80rpx;
|
||
border: 2rpx solid #F32B2B;
|
||
font-weight: bold;
|
||
font-size: 30rpx;
|
||
color: #F32B2B;
|
||
align-items: center;
|
||
justify-content: center;
|
||
background: #FFFFFF;
|
||
border-radius: 40rpx;
|
||
}
|
||
}
|
||
</style>
|