拼团功能完善

This commit is contained in:
2025-12-17 18:08:27 +08:00
parent 2fc5a428ff
commit 744f56468f
17 changed files with 2200 additions and 305 deletions

View File

@@ -0,0 +1,25 @@
<template>
<view class="u-flex box">
<text class="color-333" v-if="modelValue">modelValue</text>
<text v-else class="color-999">成团人数</text>
<view class="u-flex u-m-l-20">
<up-icon name="arrow-down" color="#999" size="14"></up-icon>
</view>
</view>
</template>
<script setup>
const modelValue=defineModel({
default:''
})
</script>
<style lang="scss">
.box{
padding: 12rpx 24rpx;
border-radius: 8rpx;
border: 2rpx solid #DDDFE6;
}
</style>

View File

@@ -6,7 +6,7 @@
left-icon-color="#fff" title-color="#fff"></up-navbar>
<view class="u-flex info u-col-center">
<image :src="imgs.map" class="map"></image>
<view class="u-line-1 u-m-l-20">这里是店铺名称</view>
<view class="u-line-1 u-m-l-20">{{shopInfo.shopName||''}}</view>
</view>
</view>
<view class="translateY20">
@@ -30,8 +30,10 @@
@click="tabs.sel=index">{{item}}</view>
</view>
<view class="u-flex" v-if="tabs.sel==0">
<up-search></up-search>
<view class="u-flex u-col-center" v-if="tabs.sel==0">
<up-search v-model="query.wareName" @search="refresh" @clear="refresh"
@custom="refresh"></up-search>
<!-- <perpoleNumber v-model="query.groupPeopleNum"></perpoleNumber> -->
</view>
<view class="u-flex orderStatus" v-if="tabs.sel==1">
<view class="orderState" :class="{'active':orders.sel==index}"
@@ -47,24 +49,24 @@
<view class="lists" v-if="tabs.sel==0">
<view class="item" v-for="(item,index) in 10" :key="index">
<view class="item" v-for="(item,index) in list" :key="index" @click="toDetail(item)">
<up-image width="218rpx" radius="16rpx" height="218rpx"></up-image>
<up-image width="218rpx" radius="16rpx" height="218rpx" :src="returnCoverImg(item)"></up-image>
<view class="u-flex-1 u-p-l-16">
<view class="u-flex u-col-center">
<text class="numbers">3人团</text>
<text class="u-line-1 font-bold u-m-l-18 name">这里是商品名称啊啊嗷嗷啊啊</text>
<text class="numbers">{{item.groupPeopleNum}}人团</text>
<text class="u-line-1 font-bold u-m-l-18 name">{{item.wareName}}</text>
</view>
<view class="members">已团9999</view>
<view class="info">
<view class="left">
<view class="">
<text class="u-font-24">拼团到手</text>
<text class="u-font-32 font-bold"> ¥333</text>
<text class="u-font-32 font-bold"> ¥{{item.groupPrice}}</text>
</view>
<view style="opacity: 0.84;">
<text class="u-font-24">原价</text>
<text class=""> ¥333</text>
<text class=""> ¥{{item.originalPrice}}</text>
</view>
</view>
<view class="right">
@@ -76,40 +78,41 @@
</view>
<view class="orders" v-else-if="tabs.sel==1">
<view class="item" v-for="(item,index) in 10" :key="index">
<view class="item" v-for="(item,index) in list" :key="index" @click="toOrderDetail(item)">
<view class="u-flex u-col-center u-row-between">
<text class="numbers">3人团</text>
<text class="status success">待成团</text>
<text class="numbers">{{1}}人团</text>
<statusVue :status="item.status"></statusVue>
</view>
<view class="u-m-t-32 u-flex">
<up-image width="154rpx" height="154rpx"></up-image>
<up-image width="154rpx" height="154rpx" :src="item.goodsImg"></up-image>
<view class="u-flex-1 u-flex u-p-l-30 u-col-center u-row-between">
<view>
<view class="">这里是商品名称</view>
<view class="u-m-t-34 price">¥999.99</view>
<view class="">{{item.wareJson.wareName}}</view>
<view class="u-m-t-34 price">¥{{item.payAmount}}</view>
</view>
<text class="u-font-40 font-bold">x1</text>
<text class="u-font-40 font-bold">x{{item.num}}</text>
</view>
</view>
<view class="u-m-t-32 info">
<view class="u-flex u-col-center">
<text class="title">可核销门店</text>
<text class="stitle">这里是店铺名称</text>
<text class="stitle">{{item.shopName}}</text>
</view>
<view class="u-flex u-m-t-32 u-col-center">
<text class="title ">门店地址</text>
<text class="stitle">这里是店铺名称</text>
<text class="stitle">{{item.shopAddress}}</text>
</view>
<view class="u-flex u-m-t-32 u-col-center">
<view class="u-flex u-m-t-32 u-col-center" v-if="showTime(item)">
<text class="title">剩余成团时间</text>
<text class="stitle price">00:39:15</text>
<text class="stitle price">{{returnTime(item)}}</text>
</view>
</view>
<view class="btns">
<view class="btn ">申请退款</view>
<view class="btn black ">邀请好友</view>
<view class="btns" v-if="showBtns(item)">
<view class="btn " @click.stop="refund(item)">申请退款</view>
<view class="btn " @click.stop="cancelRefund(item)" v-if="item.status=='退款中'">取消退款</view>
<button open-type="share" class="btn black" @click.stop="share(item)">邀请好友</button>
</view>
</view>
@@ -119,24 +122,40 @@
<script setup>
import {
reactive
} from 'vue';
wxShare
} from '@/utils/share.js'
import {
getRemainingHMS
} from '@/utils/countdown.js'
import {
onShow
} from '@dcloudio/uni-app'
import * as Api from '@/common/api/order/gbOrder.js'
import perpoleNumber from './components/perpole-number.vue'
import statusVue from '@/groupBuying/components/status.vue'
import {
computed,
reactive,
watch
} from 'vue'
const imgs = {
bg: 'https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/1/d21f2dfd7bec44618f2d5e4b88372b08.png',
bg1: 'https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/1/604c3f917daa41af9239145196c6d3f3.png',
map: 'https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/1/0a293f6e1a6a4e7b956379a5b6701104.png',
pin: 'https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/1/a9a4f8f59a6d4a46abf91141df3531fb.png'
pin: 'https://cashier-oss.oss-cn-beijing.aliyuncs.com/upload/3/4bcce5bdfa074f2a838a0209fac24241.png'
}
const shopInfo = ref(uni.cache.get('shopInfo'))
const steps = ['发起拼团', '邀请好友', '成团优惠']
const topStyle = {
backgroundImage: 'url(' + imgs.bg + ')'
}
const tabs = reactive({
list: ['正在进行中', '我的拼团'],
sel: 1
list: ['活动列表', '我的拼团'],
sel: 0
})
const orders = reactive({
list: [{
@@ -145,23 +164,215 @@
},
{
name: '待成团',
value: ''
value: '待成团'
},
{
name: '待核销',
value: ''
value: '待核销'
},
{
name: '已核销',
value: ''
value: '已核销'
},
{
name: '退款',
value: ''
value: '退款'
},
],
sel: 0
})
const query = reactive({
page: 1,
size: 10,
wareName: '',
groupPeopleNum: '',
shopId: uni.cache.get('shopId'),
})
const list = ref([])
const isEnd = ref(false)
const status = computed(() => {
return orders.list[orders.sel].value
})
watch(() => status.value, () => {
refresh()
})
function getData() {
if (tabs.sel == 0) {
Api.warePage(query).then(res => {
const newArr = res.records || []
if (query.page == 1) {
list.value = newArr
} else {
list.value.push(...newArr)
}
isEnd.value = query.page >= res.totalPage * 1 ? true : false
})
return
}
if (tabs.sel == 1) {
const {
page,
size,
shopId
} = query
Api.record({
page,
size,
shopId,
status: status.value,
}).then(res => {
const newArr = (res.records || []).map(v => {
const wareJson = JSON.parse(v.wareJson)
wareJson.wareImgs = wareJson.wareImgs.split(',').filter(v => v)
return {
...v,
goodsImg: wareJson.wareImgs[0],
wareJson,
}
})
if (query.page == 1) {
list.value = newArr
} else {
list.value.push(...newArr)
}
console.log(list.value)
isEnd.value = query.page >= res.totalPage * 1 ? true : false
})
return
}
}
function toDetail(item) {
uni.navigateTo({
url: '/groupBuying/goodsDetail/goodsDetail?wareId=' + item.id + '&shopId=' + item.shopId
})
}
function toOrderDetail(item) {
uni.navigateTo({
url: '/groupBuying/detail/index?detailId=' + item.id + '&shopId=' + item.shopId
})
}
function returnCoverImg(item) {
if (!item.wareImgs) {
return ''
}
const arr = item.wareImgs.split(',')
return arr[0]
}
function refresh() {
query.page = 1
isEnd.value = false
getData()
}
function refund(item) {
uni.showModal({
title: '提示',
content: '是否申请退款?',
showCancel: true,
success(res) {
if (res.confirm) {
Api.applyRefund({
recordId: item.id,
orderNo: item.orderNo,
}).then(res => {
if (res) {
uni.showToast({
title: '申请成功'
})
setTimeout(() => {
refresh()
}, 1000)
}
})
}
}
})
}
function camcelRefund(item) {
uni.showModal({
title: '提示',
content: '是否取消退款?',
showCancel: true,
success(res) {
if (res.confirm) {
Api.cancelRefund({
recordId: item.id,
orderNo: item.orderNo,
}).then(res => {
if (res) {
uni.showToast({
title: '取消成功'
})
setTimeout(() => {
refresh()
}, 1000)
}
})
}
}
})
}
watch(() => tabs.sel, (newval) => {
orders.sel = 0
refresh()
})
function showBtns(item) {
if (item.status == '已退款') {
return false
}
return true
}
function showTime(item) {
if (item.status == '已退款') {
return false
}
return true
}
let shareItem = null
function share(item) {
shareItem = item
}
onShareAppMessage(() => {
console.log('onShareAppMessage')
return wxShare({
title: shareItem.wareJson.wareName,
imageUrl: shareItem.goodsImg,
path:'/groupBuying/goodsDetail/goodsDetail',
query: `wareId=${shareItem.wareId}&shopId=${shareItem.shopId}`,
})
})
onLoad(getData)
let timer = null
let nowTime = ref(Date.now())
timer = setInterval(() => {
nowTime.value = Date.now()
}, 1000)
function returnTime(item) {
nowTime.value
return getRemainingHMS(item)
}
</script>
<style lang="scss" scoped>
@@ -188,9 +399,11 @@
gap: 20rpx;
border-radius: 14rpx 14rpx 0 0;
background: linear-gradient(90deg, #FFF5E6 0%, #FFD2CA 100%);
align-items: center;
.step {
display: flex;
align-items: center;
}
.index {
@@ -343,60 +556,74 @@
font-weight: 700;
line-height: 36rpx;
}
.status{
.status {
padding: 8rpx 18rpx;
border-radius: 8rpx;
border: 2rpx solid transparent;
&.success{
&.success {
border-color: rgba(123, 209, 54, 1);
color: rgba(123, 209, 54, 1);
background: rgba(123, 209, 54, 0.12);
}
&.error{
border-color:#FF1C1C;
&.error {
border-color: #FF1C1C;
color: #FF1C1C;
background: rgba(255, 28, 28, 0.18);
}
}
.price{
.price {
color: #ED5A2E;
font-weight: 700;
line-height: 36rpx;
font-size: 40rpx;
font-weight: 700;
line-height: 36rpx;
font-size: 40rpx;
}
.info{
.info {
padding: 16rpx 34rpx;
flex-direction: column;
align-items: flex-start;
border-radius: 8rpx;
background: #F8F8F8;
.title{
.title {
min-width: 208rpx;
padding-right: 8rpx;
box-sizing: border-box;
}
.stitle{
.stitle {
color: #666;
&.price{
font-size: 32rpx;
color: #ed5a2e;
font-weight: 700;
&.price {
font-size: 32rpx;
color: #ed5a2e;
font-weight: 700;
}
}
}
.btns{
.btns {
margin-top: 28rpx;
display: flex;
justify-content: flex-end;
gap: 34rpx;
.btn{
padding: 8rpx 14rpx;
.btn {
line-height: 1;
margin: 0;
padding: 12rpx 14rpx;
border-radius: 10rpx;
border: 2rpx solid #D9D9D9;
background: #FFF;
&.black{
border-color:#343030 ;
font-size: 28rpx;
&.black {
border-color: #343030;
background-color: #343030;
color: #fff;
}
@@ -404,5 +631,4 @@
}
}
}
</style>