This commit is contained in:
2025-10-27 15:55:29 +08:00
commit 6632080b83
513 changed files with 117442 additions and 0 deletions

347
pages/goods/cart.vue Normal file
View File

@@ -0,0 +1,347 @@
<template>
<page-meta :page-style="themeColor"></page-meta>
<view>
<view class="container">
<scroll-view class="scroll-view" :scroll-y="true" :show-scrollbar="false" :refresher-enabled="true" :refresher-triggered="refresherTriggered" @refresherrefresh="onRefresh">
<block v-if="hasData">
<view class="cart-header" v-if="cartData.length">
<view class="num-wrap">{{ cartData[0].cartList.length }}种商品</view>
<view class="cart-action" @click="changeAction">
{{ isAction ? $lang('complete') : $lang('edit') }}
</view>
</view>
<view class="cart-wrap" v-for="(siteItem, siteIndex) in cartData" :key="siteIndex">
<view class="coupon-use-tips" v-if="discount.coupon_info">
<view>
<text class="title color-base-text">优惠券</text>
<text class="desc">领券结算最高可减{{ discount.coupon_info.coupon_money | moneyFormat }}</text>
</view>
<view class="color-base-text" @click="$refs.couponPopup.open()">
点击{{ discount.coupon_info.receive_type == 'wait' ? '领取' : '查看' }}
<text class="iconfont icon-right"></text>
</view>
</view>
<view class="store-wrap" v-if="globalStoreConfig && globalStoreConfig.store_business == 'store' && globalStoreInfo">
<text class="iconfont icon-dianpu"></text>
<text class="name">{{globalStoreInfo.store_name}}</text>
</view>
<block v-for="(item, cartIndex) in siteItem.cartList" :key="cartIndex">
<view class="cart-goods" @touchstart="touchS($event)" @touchend="touchE($event, item)">
<view class="goods-wrap" :class="{ edit: item.edit }">
<view class="iconfont" :class="item.checked ? 'icon-yuan_checked color-base-text' : 'icon-yuan_checkbox'" @click="singleElection(siteIndex, cartIndex)"></view>
<view @click="toGoodsDetail(item)" class="goods-img">
<image :src="$util.img(item.sku_image, { size: 'mid' })" @error="imageError(siteIndex, cartIndex)" mode="aspectFill"/>
</view>
<view class="goods-info">
<view>
<view @click="toGoodsDetail(item)" class="goods-name">{{ item.goods_name }}</view>
<view class="sku-wrap">
<view class="sku">
<view class="goods-spec" v-if="item.sku_spec_format.length" @click="selectSku(item)">
<block v-for="(x, i) in item.sku_spec_format" :key="i">
{{ x.spec_name }}:{{ x.spec_value_name }}
{{ i < item.sku_spec_format.length - 1 ? ';' : '' }}
</block>
</view>
<text class="iconfont icon-unfold" v-if="item.sku_spec_format.length"></text>
</view>
</view>
</view>
<view class="goods-sub-section">
<block v-if="item.promotion_type == 1">
<block v-if="Number(item.member_price) > 0 && Number(item.member_price) < Number(item.discount_price)">
<view class="goods-price ">
<view class="bottom-price price-style large">
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
{{ parseFloat(item.member_price).toFixed(2).split('.')[0] }}
<text class="unit price-style small">.{{ parseFloat(item.member_price).toFixed(2).split('.')[1] }}</text>
<image :src="$util.img('public/uniapp/index/VIP.png')"/>
</view>
</view>
</block>
<block v-else>
<view class="goods-price ">
<view class="bottom-price price-style large">
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
{{ parseFloat(item.discount_price).toFixed(2).split('.')[0] }}
<text class="unit price-style small">.{{ parseFloat(item.discount_price).toFixed(2).split('.')[1] }}</text>
<image :src="$util.img('public/uniapp/index/discount.png')"/>
</view>
</view>
</block>
</block>
<block v-else>
<block v-if="Number(item.member_price) > 0">
<view class="goods-price">
<view class="bottom-price price-style large">
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
{{ parseFloat(item.member_price).toFixed(2).split('.')[0] }}
<text class="unit price-style small">.{{ parseFloat(item.member_price).toFixed(2).split('.')[1] }}</text>
<image :src="$util.img('public/uniapp/index/VIP.png')"/>
</view>
</view>
</block>
<block v-else>
<view class="goods-price">
<view class="bottom-price price-style large">
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
{{ parseFloat(item.price).toFixed(2).split('.')[0] }}
<text class="unit price-style small">.{{ parseFloat(item.price).toFixed(2).split('.')[1] }}</text>
</view>
</view>
</block>
</block>
<uni-number-box :min="item.min_buy > 1 ? item.min_buy : 1"
:max="item.max_buy > 0 && item.max_buy < item.stock ? item.max_buy : item.stock"
size="small" :value="initNum(item)" :index="item.cart_id"
@change="cartNumChange($event, { siteIndex, cartIndex })"
@limit="goodsLimit($event, { siteIndex, cartIndex })" />
</view>
<view class="discount-wrap" v-if="manjian && manjian['sku_' + item.sku_id]">
<text class="discount-tag">满减</text>
<scroll-view scroll-x="true" class="scroll-view">
<block v-for="(mitem, key) in manjian['sku_' + item.sku_id]" :key="key">
<text v-if="mitem.discount_money">{{ Number(mitem.limit) }}{{ mitem.discount_money }}</text>
<text class="interval" v-if="mitem.discount_money"></text>
</block>
</scroll-view>
</view>
</view>
</view>
<view class="item-del color-base-bg" :class="{ show: item.edit }" @click="deleteCart('single', siteIndex, cartIndex)">{{ $lang('del') }}</view>
</view>
</block>
</view>
<view class="cart-wrap invalid" v-if="invalidGoods.length">
<view class="cart-header">
<view class="num-wrap">
<text class="font-size-base">失效商品{{ invalidGoods.length }}</text>
</view>
<view class="cart-action color-base-text" @click="clearInvalidGoods">清空</view>
</view>
<block v-for="(goodsItem, goodsIndex) in invalidGoods" :key="goodsIndex">
<view class="cart-goods invalid-goods">
<view class="goods-wrap">
<view class="iconfont icon-yuan_checked color-tip"></view>
<view class="goods-img">
<image :src="$util.img(goodsItem.sku_image, { size: 'mid' })" mode="aspectFill"/>
</view>
<view class="goods-info">
<view class="goods-name">{{ goodsItem.sku_name }}</view>
<view>
<view class="sku">
<view class="goods-spec" v-if="goodsItem.sku_spec_format.length">
<block v-for="(x, i) in goodsItem.sku_spec_format" :key="i">
{{ x.spec_name }}:{{ x.spec_value_name }}
{{ i < goodsItem.sku_spec_format.length - 1 ? '; ' : '' }}
</block>
</view>
</view>
</view>
<view class="goods-sub-section">
<view class="goods-price">
<text class="bottom-price price-style large">
<template v-if="goodsItem.member_price > 0 && goodsItem.member_price < goodsItem.discount_price">
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
{{ parseFloat(goodsItem.member_price).toFixed(2).split('.')[0] }}
<text class="unit price-style small">.{{ parseFloat(goodsItem.member_price).toFixed(2).split('.')[1] }}</text>
<image :src="$util.img('public/uniapp/index/VIP.png')"/>
</template>
<template v-else>
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
{{ parseFloat(goodsItem.discount_price).toFixed(2).split('.')[0] }}
<text class="unit price-style small">.{{ parseFloat(goodsItem.discount_price).toFixed(2).split('.')[1] }}</text>
</template>
</text>
</view>
<text class="invalid-mark">已失效</text>
</view>
</view>
</view>
</view>
</block>
</view>
</block>
<block v-else>
<view class="cart-empty">
<ns-empty text="购物车为空" subText="赶紧去逛逛, 购买心仪的商品吧" :isIndex="Boolean(storeToken)"></ns-empty>
<button type="primary" size="mini" class="button mini" v-if="!storeToken" @click="toLogin">去登录</button>
</view>
</block>
<ns-goods-recommend ref="goodrecommend" route="cart"></ns-goods-recommend>
<view class="cart-bottom-block"></view>
<!-- 底部tabBar占位 -->
<view class="page-bottom" :style="{ height: tabBarHeight }"></view>
</scroll-view>
<uni-popup ref="discountPopup" custom-class="uni-popup-discount" type="bottom">
<view class="discount-popup popup" v-if="Object.keys(discount).length">
<view class="popup-header">
<text class="tit">优惠明细</text>
<text class="iconfont icon-close" @click="toggleDiscountPopup"></text>
</view>
<view class="popup-body" :class="{ 'safe-area': isIphoneX }" @click="toggleDiscountPopup">
<view class="detail-item">
<view class="title">商品总额</view>
<view class="money price-font">{{ discount.goods_money | moneyFormat }}</view>
</view>
<view class="detail-item" v-if="discount.coupon_money > 0">
<view class="title">优惠券</view>
<view class="money price-font reduce">-{{ discount.coupon_money | moneyFormat }}</view>
</view>
<view class="detail-item" v-if="discount.promotion_money > 0">
<view class="title">满减</view>
<view class="money reduce price-font">-{{ discount.promotion_money | moneyFormat }}
</view>
</view>
<view class="detail-item total">
<view class="title">合计</view>
<view class="money price-font ">{{ discount.order_money | moneyFormat }}</view>
</view>
</view>
<view :style="{height: tabBarHeight}"></view>
</view>
</uni-popup>
<uni-popup ref="couponPopup" custom-class="uni-popup-discount" type="bottom" v-if="discount.coupon_info">
<view class="coupon-popup popup">
<view class="popup-header">
<text class="tit">优惠券</text>
<text class="iconfont icon-close" @click="$refs.couponPopup.close()"></text>
</view>
<view class="popup-body" :class="{ 'safe-area': isIphoneX }" @click="$refs.couponPopup.close()">
<view class="coupon-item">
<view class="coupon-info" :style="{ backgroundColor: discount.coupon_info.receive_type != 'wait' ? '#F2F2F2' : 'var(--main-color-shallow)' }">
<view class="info-wrap">
<image class="coupon-line" mode="heightFix" :src="$util.img('public/uniapp/coupon/coupon_line.png')"/>
<view class="coupon-money">
<template v-if="discount.coupon_info.type == 'reward'">
<text class="unit">{{ $lang('common.currencySymbol') }}</text>
<text class="money">{{ parseFloat(discount.coupon_info.money) }}</text>
</template>
<template v-else-if="discount.coupon_info.type == 'discount'">
<text class="money">{{ parseFloat(discount.coupon_info.discount) }}</text>
<text class="unit"></text>
</template>
<view class="at-least">
<template v-if="discount.coupon_info.at_least > 0">
{{ discount.coupon_info.at_least }}可用
</template>
<template v-else>
无门槛
</template>
</view>
</view>
</view>
<view class="desc-wrap">
<view class="coupon-name">{{ discount.coupon_info.coupon_name }}</view>
<view v-if="discount.coupon_info.type == 'discount' && discount.coupon_info.discount_limit > 0" class="limit">
最多可抵{{ discount.coupon_info.discount_limit }}
</view>
<view class="time font-size-goods-tag" v-if="discount.coupon_info.validity_type == 0">
有效期{{ $util.timeStampTurnTime(discount.coupon_info.end_time) }}
</view>
<view class="time font-size-goods-tag" v-else-if="discount.coupon_info.validity_type == 1">
有效期领取之日起{{ discount.coupon_info.fixed_term }}天内有效
</view>
<view class="time font-size-goods-tag" v-else>有效期长期有效</view>
</view>
<button type="primary" v-if="discount.coupon_info.receive_type != 'wait'" disabled>已领取</button>
<button type="primary" v-else @click.stop="receiveCoupon(discount.coupon_info.coupon_type_id)">领取</button>
</view>
</view>
</view>
<view :style="{height: tabBarHeight}"></view>
<view class="cart-bottom-block"></view>
</view>
</uni-popup>
</view>
<view class="cart-bottom" :style="{ bottom: tabBarHeight }" :class="{ active: isIphoneX }" v-if="hasData">
<view class="all-election" @click="allElection">
<view class="iconfont" :class="checkAll ? 'icon-yuan_checked color-base-text' : 'icon-yuan_checkbox'"></view>
<text>{{ $lang('allElection') }}</text>
</view>
<view class="settlement-info" :style="{ visibility: isAction ? 'hidden' : 'visible' }">
<view class="money">
{{ $lang('total') }}
<text class="unit price-font">{{ $lang('common.currencySymbol') }}</text>
<block v-if="Object.keys(discount).length">
<text class="value price-font">{{ parseFloat(discount.order_money).toFixed(2).split('.')[0] }}</text>
<text class="unit price-font">.{{ parseFloat(discount.order_money).toFixed(2).split('.')[1] }}</text>
</block>
<block v-else>
<text class="value price-font">{{ parseFloat(totalPrice).toFixed(2).split('.')[0] }}</text>
<text class="unit price-font">.{{ parseFloat(totalPrice).toFixed(2).split('.')[1] }}</text>
</block>
</view>
<view class="detail" @click="toggleDiscountPopup" v-if="Object.keys(discount).length">
优惠明细
<text class="iconfont icon-unfold" :class="{ open: !discountPopupShow }"></text>
</view>
</view>
<view class="action-btn" v-if="isAction">
<button type="primary" size="mini" class="mini" @click="deleteCart('all')">{{ $lang('del') }}</button>
</view>
<view class="action-btn" v-else>
<button type="primary" size="mini" class="mini" @click="settlement" v-if="totalCount != 0">
{{ discount.coupon_info && discount.coupon_info.receive_type == 'wait' ? '领券' : '立即' }}结算({{ totalCount }})
</button>
<button type="primary" size="mini" class="mini" @click="settlement" disabled
v-else>{{ $lang('settlement') }}({{ totalCount }})</button>
</view>
</view>
<diy-bottom-nav></diy-bottom-nav>
<ns-goods-sku ref="selectSku" v-if="goodsSkuDetail" :goods-detail="goodsSkuDetail" :goods-id="goodsSkuDetail.goods_id" :max-buy="goodsSkuDetail.max_buy" :min-buy="goodsSkuDetail.min_buy" @refresh="refreshSkuDetail"></ns-goods-sku>
<!-- 加载动画 -->
<loading-cover ref="loadingCover"></loading-cover>
<!-- 返回顶部 -->
<to-top v-if="showTop" @toTop="scrollToTopNative()"></to-top>
<ns-login ref="login"></ns-login>
<!-- #ifdef MP-WEIXIN -->
<!-- 小程序隐私协议 -->
<privacy-popup ref="privacyPopup"></privacy-popup>
<!-- #endif -->
</view>
</template>
<script>
import nsGoodsRecommend from '@/components/ns-goods-recommend/ns-goods-recommend.vue';
import uniNumberBox from '@/components/uni-number-box/uni-number-box.vue';
import toTop from '@/components/toTop/toTop.vue';
import scroll from '@/common/js/scroll-view.js';
import cart from './public/js/cart.js';
export default {
components: {
nsGoodsRecommend,
uniNumberBox,
toTop
},
mixins: [scroll, cart]
};
</script>
<style lang="scss">
/deep/ .uni-popup__wrapper.uni-custom .uni-popup__wrapper-box {
background: none;
max-height: unset !important;
overflow-y: hidden !important;
}
/deep/ .uni-popup__wrapper {
border-radius: 20rpx 20rpx 0 0;
}
@import './public/css/cart.scss';
</style>

113
pages/goods/category.vue Normal file
View File

