Переглянути джерело

Merge branch 'develop' of https://gitee.com/yudaocode/yudao-mall-uniapp

# Conflicts:
#	pages/goods/index.vue
#	pages/order/confirm.vue
#	pages/order/detail.vue
YunaiV 8 місяців тому
батько
коміт
1aa944e18c
38 змінених файлів з 2520 додано та 2174 видалено
  1. 1 0
      package.json
  2. 22 14
      pages/activity/groupon/detail.vue
  3. 6 6
      pages/activity/groupon/order.vue
  4. 2 2
      pages/activity/index.vue
  5. 1 1
      pages/chat/components/select-popup.vue
  6. 146 130
      pages/commission/components/commission-log.vue
  7. 10 4
      pages/commission/goods.vue
  8. 2 5
      pages/commission/order.vue
  9. 1 1
      pages/commission/team.vue
  10. 454 406
      pages/commission/wallet.vue
  11. 23 10
      pages/coupon/detail.vue
  12. 16 11
      pages/coupon/list.vue
  13. 1 1
      pages/goods/comment/list.vue
  14. 31 31
      pages/goods/groupon.vue
  15. 322 286
      pages/goods/list.vue
  16. 31 30
      pages/goods/seckill.vue
  17. 1 1
      pages/index/category.vue
  18. 3 7
      pages/order/aftersale/apply.vue
  19. 317 280
      pages/order/aftersale/detail.vue
  20. 170 147
      pages/order/aftersale/list.vue
  21. 435 393
      pages/order/list.vue
  22. 5 3
      pages/pay/recharge-log.vue
  23. 12 9
      pages/pay/result.vue
  24. 213 165
      pages/user/address/edit.vue
  25. 137 124
      pages/user/address/list.vue
  26. 7 5
      pages/user/goods-collect.vue
  27. 10 8
      pages/user/goods-log.vue
  28. 8 9
      pages/user/info.vue
  29. 13 7
      pages/user/wallet/money.vue
  30. 18 13
      pages/user/wallet/score.vue
  31. 2 4
      sheep/components/s-address-item/s-address-item.vue
  32. 43 13
      sheep/components/s-goods-column/s-goods-column.vue
  33. 6 2
      sheep/components/s-layout/s-layout.vue
  34. 35 32
      sheep/components/s-select-seckill-sku/s-select-seckill-sku.vue
  35. 1 1
      sheep/platform/index.js
  36. 1 1
      sheep/router/index.js
  37. 10 8
      sheep/store/user.js
  38. 4 4
      sheep/ui/su-swiper/su-swiper.vue

+ 1 - 0
package.json

