新增:余额支付、微信支付、下单确认功能

This commit is contained in:
2025-07-26 12:33:45 +08:00
parent 7d255a2d3c
commit 469e020df5
13 changed files with 664 additions and 72 deletions

View File

@@ -1,6 +1,6 @@
import {useEffect, useState} from "react";
import {Image, Button, Cell, CellGroup, Input, TextArea, Space} from '@nutui/nutui-react-taro'
import {Location} from '@nutui/icons-react-taro'
import {Image, Button, Cell, CellGroup, Input, Space, ActionSheet} from '@nutui/nutui-react-taro'
import {Location, ArrowRight} from '@nutui/icons-react-taro'
import Taro from '@tarojs/taro'
import {ShopGoods} from "@/api/shop/shopGoods/model";
import {getShopGoods} from "@/api/shop/shopGoods";
@@ -8,18 +8,138 @@ import {View} from '@tarojs/components';
import {listShopUserAddress} from "@/api/shop/shopUserAddress";
import {ShopUserAddress} from "@/api/shop/shopUserAddress/model";
import './index.scss'
import Gap from "@/components/Gap";
import {TenantId} from "@/config/app";
import {payByBalance, selectPayment} from "@/api/system/payment";
import {Payment} from "@/api/system/payment/model";
const OrderConfirm = () => {
const [goods, setGoods] = useState<ShopGoods | null>(null);
const [address, setAddress] = useState<ShopUserAddress>()
const [payments, setPayments] = useState<any[]>([])
const [payment, setPayment] = useState<Payment>()
const [isVisible, setIsVisible] = useState<boolean>(false)
const router = Taro.getCurrentInstance().router;
const goodsId = router?.params?.goodsId;
const reload = async () => {
// 默认收货地址
const address = await listShopUserAddress({isDefault: true});
if(address.length > 0){
if (address.length > 0) {
setAddress(address[0])
}
// 支付方式
const paymentList = await selectPayment({});
if (paymentList && paymentList.length > 0) {
setPayments(paymentList?.map((d, _) => {
return {
type: d.type,
name: d.name,
description: d.comments
}
}))
setPayment(paymentList[0])
}
}
const handleSelect = (item: any) => {
setPayment(payments.find(payment => payment.name === item.name))
setIsVisible(false)
}
const onPay = async (goods: ShopGoods) => {
// 支付方式
if (payment?.type == 0) {
await onBalancePay(goods)
}
if (payment?.type == 1) {
await onWxPay(goods)
}
}
const onBalancePay = async (goods: ShopGoods) => {
Taro.showLoading({title: '支付中...'})
payByBalance({
payType: goods.type,
payPrice: goods.price,
totalPrice: goods.price,
userId: Taro.getStorageSync('UserId'),
tenantId: Number(TenantId)
}).then().finally(() => {
Taro.showToast({
title: '支付成功',
icon: 'success',
duration: 2000
})
Taro.hideLoading()
setTimeout(() => {
// Taro.switchTab({url: '/pages/order/order'})
}, 2000)
}).catch(() => {
Taro.hideLoading()
})
}
const onWxPay = async (goods: ShopGoods) => {
Taro.showLoading({title: '支付中...'})
Taro.request({
// url: 'https://cms-api.websoft.top/api/shop/shop-order',
url: 'http://127.0.0.1:9200/api/shop/shop-order',
method: 'POST',
header: {
'content-type': 'application/json',
'Authorization': Taro.getStorageSync('access_token'),
TenantId
},
data: {
totalPrice: goods.price,
payPrice: goods.price,
tenantId: TenantId,
payType: goods.type,
comments: goods.name,
name: goods.name
},
success: function (res) {
Taro.hideLoading()
const data = res.data.data
console.log(data, 'payInfo')
// Taro.showToast({
// title: '下单成功',
// })
//
// setTimeout(() => {
// Taro.switchTab({
// url: '/pages/order/order'
// })
// }, 1000);
// return false;
if (data) {
Taro.requestPayment({
timeStamp: data.timeStamp,
nonceStr: data.nonceStr,
package: data.package,
signType: data.signType,
paySign: data.paySign,
success: function (res) {
if (res.errMsg == "requestPayment:ok") {
console.log('购买成功')
}
},
fail: function (res) {
console.log(res)
}
})
}
},
fail: function (msg) {
console.log('支付失败')
Taro.hideLoading()
Taro.showToast({
title: `${msg}`,
icon: 'error'
})
}
})
}
useEffect(() => {
@@ -42,11 +162,18 @@ const OrderConfirm = () => {
<CellGroup>
{
address && (
<Cell>
<Cell className={'address-bottom-line'} onClick={() => Taro.navigateTo({url: '/user/address/index'})}>
<Space>
<Location/>
<View></View>
<View>{address.fullAddress}</View>
<View className={'flex flex-col w-full justify-between items-start'}>
<Space className={'flex flex-row w-full font-medium'}>
<View className={'flex-wrap text-nowrap whitespace-nowrap'}></View>
<View style={{width: '64%'}}
className={'line-clamp-1 relative'}>{address.province} {address.city} {address.region} {address.address}
</View>
</Space>
<View className={'pt-1 pb-3 text-gray-500'}>{address.name} {address.phone}</View>
</View>
</Space>
</Cell>
)
@@ -62,40 +189,72 @@ const OrderConfirm = () => {
</CellGroup>
<CellGroup>
<Cell>
<div className={'flex items-center'}>
<Image src={goods.image} width="80" height="80" lazyLoad={false}/>
<div className={'ml-2'}>
<div className={'text-sm font-bold'}>{goods.name}</div>
<div className={'text-red-500 text-lg'}>{goods.price}</div>
</div>
<Cell key={goods.goodsId}>
<Space>
<Image src={goods.image} mode={'aspectFill'} style={{
width: '80px',
height: '80px',
}} lazyLoad={false}/>
<View className={'flex flex-col'}>
<View className={'font-medium w-full'}>{goods.name}</View>
<View className={'number text-gray-400 text-sm py-2'}>80g/</View>
<Space className={'flex justify-start items-center'}>
<View className={'text-red-500'}>{goods.price}</View>
<View className={'text-gray-500 text-sm'}>x 1</View>
</Space>
</View>
</Space>
</Cell>
</CellGroup>
<CellGroup>
<Cell title={`商品总价共1件`} extra={<View className={'font-medium'}>{'¥' + goods.price}</View>}/>
{/*<Cell title={'优惠券'} extra={(*/}
{/* <View className={'flex justify-between items-center'}>*/}
{/* <View className={'text-red-500 text-sm mr-1'}>-¥0.00</View>*/}
{/* <ArrowRight className={'text-gray-400'} size={14}/>*/}
{/* </View>*/}
{/*)}/>*/}
{/*<Cell title={'配送费'} extra={'¥' + 10}/>*/}
<Cell title={'订单备注'} extra={(
<Input placeholder={'选填,请先和商家协商一致'} style={{padding: '0'}}/>
)}/>
</CellGroup>
<CellGroup>
<Cell
title={'支付方式'}
extra={(
<View className={'flex items-center gap-2'}>
<View className={'text-gray-900'}>{payment?.name}</View>
<ArrowRight className={'text-gray-400'} size={14}/>
</View>
)}
onClick={() => setIsVisible(true)}
/>
</CellGroup>
<ActionSheet
visible={isVisible}
options={payments}
onSelect={handleSelect}
onCancel={() => setIsVisible(false)}
/>
<Gap height={50}/>
<div className={'fixed z-50 bg-white w-full bottom-0 left-0 pt-4 pb-10'} style={{
boxShadow: '0 -2px 4px 0 rgba(0,0,0,0.10)'
}}>
<View className={'btn-bar flex justify-between items-center'}>
<div className={'flex justify-center items-center mx-4'}>
<span className={'total-price text-sm text-gray-500'}></span>
<span className={'text-red-500 text-xl font-bold'}>{goods.price}</span>
</div>
</Cell>
</CellGroup>
<CellGroup title="收货信息">
<Cell title="收货人">
<Input placeholder="请输入收货人姓名"/>
</Cell>
<Cell title="手机号">
<Input placeholder="请输入手机号" type="tel"/>
</Cell>
<Cell title="收货地址">
<TextArea placeholder="请输入详细收货地址"/>
</Cell>
</CellGroup>
<CellGroup title="订单备注">
<Cell>
<TextArea placeholder="请输入订单备注"/>
</Cell>
</CellGroup>
<div className={'fixed-bottom'}>
<div className={'total-price'}>
<span className={'text-red-500 text-xl font-bold'}>{goods.price}</span>
</div>
<Button type="primary" size="large" className={'submit-btn'}></Button>
<div className={'buy-btn mx-4'}>
<Button type="success" size="large" onClick={() => onPay(goods)}></Button>
</div>
</View>
</div>
</div>
);