@@ -0,0 +1,113 @@
<template>
<page-meta :page-style="themeColor"></page-meta>
<view>
<block v-if="diyData">
<block v-for="(item, index) in diyData.value" :key="index">
<view v-if="item.componentName == 'GoodsCategory'">
<diy-category @tologin="toLogin" ref="category" :value="item"></diy-category>
</view>
</block>
</block>
<ns-login ref="login"></ns-login>
<loading-cover ref="loadingCover"></loading-cover>
<!-- #ifdef MP-WEIXIN -->
<!-- 小程序隐私协议 -->
<privacy-popup ref="privacyPopup"></privacy-popup>
<!-- #endif -->
<!-- 底部tabBar -->
<view id="tab-bar">
<diy-bottom-nav></diy-bottom-nav>
</view>
</view>
</template>
<script>
export default {
components: {},
data() {
return {
diyData: null
};
},
onLoad() {
//刷新多语言
this.$langConfig.refresh();
uni.hideTabBar();
this.getDiyInfo();
},
onShow() {
if (this.$refs.category) this.$refs.category[0].pageShow();
},
onUnload() {
if (!this.storeToken && this.$refs.login) this.$refs.login.cancelCompleteInfo();
},
methods: {
getDiyInfo() {
this.$api.sendRequest({
url: '/api/diyview/info',
data: {
name: 'DIY_VIEW_GOODS_CATEGORY'
},
success: res => {
if (res.code == 0 && res.data) {
this.diyData = res.data;
if (this.diyData.value) {
this.diyData = JSON.parse(this.diyData.value);
if (this.$refs.loadingCover) this.$refs.loadingCover.hide();
}
uni.stopPullDownRefresh();
}
}
});
},
toLogin() {
this.$refs.login.open('/pages/goods/category')
}
},
onPullDownRefresh() {
uni.hideTabBar();
this.getDiyInfo();
}
};
</script>
<style lang="scss">
/deep/ .uni-popup__wrapper.uni-center {
background: rgba(0, 0, 0, 0.6);
}
/deep/ .uni-popup__wrapper-box {
border-radius: 0 !important;
}
/deep/ .uni-popup__wrapper.uni-custom.center .uni-popup__wrapper-box {
overflow-y: visible;
}
/deep/ .loading-layer {
background: #fff !important;
}
// 分类四一级展开
/deep/ .category-template-4 .template-four .uni-popup__wrapper-box {
border-radius: 0px 0px 14px 14px !important;
overflow: hidden;
}
/deep/ .category-template-4 .content-wrap .categoty-goods-wrap .goods-list {
margin-top: 30rpx;
}
/deep/ .category-template-4 .content-wrap .goods-list .goods-item .footer-wrap .right-wrap .num-action {
width: 46rpx;
height: 46rpx;
}
/deep/ .uni-page-refresh-inner .uni-page-refresh__path {
stroke: rgb(1, 1, 1) !important;
}
</style>

659
pages/goods/detail.vue Normal file
View File

@@ -0,0 +1,659 @@
<template>
<page-meta :page-style="themeColor"></page-meta>
<view>
<!-- #ifndef H5 -->
<!-- <view class="page-header" v-if="goodsSkuDetail && goodsSkuDetail.config && goodsSkuDetail.config.nav_bar_switch == 0">
<ns-navbar :data="navbarData" :isBack="true"></ns-navbar>
</view> -->
<!-- #endif -->
<goods-detail-view :goodsSkuDetail="goodsSkuDetail" ref="goodsDetailView">
<!-- 价格区域 -->
<template v-slot:price>
<!-- 限时折扣 -->
<view v-if="showDiscount && goodsSkuDetail.discountTimeMachine" class="goods-promotion">
<view class="price-info">
<view class="icon-box"><text class="iconfont icon-tutechan"></text></view>
<view class="price-box">
<view class="promotion-text">限时折扣</view>
<view class="sale-num" v-if="goodsSkuDetail.sale_show">已售{{ goodsSkuDetail.sale_num }}{{ goodsSkuDetail.unit }}</view>
</view>
</view>
<view class="countdown">
<view class="txt">距结束仅剩</view>
<view class="clockrun">
<uni-count-down
:day="goodsSkuDetail.discountTimeMachine.d"
:hour="goodsSkuDetail.discountTimeMachine.h"
:minute="goodsSkuDetail.discountTimeMachine.i"
:second="goodsSkuDetail.discountTimeMachine.s"
splitorColor="#ffffff"
backgroundColor="#ffffff"
/>
</view>
</view>
</view>
<view class="group-wrap padding-top">
<view class="goods-module-wrap">
<block v-if="goodsSkuDetail.isinformation == 0">
<template v-if="showDiscount">
<text class="price-symbol price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-font">{{ parseFloat(goodsSkuDetail.discount_price).toFixed(2).split('.')[0] }}</text>
<text class="price-symbol price-font">.{{ parseFloat(goodsSkuDetail.discount_price).toFixed(2).split('.')[1] }}</text>
</template>
<template v-else>
<template v-if="goodsSkuDetail.member_price > 0">
<text class="price-symbol price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-font">{{ parseFloat(goodsSkuDetail.member_price).toFixed(2).split('.')[0] }}</text>
<text class="price-symbol price-font">.{{ parseFloat(goodsSkuDetail.member_price).toFixed(2).split('.')[1] }}</text>
<view class="member-vip-wrap">
<image :src="$util.img('public/uniapp/goods/member_vip.png')" mode="aspectFit"/>
</view>
<view class="member-price-wrap" v-if="!goodsSkuDetail.market_price_show">
<text class="unit price-font">原价</text>
<text class="unit price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="money price-font">{{ goodsSkuDetail.price }}</text>
</view>
</template>
<template v-else>
<text class="price-symbol price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-font">{{ parseFloat(goodsSkuDetail.price).toFixed(2).split('.')[0] }}</text>
<text class="price-symbol price-font">.{{ parseFloat(goodsSkuDetail.price).toFixed(2).split('.')[1] }}</text>
</template>
</template>
<view class="market-price-wrap" v-if="goodsSkuDetail.market_price_show">
<text class="unit price-font" v-if="(showDiscount && goodsSkuDetail.price > 0) || goodsSkuDetail.market_price > 0">
{{ $lang('common.currencySymbol') }}
</text>
<text class="money price-font" v-if="showDiscount && goodsSkuDetail.price > 0">{{ goodsSkuDetail.price }}</text>
<text class="money price-font" v-else-if="goodsSkuDetail.market_price > 0">{{ goodsSkuDetail.market_price }}</text>
</view>
<view class="follow-and-share">
<text class="follow iconfont icon-share" @click="openSharePopup()"></text>
<text class="share iconfont" @click="editCollection()" :class="whetherCollection == 1 ? 'icon-likefill color-base-text' : 'icon-guanzhu'"></text>
</view>
</block>
<block v-else>
<template>
<text class="price price-font" style="font-weight: 600;">{{$lang('makebtn')}}</text>
</template>
</block>
</view>
<view class="goods-module-wrap info">
<text class="sku-name-wrap">{{ goodsSkuDetail.goods_name }}</text>
<text class="introduction" v-if="goodsSkuDetail.introduction" :style="{ color: goodsSkuDetail.config ? goodsSkuDetail.config.introduction_color : '' }">
{{ goodsSkuDetail.introduction }}
</text>
<view class="goods-tag-list" v-if="goodsSkuDetail.label_name">
<text class="tag-item">{{ goodsSkuDetail.label_name }}</text>
</view>
<view class="logistics-wrap">
<text v-if="goodsSkuDetail.stock_show">{{$lang('stock')}}: {{ goodsSkuDetail.stock +goodsSkuDetail.unit}}</text>
<text v-if="goodsSkuDetail.sale_show">{{$lang('sales')}}: {{ goodsSkuDetail.sale_num+goodsSkuDetail.unit }}</text>
</view>
<!-- 会员卡 -->
<!-- <view class="member-card-wrap" @click="$util.redirectTo('/pages_tool/member/card_buy')" v-if="membercard">
<text class="iconfont icon-huiyuan"></text>
<view class="info">开通{{ membercard.level_name }}仅需{{ membercard.member_price }}</view>
<text class="btn">立即开通</text>
</view> -->
</view>
</view>
<!-- 当前商品参与的营销活动入口 -->
<view class="group-wrap"><ns-goods-promotion ref="goodsPromotion" promotion="discount"></ns-goods-promotion></view>
<view class="group-wrap fenxiao-detail"
v-if="
goodsSkuDetail.fenxiao_detail &&
goodsSkuDetail.fenxiao_detail.words_account &&
goodsSkuDetail.fenxiao_detail.commission_money > 0 &&
goodsSkuDetail.fenxiao_detail.is_commission_money == 1
">
<view class="title color-base-text">{{$lang('commission')}}</view>
<view class="commission-ratio">
<view class="item">
<view>One {{$lang('commissiontext')}}</view>
<view class="price-color">
<text class="unit">¥</text>
<text class="money">{{ parseFloat(goodsSkuDetail.fenxiao_detail.commission_money).toFixed(2).split('.')[0] }}</text>
<text class="unit">.{{ parseFloat(goodsSkuDetail.fenxiao_detail.commission_money).toFixed(2).split('.')[1] }}</text>
</view>
</view>
</view>
</view>
<!-- <view class="group-wrap card-info" v-if="goodsSkuDetail.goods_class == 5 && goodsSkuDetail.card_info && goodsSkuDetail.card_info.relation_goods.length">
<view class="card-title">- 套餐包含以下的服务及商品 -</view>
<view class="card-desc" v-if="goodsSkuDetail.card_info.card_type == 'timecard' || goodsSkuDetail.card_info.card_type == 'commoncard'">
{{ goodsSkuDetail.card_info.card_type == 'commoncard' ? '卡项内项目/商品总的可用次数为' + goodsSkuDetail.card_info.common_num + ' ,' : '' }}
{{ goodsSkuDetail.card_info.card_type == 'timecard' ? '次数不限 ,' : '' }} 有效期为{{
(goodsSkuDetail.card_info.validity_type == 0 && '永久') ||
(goodsSkuDetail.card_info.validity_type == 1 && goodsSkuDetail.card_info.validity_day + '天') ||
(goodsSkuDetail.card_info.validity_type == 2 && $util.timeStampTurnTime(goodsSkuDetail.card_info.validity_time))
}}
</view>
<view class="card-content" :style="{ height: [cardOff ? 'auto' : '198rpx'] }">
<view class="card-item"
v-for="(item, index) in goodsSkuDetail.card_info.relation_goods"
@click="$util.redirectTo('/pages/goods/detail', { goods_id: item.goods_id })"
>
<image :src="$util.img(item.sku_image)" mode="aspectFill"/>
<view class="content">
<view class="name multi-hidden">{{ item.sku_name }}</view>
<view class="price">¥{{ item.price }}</view>
<text class="num" v-if="goodsSkuDetail.card_info.card_type == 'oncecard'">x{{ item.num }}</text>
</view>
</view>
</view>
<view class="card-off" @click="cardOff = !cardOff" v-if="goodsSkuDetail.card_info.relation_goods.length > 1">
<text>{{ cardOff ? '收起' : '展开' }}</text>
<text class="icondiy" :class="[cardOff ? 'icon-system-jiantoushang' : 'icon-system-jiantouxia']"></text>
</view>
</view> -->
</template>
<!--多规格-->
<template v-slot:skuspec>
<view class="item selected-sku-spec" @click="buyNow()">
<view class="label">{{$lang('spec')}}</view>
<view class="box">
<text v-for="(item, index) in goodsSkuDetail.sku_spec_format" :key="index">{{ item.spec_name }}/{{ item.spec_value_name }}</text>
</view>
<text class="iconfont iconright"></text>
</view>
</template>
<!-- 入口区域 -->
<!-- <template v-slot:entrance>
<view class="item coupon" v-if="couponList.length && couponList[0]['useState'] != 2" @click="openCouponPopup()">
<view class="label">领券</view>
<view class="coupon-list">
<view class="coupon-item" v-for="(item, index) in couponList" :key="index" v-if="index < 3 && item.useState != 2">
<view v-if="item.type == 'reward'">
{{
parseFloat(item.at_least) > 0
? '满' + decimalPointFormat(item.at_least) + '减' + decimalPointFormat(item.money)
: '无门槛使用' + decimalPointFormat(item.money)
}}
</view>
<view v-else-if="item.type == 'discount'">{{ '满' + decimalPointFormat(item.at_least) + '打' + parseFloat(item.discount)+'折' }}</view>
</view>
</view>
<text class="iconfont icon-right"></text>
</view>
<view class="item selected-sku-spec" v-if="goodsSkuDetail.sku_spec_format" @click="choiceSku">
<view class="label">选择</view>
<view class="box">
<text v-for="(item, index) in goodsSkuDetail.sku_spec_format" :key="index">{{ item.spec_name }}/{{ item.spec_value_name }}</text>
</view>
<text class="iconfont icon-right"></text>
</view>
<view class="item free" v-if="manjian.rule_json !== null && addonIsExist.manjian" @click="openManjianPopup()">
<view class="label">促销</view>
<text class="free-tip color-base-text">满减</text>
<text class="font-size-base value">{{ manjian.manjian_name }}</text>
<text class="iconfont icon-right"></text>
</view>
</template> -->
<!-- 业务区域 -->
<template v-slot:business>
<!-- SKU选择 -->
<ns-goods-sku
v-if="goodsSkuDetail.goods_id"
ref="goodsSku"
@refresh="refreshGoodsSkuDetail"
:goods-id="goodsSkuDetail.goods_id"
:goods-detail="goodsSkuDetail"
:max-buy="goodsSkuDetail.max_buy"
:min-buy="goodsSkuDetail.min_buy"
@getSkuId="setSkuId"
></ns-goods-sku>
<!-- 组合套餐 -->
<view v-if="bundling.length && bundling[0].bl_name && addonIsExist.bundling">
<view class="group-wrap" @click="openBundlingPopup()">
<view class="goods-cell" @click="openBundlingPopup()">
<view class="box">
<text class="tit">组合套餐</text>
<text>{{ bundling[0].bl_name }}</text>
</view>
<text class="iconfont icon-right"></text>
<!-- <view class="more-img-wrap"><image :src="$util.img('public/uniapp/goods/detail_more.png')" mode="aspectFit" /></view> -->
</view>
<scroll-view class="combo-goods-wrap color-tip" scroll-x="true">
<view class="goods-wrap">
<view class="goods-item" @click="toGoodsDetail(skuId)" v-if="bundlingType == true">
<view class="combo-img">
<image :src="$util.img(goodsSkuDetail.sku_image, { size: 'mid' })" @error="imageError()" />
<view class="price-wrap">
<text class="unit price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-font">{{ goodsSkuDetail.price }}</text>
</view>
</view>
<text class="name">{{ goodsSkuDetail.goods_name }}</text>
</view>
<block v-for="(item, index) in bundling[0].bundling_goods" :key="index">
<template v-if="index < 3">
<view class="goods-item" @click="toGoodsDetail(item.sku_id)">
<view class="combo-img">
<image :src="$util.img(item.sku_image, { size: 'mid' })" @error="bundlingImageError(0, index)" />
<view class="price-wrap">
<text class="unit price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-font">{{ item.price }}</text>
</view>
</view>
<text class="name">{{ item.sku_name }}</text>
</view>
</template>
</block>
</view>
</scroll-view>
</view>
<view @touchmove.prevent.stop>
<uni-popup ref="bundlingPopup" type="bottom">
<view class="bundling-popup-layer popup-layer">
<view class="head-wrap" @click="closeBundlingPopup()">
<text>组合套餐</text>
<text class="iconfont icon-close"></text>
</view>
<scroll-view scroll-y class="bundling-body">
<view class="bundling-view">
<block v-for="(item, index) in bundling" :key="index">
<view class="bundling-item">
<view class="title" @click="toComoDetail(item.bl_id)">
<text>{{ item.bl_name }}</text>
<text class="iconfont icon-right"></text>
</view>
<scroll-view scroll-x>
<view class="goods-wrap">
<view class="goods-item" @click="toGoodsDetail(skuId)">
<view class="combo-img">
<image :src="$util.img(goodsSkuDetail.sku_image, { size: 'mid' })" @error="imageError()" />
<view class="price-wrap">
<text class="unit price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-font">{{ goodsSkuDetail.price }}</text>
</view>
</view>
<text class="name">{{ goodsSkuDetail.goods_name }}</text>
</view>
<block v-for="(goods, goods_index) in item.bundling_goods" :key="goods_index">
<template v-if="goods_index < 3">
<view class="goods-item" @click="toGoodsDetail(goods.sku_id)">
<view class="combo-img">
<image :src="$util.img(goods.sku_image, { size: 'mid' })" @error="bundlingImageError(index, goods_index)" />
<view class="price-wrap">
<text class="unit price-font">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-font">{{ goods.price }}</text>
</view>
</view>
<text class="name">{{ goods.sku_name }}</text>
</view>
</template>
</block>
</view>
</scroll-view>
<view class="bundling-price-wrap">
<text class="label">套餐价</text>
<text class="unit price-color">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-color">{{ item.bl_price }}</text>
<button type="primary" size="mini" class="mini" @click="toComoDetail(item.bl_id)">立即购买</button>
</view>
</view>
</block>
</view>
</scroll-view>
</view>
</uni-popup>
</view>
</view>
<!-- 优惠券 -->
<view @touchmove.prevent.stop>
<uni-popup ref="couponPopup" type="bottom">
<view class="goods-coupon-popup-layer popup-layer">
<view class="head-wrap" @click="closeCouponPopup()">
<text>优惠券</text>
<text class="iconfont icon-close"></text>
</view>
<scroll-view class="coupon-body" scroll-y>
<view class="coupon-item ns-gradient-diy-goods-list" v-for="(item, index) in couponList" :key="index" v-if="hackReset">
<view class="coupon-info" :style="{ backgroundColor: item.useState == 2 ? '#F2F2F2' : 'var(--main-color-shallow)' }">
<view class="info-wrap" :class="{ disabled: item.useState == 2 }">
<image class="coupon-line" mode="heightFix" :src="$util.img('public/uniapp/coupon/coupon_line.png')"></image>
<view class="coupon-money">
<template v-if="item.type == 'reward'">
<text class="unit">{{ $lang('common.currencySymbol') }}</text>
<text class="money">{{ parseFloat(item.money) }}</text>
</template>
<template v-else-if="item.type == 'discount'">
<text class="money">{{ parseFloat(item.discount) }}</text>
<text class="unit">折</text>
</template>
<view class="at-least">
<template v-if="item.at_least > 0">
满{{ item.at_least }}可用
</template>
<template v-else>
无门槛
</template>
</view>
</view>
</view>
<view class="desc-wrap">
<view class="coupon-name">{{ item.coupon_name }}</view>
<view v-if="item.type == 'discount' && item.discount_limit > 0" class="limit">最多可抵¥{{ item.discount_limit }}</view>
<view class="time font-size-goods-tag" v-if="item.validity_type == 0">有效期:{{ $util.timeStampTurnTime(item.end_time) }}</view>
<view class="time font-size-goods-tag" v-else-if="item.validity_type == 1">有效期:领取之日起{{ item.fixed_term }}天内有效</view>
<view class="time font-size-goods-tag" v-else>有效期:长期有效</view>
</view>
<button type="primary" v-if="item.useState == 2" disabled>已抢光</button>
<button type="primary" v-else-if="item.useState == 1" disabled>已领取</button>
<button type="primary" v-else @click="receiveCoupon(item)">领取</button>
</view>
</view>
</scroll-view>
<view class="button-box"><button type="primary" @click="closeCouponPopup()">确定</button></view>
</view>
</uni-popup>
</view>
<!-- 促销 -->
<view @touchmove.prevent.stop v-if="addonIsExist.manjian">
<uni-popup ref="manjianPopup" type="bottom">
<view class="manjian-popup-layer popup-layer">
<view class="head-wrap" @click="closeManjianPopup()">
<text>促销</text>
<text class="iconfont icon-close"></text>
</view>
<scroll-view scroll-y class="manjian-body">
<view class="item" v-if="manjian.manjian != undefined" style="display: flex;">
<view class="free-tip color-base-text color-base-border">满减</view>
<text class="font-size-base">{{ manjian.manjian }}</text>
</view>
<view class="item" v-if="manjian.mansong != undefined">
<text class="free-tip color-base-text color-base-border">满送</text>
<text class="font-size-base">{{ manjian.mansong }}</text>
</view>
<view class="item" v-if="manjian.free_shipping != undefined" style="display: flex;">
<view class="free-tip color-base-text color-base-border">包邮</view>
<text class="font-size-base">{{ manjian.free_shipping }}</text>
</view>
</scroll-view>
<view class="button-box"><button type="primary" @click="closeManjianPopup()">确定</button></view>
</view>
</uni-popup>
</view>
<!--商品留言弹窗-->
<view class="goods-sku" @touchmove.prevent.stop>
<uni-popup ref="informationPopup" type="bottom">
<view class="manjian-popup-layer popup-layer" :style="{ height: FormHeight }">
<view class="head-wrap" @click="closeinformationPopup()">
<text>商品留言</text>
<text class="iconfont icon-close"></text>
</view>
<scroll-view scroll-y class="manjian-body" >
<!-- <view class="item" v-if="manjian.manjian != undefined" style="display: flex;">
<view class="free-tip color-base-text color-base-border">满减</view>
<text class="font-size-base">{{ manjian.manjian }}</text>
</view>
<view class="item" v-if="manjian.mansong != undefined">
<text class="free-tip color-base-text color-base-border">满送</text>
<text class="font-size-base">{{ manjian.mansong }}</text>
</view>
<view class="item" v-if="manjian.free_shipping != undefined" style="display: flex;">
<view class="free-tip color-base-text color-base-border">包邮</view>
<text class="font-size-base">{{ manjian.free_shipping }}</text>
</view> -->
<!-- v-if="goodsSkuDetail.goodsForm" -->
<view style="padding: 0 30rpx;">
<ns-form :data="informationform" ref="form"></ns-form>
</view>
</scroll-view>
<view class="button-box"><button type="primary" @click="saveubfirnation()">确定</button></view>
</view>
</uni-popup>
<!-- <uni-popup ref="informationPopup" type="bottom" class="sku-layer" @change="popclose">
<view class="sku-info">
<view class="body-item">
<scroll-view scroll-y class="wrap">
<ns-form :data="goodsSkuDetail.goodsForm" v-if="goodsSkuDetail.goodsForm" ref="form"></ns-form>
</scroll-view>
</view>
</view>
</uni-popup> -->
</view>
<!---->
</template>
<!-- 操作区域 -->
<template v-slot:action>
<!-- 商品底部导航 -->
<ns-goods-action :safeArea="isIphoneX">
<template v-if="goodsSkuDetail.goods_state == 1">
<ns-goods-action-button
class="goods-action-button active3"
:disabled-text="$lang('status')"
:disabled="true"
v-if="goodsSkuDetail.store_goods_status != undefined && goodsSkuDetail.store_goods_status != 1"
/>
<block v-else>
<ns-goods-action-icon :text="$lang('home')" icon="icon-shouye1" @click="goHome" />
<!-- #ifdef MP-WEIXIN -->
<ns-goods-action-icon
:text="$lang('cart')"
:cornerMarkBg="themeStyle.goods_detail.goods_cart_num_corner"
icon="icon-gouwuche2"
:corner-mark="cartNumber > 0 ? cartNumber + '' : ''"
@click="goCart"
/>
<ns-goods-action-icon :text="$lang('kefu')" icon="icox icox-kefu" :send-data="contactData" :chatParam="chatRoomParams" />
<!-- #endif -->
<!-- #ifdef H5 -->
<ns-goods-action-icon :text="$lang('follow')" :icon="whetherCollection == 1 ? 'icon-likefill color-base-text' : 'icon-guanzhu'" @click="editCollection" />
<!-- #endif -->
<block v-if="goodsSkuDetail.isinformation >= 1">
<ns-goods-action-button v-if="goodsSkuDetail.isinformation == 1" class="goods-action-button active3" disabled-text="" backgroundColor="#54c952" @click="phoneClick(goodsSkuDetail.goods_mobile)" :text="$lang('make')" :disabled="false" />
<ns-goods-action-button v-if="goodsSkuDetail.isinformation == 2" class="goods-action-button active3" disabled-text="" backgroundColor="#54c952" @click="showinformation" :text="$lang('leave')" :disabled="false" />
<!-- <ns-goods-action-button v-if="goodsSkuDetail.isinformation == 2" class="goods-action-button active3" disabled-text="" backgroundColor="#54c952" @click="buyNow" text="商品留言" :disabled="false" /> -->
</block>
<block v-else>
<block v-if="goodsSkuDetail.stock == 0 && !goodsSkuDetail.sku_spec_format">
<ns-goods-action-button class="goods-action-button active3" :disabled-text="$lang('sellout')" :disabled="true" />
</block>
<block v-else-if="
goodsSkuDetail.is_limit == 1 &&
goodsSkuDetail.limit_type == 2 &&
goodsSkuDetail.max_buy != 0 &&
goodsSkuDetail.purchased_num >= goodsSkuDetail.max_buy
">
<ns-goods-action-button class="goods-action-button active3" :disabled-text="$lang('max')" :disabled="true" />
</block>
<block v-else>
<ns-goods-action-button
class="goods-action-button"
:text="$lang('addcart')"
:backgroundColor="themeStyle.goods_detail.goods_btn_color_shallow"
@click="joinCart"
v-if="goodsSkuDetail.is_virtual == 0"
/>
<ns-goods-action-button
class="goods-action-button"
:backgroundColor="themeStyle.goods_detail.goods_btn_color"
:textColor="themeStyle.btn_text_color"
:text="$lang('buynow')"
@click="buyNow"
/>
</block>
</block>
</block>
</template>
<template v-else>
<ns-goods-action-button class="goods-action-button active3" :disabled-text="$lang('status')" :disabled="true" />
</template>
</ns-goods-action>
</template>
</goods-detail-view>
<to-top v-if="showTop" @toTop="scrollToTopNative()"></to-top>
<ns-login ref="login"></ns-login>
<loading-cover ref="loadingCover"></loading-cover>
<!-- #ifdef MP-WEIXIN -->
<!-- 小程序隐私协议 -->
<privacy-popup ref="privacyPopup"></privacy-popup>
<!-- #endif -->
</view>
</template>
<script>
import nsGoodsAction from '@/components/ns-goods-action/ns-goods-action.vue';
import nsGoodsActionIcon from '@/components/ns-goods-action-icon/ns-goods-action-icon.vue';
import nsGoodsActionButton from '@/components/ns-goods-action-button/ns-goods-action-button.vue';
import uniPopup from '@/components/uni-popup/uni-popup.vue';
import nsGoodsSku from '@/components/ns-goods-sku/ns-goods-sku.vue';
import uniCountDown from '@/components/uni-count-down/uni-count-down.vue';
import detail from './public/js/detail.js';
import scroll from '@/common/js/scroll-view.js';
import toTop from '@/components/toTop/toTop.vue';
import nsGoodsPromotion from '@/components/ns-goods-promotion/ns-goods-promotion.vue';
import goodsDetailBase from '@/common/js/goods_detail_base.js';
import goodsDetailView from '@/components/goods-detail-view/goods-detail-view.vue';
export default {
components: {
nsGoodsAction,
nsGoodsActionIcon,
nsGoodsActionButton,
uniPopup,
nsGoodsSku,
uniCountDown,
nsGoodsPromotion,
goodsDetailView,
toTop
},
mixins: [goodsDetailBase, detail, scroll]
};
</script>
<style lang="scss">
@import '@/common/css/goods_detail.scss';
@import './public/css/detail.scss';
.sku-info {
max-height: 75vh;
height: 45vh;
position: relative;
z-index: 999;
}
</style>
<style scoped>
/deep/ .action-icon-wrap .iconfont.icon-shouye1 {
font-size: 40rpx;
}
/deep/ .uni-video-cover {
background: none;
}
/deep/ .uni-video-cover-duration {
display: none;
}
/deep/ .uni-video-cover-play-button {
border-radius: 50%;
border: 4rpx solid #fff;
width: 120rpx;
height: 120rpx;
background-size: 30%;
}
.poster-layer >>> .uni-popup__wrapper-box {
max-height: initial !important;
}
/deep/ .sku-layer .uni-popup__wrapper-box {
overflow-y: initial !important;
}
.goods-promotion .countdown .clockrun >>> .uni-countdown__number {
min-width: 32rpx;
height: 32rpx;
text-align: center;
line-height: 32rpx;
border-radius: 4px;
display: inline-block;
padding: 4rpx;
margin: 0;
border: none;
}
.goods-promotion .countdown .clockrun >>> .uni-countdown__splitor {
width: 10rpx;
height: 32rpx;
line-height: 36rpx;
text-align: center;
}
.goods-promotion .countdown .clockrun >>> .uni-countdown__splitor.day {
width: initial;
}
/deep/ .uni-popup__wrapper.uni-custom .uni-popup__wrapper-box {
max-height: unset !important;
}
/deep/ .goods-action-button.active1 {
padding-left: 10px;
}
/deep/ .goods-action-button.active2 {
padding-right: 10px;
}
/deep/ .goods-action-button.active3 {
padding: 0 10px;
}
/deep/ .goods-action-button.active4 {
padding: 0 10px;
}
/deep/ .uni-popup__wrapper.bottom {
border-radius: 24rpx 24rpx 0 0;
}
/deep/ .goods-action-button.active1 .action-buttom-wrap {
height: 72rpx;
line-height: 72rpx;
}
/deep/ .goods-action-button.active2 .action-buttom-wrap {
height: 72rpx;
line-height: 72rpx;
}
/deep/ .goods-action-button.active3 .action-buttom-wrap {
height: 72rpx;
line-height: 72rpx;
margin: 20rpx 0;
}
/deep/ .goods-action-button.active4 .action-buttom-wrap {
height: 72rpx;
line-height: 72rpx;
}
</style>