@@ -90,6 +90,7 @@
   "dependencies": {
     "dayjs": "^1.11.7",
     "lodash": "^4.17.21",
+    "lodash-es": "^4.17.21",
     "luch-request": "^3.0.8",
     "pinia": "^2.0.33",
     "pinia-plugin-persist-uni": "^1.2.0",

+ 22 - 14
pages/activity/groupon/detail.vue

@@ -1,6 +1,11 @@
 <!-- 拼团订单的详情 -->
 <template>
-  <s-layout title="拼团详情" class="detail-wrap" :navbar="state.data && !state.loading ? 'inner': 'normal'" :onShareAppMessage="shareInfo">
+  <s-layout
+    title="拼团详情"
+    class="detail-wrap"
+    :navbar="state.data && !state.loading ? 'inner' : 'normal'"
+    :onShareAppMessage="shareInfo"
+  >
     <view v-if="state.loading"></view>
     <view v-if="state.data && !state.loading">
       <!-- 团长信息 + 活动信息 -->
@@ -22,7 +27,7 @@
           priceColor="#E1212B"
           @tap="
             sheep.$router.go('/pages/goods/groupon', {
-              id: state.data.headRecord.activityId
+              id: state.data.headRecord.activityId,
             })
           "
           :style="[{ top: Number(statusBarHeight + 108) + 'rpx' }]"
@@ -71,7 +76,9 @@
           </view>
           <view class="countdown-title ss-flex" v-else>
             还差
-            <view class="num">{{ state.data.headRecord.userSize - state.data.headRecord.userCount }}人</view>
+            <view class="num"
+              >{{ state.data.headRecord.userSize - state.data.headRecord.userCount }}人</view
+            >
             拼团成功
             <view class="ss-flex countdown-time">
               <view class="countdown-h ss-flex ss-row-center">{{ endTime.h }}</view>
@@ -109,7 +116,11 @@
             </view>
           </view>
           <!-- 还有几个坑位 -->
-          <view class="default-avatar ss-m-r-24 ss-m-b-20" v-for="item in state.remainNumber" :key="item">
+          <view
+            class="default-avatar ss-m-r-24 ss-m-b-20"
+            v-for="item in state.remainNumber"
+            :key="item"
+          >
             <image
               :src="sheep.$url.static('/static/img/shop/avatar/unknown.png')"
               class="avatar-img"
@@ -154,11 +165,7 @@
         </view>
         <view v-else class="ss-flex ss-row-center">
           <view v-if="state.data.orderId">
-            <button
-              class="ss-reset-button join-btn"
-              :disabled="endTime.ms <= 0"
-              @tap="onShare"
-            >
+            <button class="ss-reset-button join-btn" :disabled="endTime.ms <= 0" @tap="onShare">
               邀请好友来拼团
             </button>
           </view>
@@ -198,8 +205,8 @@
   import { onLoad } from '@dcloudio/uni-app';
   import { useDurationTime } from '@/sheep/hooks/useGoods';
   import { showShareModal } from '@/sheep/hooks/useModal';
-  import { isEmpty } from 'lodash';
-  import CombinationApi from "@/sheep/api/promotion/combination";
+  import { isEmpty } from 'lodash-es';
+  import CombinationApi from '@/sheep/api/promotion/combination';
 
   const headerBg = sheep.$url.css('/static/img/shop/user/withdraw_bg.png');
   const statusBarHeight = sheep.$platform.device.statusBarHeight * 2;
@@ -295,7 +302,9 @@
       state.remainNumber = remainNumber > 0 ? remainNumber : 0;
 
       // 获取活动信息
-      const { data: activity } = await CombinationApi.getCombinationActivity(data.headRecord.activityId);
+      const { data: activity } = await CombinationApi.getCombinationActivity(
+        data.headRecord.activityId,
+      );
       state.activity = activity;
     } else {
       state.data = null;
@@ -316,8 +325,7 @@
   .recharge-box {
     position: relative;
     margin-bottom: 120rpx;
-    background: v-bind(headerBg) center/750rpx 100%
-        no-repeat,
+    background: v-bind(headerBg) center/750rpx 100% no-repeat,
       linear-gradient(115deg, #f44739 0%, #ff6600 100%);
     border-radius: 0 0 5% 5%;
     height: 100rpx;

+ 6 - 6
pages/activity/groupon/order.vue

@@ -24,9 +24,9 @@
         </view>
         <view class="border-bottom">
           <s-goods-item
-              :img="record.picUrl"
-              :title="record.spuName"
-              :price="record.combinationPrice"
+            :img="record.picUrl"
+            :title="record.spuName"
+            :price="record.combinationPrice"
           >
             <template #groupon>
               <view class="ss-flex">
@@ -67,8 +67,8 @@
   import { reactive } from 'vue';
   import { onLoad, onReachBottom, onPullDownRefresh } from '@dcloudio/uni-app';
   import sheep from '@/sheep';
-  import _ from 'lodash';
-  import {formatOrderColor} from "@/sheep/hooks/useGoods";
+  import _ from 'lodash-es';
+  import { formatOrderColor } from '@/sheep/hooks/useGoods';
   import { resetPagination } from '@/sheep/util';
   import CombinationApi from '@/sheep/api/promotion/combination';
 
@@ -121,7 +121,7 @@
     if (code !== 0) {
       return;
     }
-    state.pagination.list = _.concat(state.pagination.list, data.list)
+    state.pagination.list = _.concat(state.pagination.list, data.list);
     state.pagination.total = data.total;
     state.loadStatus = state.pagination.list.length < state.pagination.total ? 'more' : 'noMore';
   }

+ 2 - 2
pages/activity/index.vue

@@ -63,7 +63,7 @@
   import { reactive } from 'vue';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import sheep from '@/sheep';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import RewardActivityApi from '@/sheep/api/promotion/rewardActivity';
   import { formatRewardActivityRule } from '@/sheep/hooks/useGoods';
   import SpuApi from '@/sheep/api/product/spu';
@@ -118,7 +118,7 @@
     const { code, data } = await SpuApi.getSpuPage({
       pageNo: state.pagination.pageNo,
       pageSize: state.pagination.pageSize,
-      ...params
+      ...params,
     });
     if (code !== 0) {
       return;

+ 1 - 1
pages/chat/components/select-popup.vue

@@ -32,7 +32,7 @@
 
 <script setup>
   import { reactive, watch } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import GoodsItem from './goods.vue';
   import OrderItem from './order.vue';
   import OrderApi from '@/sheep/api/trade/order';

+ 146 - 130
pages/commission/components/commission-log.vue

@@ -1,74 +1,90 @@
 <!-- 分销首页:明细列表  -->
 <template>
-	<view class="distribution-log-wrap">
-		<view class="header-box">
-			<image class="header-bg" :src="sheep.$url.static('/static/img/shop/commission/title2.png')" />
-			<view class="ss-flex header-title">
-				<view class="title">实时动态</view>
-				<text class="cicon-forward" />
-			</view>
-		</view>
-		<scroll-view scroll-y="true" @scrolltolower="loadmore" class="scroll-box log-scroll"
-			scroll-with-animation="true">
-			<view v-if="state.pagination.list">
-				<view class="log-item-box ss-flex ss-row-between" v-for="item in state.pagination.list" :key="item.id">
-					<view class="log-item-wrap">
-						<view class="log-item ss-flex ss-ellipsis-1 ss-col-center">
-							<view class="ss-flex ss-col-center">
-								<image class="log-img" :src="sheep.$url.static('/static/img/shop/avatar/notice.png')" mode="aspectFill" />
-							</view>
-							<view class="log-text ss-ellipsis-1">
+  <view class="distribution-log-wrap">
+    <view class="header-box">
+      <image class="header-bg" :src="sheep.$url.static('/static/img/shop/commission/title2.png')" />
+      <view class="ss-flex header-title">
+        <view class="title">实时动态</view>
+        <text class="cicon-forward" />
+      </view>
+    </view>
+    <scroll-view
+      scroll-y="true"
+      @scrolltolower="loadmore"
+      class="scroll-box log-scroll"
+      scroll-with-animation="true"
+    >
+      <view v-if="state.pagination.list">
+        <view
+          class="log-item-box ss-flex ss-row-between"
+          v-for="item in state.pagination.list"
+          :key="item.id"
+        >
+          <view class="log-item-wrap">
+            <view class="log-item ss-flex ss-ellipsis-1 ss-col-center">
+              <view class="ss-flex ss-col-center">
+                <image
+                  class="log-img"
+                  :src="sheep.$url.static('/static/img/shop/avatar/notice.png')"
+                  mode="aspectFill"
+                />
+              </view>
+              <view class="log-text ss-ellipsis-1">
                 {{ item.title }} {{ fen2yuan(item.price) }} 元
               </view>
-						</view>
-					</view>
-					<text class="log-time">{{ dayjs(item.createTime).fromNow() }}</text>
-				</view>
-			</view>
-
-			<!-- 加载更多 -->
-			<uni-load-more v-if="state.pagination.total > 0" :status="state.loadStatus" color="#333333"
-				@tap="loadmore" />
-		</scroll-view>
-	</view>
+            </view>
+          </view>
+          <text class="log-time">{{ dayjs(item.createTime).fromNow() }}</text>
+        </view>
+      </view>
+
+      <!-- 加载更多 -->
+      <uni-load-more
+        v-if="state.pagination.total > 0"
+        :status="state.loadStatus"
+        color="#333333"
+        @tap="loadmore"
+      />
+    </scroll-view>
+  </view>
 </template>
 
 <script setup>
-	import sheep from '@/sheep';
-	import { reactive } from 'vue';
-	import _ from 'lodash';
-	import dayjs from 'dayjs';
+  import sheep from '@/sheep';
+  import { reactive } from 'vue';
+  import _ from 'lodash-es';
+  import dayjs from 'dayjs';
   import BrokerageApi from '@/sheep/api/trade/brokerage';
   import { fen2yuan } from '../../../sheep/hooks/useGoods';
 
-	const state = reactive({
-		loadStatus: '',
-		pagination: {
+  const state = reactive({
+    loadStatus: '',
+    pagination: {
       list: [],
       total: 0,
       pageNo: 1,
       pageSize: 1,
-		},
-	});
+    },
+  });
 
-	async function getLog() {
+  async function getLog() {
     state.loadStatus = 'loading';
     const { code, data } = await BrokerageApi.getBrokerageRecordPage({
       pageNo: state.pagination.pageNo,
-      pageSize: state.pagination.pageSize
-		});
+      pageSize: state.pagination.pageSize,
+    });
     if (code !== 0) {
       return;
     }
     state.pagination.list = _.concat(state.pagination.list, data.list);
     state.pagination.total = data.total;
     state.loadStatus = state.pagination.list.length < state.pagination.total ? 'more' : 'noMore';
-	}
+  }
 
-	getLog();
+  getLog();
 
-	// 加载更多
-	function loadmore() {
+  // 加载更多
+  function loadmore() {
     if (state.loadStatus === 'noMore') {
       return;
     }
@@ -78,88 +94,88 @@
 </script>
 
 <style lang="scss" scoped>
-	.distribution-log-wrap {
-		width: 690rpx;
-		margin: 0 auto;
-		margin-bottom: 20rpx;
-		border-radius: 12rpx;
-		z-index: 3;
-		position: relative;
-
-		.header-box {
-			width: 690rpx;
-			height: 76rpx;
-			position: relative;
-
-			.header-bg {
-				width: 690rpx;
-				height: 76rpx;
-			}
-
-			.header-title {
-				position: absolute;
-				left: 20rpx;
-				top: 24rpx;
-			}
-
-			.title {
-				font-size: 28rpx;
-				font-weight: 500;
-				color: #ffffff;
-				line-height: 30rpx;
-			}
-
-			.cicon-forward {
-				font-size: 30rpx;
-				font-weight: 400;
-				color: #ffffff;
-				line-height: 30rpx;
-			}
-		}
-
-		.log-scroll {
-			height: 600rpx;
-			background: #fdfae9;
-			padding: 10rpx 20rpx 0;
-			box-sizing: border-box;
-			border-radius: 0 0 12rpx 12rpx;
-
-			.log-item-box {
-				margin-bottom: 20rpx;
-
-				.log-time {
-					// margin-left: 30rpx;
-					text-align: right;
-					font-size: 24rpx;
-					font-family: OPPOSANS;
-					font-weight: 400;
-					color: #c4c4c4;
-				}
-			}
-
-			.loadmore-wrap {
-				// line-height: 80rpx;
-			}
-
-			.log-item {
-				// background: rgba(#ffffff, 0.2);
-				border-radius: 24rpx;
-				padding: 6rpx 20rpx 6rpx 12rpx;
-
-				.log-img {
-					width: 40rpx;
-					height: 40rpx;
-					border-radius: 50%;
-					margin-right: 10rpx;
-				}
-
-				.log-text {
-					max-width: 480rpx;
-					font-size: 24rpx;
-					font-weight: 500;
-					color: #333333;
-				}
-			}
-		}
-	}
-</style>
+  .distribution-log-wrap {
+    width: 690rpx;
+    margin: 0 auto;
+    margin-bottom: 20rpx;
+    border-radius: 12rpx;
+    z-index: 3;
+    position: relative;
+
+    .header-box {
+      width: 690rpx;
+      height: 76rpx;
+      position: relative;
+
+      .header-bg {
+        width: 690rpx;
+        height: 76rpx;
+      }
+
+      .header-title {
+        position: absolute;
+        left: 20rpx;
+        top: 24rpx;
+      }
+
+      .title {
+        font-size: 28rpx;
+        font-weight: 500;
+        color: #ffffff;
+        line-height: 30rpx;
+      }
+
+      .cicon-forward {
+        font-size: 30rpx;
+        font-weight: 400;
+        color: #ffffff;
+        line-height: 30rpx;
+      }
+    }
+
+    .log-scroll {
+      height: 600rpx;
+      background: #fdfae9;
+      padding: 10rpx 20rpx 0;
+      box-sizing: border-box;
+      border-radius: 0 0 12rpx 12rpx;
+
+      .log-item-box {
+        margin-bottom: 20rpx;
+
+        .log-time {
+          // margin-left: 30rpx;
+          text-align: right;
+          font-size: 24rpx;
+          font-family: OPPOSANS;
+          font-weight: 400;
+          color: #c4c4c4;
+        }
+      }
+
+      .loadmore-wrap {
+        // line-height: 80rpx;
+      }
+
+      .log-item {
+        // background: rgba(#ffffff, 0.2);
+        border-radius: 24rpx;
+        padding: 6rpx 20rpx 6rpx 12rpx;
+
+        .log-img {
+          width: 40rpx;
+          height: 40rpx;
+          border-radius: 50%;
+          margin-right: 10rpx;
+        }
+
+        .log-text {
+          max-width: 480rpx;
+          font-size: 24rpx;
+          font-weight: 500;
+          color: #333333;
+        }
+      }
+    }
+  }
+</style>

+ 10 - 4
pages/commission/goods.vue

@@ -14,12 +14,18 @@
       >
         <template #rightBottom>
           <view class="ss-flex ss-row-between">
-            <view class="commission-num" v-if="item.brokerageMinPrice === undefined">预计佣金:计算中</view>
-            <view class="commission-num" v-else-if="item.brokerageMinPrice === item.brokerageMaxPrice">
+            <view class="commission-num" v-if="item.brokerageMinPrice === undefined"
+              >预计佣金:计算中</view
+            >
+            <view
+              class="commission-num"
+              v-else-if="item.brokerageMinPrice === item.brokerageMaxPrice"
+            >
               预计佣金:{{ fen2yuan(item.brokerageMinPrice) }}
             </view>
             <view class="commission-num" v-else>
-              预计佣金:{{ fen2yuan(item.brokerageMinPrice) }} ~ {{ fen2yuan(item.brokerageMaxPrice) }}
+              预计佣金:{{ fen2yuan(item.brokerageMinPrice) }} ~
+              {{ fen2yuan(item.brokerageMaxPrice) }}
             </view>
             <button
               class="ss-reset-button share-btn ui-BG-Main-Gradient"
@@ -53,7 +59,7 @@
   import $share from '@/sheep/platform/share';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { reactive } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import { showShareModal } from '@/sheep/hooks/useModal';
   import SpuApi from '@/sheep/api/product/spu';
   import BrokerageApi from '@/sheep/api/trade/brokerage';

+ 2 - 5
pages/commission/order.vue

@@ -41,10 +41,7 @@
           <view class="no-box ss-flex ss-col-center ss-row-between">
             <text class="order-code">订单编号:{{ item.bizId }}</text>
             <text class="order-state">
-              {{
-                item.status === 0 ? '待结算'
-                  : item.status === 1 ? '已结算' : '已取消'
-              }}
+              {{ item.status === 0 ? '待结算' : item.status === 1 ? '已结算' : '已取消' }}
               ( 佣金 {{ fen2yuan(item.price) }} 元 )
             </text>
           </view>
@@ -77,7 +74,7 @@
   import sheep from '@/sheep';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { reactive } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import { onPageScroll } from '@dcloudio/uni-app';
   import { resetPagination } from '@/sheep/util';
   import BrokerageApi from '@/sheep/api/trade/brokerage';

+ 1 - 1
pages/commission/team.vue

@@ -235,7 +235,7 @@
   import sheep from '@/sheep';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { computed, reactive, ref } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import { onPageScroll } from '@dcloudio/uni-app';
   import BrokerageApi from '@/sheep/api/trade/brokerage';
 

+ 454 - 406
pages/commission/wallet.vue

@@ -1,196 +1,243 @@
 <!-- 分销 - 佣金明细 -->
 <template>
-	<s-layout class="wallet-wrap" title="佣金">
-		<!-- 钱包卡片 -->
-		<view class="header-box ss-flex ss-row-center ss-col-center">
-			<view class="card-box ui-BG-Main ui-Shadow-Main">
-				<view class="card-head ss-flex ss-col-center">
-					<view class="card-title ss-m-r-10">当前佣金(元)</view>
-					<view @tap="state.showMoney = !state.showMoney" class="ss-eye-icon"
-						:class="state.showMoney ? 'cicon-eye' : 'cicon-eye-off'" />
-				</view>
-				<view class="ss-flex ss-row-between ss-col-center ss-m-t-30">
-					<view class="money-num">{{ state.showMoney ? fen2yuan(state.summary.withdrawPrice || 0) : '*****' }}</view>
-					<view class="ss-flex">
-						<view class="ss-m-r-20">
-							<button class="ss-reset-button withdraw-btn" @tap="sheep.$router.go('/pages/commission/withdraw')">
-								提现
-							</button>
-						</view>
-						<button class="ss-reset-button balance-btn ss-m-l-20" @tap="state.showModal = true">
-							转余额
-						</button>
-					</view>
-				</view>
-
-				<view class="ss-flex">
-					<view class="loading-money">
-						<view class="loading-money-title">冻结佣金</view>
-						<view class="loading-money-num">
+  <s-layout class="wallet-wrap" title="佣金">
+    <!-- 钱包卡片 -->
+    <view class="header-box ss-flex ss-row-center ss-col-center">
+      <view class="card-box ui-BG-Main ui-Shadow-Main">
+        <view class="card-head ss-flex ss-col-center">
+          <view class="card-title ss-m-r-10">当前佣金(元)</view>
+          <view
+            @tap="state.showMoney = !state.showMoney"
+            class="ss-eye-icon"
+            :class="state.showMoney ? 'cicon-eye' : 'cicon-eye-off'"
+          />
+        </view>
+        <view class="ss-flex ss-row-between ss-col-center ss-m-t-30">
+          <view class="money-num">{{
+            state.showMoney ? fen2yuan(state.summary.withdrawPrice || 0) : '*****'
+          }}</view>
+          <view class="ss-flex">
+            <view class="ss-m-r-20">
+              <button
+                class="ss-reset-button withdraw-btn"
+                @tap="sheep.$router.go('/pages/commission/withdraw')"
+              >
+                提现
+              </button>
+            </view>
+            <button class="ss-reset-button balance-btn ss-m-l-20" @tap="state.showModal = true">
+              转余额
+            </button>
+          </view>
+        </view>
+
+        <view class="ss-flex">
+          <view class="loading-money">
+            <view class="loading-money-title">冻结佣金</view>
+            <view class="loading-money-num">
               {{ state.showMoney ? fen2yuan(state.summary.frozenPrice || 0) : '*****' }}
             </view>
-					</view>
-					<view class="loading-money ss-m-l-100">
-						<view class="loading-money-title">可提现佣金</view>
-						<view class="loading-money-num">
+          </view>
+          <view class="loading-money ss-m-l-100">
+            <view class="loading-money-title">可提现佣金</view>
+            <view class="loading-money-num">
               {{ state.showMoney ? fen2yuan(state.summary.brokeragePrice || 0) : '*****' }}
             </view>
-					</view>
-				</view>
-			</view>
-		</view>
-
-		<su-sticky>
-			<!-- 统计 -->
-			<view class="filter-box ss-p-x-30 ss-flex ss-col-center ss-row-between">
-				<uni-datetime-picker v-model="state.date" type="daterange" @change="onChangeTime" :end="state.today">
-					<button class="ss-reset-button date-btn">
-						<text>{{ dateFilterText }}</text>
-						<text class="cicon-drop-down ss-seldate-icon" />
-					</button>
-				</uni-datetime-picker>
-
-				<view class="total-box">
+          </view>
+        </view>
+      </view>
+    </view>
+
+    <su-sticky>
+      <!-- 统计 -->
+      <view class="filter-box ss-p-x-30 ss-flex ss-col-center ss-row-between">
+        <uni-datetime-picker
+          v-model="state.date"
+          type="daterange"
+          @change="onChangeTime"
+          :end="state.today"
+        >
+          <button class="ss-reset-button date-btn">
+            <text>{{ dateFilterText }}</text>
+            <text class="cicon-drop-down ss-seldate-icon" />
+          </button>
+        </uni-datetime-picker>
+
+        <view class="total-box">
           <!-- TODO 芋艿:这里暂时不考虑做 -->
-					<!-- <view class="ss-m-b-10">总收入¥{{ state.pagination.income.toFixed(2) }}</view> -->
-					<!-- <view>总支出¥{{ (-state.pagination.expense).toFixed(2) }}</view> -->
-				</view>
-			</view>
-			<su-tabs :list="tabMaps" @change="onChangeTab" :scrollable="false" :current="state.currentTab" />
-		</su-sticky>
-		<s-empty v-if="state.pagination.total === 0" icon="/static/data-empty.png" text="暂无数据"></s-empty>
+          <!-- <view class="ss-m-b-10">总收入¥{{ state.pagination.income.toFixed(2) }}</view> -->
+          <!-- <view>总支出¥{{ (-state.pagination.expense).toFixed(2) }}</view> -->
+        </view>
+      </view>
+      <su-tabs
+        :list="tabMaps"
+        @change="onChangeTab"
+        :scrollable="false"
+        :current="state.currentTab"
+      />
+    </su-sticky>
+    <s-empty
+      v-if="state.pagination.total === 0"
+      icon="/static/data-empty.png"
+      text="暂无数据"
+    ></s-empty>
 
     <!-- 转余额弹框 -->
-		<su-popup :show="state.showModal" type="bottom" round="20" @close="state.showModal = false" showClose>
-			<view class="ss-p-x-20 ss-p-y-30">
-				<view class="model-title ss-m-b-30 ss-m-l-20">转余额</view>
-				<view class="model-subtitle ss-m-b-100 ss-m-l-20">将您的佣金转到余额中继续消费</view>
-				<view class="input-box ss-flex ss-col-center border-bottom ss-m-b-70 ss-m-x-20">
-					<view class="unit">¥</view>
-					<uni-easyinput :inputBorder="false" class="ss-flex-1 ss-p-l-10" v-model="state.price" type="number"
-                         placeholder="请输入金额" />
-				</view>
-				<button class="ss-reset-button model-btn ui-BG-Main-Gradient ui-Shadow-Main" @tap="onConfirm">
-					确定
-				</button>
-			</view>
-		</su-popup>
-
-		<!-- 钱包记录 -->
-		<view v-if="state.pagination.total > 0">
-			<view class="wallet-list ss-flex border-bottom" v-for="item in state.pagination.list" :key="item.id">
-				<view class="list-content">
-					<view class="title-box ss-flex ss-row-between ss-m-b-20">
-						<text class="title ss-line-1">{{ item.title }}</text>
-						<view class="money">
-							<text v-if="item.price >= 0" class="add">+{{ fen2yuan(item.price) }}</text>
-							<text v-else class="minus">{{ fen2yuan(item.price) }}</text>
-						</view>
-					</view>
-					<text class="time">{{ sheep.$helper.timeFormat(item.createTime, 'yyyy-mm-dd hh:MM:ss') }}</text>
-				</view>
-			</view>
-		</view>
-
-		<!-- <u-gap></u-gap> -->
-		<uni-load-more v-if="state.pagination.total > 0" :status="state.loadStatus" :content-text="{
+    <su-popup
+      :show="state.showModal"
+      type="bottom"
+      round="20"
+      @close="state.showModal = false"
+      showClose
+    >
+      <view class="ss-p-x-20 ss-p-y-30">
+        <view class="model-title ss-m-b-30 ss-m-l-20">转余额</view>
+        <view class="model-subtitle ss-m-b-100 ss-m-l-20">将您的佣金转到余额中继续消费</view>
+        <view class="input-box ss-flex ss-col-center border-bottom ss-m-b-70 ss-m-x-20">
+          <view class="unit">¥</view>
+          <uni-easyinput
+            :inputBorder="false"
+            class="ss-flex-1 ss-p-l-10"
+            v-model="state.price"
+            type="number"
+            placeholder="请输入金额"
+          />
+        </view>
+        <button
+          class="ss-reset-button model-btn ui-BG-Main-Gradient ui-Shadow-Main"
+          @tap="onConfirm"
+        >
+          确定
+        </button>
+      </view>
+    </su-popup>
+
+    <!-- 钱包记录 -->
+    <view v-if="state.pagination.total > 0">
+      <view
+        class="wallet-list ss-flex border-bottom"
+        v-for="item in state.pagination.list"
+        :key="item.id"
+      >
+        <view class="list-content">
+          <view class="title-box ss-flex ss-row-between ss-m-b-20">
+            <text class="title ss-line-1">{{ item.title }}</text>
+            <view class="money">
+              <text v-if="item.price >= 0" class="add">+{{ fen2yuan(item.price) }}</text>
+              <text v-else class="minus">{{ fen2yuan(item.price) }}</text>
+            </view>
+          </view>
+          <text class="time">{{
+            sheep.$helper.timeFormat(item.createTime, 'yyyy-mm-dd hh:MM:ss')
+          }}</text>
+        </view>
+      </view>
+    </view>
+
+    <!-- <u-gap></u-gap> -->
+    <uni-load-more
+      v-if="state.pagination.total > 0"
+      :status="state.loadStatus"
+      :content-text="{
         contentdown: '上拉加载更多',
-      }" />
-	</s-layout>
+      }"
+    />
+  </s-layout>
 </template>
 
 <script setup>
-	import { computed, reactive } from 'vue';
-	import { onLoad, onReachBottom } from '@dcloudio/uni-app';
-	import sheep from '@/sheep';
-	import dayjs from 'dayjs';
-	import _ from 'lodash';
+  import { computed, reactive } from 'vue';
+  import { onLoad, onReachBottom } from '@dcloudio/uni-app';
+  import sheep from '@/sheep';
+  import dayjs from 'dayjs';
+  import _ from 'lodash-es';
   import BrokerageApi from '@/sheep/api/trade/brokerage';
   import { fen2yuan } from '@/sheep/hooks/useGoods';
   import { resetPagination } from '@/sheep/util';
 
-	const headerBg = sheep.$url.css('/static/img/shop/user/wallet_card_bg.png');
+  const headerBg = sheep.$url.css('/static/img/shop/user/wallet_card_bg.png');
 
-	const state = reactive({
+  const state = reactive({
     showMoney: false,
     summary: {}, // 分销信息
 
     today: '',
     date: [],
-		currentTab: 0,
-		pagination: {
+    currentTab: 0,
+    pagination: {
       list: [],
       total: 0,
       pageNo: 1,
       pageSize: 1,
     },
-		loadStatus: '',
+    loadStatus: '',
 
     price: undefined,
-		showModal: false,
-	});
-
-	const tabMaps = [{
-			name: '分佣',
-			value: '1', // BrokerageRecordBizTypeEnum.ORDER
-		},
-		{
-			name: '提现',
-			value: '2', // BrokerageRecordBizTypeEnum.WITHDRAW
-		}
-	];
-
-	const dateFilterText = computed(() => {
-		if (state.date[0] === state.date[1]) {
-			return state.date[0];
-		} else {
-			return state.date.join('~');
-		}
-	});
-
-	async function getLogList() {
-		state.loadStatus = 'loading';
-		let { code, data } = await BrokerageApi.getBrokerageRecordPage({
-			pageSize: state.pagination.pageSize,
-			pageNo: state.pagination.pageNo,
+    showModal: false,
+  });
+
+  const tabMaps = [
+    {
+      name: '分佣',
+      value: '1', // BrokerageRecordBizTypeEnum.ORDER
+    },
+    {
+      name: '提现',
+      value: '2', // BrokerageRecordBizTypeEnum.WITHDRAW
+    },
+  ];
+
+  const dateFilterText = computed(() => {
+    if (state.date[0] === state.date[1]) {
+      return state.date[0];
+    } else {
+      return state.date.join('~');
+    }
+  });
+
+  async function getLogList() {
+    state.loadStatus = 'loading';
+    let { code, data } = await BrokerageApi.getBrokerageRecordPage({
+      pageSize: state.pagination.pageSize,
+      pageNo: state.pagination.pageNo,
       bizType: tabMaps[state.currentTab].value,
       'createTime[0]': state.date[0] + ' 00:00:00',
       'createTime[1]': state.date[1] + ' 23:59:59',
-		});
-		if (code !== 0) {
+    });
+    if (code !== 0) {
       return;
-		}
+    }
     state.pagination.list = _.concat(state.pagination.list, data.list);
     state.pagination.total = data.total;
     state.loadStatus = state.pagination.list.length < state.pagination.total ? 'more' : 'noMore';
-	}
+  }
 
-	function onChangeTab(e) {
-		resetPagination(state.pagination);
-		state.currentTab = e.index;
-		getLogList();
-	}
+  function onChangeTab(e) {
+    resetPagination(state.pagination);
+    state.currentTab = e.index;
+    getLogList();
+  }
 
-	function onChangeTime(e) {
-		state.date[0] = e[0];
-		state.date[1] = e[e.length - 1];
+  function onChangeTime(e) {
+    state.date[0] = e[0];
+    state.date[1] = e[e.length - 1];
     resetPagination(state.pagination);
-		getLogList();
-	}
-
-	// 确认操作(转账到余额)
-	async function onConfirm() {
-		if (state.price <= 0) {
-			sheep.$helper.toast('请输入正确的金额');
-			return;
-		}
-		uni.showModal({
-			title: '提示',
-			content: '确认把您的佣金转入到余额钱包中?',
-			success: async function(res) {
-				if (!res.confirm) {
+    getLogList();
+  }
+
+  // 确认操作(转账到余额)
+  async function onConfirm() {
+    if (state.price <= 0) {
+      sheep.$helper.toast('请输入正确的金额');
+      return;
+    }
+    uni.showModal({
+      title: '提示',
+      content: '确认把您的佣金转入到余额钱包中?',
+      success: async function (res) {
+        if (!res.confirm) {
           return;
-				}
+        }
         const { code } = await BrokerageApi.createBrokerageWithdraw({
           type: 1, // 钱包
           price: state.price * 100,
@@ -199,272 +246,273 @@
           state.showModal = false;
           await getAgentInfo();
           onChangeTab({
-            index: 1
+            index: 1,
           });
         }
-			}
-		});
-	}
+      },
+    });
+  }
 
-	async function getAgentInfo() {
-		const { code, data } = await BrokerageApi.getBrokerageUserSummary();
+  async function getAgentInfo() {
+    const { code, data } = await BrokerageApi.getBrokerageUserSummary();
     if (code !== 0) {
       return;
     }
     state.summary = data;
-	}
+  }
 
-	onLoad(async (options) => {
-		state.today = dayjs().format('YYYY-MM-DD');
-		state.date = [state.today, state.today];
-    if (options.type === 2) { // 切换到“提现” tab 下
+  onLoad(async (options) => {
+    state.today = dayjs().format('YYYY-MM-DD');
+    state.date = [state.today, state.today];
+    if (options.type === 2) {
+      // 切换到“提现” tab 下
       state.currentTab = 1;
     }
-		getLogList();
-		getAgentInfo();
-	});
-
-	onReachBottom(() => {
-		if (state.loadStatus === 'noMore') {
-			return;
-		}
+    getLogList();
+    getAgentInfo();
+  });
+
+  onReachBottom(() => {
+    if (state.loadStatus === 'noMore') {
+      return;
+    }
     state.pagination.pageNo++;
     getLogList();
-	});
+  });
 </script>
 
 <style lang="scss" scoped>
-	// 钱包
-	.header-box {
-		background-color: $white;
-		padding: 30rpx;
-
-		.card-box {
-			width: 100%;
-			min-height: 300rpx;
-			padding: 40rpx;
-			background-size: 100% 100%;
-			border-radius: 30rpx;
-			overflow: hidden;
-			position: relative;
-			z-index: 1;
-			box-sizing: border-box;
-
-			&::after {
-				content: '';
-				display: block;
-				width: 100%;
-				height: 100%;
-				z-index: 2;
-				position: absolute;
-				top: 0;
-				left: 0;
-				background: v-bind(headerBg) no-repeat;
-				pointer-events: none;
-			}
-
-			.card-head {
-				color: $white;
-				font-size: 24rpx;
-			}
-
-			.ss-eye-icon {
-				font-size: 40rpx;
-				color: $white;
-			}
-
-			.money-num {
-				font-size: 40rpx;
-				line-height: normal;
-				font-weight: 500;
-				color: $white;
-				font-family: OPPOSANS;
-			}
-
-			.reduce-num {
-				font-size: 26rpx;
-				font-weight: 400;
-				color: $white;
-			}
-
-			.withdraw-btn {
-				width: 120rpx;
-				height: 60rpx;
-				line-height: 60rpx;
-				border-radius: 30px;
-				font-size: 24rpx;
-				font-weight: 500;
-				background-color: $white;
-				color: var(--ui-BG-Main);
-			}
-
-			.balance-btn {
-				width: 120rpx;
-				height: 60rpx;
-				line-height: 60rpx;
-				border-radius: 30px;
-				font-size: 24rpx;
-				font-weight: 500;
-				color: $white;
-				border: 1px solid $white;
-			}
-		}
-	}
-
-	.loading-money {
-		margin-top: 56rpx;
-
-		.loading-money-title {
-			font-size: 24rpx;
-			font-weight: 400;
-			color: #ffffff;
-			line-height: normal;
-			margin-bottom: 30rpx;
-		}
-
-		.loading-money-num {
-			font-size: 30rpx;
-			font-family: OPPOSANS;
-			font-weight: 500;
-			color: #fefefe;
-		}
-	}
-
-	// 筛选
-
-	.filter-box {
-		height: 120rpx;
-		padding: 0 30rpx;
-		background-color: $bg-page;
-
-		.total-box {
-			font-size: 24rpx;
-			font-weight: 500;
-			color: $dark-9;
-		}
-
-		.date-btn {
-			background-color: $white;
-			line-height: 54rpx;
-			border-radius: 27rpx;
-			padding: 0 20rpx;
-			font-size: 24rpx;
-			font-weight: 500;
-			color: $dark-6;
-
-			.ss-seldate-icon {
-				font-size: 50rpx;
-				color: $dark-9;
-			}
-		}
-	}
-
-	// tab
-	.wallet-tab-card {
-		.tab-item {
-			height: 80rpx;
-			position: relative;
-
-			.tab-title {
-				font-size: 30rpx;
-			}
-
-			.cur-tab-title {
-				font-weight: $font-weight-bold;
-			}
-
-			.tab-line {
-				width: 60rpx;
-				height: 6rpx;
-				border-radius: 6rpx;
-				position: absolute;
-				left: 50%;
-				transform: translateX(-50%);
-				bottom: 2rpx;
-				background-color: var(--ui-BG-Main);
-			}
-		}
-	}
-
-	// 钱包记录
-	.wallet-list {
-		padding: 30rpx;
-		background-color: #ffff;
-
-		.head-img {
-			width: 70rpx;
-			height: 70rpx;
-			border-radius: 50%;
-			background: $gray-c;
-		}
-
-		.list-content {
-			justify-content: space-between;
-			align-items: flex-start;
-			flex: 1;
-
-			.title {
-				font-size: 28rpx;
-				color: $dark-3;
-				width: 400rpx;
-			}
-
-			.time {
-				color: $gray-c;
-				font-size: 22rpx;
-			}
-		}
-
-		.money {
-			font-size: 28rpx;
-			font-weight: bold;
-			font-family: OPPOSANS;
-
-			.add {
-				color: var(--ui-BG-Main);
-			}
-
-			.minus {
-				color: $dark-3;
-			}
-		}
-	}
-
-	.model-title {
-		font-size: 36rpx;
-		font-weight: bold;
-		color: #333333;
-	}
-
-	.model-subtitle {
-		font-size: 26rpx;
-		color: #c2c7cf;
-	}
-
-	.model-btn {
-		width: 100%;
-		height: 80rpx;
-		border-radius: 40rpx;
-		font-size: 28rpx;
-		font-weight: 500;
-		color: #ffffff;
-		line-height: normal;
-	}
-
-	.input-box {
-		height: 100rpx;
-
-		.unit {
-			font-size: 48rpx;
-			color: #333;
-			font-weight: 500;
-			line-height: normal;
-		}
-
-		.uni-easyinput__placeholder-class {
-			font-size: 30rpx;
-			height: 40rpx;
-			line-height: normal;
-		}
-	}
-</style>
+  // 钱包
+  .header-box {
+    background-color: $white;
+    padding: 30rpx;
+
+    .card-box {
+      width: 100%;
+      min-height: 300rpx;
+      padding: 40rpx;
+      background-size: 100% 100%;
+      border-radius: 30rpx;
+      overflow: hidden;
+      position: relative;
+      z-index: 1;
+      box-sizing: border-box;
+
+      &::after {
+        content: '';
+        display: block;
+        width: 100%;
+        height: 100%;
+        z-index: 2;
+        position: absolute;
+        top: 0;
+        left: 0;
+        background: v-bind(headerBg) no-repeat;
+        pointer-events: none;
+      }
+
+      .card-head {
+        color: $white;
+        font-size: 24rpx;
+      }
+
+      .ss-eye-icon {
+        font-size: 40rpx;
+        color: $white;
+      }
+
+      .money-num {
+        font-size: 40rpx;
+        line-height: normal;
+        font-weight: 500;
+        color: $white;
+        font-family: OPPOSANS;
+      }
+
+      .reduce-num {
+        font-size: 26rpx;
+        font-weight: 400;
+        color: $white;
+      }
+
+      .withdraw-btn {
+        width: 120rpx;
+        height: 60rpx;
+        line-height: 60rpx;
+        border-radius: 30px;
+        font-size: 24rpx;
+        font-weight: 500;
+        background-color: $white;
+        color: var(--ui-BG-Main);
+      }
+
+      .balance-btn {
+        width: 120rpx;
+        height: 60rpx;
+        line-height: 60rpx;
+        border-radius: 30px;
+        font-size: 24rpx;
+        font-weight: 500;
+        color: $white;
+        border: 1px solid $white;
+      }
+    }
+  }
+
+  .loading-money {
+    margin-top: 56rpx;
+
+    .loading-money-title {
+      font-size: 24rpx;
+      font-weight: 400;
+      color: #ffffff;
+      line-height: normal;
+      margin-bottom: 30rpx;
+    }
+
+    .loading-money-num {
+      font-size: 30rpx;
+      font-family: OPPOSANS;
+      font-weight: 500;
+      color: #fefefe;
+    }
+  }
+
+  // 筛选
+
+  .filter-box {
+    height: 120rpx;
+    padding: 0 30rpx;
+    background-color: $bg-page;
+
+    .total-box {
+      font-size: 24rpx;
+      font-weight: 500;
+      color: $dark-9;
+    }
+
+    .date-btn {
+      background-color: $white;
+      line-height: 54rpx;
+      border-radius: 27rpx;
+      padding: 0 20rpx;
+      font-size: 24rpx;
+      font-weight: 500;
+      color: $dark-6;
+
+      .ss-seldate-icon {
+        font-size: 50rpx;
+        color: $dark-9;
+      }
+    }
+  }
+
+  // tab
+  .wallet-tab-card {
+    .tab-item {
+      height: 80rpx;
+      position: relative;
+
+      .tab-title {
+        font-size: 30rpx;
+      }
+
+      .cur-tab-title {
+        font-weight: $font-weight-bold;
+      }
+
+      .tab-line {
+        width: 60rpx;
+        height: 6rpx;
+        border-radius: 6rpx;
+        position: absolute;
+        left: 50%;
+        transform: translateX(-50%);
+        bottom: 2rpx;
+        background-color: var(--ui-BG-Main);
+      }
+    }
+  }
+
+  // 钱包记录
+  .wallet-list {
+    padding: 30rpx;
+    background-color: #ffff;
+
+    .head-img {
+      width: 70rpx;
+      height: 70rpx;
+      border-radius: 50%;
+      background: $gray-c;
+    }
+
+    .list-content {
+      justify-content: space-between;
+      align-items: flex-start;
+      flex: 1;
+
+      .title {
+        font-size: 28rpx;
+        color: $dark-3;
+        width: 400rpx;
+      }
+
+      .time {
+        color: $gray-c;
+        font-size: 22rpx;
+      }
+    }
+
+    .money {
+      font-size: 28rpx;
+      font-weight: bold;
+      font-family: OPPOSANS;
+
+      .add {
+        color: var(--ui-BG-Main);
+      }
+
+      .minus {
+        color: $dark-3;
+      }
+    }
+  }
+
+  .model-title {
+    font-size: 36rpx;
+    font-weight: bold;
+    color: #333333;
+  }
+
+  .model-subtitle {
+    font-size: 26rpx;
+    color: #c2c7cf;
+  }
+
+  .model-btn {
+    width: 100%;
+    height: 80rpx;
+    border-radius: 40rpx;
+    font-size: 28rpx;
+    font-weight: 500;
+    color: #ffffff;
+    line-height: normal;
+  }
+
+  .input-box {
+    height: 100rpx;
+
+    .unit {
+      font-size: 48rpx;
+      color: #333;
+      font-weight: 500;
+      line-height: normal;
+    }
+
+    .uni-easyinput__placeholder-class {
+      font-size: 30rpx;
+      height: 40rpx;
+      line-height: normal;
+    }
+  }
+</style>

+ 23 - 10
pages/coupon/detail.vue

@@ -16,13 +16,16 @@
             <view class="title ss-m-t-50 ss-m-b-20 ss-m-x-20">{{ state.coupon.name }}</view>
             <view class="subtitle ss-m-b-50">
               满 {{ fen2yuan(state.coupon.usePrice) }} 元,
-              {{ state.coupon.discountType === 1
-                ? '减 ' + fen2yuan(state.coupon.discountPrice) + ' 元'
-                : '打 ' + state.coupon.discountPercent / 10.0 + ' 折' }}
+              {{
+                state.coupon.discountType === 1
+                  ? '减 ' + fen2yuan(state.coupon.discountPrice) + ' 元'
+                  : '打 ' + state.coupon.discountPercent / 10.0 + ' 折'
+              }}
             </view>
             <button
               class="ss-reset-button ss-m-b-30"
-              :class="state.coupon.canTake || state.coupon.status === 1
+              :class="
+                state.coupon.canTake || state.coupon.status === 1
                   ? 'use-btn' // 优惠劵模版(可领取)、优惠劵(可使用)
                   : 'disable-btn'
               "
@@ -31,7 +34,13 @@
             >
               <text v-if="state.id > 0">{{ state.coupon.canTake ? '立即领取' : '已领取' }}</text>
               <text v-else>
-                {{ state.coupon.status === 1 ? '立即使用' : state.coupon.status === 2 ? '已使用' : '已过期' }}
+                {{
+                  state.coupon.status === 1
+                    ? '立即使用'
+                    : state.coupon.status === 2
+                    ? '已使用'
+                    : '已过期'
+                }}
               </text>
             </button>
             <view class="time ss-m-y-30" v-if="state.coupon.validityType === 2">
@@ -140,7 +149,7 @@
   import sheep from '@/sheep';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { reactive } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import CouponApi from '@/sheep/api/promotion/coupon';
   import { fen2yuan } from '@/sheep/hooks/useGoods';
   import SpuApi from '@/sheep/api/product/spu';
@@ -176,7 +185,7 @@
     const { code, data } = await SpuApi.getSpuPage({
       categoryId: state.categoryId,
       pageNo: state.pagination.pageNo,
-      pageSize: state.pagination.pageSize
+      pageSize: state.pagination.pageSize,
     });
     if (code !== 0) {
       return;
@@ -197,7 +206,9 @@
 
   // 获得分类列表
   async function getCategoryList() {
-    const { data, code } = await CategoryApi.getCategoryListByIds(state.coupon.productScopeValues.join(','));
+    const { data, code } = await CategoryApi.getCategoryListByIds(
+      state.coupon.productScopeValues.join(','),
+    );
     if (code !== 0) {
       return;
     }
@@ -225,8 +236,10 @@
 
   // 加载优惠劵信息
   async function getCouponContent() {
-    const { code, data } = state.id > 0 ? await CouponApi.getCouponTemplate(state.id)
-      : await CouponApi.getCoupon(state.couponId);
+    const { code, data } =
+      state.id > 0
+        ? await CouponApi.getCouponTemplate(state.id)
+        : await CouponApi.getCoupon(state.couponId);
     if (code !== 0) {
       return;
     }

+ 16 - 11
pages/coupon/list.vue

@@ -45,7 +45,7 @@
           <template #default>
             <button
               class="ss-reset-button card-btn ss-flex ss-row-center ss-col-center"
-              :class=" item.status !== 1 ? 'disabled-btn': ''"
+              :class="item.status !== 1 ? 'disabled-btn' : ''"
               :disabled="item.status !== 1"
               @click.stop="sheep.$router.go('/pages/coupon/detail', { couponId: item.id })"
             >
@@ -56,9 +56,14 @@
       </view>
     </template>
 
-    <uni-load-more v-if="state.pagination.total > 0" :status="state.loadStatus" :content-text="{
+    <uni-load-more
+      v-if="state.pagination.total > 0"
+      :status="state.loadStatus"
+      :content-text="{
         contentdown: '上拉加载更多',
-      }" @tap="loadMore" />
+      }"
+      @tap="loadMore"
+    />
   </s-layout>
 </template>
 
@@ -66,7 +71,7 @@
   import sheep from '@/sheep';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { reactive } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import { resetPagination } from '@/sheep/util';
   import CouponApi from '@/sheep/api/promotion/coupon';
 
@@ -78,7 +83,7 @@
       list: [],
       total: 0,
       pageNo: 1,
-      pageSize: 5
+      pageSize: 5,
     },
     loadStatus: '',
   });
@@ -106,9 +111,9 @@
   function onTabsChange(e) {
     state.currentTab = e.index;
     state.type = e.value;
-    resetPagination(state.pagination)
+    resetPagination(state.pagination);
     if (state.currentTab === 0) {
-    	getData();
+      getData();
     } else {
       getCoupon();
     }
@@ -135,7 +140,7 @@
     const { data, code } = await CouponApi.getCouponPage({
       pageNo: state.pagination.pageNo,
       pageSize: state.pagination.pageSize,
-      status: state.type
+      status: state.type,
     });
     if (code !== 0) {
       return;
@@ -177,13 +182,13 @@
     // 领劵中心
     if (Option.type === 'all' || !Option.type) {
       getData();
-    // 我的优惠劵
+      // 我的优惠劵
     } else {
       Option.type === 'geted'
         ? (state.currentTab = 1)
         : Option.type === 'used'
-          ? (state.currentTab = 2)
-          : (state.currentTab = 3);
+        ? (state.currentTab = 2)
+        : (state.currentTab = 3);
       state.type = state.currentTab;
       getCoupon();
     }

+ 1 - 1
pages/goods/comment/list.vue

@@ -30,7 +30,7 @@
   import CommentApi from '@/sheep/api/product/comment';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { reactive } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import commentItem from '../components/detail/comment-item.vue';
 
   const state = reactive({

+ 31 - 31
pages/goods/groupon.vue

@@ -7,12 +7,16 @@
     <detailSkeleton v-if="state.skeletonLoading" />
     <!-- 下架/售罄提醒 -->
     <s-empty
-        v-else-if="state.goodsInfo === null || state.activity.status !== 0 || state.activity.endTime < new Date().getTime()"
-        text="活动不存在或已结束"
-        icon="/static/soldout-empty.png"
-        showAction
-        actionText="返回上一页"
-        @clickAction="sheep.$router.back()"
+      v-else-if="
+        state.goodsInfo === null ||
+        state.activity.status !== 0 ||
+        state.activity.endTime < new Date().getTime()
+      "
+      text="活动不存在或已结束"
+      icon="/static/soldout-empty.png"
+      showAction
+      actionText="返回上一页"
+      @clickAction="sheep.$router.back()"
     />
     <block v-else>
       <view class="detail-swiper-selector">
@@ -47,10 +51,7 @@
                 </view>
               </view>
               <view class="ss-flex ss-row-between">
-                <view
-                  class="origin-price ss-flex ss-col-center"
-                  v-if="state.goodsInfo.price"
-                >
+                <view class="origin-price ss-flex ss-col-center" v-if="state.goodsInfo.price">
                   单买价:
                   <view class="origin-price-text">
                     {{ fen2yuan(state.goodsInfo.price) }}
@@ -123,7 +124,9 @@
             "
             :disabled="state.goodsInfo.stock === 0 || state.activity.status !== 0"
           >
-            <view class="btn-price">{{ fen2yuan(state.activity.price || state.goodsInfo.price) }}</view>
+            <view class="btn-price">{{
+              fen2yuan(state.activity.price || state.goodsInfo.price)
+            }}</view>
             <view v-if="state.activity.startTime > new Date().getTime()">未开始</view>
             <view v-else-if="state.activity.endTime <= new Date().getTime()">已结束</view>
             <view v-else>
@@ -141,7 +144,7 @@
   import { reactive, computed } from 'vue';
   import { onLoad, onPageScroll } from '@dcloudio/uni-app';
   import sheep from '@/sheep';
-  import { isEmpty } from 'lodash';
+  import { isEmpty } from 'lodash-es';
   import detailNavbar from './components/detail/detail-navbar.vue';
   import detailCellSku from './components/detail/detail-cell-sku.vue';
   import detailTabbar from './components/detail/detail-tabbar.vue';
@@ -149,29 +152,27 @@
   import detailCommentCard from './components/detail/detail-comment-card.vue';
   import detailContentCard from './components/detail/detail-content-card.vue';
   import grouponCardList from './components/groupon/groupon-card-list.vue';
-  import {useDurationTime, formatGoodsSwiper, fen2yuan} from '@/sheep/hooks/useGoods';
-  import CombinationApi from "@/sheep/api/promotion/combination";
-  import SpuApi from "@/sheep/api/product/spu";
+  import { useDurationTime, formatGoodsSwiper, fen2yuan } from '@/sheep/hooks/useGoods';
+  import CombinationApi from '@/sheep/api/promotion/combination';
+  import SpuApi from '@/sheep/api/product/spu';
 
   const headerBg = sheep.$url.css('/static/img/shop/goods/groupon-bg.png');
   const btnBg = sheep.$url.css('/static/img/shop/goods/groupon-btn.png');
-  const disabledBtnBg = sheep.$url.css(
-    '/static/img/shop/goods/activity-btn-disabled.png',
-  );
+  const disabledBtnBg = sheep.$url.css('/static/img/shop/goods/activity-btn-disabled.png');
   const grouponBg = sheep.$url.css('/static/img/shop/goods/groupon-tip-bg.png');
 
   onPageScroll(() => {});
   const state = reactive({
-    skeletonLoading: true,  // 骨架屏
-    goodsId: 0,             // 商品ID
-    goodsInfo: {},          // 商品信息
-    goodsSwiper: [],        // 商品轮播图
-    showSelectSku: false,   // 显示规格弹框
-    selectedSkuPrice: {},   // 选中的规格价格
-    activity: {},           // 团购活动
-    grouponId: 0,           // 团购ID
-    grouponNum: 0,          // 团购人数
-    grouponAction: 'create',  // 团购操作
+    skeletonLoading: true, // 骨架屏
+    goodsId: 0, // 商品ID
+    goodsInfo: {}, // 商品信息
+    goodsSwiper: [], // 商品轮播图
+    showSelectSku: false, // 显示规格弹框
+    selectedSkuPrice: {}, // 选中的规格价格
+    activity: {}, // 团购活动
+    grouponId: 0, // 团购ID
+    grouponNum: 0, // 团购人数
+    grouponAction: 'create', // 团购操作
     combinationHeadId: null, // 拼团团长编号
   });
 
@@ -261,7 +262,7 @@
     // 加载商品信息
     const { data: spu } = await SpuApi.getSpuDetail(activity.spuId);
     state.goodsId = spu.id;
-    activity.products.forEach(product => {
+    activity.products.forEach((product) => {
       spu.price = Math.min(spu.price, product.combinationPrice); // 设置 SPU 的最低价格
     });
     // 关闭骨架屏
@@ -475,8 +476,7 @@
   }
 
   .groupon-box {
-    background: v-bind(grouponBg)
-      no-repeat;
+    background: v-bind(grouponBg) no-repeat;
     background-size: 100% 100%;
   }
 

+ 322 - 286
pages/goods/list.vue

@@ -1,362 +1,398 @@
 <template>
-	<s-layout navbar="normal" :leftWidth="0" :rightWidth="0" tools="search" :defaultSearch="state.keyword"
-		@search="onSearch">
-		<!-- 筛选 -->
-		<su-sticky bgColor="#fff">
-			<view class="ss-flex">
-				<view class="ss-flex-1">
-					<su-tabs :list="state.tabList" :scrollable="false" @change="onTabsChange"
-                   :current="state.currentTab" />
-				</view>
-				<view class="list-icon" @tap="state.iconStatus = !state.iconStatus">
-					<text v-if="state.iconStatus" class="sicon-goods-list" />
-					<text v-else class="sicon-goods-card" />
-				</view>
-			</view>
-		</su-sticky>
-
-		<!-- 弹窗 -->
-		<su-popup :show="state.showFilter" type="top" round="10" :space="sys_navBar + 38" backgroundColor="#F6F6F6"
-			:zIndex="10" @close="state.showFilter = false">
-			<view class="filter-list-box">
-				<view class="filter-item" v-for="(item, index) in state.tabList[state.currentTab].list"
-					:key="item.value" :class="[{ 'filter-item-active': index === state.curFilter }]"
-					@tap="onFilterItem(index)">
-					{{ item.label }}
-				</view>
-			</view>
-		</su-popup>
+  <s-layout
+    navbar="normal"
+    :leftWidth="0"
+    :rightWidth="0"
+    tools="search"
+    :defaultSearch="state.keyword"
+    @search="onSearch"
+  >
+    <!-- 筛选 -->
+    <su-sticky bgColor="#fff">
+      <view class="ss-flex">
+        <view class="ss-flex-1">
+          <su-tabs
+            :list="state.tabList"
+            :scrollable="false"
+            @change="onTabsChange"
+            :current="state.currentTab"
+          />
+        </view>
+        <view class="list-icon" @tap="state.iconStatus = !state.iconStatus">
+          <text v-if="state.iconStatus" class="sicon-goods-list" />
+          <text v-else class="sicon-goods-card" />
+        </view>
+      </view>
+    </su-sticky>
+
+    <!-- 弹窗 -->
+    <su-popup
+      :show="state.showFilter"
+      type="top"
+      round="10"
+      :space="sys_navBar + 38"
+      backgroundColor="#F6F6F6"
+      :zIndex="10"
+      @close="state.showFilter = false"
+    >
+      <view class="filter-list-box">
+        <view
+          class="filter-item"
+          v-for="(item, index) in state.tabList[state.currentTab].list"
+          :key="item.value"
+          :class="[{ 'filter-item-active': index === state.curFilter }]"
+          @tap="onFilterItem(index)"
+        >
+          {{ item.label }}
+        </view>
+      </view>
+    </su-popup>
 
     <!-- 情况一:单列布局 -->
-		<view v-if="state.iconStatus && state.pagination.total > 0" class="goods-list ss-m-t-20">
-			<view class="ss-p-l-20 ss-p-r-20 ss-m-b-20" v-for="item in state.pagination.list" :key="item.id">
-				<s-goods-column
+    <view v-if="state.iconStatus && state.pagination.total > 0" class="goods-list ss-m-t-20">
+      <view
+        class="ss-p-l-20 ss-p-r-20 ss-m-b-20"
+        v-for="item in state.pagination.list"
+        :key="item.id"
+      >
+        <s-goods-column
           class=""
           size="lg"
           :data="item"
           :topRadius="10"
           :bottomRadius="10"
-					@click="sheep.$router.go('/pages/goods/index', { id: item.id })"
+          @click="sheep.$router.go('/pages/goods/index', { id: item.id })"
         />
-			</view>
-		</view>
+      </view>
+    </view>
     <!-- 情况二:双列布局 -->
-    <view v-if="!state.iconStatus && state.pagination.total > 0"
-			class="ss-flex ss-flex-wrap ss-p-x-20 ss-m-t-20 ss-col-top">
-			<view class="goods-list-box">
-				<view class="left-list" v-for="item in state.leftGoodsList" :key="item.id">
-					<s-goods-column
+    <view
+      v-if="!state.iconStatus && state.pagination.total > 0"
+      class="ss-flex ss-flex-wrap ss-p-x-20 ss-m-t-20 ss-col-top"
+    >
+      <view class="goods-list-box">
+        <view class="left-list" v-for="item in state.leftGoodsList" :key="item.id">
+          <s-goods-column
             class="goods-md-box"
             size="md"
             :data="item"
             :topRadius="10"
             :bottomRadius="10"
-						@click="sheep.$router.go('/pages/goods/index', { id: item.id })"
-						@getHeight="mountMasonry($event, 'left')"
+            @click="sheep.$router.go('/pages/goods/index', { id: item.id })"
+            @getHeight="mountMasonry($event, 'left')"
           >
-						<template v-slot:cart>
-							<button class="ss-reset-button cart-btn" />
-						</template>
-					</s-goods-column>
-				</view>
-			</view>
-			<view class="goods-list-box">
-				<view class="right-list" v-for="item in state.rightGoodsList" :key="item.id">
-					<s-goods-column
+            <template v-slot:cart>
+              <button class="ss-reset-button cart-btn" />
+            </template>
+          </s-goods-column>
+        </view>
+      </view>
+      <view class="goods-list-box">
+        <view class="right-list" v-for="item in state.rightGoodsList" :key="item.id">
+          <s-goods-column
             class="goods-md-box"
             size="md"
             :topRadius="10"
             :bottomRadius="10"
             :data="item"
-						@click="sheep.$router.go('/pages/goods/index', { id: item.id })"
-						@getHeight="mountMasonry($event, 'right')"
+            @click="sheep.$router.go('/pages/goods/index', { id: item.id })"
+            @getHeight="mountMasonry($event, 'right')"
           >
-						<template v-slot:cart>
-							<button class="ss-reset-button cart-btn" />
-						</template>
-					</s-goods-column>
-				</view>
-			</view>
-		</view>
-		<uni-load-more v-if="state.pagination.total > 0" :status="state.loadStatus" :content-text="{
+            <template v-slot:cart>
+              <button class="ss-reset-button cart-btn" />
+            </template>
+          </s-goods-column>
+        </view>
+      </view>
+    </view>
+    <uni-load-more
+      v-if="state.pagination.total > 0"
+      :status="state.loadStatus"
+      :content-text="{
         contentdown: '上拉加载更多',
-      }" @tap="loadMore" />
-		<s-empty v-if="state.pagination.total === 0" icon="/static/soldout-empty.png" text="暂无商品" />
-	</s-layout>
+      }"
+      @tap="loadMore"
+    />
+    <s-empty v-if="state.pagination.total === 0" icon="/static/soldout-empty.png" text="暂无商品" />
+  </s-layout>
 </template>
 
 <script setup>
-	import { reactive } from 'vue';
-	import { onLoad, onReachBottom } from '@dcloudio/uni-app';
-	import sheep from '@/sheep';
-	import _ from 'lodash';
+  import { reactive } from 'vue';
+  import { onLoad, onReachBottom } from '@dcloudio/uni-app';
+  import sheep from '@/sheep';
+  import _ from 'lodash-es';
   import { resetPagination } from '@/sheep/util';
   import SpuApi from '@/sheep/api/product/spu';
 
-	const sys_navBar = sheep.$platform.navbar;
-	const emits = defineEmits(['close', 'change']);
+  const sys_navBar = sheep.$platform.navbar;
+  const emits = defineEmits(['close', 'change']);
 
-	const state = reactive({
-		pagination: {
-			list: [],
+  const state = reactive({
+    pagination: {
+      list: [],
       total: 0,
       pageNo: 1,
-			pageSize: 6,
-		},
-		currentSort: undefined,
-		currentOrder: undefined,
-		currentTab: 0, // 当前选中的 tab
-		curFilter: 0, // 当前选中的 list 筛选项
-		showFilter: false,
-		iconStatus: false, // true - 单列布局;false - 双列布局
+      pageSize: 6,
+    },
+    currentSort: undefined,
+    currentOrder: undefined,
+    currentTab: 0, // 当前选中的 tab
+    curFilter: 0, // 当前选中的 list 筛选项
+    showFilter: false,
+    iconStatus: false, // true - 单列布局;false - 双列布局
     keyword: '',
     categoryId: 0,
-		tabList: [{
-				name: '综合推荐',
-				list: [{
-						label: '综合推荐'
-					},
-					{
-						label: '价格升序',
-						sort: 'price',
-						order: true,
-					},
-					{
-						label: '价格降序',
-						sort: 'price',
-						order: false,
-					},
-				],
-			},
-			{
-				name: '销量',
-				sort: 'salesCount',
-				order: false
-			},
-			{
-				name: '新品优先',
-				value: 'createTime',
-        order: false
-			},
-		],
-		loadStatus: '',
-		leftGoodsList: [], // 双列布局 - 左侧商品
-		rightGoodsList: [], // 双列布局 - 右侧商品
-	});
-
-	// 加载瀑布流
-	let count = 0;
-	let leftHeight = 0;
-	let rightHeight = 0;
+    tabList: [
+      {
+        name: '综合推荐',
+        list: [
+          {
+            label: '综合推荐',
+          },
+          {
+            label: '价格升序',
+            sort: 'price',
+            order: true,
+          },
+          {
+            label: '价格降序',
+            sort: 'price',
+            order: false,
+          },
+        ],
+      },
+      {
+        name: '销量',
+        sort: 'salesCount',
+        order: false,
+      },
+      {
+        name: '新品优先',
+        value: 'createTime',
+        order: false,
+      },
+    ],
+    loadStatus: '',
+    leftGoodsList: [], // 双列布局 - 左侧商品
+    rightGoodsList: [], // 双列布局 - 右侧商品
+  });
+
+  // 加载瀑布流
+  let count = 0;
+  let leftHeight = 0;
+  let rightHeight = 0;
 
   // 处理双列布局 leftGoodsList + rightGoodsList
-	function mountMasonry(height = 0, where = 'left') {
-		if (!state.pagination.list[count]) {
+  function mountMasonry(height = 0, where = 'left') {
+    if (!state.pagination.list[count]) {
       return;
     }
 
-		if (where === 'left') {
-			leftHeight += height;
-		} else {
-			rightHeight += height;
-		}
-		if (leftHeight <= rightHeight) {
-			state.leftGoodsList.push(state.pagination.list[count]);
-		} else {
-			state.rightGoodsList.push(state.pagination.list[count]);
-		}
-		count++;
-	}
+    if (where === 'left') {
+      leftHeight += height;
+    } else {
+      rightHeight += height;
+    }
+    if (leftHeight <= rightHeight) {
+      state.leftGoodsList.push(state.pagination.list[count]);
+    } else {
+      state.rightGoodsList.push(state.pagination.list[count]);
+    }
+    count++;
+  }
 
   // 清空列表
-	function emptyList() {
+  function emptyList() {
     resetPagination(state.pagination);
     state.leftGoodsList = [];
-		state.rightGoodsList = [];
-		count = 0;
-		leftHeight = 0;
-		rightHeight = 0;
-	}
-
-	// 搜索
-	function onSearch(e) {
-		state.keyword = e;
-		emptyList();
-		getList(state.currentSort, state.currentOrder);
-	}
-
-	// 点击
-	function onTabsChange(e) {
+    state.rightGoodsList = [];
+    count = 0;
+    leftHeight = 0;
+    rightHeight = 0;
+  }
+
+  // 搜索
+  function onSearch(e) {
+    state.keyword = e;
+    emptyList();
+    getList(state.currentSort, state.currentOrder);
+  }
+
+  // 点击
+  function onTabsChange(e) {
     // 如果点击的是【综合推荐】,则直接展开或者收起筛选项
-		if (state.tabList[e.index].list) {
-			state.currentTab = e.index;
-			state.showFilter = !state.showFilter;
-			return;
-		}
+    if (state.tabList[e.index].list) {
+      state.currentTab = e.index;
+      state.showFilter = !state.showFilter;
+      return;
+    }
     state.showFilter = false;
 
     // 如果点击的是【销量】或者【新品优先】,则直接切换 tab
-		if (e.index === state.currentTab) {
-			return;
-		}
+    if (e.index === state.currentTab) {
+      return;
+    }
 
     state.currentTab = e.index;
     state.currentSort = e.sort;
     state.currentOrder = e.order;
-		emptyList();
-		getList(e.sort, e.order);
-	}
+    emptyList();
+    getList(e.sort, e.order);
+  }
 
-	// 点击 tab 的 list 筛选项
-	const onFilterItem = (val) => {
+  // 点击 tab 的 list 筛选项
+  const onFilterItem = (val) => {
     // 如果点击的是当前的筛选项,则直接收起筛选项,不要加载数据
     // 这里选择 tabList[0] 的原因,是目前只有它有 list
-		if (state.currentSort === state.tabList[0].list[val].sort
-      && state.currentOrder === state.tabList[0].list[val].order) {
-			state.showFilter = false;
-			return;
-		}
+    if (
+      state.currentSort === state.tabList[0].list[val].sort &&
+      state.currentOrder === state.tabList[0].list[val].order
+    ) {
+      state.showFilter = false;
+      return;
+    }
     state.showFilter = false;
 
     // 设置筛选条件
-		state.curFilter = val;
-		state.tabList[0].name = state.tabList[0].list[val].label;
-		state.currentSort = state.tabList[0].list[val].sort;
-		state.currentOrder = state.tabList[0].list[val].order;
-		// 清空 + 加载数据
+    state.curFilter = val;
+    state.tabList[0].name = state.tabList[0].list[val].label;
+    state.currentSort = state.tabList[0].list[val].sort;
+    state.currentOrder = state.tabList[0].list[val].order;
+    // 清空 + 加载数据
     emptyList();
-		getList();
-	}
+    getList();
+  };
 
-	async function getList() {
-		state.loadStatus = 'loading';
-		const { code, data } = await SpuApi.getSpuPage({
+  async function getList() {
+    state.loadStatus = 'loading';
+    const { code, data } = await SpuApi.getSpuPage({
       pageNo: state.pagination.pageNo,
       pageSize: state.pagination.pageSize,
-			sortField: state.currentSort,
-			sortAsc: state.currentOrder,
-			categoryId: state.categoryId,
-			keyword: state.keyword,
-		});
+      sortField: state.currentSort,
+      sortAsc: state.currentOrder,
+      categoryId: state.categoryId,
+      keyword: state.keyword,
+    });
     if (code !== 0) {
       return;
     }
-    state.pagination.list = _.concat(state.pagination.list, data.list)
+    state.pagination.list = _.concat(state.pagination.list, data.list);
     state.pagination.total = data.total;
     state.loadStatus = state.pagination.list.length < state.pagination.total ? 'more' : 'noMore';
     mountMasonry();
-	}
+  }
 
-	// 加载更多
-	function loadMore() {
+  // 加载更多
+  function loadMore() {
     if (state.loadStatus === 'noMore') {
       return;
     }
     state.pagination.pageNo++;
     getList(state.currentSort, state.currentOrder);
-	}
-
-	onLoad((options) => {
-		state.categoryId = options.categoryId;
-		state.keyword = options.keyword;
-		getList(state.currentSort, state.currentOrder);
-	});
-
-	// 上拉加载更多
-	onReachBottom(() => {
-		loadMore();
-	});
+  }
+
+  onLoad((options) => {
+    state.categoryId = options.categoryId;
+    state.keyword = options.keyword;
+    getList(state.currentSort, state.currentOrder);
+  });
+
+  // 上拉加载更多
+  onReachBottom(() => {
+    loadMore();
+  });
 </script>
 
 <style lang="scss" scoped>
-	.goods-list-box {
-		width: 50%;
-		box-sizing: border-box;
-
-		.left-list {
-			margin-right: 10rpx;
-			margin-bottom: 20rpx;
-		}
-
-		.right-list {
-			margin-left: 10rpx;
-			margin-bottom: 20rpx;
-		}
-	}
-
-	.goods-box {
-		&:nth-last-of-type(1) {
-			margin-bottom: 0 !important;
-		}
-
-		&:nth-child(2n) {
-			margin-right: 0;
-		}
-	}
-
-	.list-icon {
-		width: 80rpx;
-
-		.sicon-goods-card {
-			font-size: 40rpx;
-		}
-
-		.sicon-goods-list {
-			font-size: 40rpx;
-		}
-	}
-
-	.goods-card {
-		margin-left: 20rpx;
-	}
-
-	.list-filter-tabs {
-		background-color: #fff;
-	}
-
-	.filter-list-box {
-		padding: 28rpx 52rpx;
-
-		.filter-item {
-			font-size: 28rpx;
-			font-weight: 500;
-			color: #333333;
-			line-height: normal;
-			margin-bottom: 24rpx;
-
-			&:nth-last-child(1) {
-				margin-bottom: 0;
-			}
-		}
-
-		.filter-item-active {
-			color: var(--ui-BG-Main);
-		}
-	}
-
-	.tab-item {
-		height: 50px;
-		position: relative;
-		z-index: 11;
-
-		.tab-title {
-			font-size: 30rpx;
-		}
-
-		.cur-tab-title {
-			font-weight: $font-weight-bold;
-		}
-
-		.tab-line {
-			width: 60rpx;
-			height: 6rpx;
-			border-radius: 6rpx;
-			position: absolute;
-			left: 50%;
-			transform: translateX(-50%);
-			bottom: 10rpx;
-			background-color: var(--ui-BG-Main);
-			z-index: 12;
-		}
-	}
-</style>
+  .goods-list-box {
+    width: 50%;
+    box-sizing: border-box;
+
+    .left-list {
+      margin-right: 10rpx;
+      margin-bottom: 20rpx;
+    }
+
+    .right-list {
+      margin-left: 10rpx;
+      margin-bottom: 20rpx;
+    }
+  }
+
+  .goods-box {
+    &:nth-last-of-type(1) {
+      margin-bottom: 0 !important;
+    }
+
+    &:nth-child(2n) {
+      margin-right: 0;
+    }
+  }
+
+  .list-icon {
+    width: 80rpx;
+
+    .sicon-goods-card {
+      font-size: 40rpx;
+    }
+
+    .sicon-goods-list {
+      font-size: 40rpx;
+    }
+  }
+
+  .goods-card {
+    margin-left: 20rpx;
+  }
+
+  .list-filter-tabs {
+    background-color: #fff;
+  }
+
+  .filter-list-box {
+    padding: 28rpx 52rpx;
+
+    .filter-item {
+      font-size: 28rpx;
+      font-weight: 500;
+      color: #333333;
+      line-height: normal;
+      margin-bottom: 24rpx;
+
+      &:nth-last-child(1) {
+        margin-bottom: 0;
+      }
+    }
+
+    .filter-item-active {
+      color: var(--ui-BG-Main);
+    }
+  }
+
+  .tab-item {
+    height: 50px;
+    position: relative;
+    z-index: 11;
+
+    .tab-title {
+      font-size: 30rpx;
+    }
+
+    .cur-tab-title {
+      font-weight: $font-weight-bold;
+    }
+
+    .tab-line {
+      width: 60rpx;
+      height: 6rpx;
+      border-radius: 6rpx;
+      position: absolute;
+      left: 50%;
+      transform: translateX(-50%);
+      bottom: 10rpx;
+      background-color: var(--ui-BG-Main);
+      z-index: 12;
+    }
+  }
+</style>

+ 31 - 30
pages/goods/seckill.vue

@@ -69,10 +69,7 @@
 
         <!-- 功能卡片 -->
         <view class="detail-cell-card detail-card ss-flex-col">
-          <detail-cell-sku
-            :sku="state.selectedSku"
-            @tap="state.showSelectSku = true"
-          />
+          <detail-cell-sku :sku="state.selectedSku" @tap="state.showSelectSku = true" />
         </view>
         <!-- 规格与数量弹框 -->
         <s-select-seckill-sku
@@ -107,7 +104,9 @@
           <button v-else class="ss-reset-button origin-price-btn ss-flex-col">
             <view
               class="no-original"
-              :class="state.goodsInfo.stock === 0 || timeStatusEnum !== TimeStatusEnum.STARTED ? '' : ''"
+              :class="
+                state.goodsInfo.stock === 0 || timeStatusEnum !== TimeStatusEnum.STARTED ? '' : ''
+              "
             >
               秒杀价
             </view>
@@ -136,11 +135,11 @@
 </template>
 
 <script setup>
-  import {reactive, computed, ref} from 'vue';
+  import { reactive, computed, ref } from 'vue';
   import { onLoad, onPageScroll } from '@dcloudio/uni-app';
   import sheep from '@/sheep';
-  import {isEmpty, min} from 'lodash';
-  import {useDurationTime, formatGoodsSwiper, fen2yuan} from '@/sheep/hooks/useGoods';
+  import { isEmpty, min } from 'lodash-es';
+  import { useDurationTime, formatGoodsSwiper, fen2yuan } from '@/sheep/hooks/useGoods';
   import detailNavbar from './components/detail/detail-navbar.vue';
   import detailCellSku from './components/detail/detail-cell-sku.vue';
   import detailTabbar from './components/detail/detail-tabbar.vue';
@@ -148,15 +147,13 @@
   import detailCommentCard from './components/detail/detail-comment-card.vue';
   import detailContentCard from './components/detail/detail-content-card.vue';
   import detailProgress from './components/detail/detail-progress.vue';
-  import SeckillApi from "@/sheep/api/promotion/seckill";
-  import SpuApi from "@/sheep/api/product/spu";
-  import {getTimeStatusEnum, TimeStatusEnum} from "@/sheep/util/const";
+  import SeckillApi from '@/sheep/api/promotion/seckill';
+  import SpuApi from '@/sheep/api/product/spu';
+  import { getTimeStatusEnum, TimeStatusEnum } from '@/sheep/util/const';
 
   const headerBg = sheep.$url.css('/static/img/shop/goods/seckill-bg.png');
   const btnBg = sheep.$url.css('/static/img/shop/goods/seckill-btn.png');
-  const disabledBtnBg = sheep.$url.css(
-    '/static/img/shop/goods/activity-btn-disabled.png',
-  );
+  const disabledBtnBg = sheep.$url.css('/static/img/shop/goods/activity-btn-disabled.png');
   const seckillBg = sheep.$url.css('/static/img/shop/goods/seckill-tip-bg.png');
   const grouponBg = sheep.$url.css('/static/img/shop/goods/groupon-tip-bg.png');
 
@@ -221,36 +218,40 @@
     );
   });
 
-  const activity = ref()
-  const timeStatusEnum = ref('')
+  const activity = ref();
+  const timeStatusEnum = ref('');
   // 查询活动
   const getActivity = async (id) => {
-    const { data } = await SeckillApi.getSeckillActivity(id)
-    activity.value = data
-    timeStatusEnum.value = getTimeStatusEnum(activity.startTime, activity.endTime)
+    const { data } = await SeckillApi.getSeckillActivity(id);
+    activity.value = data;
+    timeStatusEnum.value = getTimeStatusEnum(activity.startTime, activity.endTime);
 
     // 查询商品
-    await getSpu(data.spuId)
-  }
+    await getSpu(data.spuId);
+  };
 
   const getSpu = async (id) => {
-    const { data } = await SpuApi.getSpuDetail(id)
+    const { data } = await SpuApi.getSpuDetail(id);
     // 模拟
-    data.activity_type = 'seckill'
-    state.goodsInfo = data
+    data.activity_type = 'seckill';
+    state.goodsInfo = data;
     // 处理轮播图
     state.goodsSwiper = formatGoodsSwiper(state.goodsInfo.sliderPicUrls);
 
     // 默认显示最低价
-    state.goodsInfo.price = min([state.goodsInfo.price, ...activity.value.products.map(spu => spu.seckillPrice)])
+    state.goodsInfo.price = min([
+      state.goodsInfo.price,
+      ...activity.value.products.map((spu) => spu.seckillPrice),
+    ]);
 
     // 价格、库存使用活动的
-    data.skus.forEach(sku => {
-      const product = activity.value.products.find(product => product.skuId === sku.id);
+    data.skus.forEach((sku) => {
+      const product = activity.value.products.find((product) => product.skuId === sku.id);
       if (product) {
         sku.price = product.seckillPrice;
         sku.stock = Math.min(sku.stock, product.stock);
-      } else { // 找不到可能是没配置,则不能发起秒杀
+      } else {
+        // 找不到可能是没配置,则不能发起秒杀
         sku.stock = 0;
       }
       // 设置限购数量
@@ -264,7 +265,7 @@
     });
 
     state.skeletonLoading = false;
-  }
+  };
 
   onLoad((options) => {
     // 非法参数
@@ -274,7 +275,7 @@
     }
 
     // 查询活动
-    getActivity(options.id)
+    getActivity(options.id);
   });
 </script>
 

+ 1 - 1
pages/index/category.vue

@@ -63,7 +63,7 @@
   import SpuApi from '@/sheep/api/product/spu';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { computed, reactive } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import { handleTree } from '@/sheep/util';
 
   const state = reactive({

+ 3 - 7
pages/order/aftersale/apply.vue

@@ -98,11 +98,7 @@
         </view>
         <view class="modal-content content_box">
           <radio-group @change="onChange">
-            <label
-              class="radio ss-flex ss-col-center"
-              v-for="item in state.reasonList"
-              :key="item"
-            >
+            <label class="radio ss-flex ss-col-center" v-for="item in state.reasonList" :key="item">
               <view class="ss-flex-1 ss-p-20">{{ item }}</view>
               <radio
                 :value="item"
@@ -153,9 +149,9 @@
     ],
     reasonList: [], // 可选的申请原因数组
     showModal: false, // 是否显示申请原因弹窗
-    currentValue: '' // 当前选择的售后原因
+    currentValue: '', // 当前选择的售后原因
   });
-  const formData = reactive({
+  let formData = reactive({
     way: '',
     applyReason: '',
     applyDescription: '',

+ 317 - 280
pages/order/aftersale/detail.vue

@@ -1,156 +1,193 @@
 <!-- 售后详情 -->
 <template>
-	<s-layout title="售后详情" :navbar="!isEmpty(state.info) && state.loading ? 'inner' : 'normal'">
-		<view class="content_box" v-if="!isEmpty(state.info) && state.loading">
-			<!-- 步骤条 -->
-			<view class="steps-box ss-flex" :style="[
+  <s-layout title="售后详情" :navbar="!isEmpty(state.info) && state.loading ? 'inner' : 'normal'">
+    <view class="content_box" v-if="!isEmpty(state.info) && state.loading">
+      <!-- 步骤条 -->
+      <view
+        class="steps-box ss-flex"
+        :style="[
           {
             marginTop: '-' + Number(statusBarHeight + 88) + 'rpx',
             paddingTop: Number(statusBarHeight + 88) + 'rpx',
           },
-        ]">
-				<view class="ss-flex">
-					<view class="steps-item" v-for="(item, index) in state.list" :key="index">
-						<view class="ss-flex">
-							<text class="sicon-circleclose"
-                    v-if="state.list.length - 1 === index && [61, 62, 63].includes(state.info.status)" />
-							<text class="sicon-circlecheck" v-else
-                    :class="state.active >= index ? 'activity-color' : 'info-color'" />
-
-							<view v-if="state.list.length - 1 !== index" class="line"
-                    :class="state.active >= index ? 'activity-bg' : 'info-bg'" />
-						</view>
-						<view class="steps-item-title" :class="state.active >= index ? 'activity-color' : 'info-color'">
-							{{ item.title }}
-						</view>
-					</view>
-				</view>
-			</view>
-
-			<!-- 服务状态 -->
-			<view class="status-box ss-flex ss-col-center ss-row-between ss-m-x-20"
-            @tap="sheep.$router.go('/pages/order/aftersale/log', { id: state.id })">
-				<view class="">
-					<view class="status-text">
+        ]"
+      >
+        <view class="ss-flex">
+          <view class="steps-item" v-for="(item, index) in state.list" :key="index">
+            <view class="ss-flex">
+              <text
+                class="sicon-circleclose"
+                v-if="state.list.length - 1 === index && [61, 62, 63].includes(state.info.status)"
+              />
+              <text
+                class="sicon-circlecheck"
+                v-else
+                :class="state.active >= index ? 'activity-color' : 'info-color'"
+              />
+
+              <view
+                v-if="state.list.length - 1 !== index"
+                class="line"
+                :class="state.active >= index ? 'activity-bg' : 'info-bg'"
+              />
+            </view>
+            <view
+              class="steps-item-title"
+              :class="state.active >= index ? 'activity-color' : 'info-color'"
+            >
+              {{ item.title }}
+            </view>
+          </view>
+        </view>
+      </view>
+
+      <!-- 服务状态 -->
+      <view
+        class="status-box ss-flex ss-col-center ss-row-between ss-m-x-20"
+        @tap="sheep.$router.go('/pages/order/aftersale/log', { id: state.id })"
+      >
+        <view class="">
+          <view class="status-text">
             {{ formatAfterSaleStatusDescription(state.info) }}
           </view>
-					<view class="status-time">
+          <view class="status-time">
             {{ sheep.$helper.timeFormat(state.info.updateTime, 'yyyy-mm-dd hh:MM:ss') }}
           </view>
-				</view>
-				<text class="ss-iconfont _icon-forward" style="color: #666" />
-			</view>
-
-			<!-- 退款金额 -->
-			<view class="aftersale-money ss-flex ss-col-center ss-row-between">
-				<view class="aftersale-money--title">退款总额</view>
-				<view class="aftersale-money--num">¥{{ fen2yuan(state.info.refundPrice) }}</view>
-			</view>
-			<!-- 服务商品 -->
-			<view class="order-shop">
-				<s-goods-item
-          :img=" state.info.picUrl"
-          :title=" state.info.spuName"
-					:titleWidth="480"
+        </view>
+        <text class="ss-iconfont _icon-forward" style="color: #666" />
+      </view>
+
+      <!-- 退款金额 -->
+      <view class="aftersale-money ss-flex ss-col-center ss-row-between">
+        <view class="aftersale-money--title">退款总额</view>
+        <view class="aftersale-money--num">¥{{ fen2yuan(state.info.refundPrice) }}</view>
+      </view>
+      <!-- 服务商品 -->
+      <view class="order-shop">
+        <s-goods-item
+          :img="state.info.picUrl"
+          :title="state.info.spuName"
+          :titleWidth="480"
           :skuText="state.info.properties.map((property) => property.valueName).join(' ')"
-          :num=" state.info.count"
+          :num="state.info.count"
         />
-			</view>
-
-			<!-- 服务内容 -->
-			<view class="aftersale-content">
-				<view class="aftersale-item ss-flex ss-col-center">
-					<view class="item-title">服务单号:</view>
-					<view class="item-content ss-m-r-16">{{ state.info.no }}</view>
-					<button class="ss-reset-button copy-btn" @tap="onCopy">复制</button>
-				</view>
-				<view class="aftersale-item ss-flex ss-col-center">
-					<view class="item-title">申请时间:</view>
-					<view class="item-content">
-						{{ sheep.$helper.timeFormat(state.info.createTime, 'yyyy-mm-dd hh:MM:ss') }}
-					</view>
-				</view>
-				<view class="aftersale-item ss-flex ss-col-center">
-					<view class="item-title">售后类型:</view>
-					<view class="item-content">{{ state.info.way === 10 ? '仅退款' : '退款退货' }}</view>
-				</view>
-				<view class="aftersale-item ss-flex ss-col-center">
-					<view class="item-title">申请原因:</view>
-					<view class="item-content">{{ state.info.applyReason }}</view>
-				</view>
-				<view class="aftersale-item ss-flex ss-col-center">
-					<view class="item-title">相关描述:</view>
-					<view class="item-content">{{ state.info.applyDescription }}</view>
-				</view>
-			</view>
-		</view>
+      </view>
+
+      <!-- 服务内容 -->
+      <view class="aftersale-content">
+        <view class="aftersale-item ss-flex ss-col-center">
+          <view class="item-title">服务单号:</view>
+          <view class="item-content ss-m-r-16">{{ state.info.no }}</view>
+          <button class="ss-reset-button copy-btn" @tap="onCopy">复制</button>
+        </view>
+        <view class="aftersale-item ss-flex ss-col-center">
+          <view class="item-title">申请时间:</view>
+          <view class="item-content">
+            {{ sheep.$helper.timeFormat(state.info.createTime, 'yyyy-mm-dd hh:MM:ss') }}
+          </view>
+        </view>
+        <view class="aftersale-item ss-flex ss-col-center">
+          <view class="item-title">售后类型:</view>
+          <view class="item-content">{{ state.info.way === 10 ? '仅退款' : '退款退货' }}</view>
+        </view>
+        <view class="aftersale-item ss-flex ss-col-center">
+          <view class="item-title">申请原因:</view>
+          <view class="item-content">{{ state.info.applyReason }}</view>
+        </view>
+        <view class="aftersale-item ss-flex ss-col-center">
+          <view class="item-title">相关描述:</view>
+          <view class="item-content">{{ state.info.applyDescription }}</view>
+        </view>
+      </view>
+    </view>
 
     <!-- 操作区 -->
-		<s-empty v-if="isEmpty(state.info) && state.loading" icon="/static/order-empty.png" text="暂无该订单售后详情" />
-		<su-fixed bottom placeholder bg="bg-white" v-if="!isEmpty(state.info)">
-			<view class="foot_box">
-        <button class="ss-reset-button btn" v-if="state.info.buttons?.includes('cancel')"
-                @tap="onApply(state.info.id)">
+    <s-empty
+      v-if="isEmpty(state.info) && state.loading"
+      icon="/static/order-empty.png"
+      text="暂无该订单售后详情"
+    />
+    <su-fixed bottom placeholder bg="bg-white" v-if="!isEmpty(state.info)">
+      <view class="foot_box">
+        <button
+          class="ss-reset-button btn"
+          v-if="state.info.buttons?.includes('cancel')"
+          @tap="onApply(state.info.id)"
+        >
           取消申请
         </button>
-        <button class="ss-reset-button btn" v-if="state.info.buttons?.includes('delivery')"
-                @tap="sheep.$router.go('/pages/order/aftersale/return-delivery', { id: state.info.id })">
+        <button
+          class="ss-reset-button btn"
+          v-if="state.info.buttons?.includes('delivery')"
+          @tap="sheep.$router.go('/pages/order/aftersale/return-delivery', { id: state.info.id })"
+        >
           填写退货
         </button>
-				<button class="ss-reset-button contcat-btn btn" @tap="sheep.$router.go('/pages/chat/index')">
+        <button
+          class="ss-reset-button contcat-btn btn"
+          @tap="sheep.$router.go('/pages/chat/index')"
+        >
           联系客服
         </button>
-			</view>
-		</su-fixed>
-	</s-layout>
+      </view>
+    </su-fixed>
+  </s-layout>
 </template>
 
 <script setup>
-	import sheep from '@/sheep';
-	import { onLoad } from '@dcloudio/uni-app';
-	import { reactive } from 'vue';
-	import { isEmpty } from 'lodash';
-  import { fen2yuan, formatAfterSaleStatusDescription, handleAfterSaleButtons } from '@/sheep/hooks/useGoods';
+  import sheep from '@/sheep';
+  import { onLoad } from '@dcloudio/uni-app';
+  import { reactive } from 'vue';
+  import { isEmpty } from 'lodash-es';
+  import {
+    fen2yuan,
+    formatAfterSaleStatusDescription,
+    handleAfterSaleButtons,
+  } from '@/sheep/hooks/useGoods';
   import AfterSaleApi from '@/sheep/api/trade/afterSale';
 
-	const statusBarHeight = sheep.$platform.device.statusBarHeight * 2;
-	const headerBg = sheep.$url.css('/static/img/shop/order/order_bg.png');
-	const state = reactive({
+  const statusBarHeight = sheep.$platform.device.statusBarHeight * 2;
+  const headerBg = sheep.$url.css('/static/img/shop/order/order_bg.png');
+  const state = reactive({
     id: 0, // 售后编号
     info: {}, // 收货信息
-		loading: false,
+    loading: false,
     active: 0, // 在 list 的激活位置
-    list: [{
-      title: '提交申请',
-    }, {
-      title: '处理中',
-    }, {
-      title: '完成'
-    }], // 时间轴
-	});
-
-	function onApply(id) {
-		uni.showModal({
-			title: '提示',
-			content: '确定要取消此申请吗?',
-			success: async function(res) {
-				if (!res.confirm) {
-					return;
-				}
+    list: [
+      {
+        title: '提交申请',
+      },
+      {
+        title: '处理中',
+      },
+      {
+        title: '完成',
+      },
+    ], // 时间轴
+  });
+
+  function onApply(id) {
+    uni.showModal({
+      title: '提示',
+      content: '确定要取消此申请吗?',
+      success: async function (res) {
+        if (!res.confirm) {
+          return;
+        }
         const { code } = await AfterSaleApi.cancelAfterSale(id);
         if (code === 0) {
           await getDetail(id);
         }
-			},
-		});
-	}
+      },
+    });
+  }
 
   // 复制
   const onCopy = () => {
-		sheep.$helper.copyText(state.info.no);
-	};
+    sheep.$helper.copyText(state.info.no);
+  };
 
-	async function getDetail(id) {
+  async function getDetail(id) {
     state.loading = true;
     const { code, data } = await AfterSaleApi.getAfterSale(id);
     if (code !== 0) {
@@ -170,173 +207,173 @@
     } else if ([61, 62, 63].includes(state.info.status)) {
       state.active = 2;
     }
-	}
+  }
 
-	onLoad((options) => {
+  onLoad((options) => {
     if (!options.id) {
       sheep.$helper.toast(`缺少订单信息,请检查`);
-      return
+      return;
     }
-		state.id = options.id;
-		getDetail(options.id);
-	});
+    state.id = options.id;
+    getDetail(options.id);
+  });
 </script>
 
 <style lang="scss" scoped>
-	// 步骤条
-	.steps-box {
-		width: 100%;
-		height: 190rpx;
-		background: v-bind(headerBg) no-repeat,
-			linear-gradient(90deg, var(--ui-BG-Main), var(--ui-BG-Main-gradient));
-		background-size: 750rpx 100%;
-		padding-left: 72rpx;
-
-		.steps-item {
-			.sicon-circleclose {
-				font-size: 24rpx;
-				color: #fff;
-			}
-
-			.sicon-circlecheck {
-				font-size: 24rpx;
-			}
-
-			.steps-item-title {
-				font-size: 24rpx;
-				font-weight: 400;
-				margin-top: 16rpx;
-				margin-left: -36rpx;
-				width: 100rpx;
-				text-align: center;
-			}
-		}
-	}
-
-	.activity-color {
-		color: #fff;
-	}
-
-	.info-color {
-		color: rgba(#fff, 0.4);
-	}
-
-	.activity-bg {
-		background: #fff;
-	}
-
-	.info-bg {
-		background: rgba(#fff, 0.4);
-	}
-
-	.line {
-		width: 270rpx;
-		height: 4rpx;
-	}
-
-	// 服务状态
-	.status-box {
-		position: relative;
-		z-index: 3;
-		background-color: #fff;
-		border-radius: 20rpx 20rpx 0px 0px;
-		padding: 20rpx;
-		margin-top: -20rpx;
-
-		.status-text {
-			font-size: 28rpx;
-
-			font-weight: 500;
-			color: rgba(51, 51, 51, 1);
-			margin-bottom: 20rpx;
-		}
-
-		.status-time {
-			font-size: 24rpx;
-
-			font-weight: 400;
-			color: rgba(153, 153, 153, 1);
-		}
-	}
-
-	// 退款金额
-	.aftersale-money {
-		background-color: #fff;
-		height: 98rpx;
-		padding: 0 20rpx;
-		margin: 20rpx;
-
-		.aftersale-money--title {
-			font-size: 28rpx;
-
-			font-weight: 500;
-			color: rgba(51, 51, 51, 1);
-		}
-
-		.aftersale-money--num {
-			font-size: 28rpx;
-			font-family: OPPOSANS;
-			font-weight: 500;
-			color: #ff3000;
-		}
-	}
-
-	// order-shop
-	.order-shop {
-		padding: 20rpx;
-		background-color: #fff;
-		margin: 0 20rpx 20rpx 20rpx;
-	}
-
-	// 服务内容
-	.aftersale-content {
-		background-color: #fff;
-		padding: 20rpx;
-		margin: 0 20rpx;
-
-		.aftersale-item {
-			height: 60rpx;
-
-			.copy-btn {
-				background: #eeeeee;
-				color: #333;
-				border-radius: 20rpx;
-				width: 75rpx;
-				height: 40rpx;
-				font-size: 22rpx;
-			}
-
-			.item-title {
-				color: #999;
-				font-size: 28rpx;
-			}
-
-			.item-content {
-				color: #333;
-				font-size: 28rpx;
-			}
-		}
-	}
-
-	// 底部功能
-	.foot_box {
-		height: 100rpx;
-		background-color: #fff;
-		display: flex;
-		align-items: center;
-		justify-content: flex-end;
-
-		.btn {
-			width: 160rpx;
-			line-height: 60rpx;
-			background: rgba(238, 238, 238, 1);
-			border-radius: 30rpx;
-			padding: 0;
-			margin-right: 20rpx;
-			font-size: 26rpx;
-
-			font-weight: 400;
-			color: rgba(51, 51, 51, 1);
-		}
-	}
-</style>
+  // 步骤条
+  .steps-box {
+    width: 100%;
+    height: 190rpx;
+    background: v-bind(headerBg) no-repeat,
+      linear-gradient(90deg, var(--ui-BG-Main), var(--ui-BG-Main-gradient));
+    background-size: 750rpx 100%;
+    padding-left: 72rpx;
+
+    .steps-item {
+      .sicon-circleclose {
+        font-size: 24rpx;
+        color: #fff;
+      }
+
+      .sicon-circlecheck {
+        font-size: 24rpx;
+      }
+
+      .steps-item-title {
+        font-size: 24rpx;
+        font-weight: 400;
+        margin-top: 16rpx;
+        margin-left: -36rpx;
+        width: 100rpx;
+        text-align: center;
+      }
+    }
+  }
+
+  .activity-color {
+    color: #fff;
+  }
+
+  .info-color {
+    color: rgba(#fff, 0.4);
+  }
+
+  .activity-bg {
+    background: #fff;
+  }
+
+  .info-bg {
+    background: rgba(#fff, 0.4);
+  }
+
+  .line {
+    width: 270rpx;
+    height: 4rpx;
+  }
+
+  // 服务状态
+  .status-box {
+    position: relative;
+    z-index: 3;
+    background-color: #fff;
+    border-radius: 20rpx 20rpx 0px 0px;
+    padding: 20rpx;
+    margin-top: -20rpx;
+
+    .status-text {
+      font-size: 28rpx;
+
+      font-weight: 500;
+      color: rgba(51, 51, 51, 1);
+      margin-bottom: 20rpx;
+    }
+
+    .status-time {
+      font-size: 24rpx;
+
+      font-weight: 400;
+      color: rgba(153, 153, 153, 1);
+    }
+  }
+
+  // 退款金额
+  .aftersale-money {
+    background-color: #fff;
+    height: 98rpx;
+    padding: 0 20rpx;
+    margin: 20rpx;
+
+    .aftersale-money--title {
+      font-size: 28rpx;
+
+      font-weight: 500;
+      color: rgba(51, 51, 51, 1);
+    }
+
+    .aftersale-money--num {
+      font-size: 28rpx;
+      font-family: OPPOSANS;
+      font-weight: 500;
+      color: #ff3000;
+    }
+  }
+
+  // order-shop
+  .order-shop {
+    padding: 20rpx;
+    background-color: #fff;
+    margin: 0 20rpx 20rpx 20rpx;
+  }
+
+  // 服务内容
+  .aftersale-content {
+    background-color: #fff;
+    padding: 20rpx;
+    margin: 0 20rpx;
+
+    .aftersale-item {
+      height: 60rpx;
+
+      .copy-btn {
+        background: #eeeeee;
+        color: #333;
+        border-radius: 20rpx;
+        width: 75rpx;
+        height: 40rpx;
+        font-size: 22rpx;
+      }
+
+      .item-title {
+        color: #999;
+        font-size: 28rpx;
+      }
+
+      .item-content {
+        color: #333;
+        font-size: 28rpx;
+      }
+    }
+  }
+
+  // 底部功能
+  .foot_box {
+    height: 100rpx;
+    background-color: #fff;
+    display: flex;
+    align-items: center;
+    justify-content: flex-end;
+
+    .btn {
+      width: 160rpx;
+      line-height: 60rpx;
+      background: rgba(238, 238, 238, 1);
+      border-radius: 30rpx;
+      padding: 0;
+      margin-right: 20rpx;
+      font-size: 26rpx;
+
+      font-weight: 400;
+      color: rgba(51, 51, 51, 1);
+    }
+  }
+</style>

+ 170 - 147
pages/order/aftersale/list.vue

@@ -1,187 +1,210 @@
 <!-- 售后列表 -->
 <template>
-	<s-layout title="售后列表">
-		<!-- tab -->
-		<su-sticky bgColor="#fff">
-			<su-tabs :list="tabMaps" :scrollable="false" @change="onTabsChange" :current="state.currentTab" />
-		</su-sticky>
-		<s-empty v-if="state.pagination.total === 0" icon="/static/data-empty.png" text="暂无数据" />
-		<!-- 列表 -->
-		<view v-if="state.pagination.total > 0">
-			<view class="list-box ss-m-y-20" v-for="order in state.pagination.list" :key="order.id"
-				@tap="sheep.$router.go('/pages/order/aftersale/detail', { id: order.id })">
-				<view class="order-head ss-flex ss-col-center ss-row-between">
-					<text class="no">服务单号:{{ order.no }}</text>
-					<text class="state">{{ formatAfterSaleStatus(order) }}</text>
-				</view>
-				<s-goods-item
+  <s-layout title="售后列表">
+    <!-- tab -->
+    <su-sticky bgColor="#fff">
+      <su-tabs
+        :list="tabMaps"
+        :scrollable="false"
+        @change="onTabsChange"
+        :current="state.currentTab"
+      />
+    </su-sticky>
+    <s-empty v-if="state.pagination.total === 0" icon="/static/data-empty.png" text="暂无数据" />
+    <!-- 列表 -->
+    <view v-if="state.pagination.total > 0">
+      <view
+        class="list-box ss-m-y-20"
+        v-for="order in state.pagination.list"
+        :key="order.id"
+        @tap="sheep.$router.go('/pages/order/aftersale/detail', { id: order.id })"
+      >
+        <view class="order-head ss-flex ss-col-center ss-row-between">
+          <text class="no">服务单号:{{ order.no }}</text>
+          <text class="state">{{ formatAfterSaleStatus(order) }}</text>
+        </view>
+        <s-goods-item
           :img="order.picUrl"
           :title="order.spuName"
-					:skuText="order.properties.map((property) => property.valueName).join(' ')"
+          :skuText="order.properties.map((property) => property.valueName).join(' ')"
           :price="order.refundPrice"
         />
-				<view class="apply-box ss-flex ss-col-center ss-row-between border-bottom ss-p-x-20">
-					<view class="ss-flex ss-col-center">
-						<view class="title ss-m-r-20">{{ order.way === 10 ? '仅退款' : '退款退货' }}</view>
-						 <view class="value">{{ formatAfterSaleStatusDescription(order) }}</view>
-					</view>
-					<text class="_icon-forward"></text>
-				</view>
-				<view class="tool-btn-box ss-flex ss-col-center ss-row-right ss-p-r-20">
+        <view class="apply-box ss-flex ss-col-center ss-row-between border-bottom ss-p-x-20">
+          <view class="ss-flex ss-col-center">
+            <view class="title ss-m-r-20">{{ order.way === 10 ? '仅退款' : '退款退货' }}</view>
+            <view class="value">{{ formatAfterSaleStatusDescription(order) }}</view>
+          </view>
+          <text class="_icon-forward"></text>
+        </view>
+        <view class="tool-btn-box ss-flex ss-col-center ss-row-right ss-p-r-20">
           <!-- TODO 功能缺失:填写退货信息 -->
-					<view>
-						<button class="ss-reset-button tool-btn" @tap.stop="onApply(order.id)"
-							v-if="order?.buttons.includes('cancel')">取消申请</button>
-					</view>
-				</view>
-			</view>
-		</view>
-		<uni-load-more v-if="state.pagination.total > 0" :status="state.loadStatus" :content-text="{
+          <view>
+            <button
+              class="ss-reset-button tool-btn"
+              @tap.stop="onApply(order.id)"
+              v-if="order?.buttons.includes('cancel')"
+              >取消申请</button
+            >
+          </view>
+        </view>
+      </view>
+    </view>
+    <uni-load-more
+      v-if="state.pagination.total > 0"
+      :status="state.loadStatus"
+      :content-text="{
         contentdown: '上拉加载更多',
-      }" @tap="loadMore" />
-	</s-layout>
+      }"
+      @tap="loadMore"
+    />
+  </s-layout>
 </template>
 
 <script setup>
-	import sheep from '@/sheep';
-	import { onLoad, onReachBottom } from '@dcloudio/uni-app';
-	import { reactive } from 'vue';
-	import _ from 'lodash';
-  import { formatAfterSaleStatus, formatAfterSaleStatusDescription, handleAfterSaleButtons } from '@/sheep/hooks/useGoods';
+  import sheep from '@/sheep';
+  import { onLoad, onReachBottom } from '@dcloudio/uni-app';
+  import { reactive } from 'vue';
+  import _ from 'lodash-es';
+  import {
+    formatAfterSaleStatus,
+    formatAfterSaleStatusDescription,
+    handleAfterSaleButtons,
+  } from '@/sheep/hooks/useGoods';
   import AfterSaleApi from '@/sheep/api/trade/afterSale';
   import { resetPagination } from '@/sheep/util';
 
-	const state = reactive({
-		currentTab: 0,
-		showApply: false,
-		pagination: {
+  const state = reactive({
+    currentTab: 0,
+    showApply: false,
+    pagination: {
       list: [],
       total: 0,
       pageNo: 1,
-      pageSize: 10
-		},
-		loadStatus: '',
-	});
+      pageSize: 10,
+    },
+    loadStatus: '',
+  });
 
   // TODO 芋艿:优化点,增加筛选
-	const tabMaps = [{
-			name: '全部',
-			value: 'all',
-		},
-		// {
-		//   name: '申请中',
-		//   value: 'nooper',
-		// },
-		// {
-		//   name: '处理中',
-		//   value: 'ing',
-		// },
-		// {
-		//   name: '已完成',
-		//   value: 'completed',
-		// },
-		// {
-		//   name: '已拒绝',
-		//   value: 'refuse',
-		// },
-	];
-
-	// 切换选项卡
-	function onTabsChange(e) {
+  const tabMaps = [
+    {
+      name: '全部',
+      value: 'all',
+    },
+    // {
+    //   name: '申请中',
+    //   value: 'nooper',
+    // },
+    // {
+    //   name: '处理中',
+    //   value: 'ing',
+    // },
+    // {
+    //   name: '已完成',
+    //   value: 'completed',
+    // },
+    // {
+    //   name: '已拒绝',
+    //   value: 'refuse',
+    // },
+  ];
+
+  // 切换选项卡
+  function onTabsChange(e) {
     resetPagination(state.pagination);
-		state.currentTab = e.index;
-		getOrderList();
-	}
-
-	// 获取售后列表
-	async function getOrderList() {
-		state.loadStatus = 'loading';
-		let { data, code } = await AfterSaleApi.getAfterSalePage({
-			// type: tabMaps[state.currentTab].value,
+    state.currentTab = e.index;
+    getOrderList();
+  }
+
+  // 获取售后列表
+  async function getOrderList() {
+    state.loadStatus = 'loading';
+    let { data, code } = await AfterSaleApi.getAfterSalePage({
+      // type: tabMaps[state.currentTab].value,
       pageNo: state.pagination.pageNo,
       pageSize: state.pagination.pageSize,
-		});
-		if (code !== 0) {
+    });
+    if (code !== 0) {
       return;
-		}
-    data.list.forEach(order => handleAfterSaleButtons(order));
+    }
+    data.list.forEach((order) => handleAfterSaleButtons(order));
     state.pagination.list = _.concat(state.pagination.list, data.list);
     state.pagination.total = data.total;
     state.loadStatus = state.pagination.list.length < state.pagination.total ? 'more' : 'noMore';
-	}
-
-	function onApply(orderId) {
-		uni.showModal({
-			title: '提示',
-			content: '确定要取消此申请吗?',
-			success: async function(res) {
-				if (!res.confirm) {
+  }
+
+  function onApply(orderId) {
+    uni.showModal({
+      title: '提示',
+      content: '确定要取消此申请吗?',
+      success: async function (res) {
+        if (!res.confirm) {
           return;
-				}
+        }
         const { code } = await AfterSaleApi.cancelAfterSale(orderId);
         if (code === 0) {
           resetPagination(state.pagination);
           await getOrderList();
         }
-			},
-		});
-	}
-
-	onLoad(async (options) => {
-		if (options.type) {
-			state.currentTab = options.type;
-		}
-		await getOrderList();
-	});
-
-	// 加载更多
-	function loadMore() {
+      },
+    });
+  }
+
+  onLoad(async (options) => {
+    if (options.type) {
+      state.currentTab = options.type;
+    }
+    await getOrderList();
+  });
+
+  // 加载更多
+  function loadMore() {
     if (state.loadStatus === 'noMore') {
-      return
+      return;
     }
     state.pagination.pageNo++;
     getOrderList();
-	}
+  }
 
-	// 上拉加载更多
-	onReachBottom(() => {
-		loadMore();
-	});
+  // 上拉加载更多
+  onReachBottom(() => {
+    loadMore();
+  });
 </script>
 
 <style lang="scss" scoped>
-	.list-box {
-		background-color: #fff;
-
-		.order-head {
-			padding: 0 25rpx;
-			height: 77rpx;
-		}
-
-		.apply-box {
-			height: 82rpx;
-
-			.title {
-				font-size: 24rpx;
-			}
-
-			.value {
-				font-size: 22rpx;
-				color: $dark-6;
-			}
-		}
-
-		.tool-btn-box {
-			height: 100rpx;
-
-			.tool-btn {
-				width: 160rpx;
-				height: 60rpx;
-				background: #f6f6f6;
-				border-radius: 30rpx;
-				font-size: 26rpx;
-				font-weight: 400;
-			}
-		}
-	}
-</style>
+  .list-box {
+    background-color: #fff;
+
+    .order-head {
+      padding: 0 25rpx;
+      height: 77rpx;
+    }
+
+    .apply-box {
+      height: 82rpx;
+
+      .title {
+        font-size: 24rpx;
+      }
+
+      .value {
+        font-size: 22rpx;
+        color: $dark-6;
+      }
+    }
+
+    .tool-btn-box {
+      height: 100rpx;
+
+      .tool-btn {
+        width: 160rpx;
+        height: 60rpx;
+        background: #f6f6f6;
+        border-radius: 30rpx;
+        font-size: 26rpx;
+        font-weight: 400;
+      }
+    }
+  }
+</style>

+ 435 - 393
pages/order/list.vue

@@ -1,243 +1,284 @@
 <!-- 订单列表 -->
 <template>
-	<s-layout title="我的订单">
-		<su-sticky bgColor="#fff">
-			<su-tabs :list="tabMaps" :scrollable="false" @change="onTabsChange" :current="state.currentTab" />
-		</su-sticky>
-		<s-empty v-if="state.pagination.total === 0" icon="/static/order-empty.png" text="暂无订单" />
-		<view v-if="state.pagination.total > 0">
-			<view class="bg-white order-list-card-box ss-r-10 ss-m-t-14 ss-m-20" v-for="order in state.pagination.list"
-            :key="order.id" @tap="onOrderDetail(order.id)">
-				<view class="order-card-header ss-flex ss-col-center ss-row-between ss-p-x-20">
-					<view class="order-no">订单号:{{ order.no }}</view>
-					<view class="order-state ss-font-26" :class="formatOrderColor(order)">
+  <s-layout title="我的订单">
+    <su-sticky bgColor="#fff">
+      <su-tabs
+        :list="tabMaps"
+        :scrollable="false"
+        @change="onTabsChange"
+        :current="state.currentTab"
+      />
+    </su-sticky>
+    <s-empty v-if="state.pagination.total === 0" icon="/static/order-empty.png" text="暂无订单" />
+    <view v-if="state.pagination.total > 0">
+      <view
+        class="bg-white order-list-card-box ss-r-10 ss-m-t-14 ss-m-20"
+        v-for="order in state.pagination.list"
+        :key="order.id"
+        @tap="onOrderDetail(order.id)"
+      >
+        <view class="order-card-header ss-flex ss-col-center ss-row-between ss-p-x-20">
+          <view class="order-no">订单号:{{ order.no }}</view>
+          <view class="order-state ss-font-26" :class="formatOrderColor(order)">
             {{ formatOrderStatus(order) }}
           </view>
-				</view>
-				<view class="border-bottom" v-for="item in order.items" :key="item.id">
-					<s-goods-item
+        </view>
+        <view class="border-bottom" v-for="item in order.items" :key="item.id">
+          <s-goods-item
             :img="item.picUrl"
             :title="item.spuName"
-						:skuText="item.properties.map((property) => property.valueName).join(' ')"
-						:price="item.price"
+            :skuText="item.properties.map((property) => property.valueName).join(' ')"
+            :price="item.price"
             :num="item.count"
           />
-				</view>
-				<view class="pay-box ss-m-t-30 ss-flex ss-row-right ss-p-r-20">
-					<view class="ss-flex ss-col-center">
-						<view class="discounts-title pay-color">共 {{ order.productCount }} 件商品,总金额:</view>
-						<view class="discounts-money pay-color">
-							¥{{ fen2yuan(order.payPrice) }}
-            </view>
-					</view>
-				</view>
-				<view class="order-card-footer ss-flex ss-col-center ss-p-x-20"
-              :class="order.buttons.length > 3 ? 'ss-row-between' : 'ss-row-right'">
-					<view class="ss-flex ss-col-center">
-						<button v-if="order.buttons.includes('combination')" class="tool-btn ss-reset-button"
-							@tap.stop="onOrderGroupon(order)">
+        </view>
+        <view class="pay-box ss-m-t-30 ss-flex ss-row-right ss-p-r-20">
+          <view class="ss-flex ss-col-center">
+            <view class="discounts-title pay-color"
+              >共 {{ order.productCount }} 件商品,总金额:</view
+            >
+            <view class="discounts-money pay-color"> ¥{{ fen2yuan(order.payPrice) }} </view>
+          </view>
+        </view>
+        <view
+          class="order-card-footer ss-flex ss-col-center ss-p-x-20"
+          :class="order.buttons.length > 3 ? 'ss-row-between' : 'ss-row-right'"
+        >
+          <view class="ss-flex ss-col-center">
+            <button
+              v-if="order.buttons.includes('combination')"
+              class="tool-btn ss-reset-button"
+              @tap.stop="onOrderGroupon(order)"
+            >
               拼团详情
-						</button>
-						<button v-if="order.buttons.length === 0" class="tool-btn ss-reset-button"
-                    @tap.stop="onOrderDetail(order.id)">
+            </button>
+            <button
+              v-if="order.buttons.length === 0"
+              class="tool-btn ss-reset-button"
+              @tap.stop="onOrderDetail(order.id)"
+            >
               查看详情
-						</button>
-						<button v-if="order.buttons.includes('confirm')" class="tool-btn ss-reset-button"
-                    @tap.stop="onConfirm(order)">
+            </button>
+            <button
+              v-if="order.buttons.includes('confirm')"
+              class="tool-btn ss-reset-button"
+              @tap.stop="onConfirm(order)"
+            >
               确认收货
-						</button>
-						<button v-if="order.buttons.includes('express')" class="tool-btn ss-reset-button"
-                    @tap.stop="onExpress(order.id)">
-							查看物流
-						</button>
-						<button v-if="order.buttons.includes('cancel')" class="tool-btn ss-reset-button"
-                    @tap.stop="onCancel(order.id)">
-							取消订单
-						</button>
-						<button v-if="order.buttons.includes('comment')" class="tool-btn ss-reset-button"
-                    @tap.stop="onComment(order.id)">
-							评价
-						</button>
-						<button v-if="order.buttons.includes('delete')" class="delete-btn ss-reset-button"
-                    @tap.stop="onDelete(order.id)">
-							删除订单
-						</button>
-						<button v-if="order.buttons.includes('pay')" class="tool-btn ss-reset-button ui-BG-Main-Gradient"
-                    @tap.stop="onPay(order.payOrderId)">
-							继续支付
-						</button>
-					</view>
-				</view>
-			</view>
-		</view>
-
-		<!-- 加载更多 -->
-		<uni-load-more v-if="state.pagination.total > 0" :status="state.loadStatus" :content-text="{
+            </button>
+            <button
+              v-if="order.buttons.includes('express')"
+              class="tool-btn ss-reset-button"
+              @tap.stop="onExpress(order.id)"
+            >
+              查看物流
+            </button>
+            <button
+              v-if="order.buttons.includes('cancel')"
+              class="tool-btn ss-reset-button"
+              @tap.stop="onCancel(order.id)"
+            >
+              取消订单
+            </button>
+            <button
+              v-if="order.buttons.includes('comment')"
+              class="tool-btn ss-reset-button"
+              @tap.stop="onComment(order.id)"
+            >
+              评价
+            </button>
+            <button
+              v-if="order.buttons.includes('delete')"
+              class="delete-btn ss-reset-button"
+              @tap.stop="onDelete(order.id)"
+            >
+              删除订单
+            </button>
+            <button
+              v-if="order.buttons.includes('pay')"
+              class="tool-btn ss-reset-button ui-BG-Main-Gradient"
+              @tap.stop="onPay(order.payOrderId)"
+            >
+              继续支付
+            </button>
+          </view>
+        </view>
+      </view>
+    </view>
+
+    <!-- 加载更多 -->
+    <uni-load-more
+      v-if="state.pagination.total > 0"
+      :status="state.loadStatus"
+      :content-text="{
         contentdown: '上拉加载更多',
-      }" @tap="loadMore" />
-	</s-layout>
+      }"
+      @tap="loadMore"
+    />
+  </s-layout>
 </template>
 
 <script setup>
-	import { reactive } from 'vue';
-	import { onLoad, onReachBottom, onPullDownRefresh } from '@dcloudio/uni-app';
+  import { reactive } from 'vue';
+  import { onLoad, onReachBottom, onPullDownRefresh } from '@dcloudio/uni-app';
   import {
     fen2yuan,
-    formatOrderColor, formatOrderStatus, handleOrderButtons,
+    formatOrderColor,
+    formatOrderStatus,
+    handleOrderButtons,
   } from '@/sheep/hooks/useGoods';
-	import sheep from '@/sheep';
-	import _ from 'lodash';
-	import {
-		isEmpty
-	} from 'lodash';
+  import sheep from '@/sheep';
+  import _ from 'lodash-es';
+  import { isEmpty } from 'lodash-es';
   import OrderApi from '@/sheep/api/trade/order';
   import { resetPagination } from '@/sheep/util';
 
-	// 数据
-	const state = reactive({
-		currentTab: 0, // 选中的 tabMaps 下标
-		pagination: {
+  // 数据
+  const state = reactive({
+    currentTab: 0, // 选中的 tabMaps 下标
+    pagination: {
       list: [],
       total: 0,
       pageNo: 1,
       pageSize: 5,
-		},
-		loadStatus: ''
-	});
-
-	const tabMaps = [{
-			name: '全部'
-		},
-		{
-			name: '待付款',
-			value: 0,
-		},
-		{
-			name: '待发货',
-			value: 10,
-		},
-		{
-			name: '待收货',
-			value: 20,
-		},
-		{
-			name: '待评价',
-			value: 30,
-		},
-	];
-
-	// 切换选项卡
-	function onTabsChange(e) {
-		if (state.currentTab === e.index) {
+    },
+    loadStatus: '',
+  });
+
+  const tabMaps = [
+    {
+      name: '全部',
+    },
+    {
+      name: '待付款',
+      value: 0,
+    },
+    {
+      name: '待发货',
+      value: 10,
+    },
+    {
+      name: '待收货',
+      value: 20,
+    },
+    {
+      name: '待评价',
+      value: 30,
+    },
+  ];
+
+  // 切换选项卡
+  function onTabsChange(e) {
+    if (state.currentTab === e.index) {
       return;
     }
     // 重头加载代码
-		resetPagination(state.pagination);
-		state.currentTab = e.index;
-		getOrderList();
-	}
-
-	// 订单详情
-	function onOrderDetail(id) {
-		sheep.$router.go('/pages/order/detail', {
-			id,
-		});
-	}
-
-	// 跳转拼团记录的详情
-	function onOrderGroupon(order) {
-		sheep.$router.go('/pages/activity/groupon/detail', {
-			id: order.combinationRecordId,
-		});
-	}
-
-	// 继续支付
-	function onPay(payOrderId) {
-		sheep.$router.go('/pages/pay/index', {
-			id: payOrderId,
-		});
-	}
-
-	// 评价
-	function onComment(id) {
-		sheep.$router.go('/pages/goods/comment/add', {
-			id,
-		});
-	}
-
-	// 确认收货 TODO 芋艿:待测试
-	async function onConfirm(order, ignore = false) {
-		// 需开启确认收货组件
-		// todo: 芋艿:需要后续接入微信收货组件
-		// 1.怎么检测是否开启了发货组件功能?如果没有开启的话就不能在这里return出去
-		// 2.如果开启了走mpConfirm方法,需要在App.vue的show方法中拿到确认收货结果
-		let isOpenBusinessView = true;
-		if (
-			sheep.$platform.name === 'WechatMiniProgram' &&
-			!isEmpty(order.wechat_extra_data) &&
-			isOpenBusinessView &&
-			!ignore
-		) {
-			mpConfirm(order);
-			return;
-		}
-
-		// 正常的确认收货流程
-		const { code } = await OrderApi.receiveOrder(order.id);
-		if (code === 0) {
+    resetPagination(state.pagination);
+    state.currentTab = e.index;
+    getOrderList();
+  }
+
+  // 订单详情
+  function onOrderDetail(id) {
+    sheep.$router.go('/pages/order/detail', {
+      id,
+    });
+  }
+
+  // 跳转拼团记录的详情
+  function onOrderGroupon(order) {
+    sheep.$router.go('/pages/activity/groupon/detail', {
+      id: order.combinationRecordId,
+    });
+  }
+
+  // 继续支付
+  function onPay(payOrderId) {
+    sheep.$router.go('/pages/pay/index', {
+      id: payOrderId,
+    });
+  }
+
+  // 评价
+  function onComment(id) {
+    sheep.$router.go('/pages/goods/comment/add', {
+      id,
+    });
+  }
+
+  // 确认收货 TODO 芋艿:待测试
+  async function onConfirm(order, ignore = false) {
+    // 需开启确认收货组件
+    // todo: 芋艿:需要后续接入微信收货组件
+    // 1.怎么检测是否开启了发货组件功能?如果没有开启的话就不能在这里return出去
+    // 2.如果开启了走mpConfirm方法,需要在App.vue的show方法中拿到确认收货结果
+    let isOpenBusinessView = true;
+    if (
+      sheep.$platform.name === 'WechatMiniProgram' &&
+      !isEmpty(order.wechat_extra_data) &&
+      isOpenBusinessView &&
+      !ignore
+    ) {
+      mpConfirm(order);
+      return;
+    }
+
+    // 正常的确认收货流程
+    const { code } = await OrderApi.receiveOrder(order.id);
+    if (code === 0) {
       resetPagination(state.pagination);
       await getOrderList();
-		}
-	}
-
-	// #ifdef MP-WEIXIN
-	// 小程序确认收货组件 TODO 芋艿:后续再接入
-	function mpConfirm(order) {
-		if (!wx.openBusinessView) {
-			sheep.$helper.toast(`请升级微信版本`);
-			return;
-		}
-		wx.openBusinessView({
-			businessType: 'weappOrderConfirm',
-			extraData: {
-				merchant_id: '1481069012',
-				merchant_trade_no: order.wechat_extra_data.merchant_trade_no,
-				transaction_id: order.wechat_extra_data.transaction_id,
-			},
-			success(response) {
-				console.log('success:', response);
-				if (response.errMsg === 'openBusinessView:ok') {
-					if (response.extraData.status === 'success') {
-						onConfirm(order, true);
-					}
-				}
-			},
-			fail(error) {
-				console.log('error:', error);
-			},
-			complete(result) {
-				console.log('result:', result);
-			},
-		});
-	}
-	// #endif
-
-	// 查看物流
-	async function onExpress(id) {
-		sheep.$router.go('/pages/order/express/log', {
+    }
+  }
+
+  // #ifdef MP-WEIXIN
+  // 小程序确认收货组件 TODO 芋艿:后续再接入
+  function mpConfirm(order) {
+    if (!wx.openBusinessView) {
+      sheep.$helper.toast(`请升级微信版本`);
+      return;
+    }
+    wx.openBusinessView({
+      businessType: 'weappOrderConfirm',
+      extraData: {
+        merchant_id: '1481069012',
+        merchant_trade_no: order.wechat_extra_data.merchant_trade_no,
+        transaction_id: order.wechat_extra_data.transaction_id,
+      },
+      success(response) {
+        console.log('success:', response);
+        if (response.errMsg === 'openBusinessView:ok') {
+          if (response.extraData.status === 'success') {
+            onConfirm(order, true);
+          }
+        }
+      },
+      fail(error) {
+        console.log('error:', error);
+      },
+      complete(result) {
+        console.log('result:', result);
+      },
+    });
+  }
+  // #endif
+
+  // 查看物流
+  async function onExpress(id) {
+    sheep.$router.go('/pages/order/express/log', {
       id,
-		});
-	}
-
-	// 取消订单
-	async function onCancel(orderId) {
-		uni.showModal({
-			title: '提示',
-			content: '确定要取消订单吗?',
-			success: async function(res) {
-				if (!res.confirm) {
+    });
+  }
+
+  // 取消订单
+  async function onCancel(orderId) {
+    uni.showModal({
+      title: '提示',
+      content: '确定要取消订单吗?',
+      success: async function (res) {
+        if (!res.confirm) {
           return;
-				}
+        }
         const { code } = await OrderApi.cancelOrder(orderId);
         if (code === 0) {
           // 修改数据的状态
@@ -246,208 +287,209 @@
           orderInfo.status = 40;
           handleOrderButtons(orderInfo);
         }
-			},
-		});
-	}
-
-	// 删除订单
-	function onDelete(orderId) {
-		uni.showModal({
-			title: '提示',
-			content: '确定要删除订单吗?',
-			success: async function(res) {
-				if (res.confirm) {
-					const { code } = await OrderApi.deleteOrder(orderId);
-					if (code === 0) {
+      },
+    });
+  }
+
+  // 删除订单
+  function onDelete(orderId) {
+    uni.showModal({
+      title: '提示',
+      content: '确定要删除订单吗?',
+      success: async function (res) {
+        if (res.confirm) {
+          const { code } = await OrderApi.deleteOrder(orderId);
+          if (code === 0) {
             // 删除数据
-						let index = state.pagination.list.findIndex((order) => order.id === orderId);
-						state.pagination.list.splice(index, 1);
-					}
-				}
-			},
-		});
-	}
-
-	// 获取订单列表
-	async function getOrderList() {
-		state.loadStatus = 'loading';
-		let { code, data } = await OrderApi.getOrderPage({
+            let index = state.pagination.list.findIndex((order) => order.id === orderId);
+            state.pagination.list.splice(index, 1);
+          }
+        }
+      },
+    });
+  }
+
+  // 获取订单列表
+  async function getOrderList() {
+    state.loadStatus = 'loading';
+    let { code, data } = await OrderApi.getOrderPage({
       pageNo: state.pagination.pageNo,
       pageSize: state.pagination.pageSize,
       status: tabMaps[state.currentTab].value,
-			commentStatus: tabMaps[state.currentTab].value === 30 ? false : null
-		});
+      commentStatus: tabMaps[state.currentTab].value === 30 ? false : null,
+    });
     if (code !== 0) {
       return;
     }
-    data.list.forEach(order => handleOrderButtons(order));
-    state.pagination.list = _.concat(state.pagination.list, data.list)
+    data.list.forEach((order) => handleOrderButtons(order));
+    state.pagination.list = _.concat(state.pagination.list, data.list);
     state.pagination.total = data.total;
     state.loadStatus = state.pagination.list.length < state.pagination.total ? 'more' : 'noMore';
   }
 
-	onLoad(async (options) => {
-		if (options.type) {
-			state.currentTab = options.type;
-		}
-		await getOrderList();
-	});
-
-	// 加载更多
-	function loadMore() {
-		if (state.loadStatus === 'noMore') {
-      return
-		}
+  onLoad(async (options) => {
+    if (options.type) {
+      state.currentTab = options.type;
+    }
+    await getOrderList();
+  });
+
+  // 加载更多
+  function loadMore() {
+    if (state.loadStatus === 'noMore') {
+      return;
+    }
     state.pagination.pageNo++;
     getOrderList();
   }
 
-	// 上拉加载更多
-	onReachBottom(() => {
-		loadMore();
-	});
+  // 上拉加载更多
+  onReachBottom(() => {
+    loadMore();
+  });
 
-	// 下拉刷新
-	onPullDownRefresh(() => {
+  // 下拉刷新
+  onPullDownRefresh(() => {
     resetPagination(state.pagination);
-		getOrderList();
-		setTimeout(function() {
-			uni.stopPullDownRefresh();
-		}, 800);
-	});
+    getOrderList();
+    setTimeout(function () {
+      uni.stopPullDownRefresh();
+    }, 800);
+  });
 </script>
 
 <style lang="scss" scoped>
-	.score-img {
-		width: 36rpx;
-		height: 36rpx;
-		margin: 0 4rpx;
-	}
-
-	.tool-btn {
-		width: 160rpx;
-		height: 60rpx;
-		background: #f6f6f6;
-		font-size: 26rpx;
-		border-radius: 30rpx;
-		margin-right: 10rpx;
-
-		&:last-of-type {
-			margin-right: 0;
-		}
-	}
-
-	.delete-btn {
-		width: 160rpx;
-		height: 56rpx;
-		color: #ff3000;
-		background: #fee;
-		border-radius: 28rpx;
-		font-size: 26rpx;
-		margin-right: 10rpx;
-		line-height: normal;
-
-		&:last-of-type {
-			margin-right: 0;
-		}
-	}
-
-	.apply-btn {
-		width: 140rpx;
-		height: 50rpx;
-		border-radius: 25rpx;
-		font-size: 24rpx;
-		border: 2rpx solid #dcdcdc;
-		line-height: normal;
-		margin-left: 16rpx;
-	}
-
-	.swiper-box {
-		flex: 1;
-
-		.swiper-item {
-			height: 100%;
-			width: 100%;
-		}
-	}
-
-	.order-list-card-box {
-		.order-card-header {
-			height: 80rpx;
-
-			.order-no {
-				font-size: 26rpx;
-				font-weight: 500;
-			}
-
-			.order-state {}
-		}
-
-		.pay-box {
-			.discounts-title {
-				font-size: 24rpx;
-				line-height: normal;
-				color: #999999;
-			}
-
-			.discounts-money {
-				font-size: 24rpx;
-				line-height: normal;
-				color: #999;
-				font-family: OPPOSANS;
-			}
-
-			.pay-color {
-				color: #333;
-			}
-		}
-
-		.order-card-footer {
-			height: 100rpx;
-
-			.more-item-box {
-				padding: 20rpx;
-
-				.more-item {
-					height: 60rpx;
-
-					.title {
-						font-size: 26rpx;
-					}
-				}
-			}
-
-			.more-btn {
-				color: $dark-9;
-				font-size: 24rpx;
-			}
-
-			.content {
-				width: 154rpx;
-				color: #333333;
-				font-size: 26rpx;
-				font-weight: 500;
-			}
-		}
-	}
-
-	:deep(.uni-tooltip-popup) {
-		background: var(--ui-BG);
-	}
-
-	.warning-color {
-		color: #faad14;
-	}
-
-	.danger-color {
-		color: #ff3000;
-	}
-
-	.success-color {
-		color: #52c41a;
-	}
-
-	.info-color {
-		color: #999999;
-	}
-</style>
+  .score-img {
+    width: 36rpx;
+    height: 36rpx;
+    margin: 0 4rpx;
+  }
+
+  .tool-btn {
+    width: 160rpx;
+    height: 60rpx;
+    background: #f6f6f6;
+    font-size: 26rpx;
+    border-radius: 30rpx;
+    margin-right: 10rpx;
+
+    &:last-of-type {
+      margin-right: 0;
+    }
+  }
+
+  .delete-btn {
+    width: 160rpx;
+    height: 56rpx;
+    color: #ff3000;
+    background: #fee;
+    border-radius: 28rpx;
+    font-size: 26rpx;
+    margin-right: 10rpx;
+    line-height: normal;
+
+    &:last-of-type {
+      margin-right: 0;
+    }
+  }
+
+  .apply-btn {
+    width: 140rpx;
+    height: 50rpx;
+    border-radius: 25rpx;
+    font-size: 24rpx;
+    border: 2rpx solid #dcdcdc;
+    line-height: normal;
+    margin-left: 16rpx;
+  }
+
+  .swiper-box {
+    flex: 1;
+
+    .swiper-item {
+      height: 100%;
+      width: 100%;
+    }
+  }
+
+  .order-list-card-box {
+    .order-card-header {
+      height: 80rpx;
+
+      .order-no {
+        font-size: 26rpx;
+        font-weight: 500;
+      }
+
+      .order-state {
+      }
+    }
+
+    .pay-box {
+      .discounts-title {
+        font-size: 24rpx;
+        line-height: normal;
+        color: #999999;
+      }
+
+      .discounts-money {
+        font-size: 24rpx;
+        line-height: normal;
+        color: #999;
+        font-family: OPPOSANS;
+      }
+
+      .pay-color {
+        color: #333;
+      }
+    }
+
+    .order-card-footer {
+      height: 100rpx;
+
+      .more-item-box {
+        padding: 20rpx;
+
+        .more-item {
+          height: 60rpx;
+
+          .title {
+            font-size: 26rpx;
+          }
+        }
+      }
+
+      .more-btn {
+        color: $dark-9;
+        font-size: 24rpx;
+      }
+
+      .content {
+        width: 154rpx;
+        color: #333333;
+        font-size: 26rpx;
+        font-weight: 500;
+      }
+    }
+  }
+
+  :deep(.uni-tooltip-popup) {
+    background: var(--ui-BG);
+  }
+
+  .warning-color {
+    color: #faad14;
+  }
+
+  .danger-color {
+    color: #ff3000;
+  }
+
+  .success-color {
+    color: #52c41a;
+  }
+
+  .info-color {
+    color: #999999;
+  }
+</style>

+ 5 - 3
pages/pay/recharge-log.vue

@@ -8,7 +8,7 @@
           <view class="title">充值金额</view>
           <view class="num" :class="item.refundStatus === 10 ? 'danger-color' : 'success-color'">
             {{ fen2yuan(item.payPrice) }} 元
-            <text v-if="item.bonusPrice > 0">(赠送 {{ fen2yuan(item.bonusPrice)}} 元)</text>
+            <text v-if="item.bonusPrice > 0">(赠送 {{ fen2yuan(item.bonusPrice) }} 元)</text>
           </view>
         </view>
         <view class="status-box item ss-flex ss-col-center ss-row-between">
@@ -30,7 +30,9 @@
         </view>
         <view class="time-box item ss-flex ss-col-center ss-row-between">
           <text class="item-title">充值时间</text>
-          <view class="time"> {{ sheep.$helper.timeFormat(item.payTime, 'yyyy-mm-dd hh:MM:ss') }}</view>
+          <view class="time">
+            {{ sheep.$helper.timeFormat(item.payTime, 'yyyy-mm-dd hh:MM:ss') }}</view
+          >
         </view>
       </view>
     </view>
@@ -53,7 +55,7 @@
 <script setup>
   import { reactive } from 'vue';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import PayWalletApi from '@/sheep/api/pay/wallet';
   import sheep from '@/sheep';
   import { fen2yuan } from '../../sheep/hooks/useGoods';

+ 12 - 9
pages/pay/result.vue

@@ -50,7 +50,10 @@
       </view>
 
       <!-- #ifdef MP -->
-      <view class="subscribe-box ss-flex ss-m-t-44" v-if="showSubscribeBtn && state.orderType === 'goods'">
+      <view
+        class="subscribe-box ss-flex ss-m-t-44"
+        v-if="showSubscribeBtn && state.orderType === 'goods'"
+      >
         <image class="subscribe-img" :src="sheep.$url.static('/static/img/shop/order/cargo.png')" />
         <view class="subscribe-title ss-m-r-48 ss-m-l-16">获取实时发货信息与订单状态</view>
         <view class="subscribe-start" @tap="subscribeMessage">立即订阅</view>
@@ -63,7 +66,7 @@
 <script setup>
   import { onLoad, onHide, onShow } from '@dcloudio/uni-app';
   import { reactive, computed, ref } from 'vue';
-  import { isEmpty } from 'lodash';
+  import { isEmpty } from 'lodash-es';
   import sheep from '@/sheep';
   import PayOrderApi from '@/sheep/api/pay/order';
   import { fen2yuan } from '@/sheep/hooks/useGoods';
@@ -114,12 +117,12 @@
         uni.showModal({
           title: '支付结果',
           showCancel: false, // 不要取消按钮
-          content: "支付成功",
+          content: '支付成功',
           success: () => {
             // 订阅只能由用户主动触发,只能包一层 showModal 诱导用户点击
             autoSubscribeMessage();
-          }
-        })
+          },
+        });
 
         // #endif
         // 特殊:获得商品订单信息
@@ -153,8 +156,8 @@
   }
 
   // #ifdef MP
-  const showSubscribeBtn = ref(false) // 默认隐藏
-  const SUBSCRIBE_BTN_STATUS_STORAGE_KEY = "subscribe_btn_status"
+  const showSubscribeBtn = ref(false); // 默认隐藏
+  const SUBSCRIBE_BTN_STATUS_STORAGE_KEY = 'subscribe_btn_status';
   function subscribeMessage() {
     if (state.orderType !== 'goods') {
       return;
@@ -176,11 +179,11 @@
     const subscribeBtnStatus = uni.getStorageSync(SUBSCRIBE_BTN_STATUS_STORAGE_KEY);
     if (!subscribeBtnStatus) {
       showSubscribeBtn.value = true;
-      return
+      return;
     }
 
     // 2. 订阅消息
-    subscribeMessage()
+    subscribeMessage();
   }
   // #endif
 

+ 213 - 165
pages/user/address/edit.vue

@@ -1,78 +1,118 @@
 <!-- 收货地址的新增/编辑 -->
 <template>
-	<s-layout :title="state.model.id ? '编辑地址' : '新增地址'">
-		<uni-forms ref="addressFormRef" v-model="state.model" :rules="rules" validateTrigger="bind"
-			labelWidth="160" labelAlign="left" border :labelStyle="{ fontWeight: 'bold' }">
-			<view class="bg-white form-box ss-p-x-30">
-				<uni-forms-item name="name" label="收货人" class="form-item">
-					<uni-easyinput v-model="state.model.name" placeholder="请填写收货人姓名" :inputBorder="false"
-						placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal" />
-				</uni-forms-item>
+  <s-layout :title="state.model.id ? '编辑地址' : '新增地址'">
+    <uni-forms
+      ref="addressFormRef"
+      v-model="state.model"
+      :rules="rules"
+      validateTrigger="bind"
+      labelWidth="160"
+      labelAlign="left"
+      border
+      :labelStyle="{ fontWeight: 'bold' }"
+    >
+      <view class="bg-white form-box ss-p-x-30">
+        <uni-forms-item name="name" label="收货人" class="form-item">
+          <uni-easyinput
+            v-model="state.model.name"
+            placeholder="请填写收货人姓名"
+            :inputBorder="false"
+            placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal"
+          />
+        </uni-forms-item>
 
-				<uni-forms-item name="mobile" label="手机号" class="form-item">
-					<uni-easyinput v-model="state.model.mobile" type="number" placeholder="请输入手机号" :inputBorder="false"
-						placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal">
-					</uni-easyinput>
-				</uni-forms-item>
-				<uni-forms-item name="areaName" label="省市区" @tap="state.showRegion = true" class="form-item">
-					<uni-easyinput v-model="state.model.areaName" disabled :inputBorder="false"
-						:styles="{ disableColor: '#fff', color: '#333' }"
-						placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal"
-						placeholder="请选择省市区">
-						<template v-slot:right>
-							<uni-icons type="right" />
-						</template>
-					</uni-easyinput>
-				</uni-forms-item>
-				<uni-forms-item name="detailAddress" label="详细地址" :formItemStyle="{ alignItems: 'flex-start' }"
-					:labelStyle="{ lineHeight: '5em' }" class="textarea-item">
-					<uni-easyinput :inputBorder="false" type="textarea" v-model="state.model.detailAddress"
-						placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal"
-						placeholder="请输入详细地址" clearable />
-				</uni-forms-item>
-			</view>
-			<view class="ss-m-y-20 bg-white ss-p-x-30 ss-flex ss-row-between ss-col-center default-box">
-				<view class="default-box-title"> 设为默认地址 </view>
-				<su-switch style="transform: scale(0.8)" v-model="state.model.defaultStatus" />
-			</view>
-		</uni-forms>
-		<su-fixed bottom :opacity="false" bg="" placeholder :noFixed="false" :index="10">
-			<view class="footer-box ss-flex-col ss-row-between ss-p-20">
-				<view class="ss-m-b-20">
+        <uni-forms-item name="mobile" label="手机号" class="form-item">
+          <uni-easyinput
+            v-model="state.model.mobile"
+            type="number"
+            placeholder="请输入手机号"
+            :inputBorder="false"
+            placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal"
+          >
+          </uni-easyinput>
+        </uni-forms-item>
+        <uni-forms-item
+          name="areaName"
+          label="省市区"
+          @tap="state.showRegion = true"
+          class="form-item"
+        >
+          <uni-easyinput
+            v-model="state.model.areaName"
+            disabled
+            :inputBorder="false"
+            :styles="{ disableColor: '#fff', color: '#333' }"
+            placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal"
+            placeholder="请选择省市区"
+          >
+            <template v-slot:right>
+              <uni-icons type="right" />
+            </template>
+          </uni-easyinput>
+        </uni-forms-item>
+        <uni-forms-item
+          name="detailAddress"
+          label="详细地址"
+          :formItemStyle="{ alignItems: 'flex-start' }"
+          :labelStyle="{ lineHeight: '5em' }"
+          class="textarea-item"
+        >
+          <uni-easyinput
+            :inputBorder="false"
+            type="textarea"
+            v-model="state.model.detailAddress"
+            placeholderStyle="color:#BBBBBB;font-size:30rpx;font-weight:400;line-height:normal"
+            placeholder="请输入详细地址"
+            clearable
+          />
+        </uni-forms-item>
+      </view>
+      <view class="ss-m-y-20 bg-white ss-p-x-30 ss-flex ss-row-between ss-col-center default-box">
+        <view class="default-box-title"> 设为默认地址 </view>
+        <su-switch style="transform: scale(0.8)" v-model="state.model.defaultStatus" />
+      </view>
+    </uni-forms>
+    <su-fixed bottom :opacity="false" bg="" placeholder :noFixed="false" :index="10">
+      <view class="footer-box ss-flex-col ss-row-between ss-p-20">
+        <view class="ss-m-b-20">
           <button class="ss-reset-button save-btn ui-Shadow-Main" @tap="onSave">保存</button>
         </view>
-				<button v-if="state.model.id" class="ss-reset-button cancel-btn" @tap="onDelete">
-					删除
-				</button>
-			</view>
-		</su-fixed>
+        <button v-if="state.model.id" class="ss-reset-button cancel-btn" @tap="onDelete">
+          删除
+        </button>
+      </view>
+    </su-fixed>
 
-		<!-- 省市区弹窗 -->
-		<su-region-picker :show="state.showRegion" @cancel="state.showRegion = false" @confirm="onRegionConfirm" />
-	</s-layout>
+    <!-- 省市区弹窗 -->
+    <su-region-picker
+      :show="state.showRegion"
+      @cancel="state.showRegion = false"
+      @confirm="onRegionConfirm"
+    />
+  </s-layout>
 </template>
 
 <script setup>
-	import { ref, reactive, unref } from 'vue';
-	import sheep from '@/sheep';
-	import { onLoad } from '@dcloudio/uni-app';
-	import _ from 'lodash';
-	import { mobile } from '@/sheep/validate/form';
+  import { ref, reactive, unref } from 'vue';
+  import sheep from '@/sheep';
+  import { onLoad } from '@dcloudio/uni-app';
+  import _ from 'lodash-es';
+  import { mobile } from '@/sheep/validate/form';
   import AreaApi from '@/sheep/api/system/area';
   import AddressApi from '@/sheep/api/member/address';
 
-	const addressFormRef = ref(null);
-	const state = reactive({
-		showRegion: false,
-		model: {
-			name: '',
-			mobile: '',
+  const addressFormRef = ref(null);
+  const state = reactive({
+    showRegion: false,
+    model: {
+      name: '',
+      mobile: '',
       detailAddress: '',
-			defaultStatus: false,
+      defaultStatus: false,
       areaName: '',
-		},
+    },
     rules: {},
-	});
+  });
 
   const rules = {
     name: {
@@ -85,93 +125,99 @@
     },
     mobile,
     detailAddress: {
-      rules: [{
-        required: true,
-        errorMessage: '请输入详细地址',
-      }]
+      rules: [
+        {
+          required: true,
+          errorMessage: '请输入详细地址',
+        },
+      ],
     },
     areaName: {
-      rules: [{
-        required: true,
-        errorMessage: '请选择您的位置'
-      }]
+      rules: [
+        {
+          required: true,
+          errorMessage: '请选择您的位置',
+        },
+      ],
     },
   };
 
   // 确认选择地区
-	const onRegionConfirm = (e) => {
-    state.model.areaName = `${e.province_name} ${e.city_name} ${e.district_name}`
+  const onRegionConfirm = (e) => {
+    state.model.areaName = `${e.province_name} ${e.city_name} ${e.district_name}`;
     state.model.areaId = e.district_id;
-		state.showRegion = false;
-	};
+    state.showRegion = false;
+  };
 
   // 获得地区数据
-	const getAreaData = () => {
-		if (_.isEmpty(uni.getStorageSync('areaData'))) {
+  const getAreaData = () => {
+    if (_.isEmpty(uni.getStorageSync('areaData'))) {
       AreaApi.getAreaTree().then((res) => {
         if (res.code === 0) {
           uni.setStorageSync('areaData', res.data);
         }
       });
-		}
-	};
+    }
+  };
 
   // 保存收货地址
-	const onSave = async () => {
+  const onSave = async () => {
     // 参数校验
-		const validate = await unref(addressFormRef)
-			.validate()
-			.catch((error) => {
-				console.log('error: ', error);
-			});
-		if (!validate) {
+    const validate = await unref(addressFormRef)
+      .validate()
+      .catch((error) => {
+        console.log('error: ', error);
+      });
+    if (!validate) {
       return;
     }
 
     // 提交请求
     const formData = {
-      ...state.model
+      ...state.model,
+    };
+    const { code } =
+      state.model.id > 0
+        ? await AddressApi.updateAddress(formData)
+        : await AddressApi.createAddress(formData);
+    if (code === 0) {
+      sheep.$router.back();
     }
-    const {code } = state.model.id > 0 ? await AddressApi.updateAddress(formData)
-      : await AddressApi.createAddress(formData);
-		if (code === 0) {
-			sheep.$router.back();
-		}
-	};
+  };
 
   // 删除收货地址
-	const onDelete = () => {
-		uni.showModal({
-			title: '提示',
-			content: '确认删除此收货地址吗?',
-			success: async function(res) {
-				if (!res.confirm) {
-					return;
-				}
+  const onDelete = () => {
+    uni.showModal({
+      title: '提示',
+      content: '确认删除此收货地址吗?',
+      success: async function (res) {
+        if (!res.confirm) {
+          return;
+        }
         const { code } = await AddressApi.deleteAddress(state.model.id);
         if (code === 0) {
           sheep.$router.back();
         }
-			},
-		});
-	};
+      },
+    });
+  };
 
-	onLoad(async (options) => {
+  onLoad(async (options) => {
     // 获得地区数据
-		getAreaData();
+    getAreaData();
     // 情况一:基于 id 获得收件地址
-		if (options.id) {
-			let { code, data} = await AddressApi.getAddress(options.id);
+    if (options.id) {
+      let { code, data } = await AddressApi.getAddress(options.id);
       if (code !== 0) {
         return;
       }
       state.model = data;
-		}
-     // 情况二:微信导入
+    }
+    // 情况二:微信导入
     if (options.data) {
       let data = JSON.parse(options.data);
       const areaData = uni.getStorageSync('areaData');
-      const findAreaByName = (areas, name) => areas.find(item => item.name === name);
+      const findAreaByName = (areas, name) => areas.find((item) => item.name === name);
 
       let provinceObj = findAreaByName(areaData, data.province_name);
       let cityObj = provinceObj ? findAreaByName(provinceObj.children, data.city_name) : undefined;
@@ -181,77 +227,79 @@
       state.model = {
         ...state.model,
         areaId,
-        areaName: [data.province_name, data.city_name, data.district_name].filter(Boolean).join(" "),
+        areaName: [data.province_name, data.city_name, data.district_name]
+          .filter(Boolean)
+          .join(' '),
         defaultStatus: false,
         detailAddress: data.address,
         mobile: data.mobile,
         name: data.consignee,
       };
-		}
-	});
+    }
+  });
 </script>
 
 <style lang="scss" scoped>
-	:deep() {
-		.uni-forms-item__label .label-text {
-			font-size: 28rpx !important;
-			color: #333333 !important;
-			line-height: normal !important;
-		}
+  :deep() {
+    .uni-forms-item__label .label-text {
+      font-size: 28rpx !important;
+      color: #333333 !important;
+      line-height: normal !important;
+    }
 
-		.uni-easyinput__content-input {
-			font-size: 28rpx !important;
-			color: #333333 !important;
-			line-height: normal !important;
-			padding-left: 0 !important;
-		}
+    .uni-easyinput__content-input {
+      font-size: 28rpx !important;
+      color: #333333 !important;
+      line-height: normal !important;
+      padding-left: 0 !important;
+    }
 
-		.uni-easyinput__content-textarea {
-			font-size: 28rpx !important;
-			color: #333333 !important;
-			line-height: normal !important;
-			margin-top: 8rpx !important;
-		}
+    .uni-easyinput__content-textarea {
+      font-size: 28rpx !important;
+      color: #333333 !important;
+      line-height: normal !important;
+      margin-top: 8rpx !important;
+    }
 
-		.uni-icons {
-			font-size: 40rpx !important;
-		}
+    .uni-icons {
+      font-size: 40rpx !important;
+    }
 
-		.is-textarea-icon {
-			margin-top: 22rpx;
-		}
+    .is-textarea-icon {
+      margin-top: 22rpx;
+    }
 
-		.is-disabled {
-			color: #333333;
-		}
-	}
+    .is-disabled {
+      color: #333333;
+    }
+  }
 
-	.default-box {
-		width: 100%;
-		box-sizing: border-box;
-		height: 100rpx;
+  .default-box {
+    width: 100%;
+    box-sizing: border-box;
+    height: 100rpx;
 
-		.default-box-title {
-			font-size: 28rpx;
-			color: #333333;
-			line-height: normal;
-		}
-	}
+    .default-box-title {
+      font-size: 28rpx;
+      color: #333333;
+      line-height: normal;
+    }
+  }
 
-	.footer-box {
-		.save-btn {
-			width: 710rpx;
-			height: 80rpx;
-			border-radius: 40rpx;
-			background: linear-gradient(90deg, var(--ui-BG-Main), var(--ui-BG-Main-gradient));
-			color: $white;
-		}
+  .footer-box {
+    .save-btn {
+      width: 710rpx;
+      height: 80rpx;
+      border-radius: 40rpx;
+      background: linear-gradient(90deg, var(--ui-BG-Main), var(--ui-BG-Main-gradient));
+      color: $white;
+    }
 
-		.cancel-btn {
-			width: 710rpx;
-			height: 80rpx;
-			border-radius: 40rpx;
-			background: var(--ui-BG);
-		}
-	}
-</style>
+    .cancel-btn {
+      width: 710rpx;
+      height: 80rpx;
+      border-radius: 40rpx;
+      background: var(--ui-BG);
+    }
+  }
+</style>

+ 137 - 124
pages/user/address/list.vue

@@ -1,143 +1,156 @@
 <!-- 收件地址列表 -->
 <template>
-	<s-layout title="收货地址" :bgStyle="{ color: '#FFF' }">
-		<view v-if="state.list.length">
-			<s-address-item hasBorderBottom v-for="item in state.list" :key="item.id" :item="item"
-                      @tap="onSelect(item)" />
-		</view>
+  <s-layout title="收货地址" :bgStyle="{ color: '#FFF' }">
+    <view v-if="state.list.length">
+      <s-address-item
+        hasBorderBottom
+        v-for="item in state.list"
+        :key="item.id"
+        :item="item"
+        @tap="onSelect(item)"
+      />
+    </view>
 
-		<su-fixed bottom placeholder>
-			<view class="footer-box ss-flex ss-row-between ss-p-20">
-				<!-- 微信小程序和微信H5 -->
-				<button v-if="['WechatMiniProgram', 'WechatOfficialAccount'].includes(sheep.$platform.name)"
-					@tap="importWechatAddress"
-					class="border ss-reset-button sync-wxaddress ss-m-20 ss-flex ss-row-center ss-col-center">
-					<text class="cicon-weixin ss-p-r-10" style="color: #09bb07; font-size: 40rpx"></text>
-					导入微信地址
-				</button>
-				<button class="add-btn ss-reset-button ui-Shadow-Main"
-					@tap="sheep.$router.go('/pages/user/address/edit')">
-					新增收货地址
-				</button>
-			</view>
-		</su-fixed>
-		<s-empty v-if="state.list.length === 0 && !state.loading" text="暂无收货地址" icon="/static/data-empty.png" />
-	</s-layout>
+    <su-fixed bottom placeholder>
+      <view class="footer-box ss-flex ss-row-between ss-p-20">
+        <!-- 微信小程序和微信H5 -->
+        <button
+          v-if="['WechatMiniProgram', 'WechatOfficialAccount'].includes(sheep.$platform.name)"
+          @tap="importWechatAddress"
+          class="border ss-reset-button sync-wxaddress ss-m-20 ss-flex ss-row-center ss-col-center"
+        >
+          <text class="cicon-weixin ss-p-r-10" style="color: #09bb07; font-size: 40rpx"></text>
+          导入微信地址
+        </button>
+        <button
+          class="add-btn ss-reset-button ui-Shadow-Main"
+          @tap="sheep.$router.go('/pages/user/address/edit')"
+        >
+          新增收货地址
+        </button>
+      </view>
+    </su-fixed>
+    <s-empty
+      v-if="state.list.length === 0 && !state.loading"
+      text="暂无收货地址"
+      icon="/static/data-empty.png"
+    />
+  </s-layout>
 </template>
 
 <script setup>
-	import { reactive, onBeforeMount } from 'vue';
-	import { onShow } from '@dcloudio/uni-app';
-	import sheep from '@/sheep';
-	import { isEmpty } from 'lodash';
+  import { reactive, onBeforeMount } from 'vue';
+  import { onShow } from '@dcloudio/uni-app';
+  import sheep from '@/sheep';
+  import { isEmpty } from 'lodash-es';
   import AreaApi from '@/sheep/api/system/area';
   import AddressApi from '@/sheep/api/member/address';
 
-	const state = reactive({
-		list: [], // 地址列表
-		loading: true,
-	});
+  const state = reactive({
+    list: [], // 地址列表
+    loading: true,
+  });
 
-	// 选择收货地址
-	const onSelect = (addressInfo) => {
-		uni.$emit('SELECT_ADDRESS', {
-			addressInfo,
-		});
-		sheep.$router.back();
-	};
+  // 选择收货地址
+  const onSelect = (addressInfo) => {
+    uni.$emit('SELECT_ADDRESS', {
+      addressInfo,
+    });
+    sheep.$router.back();
+  };
 
-	// 导入微信地址
+  // 导入微信地址
   // TODO 芋艿:未测试
-	function importWechatAddress() {
-		let wechatAddress = {};
-		// #ifdef MP
-		uni.chooseAddress({
-			success: (res) => {
-				wechatAddress = {
-					consignee: res.userName,
-					mobile: res.telNumber,
-					province_name: res.provinceName,
-					city_name: res.cityName,
-					district_name: res.countyName,
-					address: res.detailInfo,
-					region: '',
-					is_default: false,
-				};
-				if (!isEmpty(wechatAddress)) {
-					sheep.$router.go('/pages/user/address/edit', {
-						data: JSON.stringify(wechatAddress),
-					});
-				}
-			},
-			fail: (err) => {
-				console.log('%cuni.chooseAddress,调用失败', 'color:green;background:yellow');
-			},
-		});
-		// #endif
-		// #ifdef H5
-		sheep.$platform.useProvider('wechat').jssdk.openAddress({
-			success: (res) => {
-				wechatAddress = {
-					consignee: res.userName,
-					mobile: res.telNumber,
-					province_name: res.provinceName,
-					city_name: res.cityName,
-					district_name: res.countryName,
-					address: res.detailInfo,
-					region: '',
-					is_default: false,
-				};
-				if (!isEmpty(wechatAddress)) {
-					sheep.$router.go('/pages/user/address/edit', {
-						data: JSON.stringify(wechatAddress),
-					});
-				}
-			},
-		});
-		// #endif
-	}
+  function importWechatAddress() {
+    let wechatAddress = {};
+    // #ifdef MP
+    uni.chooseAddress({
+      success: (res) => {
+        wechatAddress = {
+          consignee: res.userName,
+          mobile: res.telNumber,
+          province_name: res.provinceName,
+          city_name: res.cityName,
+          district_name: res.countyName,
+          address: res.detailInfo,
+          region: '',
+          is_default: false,
+        };
+        if (!isEmpty(wechatAddress)) {
+          sheep.$router.go('/pages/user/address/edit', {
+            data: JSON.stringify(wechatAddress),
+          });
+        }
+      },
+      fail: (err) => {
+        console.log('%cuni.chooseAddress,调用失败', 'color:green;background:yellow');
+      },
+    });
+    // #endif
+    // #ifdef H5
+    sheep.$platform.useProvider('wechat').jssdk.openAddress({
+      success: (res) => {
+        wechatAddress = {
+          consignee: res.userName,
+          mobile: res.telNumber,
+          province_name: res.provinceName,
+          city_name: res.cityName,
+          district_name: res.countryName,
+          address: res.detailInfo,
+          region: '',
+          is_default: false,
+        };
+        if (!isEmpty(wechatAddress)) {
+          sheep.$router.go('/pages/user/address/edit', {
+            data: JSON.stringify(wechatAddress),
+          });
+        }
+      },
+    });
+    // #endif
+  }
 
-	onShow(async () => {
-		state.list = (await AddressApi.getAddressList()).data;
-		state.loading = false;
-	});
+  onShow(async () => {
+    state.list = (await AddressApi.getAddressList()).data;
+    state.loading = false;
+  });
 
-	onBeforeMount(() => {
-		if (!!uni.getStorageSync('areaData')) {
-			return;
-		}
-		// 提前加载省市区数据
+  onBeforeMount(() => {
+    if (!!uni.getStorageSync('areaData')) {
+      return;
+    }
+    // 提前加载省市区数据
     AreaApi.getAreaTree().then((res) => {
-			if (res.code === 0) {
-				uni.setStorageSync('areaData', res.data);
-			}
-		});
-	});
+      if (res.code === 0) {
+        uni.setStorageSync('areaData', res.data);
+      }
+    });
+  });
 </script>
 
 <style lang="scss" scoped>
