浏览代码

优惠券列表弹窗,优惠券选择

喻文俊 3 年之前
父节点
当前提交
75140f0cb7

+ 2 - 0
common/common.js

@@ -178,6 +178,8 @@ export function debounce(fn, delay, isImmediate) {
     }
 }
 
+
+
 const install = Vue => {
     console.log('初始化挂载($reg)工具库 common.js')
     Vue.prototype.$reg = {

+ 55 - 0
common/couponUtil.js

@@ -0,0 +1,55 @@
+import { isIntersect } from '@/common/util.js'
+// 优惠商品统计价格
+export let countPrice = 0
+
+// 获取选中商品
+export function fetchSelectedProducts(goodsList) {
+    const productList = []
+    goodsList.forEach(shop => {
+        shop.productList.forEach(prod => {
+            if (prod.productsChecked) {
+                productList.push(prod)
+            }
+        })
+    })
+    console.log(productList)
+    return productList
+}
+
+// 根据选中商品筛选可用优惠券并排序
+export function findCouponBySelected(ids, couponList) {
+    return couponList.filter(coupon => coupon.productType === 1 || isIntersect(ids, coupon.productIds.split(',')))
+        .sort((a, b) => b.couponAmount - a.couponAmount)
+}
+
+// 判断可用优惠券是否满足使用条件
+export function canUseCoupon(current, productIds, canUseCouponList, selectedPoducts) {
+    if (productIds.length <= 0) return -1
+    const len = canUseCouponList.length
+    if (current >= len) return len
+    const currentCoupon = canUseCouponList[current]
+    // 无门槛
+    if (currentCoupon.noThresholdFlag === 1) return current
+    // 是否满足条件
+    if (currentCoupon.noThresholdFlag === 0) {
+        countPrice = selectedPoducts.reduce((countPrice, prod) => {
+            // 全部商品可用
+            if (currentCoupon.productType === 1) {
+                countPrice += prod.price * prod.productCount
+            } else {
+                // 部分商品可用
+                const couponProductIds = currentCoupon.productIds.split(',')
+                if (couponProductIds.includes(prod.productId.toString())) {
+                    countPrice += prod.price * prod.productCount
+                }
+            }
+            return countPrice
+        }, 0)
+        if (countPrice >= currentCoupon.touchPrice) return current
+    }
+    return canUseCoupon(++current, productIds, canUseCouponList, selectedPoducts)
+}
+
+export function getCountPrice(){
+    return countPrice
+}

+ 6 - 0
common/util.js

@@ -72,6 +72,12 @@ export const dateFormat = (date = new Date(), format = 'yyyy-MM-dd hh:mm:ss') =>
     return format
 }
 
+// 两个简单数组是否交集
+export const isIntersect = (arr1 = [], arr2 = []) => {
+    // console.log(arr1, arr2)
+    return arr1.some(v => arr2.indexOf(v.toString()) > -1)
+}
+
 const install = (Vue, vm) => {
     console.log('初始化挂载($util)工具方法 util.js ')
     Vue.prototype.$util = { msg, prePage, modal }

+ 1 - 0
components/cm-module/cm-cart-product/cm-cart-product.vue

@@ -151,6 +151,7 @@ export default {
         ...mapMutations('cart', ['selectProduct', 'selectAllShopProduct', 'selectFailure']),
         // 商品数量变化
         numberChange(product, count) {
+            this.$emit('countChange')
             this.countChange(product, count)
         },
         // 勾选 / 取消勾选 供应商下所有商品

+ 55 - 10
components/cm-module/cm-coupon-list/cm-coupon-list.vue

@@ -11,7 +11,12 @@
                     <view class="other" v-if="listType !== 'receive'">
                         <!-- 勾选不使用优惠券 -->
                         <view class="unset" v-if="listType === 'use'">
-                            <text>不使用优惠券</text> <text class="radio-flag iconfont icon-xuanze"></text>
+                            <text>不使用优惠券</text>
+                            <text
+                                class="radio-flag iconfont"
+                                :class="currentId === -1 ? 'icon-xuanze' : 'icon-weixuanze'"
+                                @click="noChoose"
+                            ></text>
                         </view>
                         <!-- tab切换 -->
                         <view class="tabs" v-if="listType === 'search'">
@@ -22,13 +27,24 @@
                                 :key="index"
                                 @click="checkedTab(index)"
                             >
-                                <text>{{ tab.name }}</text> <text>({{ 1 }})</text>
+                                <text>{{ tab.name }}</text>
                             </view>
                         </view>
                     </view>
                     <view class="list" :class="['scroll-' + listType]">
                         <!-- 优惠券列表 -->
-                        <!-- <cm-coupon :key="i" v-for="i in 6"></cm-coupon> -->
+                        <template v-for="(coupon, index) in couponList">
+                            <cm-coupon
+                                :key="index"
+                                :couponData="coupon"
+                                @btnClick="couponClick"
+                                :showStatus="showStatus"
+                                :btnUseType="btnUseType"
+                                :chooseAble="chooseAble"
+                                @choose="choose"
+                                :currentId="currentId"
+                            ></cm-coupon>
+                        </template>
                         <!-- 优惠券为空 -->
                         <cm-empty
                             message="暂无任何优惠券~"
@@ -78,13 +94,26 @@ export default {
         listType: {
             type: String,
             default: 'receive'
-        }
-    },
-    data() {
-        return {
-            baseUrl: this.$Static,
-            currentTab: 0,
-            tabs: [
+        },
+        btnUseType: {
+            type: Number,
+            default: 1
+        },
+        showStatus: {
+            type: Boolean,
+            default: false
+        },
+        chooseAble: {
+            type: Boolean,
+            default: false
+        },
+        currentId: {
+            type: Number,
+            default: -1
+        },
+        tabs: {
+            type: Array,
+            default: () => [
                 {
                     name: '已领取优惠券'
                 },
@@ -94,6 +123,12 @@ export default {
             ]
         }
     },
+    data() {
+        return {
+            baseUrl: this.$Static,
+            currentTab: 0
+        }
+    },
     computed: {
         ...mapGetters(['isIphoneX'])
     },
@@ -104,6 +139,16 @@ export default {
         },
         checkedTab(index) {
             this.currentTab = index
+            this.$emit('tabClick', index)
+        },
+        couponClick() {
+            this.$emit('couponClick')
+        },
+        choose(coupon) {
+            this.$emit('chooseCoupon', coupon)
+        },
+        noChoose() {
+            this.$emit('chooseCoupon', { couponId: -1,  })
         }
     }
 }

+ 43 - 11
components/cm-module/cm-coupon/cm-coupon.vue

@@ -20,15 +20,33 @@
                 <view class="row bold">{{ couponData.couponName }}</view>
                 <!-- 适用范围 -->
                 <view class="row">{{ couponData.productType | formatUseType }}</view>
-                <!-- 截止日期 -->
-                <view class="end-time">截止日期:{{ couponData.receivePeriod | formatDate }}</view>
+                <!-- 截止日期 receivePeriod usePeriod-->
+                <view class="end-time" v-if="couponData.useStatus === 0"
+                    >截止日期:{{ couponData.receivePeriod | formatDate }}</view
+                >
+                <view class="end-time" v-else>截止日期:{{ couponData.usePeriod | formatDate }}</view>
             </view>
             <view class="footer">
-                <view class="btn" @click="handleBtnClick" v-if="couponData.useStatus === 0">领取</view>
-                <view class="btn plain" @click="handleBtnClick" v-if="couponData.useStatus === 1">去使用</view>
+                <template v-if="!chooseAble">
+                    <view class="btn" @click="handleBtnClick" v-if="couponData.useStatus === 0">领取</view>
+                    <template v-if="couponData.useStatus === 1">
+                        <view class="btn plain" @click="handleBtnClick" v-if="btnUseType === 1">去使用</view>
+                        <view class="btn" @click="handleBtnClick" v-else>可用商品</view>
+                    </template>
+                </template>
+                <template v-if="chooseAble">
+                    <view class="btn" @click="handleBtnClick" v-if="!couponData.canSelect">去凑单</view>
+                </template>
             </view>
-            <!-- <text class="radio-flag iconfont icon-weixuanze"></text> -->
-            <text class="radio-flag iconfont icon-xuanze" v-if="chooseAble" @click="choose"></text>
+            <!-- <text class="radio-flag iconfont icon-weixuanze"></text> canSelect-->
+            <template v-if="chooseAble">
+                <text
+                    class="radio-flag iconfont "
+                    :class="currentId === couponData.couponId ? 'icon-xuanze' : 'icon-weixuanze'"
+                    v-if="couponData.canSelect"
+                    @click="choose"
+                ></text>
+            </template>
         </view>
     </view>
 </template>
@@ -52,6 +70,13 @@ export default {
         showStatus: {
             type: Boolean,
             default: false
+        },
+        btnUseType: {
+            type: Number,
+            default: 1
+        },
+        currentId: {
+            type: Number
         }
     },
     filters: {
@@ -91,7 +116,7 @@ export default {
                 2: 'used', // 已使用
                 3: 'expired' //已失效
             }
-            return type[this.couponData.useStatus + 1]
+            return type[this.couponData.useStatus]
         },
         // 优惠券是能否领取和使用
         canUse() {
@@ -113,15 +138,22 @@ export default {
                 1: this.useCoupon // 使用优惠券
             }
             // 将优惠券id作为参数传递进去
-            clickFns[this.couponData.useStatus](this.couponData.couponId).then(res=>{
+            clickFns[this.couponData.useStatus](this.couponData.couponId).then(res => {
                 // 向父组件发送领取优惠券事件
-                this.couponData.useStatus === 0 && this.$emit('btnClick', this.couponData)
+                this.$emit('btnClick', this.couponData)
             })
         },
         // 使用优惠券
-        useCoupon() {
+        useCoupon(couponId) {
+            const type = this.couponData.productType
+            if (type === 1) {
+                console.log('全部商品可用')
+                this.$api.switchTabTo('/pages/tabBar/index/index')
+            } else {
+                console.log('部分商品可用')
+                this.$api.navigateTo(`/pages/goods/good-coupon-list?couponId=${couponId}`)
+            }
             return Promise.resolve()
-            console.log('使用优惠券')
         }
     }
 }

+ 1 - 0
components/cm-module/cm-product/cm-product.vue

@@ -10,6 +10,7 @@
             <view class="tags">
                 <!-- <view class="tag type1">自营</view> -->
                 <view class="tag type2" v-if="data.activeStatus == 1">活动价</view>
+                <view class="tag type2" v-if="data.couponsLogo">优惠券</view>
             </view>
             <!-- 底部 -->
             <view class="footer">

+ 1 - 1
components/cm-module/cm-selector-coupons/cm-selector-coupons.vue

@@ -1,5 +1,5 @@
 <template>
-    <view class="selector-coupons" :style="{ top: top + 'px' }" v-if="visible">
+    <view class="selector-coupons" :style="{ top: top + 'px' }" v-if="visible" @click="$emit('click')">
         <image :src="image"></image>
         <view class="content">
             <text class="title">{{ title }}</text> <text class="subTitle">{{ subTitle }}</text>

+ 20 - 10
components/cm-module/orderDetails/orderInformation.vue

@@ -12,29 +12,39 @@
             </view>
             <view class="information-view title">
                 <view class="view-num">
-                    订单总额:<label class="label"
-                        >¥{{ orderData.payTotalFee ? (orderData.payTotalFee | NumFormat) : '' }}</label
-                    >
+                    <text>订单总额:</text>
+                    <label class="label">
+                        ¥{{ orderData.payTotalFee ? orderData.payTotalFee : '' | NumFormat }}
+                    </label>
+                </view>
+            </view>
+            <view class="information-view title">
+                <view class="view-num">
+                    <text>优惠券:</text>
+                    <label class="label">
+                        ¥{{ orderData.couponAmount ? orderData.couponAmount : '' | NumFormat }}
+                    </label>
                 </view>
             </view>
             <view class="information-view">
                 <view class="view-num time">
-                    下单时间:<label class="label">{{ orderData.orderTime ? orderData.orderTime : '' }}</label>
+                    <text>下单时间:</text>
+                    <label class="label">{{ orderData.orderTime ? orderData.orderTime : '' }}</label>
                 </view>
             </view>
             <view class="information-view bame">
-                <view class="view-num"> 运费:<label class="label">包邮</label> </view>
+                <view class="view-num"> <text> 运费:</text> <label class="label">包邮</label> </view>
             </view>
             <view class="information-view">
                 <view class="view-num time" v-if="orderData.receiptAmount > 0">
-                    支付时间:<label class="label">{{ orderData.receiptDate ? orderData.receiptDate : '' }}</label>
+                    <text>支付时间:</text>
+                    <label class="label">{{ orderData.receiptDate ? orderData.receiptDate : '' }}</label>
                 </view>
             </view>
             <view class="information-view bame">
                 <view class="view-man">
-                    已退货/已取消:<label class="label"
-                        >{{ orderData.returnedNum }}/{{ orderData.actualCancelNum }}</label
-                    >
+                    <text>已退货/已取消:</text>
+                    <label class="label">{{ orderData.returnedNum }}/{{ orderData.actualCancelNum }}</label>
                 </view>
             </view>
         </view>
@@ -42,7 +52,7 @@
 </template>
 
 <script>
-import thorui from '@/components/clipboard/clipboard.thorui.js'; 
+import thorui from '@/components/clipboard/clipboard.thorui.js'
 export default {
     name: 'information',
     props: {

+ 2 - 0
main.js

@@ -6,6 +6,7 @@ import Api from './common/utilsTools.js'
 import Common from './common/common.js'
 import Util from './common/util.js'
 
+
 //友盟+小程序统计
 // #ifdef MP-WEIXIN
 // import '@/common/config/uma.init.js'
@@ -25,6 +26,7 @@ Vue.use(Common)
 // ServiceApi接口方法
 Vue.use(ServiceApi)
 
+
 const app = new Vue({
     store,
     ...App

+ 1 - 0
pages.json

@@ -9,6 +9,7 @@
                 "backgroundColor": "#F952B7",
                 "navigationBarBackgroundColor": "#F952B7",
                 "navigationBarTextStyle": "white"
+                
             }
         },
         {

+ 140 - 16
pages/goods/cart.vue

@@ -16,8 +16,8 @@
                 </view>
                 <!-- TODO -->
                 <view class="receive-coupon">
-                    <view class="tip-text">还差¥200可用“满200元减50元”优惠券</view>
-                    <view class="btn" @click="couponVisible = true">领券</view>
+                    <view class="tip-text">{{ couponTipText }}</view>
+                    <view class="btn" @click="receiveCoupon">领券</view>
                 </view>
             </template>
             <!-- 购物车列表 -->
@@ -54,8 +54,9 @@
                             <text>总价:</text> <text class="total-price">¥{{ allPrice | NumFormat }}</text>
                         </view>
                         <!-- TODO -->
-                        <view class="row">
-                            <text>共减</text> <text class="discounted-price">¥200.00</text>
+                        <view class="row" v-if="currentCouponIndex > -1">
+                            <text>共减</text>
+                            <text class="discounted-price">¥{{ currentCoupon.couponAmount | NumFormat }}</text>
                             <text @click="showDiscountedDetail">优惠明细</text>
                             <text
                                 class="iconfont"
@@ -78,8 +79,13 @@
         <cm-coupon-list
             title="优惠券"
             listType="search"
+            :couponList="couponList"
             :visible="couponVisible"
+            :btnUseType="2"
             @close="closeCouponList"
+            @tabClick="couponListTabClick"
+            @couponClick="couponClick"
+            :tabs="couponListTabs"
         ></cm-coupon-list>
         <!-- 优惠明细 -->
         <cm-drawer
@@ -92,10 +98,18 @@
         >
             <template>
                 <view class="discounted-ditail">
-                    <view class="row"> <text>商品总额</text> <text>¥450.00</text> </view>
-                    <view class="row"> <text>促销满减</text> <text class="red">-¥180.00</text> </view>
-                    <view class="row"> <text>优惠券</text> <text class="red">-¥20.00</text> </view>
-                    <view class="row total"> <text>总计</text> <text>¥250.00</text> </view>
+                    <view class="row">
+                        <text>商品总额</text> <text>¥{{ allPrice | NumFormat }}</text>
+                    </view>
+                    <view class="row">
+                        <text>促销满减</text> <text class="red">-¥{{ discountedPrice | NumFormat }}</text>
+                    </view>
+                    <view class="row" v-if="currentCouponIndex > -1">
+                        <text>优惠券</text> <text class="red">-¥{{ currentCoupon.couponAmount | NumFormat }}</text>
+                    </view>
+                    <view class="row total">
+                        <text>总计</text> <text>¥{{ finallyPrice | NumFormat }}</text>
+                    </view>
                     <view class="tip"> 实际订单金额以结算页为准 </view>
                 </view>
             </template>
@@ -121,6 +135,7 @@ import CmDrawer from '@/components/cm-module/cm-drawer/cm-drawer.vue'
 import CmCartProduct from '@/components/cm-module/cm-cart-product/cm-cart-product.vue'
 import HeaderCart from '@/components/cm-module/headerNavbar/header-cart.vue'
 import CmEmpty from '@/components/cm-module/cm-empty/cm-empty.vue'
+import { fetchSelectedProducts, findCouponBySelected, canUseCoupon, getCountPrice } from '@/common/couponUtil.js'
 
 import { mapGetters, mapActions, mapMutations } from 'vuex'
 
@@ -161,7 +176,14 @@ export default {
             listType: 'normal',
             failureListType: 'expired',
             scrollTop: 0,
-            isRequest: true
+            isRequest: true,
+
+            currentCouponIndex: -1,
+            selectedPoducts: [], //已勾选商品列表
+            receiveCouponList: [], // 已领取优惠券
+            ableCouponList: [], // 可领取优惠券
+            canUseCouponList: [], // 当前选中商品可使用的优惠券
+            currentTabIndex: 0
         }
     },
     onLoad() {
@@ -176,7 +198,8 @@ export default {
             'failureList',
             'kindCount',
             'userId',
-            'cartIds'
+            'cartIds',
+            'productIds'
         ]),
         //被选中的产品数量
         allCount() {
@@ -203,13 +226,67 @@ export default {
             if (this.cartTopFixed) {
                 paddingTop += 40
             }
-            if(this.isIphoneX){
+            if (this.isIphoneX) {
                 paddingBottom += 40
             }
             return {
                 paddingTop: paddingTop + 'px',
                 paddingBottom: paddingBottom + 'rpx'
             }
+        },
+        currentCoupon() {
+            return this.canUseCouponList[this.currentCouponIndex]
+        },
+        nextCoupon() {
+            if (this.currentCouponIndex <= 0) {
+                return this.currentCoupon
+            } else {
+                return this.canUseCouponList[this.currentCouponIndex - 1]
+            }
+        },
+        discountedPrice() {
+            return 0
+        },
+        finallyPrice() {
+            if (this.currentCoupon) {
+                return this.allPrice - this.discountedPrice - this.currentCoupon.couponAmount
+            }
+            return this.allPrice - this.discountedPrice
+        },
+        couponTipText() {
+            if (this.currentCouponIndex === -1) return ''
+            if (this.currentCoupon === this.nextCoupon) {
+                if (this.nextCoupon.noThresholdFlag === 1) {
+                    return `已享“减${this.currentCoupon.couponAmount}元”优惠券`
+                }
+                return `已享“满${this.currentCoupon.touchPrice}元减${this.currentCoupon.couponAmount}元”优惠券`
+            }
+            return `还差¥${this.nextCoupon.touchPrice - getCountPrice()}元可用“满${this.nextCoupon.touchPrice}元减${
+                this.nextCoupon.couponAmount
+            }元”优惠券`
+        },
+        couponList() {
+            if (this.currentTabIndex === 0) {
+                return this.receiveCouponList
+            } else {
+                return this.ableCouponList
+            }
+        },
+        couponListTabs() {
+            const tabs = []
+            const receiveCount = this.receiveCouponList.length
+            const ableCouponCount = this.ableCouponList.length
+            if (receiveCount > 0) {
+                tabs.push({ name: `已领取优惠券(${receiveCount})` })
+            } else {
+                tabs.push({ name: '已领取优惠券' })
+            }
+            if (ableCouponCount > 0) {
+                tabs.push({ name: `可领取优惠券(${ableCouponCount})` })
+            } else {
+                tabs.push({ name: '可领取优惠券' })
+            }
+            return tabs
         }
     },
     filters: {
@@ -228,6 +305,7 @@ export default {
             deep: true,
             handler(val, oldval) {
                 this.totalPeice()
+                this.resetCouponUtil()
             }
         },
         isshowDelbtn(val) {
@@ -260,15 +338,50 @@ export default {
     },
     methods: {
         ...mapActions('cart', ['initCart', 'removeFromCart']),
-        ...mapMutations('cart', ['selectAllProduct', 'saveCartIds', 'selectAllFailure']),
+        ...mapMutations('cart', ['selectAllProduct', 'saveCartIds', 'selectAllFailure', 'saveProductIds']),
         initData() {
             this.saveCartIds([]) // 清空已选项
+            this.saveProductIds([]) // 清空已选项
             this.isCheckAll = false
             this.isshowDelbtn = false
             this.initCart().finally(() => {
                 this.isRequest = false
+                this.getCouponList()
             })
         },
+        // 获取优惠券列表
+        getCouponList() {
+            const productIds = []
+            this.goodsList.forEach(shop => shop.productList.forEach(product => productIds.push(product.productId)))
+            this.CouponService.GetCouponByProductIds({ userId: this.userId, productIds: productIds.join(',') }).then(
+                res => {
+                    this.receiveCouponList = res.data.receiveCouponList
+                    this.ableCouponList = res.data.ableCouponList
+                    this.resetCouponUtil()
+                }
+            )
+        },
+        resetCouponUtil() {
+            this.selectedPoducts = fetchSelectedProducts(this.goodsList)
+            this.canUseCouponList = findCouponBySelected(this.productIds, this.receiveCouponList)
+            this.currentCouponIndex = canUseCoupon(0, this.productIds, this.canUseCouponList, this.selectedPoducts)
+        },
+        // 领取优惠券弹窗
+        receiveCoupon() {
+            this.couponVisible = true
+            this.getCouponList()
+        },
+        couponClick() {
+            // 领取优惠券
+            if (this.currentTabIndex === 1) {
+                this.getCouponList()
+            } else {
+                this.couponVisible = false
+            }
+        },
+        couponListTabClick(index) {
+            this.currentTabIndex = index
+        },
         // 关闭优惠券弹窗
         closeCouponList() {
             this.couponVisible = false
@@ -314,15 +427,19 @@ export default {
             if (this.isshowDelbtn) {
                 this.isCheckAll = this.isCheckAll && this.failureList.every(product => product.productsChecked)
             }
-            this.saveCartIds(this.getCheckedProductId())
+            this.getCheckedProductId()
         },
         // 获取勾选商品的id
         getCheckedProductId() {
             const cartIds = []
+            const productIds = []
             // 获取所有有效商品cartId
             this.goodsList.forEach(shop => {
                 const ids = shop.productList.reduce((cartIds, prod) => {
-                    if (prod.productsChecked) cartIds.push(prod.cartId)
+                    if (prod.productsChecked) {
+                        cartIds.push(prod.cartId)
+                        productIds.push(prod.productId)
+                    }
                     return cartIds
                 }, [])
                 cartIds.push(...ids)
@@ -335,8 +452,9 @@ export default {
                 }, [])
                 cartIds.push(...ids)
             }
-            console.log(cartIds)
-            return cartIds
+            this.saveProductIds(productIds) // 保存已选商品
+            this.saveCartIds(cartIds)
+            this.resetCouponUtil()
         },
         //计算总价格,每次调用此方法,将初始值为0,遍历价格并累加
         totalPeice() {
@@ -375,6 +493,7 @@ export default {
             this.isSelectAll()
             this.isshowDelbtn = false
         },
+
         //删除购物车商品
         deleteList() {
             if (this.cartIds.length <= 0) {
@@ -402,6 +521,7 @@ export default {
                 allPrice: this.allPrice,
                 allCount: this.allCount,
                 cartIds: this.cartIds.join(','),
+                productIds: this.productIds.join(','),
                 productCount: ''
             }
             this.$api.navigateTo(`/pages/user/order/create-order?data=${JSON.stringify({ data: cartPramsData })}`)
@@ -491,8 +611,12 @@ export default {
         padding: 24rpx;
         background: #fff;
         .tip-text {
+            width: 560rpx;
             font-size: 26rpx;
             color: #ff457b;
+            white-space: nowrap;
+            overflow: hidden;
+            text-overflow: ellipsis;
         }
         .btn {
             width: 88rpx;

+ 78 - 264
pages/goods/good-coupon-list.vue

@@ -1,68 +1,69 @@
 <template>
-    <view class="container clearfix tui-skeleton">
+    <view class="good-coupon-list">
         <!-- 骨架 -->
         <tui-skeleton v-if="skeletonShow" :isLoading="true" loadingType="2"></tui-skeleton>
-        <!-- 搜索 -->
-        <sui-search placeholder="请输入商品关键词" :radius="30" @search="searchBlur" @clear="searchClear"></sui-search>
-        <!-- 商品列表 -->
-        <view class="container-section clearfix">
-            <!-- 商品列表区域 -->
-            <view class="product-list" v-for="(pro, index) in productList" :key="index" @click.stop="Details(pro)">
-                <view class="product-list-image">
-                    <image class="product-image" :src="pro.mainImage" mode=""></image>
-                    <!-- 推荐 -->
-                    <image
-                        class="product-icon"
-                        :src="StaticUrl + 'recommend.png'"
-                        mode=""
-                        v-if="pro.recommend === '1'"
-                    ></image>
+        <template v-else>
+            <!-- 列表为空 -->
+            <cm-empty
+                v-if="productList.length <= 0"
+                message="暂无任何商品~"
+                :image="baseUrl + 'icon-empty-search.png'"
+                :offset="90"
+            ></cm-empty>
+            <template v-else>
+                <!-- 搜索 -->
+                <sui-search
+                    placeholder="请输入商品关键词"
+                    :radius="30"
+                    @search="searchBlur"
+                    @clear="searchClear"
+                    class="sui-search"
+                ></sui-search>
+                <!-- 商品列表 -->
+                <view class="product-list">
+                    <template v-for="(product, index) in productList">
+                        <cm-product class="product" :key="index" :data="product"></cm-product>
+                    </template>
                 </view>
-                <view class="product-list-msg">
-                    <view class="product-msg-name">{{ pro.name }}</view>
-                    <view class="product-list-tag " v-if="pro.activeStatus == 1">
-                        <text class="tag tag-02">活动价</text>
-                    </view>
-                    <view class="product-list-pri">
-                        <view class="price">¥{{ pro.price | PriceFormat }}</view>
-                        <view class="carts" @click.stop="handAddCarts(pro)">
-                            <view class="carts-add"> <text class="iconfont icon-gouwuche"></text> </view>
-                        </view>
-                    </view>
-                </view>
-            </view>
-        </view>
-        <tui-loadmore :index="2" :visible="isRequest"></tui-loadmore>
-        <tui-nomore :text="loadingText" :visible="!isRequest"></tui-nomore>
+                <!-- 加载更多 -->
+                <template v-if="productList.length > 6">
+                    <tui-loadmore :index="2" :visible="isRequest"></tui-loadmore>
+                    <tui-nomore :text="loadingText" :visible="!isRequest" backgroundColor="#fff"></tui-nomore>
+                </template>
+            </template>
+        </template>
         <!-- 侧边 -->
         <scroll-top :isScrollTop="isScrollTop" :bottom="160"></scroll-top>
     </view>
 </template>
 
 <script>
-import authorize from '@/common/authorize.js'
-import banner from '@/components/cm-module/homeIndex/banner.vue'
+import CmProduct from '@/components/cm-module/cm-product/cm-product.vue'
 import SuiSearch from '@/components/sui-search/sui-search.vue'
+import CmEmpty from '@/components/cm-module/cm-empty/cm-empty.vue'
 import { mapGetters, mapActions } from 'vuex'
 export default {
     components: {
-        banner,
+        CmEmpty,
         SuiSearch,
+        CmProduct
     },
     data() {
         return {
-            StaticUrl: this.$Static,
-            title: '', // 页面标题
-            floorId: '', //楼层id
-            skeletonShow: true,
+            baseUrl: this.$Static,
             productList: [], //商品列表
-            pageNum: 1,
-            pageSize: 10,
+            listQuery: {
+                userId: '',
+                couponId: '',
+                pageNum: 1,
+                pageSize: 10,
+                productName: ''
+            },
             hasNextPage: false,
             isScrollTop: false,
             isRequest: true,
-            keywords: '',
-            isRefresh: false
+            isRefresh: false,
+            timer: null
         }
     },
     filters: {
@@ -72,7 +73,8 @@ export default {
         }
     },
     onLoad(options) {
-        this.floorId = options.floorId
+        this.listQuery.couponId = options.couponId
+        this.listQuery.userId = this.userId
         this.fetchProductList()
     },
     computed: {
@@ -85,32 +87,23 @@ export default {
         ...mapActions('cart', ['addToCart']),
         //初始化商品数据列表
         fetchProductList() {
-            this.isRequest = true
-            this.ProductService.QueryProductList({
-                pageNum: this.pageNum,
-                pageSize: this.pageSize,
-                // floorId: this.floorId
-                floorId: 2
-            })
+            this.CouponService.ProductInfoByCoupon(this.listQuery)
                 .then(response => {
                     let data = response.data
-                    this.pageNum++
-                    this.hasNextPage = data.hasNextPage
-                    // 获取购物车商品数量
-                    // this.GetCartNumber();
-                    this.skeletonShow = false
                     if (this.isRefresh) {
                         this.productList = data.list
                     } else {
                         this.productList = [...this.productList, ...data.list]
                     }
+                    this.hasNextPage = data.hasNextPage
+                    this.listQuery.pageNum++
                 })
                 .catch(error => {
                     this.$util.msg(error.msg, 2000)
                 })
                 .finally(() => {
                     this.isRequest = false
-                    if(this.isRefresh){
+                    if (this.isRefresh) {
                         setTimeout(() => {
                             uni.stopPullDownRefresh()
                             this.isRefresh = false
@@ -118,23 +111,15 @@ export default {
                     }
                 })
         },
-        // 商品详情
-        Details(pro) {
-            this.$api.navigateTo(`/pages/goods/product?productId=${pro.productId}`)
-        },
-        // 添加到购物车
-        handAddCarts(pro) {
-            this.addToCart({ productId: pro.productId })
-        },
         // 搜索框失去焦点
         searchBlur(val) {
-            this.keywords = val
-            console.log('搜索框清空', this.keywords)
+            this.listQuery.productName = val
+            this.listQuery.pageNum = 1
+            this.fetchProductList()
         },
         // 搜索框清空
         searchClear() {
-            this.keywords = ''
-            console.log('搜索框清空', this.keywords)
+            this.listQuery.productName = ''
         }
     },
     // 监听页面滚动事件
@@ -149,209 +134,38 @@ export default {
     },
     onReachBottom() {
         if (!this.hasNextPage) return
-        this.fetchProductList()
-    },
-    onShareAppMessage(res) {
-        //分享转发
-        if (res.from === 'button') {
-            // 来自页面内转发按钮
-        }
-        return {
-            title: '国内外知名美容院线护肤品线上商城~',
-            path: 'pages/tabBar/index/index',
-            imageUrl: 'https://static.caimei365.com/app/mini-hehe/icon/icon-index-share.jpg'
-        }
+        clearTimeout(this.timer)
+        this.timer = setTimeout(() => {
+            console.log('触底了')
+            this.fetchProductList()
+        }, 200)
     }
 }
 </script>
 
-<style lang="scss">
-page {
-    background-color: #f7f7f7;
-}
-.container {
-    width: 750rxp;
-    height: auto;
-}
-.navbar-wrap {
-    position: fixed;
-    width: 100%;
-    top: 0;
-    z-index: 100000;
+<style lang="scss" scoped>
+.good-coupon-list {
+    padding-top: 124rpx;
+    min-height: 100%;
+    background: #f7f7f7;
     box-sizing: border-box;
-    background-image: linear-gradient(0deg, #f83c6c 0%, #fa55bf 100%);
-    background-size: cover;
-    border-bottom: none;
-    &.bgnone {
-        background: rgba(255, 255, 255, 0);
-    }
-    &.bgclass {
-        background: #f94a9b;
+    .sui-search {
+        position: fixed;
+        width: 100%;
+        top: 0;
+        left: 0;
+        z-index: 999;
     }
-}
-.navbar-text {
-    font-size: 30rpx;
-    color: #000000;
-    font-weight: 500;
-}
-.navbar-text.center {
-    text-align: center;
-}
-.navbar-text.left {
-    text-align: left;
-    padding-left: 45px;
-}
-.navbar-icon {
-    position: fixed;
-    display: flex;
-    box-sizing: border-box;
-}
-.navbar-icon .iconfont {
-    display: inline-block;
-    overflow: hidden;
-    font-size: 44rpx;
-    padding-right: 40rpx;
-    margin-top: 1px;
-}
-.navbar-icon .icon-iconfonticonfontsousuo1 {
-    color: #000000;
-}
-.navbar-icon view {
-    height: 18px;
-    border-left: 0.5px solid rgba(0, 0, 0, 0.3);
-    margin-top: 6px;
-}
-.navbar-loading {
-    background: #fff;
-    text-align: center;
-}
-.container-section {
-    width: 100%;
-    height: auto;
-    background-color: #f7f7f7;
-    box-sizing: border-box;
-    padding: 0 24rpx;
     .product-list {
-        width: 339rpx;
-        height: 532rpx;
-        float: left;
-        margin-right: 24rpx;
-        margin-top: 24rpx;
-        background-color: #ffffff;
-        border-radius: 16rpx;
-        &:nth-child(2n) {
-            margin-right: 0;
-        }
-        .product-list-image {
-            width: 100%;
-            height: 339rpx;
-            float: left;
-            position: relative;
-            .product-image {
-                width: 100%;
-                height: 100%;
-                display: block;
-                border-radius: 16rpx 16rpx 0 0;
-            }
-            .product-icon {
-                width: 68rpx;
-                height: 55rpx;
-                display: block;
-                position: absolute;
-                top: 0;
-                left: 34rpx;
-            }
-        }
-        .product-list-msg {
-            width: 100%;
-            height: 193rpx;
-            box-sizing: border-box;
-            padding: 16rpx 24rpx;
-            float: left;
-            position: relative;
-            .product-msg-name {
-                width: 100%;
-                height: 72rpx;
-                line-height: 35rpx;
-                text-overflow: ellipsis;
-                overflow: hidden;
-                display: -webkit-box;
-                -webkit-line-clamp: 2;
-                line-clamp: 2;
-                -webkit-box-orient: vertical;
-                font-size: $font-size-26;
-                color: #333333;
-                text-align: justify;
-                float: left;
-            }
-            .product-list-tag {
-                position: relative;
-                z-index: 9;
-                width: 100%;
-                height: 30rpx;
-                margin-top: 8rpx;
-                float: left;
-                .tag {
-                    display: inline-block;
-                    height: 32rpx;
-                    font-size: 22rpx;
-                    line-height: 30rpx;
-                    text-align: center;
-                    color: #f83c6c;
-                    float: left;
-                    margin-right: 10rpx;
-                    &.tag-02 {
-                        width: 80rpx;
-                        background: url(https://static.caimei365.com/app/mini-hehe/icon/icon-active.png) top center
-                            no-repeat;
-                        background-size: contain;
-                    }
-                    &.tag-01 {
-                        width: 56rpx;
-                        color: #fff;
-                        background-color: #f83c6c;
-                        border-radius: 4rpx;
-                    }
-                }
-            }
-            .product-list-pri {
-                width: 100%;
-                height: 44rpx;
-                float: left;
-                position: absolute;
-                bottom: 16rpx;
-                left: 0;
-                box-sizing: border-box;
-                padding: 0 24rpx;
-                .price {
-                    float: left;
-                    font-size: $font-size-26;
-                    color: #f83c6c;
-                    font-weight: bold;
-                    line-height: 44rpx;
-                }
-                .carts {
-                    float: right;
-                    .carts-add {
-                        width: 44rpx;
-                        height: 44rpx;
-                        text-align: center;
-                        line-height: 44rpx;
-                        background-color: #ff457b;
-                        border-radius: 50%;
-                        .iconfont {
-                            font-size: 32rpx;
-                            color: #ffffff;
-                        }
-                    }
-                }
-            }
+        display: flex;
+        justify-content: space-between;
+        flex-wrap: wrap;
+        padding: 0 24rpx 12rpx;
+        background-color: #f7f7f7;
+        box-sizing: border-box;
+        .product {
+            margin: 12rpx 0;
         }
     }
 }
-.clearfix::after {
-    content: '';
-    display: block;
-    clear: both;
-}
 </style>

+ 6 - 3
pages/goods/product-activi.vue

@@ -285,7 +285,7 @@
 </template>
 
 <script>
-import { mapGetters } from 'vuex'
+import { mapGetters, mapMutations } from 'vuex'
 import HeaderProduct from '@/components/cm-module/headerNavbar/header-poduct' //自定义导航
 import cmPrice from '@/components/cm-module/productDetails/cm-price-activity.vue' //价格显示
 import cmAttributes from '@/components/cm-module/productDetails/cm-attributes.vue' //规格信息
@@ -369,6 +369,8 @@ export default {
         this.linkPath = option.path
         this.isHeaderPoduct = true
         if (this.isShareType == 'share') {
+            // 收集分享信息
+            this.setInviteUserId(option.inviteUserId)
             wxLogin.wxLoginAuthorize()
         }
         if (option.page == 2) {
@@ -377,7 +379,7 @@ export default {
         this.getWinHeight()
     },
     computed: {
-        ...mapGetters(['hasLogin', 'isIphoneX'])
+        ...mapGetters(['hasLogin', 'isIphoneX', 'userId'])
     },
     filters: {
         NumFormat(value) {
@@ -387,6 +389,7 @@ export default {
         }
     },
     methods: {
+        ...mapMutations('user', ['setInviteUserId']),
         initData() {
             // 初始化商品详情查询
             this.ProductService.QueryProductDetils({
@@ -761,7 +764,7 @@ export default {
         }
         return {
             title: `${this.product.name}`,
-            path: `pages/goods/product?type=share&productId=${this.productId}`,
+            path: `pages/goods/product?type=share&productId=${this.productId}&inviteUserId=${this.userId}`,
             imageUrl: `${this.productImage[0]}`
         }
     },

+ 64 - 23
pages/goods/product.vue

@@ -125,11 +125,10 @@
                         <text class="iconfont icon-chakangengduo"></text>
                     </view>
                     <!-- 优惠券  TODO -->
-                    <view class="product-coupon" @click="couponVisible = true">
+                    <view class="product-coupon" @click="couponVisible = true" v-if="couponList.length > 0">
                         <view class="title">优惠券:</view>
                         <view class="coupon-tags">
-                            <text class="tag">满5000减100</text> <text class="tag">满5000减100</text>
-                            <text class="tag">满5000减100</text>
+                            <text class="tag" v-for="(tagName, index) in couponTags" :key="index">{{ tagName }}</text>
                         </view>
                         <text class="iconfont icon-chakangengduo"></text>
                     </view>
@@ -291,12 +290,20 @@
             </view>
         </template>
         <!-- 优惠券列表 TODO-->
-        <cm-coupon-list title="获取优惠券" listType="receive" :visible="couponVisible" @close="closeCouponList"></cm-coupon-list>
+        <cm-coupon-list
+            title="获取优惠券"
+            listType="receive"
+            :couponList="couponList"
+            :visible="couponVisible"
+            :showStatus="true"
+            @close="closeCouponList"
+            @couponClick="couponClick"
+        ></cm-coupon-list>
     </view>
 </template>
 
 <script>
-import { mapGetters, mapActions } from 'vuex'
+import { mapGetters, mapActions, mapMutations } from 'vuex'
 import HeaderProduct from '@/components/cm-module/headerNavbar/header-poduct' //自定义导航
 import cmPrice from '@/components/cm-module/productDetails/cm-price.vue' //价格显示
 import cmAttributes from '@/components/cm-module/productDetails/cm-attributes.vue' //规格信息
@@ -370,7 +377,8 @@ export default {
             sectionTopRangeArr: [],
             winHeight: '',
             isShowButton: false,
-            couponVisible: false
+            couponVisible: false,
+            couponList: []
         }
     },
     onLoad(option) {
@@ -379,15 +387,31 @@ export default {
         this.linkPath = option.path
         this.isHeaderPoduct = true
         if (this.isShareType == 'share') {
+            // 收集分享信息
+            this.setInviteUserId(option.inviteUserId)
             wxLogin.wxLoginAuthorize()
         }
         if (option.page == 2) {
             this.backPage = option.page
         }
         this.getWinHeight()
+        this.getCouponByProduct()
     },
     computed: {
-        ...mapGetters(['hasLogin', 'isIphoneX', 'kindCount', 'userIdentity', 'userId'])
+        ...mapGetters(['hasLogin', 'isIphoneX', 'kindCount', 'userIdentity', 'userId']),
+        // 优惠券标签
+        couponTags() {
+            const result = []
+            for (let i = 0; i < this.couponList.length; i++) {
+                if (i >= 3) return result
+                if (this.couponList[i].noThresholdFlag === 1) {
+                    result.push(`减${this.couponList[i].couponAmount}`)
+                } else {
+                    result.push(`满${this.couponList[i].touchPrice}减${this.couponList[i].couponAmount}`)
+                }
+            }
+            return result
+        }
     },
     filters: {
         NumFormat(value) {
@@ -398,11 +422,13 @@ export default {
     },
     methods: {
         ...mapActions('cart', ['addToCart', 'getCartNumber']),
+        ...mapMutations('user', ['setInviteUserId']),
+        // 关闭优惠券列表
         closeCouponList() {
             this.couponVisible = false
         },
+        // 初始化商品详情查询
         initData() {
-            // 初始化商品详情查询
             this.ProductService.QueryProductDetils({
                 productId: this.productId
             })
@@ -443,13 +469,26 @@ export default {
                     this.$util.msg(error.msg, 2000)
                 })
         },
+        // 获取当前商品可用优惠券列表
+        getCouponByProduct() {
+            this.CouponService.GetCouponByProduct({
+                productId: this.productId,
+                userId: this.userId
+            }).then(res => {
+                this.couponList = res.data
+            })
+        },
+        // 优惠券列表按钮点击事件
+        couponClick() {
+            this.couponVisible = false
+        },
+        //顶部商品图片切换
         swiperChange(e) {
-            //顶部商品图片切换
             const index = e.detail.current
             this.current = index
         },
+        //顶部商品图片预览
         previewImg(index) {
-            //顶部商品图片预览
             isPreviewImg = true
             let previewUrls = this.productImage
             uni.previewImage({
@@ -458,8 +497,8 @@ export default {
                 longPressActions: ''
             })
         },
+        //商品详情&&供应商信息tab切换
         tabClick(index) {
-            //商品详情&&供应商信息tab切换
             this.tabSelectFlag = true
             this.tabCurrentIndex = index
             let classIndex = '.product-details' + index
@@ -486,29 +525,29 @@ export default {
         handleContact(e) {
             //跳转小程序客服
         },
+        //底部购物车按钮点击
         buyProductCart() {
-            //底部购物车按钮点击
             if (this.hasLogin) {
                 this.$api.navigateTo('/pages/goods/cart')
             } else {
                 this.$api.navigateTo('/pages/login/login')
             }
         },
+        //加入购物车&&立即购买点击
         btnGetConfirm(type) {
-            //加入购物车&&立即购买点击
             if (this.hasLogin) {
                 this.showSpec(type)
             } else {
                 this.$api.navigateTo('/pages/login/login')
             }
         },
+        //popup弹窗数量增加按钮
         changeCountAdd() {
-            //popup弹窗数量增加按钮
             this.number++
             this.processActivityPrice()
         },
+        //popup弹窗数量减按钮
         changeCountSub() {
-            //popup弹窗数量减按钮
             if (this.number == 1) {
                 this.isQuantity = true
                 this.$util.msg('购买数量不能低于1', 2000)
@@ -519,6 +558,7 @@ export default {
                 this.isQuantity = false
             }
         },
+        // 设置购买数量
         changeNumber(e) {
             let _value = e.detail.value
             if (!this.$api.isNumber(_value)) {
@@ -531,8 +571,8 @@ export default {
             }
             this.processActivityPrice()
         },
+        //单独处理活动价格和阶梯价格
         processActivityPrice() {
-            //单独处理活动价格和阶梯价格
             if ((this.ladderPriceFlag == '0' && this.product.actStatus == 0) || this.product.actStatus == 1) {
                 this.buyRetailPrice = this.product.retailPrice
             } else {
@@ -543,20 +583,20 @@ export default {
                 })
             }
         },
+        //显示选择数量确认弹窗
         showSpec(type) {
-            //显示选择数量确认弹窗
             this.isBtnType = type
             this.specClass = 'show'
         },
+        //关闭选择数量确认弹窗
         hideSpec() {
-            //关闭选择数量确认弹窗
             this.specClass = 'hide'
             setTimeout(() => {
                 this.specClass = 'none'
             }, 200)
         },
+        //加入购物车&&立即购买跳转订单页并关闭弹窗
         btnConfirm() {
-            //加入购物车&&立即购买跳转订单页并关闭弹窗
             if (this.isBtnType == 'add') {
                 this.addToCart({
                     productId: this.productId,
@@ -567,8 +607,8 @@ export default {
                 this.toConfirmation()
             }
         },
+        //跳转确认订单页面
         toConfirmation() {
-            //跳转确认订单页面
             this.specClass = 'hide'
             let productStp = {
                 allPrice: this.number * this.buyRetailPrice,
@@ -583,11 +623,12 @@ export default {
                 this.specClass = 'none'
             }, 200)
         },
+        // 获得胶囊按钮位置信息
         setHeaderBtnPosi() {
-            // 获得胶囊按钮位置信息
             let headerBtnPosi = uni.getMenuButtonBoundingClientRect()
             return headerBtnPosi
         },
+        // 获取设备信息
         setSysteminfo() {
             let systeminfo
             uni.getSystemInfo({
@@ -608,7 +649,7 @@ export default {
             }
             return {
                 title: `${this.product.name}`,
-                path: `pages/goods/product?type=share&productId=${this.productId}`,
+                path: `pages/goods/product?type=share&productId=${this.productId}&inviteUserId=${this.userId}`,
                 imageUrl: `${this.productImage[0]}`
             }
         },
@@ -710,7 +751,7 @@ export default {
         }
         return {
             title: `${this.product.name}`,
-            path: `pages/goods/product?type=share&productId=${this.productId}`,
+            path: `pages/goods/product?type=share&productId=${this.productId}&inviteUserId=${this.userId}`,
             imageUrl: `${this.productImage[0]}`
         }
     },

+ 7 - 3
pages/goods/search.vue

@@ -96,7 +96,7 @@
 </template>
 
 <script>
-import { mapGetters, mapActions } from 'vuex'
+import { mapGetters, mapActions, mapMutations } from 'vuex'
 import modalLayer from '@/components/cm-module/modal-layer/modal-layer'
 import authorize from '@/common/authorize.js'
 import wxLogin from '@/services/wxLogin.js'
@@ -149,6 +149,8 @@ export default {
     },
     onLoad(option) {
         if (option.type == 'share') {
+            // 收集分享信息
+            this.setInviteUserId(option.inviteUserId)
             wxLogin.wxLoginAuthorize()
         }
         this.$api.getStorage().then(resolve => {
@@ -171,10 +173,12 @@ export default {
         }
     },
     computed: {
-        ...mapGetters(['hasLogin'])
+        ...mapGetters(['hasLogin', 'userId'])
     },
     methods: {
         ...mapActions('cart',['addToCart']),
+        ...mapActions('user',['setInviteUserId']),
+        ...mapMutations('user', ['setInviteUserId']),
         InitGetSerachRecord() {
             //查询搜索历史记录
             this.ProductService.GetProductSearchHistory({ userId: this.listQuery.userId }).then(response => {
@@ -333,7 +337,7 @@ export default {
         }
         return {
             title: `点击查看“${this.listQuery.name}”相关的商品`,
-            path: `/pages/goods/search?type=share&keyWord=${this.listQuery.name}`
+            path: `/pages/goods/search?type=share&keyWord=${this.listQuery.name}&inviteUserId=${this.userId}`
         }
     },
     onShow() {

+ 166 - 35
pages/tabBar/cart/index.vue

@@ -10,8 +10,8 @@
                 </view>
                 <!-- TODO -->
                 <view class="receive-coupon">
-                    <view class="tip-text">还差¥200可用“满200元减50元”优惠券</view>
-                    <view class="btn" @click="couponVisible = true">领券</view>
+                    <view class="tip-text">{{ couponTipText }}</view>
+                    <view class="btn" @click="receiveCoupon">领券</view>
                 </view>
             </template>
             <!-- 购物车列表 -->
@@ -47,8 +47,9 @@
                             <text>总价:</text> <text class="total-price">¥{{ allPrice | NumFormat }}</text>
                         </view>
                         <!-- TODO -->
-                        <view class="row">
-                            <text>共减</text> <text class="discounted-price">¥200.00</text>
+                        <view class="row" v-if="currentCouponIndex > -1">
+                            <text>共减</text>
+                            <text class="discounted-price">¥{{ currentCoupon.couponAmount | NumFormat }}</text>
                             <text @click="showDiscountedDetail">优惠明细</text>
                             <text
                                 class="iconfont"
@@ -71,8 +72,13 @@
         <cm-coupon-list
             title="优惠券"
             listType="search"
+            :couponList="couponList"
             :visible="couponVisible"
+            :btnUseType="2"
             @close="closeCouponList"
+            @tabClick="couponListTabClick"
+            @couponClick="couponClick"
+            :tabs="couponListTabs"
         ></cm-coupon-list>
         <!-- 优惠明细 -->
         <cm-drawer
@@ -85,10 +91,18 @@
         >
             <template>
                 <view class="discounted-ditail">
-                    <view class="row"> <text>商品总额</text> <text>¥450.00</text> </view>
-                    <view class="row"> <text>促销满减</text> <text class="red">-¥180.00</text> </view>
-                    <view class="row"> <text>优惠券</text> <text class="red">-¥20.00</text> </view>
-                    <view class="row total"> <text>总计</text> <text>¥250.00</text> </view>
+                    <view class="row">
+                        <text>商品总额</text> <text>¥{{ allPrice | NumFormat }}</text>
+                    </view>
+                    <view class="row">
+                        <text>促销满减</text> <text class="red">-¥{{ discountedPrice | NumFormat }}</text>
+                    </view>
+                    <view class="row" v-if="currentCouponIndex > -1">
+                        <text>优惠券</text> <text class="red">-¥{{ currentCoupon.couponAmount | NumFormat }}</text>
+                    </view>
+                    <view class="row total">
+                        <text>总计</text> <text>¥{{ finallyPrice | NumFormat }}</text>
+                    </view>
                     <view class="tip"> 实际订单金额以结算页为准 </view>
                 </view>
             </template>
@@ -108,12 +122,13 @@
 </template>
 
 <script>
-import authorize from '@/common/authorize.js'
+import { isIntersect } from '@/common/util.js'
 import CmCouponList from '@/components/cm-module/cm-coupon-list/cm-coupon-list'
 import CmDrawer from '@/components/cm-module/cm-drawer/cm-drawer.vue'
 import CmCartProduct from '@/components/cm-module/cm-cart-product/cm-cart-product.vue'
 import CmEmpty from '@/components/cm-module/cm-empty/cm-empty.vue'
 import { mapGetters, mapActions, mapMutations } from 'vuex'
+import { fetchSelectedProducts, findCouponBySelected, canUseCoupon, getCountPrice } from '@/common/couponUtil.js'
 
 export default {
     components: {
@@ -141,12 +156,17 @@ export default {
             listType: 'normal',
             failureListType: 'expired',
             scrollTop: 0,
-            isRequest: true
+            isRequest: true,
+
+            currentCouponIndex: -1,
+            selectedPoducts: [], //已勾选商品列表
+            receiveCouponList: [], // 已领取优惠券
+            ableCouponList: [], // 可领取优惠券
+            canUseCouponList: [], // 当前选中商品可使用的优惠券
+            currentTabIndex: 0
         }
     },
-    onLoad() {
-        this.setScrollHeight()
-    },
+
     computed: {
         ...mapGetters([
             'hasLogin',
@@ -156,7 +176,8 @@ export default {
             'failureList',
             'kindCount',
             'userId',
-            'cartIds'
+            'cartIds',
+            'productIds'
         ]),
         //被选中的产品数量
         allCount() {
@@ -164,6 +185,60 @@ export default {
         },
         cartTopFixed() {
             return this.scrollTop > 0 && !this.isshowDelbtn
+        },
+        currentCoupon() {
+            return this.canUseCouponList[this.currentCouponIndex]
+        },
+        nextCoupon() {
+            if (this.currentCouponIndex <= 0) {
+                return this.currentCoupon
+            } else {
+                return this.canUseCouponList[this.currentCouponIndex - 1]
+            }
+        },
+        discountedPrice() {
+            return 0
+        },
+        finallyPrice() {
+            if (this.currentCoupon) {
+                return this.allPrice - this.discountedPrice - this.currentCoupon.couponAmount
+            }
+            return this.allPrice - this.discountedPrice
+        },
+        couponTipText() {
+            if (this.currentCouponIndex === -1) return ''
+            if (this.currentCoupon === this.nextCoupon) {
+                if (this.nextCoupon.noThresholdFlag === 1) {
+                    return `已享“减${this.currentCoupon.couponAmount}元”优惠券`
+                }
+                return `已享“满${this.currentCoupon.touchPrice}元减${this.currentCoupon.couponAmount}元”优惠券`
+            }
+            return `还差¥${this.nextCoupon.touchPrice - getCountPrice()}元可用“满${this.nextCoupon.touchPrice}元减${
+                this.nextCoupon.couponAmount
+            }元”优惠券`
+        },
+        couponList() {
+            if (this.currentTabIndex === 0) {
+                return this.receiveCouponList
+            } else {
+                return this.ableCouponList
+            }
+        },
+        couponListTabs() {
+            const tabs = []
+            const receiveCount = this.receiveCouponList.length
+            const ableCouponCount = this.ableCouponList.length
+            if (receiveCount > 0) {
+                tabs.push({ name: `已领取优惠券(${receiveCount})` })
+            } else {
+                tabs.push({ name: '已领取优惠券' })
+            }
+            if (ableCouponCount > 0) {
+                tabs.push({ name: `可领取优惠券(${ableCouponCount})` })
+            } else {
+                tabs.push({ name: '可领取优惠券' })
+            }
+            return tabs
         }
     },
     filters: {
@@ -182,6 +257,7 @@ export default {
             deep: true,
             handler(val, oldval) {
                 this.totalPeice()
+                this.resetCouponUtil()
             }
         },
         isshowDelbtn(val) {
@@ -202,6 +278,9 @@ export default {
             }, 2000)
         })
     },
+    onPageScroll(e) {
+        this.scrollTop = e.scrollTop
+    },
     onShow() {
         if (this.hasLogin) {
             this.initData()
@@ -209,34 +288,60 @@ export default {
             this.$api.redirectTo('/pages/login/login')
         }
     },
-    onPageScroll(e) {
-        this.scrollTop = e.scrollTop
+    onLoad() {
+        this.setScrollHeight()
     },
     methods: {
         ...mapActions('cart', ['initCart', 'removeFromCart']),
-        ...mapMutations('cart', ['selectAllProduct', 'saveCartIds', 'selectAllFailure']),
+        ...mapMutations('cart', ['selectAllProduct', 'saveCartIds', 'selectAllFailure', 'saveProductIds']),
         initData() {
             this.saveCartIds([]) // 清空已选项
+            this.saveProductIds([]) // 清空已选项
             this.isCheckAll = false
             this.isshowDelbtn = false
-            this.initCart().finally(() => {
-                this.isRequest = false
-            })
+            // 初始化购物车后也要获取商品下的优惠券列表
+            this.initCart()
+                .then(() => {
+                    this.getCouponList()
+                })
+                .finally(() => {
+                    this.isRequest = false
+                })
         },
-        // 关闭优惠券弹窗
-        closeCouponList() {
-            this.couponVisible = false
+        // 获取优惠券列表
+        getCouponList() {
+            if (this.isEmpty) return
+            const productIds = []
+            this.goodsList.forEach(shop => shop.productList.forEach(product => productIds.push(product.productId)))
+            this.CouponService.GetCouponByProductIds({ userId: this.userId, productIds: productIds.join(',') }).then(
+                res => {
+                    this.receiveCouponList = res.data.receiveCouponList
+                    this.ableCouponList = res.data.ableCouponList
+                    this.resetCouponUtil()
+                }
+            )
         },
-        // 活动价弹窗
-        clickPopupShow(pros, type) {
-            if (pros.ladderList.length > 0) {
-                this.popupShow = true
-                this.handlerPros = pros
+        resetCouponUtil() {
+            if(this.receiveCouponList.length <= 0) return
+            this.selectedPoducts = fetchSelectedProducts(this.goodsList)
+            this.canUseCouponList = findCouponBySelected(this.productIds, this.receiveCouponList)
+            this.currentCouponIndex = canUseCoupon(0, this.productIds, this.canUseCouponList, this.selectedPoducts)
+        },
+        couponListTabClick(index) {
+            this.currentTabIndex = index
+        },
+        couponClick() {
+            // 领取优惠券
+            if (this.currentTabIndex === 1) {
+                this.getCouponList()
+            }else{
+                this.couponVisible = false
             }
         },
-        // 优惠明细
-        showDiscountedDetail() {
-            this.showDitail = true
+        // 领取优惠券弹窗
+        receiveCoupon(){
+            this.couponVisible = true
+            this.getCouponList()
         },
         // 勾选单个失效商品
         chooseFailureProduct() {
@@ -268,15 +373,19 @@ export default {
             if (this.isshowDelbtn) {
                 this.isCheckAll = this.isCheckAll && this.failureList.every(product => product.productsChecked)
             }
-            this.saveCartIds(this.getCheckedProductId())
+            this.getCheckedProductId()
         },
         // 获取勾选商品的id
         getCheckedProductId() {
             const cartIds = []
+            const productIds = []
             // 获取所有有效商品cartId
             this.goodsList.forEach(shop => {
                 const ids = shop.productList.reduce((cartIds, prod) => {
-                    if (prod.productsChecked) cartIds.push(prod.cartId)
+                    if (prod.productsChecked) {
+                        cartIds.push(prod.cartId)
+                        productIds.push(prod.productId)
+                    }
                     return cartIds
                 }, [])
                 cartIds.push(...ids)
@@ -289,8 +398,9 @@ export default {
                 }, [])
                 cartIds.push(...ids)
             }
-            console.log(cartIds)
-            return cartIds
+            this.saveProductIds(productIds) // 保存已选商品
+            this.saveCartIds(cartIds)
+            this.resetCouponUtil()
         },
         //计算总价格,每次调用此方法,将初始值为0,遍历价格并累加
         totalPeice() {
@@ -347,6 +457,22 @@ export default {
             })
             this.modal = false
         },
+        // 关闭优惠券弹窗
+        closeCouponList() {
+            this.couponVisible = false
+        },
+        // 活动价弹窗
+        clickPopupShow(pros, type) {
+            if (pros.ladderList.length > 0) {
+                this.popupShow = true
+                this.handlerPros = pros
+            }
+        },
+        // 优惠明细
+        showDiscountedDetail() {
+            this.showDitail = true
+        },
+
         //跳转确认订单页面
         toConfirmation() {
             if (this.cartIds.length <= 0) {
@@ -356,6 +482,7 @@ export default {
                 allPrice: this.allPrice,
                 allCount: this.allCount,
                 cartIds: this.cartIds.join(','),
+                productIds: this.productIds.join(','),
                 productCount: ''
             }
             this.$api.navigateTo(`/pages/user/order/create-order?data=${JSON.stringify({ data: cartPramsData })}`)
@@ -432,8 +559,12 @@ export default {
         padding: 24rpx;
         background: #fff;
         .tip-text {
+            width: 560rpx;
             font-size: 26rpx;
             color: #ff457b;
+            white-space: nowrap;
+            overflow: hidden;
+            text-overflow: ellipsis;
         }
         .btn {
             width: 88rpx;

+ 13 - 6
pages/tabBar/index/index.vue

@@ -51,13 +51,13 @@
                 title="呵呵商城"
                 subTitle="您已获得优惠券奖励,赶紧去领取吧!"
                 :image="StaticUrl + 'logo.png'"
+                @click="handleSelectorClick"
             ></cm-selector-coupons>
         </template>
     </view>
 </template>
 
 <script>
-import authorize from '@/common/authorize.js'
 import banner from '@/components/cm-module/homeIndex/banner.vue'
 import CmProduct from '@/components/cm-module/cm-product/cm-product.vue'
 import CmActivePopup from '@/components/cm-module/cm-active-popup/cm-active-popup.vue'
@@ -82,15 +82,17 @@ export default {
             hasNextPage: false,
             isScrollTop: false,
             isRequest: true,
-            activePopupVisible: true, // 活动弹窗
+            activePopupVisible: false, // 活动弹窗
             tipVisible: true //优惠券领取提示
         }
     },
-    onLoad() {
+    onLoad(option) {
+        // 收集分享信息
+        if (option.type && option.type === 'share') this.setInviteUserId(option.inviteUserId)
         this.init()
     },
     computed: {
-        ...mapGetters(['hasLogin', 'activePopupType']),
+        ...mapGetters(['hasLogin', 'activePopupType', 'userId']),
         couponActivityIcon() {
             let icon = 'news'
             switch (this.activePopupType) {
@@ -115,6 +117,7 @@ export default {
     },
     methods: {
         ...mapMutations('coupon', ['updatePopupType']),
+        ...mapMutations('user', ['setInviteUserId']),
         ...mapActions('user', ['wechatlogin']),
         ...mapActions('cart', ['getCartNumber']),
         // 首页初始化
@@ -144,6 +147,9 @@ export default {
                 this.productFloor = response.data
             })
         },
+        handleSelectorClick(){
+            this.$api.navigateTo('/pages/user/activity/coupon-find-list')
+        },
         //跳转楼层
         navToDetailPage(floor) {
             this.$api.navigateTo(`/pages/goods/good-floorMore?floorId=${floor.floorId}&title=${floor.title}`)
@@ -158,6 +164,7 @@ export default {
         // 活动弹窗关闭
         activeClosed() {
             this.activePopupVisible = false
+            console.log(this.activePopupType)
             this.updatePopupType(this.activePopupType - 1)
             uni.setStorageSync('couponPopupType', new Date().getDay())
         }
@@ -181,7 +188,7 @@ export default {
         }
         return {
             title: '国内外知名美容院线护肤品线上商城~',
-            path: 'pages/tabBar/index/index',
+            path: `pages/tabBar/index/index?type=share&inviteUserId=${this.userId}`,
             imageUrl: 'https://static.caimei365.com/app/mini-hehe/icon/icon-index-share.jpg'
         }
     },
@@ -193,7 +200,7 @@ export default {
 }
 </script>
 
-<style lang="scss">
+<style lang="scss" scoped>
 .home {
     background: url(https://static.caimei365.com/app/mini-hehe/icon/icon-index-bg.png) no-repeat top center;
     background-size: 750rpx auto;

+ 6 - 5
pages/tabBar/user/index.vue

@@ -64,8 +64,7 @@
                 <view class="place-menu-cell" @click="navigator('/pages/user/activity/coupon-list')">
                     <view class="place-left">
                         <image class="place-menu-icon" :src="StaticUrl + 'icon-coupon.png'" mode=""></image>
-                        <text class="place-menu-title">优惠券</text>
-                        <text class="coupons-count">6</text>
+                        <text class="place-menu-title">优惠券</text> <text class="coupons-count" v-if="unusedNum > 0">{{ unusedNum }}</text>
                     </view>
                     <text class="iconfont icon-chakangengduo"></text>
                 </view>
@@ -127,7 +126,7 @@ export default {
         }
     },
     computed: {
-        ...mapGetters(['hasLogin', 'userInfo', 'userId', 'userIdentity'])
+        ...mapGetters(['hasLogin', 'userInfo', 'userId', 'userIdentity', 'unusedNum'])
     },
     filters: {
         countNum(value) {
@@ -138,11 +137,13 @@ export default {
         if (this.hasLogin) {
             this.getCartNumber()
             this.GetUserInfoPersonal()
+            this.initReceiveCouponCount()
         }
     },
     methods: {
         ...mapMutations('app', ['login', 'logout']),
         ...mapActions('cart', ['getCartNumber']),
+        ...mapActions('coupon', ['initReceiveCouponCount']),
         //初始化个人中心数据
         GetUserInfoPersonal() {
             this.UserService.GetUserOrderTotal({
@@ -356,14 +357,14 @@ export default {
                 font-size: $font-size-28;
                 color: #333333;
             }
-            .coupons-count{
+            .coupons-count {
                 width: 240rpx;
                 float: right;
                 height: 36rpx;
                 line-height: 36rpx;
                 font-size: $font-size-28;
                 text-align: right;
-                color: #FF457B;
+                color: #ff457b;
             }
         }
         .iconfont {

+ 6 - 2
pages/user/activity/activity.vue

@@ -14,6 +14,7 @@
                     <view class="product-msg-name">{{ pro.name }}</view>
                     <view class="product-list-tag" v-if="pro.activeStatus === 1">
                         <text class="tag tag-01">促销</text> <text class="tag tag-02">活动价</text>
+                        <text class="tag tag-02" v-if="pro.couponsLogo">优惠券</text>
                     </view>
                     <view class="product-list-pri">
                         <view class="price">¥{{ pro.price | priceFormat }}</view>
@@ -35,7 +36,7 @@
 
 <script>
 import wxLogin from '@/services/wxLogin.js'
-import { mapGetters, mapActions } from 'vuex'
+import { mapGetters, mapActions, mapMutations } from 'vuex'
 import cmDrag from '@/components/cm-module/cm-drag/cm-drag'
 
 export default {
@@ -62,6 +63,8 @@ export default {
         }
     },
     onLoad(option) {
+        // 收集分享信息
+        if (option.type && option.type === 'share') this.setInviteUserId(option.inviteUserId)
         this.listQuery.activityId = option.activityId
         this.listQuery.userId = this.userId
         this.activityName = option.name
@@ -81,6 +84,7 @@ export default {
     },
     methods: {
         ...mapActions('cart', ['addToCart']),
+        ...mapMutations('user', ['setInviteUserId']),
         // 获取活动信息
         getProductActivityDetails() {
             this.loadmore = true
@@ -138,7 +142,7 @@ export default {
         }
         return {
             title: `${this.activityName}`,
-            path: `/pages/user/activity/activity?activityId=${this.listQuery.activityId}&userId=${this.userId}`,
+            path: `/pages/user/activity/activity?type=share&activityId=${this.listQuery.activityId}&userId=${this.userId}&inviteUserId=${this.userId}`,
             imageUrl: 'https://static.caimei365.com/app/mini-hehe/icon/icon-index-share.jpg'
         }
     }

+ 2 - 2
pages/user/activity/coupon-find-list.vue

@@ -38,13 +38,13 @@
                     <view class="row">
                         <view class="dt">好友分享券</view>
                         <view class="dd">
-                            登录用户可通过分享商城给好友,当好友成功登录后,您可以领取一张好友分享券。
+                            登录用户可通过分享商城给好友,当好友注册登录成功后,您可以领取一张好友分享券。
                         </view>
                     </view>
                     <view class="row">
                         <view class="dt">好友消费券</view>
                         <view class="dd">
-                            登录用户可通过分享商城给好友,当好友成功消费一笔订单后,您将可以领取一张好友消费券。
+                            邀请成功的好友每消费一笔订单,您将可以领取一张好友消费券。
                         </view>
                     </view>
                 </view>

+ 167 - 41
pages/user/activity/coupon-list.vue

@@ -1,40 +1,62 @@
 <template>
     <!-- TODO -->
     <view class="coupon-find-list">
+        <tui-skeleton v-if="isRequest" loadingType="2"></tui-skeleton>
         <!-- tabs -->
-        <tui-tabs
-            :tabs="tabs"
-            :currentTab="currentTab"
-            @change="tabChange"
-            :sliderWidth="118"
-            color="#333333"
-            selectedColor="#FF457B"
-            sliderBgColor="#FF457B"
-        ></tui-tabs>
-        <!-- 优惠券列表 -->
-        <swiper
-            :indicator-dots="false"
-            :autoplay="false"
-            class="swiper"
-            :style="{ height: swiperHeight + 'px' }"
-            :current="currentTab"
-            @change="swiperChange"
-        >
-            <swiper-item class="coupon-list"> <cm-coupon :key="i" v-for="i in 15"></cm-coupon> </swiper-item>
-            <swiper-item class="coupon-list"> <cm-coupon :key="i" v-for="i in 3"></cm-coupon> </swiper-item>
-            <swiper-item class="coupon-list"> 
-                <cm-empty message="暂无任何优惠券~" :image="baseUrl + 'icon-coupon-empty.png'" :offset="-12"></cm-empty>
-            </swiper-item>
-        </swiper>
-        <!-- 跳转领券中心 -->
-        <view class="footer"> <view class="btn">领券中心</view> </view>
+        <template v-else>
+            <tui-tabs
+                :tabs="tabs"
+                :currentTab="currentTab"
+                @change="tabChange"
+                :sliderWidth="118"
+                color="#333333"
+                selectedColor="#FF457B"
+                sliderBgColor="#FF457B"
+            ></tui-tabs>
+            <!-- 优惠券列表 -->
+            <swiper
+                :indicator-dots="false"
+                :autoplay="false"
+                class="swiper"
+                :style="{ height: swiperHeight + 'px' }"
+                :current="currentTab"
+                @change="swiperChange"
+            >
+                <swiper-item class="coupon-list" v-for="(item, type) of couponData" :key="type">
+                    <cm-empty
+                        v-if="item.couponList.length <= 0"
+                        message="暂无任何优惠券~"
+                        :image="baseUrl + 'icon-coupon-empty.png'"
+                        :offset="-12"
+                    ></cm-empty>
+                    <scroll-view scroll-y="true" class="coupon-scorll" @scrolltolower="scorllBottom" v-else>
+                        <template v-for="(coupon, index) in item.couponList">
+                            <cm-coupon
+                                :key="index"
+                                :couponData="coupon"
+                                @btnClick="couponClick"
+                                :showStatus="item.showStatus"
+                            ></cm-coupon>
+                        </template>
+                        <template v-if="item.couponList.length >= 6">
+                            <tui-loadmore :index="3" :visible="loadmore"></tui-loadmore>
+                            <tui-nomore :text="loadingText" :visible="!loadmore" backgroundColor="#f7f7f7"></tui-nomore>
+                        </template>
+                    </scroll-view>
+                </swiper-item>
+            </swiper>
+            <!-- 跳转领券中心 -->
+            <view class="footer">
+                <view class="btn" @click="$api.navigateTo('/pages/user/activity/coupon-find-list')">领券中心</view>
+            </view>
+        </template>
     </view>
 </template>
 
 <script>
 import CmCoupon from '@/components/cm-module/cm-coupon/cm-coupon.vue'
 import CmEmpty from '@/components/cm-module/cm-empty/cm-empty.vue'
-import { mapGetters } from 'vuex'
+import { mapGetters, mapActions } from 'vuex'
 export default {
     components: {
         CmCoupon,
@@ -44,51 +66,152 @@ export default {
         return {
             windowHeight: 0,
             baseUrl: this.$Static,
-            tabs: [
-                {
-                    name: '未使用10'
+            isRequest: true,
+            loadmore: false, // 正在加载更多
+            currentTab: 0,
+            pageSize: 6,
+            timer: null,
+            couponData: {
+                // 已领取/未使用
+                0: {
+                    type: 'received',
+                    pageNum: 1,
+                    status: 1,
+                    hasNextPage: false,
+                    couponList: [],
+                    showStatus: false,
+                    total: 0
                 },
-                {
-                    name: '已使用10'
+                // 已使用
+                1: {
+                    type: 'used',
+                    pageNum: 1,
+                    status: 2,
+                    hasNextPage: false,
+                    couponList: [],
+                    showStatus: true,
+                    total: 0
                 },
-                {
-                    name: '已失效10'
+                // 已过期
+                2: {
+                    type: 'expired',
+                    pageNum: 1,
+                    status: 3,
+                    hasNextPage: false,
+                    couponList: [],
+                    showStatus: true,
+                    total: 0
                 }
-            ],
-            currentTab: 0
+            }
         }
     },
     computed: {
-        ...mapGetters(['isIphoneX']),
+        ...mapGetters(['isIphoneX', 'userId', 'unusedNum', 'expiredNum', 'usedNum']),
         swiperHeight() {
             if (this.isIphoneX) {
                 return this.windowHeight - 120
             }
             return this.windowHeight - 80
             // return this.swiperHeight
+        },
+        // 当前选中tab对应的优惠券列表信息
+        queryInfo() {
+            return this.couponData[this.currentTab]
+        },
+        loadingText() {
+            return this.queryInfo.hasNextPage ? '上拉加载更多' : '没有更多了'
+        },
+        // tabs列表
+        tabs() {
+            return [
+                {
+                    name: this.makeTabText(this.unusedNum, '未使用')
+                },
+                {
+                    name: this.makeTabText(this.usedNum, '已使用')
+                },
+                {
+                    name: this.makeTabText(this.expiredNum, '已失效')
+                }
+            ]
         }
     },
     onLoad() {
         this.getWindowHeight()
+        this.initCouponList()
     },
     methods: {
+        // tab文字提示
+        makeTabText(number, text) {
+            if (number <= 0) return text
+            return number > 99 ? `${text} 99+` : `${text} ${number}`
+        },
+        // 初始化列表
+        async initCouponList() {
+            try {
+                await this.fetchCouponList(1)
+                await this.fetchCouponList(2)
+                await this.fetchCouponList(3)
+                this.isRequest = false
+            } catch (e) {
+                //TODO handle the exception
+                console.log(e)
+            }
+        },
+        // 获取优惠券
+        fetchCouponList(status) {
+            let query = null
+            if (status) {
+                query = this.couponData[status - 1]
+            } else {
+                query = this.couponData[this.currentTab]
+            }
+            // 查询参数
+            const listQuery = {
+                userId: this.userId,
+                pageSize: this.pageSize,
+                pageNum: query.pageNum,
+                status: status || query.status
+            }
+            this.loadmore = true
+            return this.CouponService.CouponReceiveList(listQuery).then(res => {
+                query.hasNextPage = res.data.hasNextPage
+                query.total = res.data.total
+                query.couponList = [...query.couponList, ...res.data.list]
+                query.pageNum++
+                this.loadmore = false
+            })
+        },
+        // tab切换
         tabChange(e) {
             this.currentTab = e.index
+            if (this.queryInfo.pageNum === 1) this.fetchCouponList()
         },
-        swiperChange(e){
+        // 轮播图切换
+        swiperChange(e) {
             this.currentTab = e.detail.current
+            if (this.queryInfo.pageNum === 1) this.fetchCouponList()
         },
         // 获取可用屏幕高度
-        getWindowHeight(){
+        getWindowHeight() {
             this.windowHeight = uni.getSystemInfoSync().windowHeight
             console.log(this.windowHeight)
+        },
+        // 加载更多
+        scorllBottom() {
+            if (!this.queryInfo.hasNextPage) return
+            clearTimeout(this.timer)
+            this.timer = setTimeout(() => {
+                console.log('触底了')
+                this.fetchCouponList()
+            }, 200)
         }
     }
 }
 </script>
 
 <style lang="scss" scoped>
-page{
+page {
     width: 100%;
     height: 100%;
     background: #f7f7f7;
@@ -96,9 +219,12 @@ page{
 .swiper {
     height: 800rpx;
     background: #f7f7f7;
-    .coupon-list{
+    .coupon-list {
         height: 100%;
         overflow-y: scroll;
+        .coupon-scorll {
+            height: 100%;
+        }
     }
 }
 .footer {

+ 7 - 3
pages/user/address/addressManage.vue

@@ -70,8 +70,9 @@
 
 <script>
 import CityPicker from '@/components/mpvue-citypicker/mpvueCityPicker.vue'
+import { mapGetters } from 'vuex'
 export default {
-    components:{
+    components: {
         CityPicker
     },
     data() {
@@ -94,6 +95,9 @@ export default {
             params: {} //参数
         }
     },
+    computed: {
+        ...mapGetters(['userId'])
+    },
     onLoad(option) {
         let title = '添加新地址'
         if (option.type === 'edit') {
@@ -106,7 +110,7 @@ export default {
             this.addressData.allAddress = `${optionData.provinceName}-${optionData.cityName}-${optionData.townName}`
             this.addressData.address = optionData.address
             this.addressData.defaultFlag = optionData.defaultFlag
-            this.addressData.userId = optionData.userId
+            this.addressData.userId = this.userId
             this.addressData.mobile = optionData.mobile
             this.addressData.townId = optionData.townId
             this.addressData.addressId = optionData.addressId
@@ -156,7 +160,7 @@ export default {
             if (this.addType == 1) {
                 this.params = {
                     // 测试id
-                    userId: this.addressData.userId, //用户id ,只在新增收货地址时传
+                    userId: this.userId, //用户id ,只在新增收货地址时传
                     shouHuoRen: this.addressData.shouHuoRen, //收货人
                     townId: this.addressData.townId, //区ID
                     address: this.addressData.address, //地址

+ 140 - 50
pages/user/order/create-order.vue

@@ -10,14 +10,25 @@
             @handleGoodList="handChangeInputGoodsList"
         ></goodsList>
         <!-- 选择优惠券 TODO-->
-        <view class="select-coupon" @click="couponVisible = true">
+        <view class="select-coupon" @click="couponVisible = true" v-if="receiveCouponList.length > 0">
             <view class="left-title">优惠券</view>
             <view class="right-content">
-                <view class="coupon-amount">-¥20.00</view> <view class="iconfont icon-chakangengduo"></view>
+                <view class="coupon-amount">-¥{{ couponAmount | NumFormat }}</view>
+                <view class="iconfont icon-chakangengduo"></view>
             </view>
         </view>
         <!-- 优惠券列表 TODO-->
-        <cm-coupon-list title="优惠券" listType="use" :visible="couponVisible" @close="closeCouponList"></cm-coupon-list>
+        <cm-coupon-list
+            title="优惠券"
+            listType="use"
+            :visible="couponVisible"
+            @close="closeCouponList"
+            :chooseAble="true"
+            :showStatus="false"
+            :couponList="receiveCouponList"
+            @chooseCoupon="chooseCoupon"
+            :currentId="currentCouponId"
+        ></cm-coupon-list>
         <!-- 运费 -->
         <seller-freight ref="freight" v-if="isRequest" :freightDatas="freightData"> </seller-freight>
         <!-- 底部 -->
@@ -27,9 +38,10 @@
                     <text>共{{ allCount }}件商品</text>
                 </view>
                 <view class="footer-price">
-                    <view class="sum" :class="totalFullReduction == 0 ? 'none' : ''"
-                        >总价:<text class="price">¥{{ payAllPrice | NumFormat }}</text></view
-                    >
+                    <view class="sum" :class="totalFullReduction == 0 ? 'none' : ''">
+                        <view class="price">总价:¥{{ payAllPrice | NumFormat }}</view>
+                        <view class="discount">共减 ¥{{ discountedPrice | NumFormat }}</view>
+                    </view>
                 </view>
             </view>
             <view class="footer-submit" @click.stop="orderSubmitMit">
@@ -45,6 +57,7 @@ import choiceAddress from '@/components/cm-module/createOrder/address'
 import goodsList from '@/components/cm-module/createOrder/goodsList'
 import sellerFreight from '@/components/cm-module/createOrder/sellerFreight'
 import CmCouponList from '@/components/cm-module/cm-coupon-list/cm-coupon-list'
+import { mapGetters } from 'vuex'
 export default {
     components: {
         choiceAddress,
@@ -61,7 +74,6 @@ export default {
             allCount: 1, //订单提交总数量
             totalOriginalPrice: 0, //订单总原价(划线部分)
             totalFullReduction: 0, //满减金额
-            payAllPrice: 0.0, //订单提交总金额
             allPrice: 0.0, //订单总金额
             townId: '', //区ID
             isRequest: false, //是否加载完成渲染子组件
@@ -85,27 +97,45 @@ export default {
                     orderShouldPayFee: 0
                 }
             },
-            orderInfo: ''
+            orderInfo: '',
+            receiveCouponList: [],
+            currentCouponId: -1,
+            currentCoupon: null
         }
     },
     onLoad(option) {
         //商品数据
         let data = JSON.parse(option.data)
         this.allCount = data.data.allCount
-        console.log(data)
         if (option.type == 'prodcut') {
             this.subParams.cartType = 2
             this.params.productCount = data.data.productCount
             this.params.productId = data.data.productId
             this.params.heUserId = data.data.heUserId ? data.data.heUserId : 0
+            this.productIds = data.data.productId.toString()
         } else {
             this.subParams.cartType = 1
             this.params.cartIds = data.data.cartIds
+            this.productIds = data.data.productIds
+        }
+        this.params.userId = this.userId
+        this.subParams.userId = this.userId
+        this.getInitCrearOrder(this.params)
+    },
+    computed: {
+        ...mapGetters(['userId']),
+        // 选中的优惠券的金额
+        couponAmount() {
+            return this.currentCoupon ? this.currentCoupon.couponAmount : 0
+        },
+        // 优惠价格
+        discountedPrice() {
+            return this.couponAmount
+        },
+        // 支付金额
+        payAllPrice() {
+            return this.allPrice - this.couponAmount
         }
-        this.$api.getStorage().then(resolve => {
-            this.params.userId = this.subParams.userId = resolve.userId ? resolve.userId : 0
-            this.getInitCrearOrder(this.params)
-        })
     },
     filters: {
         NumFormat(value) {
@@ -114,44 +144,96 @@ export default {
         }
     },
     methods: {
-        closeCouponList(){
+        closeCouponList() {
+            this.couponVisible = false
+        },
+        // 获取可用优惠券
+        fetchCouponList() {
+            this.CouponService.GetCouponByProductIds({ userId: this.userId, productIds: this.productIds }).then(res => {
+                this.receiveCouponList = res.data.receiveCouponList
+                this.filterCouponList()
+            })
+        },
+        // 对优惠券进行分类排序
+        filterCouponList() {
+            const productList = []
+            this.goodsData.forEach(shop => productList.push(...shop.productList.map(prod => prod)))
+            let canUseCouponList = []
+            let notUseCouponList = []
+            this.list = this.receiveCouponList.forEach(coupon => {
+                if (
+                    coupon.noThresholdFlag === 1 ||
+                    (coupon.productType === 1 && this.allProdoceUseCheck(productList, coupon)) ||
+                    (coupon.productType === 2 && this.someProductUseCheck(productList, coupon))
+                ) {
+                    coupon.canSelect = true
+                    canUseCouponList.push(coupon)
+                } else {
+                    coupon.canSelect = false
+                    notUseCouponList.push(coupon)
+                }
+            })
+            // 金额高的拍前面
+            canUseCouponList = canUseCouponList.sort((a, b) => b.couponAmount - a.couponAmount)
+            notUseCouponList = notUseCouponList.sort((a, b) => b.couponAmount - a.couponAmount)
+            this.receiveCouponList = [...canUseCouponList, ...notUseCouponList]
+            // 当有可用优惠券时 默认选取第一个最优惠的
+            if (this.receiveCouponList.length > 0) {
+                this.currentCouponId = this.receiveCouponList[0].couponId
+                this.currentCoupon = this.receiveCouponList[0]
+            }
+        },
+        // 判断全部商品可用 是否可勾选使用
+        allProdoceUseCheck(productList, coupon) {
+            return productList.some(prod => prod.price * prod.productCount >= coupon.couponAmount)
+        },
+        // 判断指定商品可用 是否可勾选使用
+        someProductUseCheck(productList, coupon) {
+            return productList.some(
+                prod =>
+                    coupon.productIds.indexOf(prod.productId.toString()) > -1 &&
+                    prod.price * prod.productCount >= coupon.couponAmount
+            )
+        },
+        // 选中优惠券
+        chooseCoupon(coupon) {
+            if (coupon.couponId > -1) {
+                this.currentCoupon = coupon
+                this.currentCouponId = coupon.couponId
+            } else {
+                this.currentCoupon = null
+                this.currentCouponId = -1
+            }
             this.couponVisible = false
+            console.log(coupon)
         },
+        //确认订单初始化信息
         getInitCrearOrder(params) {
-            //确认订单初始化信息
             this.OrderService.QueryOrderConfirm(params)
                 .then(response => {
                     let data = response.data
-                    let productIds = []
                     this.isRequest = true
                     this.goodsData = data.shopList
-                    console.log(this.goodsData)
-                    // this.totalFullReduction = data.totalFullReduction
-                    // this.totalOriginalPrice = data.totalFullReduction + data.totalPrice
-                    this.allPrice = this.payAllPrice = data.totalPrice
-                    this.subParams.payInfo.orderShouldPayFee = this.payAllPrice.toFixed(2)
-                    console.log('this.subParams.payInfo.orderShouldPayFee', this.subParams.payInfo.orderShouldPayFee)
+                    this.allPrice = data.totalPrice
+                    
+                    this.fetchCouponList()
                 })
                 .catch(error => {
                     this.$util.msg(error.msg, 2000)
                 })
         },
+        //获取地址信息
         getAddressData() {
-            //获取地址信息
-            this.$api.getStorage().then(resolve => {
-                this.UserService.QueryAddressList({ pageNum: 1, pageSize: 1, userId: resolve.userId }).then(
-                    response => {
-                        this.isAddress = true
-                        this.addressData = {}
-                        if (response.data.list != '') {
-                            this.subParams.addressId = response.data.list[0].addressId
-                            this.townId = response.data.list[0].townId
-                            this.addressData = response.data.list[0]
-                        } else {
-                            this.addressData = this.addressData
-                        }
-                    }
-                )
+            this.UserService.QueryAddressList({ pageNum: 1, pageSize: 1, userId: this.userId }).then(response => {
+                this.isAddress = true
+                this.addressData = {}
+                if (response.data.list != '') {
+                    this.subParams.addressId = response.data.list[0].addressId
+                    this.townId = response.data.list[0].townId
+                    this.addressData = response.data.list[0]
+                } else {
+                    this.addressData = this.addressData
+                }
             })
         },
         handChangeInputGoodsList(data) {
@@ -160,13 +242,11 @@ export default {
         },
         orderSubmitMit() {
             //提交订单
-            if (this.isSubLoading) {
-                return
-            }
-            if (this.subParams.addressId == '') {
-                this.$util.msg('请先添加收货地址~', 2000)
-                return
-            }
+            if (this.isSubLoading) return
+            if (this.subParams.addressId == '') return this.$util.msg('请先添加收货地址~', 2000)
+            // 选中的优惠券id
+            this.subParams.couponId = this.currentCouponId === -1 ? '' : this.currentCouponId
+            this.subParams.payInfo.orderShouldPayFee = this.payAllPrice
             // 处理商品信息及留言
             this.subParams.orderInfo = this.goodsData.map(el => {
                 let productInfo = []
@@ -179,7 +259,7 @@ export default {
                 })
                 return { shopId: el.shopId, note: el.note ? el.note : '', productInfo: productInfo }
             })
-            console.log(this.subParams)
+            debugger
             this.isSubLoading = true
             this.OrderService.CreatedOrderSubmit(this.subParams)
                 .then(response => {
@@ -231,8 +311,6 @@ export default {
                     wx.reLaunch({ url: '/pages/tabBar/index/index' })
                 },
                 fail: function(res) {
-                    console.log(res)
-                    console.log('ORDERID', self.orderInfo)
                     self.$api.redirectTo(`/pages/user/order/success?data=${JSON.stringify({ data: self.orderInfo })}`)
                 },
                 complete: function(res) {}
@@ -259,6 +337,9 @@ page {
     height: auto;
     background: #f7f7f7;
 }
+.container {
+    height: initial;
+}
 .btn-hover {
     background: #ffffff;
 }
@@ -398,12 +479,12 @@ page {
     align-items: center;
     width: 100%;
     height: 110rpx;
-    line-height: 110rpx;
     justify-content: space-between;
     font-size: $font-size-28;
     background-color: #ffffff;
     z-index: 998;
     color: $text-color;
+    border-top: 1px solid #f7f7f7;
     .footer-le {
         width: 570rpx;
         height: 100%;
@@ -412,6 +493,7 @@ page {
     .footer-count {
         float: left;
         padding-left: 24rpx;
+        line-height: 110rpx;
         width: 170rpx;
         box-sizing: border-box;
         font-size: $font-size-26;
@@ -423,15 +505,23 @@ page {
         padding-right: 20rpx;
         box-sizing: border-box;
         width: 370rpx;
+        padding-left: 24rpx;
         .sum {
+            display: flex;
+            justify-content: center;
+            flex-direction: column;
+            align-items: flex-start;
             width: 100%;
             height: 110rpx;
-            line-height: 110rpx;
-            float: left;
             .price {
                 font-size: $font-size-32;
                 color: $color-system;
             }
+            .discount {
+                // margin-top: 32rpx;
+                font-size: $font-size-24;
+                color: #ff457b;
+            }
         }
     }
     .footer-submit {

+ 69 - 87
pages/user/order/order-list-retail.vue

@@ -1,5 +1,6 @@
 <template>
     <view class="container" :style="{ paddingTop: navbarHeight + 82 + 'px' }">
+        <tui-skeleton v-if="skeletonShow" loadingType="2"></tui-skeleton>
         <!-- 自定义返回 -->
         <header-order
             :systeminfo="systeminfo"
@@ -43,20 +44,13 @@
             :style="{ height: winHeight + 'px' }"
         >
             <swiper-item v-for="(tabItem, index) in orderTabBar" :key="index">
-                <tui-skeleton
-                    v-if="skeletonShow"
-                    backgroundColor="#fafafa"
-                    borderRadius="10rpx"
-                    :isLoading="false"
-                    :loadingType="5"
-                ></tui-skeleton>
                 <scroll-view
                     scroll-y
-                    class="scoll-y tui-skeleton"
+                    class="scoll-y"
                     @scrolltolower="scrolltolower"
                     :style="{ height: winHeight + 'px' }"
                 >
-                    <view :class="{ 'tui-order-list': scrollTop >= 0 }" class="tui-skeleton clearfix">
+                    <view :class="{ 'tui-order-list': scrollTop >= 0 }" class="clearfix">
                         <!-- 空白页 -->
                         <empty
                             v-if="tabItem.loaded === true && tabItem.orderList.length === 0"
@@ -72,23 +66,21 @@
                             >
                                 <view class="order-title">
                                     <view class="order-title-t">
-                                        <text class="bage-text tui-skeleton-fillet"
+                                        <text class="bage-text"
                                             ><text class="text">订单编号:</text>{{ order.orderNo }}</text
                                         >
                                     </view>
                                     <view class="order-title-b">
-                                        <view class="order-title-btxt tui-skeleton-fillet"
+                                        <view class="order-title-btxt"
                                             ><text class="text">下单时间:</text>{{ order.orderTime }}</view
                                         >
-                                        <view class="order-title-tip tui-skeleton-fillet">{{
-                                            StateExpFormat(order.status)
-                                        }}</view>
+                                        <view class="order-title-tip">{{ StateExpFormat(order.status) }}</view>
                                     </view>
                                 </view>
                                 <block v-for="(shop, sindex) in order.shopOrderList" :key="sindex">
                                     <view class="goods-title">
                                         <view class="title-logo"><image :src="shop.shopLogo" mode=""></image></view>
-                                        <view class="title-text tui-skeleton-fillet">{{ shop.shopName }}</view>
+                                        <view class="title-text">{{ shop.shopName }}</view>
                                     </view>
                                     <view
                                         class="goods-item"
@@ -97,14 +89,10 @@
                                         @click.stop="detail(order.orderId)"
                                     >
                                         <view class="goods-pros-t">
-                                            <view class="pros-img tui-skeleton-fillet">
-                                                <image :src="pros.productImage" alt="" />
-                                            </view>
+                                            <view class="pros-img"> <image :src="pros.productImage" alt="" /> </view>
                                             <view class="pros-product clearfix">
-                                                <view class="producttitle tui-skeleton-fillet">{{ pros.name }}</view>
-                                                <view
-                                                    class="productspec tui-skeleton-fillet"
-                                                    v-if="pros.productCategory != 2"
+                                                <view class="producttitle">{{ pros.name }}</view>
+                                                <view class="productspec" v-if="pros.productCategory != 2"
                                                     >规格:{{ pros.productUnit }}</view
                                                 >
                                                 <view class="floor-item-act" v-if="pros.ladderPriceFlag === '1'">
@@ -115,10 +103,10 @@
                                                     >
                                                 </view>
                                                 <view class="productprice">
-                                                    <view class="price tui-skeleton-fillet"
+                                                    <view class="price"
                                                         ><text>¥{{ pros.price | NumFormat }}</text></view
                                                     >
-                                                    <view class="count tui-skeleton-fillet"
+                                                    <view class="count"
                                                         ><text class="small">x</text>{{ pros.num }}</view
                                                     >
                                                 </view>
@@ -128,14 +116,14 @@
                                 </block>
                                 <view class="order-footer">
                                     <view class="order-footer-bot">
-                                        <view class="count tui-skeleton-fillet">共{{ order.productCount }}件商品</view>
+                                        <view class="count">共{{ order.productCount }}件商品</view>
                                         <view
-                                            class="money tui-skeleton-fillet"
+                                            class="money"
                                             v-if="order.status == 31 || order.status == 32 || order.status == 33"
                                         >
                                             已支付:<text class="color">¥{{ order.receiptAmount | NumFormat }}</text>
                                         </view>
-                                        <view class="money tui-skeleton-fillet" v-else>
+                                        <view class="money" v-else>
                                             待付总额:<text class="color"
                                                 >¥{{ order.pendingPayments | NumFormat }}</text
                                             >
@@ -143,7 +131,6 @@
                                     </view>
                                 </view>
                                 <!-- 底部button -->
-
                                 <order-button
                                     v-if="order.userId == userId"
                                     ref="orderButton"
@@ -157,7 +144,7 @@
                             <tui-loadmore :visible="loadding" :index="3" type="black"></tui-loadmore>
                             <tui-nomore
                                 :visible="!pullUpOn"
-                                :backgroundColor="'#F7F7F7'"
+                                :backgroundColor="'#ffffff'"
                                 :text="nomoreText"
                             ></tui-nomore>
                             <!--加载loadding-->
@@ -215,6 +202,7 @@ import HeaderOrder from '@/components/cm-module/headerNavbar/header-order' //自
 import orderButton from '@/components/cm-module/orderDetails/orderListButton' //按钮
 import modalLayer from '@/components/cm-module/modal-layer/modal-layer'
 import empty from '@/components/cm-module/empty/empty'
+import { mapGetters } from 'vuex'
 
 export default {
     components: {
@@ -246,7 +234,6 @@ export default {
             currentTab: 0, //预设当前项的值
             screenTab: 0, //筛选预设当前项的值
             scrollLeft: 0, //tab标题的滚动条位置
-            userId: 0,
             orderData: [],
             btnoRderID: 0, //点击按钮传入的的订单ID
             pageNum: 1, //页数
@@ -281,6 +268,18 @@ export default {
             invalidList: []
         }
     },
+    computed: {
+        ...mapGetters(['userId'])
+    },
+    filters: {
+        NumFormat(value) {
+            //处理金额
+            return Number(value).toFixed(2)
+        }
+    },
+    onPageScroll(e) {
+        this.scrollTop = e.scrollTop
+    },
     onLoad(e) {
         let self = this
         if (e.type === 'detele') {
@@ -297,11 +296,10 @@ export default {
             }
         })
     },
-    filters: {
-        NumFormat(value) {
-            //处理金额
-            return Number(value).toFixed(2)
-        }
+    onShow() {
+        this.isModalLayer = false
+        this.GetOrderDatainit(this.currentTab)
+        // console.log(this.orderTabBar)
     },
     methods: {
         goShophome(id) {
@@ -366,58 +364,50 @@ export default {
              * @param:pageSize(每页条数)
              * @param:organizeID(全局变量组织ID)
              */
-
-            setTimeout(() => {
-                this.skeletonShow = false
-                this.isOnloadFlag = false
-            }, 1500)
             let orderItem = this.orderTabBar[index]
             let state = orderItem.state
             if (source === 'tabChange' && orderItem.loaded === true) {
                 //tab切换只有第一次需要加载数据
                 return
             }
-            setTimeout(() => {
-                this.$api.getStorage().then(resolve => {
-                    this.userId = resolve.userId
-                    this.OrderService.QueryOrderDealerList({
-                        orderState: index,
-                        orderType: this.screenTab,
-                        userId: resolve.userId,
-                        pageNum: 1,
-                        pageSize: this.pageSize
+            this.OrderService.QueryOrderDealerList({
+                orderState: index,
+                orderType: this.screenTab,
+                userId: this.userId,
+                pageNum: 1,
+                pageSize: this.pageSize
+            })
+                .then(response => {
+                    let data = response.data
+                    //loaded新字段用于表示数据加载完毕,如果为空可以显示空白页
+                    let orderList = data.list.filter(item => {
+                        //添加不同状态下订单的表现形式
+                        item = Object.assign(item, this.StateExpFormat(item.state))
+                        return item
                     })
-                        .then(response => {
-                            let data = response.data
-                            //loaded新字段用于表示数据加载完毕,如果为空可以显示空白页
-                            let orderList = data.list.filter(item => {
-                                //添加不同状态下订单的表现形式
-                                item = Object.assign(item, this.StateExpFormat(item.state))
-                                return item
-                            })
-                            orderItem.orderList = []
-                            orderList.forEach(item => {
-                                orderItem.orderList.push(item)
-                            })
-                            this.$set(orderItem, 'loaded', true)
-                            this.hasNextPage = data.hasNextPage
-                            if (this.hasNextPage) {
-                                this.pullUpOn = false
-                                this.nomoreText = '上拉显示更多'
-                            } else {
-                                if (orderItem.orderList.length < 2) {
-                                    this.pullUpOn = true
-                                } else {
-                                    this.pullUpOn = false
-                                    this.nomoreText = '已至底部'
-                                }
-                            }
-                        })
-                        .catch(error => {
-                            this.$util.msg(error.msg, 2000)
-                        })
+                    orderItem.orderList = []
+                    orderList.forEach(item => {
+                        orderItem.orderList.push(item)
+                    })
+                    this.$set(orderItem, 'loaded', true)
+                    this.hasNextPage = data.hasNextPage
+                    if (this.hasNextPage) {
+                        this.pullUpOn = false
+                        this.nomoreText = '上拉显示更多'
+                    } else {
+                        if (orderItem.orderList.length < 2) {
+                            this.pullUpOn = true
+                        } else {
+                            this.pullUpOn = false
+                            this.nomoreText = '已至底部'
+                        }
+                    }
+                    this.skeletonShow = false
+                    this.isOnloadFlag = false
+                })
+                .catch(error => {
+                    this.$util.msg(error.msg, 2000)
                 })
-            }, 600)
         },
         getOnReachBottomData(index) {
             //上拉加载
@@ -732,14 +722,6 @@ export default {
             })
             return HtmlStateText
         }
-    },
-    onPageScroll(e) {
-        this.scrollTop = e.scrollTop
-    },
-    onShow() {
-        this.isModalLayer = false
-        this.GetOrderDatainit(this.currentTab)
-        // console.log(this.orderTabBar)
     }
 }
 </script>

+ 30 - 30
pages/user/order/order-list.vue

@@ -1,5 +1,12 @@
 <template>
     <view class="container" :style="{ paddingTop: navbarHeight + 'px' }">
+        <tui-skeleton
+            v-if="skeletonShow"
+            backgroundColor="#fafafa"
+            borderRadius="10rpx"
+            :isLoading="false"
+            :loadingType="2"
+        ></tui-skeleton>
         <!-- 自定义返回 -->
         <header-order
             :systeminfo="systeminfo"
@@ -30,15 +37,9 @@
             :style="{ height: winHeight + 'px' }"
         >
             <swiper-item v-for="(tabItem, index) in orderTabBar" :key="index">
-                <tui-skeleton
-                    v-if="skeletonShow"
-                    backgroundColor="#fafafa"
-                    borderRadius="10rpx"
-                    :isLoading="false"
-                    :loadingType="5"
-                ></tui-skeleton>
-                <scroll-view scroll-y class="scoll-y tui-skeleton" @scrolltolower="scrolltolower">
-                    <view :class="{ 'tui-order-list': scrollTop >= 0 }" class="tui-skeleton clearfix">
+                
+                <scroll-view scroll-y class="scoll-y" @scrolltolower="scrolltolower">
+                    <view :class="{ 'tui-order-list': scrollTop >= 0 }" class="clearfix">
                         <!-- 空白页 -->
                         <empty
                             v-if="tabItem.loaded === true && tabItem.orderList.length === 0"
@@ -54,15 +55,15 @@
                             >
                                 <view class="order-title">
                                     <view class="order-title-t">
-                                        <text class="bage-text tui-skeleton-fillet"
+                                        <text class="bage-text"
                                             ><text class="text">订单编号:</text>{{ order.orderNo }}</text
                                         >
                                     </view>
                                     <view class="order-title-b">
-                                        <view class="order-title-btxt tui-skeleton-fillet"
+                                        <view class="order-title-btxt"
                                             ><text class="text">下单时间:</text>{{ order.orderTime }}</view
                                         >
-                                        <view class="order-title-tip tui-skeleton-fillet">{{
+                                        <view class="order-title-tip">{{
                                             StateExpFormat(order.status)
                                         }}</view>
                                     </view>
@@ -70,7 +71,7 @@
                                 <block v-for="(shop, sindex) in order.shopOrderList" :key="sindex">
                                     <view class="goods-title">
                                         <view class="title-logo"><image :src="shop.shopLogo" mode=""></image></view>
-                                        <view class="title-text tui-skeleton-fillet">{{ shop.shopName }}</view>
+                                        <view class="title-text">{{ shop.shopName }}</view>
                                     </view>
                                     <view
                                         class="goods-item"
@@ -79,13 +80,13 @@
                                         @click.stop="detail(order.orderId)"
                                     >
                                         <view class="goods-pros-t">
-                                            <view class="pros-img tui-skeleton-fillet">
+                                            <view class="pros-img">
                                                 <image :src="pros.productImage" alt="" />
                                             </view>
                                             <view class="pros-product clearfix">
-                                                <view class="producttitle tui-skeleton-fillet">{{ pros.name }}</view>
+                                                <view class="producttitle">{{ pros.name }}</view>
                                                 <view
-                                                    class="productspec tui-skeleton-fillet"
+                                                    class="productspec"
                                                     v-if="pros.productCategory != 2"
                                                     >规格:{{ pros.productUnit }}</view
                                                 >
@@ -95,10 +96,10 @@
                                                     >
                                                 </view>
                                                 <view class="productprice">
-                                                    <view class="price tui-skeleton-fillet"
+                                                    <view class="price"
                                                         ><text>¥{{ pros.price | NumFormat }}</text></view
                                                     >
-                                                    <view class="count tui-skeleton-fillet"
+                                                    <view class="count"
                                                         ><text class="small">x</text>{{ pros.num }}</view
                                                     >
                                                 </view>
@@ -108,14 +109,14 @@
                                 </block>
                                 <view class="order-footer">
                                     <view class="order-footer-bot">
-                                        <view class="count tui-skeleton-fillet">共{{ order.productCount }}件商品</view>
+                                        <view class="count">共{{ order.productCount }}件商品</view>
                                         <view
-                                            class="money tui-skeleton-fillet"
+                                            class="money"
                                             v-if="order.status == 31 || order.status == 32 || order.status == 33"
                                         >
                                             已支付:<text class="color">¥{{ order.receiptAmount | NumFormat }}</text>
                                         </view>
-                                        <view class="money tui-skeleton-fillet" v-else>
+                                        <view class="money" v-else>
                                             待付总额:<text class="color"
                                                 >¥{{ order.pendingPayments | NumFormat }}</text
                                             >
@@ -279,6 +280,14 @@ export default {
             return Number(value).toFixed(2)
         }
     },
+    onPageScroll(e) {
+        this.scrollTop = e.scrollTop
+    },
+    onShow() {
+        this.isModalLayer = false
+        this.GetOrderDatainit(this.currentTab)
+        // console.log(this.orderTabBar)
+    },
     methods: {
         // 滚动切换标签样式
         onChange: function(e) {
@@ -331,7 +340,6 @@ export default {
              * @param:pageSize(每页条数)
              * @param:organizeID(全局变量组织ID)
              */
-
             setTimeout(() => {
                 this.skeletonShow = false
                 this.isOnloadFlag = false
@@ -695,14 +703,6 @@ export default {
             })
             return HtmlStateText
         }
-    },
-    onPageScroll(e) {
-        this.scrollTop = e.scrollTop
-    },
-    onShow() {
-        this.isModalLayer = false
-        this.GetOrderDatainit(this.currentTab)
-        // console.log(this.orderTabBar)
     }
 }
 </script>

+ 16 - 0
services/coupon.service.js

@@ -55,4 +55,20 @@ export default class CouponService {
             isLoading: false,
         })
     }
+    // 商品详情优惠券
+    GetCouponByProduct(data = {}) {
+        return this.AjaxService.get({
+            url: '/coupon/product/detail',
+            data,
+            isLoading: false,
+        })
+    }
+    // 根据商品id列表获取优惠券
+    GetCouponByProductIds(data = {}) {
+        return this.AjaxService.get({
+            url: '/coupon/productIds',
+            data,
+            isLoading: false,
+        })
+    }
 }

+ 6 - 1
store/getters.js

@@ -10,14 +10,19 @@ const getters = {
     userId: state => state.user.userId,
     userIdentity: state => state.user.userIdentity,
     hasLogin: state => state.user.hasLogin,
+    inviteUserId: state => state.user.inviteUserId,
     // 购物车
     kindCount: state => state.cart.kindCount,
     failureList: state => state.cart.failureList,
     goodsList: state => state.cart.goodsList,
     isEmpty: state => state.cart.isEmpty,
     cartIds: state => state.cart.cartIds,
+    productIds: state => state.cart.productIds,
     // 优惠券
-    activePopupType: state=>state.coupon.activePopupType
+    activePopupType: state => state.coupon.activePopupType,
+    expiredNum: state => state.coupon.expiredNum,
+    unusedNum: state => state.coupon.unusedNum,
+    usedNum: state => state.coupon.usedNum
 }
 
 export default getters

+ 5 - 1
store/modules/cart.js

@@ -49,6 +49,7 @@ const state = {
     goodsList: [], //购物车的商品
     failureList: [], //失效商品列表
     cartIds: [], // 已勾选商品cartId列表
+    productIds: [],
     kindCount: 0,
 }
 
@@ -72,6 +73,9 @@ const mutations = {
     saveCartIds(state, ids) {
         state.cartIds = ids
     },
+    saveProductIds(state, ids){
+        state.productIds = ids
+    },
     // 勾选/不勾选 失效商品
     selectFailure(state, { productId, checked }) {
         state.failureList.forEach(prod => {
@@ -221,7 +225,7 @@ const actions = {
     },
     // 加减购物车商品更新到后台
     updateShoppogCount({ dispatch, state }, { cartId, productCount }) {
-        productService.ShoppingCartUpdate({
+        return productService.ShoppingCartUpdate({
             cartId,
             productCount
         }).finally(() => {

+ 18 - 19
store/modules/coupon.js

@@ -6,27 +6,21 @@ import { msg as showMsg } from '@/common/util.js'
 
 const state = {
     showCouponPopup: true, // 是否显示优惠券入口弹窗
-    activeCouponList: [], // 未使用
-    expiredCouponList: [], // 已过期
-    usedCouponList: [], // 已使用
-    activePopupType: 0 // 0 禁用 1 老用户 2 新用户
+    activePopupType: 0, // 0 禁用 1 老用户 2 新用户
+    expiredNum: 0,
+    unusedNum: 0,
+    usedNum: 0
 }
 const mutations = {
-    // 更新未使用优惠券
-    updateActive(state, list) {
-        state.activeCouponList = list
-    },
-    // 更新已过期优惠券
-    updateExpired(state, list) {
-        state.expiredCouponList = list
-    },
-    // 更新已使用优惠券
-    updateUsed(state, list) {
-        state.usedCouponList = list
+    // 设置已领取优惠券数量
+    setReceiveCouponCount(state, data) {
+        state.unusedNum = data.unusedNum
+        state.usedNum = data.usedNum
+        state.expiredNum = data.expiredNum
     },
     // 更新弹窗类型
     updatePopupType(state, type) {
-        state.activePopupType = type
+        state.activePopupType = type <= 0 ? 0 : type
     },
     // 设置优惠券弹窗是否显示
     setCouponPopupStatus(state, status) {
@@ -34,16 +28,21 @@ const mutations = {
     }
 }
 const actions = {
-    // 查询已领取优惠券
-    fetchCouponList() {},
     // 领取优惠券
-    receiveCoupon({ rootGetters }, couponId) {
+    receiveCoupon({ rootGetters, dispatch }, couponId) {
         return couponService.ReceiveCoupon({ couponId, userId: rootGetters.userId }).then(res => {
+            dispatch('initReceiveCouponCount')
             showMsg('领取成功', 1500, false, 'success')
         }).catch(error => {
             showMsg(error.msg, 2000)
         })
     },
+    // 初始化已领取优惠券数量
+    initReceiveCouponCount({ commit, rootGetters }) {
+        couponService.CouponReceiveCount({ userId: rootGetters.userId }).then(res => {
+            commit('setReceiveCouponCount', res.data)
+        })
+    },
     // 优惠券活动弹窗信息
     getCouponActivity({ commit, rootGetters, state }) {
         if (!state.showCouponPopup) return

+ 9 - 1
store/modules/user.js

@@ -9,6 +9,7 @@ const state = {
     userInfo: null,
     hasLogin: false,
     isWxAuthorize: false,
+    inviteUserId: '',
 }
 const mutations = {
     // 用户登录
@@ -31,6 +32,10 @@ const mutations = {
         state.userIdentity = ''
         userInfo && uni.setStorageSync('openId', userInfo.openId)
     },
+    // 设置邀请用户id
+    setInviteUserId(state, id){
+        state.inviteUserId = parseInt(id)
+    }
 }
 const actions = {
     // 微信授权登录
@@ -43,21 +48,24 @@ const actions = {
                 commit('LOGIN', response.data)
                 dispatch('cart/getCartNumber', state.userId, { root: true }) // 获取购物车数量信息
                 dispatch('coupon/getCouponActivity', null, { root: true }) // 获取优惠券弹窗信息
+                dispatch('coupon/initReceiveCouponCount', null, { root: true }) // 获取已领取优惠券数量
             })
             .catch(error => {
                 console.log('游客')
                 dispatch('coupon/getCouponActivity', null, { root: true }) // 游客也要获取优惠券弹窗信息
                 commit('LOGIN_OUT', error.data)
             })
-    }, 
+    },
     // 手机号注册登录
     customLogin({ commit, state, dispatch }, params) {
+        params.shareUserId = state.inviteUserId
         userService.UserMobileLogin(params)
             .then(response => {
                 // 保存用户信息
                 commit('LOGIN', response.data)
                 dispatch('cart/getCartNumber', state.userId, { root: true }) // 获取购物车数量信息
                 dispatch('coupon/getCouponActivity', null, { root: true }) // 获取优惠券弹窗信息
+                dispatch('coupon/initReceiveCouponCount', null, { root: true }) // 获取已领取优惠券数量
                 // 登录成功提示
                 showMsg('登录成功', 1500, false, 'success')
                 setTimeout(() => {