317
pages/goods/list.vue Normal file
View File

@@ -0,0 +1,317 @@
<template>
<page-meta :page-style="themeColor"></page-meta>
<view class="content">
<view class="head-wrap">
<!-- 搜索区域 -->
<view class="search-wrap uni-flex uni-row">
<view class="flex-item input-wrap">
<input class="uni-input" maxlength="50" v-model="keyword" @confirm="search()" :placeholder="langstatus?$lang('Search'):'请输入您要搜索的商品'" />
<text class="iconfont icon-sousuo3" @click.stop="search()"></text>
</view>
<view class="iconfont" :class="{ 'icon-apps': isList, 'icon-list': !isList }" @click="changeListStyle()"></view>
</view>
<!-- 排序 -->
<view class="sort-wrap">
<view class="comprehensive-wrap" :class="{ 'color-base-text': orderType === '' }" @click="sortTabClick('')">
<text :class="{ 'color-base-text': orderType === '' }">{{langstatus?$lang('Random'):'综合'}}</text>
</view>
<view :class="{ 'color-base-text': orderType === 'sale_num' }" @click="sortTabClick('sale_num')">{{langstatus?$lang('Sales'):'销量'}}
</view>
<view class="price-wrap" @click="sortTabClick('discount_price')">
<text :class="{ 'color-base-text': orderType === 'discount_price' }">{{langstatus?$lang('Price'):'价格'}}</text>
<view class="iconfont-wrap">
<view class="iconfont icon-iconangledown-copy asc" :class="{ 'color-base-text': priceOrder === 'asc' && orderType === 'discount_price' }"></view>
<view class="iconfont icon-iconangledown desc" :class="{ 'color-base-text': priceOrder === 'desc' && orderType === 'discount_price' }"></view>
</view>
</view>
<view :class="{ 'color-base-text': orderType === 'screen' }" class="screen-wrap">
<text @click="sortTabClick('screen')">{{langstatus?$lang('Filter'):'筛选'}}</text>
<view @click="sortTabClick('screen')" class="iconfont-wrap">
<view class="iconfont icon-shaixuan color-tip"></view>
</view>
</view>
</view>
</view>
<mescroll-uni top="180" ref="mescroll" @getData="getGoodsList">
<block slot="list">
<view class="goods-list single-column" :class="{ show: isList }">
<view class="goods-item margin-bottom" v-for="(item, index) in goodsList" :key="index" @click="toDetail(item)">
<view class="goods-img">
<image :src="goodsImg(item.goods_image)" mode="widthFix" @error="imgError(index)"></image>
<view class="color-base-bg goods-tag" v-if="goodsTag(item) != ''">{{ goodsTag(item) }}</view>
<view class="sell-out" v-if="item.goods_stock <= 0">
<text class="iconfont icon-shuqing"></text>
</view>
</view>
<view class="info-wrap">
<view class="name-wrap">
<view class="goods-name" :class="[{ 'using-hidden': config.nameLineMode == 'single' }, { 'multi-hidden': config.nameLineMode == 'multiple' }]">
<block v-if="langstatus">
<block v-if="lang == 'en-us'">
{{ item.en_goods_name }}
</block>
<block v-else>
{{ item.goods_name }}
</block>
</block>
<block v-else>
{{ item.goods_name }}
</block>
</view>
</view>
<view class="lineheight-clear">
<view class="discount-price" v-if="item.isinformation == 0">
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-style large">{{ parseFloat(showPrice(item)).toFixed(2).split('.')[0] }}</text>
<text class="unit price-style small">.{{ parseFloat(showPrice(item)).toFixed(2).split('.')[1] }}</text>
</view>
<view class="discount-price" v-else>
<text class="price price-style large">{{langstatus?$lang('Make'):'咨询'}}</text>
</view>
<view class="member-price-tag" v-if="item.member_price && item.member_price == showPrice(item)">
<image :src="$util.img('public/uniapp/index/VIP.png')" mode="widthFix"></image>
</view>
<view class="member-price-tag" v-else-if="item.promotion_type == 1">
<image :src="$util.img('public/uniapp/index/discount.png')" mode="widthFix"></image>
</view>
</view>
<view class="pro-info" v-if="item.isinformation == 0">
<view class="delete-price color-tip price-font" v-if="showMarketPrice(item)">
<text class="unit">{{ $lang('common.currencySymbol') }}</text>
<text>{{ showMarketPrice(item) }}</text>
</view>
<view class="block-wrap">
<view class="sale color-tip" v-if="item.sale_show">已售{{ item.sale_num }}{{ item.unit ? item.unit : '' }}</view>
</view>
<view class="cart-action-wrap" v-if="config.control && item.is_virtual == 0">
<!-- 购物车图标 -->
<view v-if="config.style == 'icon-cart'" :style="{
color: config.theme == 'diy' ? config.textColor : '',
borderColor: config.theme == 'diy' ? config.textColor : ''
}" class="cart shopping-cart-btn iconfont icon-gouwuche click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
<view class="click-event"></view>
</view>
<!--加号图标 -->
<view v-else-if="config.style == 'icon-add'" :style="{
color: config.theme == 'diy' ? config.textColor : '',
borderColor: config.theme == 'diy' ? config.textColor : ''
}" class="cart plus-sign-btn iconfont icon-add1 click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
<view class="click-event"></view>
</view>
<!-- 按钮 -->
<view v-else-if="config.style == 'button'" :style="{
backgroundColor: config.theme == 'diy' ? config.bgColor : '',
color: config.theme == 'diy' ? config.textColor : '',
fontWeight: config.theme == 'diy' ? (config.fontWeight ? 'bold' : 'normal') : '',
padding: config.theme == 'diy' ? '12rpx ' + config.padding * 2 + 'rpx' : ''
}" class="cart buy-btn click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
{{ config.text }}
<view class="click-event"></view>
</view>
<!--自定义图标 -->
<view v-else-if="config.style == 'icon-diy'" :style="{
color: config.theme == 'diy' ? config.textColor : ''
}" class="icon-diy click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
<view class="click-event"></view>
<diy-icon :icon="config.iconDiy.icon" :value="config.iconDiy.style ? config.iconDiy.style : null"></diy-icon>
</view>
</view>
</view>
</view>
</view>
</view>
<view class="goods-list double-column" :class="{ show: !isList }">
<view class="goods-item margin-bottom" v-for="(item, index) in goodsList" :key="index"
@click="toDetail(item)" :style="{ left: listPosition[index] ? listPosition[index].left : '', top: listPosition[index] ? listPosition[index].top : '' }">
<view class="goods-img">
<image :src="goodsImg(item.goods_image)" mode="widthFix" @error="imgError(index)"></image>
<view class="color-base-bg goods-tag" v-if="goodsTag(item) != ''">{{ goodsTag(item) }}</view>
<view class="sell-out" v-if="item.stock <= 0">
<text class="iconfont icon-shuqing"></text>
</view>
</view>
<view class="info-wrap">
<view class="goods-name" :class="[{ 'using-hidden': config.nameLineMode == 'single' }, { 'multi-hidden': config.nameLineMode == 'multiple' }]">
{{ item.goods_name }}
</view>
<view class="lineheight-clear">
<view class="discount-price" v-if="item.isinformation == 0">
<text class="unit price-style small">{{ $lang('common.currencySymbol') }}</text>
<text class="price price-style large">{{ parseFloat(showPrice(item)).toFixed(2).split('.')[0] }}</text>
<text class="unit price-style small">.{{ parseFloat(showPrice(item)).toFixed(2).split('.')[1] }}</text>
</view>
<view class="discount-price" v-else>
<text class="price price-style large">{{langstatus?$lang('Make'):'咨询'}}</text>
</view>
<view class="member-price-tag" v-if="item.member_price && item.member_price == showPrice(item)">
<image :src="$util.img('public/uniapp/index/VIP.png')" mode="widthFix"></image>
</view>
<view class="member-price-tag" v-else-if="item.promotion_type == 1">
<image :src="$util.img('public/uniapp/index/discount.png')" mode="widthFix"></image>
</view>
<view class="delete-price color-tip price-font" v-if="showMarketPrice(item)">
<text class="unit">{{ $lang('common.currencySymbol') }}</text>
<text>{{ showMarketPrice(item) }}</text>
</view>
</view>
<view class="pro-info" v-if="item.isinformation == 0">
<view class="block-wrap" >
<view class="sale color-tip" v-if="item.sale_show">已售{{ item.sale_num }}{{ item.unit ? item.unit : '' }}</view>
</view>
<view class="cart-action-wrap" v-if="config.control && item.is_virtual == 0">
<!-- 购物车图标 -->
<view v-if="config.style == 'icon-cart'" :style="{
color: config.theme == 'diy' ? config.textColor : '',
borderColor: config.theme == 'diy' ? config.textColor : ''
}" class="cart shopping-cart-btn iconfont icon-gouwuche click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
<view class="click-event"></view>
</view>
<!--加号图标 -->
<view v-else-if="config.style == 'icon-add'" :style="{
color: config.theme == 'diy' ? config.textColor : '',
borderColor: config.theme == 'diy' ? config.textColor : ''
}" class="cart plus-sign-btn iconfont icon-add1 click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
<view class="click-event"></view>
</view>
<!-- 按钮 -->
<view v-else-if="config.style == 'button'" :style="{
backgroundColor: config.theme == 'diy' ? config.bgColor : '',
color: config.theme == 'diy' ? config.textColor : '',
fontWeight: config.theme == 'diy' ? (config.fontWeight ? 'bold' : 'normal') : '',
padding: config.theme == 'diy' ? '12rpx ' + config.padding * 2 + 'rpx' : ''
}" class="cart buy-btn click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
{{ config.text }}
<view class="click-event"></view>
</view>
<!--自定义图标 -->
<view v-else-if="config.style == 'icon-diy'" :style="{
color: config.theme == 'diy' ? config.textColor : ''
}" class="icon-diy click-wrap" :id="'goods-' + item.id"
@click.stop="$refs.goodsSkuIndex.addCart(config.cartEvent, item, $event)">
<view class="click-event"></view>
<diy-icon :icon="config.iconDiy.icon" :value="config.iconDiy.style ? config.iconDiy.style : null"></diy-icon>
</view>
</view>
</view>
</view>
</view>
</view>
<view v-if="goodsList.length == 0 && emptyShow"><ns-empty text="暂无商品"></ns-empty></view>
</block>
</mescroll-uni>
<ns-goods-sku-index ref="goodsSkuIndex" @addCart="addCart"></ns-goods-sku-index>
<!-- 筛选弹出框 -->
<uni-drawer :visible="showScreen" mode="right" @close="showScreen = false" class="screen-wrap">
<view class="title color-tip">筛选</view>
<scroll-view scroll-y>
<!-- 包邮 -->
<!-- <view class="item-wrap">
<view class="label"><text>是否包邮</text></view>
<view class="list">
<uni-tag :inverted="true" text="包邮" :type="isFreeShipping ? 'primary' : 'default'" @click="isFreeShipping = !isFreeShipping" />
</view>
</view> -->
<!-- 价格筛选项 -->
<!-- <view class="item-wrap">
<view class="label"><text>价格区间()</text></view>
<view class="price-wrap">
<input class="uni-input" type="digit" v-model="minPrice" placeholder="最低价" />
<view class="h-line"></view>
<input class="uni-input" type="digit" v-model="maxPrice" placeholder="最高价" />
</view>
</view> -->
<!-- 品牌筛选项 -->
<!-- <view class="item-wrap" v-if="brandList.length > 0">
<view class="label"><text>品牌</text></view>
<view class="list">
<view v-for="(item, index) in brandList" :key="index">
<uni-tag :inverted="true" :text="item.brand_name" :type="item.brand_id == brandId ? 'primary' : 'default'" @click="brandId == item.brand_id ? (brandId = 0) : (brandId = item.brand_id)" />
</view>
</view>
</view> -->
<!-- 分类筛选项 -->
<view class="category-list-wrap">
<text class="first">全部分类</text>
<view class="class-box">
<view @click="selectedCategory('')" class="list-wrap">
<text :class="{ selected: !categoryId, 'color-base-text': !categoryId }">全部</text>
</view>
<view @click="selectedCategory(item.category_id)" v-for="(item, index) in categoryList" :key="index" class="list-wrap">
<text :class="{ selected: item.category_id == categoryId, 'color-base-text': item.category_id == categoryId }">{{ item.category_name }}</text>
</view>
</view>
</view>
</scroll-view>
<view class="footer" :class="{ 'safe-area': isIphoneX }">
<button type="default" class="footer-box" @click="resetData">重置</button>
<button type="primary" class="footer-box1" @click="screenData">确定</button>
</view>
</uni-drawer>
<loading-cover ref="loadingCover"></loading-cover>
<!-- #ifdef MP-WEIXIN -->
<!-- 小程序隐私协议 -->
<privacy-popup ref="privacyPopup"></privacy-popup>
<!-- #endif -->
</view>
</template>
<script>
import uniDrawer from '@/components/uni-drawer/uni-drawer.vue';
import uniTag from '@/components/uni-tag/uni-tag.vue';
import nsGoodsSkuIndex from '@/components/ns-goods-sku/ns-goods-sku-index.vue';
import list from './public/js/list.js';
export default {
components: {
uniDrawer,
uniTag,
nsGoodsSkuIndex
},
data() {
return {};
},
mixins: [list]
};
</script>
<style lang="scss">
@import './public/css/list.scss';
</style>
<style scoped>
>>>.uni-tag--primary.uni-tag--inverted {
background-color: #f5f5f5 !important;
}
/deep/ .sku-layer .uni-popup__wrapper.uni-custom .uni-popup__wrapper-box {
max-height: unset !important;
}
</style>