-	.footer-box {
-		.add-btn {
-			flex: 1;
-			background: linear-gradient(90deg, var(--ui-BG-Main), var(--ui-BG-Main-gradient));
-			border-radius: 80rpx;
-			font-size: 30rpx;
-			font-weight: 500;
-			line-height: 80rpx;
-			color: $white;
-			position: relative;
-			z-index: 1;
-		}
+  .footer-box {
+    .add-btn {
+      flex: 1;
+      background: linear-gradient(90deg, var(--ui-BG-Main), var(--ui-BG-Main-gradient));
+      border-radius: 80rpx;
+      font-size: 30rpx;
+      font-weight: 500;
+      line-height: 80rpx;
+      color: $white;
+      position: relative;
+      z-index: 1;
+    }
 
-		.sync-wxaddress {
-			flex: 1;
-			line-height: 80rpx;
-			background: $white;
-			border-radius: 80rpx;
-			font-size: 30rpx;
-			font-weight: 500;
-			color: $dark-6;
-			margin-right: 18rpx;
-		}
-	}
-</style>
+    .sync-wxaddress {
+      flex: 1;
+      line-height: 80rpx;
+      background: $white;
+      border-radius: 80rpx;
+      font-size: 30rpx;
+      font-weight: 500;
+      color: $dark-6;
+      margin-right: 18rpx;
+    }
+  }
+</style>

