Browse Source

refactor(mall): 优化订单确认页面的优惠券选择逻辑- 将 selectedCoupons 数组中的 couponId 字段改为 id 字段
- 优化了优惠券数据的处理和显示

EvilDragon 4 months ago
parent
commit
fa3986ae96

+ 14 - 11
packages/app/src/components/moment-item.vue

@@ -30,7 +30,10 @@ const { getMemberLevelLogo } = memberLevelsStore
 const dictStore = useDictStore()
 const { getOptionLabel } = dictStore
 const imgClass = ref('')
-const isVideo = ref(false)
+// const isVideo = ref(false)
+const isVideo = computed(
+  () => props.options.bannerUrls?.length && isImageOrVideo(props.options.bannerUrls[0]) === 'video',
+)
 const toDetail = () => {
   uni.navigateTo({
     url: `/pages/home/moment/index?${stringify({ id: props.options.id })}`,
@@ -55,12 +58,12 @@ onMounted(async () => {
       imgClass.value = 'w-[44vw]'
     }
   }
-  if (
-    props.options.bannerUrls?.length === 1 &&
-    isImageOrVideo(props.options.bannerUrls[0]) === 'video'
-  ) {
-    isVideo.value = true
-  }
+  // if (
+  //   props.options.bannerUrls?.length === 1 &&
+  //   isImageOrVideo(props.options.bannerUrls[0]) === 'video'
+  // ) {
+  //   isVideo.value = true
+  // }
 })
 </script>
 <template>
@@ -71,9 +74,9 @@ onMounted(async () => {
           class="overflow-hidden rounded-full"
           @click.stop="
             features.toDesignerHomePage &&
-              ['1', '2'].includes(options?.circleType) &&
-              currRoute().path !== '/pages/mine/homepage/index' &&
-              router.push(`/pages/mine/homepage/index?id=${options.stylistId}`)
+            ['1', '2'].includes(options?.circleType) &&
+            currRoute().path !== '/pages/mine/homepage/index' &&
+            router.push(`/pages/mine/homepage/index?id=${options.stylistId}`)
           "
         >
           <wd-img
@@ -157,7 +160,7 @@ onMounted(async () => {
         <!-- {{ options.spaceAddr }}·{{ options.spaceType }}·{{ options.designStyle }} -->
         {{ options.circleDesc }}
       </div>
-      <view class="my-5.5 flex flex-wrap gap-3.5">
+      <view v-if="props.options.tagName !== ''" class="my-5.5 flex flex-wrap gap-3.5">
         <template v-if="props.options.tagName !== ''">
           <template v-for="it of props.options.tagName?.split(',')" :key="it">
             <Tag>{{ it }}</Tag>

+ 22 - 0
packages/app/src/pages/home/components/moment-video.vue

@@ -0,0 +1,22 @@
+<script setup lang="ts">
+import { getCurrentInstance } from 'vue'
+
+const instance = getCurrentInstance()
+const props = withDefaults(defineProps<{ src: string; enableProgressGesture: boolean }>(), {
+  enableProgressGesture: false,
+})
+const videoRef = ref()
+const videoContext = ref<UniNamespace.VideoContext>()
+onMounted(() => {
+  videoContext.value = uni.createVideoContext('video', instance)
+})
+defineExpose({
+  videoContext,
+})
+</script>
+
+<template>
+  <video class="w-full h-full" id="video" v-bind="props"></video>
+</template>
+
+<style scoped lang="scss"></style>

+ 1 - 1
packages/app/src/pages/home/mall/confirm-order/index.vue

@@ -64,7 +64,7 @@ const handlePay = async () => {
 
   const couponList =
     selectedCoupons.value?.map((it) => ({
-      couponId: it.couponId,
+      couponId: it.id,
       projectIds: it.productIds,
       buinessId: it.buinessId,
     })) || []

+ 79 - 40
packages/app/src/pages/home/moment/index.vue

@@ -34,6 +34,8 @@ import { getRect, addUnit } from 'wot-design-uni/components/common/util'
 import Card from '@/components/card.vue'
 import { get } from 'radash'
 import { DictType } from '../../../core/libs/models'
+import MomentVideo from '@/pages/home/components/moment-video.vue'
+import {ComponentExposed} from "vue-component-type-helpers";
 
 const { features, clickByPermission } = usePermissions()
 const userStore = useUserStore()
@@ -42,11 +44,12 @@ const router = useRouter()
 const dictStore = useDictStore()
 const { getOptionLabel } = dictStore
 const id = ref()
-const currentImg = ref(0)
+const current = ref(0)
 const isShared = ref(false)
-const commeentRef = ref<InstanceType<typeof WdInput>>()
+const commentRef = ref<InstanceType<typeof WdInput>>()
 const commentItemRef = ref<InstanceType<typeof CommentItem>[]>()
 const instance = getCurrentInstance()
+const momentVideoRef = ref<ComponentExposed<typeof MomentVideo>[]>()
 
 const focus = ref(false)
 const { data, run } = useRequest(() => getCircle(id.value), { initialData: {} })
@@ -62,24 +65,25 @@ const { data: circleUpvotes, run: setCircleUpvotes } = useRequest(
   () => getCircleUpvotes(id.value),
   { initialData: { list: [], total: 0 } },
 )
-const swiperSizes = ref()
 const swiperStyle = ref()
 const reviewContent = ref('')
-const isVideo = ref(false)
 const reviewId = ref()
 const refreshIndex = ref<number>()
-const handleChange = ({ detail: { current } }) => {
-	// console.log(current)
-	currentImg.value = current;
-  // swiperStyle.value = {
-  //   height: swiperSizes.value[current].height + 'px',
-  // }
+const isVideo = computed(
+  () => data.value?.bannerUrls?.length && isImageOrVideo(data.value.bannerUrls.at(0)) === 'video',
+)
+const handleChange = ({ detail }) => {
+  console.log('current', current.value, detail.current)
+  console.log(momentVideoRef.value)
+  if (isVideo.value) {
+    momentVideoRef.value[current.value]?.videoContext.pause()
+  }
+  current.value = detail.current
 }
 const setSwiperStyle = async () => {
   if (!data.value.bannerUrls.length) return
   const { screenWidth } = await uni.getSystemInfo()
-  if (data.value.bannerUrls.length === 1 && isImageOrVideo(data.value.bannerUrls[0]) === 'video') {
-    isVideo.value = true
+  if (isImageOrVideo(data.value.bannerUrls[0]) === 'video') {
     return
   }
 
@@ -90,17 +94,19 @@ const setSwiperStyle = async () => {
     height:
       height > width
         ? addUnit(500)
-        : height === width?addUnit(screenWidth):addUnit(
-            screenWidth / width > 1
-              ? height / (screenWidth / width)
-              : height * (screenWidth / width),
-          ),
+        : height === width
+          ? addUnit(screenWidth)
+          : addUnit(
+              screenWidth / width > 1
+                ? height / (screenWidth / width)
+                : height * (screenWidth / width),
+            ),
   }
   console.log('swiperStyle', swiperStyle.value)
 }
 const handleSend = async () => {
   if (!reviewContent.value) {
-    uni.showToast({ title: '请输入评论内容', icon: 'none' })
+    await uni.showToast({ title: '请输入评论内容', icon: 'none' })
     return
   }
   const { code, msg } = await createCircleReview({
@@ -111,13 +117,13 @@ const handleSend = async () => {
     replayReviewId: reviewId.value,
   })
   if (code !== 0) {
-    uni.showToast({ title: msg, icon: 'none' })
+    await uni.showToast({ title: msg, icon: 'none' })
   } else {
     reviewContent.value = ''
-    uni.showToast({ title: '评论成功', icon: 'none' })
+    await uni.showToast({ title: '评论成功', icon: 'none' })
     if (refreshIndex.value) {
       console.log(instance.refs)
-      commentItemRef.value.at(refreshIndex.value).refresh()
+      await commentItemRef.value.at(refreshIndex.value).refresh()
       reviewId.value = undefined
       refreshIndex.value = undefined
     } else {
@@ -133,14 +139,14 @@ const handleReplay = async (options) => {
 }
 const handleDelete = async (index?: number) => {
   if (index !== undefined) {
-    commentItemRef.value.at(index).refresh()
+    await commentItemRef.value.at(index).refresh()
   } else {
     await runGetReviews()
   }
 }
 const handleUpvote = async (index?: number) => {
   if (index !== undefined) {
-    commentItemRef.value.at(index).refresh()
+    await commentItemRef.value.at(index).refresh()
   } else {
     await run()
   }
@@ -196,18 +202,51 @@ onShareAppMessage(async ({ from, target }) => {
     <template v-if="data.circleType === '1'">
       <template v-if="!isVideo">
         <div class="pos-relative">
-		  <div class="currentImg">{{ currentImg + 1 }}/{{data?.bannerUrls.length}}</div>	
-          <swiper :current="currentImg" :style="swiperStyle" @change="handleChange" :indicator-dots="true">
+          <div class="currentImg">{{ current + 1 }}/{{ data?.bannerUrls.length }}</div>
+          <swiper
+            :current="current"
+            :style="swiperStyle"
+            @change="handleChange"
+            :indicator-dots="true"
+          >
             <template v-for="it of data?.bannerUrls" :key="it">
               <swiper-item>
-                <wd-img width="100%" height="100%" :src="it" mode="aspectFill" :enable-preview="true"></wd-img>
+                <wd-img
+                  width="100%"
+                  height="100%"
+                  :src="it"
+                  mode="aspectFill"
+                  :enable-preview="true"
+                ></wd-img>
               </swiper-item>
             </template>
           </swiper>
         </div>
       </template>
       <template v-if="isVideo">
-        <video width="100%" class="w-full aspect-[1.64/1]" :src="data?.bannerUrls[0]"></video>
+        <div class="relative aspect-[1.64/1]">
+          <div class="currentImg">{{ current + 1 }}/{{ data?.bannerUrls.length }}</div>
+          <swiper @change="handleChange">
+            <template v-for="it of data?.bannerUrls" :key="it">
+              <swiper-item>
+                <!--                <video-->
+                <!--                  ref="momentVideo"-->
+                <!--                  width="100%"-->
+                <!--                  class="w-full aspect-[1.64/1]"-->
+                <!--                  :controls="'contimg'"-->
+                <!--                  :loop="true"-->
+                <!--                  :enable-progress-gesture="false"-->
+                <!--                  :src="it"-->
+                <!--                ></video>-->
+                <MomentVideo
+                  ref="momentVideoRef"
+                  :src="it"
+                  :enable-progress-gesture="false"
+                ></MomentVideo>
+              </swiper-item>
+            </template>
+          </swiper>
+        </div>
       </template>
     </template>
     <template v-if="data.circleType === '2'">
@@ -342,7 +381,7 @@ onShareAppMessage(async ({ from, target }) => {
       <div class="bg-white flex items-center">
         <div class="w-[168px] bg-[#f6f6f6] rounded-[60px] px-3.5 py-2 flex items-center">
           <wd-input
-            ref="commeentRef"
+            ref="commentRef"
             custom-class="bg-transparent!"
             no-border
             confirm-type="send"
@@ -405,15 +444,15 @@ onShareAppMessage(async ({ from, target }) => {
   </view>
 </template>
 <style lang="scss" scope>
-	.currentImg{
-		position:absolute;
-		z-index:2;
-		color:#fff;
-		background-color: rgba(0,0,0,.5);
-		top:10rpx;
-		right:10rpx;
-		padding:4rpx 20rpx;
-		font-size:24rpx;
-		border-radius: 8rpx;
-	}
-</style>
+.currentImg {
+  position: absolute;
+  z-index: 2;
+  color: #fff;
+  background-color: rgba(0, 0, 0, 0.5);
+  top: 10rpx;
+  right: 10rpx;
+  padding: 4rpx 20rpx;
+  font-size: 24rpx;
+  border-radius: 8rpx;
+}
+</style>

+ 43 - 22
packages/app/src/pages/mine/orders/detail/index.vue

@@ -7,14 +7,27 @@ import { cancelOrder, getPointsOrder } from '../../../../core/libs/requests'
 import BottomAppBar from '@/components/bottom-app-bar.vue'
 import dayjs from 'dayjs'
 import { requestToast } from '../../../../core/utils/common'
+import { useMessage } from 'wot-design-uni'
 
+const { confirm } = useMessage()
 const id = ref()
 const status = ref({ '0': '已报名', '1': '已完成', '2': '未核销', '3': '已取消', '4': '待交付' })
-const payTypes = ref({ 0: '积分支付', 1: '现金支付' })
-const { data, run: setData } = useRequest(() => getPointsOrder(id.value), { initialData: {} })
+const payTypes = ref({ '0': '积分支付', '1': '现金支付' })
+const { data, run: setData } = useRequest(() => getPointsOrder(id.value), {})
 const handleSubmit = async () => {
-  await requestToast(() => cancelOrder(id.value), { success: true, successTitle: '取消成功' })
-  await setData()
+  await confirm({
+    title: '是否确认取消订单?',
+    beforeConfirm: async ({ resolve }) => {
+      const { code } = await requestToast(() => cancelOrder(id.value), {
+        success: true,
+        successTitle: '取消成功',
+      })
+      if (code === 0) {
+        await setData()
+        resolve(true)
+      }
+    },
+  })
 }
 onLoad((query: { id: string }) => {
   id.value = query.id
@@ -27,7 +40,7 @@ onLoad((query: { id: string }) => {
       <div
         class="text-right text-[#ef4343] text-sm font-normal font-['PingFang_SC'] leading-normal"
       >
-        {{ status[data.orderStatus] }}
+        {{ status[data?.orderStatus] }}
       </div>
     </div>
     <div class="flex gap-4 border-b border-b-solid border-b-[#f2f2f2] pb-5">
@@ -35,54 +48,62 @@ onLoad((query: { id: string }) => {
         width="94"
         height="94"
         custom-class="rounded-2xl overflow-hidden"
-        :src="data.orderImgUrl"
+        :src="data?.orderImgUrl"
       />
       <div class="flex flex-col flex-1">
         <div class="text-black text-base font-normal font-['PingFang_SC'] leading-normal">
-          {{ data.projectName }}
+          {{ data?.projectName }}
         </div>
         <div
           class="text-start text-black/40 text-sm font-normal font-['PingFang_SC'] leading-normal"
         >
-          x{{ data.orderQuantity }}
+          x{{ data?.orderQuantity }}
         </div>
         <div class="flex-1"></div>
         <div
           class="text-start text-black/60 text-sm font-normal font-['PingFang_SC'] leading-normal"
         >
-          {{ data.points }}积分
+          {{ data?.points }}积分
         </div>
       </div>
       <div>
         <div class="text-black/40 text-sm font-normal font-['PingFang_SC'] leading-normal">
           <!-- 已完成 -->
-          {{ status[data.orderStatus] }}
+          {{ status[data?.orderStatus] }}
         </div>
       </div>
     </div>
     <SectionHeading
-      v-if="data.orderMoney"
+      v-if="data?.orderMoney"
       title="订单金额"
       size="sm"
-      :end-text="`¥ ${data.orderMoney}`"
+      :end-text="`¥ ${data?.orderMoney}`"
     ></SectionHeading>
-    <SectionHeading title="总积分" size="sm" :end-text="`${data.points}`"></SectionHeading>
-    <SectionHeading title="实际支付积分" size="sm" :end-text="`${data.payPoints}`"></SectionHeading>
-    <SectionHeading title="订单号" size="sm" :end-text="data.orderNo"></SectionHeading>
+    <SectionHeading title="总积分" size="sm" :end-text="`${data?.points ?? 0}`"></SectionHeading>
+    <SectionHeading
+      title="实际支付积分"
+      size="sm"
+      :end-text="`${data?.payPoints ?? 0}`"
+    ></SectionHeading>
+    <SectionHeading title="订单号" size="sm" :end-text="data?.orderNo"></SectionHeading>
     <SectionHeading
       title="支付时间"
       size="sm"
-      :end-text="dayjs(data.createTime).format('YYYY-MM-DD hh:mm')"
+      :end-text="dayjs(data?.createTime).format('YYYY-MM-DD HH:mm')"
+    ></SectionHeading>
+    <SectionHeading
+      title="支付方式"
+      size="sm"
+      :end-text="payTypes[String(data?.payType)]"
     ></SectionHeading>
-    <SectionHeading title="支付方式" size="sm" :end-text="payTypes[data.payType]"></SectionHeading>
-    <template v-if="data.orderStatus === '3'">
+    <template v-if="data?.orderStatus === '3'">
       <SectionHeading
         title="取消时间"
         size="sm"
-        :end-text="dayjs(data.cancelTime).format('YYYY-MM-DD hh:mm')"
+        :end-text="dayjs(data?.cancelTime).format('YYYY-MM-DD HH:mm')"
       ></SectionHeading>
-      <SectionHeading title="返还积分" size="sm" :end-text="`${data.payPoints}`"></SectionHeading>
-      <SectionHeading title="取消人" size="sm" :end-text="data.cancelUser"></SectionHeading>
+      <SectionHeading title="返还积分" size="sm" :end-text="`${data?.payPoints}`"></SectionHeading>
+      <SectionHeading title="取消人" size="sm" :end-text="data?.cancelUser"></SectionHeading>
     </template>
     <div class="flex-1"></div>
     <BottomAppBar fixed>
@@ -90,7 +111,7 @@ onLoad((query: { id: string }) => {
         <wd-button
           :round="false"
           block
-          v-if="['2', '4'].includes(data.orderStatus)"
+          v-if="['2', '4'].includes(data?.orderStatus)"
           @click="handleSubmit"
         >
           取消订单

+ 2 - 2
packages/app/src/pages/publish/moment/index.vue

@@ -137,12 +137,12 @@ onUnmounted(() => {
 })
 onLoad(async (query: { circleType: '1' | '2' }) => {
   circleType.value = query.circleType as CircleType
-  uni.setNavigationBarTitle({ title: { '1': '个人动态', '2': '设计案例' }[circleType.value] })
+  await uni.setNavigationBarTitle({ title: { '1': '个人动态', '2': '设计案例' }[circleType.value] })
   const optionsSchema = {
     designStyle: getByDictType(DictType.memberDesignStyle).then(({ data }) => data),
     spaceType: getByDictType(DictType.circleSpaceType).then(({ data }) => data),
   }
-  const res = await zipToObject(
+  const res = zipToObject(
     Object.keys(optionsSchema),
     await Promise.all(Object.values(optionsSchema)),
   )

+ 2 - 2
packages/merchant/src/pages/common/orders/detail/index.vue

@@ -72,14 +72,14 @@ onLoad((query?: Record<string | 'id', any>) => {
     <SectionHeading
       title="支付时间"
       size="sm"
-      :end-text="dayjs(data.createTime).format('YYYY-MM-DD hh:mm')"
+      :end-text="dayjs(data.createTime).format('YYYY-MM-DD HH:mm')"
     ></SectionHeading>
     <SectionHeading title="支付方式" size="sm" :end-text="payTypes[data.payType]"></SectionHeading>
     <template v-if="data.orderStatus === '3'">
       <SectionHeading
         title="取消时间"
         size="sm"
-        :end-text="dayjs(data.cancelTime).format('YYYY-MM-DD hh:mm')"
+        :end-text="dayjs(data.cancelTime).format('YYYY-MM-DD HH:mm')"
       ></SectionHeading>
       <SectionHeading title="返还积分" size="sm" :end-text="`${data.payPoints}`"></SectionHeading>
       <SectionHeading title="取消人" size="sm" :end-text="data.cancelUser"></SectionHeading>

+ 1 - 1
packages/merchant/src/pages/home/index.vue

@@ -275,7 +275,7 @@ onShareAppMessage(() => ({}))
                     <div
                       class="mt-3 text-black/30 text-xs font-normal font-['PingFang_SC'] leading-none"
                     >
-                      {{ dayjs(it.createTime).format('YYYY-MM-DD hh:mm') }}
+                      {{ dayjs(it.createTime).format('YYYY-MM-DD HH:mm') }}
                     </div>
                   </Card>
                 </template>

+ 1 - 1
packages/merchant/src/pages/mine/index.vue

@@ -116,7 +116,7 @@ onPageScroll(({ scrollTop }: { scrollTop: number }) => {
                           class="text-black/90 text-sm font-normal font-['PingFang_SC'] leading-normal"
                         >
                           支付时间:
-                          {{ dayjs(it.completeTime).format('YYYY-MM-DD hh:mm') }}
+                          {{ dayjs(it.completeTime).format('YYYY-MM-DD HH:mm') }}
                         </div>
                         <div
                           class="text-xs font-normal font-['PingFang_SC'] leading-normal"