View File

@@ -0,0 +1,647 @@
.container {
width: 100vw;
height: 100vh;;
display: flex;
flex-direction: column;
}
.scroll-view {
flex: 1;
height: 0;
transform: translateX(0);
}
.cart-header {
padding: 20rpx 0;
display: flex;
align-items: center;
justify-content: space-between;
line-height: 36rpx;
background: #f7f7f7;
.num-wrap {
margin-left: $margin-both;
color: #666666;
font-size: 26rpx;
}
.cart-action {
line-height: inherit;
margin-right: $margin-both;
color: #666666;
font-size: 26rpx;
}
&.invalid {
margin-left: $margin-both;
margin-top: $margin-updown;
flex: 1;
line-height: inherit;
}
}
.cart-wrap {
margin: 0 24rpx 24rpx;
border-radius: 16rpx;
overflow: hidden;
.fixed-wrap {
height: 116rpx;
}
.cart-goods {
background: #fff;
box-sizing: border-box;
position: relative;
padding: 30rpx 0 30rpx 30rpx;
&::after {
content: '';
position: absolute;
left: 20rpx;
right: 20rpx;
height: 2rpx;
bottom: 0;
background-color: #f2f2f2;
}
&:last-of-type::after {
height: 0;
}
.goods-wrap {
display: flex;
position: relative;
padding-left: 64rpx;
transition: all 0.1s;
& > .iconfont {
font-size: 40rpx;
position: absolute;
top: 50%;
left: 0;
transform: translateY(-50%);
transition: all 0.2s;
}
& > .icon-yuan_checkbox {
color: $color-disabled;
}
&.edit {
transform: translateX(-70rpx);
> .iconfont {
opacity: 0;
}
}
.goods-img {
width: 180rpx;
height: 180rpx;
image {
width: 100%;
height: 100%;
border-radius: 8rpx;
}
}
.goods-info {
flex: 1;
width: 0;
padding: 0 30rpx;
display: flex;
flex-direction: column;
justify-content: space-between;
.goods-name {
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 2;
overflow: hidden;
line-height: 1.5;
font-size: $font-size-base;
}
.sku-wrap {
white-space: nowrap;
text-overflow: ellipsis;
overflow: hidden;
width: 100%;
.sku {
line-height: 1;
margin: 10rpx 0 18rpx 0;
display: inline-flex;
align-items: center;
background: #f4f4f4;
border-radius: 8rpx;
padding: 0 10rpx 0 20rpx;
.goods-spec {
color: #666666;
font-size: 24rpx;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.iconfont {
font-size: 28rpx;
padding-left: 10rpx;
color: #666666;
}
}
}
.goods-sub-section {
display: flex;
justify-content: space-between;
width: 100%;
align-items: center;
.unit {
font-size: $font-size-tag;
margin-right: 4rpx;
}
.goods-price {
display: flex;
flex-direction: row;
font-weight: bold;
color: var(--price-color);
.bottom-price {
width: 100%;
font-size: $font-size-toolbar;
line-height: 1;
color: var(--price-color);
image {
width: 56rpx;
height: 22rpx;
margin-left: 6rpx;
}
}
}
/deep/ .decrease {
width: 52rpx;
height: 52rpx;
line-height: 48rpx;
font-size: 40rpx;
border-radius: 10rpx 0px 0px 10rpx;
}
/deep/ input {
height: 52rpx;
line-height: 52rpx;
}
/deep/ .increase {
width: 52rpx;
height: 52rpx;
line-height: 48rpx;
font-size: 40rpx;
border-radius: 0px 10rpx 10rpx 0px;
}
}
}
}
.item-del {
position: absolute;
width: 0;
height: 99%;
color: #fff;
right: 0;
top: 0;
display: flex;
align-items: center;
justify-content: center;
transition: all 0.3s;
overflow: hidden;
white-space: nowrap;
font-size: $font-size-tag;
&.show {
width: 90rpx;
}
}
&:first-child {
padding-top: 30rpx;
}
&:last-child {
.goods-info {
border-bottom: none;
padding-bottom: 0;
}
}
.discount-wrap {
line-height: 1.5;
font-size: 24rpx;
margin-top: 20rpx;
display: flex;
.discount-tag {
color: $base-color;
line-height: 1;
padding: 0 10rpx;
border-radius: $border-radius;
border: 1.5px solid $base-color;
margin-right: 10rpx;
white-space: nowrap;
line-height: 32rpx;
background: var(--main-color-shallow);
}
.interval {
height: 20rpx;
margin: 0 10rpx;
border-left: 2rpx solid #ddd;
white-space: nowrap;
margin-top: 10rpx;
&:last-child {
display: none;
}
}
.scroll-view {
flex: 1;
width: 0;
height: 100%;
white-space: nowrap;
}
}
}
.invalid-goods {
.invalid-mark {
color: $color-tip;
padding: 6rpx 16rpx;
display: inline-block;
font-size: $font-size-goods-tag;
}
}
}
.invalid .cart-header {
padding-top: 0;
}
.invalid .cart-header + .cart-goods {
padding-top: 30rpx;
}
.cart-bottom-block {
height: 100rpx;
margin-top: 20rpx;
}
.cart-bottom {
width: 100vw;
height: 100rpx;
position: fixed;
left: 0;
bottom: var(--tab-bar-height, 0);
background: #fff;
overflow: hidden;
display: flex;
z-index: 9;
.all-election {
height: 100rpx;
position: relative;
display: inline-block;
& > .iconfont {
font-size: 40rpx;
position: absolute;
top: 50%;
left: 30rpx;
transform: translateY(-50%);
}
& > .icon-yuan_checkbox {
color: $color-disabled;
}
& > text {
margin-left: 56rpx;
line-height: 100rpx;
padding-left: 30rpx;
}
}
.settlement-info {
flex: 1;
width: 0;
padding-right: 10rpx;
display: flex;
flex-direction: column;
justify-content: center;
text-align: right;
.money {
line-height: 1;
font-size: 32rpx;
.value {
font-weight: bold;
color: var(--price-color);
}
.unit {
font-size: $font-size-tag;
margin-right: 4rpx;
color: var(--price-color);
font-weight: bold;
}
}
.detail {
line-height: 1;
font-size: 22rpx;
color: #666666;
margin-top: 10rpx;
.iconfont {
font-size: 28rpx;
margin-left: 6rpx;
transition: all 0.1s;
display: inline-block;
&.open {
transform: rotate(180deg);
}
}
}
}
.action-btn {
// width: 200rpx;
height: 100rpx;
line-height: 100rpx;
border-radius: 0;
margin: 0;
display: flex;
justify-content: flex-end;
align-items: center;
margin-right: 30rpx;
white-space: nowrap;
button {
padding: 0 30rpx;
height: 70rpx;
line-height: 70rpx;
font-size: $font-size-base;
font-weight: bold;
border-radius: 50rpx;
&.delete {
height: 50rpx;
line-height: 46rpx;
}
}
}
}
.cart-bottom.active {
bottom: calc(constant(safe-area-inset-bottom) + 110rpx) !important;
bottom: calc(env(safe-area-inset-bottom) + 110rpx) !important;
}
.cart-empty {
text-align: center;
padding: 140rpx $padding 80rpx $padding;
image {
width: 380rpx;
}
button {
min-width: 300rpx;
margin-top: 100rpx;
height: 70rpx;
line-height: 70rpx !important;
font-size: $font-size-base;
border-radius: 50rpx;
&.visit-the {
font-weight: bold;
}
}
}
.popup {
width: 100vw;
background: #fff;
border-top-left-radius: 24rpx;
border-top-right-radius: 24rpx;
.popup-header {
display: flex;
position: relative;
padding: 40rpx;
.tit {
flex: 1;
font-size: $font-size-toolbar;
line-height: 1;
text-align: center;
}
.iconfont {
line-height: 1;
position: absolute;
right: 30rpx;
top: 50%;
transform: translate(0, -50%);
color: $color-tip;
font-size: $font-size-toolbar;
}
}
.popup-body {
}
}
.discount-popup {
.popup-body {
min-height: 300rpx;
}
.detail-item {
height: 60rpx;
display: flex;
align-items: center;
justify-content: space-between;
padding: 0 30rpx;
.money {
font-weight: bold;
}
.reduce {
color: var(--price-color);
}
}
.total {
margin-top: 20rpx;
.title {
font-size: 36rpx;
font-weight: bold;
}
}
}
.coupon-use-tips {
padding: 30rpx;
line-height: 1;
background: #fff;
border-bottom: 2rpx solid #eee;
display: flex;
justify-content: space-between;
align-items: center;
& view {
line-height: 1;
}
.iconfont {
font-size: 28rpx;
margin-left: 4rpx;
}
.title {
font-size: 28rpx;
font-weight: 600;
}
.desc {
font-size: 26rpx;
margin-left: 24rpx;
}
}
.coupon-item {
margin: $margin-updown $margin-both;
border-radius: 4rpx;
padding: 0;
position: relative;
background-color: #fff2f0;
&:before,
&:after {
position: absolute;
content: '';
background-color: #fff;
top: 50%;
width: 30rpx;
height: 30rpx;
border-radius: 50%;
z-index: 5;
}
&:before {
left: 0;
transform: translate(-50%, -50%);
}
&:after {
right: 0;
transform: translate(50%, -50%);
}
.coupon-info {
height: 190rpx;
display: flex;
width: 100%;
position: relative;
.info-wrap {
width: 220rpx;
height: 190rpx;
display: flex;
justify-content: center;
align-items: center;
margin-right: 20rpx;
background-repeat: no-repeat;
background-size: 100% 100%;
background: linear-gradient(to left, var(--bg-color), var(--bg-color-shallow));
position: relative;
.coupon-line {
position: absolute;
right: 0;
top: 0;
height: 100%;
}
.coupon-money {
color: #fff;
text-align: center;
line-height: 1;
.unit {
font-size: 30rpx;
}
.money {
font-size: 60rpx;
}
}
.at-least {
font-size: $font-size-tag;
color: #fff;
text-align: center;
margin-top: 20rpx;
}
}
.desc-wrap {
flex: 1;
max-width: calc(100% - 400rpx);
view {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.coupon-name {
margin-top: 10rpx;
margin-bottom: 4rpx;
font-size: $font-size-base;
}
.limit {
font-size: $font-size-activity-tag;
}
.time {
border-top: 2rpx dashed $color-disabled;
position: absolute;
bottom: 30rpx;
color: $color-tip;
padding-top: 10rpx;
line-height: 1.5;
font-size: $font-size-activity-tag;
}
}
button {
font-size: $font-size-tag;
position: absolute;
top: 50%;
right: 20rpx;
transform: translate(0, -50%);
margin: 0;
height: 50rpx;
line-height: 50rpx;
width: 100rpx;
padding: 0;
&[disabled] {
background-color: #dedede !important;
}
}
}
&.disabled {
background-color: #f2f2f2;
.coupon-money {
color: $color-tip !important;
}
.at-least {
color: $color-tip !important;
}
}
}
.uni-popup-discount {
z-index: 5;
}
.store-wrap {
display: flex;
align-items: center;
background-color: #fff;
padding: 26rpx 30rpx 0;
font-weight: bold;
line-height: 1;
.name {
font-size: $font-size-base;
margin-left: 10rpx;
}
}

View File

@@ -0,0 +1,585 @@
// 优惠券弹出层
.goods-coupon-popup-layer {
height: 800rpx;
.coupon-body {
position: absolute;
left: 0;
right: 0;
height: 65%;
.coupon-item {
margin: $margin-updown $margin-both;
border-radius: 4rpx;
padding: 0;
position: relative;
background-color: #fff2f0;
&:before,
&:after {
position: absolute;
content: '';
background-color: #fff;
top: 50%;
width: 30rpx;
height: 30rpx;
border-radius: 50%;
z-index: 5;
}
&:before {
left: 0;
transform: translate(-50%, -50%);
}
&:after {
right: 0;
transform: translate(50%, -50%);
}
.coupon-info {
height: 190rpx;
display: flex;
width: 100%;
position: relative;
.info-wrap {
width: 220rpx;
height: 190rpx;
display: flex;
justify-content: center;
align-items: center;
margin-right: 20rpx;
background-repeat: no-repeat;
background-size: 100% 100%;
background: linear-gradient(to left, var(--bg-color), var(--bg-color-shallow));
position: relative;
&.disabled {
background: #dedede;
}
.coupon-line {
position: absolute;
right: 0;
top: 0;
height: 100%;
}
.coupon-money {
color: #fff;
text-align: center;
line-height: 1;
.unit {
font-size: 30rpx;
}
.money {
font-size: 60rpx;
}
}
.at-least {
font-size: $font-size-tag;
color: #fff;
text-align: center;
margin-top: 20rpx;
}
}
.desc-wrap {
flex: 1;
max-width: calc(100% - 400rpx);
position: relative;
view {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.coupon-name {
margin-top: 10rpx;
margin-bottom: 4rpx;
font-size: $font-size-base;
}
.limit {
font-size: $font-size-activity-tag;
}
.time {
width: 100%;
border-top: 2rpx dashed $color-disabled;
position: absolute;
bottom: 30rpx;
color: $color-tip;
padding-top: 10rpx;
line-height: 1.5;
font-size: $font-size-activity-tag;
}
}
button {
font-size: $font-size-tag;
position: absolute;
top: 50%;
right: 20rpx;
transform: translate(0, -50%);
margin: 0;
height: 50rpx;
line-height: 50rpx;
width: 100rpx;
padding: 0;
&[disabled] {
background-color: #dedede !important;
}
}
}
&.disabled {
background-color: #f2f2f2;
.coupon-money {
color: $color-tip !important;
}
.at-least {
color: $color-tip !important;
}
}
}
}
}
// 满减
.manjian-popup-layer {
height: 660rpx;
.free-tip {
min-width: 72rpx;
height: 36rpx;
line-height: 36rpx;
text-align: center;
border: none;
padding: 8rpx 8rpx;
border-radius: $border-radius;
margin-right: 20rpx;
font-size: $font-size-activity-tag;
display: inline-block;
font-weight: bold;
color: var(--main-color);
background-color: var(--main-color-shallow);
}
.manjian-body {
position: absolute;
left: 0;
right: 0;
height: 60%;
.item {
padding: $padding 0;
margin: 0 30rpx;
border-bottom: 1px solid $color-line;
.value {
margin-left: 20rpx;
}
&:last-child {
border-bottom: 0;
}
}
}
}
// 组合套餐
.combo-goods-wrap {
display: flex;
// width: calc(100% - 40rpx);
white-space: nowrap;
align-items: center;
padding: 20rpx 0;
.goods-wrap {
display: flex;
align-items: center;
.goods-item {
width: 25%;
display: inline-block;
margin-right: 30rpx;
position: relative;
vertical-align: middle;
.combo-img {
height: 160rpx;
width: 160rpx;
overflow: hidden;
border-radius: $border-radius;
position: relative;
image {
width: 100%;
height: 100%;
}
.price-wrap {
position: absolute;
bottom: 0;
background: rgba(0, 0, 0, 0.4);
color: #fff;
left: 0;
width: 100%;
font-weight: bold;
.unit {
font-size: $font-size-tag;
margin-left: 10rpx;
}
.price {
font-size: $font-size-base;
}
}
}
.name {
display: block;
height: 40rpx;
line-height: 40rpx;
font-size: $font-size-tag;
margin-top: 10rpx;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
}
}
}
// 组合套餐
.bundling-popup-layer {
height: 600rpx;
.bundling-body {
position: absolute;
left: 0;
right: 0;
height: 83%;
background-color: $color-bg;
.bundling-view {
margin: 20rpx 30rpx;
border-radius: $border-radius;
.bundling-item {
padding: $padding 30rpx;
background-color: #fff;
margin-bottom: 20rpx;
.title {
margin-bottom: 20rpx;
display: flex;
justify-content: space-between;
align-items: center;
.icon-right {
position: initial;
}
}
&:last-child {
margin-bottom: 0;
}
scroll-view {
width: 100%;
white-space: nowrap;
box-sizing: border-box;
.goods-wrap {
display: flex;
align-items: center;
.goods-item {
width: 25%;
display: inline-block;
margin-right: 30rpx;
position: relative;
vertical-align: middle;
.combo-img {
height: 160rpx;
width: 160rpx;
overflow: hidden;
border-radius: $border-radius;
position: relative;
image {
width: 100%;
height: 100%;
}
.price-wrap {
position: absolute;
bottom: 0;
background: rgba(0, 0, 0, 0.4);
color: #fff;
left: 0;
width: 100%;
font-weight: bold;
.unit {
font-size: $font-size-tag;
margin-left: 10rpx;
}
.price {
font-size: $font-size-base;
}
}
}
.name {
display: block;
height: 40rpx;
line-height: 40rpx;
font-size: $font-size-tag;
margin-top: 10rpx;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
}
}
}
.bundling-price-wrap {
text-align: right;
margin-top: 20rpx;
.label {
font-size: $font-size-base;
vertical-align: middle;
margin-right: 20rpx;
}
.unit {
font-size: $font-size-tag;
vertical-align: middle;
margin-right: 4rpx;
font-weight: bold;
}
.price {
font-size: $font-size-toolbar;
vertical-align: middle;
font-weight: bold;
margin-right: 20rpx;
}
button {
vertical-align: middle;
background-color: var(--goods-btn-color);
}
}
}
}
}
}
.newdetail {
.item {
&.coupon {
.coupon-list {
flex: 1;
overflow: hidden;
line-height: 1;
height: 60rpx;
// line-height: 40rpx;
max-width: 84%;
box-sizing: border-box;
}
.coupon-item {
margin-top: 8rpx;
margin-bottom: 10rpx;
padding: 3rpx 16rpx;
margin-right: 20rpx;
position: relative;
border: 1.5px solid;
background-size: cover;
border-radius: 6rpx;
display: inline-block;
// height: 40rpx;
// line-height: 34rpx;
box-sizing: border-box;
// &:nth-child(2) {
// margin-left: 0;
// }
border-color: var(--goods-coupon);
&::after,
&::before {
content: '';
width: 12rpx;
height: 12rpx;
position: absolute;
top: 50%;
border-radius: $border-radius;
background: #fff;
border: 1px solid var(--goods-coupon) !important;
}
&::after {
left: -10rpx;
transform: translateY(-50%) rotate(-45deg);
border-top-color: transparent !important;
border-left-color: transparent !important;
}
&::before {
right: -10rpx;
transform: translateY(-50%) rotate(-45deg);
border-bottom-color: transparent !important;
border-right-color: transparent !important;
}
&:first-child {
margin-left: 0;
}
&:last-child {
margin-right: 0;
}
view {
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
font-size: 24rpx;
text-align: center;
line-height: 1.5;
// height: 36rpx;
// height: 36rpx;
// line-height: 34rpx;
color: var(--goods-coupon);
font-weight: bold;
}
}
}
}
}
.more-img-wrap {
width: 38rpx;
height: 38rpx;
position: absolute;
right: 30rpx;
image {
width: 100%;
height: 100%;
}
}
// 会员卡
.member-card-wrap {
margin-top: 20rpx;
height: 80rpx;
border-radius: 10rpx;
background: linear-gradient(to right, var(--goods-card-bg), var(--goods-card-bg-shallow));
display: flex;
align-items: center;
padding: 0 20rpx;
color: var(--goods-card-color);
.icon-huiyuan {
margin-right: 10rpx;
line-height: 1;
font-size: 32rpx;
}
.info {
flex: 1;
color: #e5ce75;
font-size: $font-size-tag;
}
.btn {
text-align: center;
line-height: 50rpx;
height: 50rpx;
border-radius: 6rpx;
width: 160rpx;
font-size: $font-size-tag;
color: #222;
font-weight: bold;
background: var(--goods-card-color);
}
}
.goods-promotion {
background: var(--promotion-color);
height: 75px;
.price-info {
display: flex;
flex-direction: row;
align-items: center;
justify-content: flex-start;
.icon-box {
margin-right: 20rpx;
.iconfont {
font-size: 60rpx;
color: #ffffff;
}
}
.price-box {
display: flex;
align-items: flex-start;
flex-direction: column;
height: 100%;
justify-content: center;
.promotion-text {
font-size: 36rpx;
color: #fff;
line-height: 1;
}
.sale-num {
display: flex;
align-items: center;
margin-top: 18rpx;
view {
color: #ffffff;
line-height: 1;
}
}
}
}
}
.countdown {
width: 220rpx;
background: var(--promotion-aux-color);
.txt {
color: #ffffff !important;
font-size: 28rpx !important;
}
.clockrun {
margin-top: 16rpx !important;
}
&:after {
position: absolute;
content: '';
top: calc(50% - 15rpx);
z-index: 5;
left: -15rpx;
width: 0;
height: 0;
border-style: solid;
border-width: 15rpx 15rpx 15rpx 0;
border-color: transparent var(--promotion-aux-color) transparent transparent;
}
}
.fenxiao-detail {
padding-top: 20rpx;
.title {
font-weight: 600;
font-size: $font-size-base;
}
.commission-ratio {
margin-top: 10rpx;
border-radius: $border-radius;
.item {
display: flex;
border-bottom: 2rpx solid $color-line;
height: 80rpx;
align-items: center;
&:last-child {
border-bottom: none;
}
view {
flex: 1;
&:first-child {
font-size: $font-size-base;
}
&:last-child {
text-align: right;
font-weight: bold;
.unit {
font-size: $font-size-tag;
margin-right: 4rpx;
}
.money {
font-size: $font-size-base;
}
}
}
}
}
}

View File

@@ -0,0 +1,647 @@
.head-wrap {
background: #fff;
position: fixed;
width: 100%;
left: 0;
z-index: 1;
.search-wrap {
flex: 0.5;
padding: 30rpx 30rpx 0;
font-size: $font-size-tag;
display: flex;
align-items: center;
.iconfont {
margin-left: 16rpx;
font-size: 36rpx;
}
.input-wrap {
flex: 1;
display: flex;
justify-content: space-between;
align-items: center;
background: $color-bg;
height: 64rpx;
padding-left: 10rpx;
border-radius: 70rpx;
input {
width: 90%;
background: $color-bg;
font-size: $font-size-tag;
height: 100%;
padding: 0 25rpx 0 40rpx;
line-height: 50rpx;
border-radius: 40rpx;
}
text {
font-size: $font-size-toolbar;
color: $color-tip;
width: 80rpx;
text-align: center;
margin-right: 20rpx;
}
}
.category-wrap,
.list-style {
display: flex;
justify-content: center;
align-items: center;
.iconfont {
font-size: 50rpx;
color: $color-tip;
}
text {
display: block;
margin-top: 60rpx;
}
}
}
.sort-wrap {
display: flex;
padding: 10rpx 20rpx 10rpx 0;
> view {
flex: 1;
text-align: center;
font-size: $font-size-base;
height: 60rpx;
line-height: 60rpx;
font-weight: bold;
}
.comprehensive-wrap {
display: flex;
justify-content: center;
align-items: center;
.iconfont-wrap {
display: inline-block;
margin-left: 10rpx;
width: 40rpx;
.iconfont {
font-size: $font-size-toolbar;
line-height: 1;
margin-bottom: 5rpx;
}
}
}
.price-wrap {
display: flex;
justify-content: center;
align-items: center;
.iconfont-wrap {
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
width: 40rpx;
.iconfont {
position: relative;
float: left;
font-size: 32rpx;
line-height: 1;
height: 20rpx;
color: #909399;
&.asc {
top: -2rpx;
}
&.desc {
top: -6rpx;
}
}
}
}
.screen-wrap {
display: flex;
justify-content: center;
align-items: center;
.iconfont-wrap {
display: inline-block;
margin-left: 10rpx;
width: 40rpx;
.iconfont {
font-size: $font-size-toolbar;
line-height: 1;
}
}
}
}
}
.category-list-wrap {
height: 100%;
.class-box {
display: flex;
flex-wrap: wrap;
padding: 0 $padding;
view {
width: calc((100% - 60rpx) / 3);
font-size: $font-size-goods-tag;
margin-right: 20rpx;
height: 60rpx;
line-height: 60rpx;
text-align: center;
margin-bottom: 12rpx;
flex-shrink: 0;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
background: rgba(245, 245, 245, 1);
border-radius: 5rpx;
&:nth-of-type(3n) {
margin-right: 0;
}
}
}
.first {
font-size: $font-size-tag;
display: block;
// background: $page-color-base;
padding: 20rpx;
}
.second {
border-bottom: 2rpx solid $color-line;
padding: 20rpx;
display: block;
font-size: $font-size-tag;
}
.third {
padding: 0 20rpx 20rpx;
overflow: hidden;
font-size: $font-size-tag;
> view {
display: inline-block;
margin-right: 20rpx;
margin-top: 20rpx;
}
.uni-tag {
padding: 0 20rpx;
}
}
}
.screen-wrap {
.title {
font-size: $font-size-tag;
padding: $padding;
background: #f6f4f5;
}
scroll-view {
height: 85%;
.item-wrap {
border-bottom: 1px solid #f0f0f0;
.label {
font-size: $font-size-tag;
padding: $padding;
view {
display: inline-block;
font-size: 60rpx;
height: 40rpx;
vertical-align: middle;
line-height: 40rpx;
}
}
.list {
margin: $margin-updown $margin-both;
overflow: hidden;
> view {
display: inline-block;
margin-right: 25rpx;
margin-bottom: 25rpx;
}
.uni-tag {
padding: 0 $padding;
font-size: $font-size-goods-tag;
background: #f5f5f5;
height: 52rpx;
line-height: 52rpx;
border: 0;
}
}
.price-wrap {
display: flex;
justify-content: center;
align-items: center;
padding: $padding;
input {
flex: 1;
background: #f5f5f5;
height: 52rpx;
width: 182rpx;
line-height: 50rpx;
font-size: $font-size-goods-tag;
border-radius: 50rpx;
text-align: center;
&:first-child {
margin-right: 10rpx;
}
&:last-child {
margin-left: 10rpx;
}
}
}
}
}
.footer {
height: 90rpx;
display: flex;
justify-content: center;
align-items: flex-start;
display: flex;
//position: absolute;
bottom: 0;
width: 100%;
.footer-box {
border-top-right-radius: 0;
border-bottom-right-radius: 0;
margin: 0;
width: 40%;
}
.footer-box1 {
border-top-left-radius: 0;
border-bottom-left-radius: 0;
margin: 0;
width: 40%;
}
}
}
.safe-area {
bottom: 68rpx !important;
}
.empty {
margin-top: 100rpx;
}
.buy-num {
font-size: $font-size-activity-tag;
}
.icon {
width: 34rpx;
height: 30rpx;
}
.list-style-new {
display: flex;
align-items: center;
.line {
width: 4rpx;
height: 28rpx;
background-color: rgba(227, 227, 227, 1);
margin-right: 60rpx;
}
}
.h-line {
width: 37rpx;
height: 2rpx;
background-color: $color-tip;
}
.lineheight-clear {
}
// 商品列表单列样式
.goods-list.single-column {
display: none;
&.show {
display: block;
}
.goods-item {
padding: 26rpx;
background: #fff;
margin: $margin-updown $margin-both;
border-radius: $border-radius;
display: flex;
position: relative;
.goods-img {
position: relative;
width: 200rpx;
height: 200rpx;
// overflow: hidden;
border-radius: $border-radius;
margin-right: 20rpx;
overflow: hidden;
image {
width: 200rpx;
height: 200rpx;
}
}
.goods-tag {
color: #fff;
line-height: 1;
padding: 8rpx 12rpx;
position: absolute;
border-top-left-radius: $border-radius;
border-bottom-right-radius: $border-radius;
top: 0;
left: 0;
font-size: $font-size-goods-tag;
}
.goods-tag-img {
position: absolute;
border-top-left-radius: $border-radius;
width: 80rpx;
height: 80rpx;
top: 26rpx;
left: 26rpx;
z-index: 5;
overflow: hidden;
image {
width: 100%;
height: 100%;
}
}
.info-wrap {
flex: 1;
display: flex;
flex-direction: column;
}
.name-wrap {
flex: 1;
}
.goods-name {
font-size: $font-size-base;
line-height: 1.3;
overflow: hidden;
text-overflow: ellipsis;
display: -webkit-box;
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
}
.introduction {
line-height: 1;
margin-top: 10rpx;
}
.discount-price {
display: inline-block;
font-weight: bold;
line-height: 1;
margin-top: 16rpx;
.unit {
margin-right: 6rpx;
color: var(--price-color);
}
.price {
color: var(--price-color);
}
}
.pro-info {
display: flex;
margin-top: auto;
align-items: center;
position: relative;
.delete-price {
text-decoration: line-through;
font-size: $font-size-tag !important;
flex: 1;
.unit {
margin-right: 0;
}
}
.block-wrap {
flex: 1;
line-height: 1;
margin-right: 20rpx;
.sale {
font-size: $font-size-tag !important;
}
}
}
.member-price-tag {
display: inline-block;
width: 60rpx;
line-height: 1;
margin-left: 6rpx;
image {
width: 100%;
display: flex;
max-height: 30rpx;
}
}
.sell-out{
position: absolute;
z-index: 1;
width: 100%;
height: 100%;
top: 0;
left: 0;
display: flex;
align-items: center;
justify-content: center;
background: rgba(0, 0, 0, 0.5);
text{
color: #fff;
font-size: 150rpx;
}
}
}
}
// 商品列表双列样式
.goods-list.double-column {
display: none;
margin: 0 24rpx;
padding-top: $margin-updown;
position: relative;
flex-wrap: wrap;
justify-content: space-between;
&.show {
display: flex;
}
.goods-item {
display: flex;
flex-direction: column;
width: calc(50% - 10rpx);
border-radius: $border-radius;
overflow: hidden;
background-color: #fff;
&:nth-child(2n + 2) {
margin-right: 0;
}
.goods-img {
position: relative;
overflow: hidden;
padding-top: 100%;
border-top-left-radius: $border-radius;
border-top-right-radius: $border-radius;
image {
width: 100%;
position: absolute !important;
top: 50%;
left: 0;
transform: translateY(-50%);
}
}
.goods-tag {
color: #fff;
line-height: 1;
padding: 8rpx 16rpx;
position: absolute;
border-bottom-right-radius: $border-radius;
top: 0;
left: 0;
font-size: $font-size-goods-tag;
}
.goods-tag-img {
position: absolute;
border-top-left-radius: $border-radius;
width: 80rpx;
height: 80rpx;
top: 0;
left: 0;
z-index: 5;
overflow: hidden;
image {
width: 100%;
height: 100%;
}
}
.info-wrap {
padding: 20rpx;
display: flex;
flex-direction: column;
flex: 1;
}
.goods-name {
font-size: $font-size-base;
line-height: 1.3;
margin-top: 20rpx;
}
.lineheight-clear {
margin-top: 16rpx;
}
.discount-price {
display: inline-block;
font-weight: bold;
line-height: 1;
.unit {
margin-right: 6rpx;
color: var(--price-color);
}
.price {
color: var(--price-color);
}
}
.pro-info {
display: flex;
margin-top: auto;
align-items: center;
.block-wrap {
flex: 1;
line-height: 1;
margin-right: 20rpx;
.sale {
font-size: $font-size-tag !important;
}
}
}
.delete-price {
// display: inline-block;
// margin-left: 6rpx;
// float: right;
.unit {
margin-right: 6rpx;
}
text {
line-height: 1;
font-size: $font-size-tag !important;
}
}
.member-price-tag {
display: inline-block;
width: 60rpx;
line-height: 1;
margin-left: 6rpx;
image {
width: 100%;
}
}
.sell-out{
position: absolute;
z-index: 1;
width: 100%;
height: 100%;
top: 0;
left: 0;
display: flex;
align-items: center;
justify-content: center;
background: rgba(0, 0, 0, 0.5);
text{
color: #fff;
font-size: 250rpx;
}
}
}
}
.cart-action-wrap {
position: relative;
.shopping-cart-btn {
font-size: 36rpx;
border: 2rpx solid $base-color;
border-radius: 50%;
padding: 10rpx;
color: $base-color;
width: 36rpx;
height: 36rpx;
text-align: center;
line-height: 36rpx;
}
.plus-sign-btn {
font-size: 36rpx;
border: 2rpx solid $base-color;
border-radius: 50%;
padding: 10rpx;
color: $base-color;
width: 36rpx;
height: 36rpx;
text-align: center;
line-height: 36rpx;
}
.buy-btn {
background-color: $base-color;
color: var(--btn-text-color);
border-radius: 50rpx;
font-size: $font-size-tag;
padding: 12rpx 30rpx;
line-height: 1;
}
.icon-diy {
font-size: 80rpx;
}
}

View File

@@ -0,0 +1,599 @@
export default {
data() {
return {
cartData: [], // 购物车
checkAll: true,
totalPrice: '0.00',
totalCount: 0,
isSub: false,
invalidGoods: [], // 失效商品集合
isIphoneX: false, //判断手机是否是iphoneX以上,
isAction: false, // 是否操作删除
goodsSkuDetail: null,
discount: {},
manjian: {},
receiveSub: false,
discountPopupShow: false,
startX: '', // 触摸开始位置
endX: '', // 触摸结束位置
refresherTriggered: false, // 设置当前下拉刷新状态true 表示下拉刷新已经被触发false 表示下拉刷新未被触发
timeout: {}
};
},
onLoad() {
uni.hideTabBar();
this.isIphoneX = this.$util.uniappIsIPhoneX();
},
onShow() {
if (this.storeToken) {
this.getCartData();
} else {
this.cartData = [];
this.invalidGoods = [];
this.calculationTotalPrice();
}
},
onHide() {
this.isAction = false;
},
onUnload() {
if (!this.storeToken && this.$refs.login) this.$refs.login.cancelCompleteInfo();
},
onReady() {
if (!this.storeToken) {
if (this.$refs.loadingCover) this.$refs.loadingCover.hide();
}
},
computed: {
hasData() {
return this.cartData.length > 0 || this.invalidGoods.length > 0;
}
},
methods: {
initNum(item) {
let max_buy = item.max_buy > 0 && item.max_buy < item.stock ? item.max_buy : item.stock;
max_buy = max_buy == 0 ? 1 : max_buy;
if (item.num > max_buy) return max_buy;
return item.num;
},
/**
* 获取购物车数据
*/
getCartData() {
this.$api.sendRequest({
url: '/api/cart/goodslists',
success: res => {
if (res.code >= 0) {
if (res.data.length) this.handleCartData(res.data);
else this.cartData = [];
}
this.refresherTriggered = false;
if (this.$refs.loadingCover) this.$refs.loadingCover.hide();
},
fail: res => {
if (this.$refs.loadingCover) this.$refs.loadingCover.hide();
}
});
},
/**
* 处理购物车数据结构
*/
handleCartData(data) {
this.invalidGoods = [];
this.cartData = [];
var temp = {};
data.forEach((item, index) => {
if (item.goods_state == 1) {
if (item.store_goods_status != undefined && item.store_goods_status != 1) {
this.invalidGoods.push(item);
} else if (item.min_buy > 0 && item.min_buy > item.stock) {
// 如果最小限购超出库存则该商品失效
this.invalidGoods.push(item);
} else {
item.checked = true;
item.edit = false;
if (temp['site_' + item.site_id] != undefined) {
temp['site_' + item.site_id].cartList.push(item);
} else {
temp['site_' + item.site_id] = {
siteId: item.site_id,
siteName: item.site_name,
edit: false,
checked: true,
cartList: [item]
};
}
}
} else {
this.invalidGoods.push(item);
}
});
this.cartData = [];
Object.keys(temp).forEach(key => {
this.cartData.push(temp[key]);
});
this.calculationTotalPrice();
if (this.cartData.length) {
this.cartData[0].cartList.forEach(v => {
if (v.sku_spec_format) {
v.sku_spec_format = JSON.parse(v.sku_spec_format);
} else {
v.sku_spec_format = [];
}
});
}
if (this.invalidGoods.length) {
this.invalidGoods.forEach(v => {
if (v.sku_spec_format) {
v.sku_spec_format = JSON.parse(v.sku_spec_format);
} else {
v.sku_spec_format = [];
}
});
}
},
/**
* 单选
* @param siteIndex
* @param index
*/
singleElection(siteIndex, index) {
this.cartData[siteIndex].cartList[index].checked = !this.cartData[siteIndex].cartList[index].checked;
this.calculationTotalPrice();
},
/**
* 店铺全选
* @param checked
* @param index
*/
siteAllElection(checked, index) {
this.cartData[index].checked = checked;
this.cartData[index].cartList.forEach(item => {
item.checked = checked;
});
this.calculationTotalPrice();
},
/**
* 全选
*/
allElection(checked) {
if (typeof checked == 'boolean') {
this.checkAll = checked;
} else {
this.checkAll = !this.checkAll;
}
if (this.cartData.length) {
this.cartData.forEach(siteItem => {
siteItem.checked = this.checkAll;
siteItem.cartList.forEach(item => {
item.checked = this.checkAll;
});
});
}
this.calculationTotalPrice();
},
/**
* 计算购物车总价
*/
calculationTotalPrice() {
if (this.cartData.length) {
let totalPrice = 0,
totalCount = 0,
siteAllElectionCount = 0;
this.cartData.forEach(siteItem => {
let siteGoodsCount = 0;
siteItem.cartList.forEach(item => {
if (item.checked) {
siteGoodsCount += 1;
totalCount += parseInt(item.num);
if (Number(item.member_price) > 0 && Number(item.member_price) < Number(item.discount_price)) {
totalPrice += item.member_price * item.num;
} else {
totalPrice += item.discount_price * item.num;
}
}
});
if (siteItem.cartList.length == siteGoodsCount) {
siteItem.checked = true;
siteAllElectionCount += 1;
} else {
siteItem.checked = false;
}
});
this.totalPrice = totalPrice.toFixed(2);
this.totalCount = totalCount;
this.checkAll = this.cartData.length == siteAllElectionCount;
} else {
this.totalPrice = '0.00';
this.totalCount = 0;
}
this.discountCalculate();
},
/**
* 删除购物车
* @param tag
* @param siteIndex
* @param cartIndex
*/
deleteCart(tag, siteIndex, cartIndex) {
var cart_id = [];
if (tag == 'all') {
for (let i = 0; i < this.cartData.length; i++) {
for (let j = 0; j < this.cartData[i].cartList.length; j++) {
if (this.cartData[i].cartList[j].checked) cart_id.push(this.cartData[i].cartList[j].cart_id);
}
}
} else {
cart_id.push(this.cartData[siteIndex].cartList[cartIndex].cart_id);
}
if (cart_id.length == 0) {
this.$util.showToast({
title: '请选择要删除的商品'
});
return;
}
uni.showModal({
title: '提示',
content: cart_id.length > 1 ? '确定要删除这些商品吗?' : '确定要删除该商品吗?',
success: res => {
if (res.confirm) {
cart_id = cart_id.toString();
this.$api.sendRequest({
url: '/api/cart/delete',
data: {
cart_id
},
success: res => {
if (res.code >= 0) {
if (tag == 'all') {
// 全选
for (var i = 0; i < this.cartData.length; i++) {
for (var j = 0; j < this.cartData[i].cartList.length; j++) {
var item = this.cartData[i].cartList[j];
if (item.checked) {
this.cartData[i].cartList.splice(j, 1);
j = -1;
}
}
if (this.cartData[i].cartList.length == 0) {
this.cartData.splice(i, 1);
i = -1;
}
}
this.$store.dispatch('emptyCart');
} else {
let item = this.cartData[siteIndex].cartList;
let goods_id = item[cartIndex].goods_id;
let sku_id = item[cartIndex].sku_id;
delete this.cartList['goods_' + goods_id]['sku_' + sku_id];
if (Object.keys(this.cartList['goods_' + goods_id]).length == 2) {
delete this.cartList['goods_' + goods_id];
}
this.$store.dispatch('cartCalculate');
item.splice(cartIndex, 1);
if (item.length == 0) this.cartData.splice(siteIndex, 1);
}
this.resetEditStatus();
this.calculationTotalPrice();
} else {
this.$util.showToast({
title: res.message
});
}
}
});
}
}
});
},
/**
* 变更购物车数量
* @param {Object} params
*/
cartNumChange(num, params) {
if (isNaN(num)) return;
let data = this.cartData[params.siteIndex].cartList[params.cartIndex],
max_buy = data.is_limit && data.max_buy > 0 && data.max_buy < data.stock ? data.max_buy : data.stock,
min_buy = data.min_buy > 0 ? data.min_buy : 1;
if (num > max_buy) num = max_buy;
if (num < min_buy) num = min_buy;
let cartId = this.cartData[params.siteIndex].cartList[params.cartIndex].cart_id
if (this.timeout[cartId]) clearTimeout(this.timeout[cartId])
this.timeout[cartId] = setTimeout(() => {
this.$api.sendRequest({
url: '/api/cart/edit',
data: {
num,
cart_id: cartId
},
success: res => {
if (res.code >= 0) {
let item = this.cartData[params.siteIndex].cartList[params.cartIndex];
let goods_id = item.goods_id;
let sku_id = item.sku_id;
item.num = num;
this.cartList['goods_' + goods_id]['sku_' + sku_id].num = num;
this.$store.dispatch('cartCalculate');
this.resetEditStatus();
this.calculationTotalPrice();
} else {
this.$util.showToast({
title: res.message
});
}
}
});
}, 800)
},
/**
* 结算
*/
settlement() {
if (this.totalCount > 0) {
let cart_ids = [];
this.cartData.forEach(siteItem => {
siteItem.cartList.forEach(item => {
if (item.checked) {
cart_ids.push(item.cart_id);
}
});
});
if (this.discount.coupon_info && this.discount.coupon_info.receive_type == 'wait') this.receiveCoupon(
this.discount.coupon_info.coupon_type_id, false);
if (this.isSub) return;
this.isSub = true;
uni.removeStorageSync('delivery');
uni.setStorage({
key: 'orderCreateData',
data: {
cart_ids: cart_ids.toString()
},
success: () => {
this.$util.redirectTo('/pages/order/payment');
this.isSub = false;
}
});
}
},
/**
* 清空失效商品
*/
clearInvalidGoods() {
uni.showModal({
title: '提示',
content: '确定要清空这些商品吗?',
success: res => {
if (res.confirm) {
var cart_ids = [];
this.invalidGoods.forEach(goodsItem => {
cart_ids.push(goodsItem.cart_id);
});
if (cart_ids.length) {
this.$api.sendRequest({
url: '/api/cart/delete',
data: {
cart_id: cart_ids.toString()
},
success: res => {
if (res.code >= 0) {
this.invalidGoods = [];
this.refreshCartNumber();
} else {
this.$util.showToast({
title: res.message
});
}
}
});
}
}
}
});
},
imageError(siteIndex, cartIndex) {
this.cartData[siteIndex].cartList[cartIndex].sku_image = this.$util.getDefaultImage().goods;
this.$forceUpdate();
},
toGoodsDetail(item) {
this.$util.redirectTo('/pages/goods/detail', {
sku_id: item.sku_id
});
},
// 购物车数量
refreshCartNumber() {
if (this.storeToken) {
this.$store.dispatch('getCartNumber');
this.resetEditStatus();
}
},
goodsLimit(event, params) {
let data = this.cartData[params.siteIndex].cartList[params.cartIndex];
if (event.type == 'plus') {
if (data.max_buy > 0 && data.max_buy < data.stock) {
this.$util.showToast({
title: '该商品每人限购' + data.max_buy + '件'
});
} else {
this.$util.showToast({
title: '库存不足'
});
}
} else {
// 数量减至最少时,则删除商品
this.deleteCart('single', params.siteIndex, params.cartIndex);
// this.$util.showToast({
// title: '最少购买' + event.value + '件'
// });
}
},
toLogin() {
this.$refs.login.open();
},
// 重置编辑状态
resetEditStatus() {
if (this.cartData.length) {
for (var i = 0; i < this.cartData[0].cartList.length; i++) {
this.cartData[0].cartList[i].edit = false;
}
this.$forceUpdate();
}
},
changeAction() {
this.isAction = !this.isAction;
this.resetEditStatus();
},
selectSku(data) {
let goodsSkuDetail = this.$util.deepClone(data);
if (goodsSkuDetail.goods_spec_format) goodsSkuDetail.goods_spec_format = JSON.parse(goodsSkuDetail.goods_spec_format);
this.goodsSkuDetail = goodsSkuDetail;
this.$nextTick(() => {
this.$refs.selectSku.show('confirm', (sku_id, num) => {
this.$api.sendRequest({
url: '/api/cart/editcartsku',
data: {
cart_id: data.cart_id,
sku_id: sku_id,
num: num
},
success: res => {
if (res.code >= 0) {
this.invalidGoods = [];
this.getCartData();
this.refreshCartNumber();
} else {
this.$util.showToast({
title: res.message
});
}
}
});
}, this.goodsSkuDetail);
})
},
toggleDiscountPopup() {
if (this.$refs.discountPopup.showPopup) this.$refs.discountPopup.close();
else this.$refs.discountPopup.open();
this.discountPopupShow = !this.discountPopupShow;
},
/**
* 优惠信息计算
*/
discountCalculate() {
if (this.cartData.length == 0) return;
let skuIds = [];
this.cartData.forEach(siteItem => {
siteItem.cartList.forEach(item => {
if (item.checked) {
skuIds.push({
sku_id: item.sku_id,
num: item.num
});
}
});
});
if (skuIds.length == 0) {
this.discount = {};
return;
}
this.$api.sendRequest({
url: '/api/cartcalculate/calculate',
data: {
sku_ids: JSON.stringify(skuIds)
},
success: res => {
if (res.code >= 0 && res.data && (res.data.coupon_money > 0 || res.data.promotion_money > 0)) {
this.discount = res.data;
let manjian = {};
res.data.goods_list.forEach(item => {
if (item.promotion && item.promotion.manjian) {
manjian['sku_' + item.sku_id] = JSON.parse(item.promotion.manjian.rule_json);
}
})
Object.assign(this.manjian, manjian);
this.refresherTriggered = false;
} else {
this.discount = {};
}
}
})
},
/**
* 领取优惠券
* tips 失败时是否提示
* @param {Object} couponTypeId
*/
receiveCoupon(couponTypeId, tips = true) {
if (this.receiveSub) return;
this.receiveSub = true;
this.$api.sendRequest({
url: '/coupon/api/coupon/receive',
data: {
coupon_type_id: couponTypeId,
get_type: 2 //获取方式:1订单2.直接领取3.活动领取
},
success: res => {
if (res.code == 0) {
this.$set(this.discount.coupon_info, 'receive_type', '');
} else {
if (tips) this.$util.showToast({
title: res.message
});
this.receiveSub = false;
}
}
});
},
// 手指触摸事件 用于菜单左滑
touchS(e) {
this.startX = e.touches[0].clientX;
// console.log('开始' + e.touches[0].clientX);
},
touchE(e, cartIndex) {
this.endX = e.changedTouches[0].clientX;
// 触摸开始到停止的差值小于0左滑大于0右滑
var disX = this.startX - this.endX;
// cartIndex.edit = disX > 50;
if (disX > 50) cartIndex.edit = true;
else if (disX < 0) cartIndex.edit = false;
this.$forceUpdate();
},
moneyFormat(money) {
if (isNaN(parseFloat(money))) return money;
return parseFloat(money).toFixed(2);
},
refreshSkuDetail(goodsSkuDetail) {
this.goodsSkuDetail = goodsSkuDetail;
},
onRefresh(e) {
this.refresherTriggered = true;
if (this.storeToken) {
this.getCartData();
this.refreshCartNumber();
} else {
this.cartData = [];
this.invalidGoods = [];
this.calculationTotalPrice();
}
}
},
}

View File

@@ -0,0 +1,525 @@
export default {
data() {
return {
goodsRoute: '/pages/goods/detail',
couponList: [], //优惠券列表
couponBtnSwitch: false, //获取优惠券防止重复提交
posterApi: '/api/goods/poster',
//满减活动
manjian: {
type: 0,
manjian_name: "",
rule_json: null
},
//组合套餐
bundlingType: false,
bundling: [{
bundling_goods: {
bl_name: '',
sku_image: ''
}
}],
membercard: null, // 会员卡信息
hackReset: true,
cardOff: false,
informationform:[]//留言表单
}
},
computed: {
showDiscount() {
var flag = false;
if (
this.preview == 0 &&
this.addonIsExist.discount &&
this.goodsSkuDetail.promotion_type == 1 &&
this.goodsSkuDetail.discountTimeMachine &&
(!this.goodsSkuDetail.member_price || (this.goodsSkuDetail.member_price > 0 && Number(this.goodsSkuDetail.member_price) > Number(this.goodsSkuDetail.discount_price))
)
) {
flag = true;
}
return flag;
},
memberCardDiscount() {
let discount = 0,
showPrice = this.goodsSkuDetail.member_price > 0 && Number(this.goodsSkuDetail.member_price) < Number(this.goodsSkuDetail.discount_price) ? this.goodsSkuDetail.member_price : this.goodsSkuDetail.discount_price;
if (this.membercard && this.membercard.member_price > 0 && (parseFloat(showPrice) > parseFloat(this.membercard.member_price))) {
discount = parseFloat(showPrice) - parseFloat(this.membercard.member_price);
}
return discount.toFixed(2);
},
//表单高度
FormHeight(){
let height = 48;
if (this.goodsForm && this.goodsForm.length) {
height += this.goodsForm.length * 5;
}
height += 'vh';
return height;
}
},
onLoad(data) {
// #ifdef MP-ALIPAY
let options = my.getLaunchOptionsSync();
options.query && Object.assign(data, options.query)
// #endif
this.skuId = data.sku_id || 0;
this.goodsId = data.goods_id || 0;
// 小程序扫码进入
if (data.scene) {
var sceneParams = decodeURIComponent(data.scene);
sceneParams = sceneParams.split('&');
if (sceneParams.length) {
sceneParams.forEach(item => {
if (item.indexOf('goods_id') != -1) this.goodsId = item.split('-')[1];
});
}
}
// #ifdef MP-WEIXIN
this.getShareImg();
// #endif
},
async onShow() {
//同步获取商品详情
await this.getGoodsSkuDetail();
},
onHide() {
this.couponBtnSwitch = false;
},
methods: {
//拨打电话
phoneClick(mobile){
uni.makePhoneCall({
phoneNumber: mobile+'',
success(){},
fail(){}
})
},
setSkuId(val) {
if (val) {
this.skuId = val;
this.getBundling();
}
},
// 获取商品详情
async getGoodsSkuDetail() {
let res = await this.$api.sendRequest({
url: '/api/goodssku/detail',
async: false,
data: {
sku_id: this.skuId,
goods_id: this.goodsId,
}
});
let data = res.data;
if (data.goods_sku_detail != null) {
if (data.goods_sku_detail.promotion_type == 'presale' && data.goods_sku_detail.presale_id) {
this.$util.redirectTo('/pages_promotion/presale/detail', {
id: data.goods_sku_detail.presale_id,
sku_id: this.skuId
}, 'reLaunch');
return;
}
if(uni.getStorageSync('lang') == 'en-us') data.goods_sku_detail.goods_name = data.goods_sku_detail.en_goods_name
this.goodsSkuDetail = data.goods_sku_detail;
if (!this.skuId) this.skuId = this.goodsSkuDetail.sku_id;
if (!this.goodsId) this.goodsId = this.goodsSkuDetail.goods_id;
// 分享参数、链接
this.shareQuery = 'goods_id=' + this.goodsSkuDetail.goods_id;
this.shareUrl = this.goodsRoute + '?' + this.shareQuery;
// 在线客服聊天参数
this.chatRoomParams = {
sku_id: this.goodsSkuDetail.sku_id
};
let typeId = this.goodsSkuDetail.goods_promotion[0];
if (typeId) {
// 限时折扣
if (typeId.discount_id) {
this.chatRoomParams.type = 'discount'
this.chatRoomParams.type_id = typeId.discount_id
}
}
// 海报参数
this.posterParams = {
goods_id: this.goodsId
};
// 处理商品数据
this.handleGoodsSkuData();
// 限时折扣
if (this.goodsSkuDetail.promotion_type == 1 && this.addonIsExist.discount) {
//检测倒计时
if ((this.goodsSkuDetail.end_time - res.timestamp) > 0) {
this.goodsSkuDetail.discountTimeMachine = this.$util.countDown(this.goodsSkuDetail.end_time - res.timestamp);
} else {
this.goodsSkuDetail.promotion_type = 0;
}
}
if (this.goodsSkuDetail.promotion_type == 1 && this.goodsSkuDetail.discountTimeMachine) {
if (this.goodsSkuDetail.member_price > 0 && Number(this.goodsSkuDetail.member_price) <= Number(this.goodsSkuDetail.discount_price)) {
this.goodsSkuDetail.show_price = this.goodsSkuDetail.member_price;
} else {
this.goodsSkuDetail.show_price = this.goodsSkuDetail.discount_price;
}
} else {
if (this.goodsSkuDetail.member_price > 0) {
this.goodsSkuDetail.show_price = this.goodsSkuDetail.member_price;
} else {
this.goodsSkuDetail.show_price = this.goodsSkuDetail.price;
}
}
// 满减
if (this.goodsSkuDetail.manjian) {
this.getManjian(this.goodsSkuDetail.manjian);
}
// 会员卡
if (this.goodsSkuDetail.membercard) {
this.membercard = this.goodsSkuDetail.membercard;
}
// 优惠券
if (this.goodsSkuDetail.coupon_list) {
this.couponList = this.goodsSkuDetail.coupon_list;
this.couponList.forEach(v => {
if (v.count == v.lead_count) v.useState = 2;
else if (v.max_fetch != 0 && v.member_coupon_num && v.member_coupon_num >= v.max_fetch) v.useState = 1;
else v.useState = 0;
});
this.couponList = this.couponList.sort(this.sortBy('useState'))
}
// 组合套餐
// if (this.goodsSkuDetail.bundling_list) {
// this.handleBundlingData(this.goodsSkuDetail.bundling_list);
// }
if (this.$refs.loadingCover) this.$refs.loadingCover.hide();
} else {
this.$util.redirectTo('/pages_tool/goods/not_exist', {}, 'redirectTo');
}
},
choiceSku() {
this.$refs.goodsSku.show("buy_now", () => {
this.$store.dispatch('getCartNumber');
});
},
//商品留言打开
showinformation(){
this.informationform = this.goodsSkuDetail.goods_form
this.$refs.informationPopup.open();
},
//商品留言关闭
closeinformationPopup(){
this.$refs.informationPopup.close();
},
//保存商品留言
saveubfirnation(){
//缺少
if (!this.$refs.form.verify()) return;
// uni.setStorageSync('goodFormData', {
// goods_id: this.goodsSkuDetail.goods_id,
// form_data: this.$refs.form.formData
// });
this.$api.sendRequest({
url: '/api/goods/information',
data: {
goods_id: this.goodsSkuDetail.goods_id,
form_data: JSON.stringify(this.$refs.form.formData)
},
success: res => {
var data = res.data;
if (res.code == 0) {
}else{
this.$util.showToast({
title: res.msg
});
}
},
});
},
// 加入购物车
joinCart() {
if (!this.storeToken && this.preview == 0) {
this.$refs.login.open(this.shareUrl);
return;
}
if (this.goodsSkuDetail.is_virtual == 1) {
this.$refs.goodsSku.show("buy_now", () => {
this.$store.dispatch('getCartNumber');
});
} else {
this.$refs.goodsSku.show("join_cart", () => {
this.$store.dispatch('getCartNumber');
});
}
},
// 立即购买
buyNow() {
if (!this.storeToken && this.preview == 0) {
this.$refs.login.open(this.shareUrl);
return;
}
this.$refs.goodsSku.show("buy_now", () => {
});
},
sortBy(field) {
//根据传过来的字段进行排序,y-x 得分从高到低x-y 从低到高
return (y, x) => {
return y[field] - x[field]
}
},
// 打开优惠券弹出层
openCouponPopup() {
this.$refs.couponPopup.open();
},
// 关闭优惠券弹出层
closeCouponPopup() {
this.$refs.couponPopup.close();
},
// 领取优惠券
receiveCoupon(item) {
let that = this;
if (this.preview) return; // 开启预览,禁止任何操作和跳转
if (this.couponBtnSwitch) return;
this.couponBtnSwitch = true;
if (this.storeToken) {
this.$api.sendRequest({
url: '/coupon/api/coupon/receive',
data: {
coupon_type_id: item.coupon_type_id,
get_type: 2 //获取方式:1订单2.直接领取3.活动领取
},
success: res => {
var data = res.data;
let msg = '';
let list = this.couponList;
if (res.data.is_exist == 1 && res.code < 0) {
msg = '您已领取过该优惠券,快去使用吧';
} else if (res.code == 0) {
msg = '领取成功,快去使用吧';
} else {
msg = res.message;
}
if (res.data.is_exist == 1) {
for (let i = 0; i < list.length; i++) {
if (list[i].coupon_type_id == item.coupon_type_id) {
that.$set(that.couponList[i], 'useState', 1);
}
}
} else {
for (let i = 0; i < list.length; i++) {
if (list[i].coupon_type_id == item.coupon_type_id) {
that.$set(that.couponList[i], 'useState', 2);
}
}
}
this.$util.showToast({
title: msg
});
that.$forceUpdate()
this.hackReset = false;
this.$nextTick(() => {
this.hackReset = true;
})
this.couponBtnSwitch = false;
},
});
} else {
this.$refs.login.open(this.shareUrl);
this.couponBtnSwitch = false;
}
},
//-------------------------------------满减-------------------------------------
//获取满减信息
getManjian(data) {
this.manjian = data;
let limit = data.type == 0 ? '元' : '件';
Object.keys(data.rule_json).forEach((key) => {
var item = data.rule_json[key];
if (item.coupon_data) {
for (var i = 0; i < item.coupon_data.length; i++) {
item.coupon_data[i].coupon_num = item.coupon_num[i]
}
}
item.limit = data.type == 0 ? parseFloat(item.limit).toFixed(2) : parseInt(item.limit);
// 满减
if (item.discount_money != undefined) {
if (this.manjian.manjian == undefined) {
this.manjian.manjian = '满' + item.limit + limit + '减' + item.discount_money + '元';
} else {
this.manjian.manjian += ';满' + item.limit + limit + '减' + item.discount_money + '元';
}
}
// 满送
if (item.point != undefined || item.coupon != undefined) {
let text = '';
if (item.point != undefined) {
text = '送' + item.point + '积分';
}
if (item.coupon != undefined && item.coupon_data != undefined) {
item.coupon_data.forEach((couponItem, couponIndex) => {
if (couponItem.type == 'discount') {
if (text == '') text = '送' + item.coupon_num[couponIndex] + '张' + parseFloat(couponItem.discount) + '折优惠券';
else text += '、送' + item.coupon_num[couponIndex] + '张' + parseFloat(couponItem.discount) + '折优惠券';
} else {
if (text == '') text = '送' + item.coupon_num[couponIndex] + '张' + parseFloat(couponItem.money) + '元优惠券';
else text += '、送' + item.coupon_num[couponIndex] + '张' + parseFloat(couponItem.money) + '元优惠券';
}
})
}
if (this.manjian.mansong == undefined) {
this.manjian.mansong = '满' + item.limit + limit + text;
} else {
this.manjian.mansong += '' + '满' + item.limit + limit + text;
}
}
// 包邮
if (item.free_shipping != undefined) {
if (this.manjian.free_shipping == undefined) {
this.manjian.free_shipping = '满' + item.limit + limit + '包邮';
} else {
this.manjian.free_shipping += ';满' + item.limit + limit + '包邮';
}
}
});
},
openManjianPopup() {
this.$refs.manjianPopup.open();
},
closeManjianPopup() {
this.$refs.manjianPopup.close();
},
//-------------------------------------组合套餐-------------------------------------
//获取当前商品关联的组合套餐
getBundling() {
// 连锁门店没有营销活动
if (this.globalStoreConfig && this.globalStoreConfig.store_business == 'store') return;
this.$api.sendRequest({
url: "/bundling/api/bundling/lists",
data: {
sku_id: this.skuId
},
success: res => {
// this.handleBundlingData(res.data);
}
});
},
handleBundlingData(data) {
this.bundling = data;
if (this.bundling.length) {
for (var i = 0; i < this.bundling[0].bundling_goods.length; i++) {
if (this.bundling[0].bundling_goods[i].sku_id == this.skuId) {
this.bundlingType = true;
break;
} else {
this.bundlingType = false;
}
}
for (var i = 0; i < this.bundling.length; i++) {
for (var j = 0; j < this.bundling[i].bundling_goods.length; j++) {
if (this.bundling[i].bundling_goods[j].sku_id == this.skuId) {
this.bundling[i].bundling_goods.splice(j, 1);
}
}
}
}
},
// 打开组合套餐弹出层
openBundlingPopup() {
this.$refs.bundlingPopup.open();
},
// 关闭组合套餐弹出层
closeBundlingPopup() {
this.$refs.bundlingPopup.close();
},
imageError() {
this.goodsSkuDetail.sku_image = this.$util.getDefaultImage().goods;
this.$forceUpdate();
},
bundlingImageError(index, goods_index) {
this.bundling[index].bundling_goods[goods_index].sku_image = this.$util.getDefaultImage().goods;
this.$forceUpdate();
},
fenxiao() {
this.$refs.fenxiaoPopup.show()
},
toGoodsDetail(item) {
this.$util.redirectTo(this.goodsRoute, {
sku_id: item
});
},
toComoDetail(id) {
this.$util.redirectTo('/pages_promotion/bundling/detail', {
bl_id: id
});
},
/**
* 获取分享图
*/
getShareImg() {
let posterParams = {
goods_id: this.goodsId
};
this.$api.sendRequest({
url: '/api/goods/shareimg',
data: {
qrcode_param: JSON.stringify(posterParams)
},
success: res => {
if (res.code == 0) this.shareImg = res.data.path + '?no=' + parseInt((new Date()).getTime() / 1000);
}
})
},
/**
* 金额格式化输出
* @param {Object} money
*/
decimalPointFormat(money) {
if (isNaN(parseFloat(money))) return money;
let arr = money.toString().split(".");
let arr1 = arr[1].split("").reverse();
let arr2 = [];
arr1.forEach((item, index) => {
if (item > 1) {
arr2 = arr1.splice(index);
}
});
let str = arr2.length ? (arr[0] + "." + arr2.reverse().join("")) : arr[0];
return str;
}
}
}

View File

@@ -0,0 +1,467 @@
export default {
data() {
return {
listStyle: '',
loadingType: 'loading', //加载更多状态
orderType: '',
priceOrder: 'desc', //1 价格从低到高 2价格从高到低
categoryList: [], //排序类型
goodsList: [],
order: '',
sort: 'desc',
showScreen: false,
keyword: '',
categoryId: 0,
minPrice: '',
maxPrice: '',
isFreeShipping: false, //是否免邮
isIphoneX: false,
coupon: 0,
emptyShow: false,
isList: true, //列表样式
//分享所需标题
share_title: '',
//搜索到多少件商品
count: 0,
//当前分类名称
category_title: '',
//优惠券数据
coupon_name: '',
//列表瀑布流数据
listHeight: [],
listPosition: [],
debounce: null,
brandId: 0,
brandList: [], //品牌筛选项
config: {
fontWeight: false,
padding: 0,
cartEvent: "detail",
text: "购买",
textColor: "#FFFFFF",
theme: "default",
aroundRadius: 25,
control: true,
bgColor: "#FF6A00",
style: "button",
iconDiy: {
iconType: "icon",
icon: "",
style: {
fontSize: "60",
iconBgColor: [],
iconBgColorDeg: 0,
iconBgImg: "",
bgRadius: 0,
iconColor: [
"#000000"
],
iconColorDeg: 0
}
}
},
langstatus:0,
lang:uni.getStorageSync('lang')
}
},
onLoad(options) {
this.$api.sendRequest({
url: '/api/lucky/status',
data: {},
success: res => {
console.log(res)
this.langstatus = res.status
if(this.langstatus == 1){
// this.$langConfig.refresh();
uni.setNavigationBarTitle({
title:uni.getStorageSync('lang') == 'en-us'?'Goods List':'商品列表'
})
}
}
});
this.categoryId = options.category_id || 0;
this.keyword = options.keyword || '';
this.coupon = options.coupon || 0;
this.goods_id_arr = options.goods_id_arr || 0;
this.brandId = options.brand_id || 0;
this.loadCategoryList(this.categoryId);
this.getBrandList();
this.isIphoneX = this.$util.uniappIsIPhoneX();
//小程序分享接收source_member
if (options.source_member) {
uni.setStorageSync('source_member', options.source_member);
}
// 小程序扫码进入接收source_member
if (options.scene) {
var sceneParams = decodeURIComponent(options.scene);
sceneParams = sceneParams.split('&');
if (sceneParams.length) {
sceneParams.forEach(item => {
if (item.indexOf('sku_id') != -1) this.skuId = item.split('-')[1];
if (item.indexOf('m') != -1) uni.setStorageSync('source_member', item.split('-')[1]);
if (item.indexOf('is_test') != -1) uni.setStorageSync('is_test', 1);
});
}
}
uni.onWindowResize(res => {
if (this.debounce) clearTimeout(this.debounce);
this.waterfallflow(0);
})
},
onShow() {
//记录分享关系
if (this.storeToken && uni.getStorageSync('source_member')) {
this.$util.onSourceMember(uni.getStorageSync('source_member'));
}
},
/**
* 转发分享
*/
onShareAppMessage(res) {
var title = '搜索到' + this.count + '件“' + this.keyword + this.category_title + this.coupon_name + '”相关的优质商品';
let route = this.$util.getCurrentShareRoute(this.memberInfo ? this.memberInfo.member_id : 0);
var path = route.path;
return {
title: title,
path: path,
success: res => {
},
fail: res => {
}
};
},
// 分享到微信朋友圈
onShareTimeline() {
var title = '搜索到' + this.count + '件“' + this.keyword + this.category_title + this.coupon_name + '”相关的优质商品';
let route = this.$util.getCurrentShareRoute(this.memberInfo ? this.memberInfo.member_id : 0);
var query = route.query;
return {
title: title,
query: query,
imageUrl: ''
};
},
methods: {
/**
* 获取优惠券数据
*/
couponInfo(id) {
return new Promise(resolve => {
this.$api.sendRequest({
url: '/coupon/api/coupon/typeinfo',
data: {
coupon_type_id: id
},
success: res => {
if (res.code >= 0) {
resolve(res.data.coupon_name);
}
}
});
})
},
/**
* 获取分类名称
*/
share_select(data, id) {
return new Promise((resolve) => {
data.forEach((item) => {
if (item.category_id == id) {
resolve(item.category_name)
}
if (item.child_list && item.child_list.length > 0) {
item.child_list.forEach((v) => {
if (v.category_id == id) {
resolve(v.category_name)
}
if (v.child_list && v.child_list.length > 0) {
v.forEach((m) => {
if (m.category_id == id) {
resolve(m.category_name)
}
})
}
})
}
})
})
},
//加载分类
loadCategoryList(fid, sid) {
this.$api.sendRequest({
url: '/api/goodscategory/tree',
data: {},
success: res => {
if (res.data != null) {
this.categoryList = res.data
}
}
});
},
getGoodsList(mescroll) {
this.$api.sendRequest({
url: '/api/goodssku/page',
data: {
page: mescroll.num,
page_size: mescroll.size,
keyword: this.keyword,
category_id: this.categoryId,
brand_id: this.brandId,
min_price: this.minPrice,
max_price: this.maxPrice,
is_free_shipping: (this.isFreeShipping ? 1 : 0),
order: this.order,
sort: this.sort,
coupon: this.coupon,
goods_id_arr: this.goods_id_arr
},
success: res => {
let newArr = []
let msg = res.message;
if (res.code == 0 && res.data) {
this.count = res.data.count;
if (res.data.page_count == 0) {
this.emptyShow = true
}
newArr = res.data.list;
newArr = newArr.map(item => {
item.id = this.genNonDuplicate();
return item;
});
} else {
this.$util.showToast({
title: msg
})
}
this.category_title = '';
this.coupon_name = '';
if (res.data.config) this.config = res.data.config;
if (this.categoryId) {
this.share_select(this.categoryList, this.categoryId).then(resolve => {
this.category_title = resolve
});
}
if (this.coupon) {
this.couponInfo(this.coupon).then(resolve => {
this.coupon_name = resolve
});
}
mescroll.endSuccess(newArr.length);
//设置列表数据
if (mescroll.num == 1) this.goodsList = []; //如果是第一页需手动制空列表
this.goodsList = this.goodsList.concat(newArr); //追加新数据
if (this.$refs.loadingCover) this.$refs.loadingCover.hide();
this.waterfallflow((mescroll.num - 1) * 10);
},
fail: res => {
//联网失败的回调
mescroll.endErr();
if (this.$refs.loadingCover) this.$refs.loadingCover.hide();
}
});
},
changeListStyle() {
this.isList = !this.isList;
this.waterfallflow(0);
},
//筛选点击
sortTabClick(tag) {
if (tag == 'sale_num') {
this.order = 'sale_num';
this.sort = 'desc';
} else if (tag == 'discount_price') {
this.order = 'discount_price';
this.sort = 'desc';
} else if (tag == 'screen') {
//筛选
this.showScreen = true;
return;
} else {
this.order = '';
this.sort = '';
}
if (this.orderType === tag && tag !== 'discount_price') return;
this.orderType = tag;
if (tag === 'discount_price') {
this.priceOrder = this.priceOrder === 'asc' ? 'desc' : 'asc';
this.sort = this.priceOrder;
} else {
this.priceOrder = '';
}
this.emptyShow = false;
this.goodsList = [];
this.$refs.mescroll.refresh();
},
//商品详情
toDetail(item) {
this.$util.redirectTo('/pages/goods/detail', {
goods_id: item.goods_id
});
},
search() {
this.emptyShow = false;
this.goodsList = [];
this.$refs.mescroll.refresh();
},
selectedCategory(categoryId) {
this.categoryId = categoryId;
},
screenData() {
if (this.minPrice != '' || this.maxPrice != '') {
// if (!Number(this.minPrice) && this.minPrice) {
// this.$util.showToast({
// title: '请输入最低价'
// });
// return;
// }
if (!Number(this.maxPrice) && this.maxPrice) {
this.$util.showToast({
title: '请输入最高价'
});
return;
}
if (Number(this.minPrice) < 0 || Number(this.maxPrice) < 0) {
this.$util.showToast({
title: '筛选价格不能小于0'
});
return;
}
if (this.minPrice != '' && Number(this.minPrice) > Number(this.maxPrice) && this.maxPrice) {
this.$util.showToast({
title: '最低价不能大于最高价'
});
return;
}
if (this.maxPrice != '' && Number(this.maxPrice) < Number(this.minPrice)) {
this.$util.showToast({
title: '最高价不能小于最低价'
});
return;
}
}
this.emptyShow = false;
this.goodsList = [];
this.$refs.mescroll.refresh();
this.showScreen = false;
},
//重置数据
resetData() {
this.categoryId = 0
this.minPrice = ''
this.maxPrice = ''
this.isFreeShipping = false
},
goodsImg(imgStr) {
let imgs = imgStr.split(',');
return imgs[0] ? this.$util.img(imgs[0], {
size: 'mid'
}) : this.$util.getDefaultImage().goods;
},
imgError(index) {
this.goodsList[index].goods_image = this.$util.getDefaultImage().goods;
},
showPrice(data) {
let price = data.discount_price;
if (data.member_price && parseFloat(data.member_price) < parseFloat(price)) price = data.member_price;
return price;
},
showMarketPrice(item) {
if (item.market_price_show) {
let price = this.showPrice(item);
if (item.market_price > 0) {
return item.market_price;
} else if (parseFloat(item.price) > parseFloat(price)) {
return item.price;
}
}
return '';
},
goodsTag(data) {
return data.label_name || '';
},
/**
* 瀑布流
*/
waterfallflow(start = 0) {
if (!this.isList) {
//页面渲染完成后的事件
this.$nextTick(() => {
setTimeout(() => {
let listHeight = [];
let listPosition = [];
if (start != 0) {
listHeight = this.listHeight;
listPosition = this.listPosition;
}
let column = 2;
const query = uni.createSelectorQuery().in(this);
query.selectAll('.double-column .goods-item').boundingClientRect(data => {
for (let i = start; i < data.length; i++) {
if (i < column) {
let position = {};
position.top = uni.upx2px(20) + 'px';
if (i % column == 0) {
position.left = data[i].width * i + "px";
} else {
position.left = data[i].width * i + (i % column * uni
.upx2px(30)) + "px";
}
listPosition[i] = position;
listHeight[i] = data[i].height + uni.upx2px(20);
} else {
let minHeight = Math.min(...listHeight); // 找到第一列的最小高度
let minIndex = listHeight.findIndex(item => item === minHeight) // 找到最小高度的索引
//设置当前子元素项的位置
let position = {};
position.top = minHeight + uni.upx2px(20) + "px";
position.left = listPosition[minIndex].left;
listPosition[i] = position;
//重新定义数组最小项的高度 进行累加
listHeight[minIndex] += data[i].height + uni.upx2px(20);
}
}
this.listHeight = listHeight;
this.listPosition = listPosition;
}).exec();
}, 50)
})
}
},
getBrandList() {
var data = {
page: 1,
page_size: 0
};
this.$api.sendRequest({
url: '/api/goodsbrand/page',
data: data,
success: res => {
if (res.code == 0 && res.data) {
let data = res.data;
this.brandList = data.list;
}
}
});
},
/**
* 添加购物车回调
*/
addCart(id) {
},
genNonDuplicate(len = 6) {
return Number(Math.random().toString().substr(3, len) + Date.now()).toString(36);
}
}
}