+ 7 - 5
pages/user/goods-collect.vue

@@ -5,7 +5,8 @@
       <!-- 头部 -->
       <view class="cart-header ss-flex ss-col-center ss-row-between ss-p-x-30">
         <view class="header-left ss-flex ss-col-center ss-font-26">
-          共 <text class="goods-number ui-TC-Main ss-flex">{{ state.pagination.total }}</text> 件商品
+          共
+          <text class="goods-number ui-TC-Main ss-flex">{{ state.pagination.total }}</text> 件商品
         </view>
         <view class="header-right">
           <button
@@ -77,7 +78,8 @@
           <view class="footer-right">
             <button
               class="ss-reset-button ui-BG-Main-Gradient pay-btn ss-font-28 ui-Shadow-Main"
-              @tap="onCancel">
+              @tap="onCancel"
+            >
               取消收藏
             </button>
           </view>
@@ -100,7 +102,7 @@
   import sheep from '@/sheep';
   import { reactive } from 'vue';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import FavoriteApi from '@/sheep/api/product/favorite';
   import { resetPagination } from '@/sheep/util';
 
@@ -129,7 +131,7 @@
     if (code !== 0) {
       return;
     }
-    state.pagination.list = _.concat(state.pagination.list, data.list)
+    state.pagination.list = _.concat(state.pagination.list, data.list);
     state.pagination.total = data.total;
     state.loadStatus = state.pagination.list.length < state.pagination.total ? 'more' : 'noMore';
   }
@@ -174,7 +176,7 @@
   // 加载更多
   function loadMore() {
     if (state.loadStatus === 'noMore') {
-      return
+      return;
     }
     state.pagination.pageNo++;
     getData();

+ 10 - 8
pages/user/goods-log.vue

@@ -81,11 +81,13 @@
           </view>
           <view class="footer-right ss-flex">
             <button
-              :class="['ss-reset-button  pay-btn ss-font-28 ',
-                  {
-                    'ui-BG-Main-Gradient': state.selectedSpuIdList.length > 0,
-                    'ui-Shadow-Main': state.selectedSpuIdList.length > 0
-                  }]"
+              :class="[
+                'ss-reset-button  pay-btn ss-font-28 ',
+                {
+                  'ui-BG-Main-Gradient': state.selectedSpuIdList.length > 0,
+                  'ui-Shadow-Main': state.selectedSpuIdList.length > 0,
+                },
+              ]"
               @tap="onDelete"
             >
               删除足迹
@@ -120,9 +122,9 @@
   import sheep from '@/sheep';
   import { reactive } from 'vue';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
-  import _ from 'lodash';
-  import SpuHistoryApi from "@/sheep/api/product/history";
-  import {cloneDeep} from "@/sheep/helper/utils";
+  import _ from 'lodash-es';
+  import SpuHistoryApi from '@/sheep/api/product/history';
+  import { cloneDeep } from '@/sheep/helper/utils';
 
   const sys_navBar = sheep.$platform.navbar;
   const pagination = {

+ 8 - 9
pages/user/info.vue

@@ -26,7 +26,8 @@
             <button
               class="ss-reset-button avatar-action-btn"
               open-type="chooseAvatar"
-              @chooseavatar="onChooseAvatar">
+              @chooseavatar="onChooseAvatar"
+            >
               修改
             </button>
             <!-- #endif -->
@@ -154,10 +155,7 @@
         </view>
         <view class="ss-flex ss-col-center">
           <view class="info ss-flex ss-col-center" v-if="state.thirdInfo">
-            <image
-              class="avatar ss-m-r-20"
-              :src="sheep.$url.cdn(state.thirdInfo.avatar)"
-            />
+            <image class="avatar ss-m-r-20" :src="sheep.$url.cdn(state.thirdInfo.avatar)" />
             <text class="name">{{ state.thirdInfo.nickname }}</text>
           </view>
           <view class="bind-box ss-m-l-20">
@@ -185,7 +183,7 @@
 <script setup>
   import { computed, reactive, onBeforeMount } from 'vue';
   import sheep from '@/sheep';
-  import { clone } from 'lodash';
+  import { clone } from 'lodash-es';
   import { showAuthModal } from '@/sheep/hooks/useModal';
   import FileApi from '@/sheep/api/infra/file';
   import UserApi from '@/sheep/api/member/user';
@@ -198,14 +196,15 @@
 
   const placeholderStyle = 'color:#BBBBBB;font-size:28rpx;line-height:normal';
 
-  const sexRadioMap = [{
+  const sexRadioMap = [
+    {
       name: '男',
       value: '1',
     },
     {
       name: '女',
       value: '2',
-    }
+    },
   ];
 
   const userInfo = computed(() => sheep.$store('user').userInfo);
@@ -279,7 +278,7 @@
 
   // 保存信息
   async function onSubmit() {
-	 const { code } = await UserApi.updateUser({
+    const { code } = await UserApi.updateUser({
       avatar: state.model.avatar,
       nickname: state.model.nickname,
       sex: state.model.sex,

+ 13 - 7
pages/user/wallet/money.vue

@@ -13,7 +13,9 @@
           />
         </view>
         <view class="ss-flex ss-row-between ss-col-center ss-m-t-64">
-          <view class="money-num">{{ state.showMoney ? fen2yuan(userWallet.balance) : '*****' }}</view>
+          <view class="money-num">{{
+            state.showMoney ? fen2yuan(userWallet.balance) : '*****'
+          }}</view>
           <button class="ss-reset-button topup-btn" @tap="sheep.$router.go('/pages/pay/recharge')">
             充值
           </button>
@@ -24,7 +26,12 @@
     <su-sticky>
       <!-- 统计 -->
       <view class="filter-box ss-p-x-30 ss-flex ss-col-center ss-row-between">
-        <uni-datetime-picker v-model="state.data" type="daterange" @change="onChangeTime" :end="state.today">
+        <uni-datetime-picker
+          v-model="state.data"
+          type="daterange"
+          @change="onChangeTime"
+          :end="state.today"
+        >
           <button class="ss-reset-button date-btn">
             <text>{{ dateFilterText }}</text>
             <text class="cicon-drop-down ss-seldate-icon"></text>
@@ -82,7 +89,7 @@
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import sheep from '@/sheep';
   import dayjs from 'dayjs';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import PayWalletApi from '@/sheep/api/pay/wallet';
   import { fen2yuan } from '@/sheep/hooks/useGoods';
   import { resetPagination } from '@/sheep/util';
@@ -98,7 +105,7 @@
       list: [],
       total: 0,
       pageNo: 1,
-      pageSize: 8
+      pageSize: 8,
     },
     summary: {
       totalIncome: 0,
@@ -155,7 +162,7 @@
   // 获得钱包统计
   async function getSummary() {
     const { data, code } = await PayWalletApi.getWalletTransactionSummary({
-      'createTime': [state.date[0] + ' 00:00:00', state.date[1] + ' 23:59:59'],
+      createTime: [state.date[0] + ' 00:00:00', state.date[1] + ' 23:59:59'],
     });
     if (code !== 0) {
       return;
@@ -226,8 +233,7 @@
         position: absolute;
         top: 0;
         left: 0;
-        background: v-bind(headerBg)
-          no-repeat;
+        background: v-bind(headerBg) no-repeat;
         pointer-events: none;
       }
 

+ 18 - 13
pages/user/wallet/score.vue

@@ -24,19 +24,24 @@
     <su-sticky :customNavHeight="sys_navBar">
       <!-- 统计 -->
       <view class="filter-box ss-p-x-30 ss-flex ss-col-center ss-row-between">
-				<uni-datetime-picker v-model="state.date" type="daterange" @change="onChangeTime" :end="state.today">
-					<button class="ss-reset-button date-btn">
-						<text>{{ dateFilterText }}</text>
-						<text class="cicon-drop-down ss-seldate-icon"></text>
-					</button>
-				</uni-datetime-picker>
+        <uni-datetime-picker
+          v-model="state.date"
+          type="daterange"
+          @change="onChangeTime"
+          :end="state.today"
+        >
+          <button class="ss-reset-button date-btn">
+            <text>{{ dateFilterText }}</text>
+            <text class="cicon-drop-down ss-seldate-icon"></text>
+          </button>
+        </uni-datetime-picker>
 
         <!-- TODO 芋艿:优化 -->
-<!--				<view class="total-box">-->
-<!--					<view class="ss-m-b-10">总收入¥{{ state.pagination.income }}</view>-->
-<!--					<view>总支出¥{{ -state.pagination.expense }}</view>-->
-<!--				</view>-->
-			</view>
+        <!--				<view class="total-box">-->
+        <!--					<view class="ss-m-b-10">总收入¥{{ state.pagination.income }}</view>-->
+        <!--					<view>总支出¥{{ -state.pagination.expense }}</view>-->
+        <!--				</view>-->
+      </view>
       <su-tabs
         :list="tabMaps"
         @change="onChange"
@@ -83,7 +88,7 @@
   import sheep from '@/sheep';
   import { onLoad, onReachBottom } from '@dcloudio/uni-app';
   import { computed, reactive } from 'vue';
-  import _ from 'lodash';
+  import _ from 'lodash-es';
   import dayjs from 'dayjs';
   import PointApi from '@/sheep/api/member/point';
   import { resetPagination } from '@/sheep/util';
@@ -274,4 +279,4 @@
       }
     }
   }
-</style>
+</style>

+ 2 - 4
sheep/components/s-address-item/s-address-item.vue

@@ -18,9 +18,7 @@
       <view class="address-text">
         {{ props.item.detailAddress }}
       </view>
-      <view class="person-text">
-        {{ props.item.name }} {{ props.item.mobile }}
-      </view>
+      <view class="person-text"> {{ props.item.name }} {{ props.item.mobile }} </view>
     </view>
     <view v-else>
       <view class="address-text ss-m-b-10">请选择收货地址</view>
@@ -47,7 +45,7 @@
    * @slot 								 - 默认插槽
    */
   import sheep from '@/sheep';
-  import { isEmpty } from 'lodash';
+  import { isEmpty } from 'lodash-es';
   const props = defineProps({
     item: {
       type: Object,

+ 43 - 13
sheep/components/s-goods-column/s-goods-column.vue

@@ -11,7 +11,11 @@
       <view v-if="tagStyle.show" class="tag-icon-box">
         <image class="tag-icon" :src="sheep.$url.cdn(tagStyle.src || tagStyle.imgUrl)"></image>
       </view>
-      <image class="xs-img-box" :src="sheep.$url.cdn(data.image || data.picUrl)" mode="aspectFit"></image>
+      <image
+        class="xs-img-box"
+        :src="sheep.$url.cdn(data.image || data.picUrl)"
+        mode="aspectFit"
+      ></image>
       <view
         v-if="goodsFields.title?.show || goodsFields.name?.show || goodsFields.price?.show"
         class="xs-goods-content ss-flex-col ss-row-around"
@@ -39,14 +43,21 @@
       <view v-if="tagStyle.show" class="tag-icon-box">
         <image class="tag-icon" :src="sheep.$url.cdn(tagStyle.src || tagStyle.imgUrl)"></image>
       </view>
-      <image class="sm-img-box" :src="sheep.$url.cdn(data.image || data.picUrl)" mode="aspectFill"></image>
+      <image
+        class="sm-img-box"
+        :src="sheep.$url.cdn(data.image || data.picUrl)"
+        mode="aspectFill"
+      ></image>
 
       <view
         v-if="goodsFields.title?.show || goodsFields.name?.show || goodsFields.price?.show"
         class="sm-goods-content"
         :style="[{ color: titleColor, width: titleWidth ? titleWidth + 'rpx' : '' }]"
       >
-        <view v-if="goodsFields.title?.show || goodsFields.name?.show" class="sm-goods-title ss-line-1 ss-m-b-16">
+        <view
+          v-if="goodsFields.title?.show || goodsFields.name?.show"
+          class="sm-goods-title ss-line-1 ss-m-b-16"
+        >
           {{ data.title || data.name }}
         </view>
         <view
@@ -65,7 +76,11 @@
       <view v-if="tagStyle.show" class="tag-icon-box">
         <image class="tag-icon" :src="sheep.$url.cdn(tagStyle.src || tagStyle.imgUrl)"></image>
       </view>
-      <image class="md-img-box" :src="sheep.$url.cdn(data.image || data.picUrl)" mode="widthFix"></image>
+      <image
+        class="md-img-box"
+        :src="sheep.$url.cdn(data.image || data.picUrl)"
+        mode="widthFix"
+      ></image>
       <view
         class="md-goods-content ss-flex-col ss-row-around ss-p-b-20 ss-p-t-20 ss-p-x-16"
         :id="elId"
@@ -106,7 +121,10 @@
           </view>
 
           <view
-            v-if="(goodsFields.original_price?.show||goodsFields.marketPrice?.show) &&( data.original_price > 0|| data.marketPrice > 0)"
+            v-if="
+              (goodsFields.original_price?.show || goodsFields.marketPrice?.show) &&
+              (data.original_price > 0 || data.marketPrice > 0)
+            "
             class="goods-origin-price ss-m-t-16 font-OPPOSANS ss-flex"
             :style="[{ color: originPriceColor }]"
           >
@@ -141,7 +159,11 @@
       <view v-if="grouponTag" class="groupon-tag ss-flex ss-row-center">
         <view class="tag-icon">拼团</view>
       </view>
-      <image class="lg-img-box" :src="sheep.$url.cdn(data.image || data.picUrl)" mode="aspectFill"></image>
+      <image
+        class="lg-img-box"
+        :src="sheep.$url.cdn(data.image || data.picUrl)"
+        mode="aspectFill"
+      ></image>
       <view class="lg-goods-content ss-flex-1 ss-flex-col ss-row-between ss-p-b-10 ss-p-t-20">
         <view>
           <view
@@ -177,7 +199,10 @@
               {{ isArray(data.price) ? fen2yuan(data.price[0]) : fen2yuan(data.price) }}
             </view>
             <view
-              v-if="(goodsFields.original_price?.show||goodsFields.marketPrice?.show) &&( data.original_price > 0|| data.marketPrice > 0)"
+              v-if="
+                (goodsFields.original_price?.show || goodsFields.marketPrice?.show) &&
+                (data.original_price > 0 || data.marketPrice > 0)
+              "
               class="goods-origin-price ss-flex ss-col-bottom font-OPPOSANS"
               :style="[{ color: originPriceColor }]"
             >
@@ -192,9 +217,7 @@
       </view>
 
       <slot name="cart">
-        <view class="buy-box ss-flex ss-col-center ss-row-center" v-if="buttonShow">
-          去购买
-        </view>
+        <view class="buy-box ss-flex ss-col-center ss-row-center" v-if="buttonShow"> 去购买 </view>
       </slot>
     </view>
 
@@ -204,7 +227,11 @@
         <image class="tag-icon" :src="sheep.$url.cdn(tagStyle.src || tagStyle.imgUrl)"></image>
       </view>
 
-      <image class="sl-img-box" :src="sheep.$url.cdn(data.image || data.picUrl)" mode="aspectFill"></image>
+      <image
+        class="sl-img-box"
+        :src="sheep.$url.cdn(data.image || data.picUrl)"
+        mode="aspectFill"
+      ></image>
 
       <view class="sl-goods-content">
         <view>
@@ -241,7 +268,10 @@
               {{ isArray(data.price) ? fen2yuan(data.price[0]) : fen2yuan(data.price) }}
             </view>
             <view
-              v-if="(goodsFields.original_price?.show||goodsFields.marketPrice?.show) &&( data.original_price > 0|| data.marketPrice > 0)"
+              v-if="
+                (goodsFields.original_price?.show || goodsFields.marketPrice?.show) &&
+                (data.original_price > 0 || data.marketPrice > 0)
+              "
               class="goods-origin-price ss-m-t-16 font-OPPOSANS ss-flex"
               :style="[{ color: originPriceColor }]"
             >
@@ -296,7 +326,7 @@
   import { fen2yuan, formatSales } from '@/sheep/hooks/useGoods';
   import { formatStock } from '@/sheep/hooks/useGoods';
   import goodsCollectVue from '@/pages/user/goods-collect.vue';
-  import { isArray } from 'lodash';
+  import { isArray } from 'lodash-es';
 
   // 数据
   const state = reactive({});

+ 6 - 2
sheep/components/s-layout/s-layout.vue

@@ -31,7 +31,11 @@
         ></view>
 
         <!-- 顶部导航栏-情况4:装修组件导航栏-沉浸式 -->
-        <s-custom-navbar v-if="navbar === 'custom' && navbarMode === 'inner'" :data="navbarStyle" :showLeftButton="showLeftButton" />
+        <s-custom-navbar
+          v-if="navbar === 'custom' && navbarMode === 'inner'"
+          :data="navbarStyle"
+          :showLeftButton="showLeftButton"
+        />
 
         <!-- 页面内容插槽 -->
         <slot />
@@ -58,7 +62,7 @@
    */
   import { computed, reactive, ref } from 'vue';
   import sheep from '@/sheep';
-  import { isEmpty } from 'lodash';
+  import { isEmpty } from 'lodash-es';
   import { onShow } from '@dcloudio/uni-app';
   // #ifdef MP-WEIXIN
   import { onShareAppMessage } from '@dcloudio/uni-app';

+ 35 - 32
sheep/components/s-select-seckill-sku/s-select-seckill-sku.vue

@@ -1,31 +1,31 @@
 <!-- 秒杀商品的 SKU 选择,和 s-select-sku.vue 类似 -->
 <template>
-	<!-- 规格弹窗 -->
-	<su-popup :show="show" round="10" @close="emits('close')">
-		<!-- SKU 信息 -->
-		<view class="ss-modal-box bg-white ss-flex-col">
-			<view class="modal-header ss-flex ss-col-center">
-				<!-- 规格图 -->
-				<view class="header-left ss-m-r-30">
-					<image
-						class="sku-image"
-						:src="sheep.$url.cdn(state.selectedSku.picUrl || state.goodsInfo.picUrl)"
-						mode="aspectFill"
-					>
-					</image>
-				</view>
-				<view class="header-right ss-flex-col ss-row-between ss-flex-1">
-					<!-- 名称 -->
-					<view class="goods-title ss-line-2">{{ state.goodsInfo.name }}</view>
-					<view class="header-right-bottom ss-flex ss-col-center ss-row-between">
-						<!-- 价格 -->
-						<view class="price-text">
-							{{ fen2yuan(state.selectedSku.price || state.goodsInfo.price) }}
-						</view>
-						<!-- 秒杀价格标签 -->
-						<view class="tig ss-flex ss-col-center">
-							<view class="tig-icon ss-flex ss-col-center ss-row-center">
-	              <text class="cicon-alarm"></text>
+  <!-- 规格弹窗 -->
+  <su-popup :show="show" round="10" @close="emits('close')">
+    <!-- SKU 信息 -->
+    <view class="ss-modal-box bg-white ss-flex-col">
+      <view class="modal-header ss-flex ss-col-center">
+        <!-- 规格图 -->
+        <view class="header-left ss-m-r-30">
+          <image
+            class="sku-image"
+            :src="sheep.$url.cdn(state.selectedSku.picUrl || state.goodsInfo.picUrl)"
+            mode="aspectFill"
+          >
+          </image>
+        </view>
+        <view class="header-right ss-flex-col ss-row-between ss-flex-1">
+          <!-- 名称 -->
+          <view class="goods-title ss-line-2">{{ state.goodsInfo.name }}</view>
+          <view class="header-right-bottom ss-flex ss-col-center ss-row-between">
+            <!-- 价格 -->
+            <view class="price-text">
+              {{ fen2yuan(state.selectedSku.price || state.goodsInfo.price) }}
+            </view>
+            <!-- 秒杀价格标签 -->
+            <view class="tig ss-flex ss-col-center">
+              <view class="tig-icon ss-flex ss-col-center ss-row-center">
+                <text class="cicon-alarm"></text>
               </view>
               <view class="tig-title">秒杀价</view>
             </view>
@@ -91,8 +91,8 @@
   // 按钮状态: active,nostock
   import { computed, reactive, watch } from 'vue';
   import sheep from '@/sheep';
-  import {convertProductPropertyList, fen2yuan} from "@/sheep/hooks/useGoods";
-  import {min} from "lodash";
+  import { convertProductPropertyList, fen2yuan } from '@/sheep/hooks/useGoods';
+  import { min } from 'lodash-es';
   const emits = defineEmits(['change', 'addCart', 'buy', 'close']);
   const props = defineProps({
     modelValue: {
@@ -107,7 +107,7 @@
     singleLimitCount: {
       type: Number,
       default: 1,
-    }
+    },
   });
   const state = reactive({
     goodsInfo: computed(() => props.modelValue),
@@ -120,7 +120,7 @@
   const skuList = computed(() => {
     let skuPrices = state.goodsInfo.skus;
     for (let price of skuPrices) {
-      price.value_id_array = price.properties.map((item) => item.valueId)
+      price.value_id_array = price.properties.map((item) => item.valueId);
     }
     return skuPrices;
   });
@@ -228,7 +228,7 @@
       // 如果当前 property id 不存在于有库存的 SKU 中,则禁用
       for (let valueIndex in propertyList[propertyIndex]['values']) {
         propertyList[propertyIndex]['values'][valueIndex]['disabled'] =
-            noChooseValueIds.indexOf(propertyList[propertyIndex]['values'][valueIndex]['id']) < 0; // true 禁用 or false 不禁用
+          noChooseValueIds.indexOf(propertyList[propertyIndex]['values'][valueIndex]['id']) < 0; // true 禁用 or false 不禁用
       }
     }
   };
@@ -258,7 +258,10 @@
   const onSelectSku = (propertyId, valueId) => {
     // 清空已选择
     let isChecked = true; // 选中 or 取消选中
-    if (state.currentPropertyArray[propertyId] !== undefined && state.currentPropertyArray[propertyId] === valueId) {
+    if (
+      state.currentPropertyArray[propertyId] !== undefined &&
+      state.currentPropertyArray[propertyId] === valueId
+    ) {
       // 点击已被选中的,删除并填充 ''
       isChecked = false;
       state.currentPropertyArray.splice(propertyId, 1, '');

+ 1 - 1
sheep/platform/index.js

@@ -9,7 +9,7 @@
  * @param {Object} device - 设备信息
  */
 
-import { isEmpty } from 'lodash';
+import { isEmpty } from 'lodash-es';
 // #ifdef H5
 import { isWxBrowser } from '@/sheep/helper/utils';
 // #endif

+ 1 - 1
sheep/router/index.js

@@ -1,6 +1,6 @@
 import $store from '@/sheep/store';
 import { showAuthModal, showShareModal } from '@/sheep/hooks/useModal';
-import { isNumber, isString, isEmpty, startsWith, isObject, isNil, clone } from 'lodash';
+import { isNumber, isString, isEmpty, startsWith, isObject, isNil, clone } from 'lodash-es';
 import throttle from '@/sheep/helper/throttle';
 
 const _go = (

+ 10 - 8
sheep/store/user.js

@@ -1,6 +1,6 @@
 import { defineStore } from 'pinia';
 import $share from '@/sheep/platform/share';
-import { clone, cloneDeep } from 'lodash';
+import { clone, cloneDeep } from 'lodash-es';
 import cart from './cart';
 import app from './app';
 import { showAuthModal } from '@/sheep/hooks/useModal';
@@ -68,12 +68,12 @@ const user = defineStore({
 
     // 获取订单、优惠券等其他资产信息
     getNumData() {
-      OrderApi.getOrderCount().then(res => {
+      OrderApi.getOrderCount().then((res) => {
         if (res.code === 0) {
           this.numData.orderCount = res.data;
         }
       });
-      CouponApi.getUnusedCouponCount().then(res => {
+      CouponApi.getUnusedCouponCount().then((res) => {
         if (res.code === 0) {
           this.numData.unusedCouponCount = res.data;
         }
@@ -143,20 +143,22 @@ const user = defineStore({
       }
 
       // 绑定推广员
-      $share.bindBrokerageUser()
+      $share.bindBrokerageUser();
     },
 
     // 登出系统
     async logout() {
       this.resetUserData();
       return !this.isLogin;
-    }
+    },
   },
   persist: {
     enabled: true,
-    strategies: [{
-      key: 'user-store',
-    }]
+    strategies: [
+      {
+        key: 'user-store',
+      },
+    ],
   },
 });
 

+ 4 - 4
sheep/ui/su-swiper/su-swiper.vue

@@ -88,7 +88,7 @@
 
   import { reactive, computed } from 'vue';
   import sheep from '@/sheep';
-  import { clone } from 'lodash';
+  import { clone } from 'lodash-es';
 
   // 数据
   const state = reactive({
@@ -196,11 +196,11 @@
   const onPreview = () => {
     if (!props.isPreview) return;
     let previewImage = clone(props.list);
-    previewImage.forEach((item,index) => {
-      if(item.type === 'video') {
+    previewImage.forEach((item, index) => {
+      if (item.type === 'video') {
         previewImage.splice(index, 1);
       }
-    })
+    });
     uni.previewImage({
       urls:
         previewImage.length < 1