<template> <view> <uni-popup ref="popupRef" type="bottom" @change="changeShow"> <view class="pop"> <scroll-view scroll-y class="scroll"> <view class="image"> <swiper class="swiper" :current="current" autoplay style="width: 100%;height: 100%;" @change="changeCurrent"> <block v-if="product.slider_image && product.slider_image.length>0"> <swiper-item v-for="(item,index) in product.slider_image" :key="index"> <image class="img" :src="item"></image> </swiper-item> </block> <swiper-item v-else> <image class="img" :src="datas.image||defualtImg"></image> </swiper-item> </swiper> <view class="current">{{current+1}}/{{product.slider_image && product.slider_image.length||1}}</view> <image class="close" src="@/static/images/icon/close.png" @click="close()"></image> <view class="border"></view> </view> <view class="white_card"> <view class="flex flex_end"> <block v-if="datas.limited_price"> <view class="price">¥<text class="pro">{{leftPrice2}}.</text>{{rightPrice2}} </view> <view class="price" style="text-decoration: line-through;color: #999;font-weight: 400;font-size: 28rpx;">原价: ¥<text>{{leftPrice}}.</text>{{rightPrice}}</view> </block> <view v-else class="price">¥<text>{{leftPrice}}.</text>{{rightPrice}}</view> <!-- <view>订货价</view> --> </view> <view class="short_name">{{datas.store_name}}</view> <view class="flex"> <view class="shop_name"> <image class="icon" src="@/static/images/icon/short.png"></image> <view>{{datas.merchant.mer_name}}</view> </view> </view> <u-line></u-line> <block name="规格选中" v-for="(att, indexw) in attr" :key="indexw"> <view class="m_title">{{att.attr_name}}</view> <view class="flex" style="flex-wrap: wrap;"> <view class="attr" :class="{'attr_active': item.check}" v-for="(item, indexn) in att.attr_value" :key="indexn" @click="changeAttr(indexw, indexn)"> {{item.attr}} </view> </view> </block> <view class="m_title num"> <view>购买数量</view> <view class="input"> <view class="input_item sub" @click="subCartNum">-</view> <input class="input_item input_view" v-model="cart_num" type="number" @input="inputCartNum" /> <view class="input_item plus" @click="plusCartNum">+</view> </view> </view> <view> 商品库存 <text style="margin-left: 20rpx;">{{(sku[changeSkuKey] && sku[changeSkuKey].stock)||change.stock}}</text> </view> </view> </scroll-view> <view class="button"> <!-- <view class="b_icon" @click="navgoCart()"> <image src="@/static/images/icon/car.png"></image> <view>购物车</view> <view class="badge" v-if="goodsNum">{{goodsNum}}</view> </view> --> <view class="btn" @click.stop="$u.throttle(addcart, 1500)"> {{isBuy?'立即购买':'加入购物车'}} </view> </view> </view> </uni-popup> </view> </template> <script> import { postCartAdd, getProductDetail } from '@/api/store.js'; import { Toast } from '../libs/uniApi'; import { data } from '../uni_modules/uview-ui/libs/mixin/mixin'; export default { name: "shortPopup", props: { source:{ type: Number, default: null }, isBuy: { type: Boolean, default: false } }, data() { return { isShow: false, //当前是否打开弹窗 defualtImg: 'https://lihai001.oss-cn-chengdu.aliyuncs.com/uploads/20230130/00ebcfdf75684f5494c0193075055d1.png', datas: { image: '', store_name: '', merchant: { mer_name: '' }, price: '', }, product: {}, attrValue: [], attr: [], //多级规格 changeSkuKey: '', //多级规格选中的key sku: {}, //规格 sku_key_list: [], //规格名称列表 changeSkuKey: '', //选中的规格名称 change: { stock: '' }, cart_num: 1, //购买数量 goodsNum: 0, //购物车数量 current: 0, //轮播图当前滑块 }; }, mounted() {}, computed:{ leftPrice(){ return this.sku[this.changeSkuKey]?.price?.split('.')[0]||'0'; }, rightPrice(){ return this.sku[this.changeSkuKey]?.price?.split('.')[1]||'00'; }, leftPrice2(){ return this.datas.limited_price.split('.')[0]||'0'; }, rightPrice2(){ return this.datas.limited_price.split('.')[1]||'00'; } }, methods: { // 注入参数, setDatas(datas, goodsNum) { getProductDetail(datas.product_id).then((res)=>{ this.attr = res.data.attr; if(this.attr.length>0) this.attr.forEach((item, index)=>{ this.changeAttr(index, 0); }) else this.changeSkuKey = ''; }) this.goodsNum = goodsNum; this.datas = datas; this.product = datas.product; this.attrValue = datas.product?.attrValue; this.change = this.attrValue[0]; this.cart_num = 1; this.sku = datas.sku||{}; this.sku_key_list = Object.keys(this.sku); }, // 输入购买数量 inputCartNum(e) { if(this.sku){ if (+e.detail.value > this.sku[this.changeSkuKey].stock) { uni.showToast({ icon: 'none', title: '不能超出库存哦' }) this.$nextTick(() => { this.cart_num = this.sku[this.changeSkuKey].stock; }) } }else if (this.change.stock <= this.cart_num) { uni.showToast({ icon: 'none', title: '不能超出库存哦' }) this.$nextTick(() => { this.cart_num = this.change.stock; }) } }, // 减少购买数量 subCartNum() { if (this.cart_num <= 1) { return uni.showToast({ icon: 'none', title: '最少要买一件哦' }) } this.cart_num--; }, // 增加购买数量 plusCartNum() { return Toast('最多购买一件哦'); if(this.sku){ if (this.sku[this.changeSkuKey].stock <= this.cart_num) { return uni.showToast({ icon: 'none', title: '不能超出库存哦' }) } }else if (this.change.stock <= this.cart_num) { return uni.showToast({ icon: 'none', title: '不能超出库存哦' }) } this.cart_num++; }, changeAttr: function(indexw, indexn) { let that = this; this.$set(this.attr[indexw], 'index', this.attr[indexw].attr_values[indexn]); this.attr[indexw].attr_value.forEach((item, index)=>{ if(index==indexn)item.check = true; else item.check = false; }) let value = that.getCheckedValue().join(","); this.changeSkuKey = value; }, //获取被选中属性; getCheckedValue: function() { let productAttr = this.attr; let value = []; for (let i = 0; i < productAttr.length; i++) { for (let j = 0; j < productAttr[i].attr_values.length; j++) { if (productAttr[i].index === productAttr[i].attr_values[j]) { value.push(productAttr[i].attr_values[j]); } } } return value; }, // 加入购物车 addcart() { if (this.sku[this.changeSkuKey]) { if (this.cart_num > this.sku[this.changeSkuKey].stock) return uni.showToast({ icon: 'none', title: '不能超出库存哦' }) let data = { cart_num: this.cart_num, is_new: 0, product_attr_unique: this.sku[this.changeSkuKey].unique, product_id: this.datas.product_id, product_type: this.datas.product_type, source: this.source, spread_id: "", } let that = this let res = postCartAdd({ ...data }).then((res, err) => { if(this.isBuy) return uni.navigateTo({ url: `/pages/users/order_confirm/index?cartId=${res.data.cart_id}&type_id=${this.datas.merchant.type_id}&source=${this.source}` }); uni.showToast({ title: "加入成功", duration: 1000, }) this.$emit('addCart'); this.close(); if(this.isBuy){ this.navgoCart(); } }).catch(err => { uni.showToast({ title: err, icon: "none", duration: 1000, }) }) } else { uni.showToast({ icon: 'none', title: '商品规格不存在' }) } }, // 滑动轮播图 changeCurrent(e){ this.current = e.detail.current; }, navgoCart(url=null) { if(!url) { if(this.source) url = '/pages/order_addcart/order_addcart?source='+this.source; else url = '/pages/order_addcart/order_addcart'; } uni.navigateTo({ url }) }, open() { this.$refs.popupRef.open(); }, close() { this.$refs.popupRef.close(); }, changeShow(e) { this.isShow = e.show; } } } </script> <style lang="scss"> .pop { background-color: #fff; border-radius: 31.54rpx 31.54rpx 0rpx 0rpx; overflow: hidden; position: relative; .scroll{ height: calc(90vh - 150rpx); } .flex_end { align-items: flex-end; } .image { height: 750rpx; width: 750rpx; position: relative; .current{ position: absolute; bottom: 70rpx; left: 30rpx; width: 67rpx; height: 37rpx; background: rgba(#333, 0.2); border-radius: 11rpx 11rpx 11rpx 11rpx; text-align: center; color: #fff; font-size: 26rpx; font-family: PingFang SC-Regular, PingFang SC; font-weight: 400; } .img { width: 100%; height: 100%; border-radius: 31.54rpx 31.54rpx 0rpx 0rpx; overflow: hidden; } .close { position: absolute; top: 30rpx; right: 30rpx; width: 50.82rpx; height: 50.82rpx; } .border { position: absolute; bottom: -1rpx; left: 0; background-color: #fff; height: 40rpx; width: 100%; border-radius: 40rpx 40rpx 0 0; } } .white_card { border-radius: 31.54rpx 31.54rpx 0rpx 0rpx; background-color: #fff; margin: 0 28rpx; padding-bottom: 30rpx; color: #737373; font-size: 26.29rpx; .price { font-size: 35rpx; font-family: SF Pro Display-Semibold, SF Pro Display; font-weight: 600; color: #F84221; padding-right: 30rpx; .pro { font-size: 49.07rpx; } } .short_name { font-size: 33rpx; font-family: PingFang SC-Semibold, PingFang SC; font-weight: 600; color: #333333; } .shop_name { display: flex; background: #FEF5F3; padding: 0 16rpx; border-radius: 26rpx 26rpx 26rpx 26rpx; margin-top: 30rpx; margin-bottom: 20rpx; align-items: center; .icon { width: 31.54rpx; height: 31.54rpx; margin-right: 10rpx; } } .m_title { font-size: 30rpx; font-family: PingFang SC-Medium, PingFang SC; font-weight: 500; color: #333333; margin-top: 31rpx; margin-bottom: 21rpx; } .attr { opacity: 1; border: 1rpx solid #F84221; color: #333333; padding: 15rpx 30rpx; margin-right: 20rpx; height: 63rpx; line-height: 60rpx; border-radius: 63rpx; display: flex; align-items: center; justify-content: center; } .attr_active{ // background-color: #FEF5F3; // color: #F84221; background-color: #F84221; color: #fff; } .num { display: flex; justify-content: space-between; align-items: center; .input { display: flex; align-items: center; height: 48rpx; .input_item { width: 44rpx; height: 44rpx; text-align: center; line-height: 40rpx; border: 2rpx solid #fff; font-size: 26rpx; color: #333; } .input_view { width: 60rpx; } .sub { border: 2rpx solid #FCB9AD; border-radius: 7rpx 0rpx 0rpx 7rpx; background: #FFFFFF; font-size: 26rpx; color: #B3B3B3; } .plus { border: 2rpx solid #FCB9AD; border-radius: 0rpx 7rpx 7rpx 0rpx; background: #FFFFFF; font-size: 26rpx; color: #B3B3B3; } } } } .button { padding: 28rpx; margin-bottom: 28rpx; background-color: #fff; display: flex; justify-content: space-around; padding-bottom: constant(safe-area-inset-bottom); ///兼容 IOS<11.2/ padding-bottom: env(safe-area-inset-bottom); ///兼容 IOS>11.2/ padding-bottom: constant(safe-area-inset-bottom); ///兼容 IOS<11.2/ padding-bottom: env(safe-area-inset-bottom); ///兼容 IOS>11.2/ .b_icon { display: flex; flex-direction: column; align-items: center; font-size: 19rpx; font-weight: 400; color: #333333; position: relative; image { width: 50.82rpx; height: 50.82rpx; } .badge { position: absolute; top: -5rpx; right: -10rpx; color: #fff; min-width: 28rpx; height: 28rpx; text-align: center; line-height: 24rpx; background: #F84221; border-radius: 16rpx 16rpx 16rpx 16rpx; border: 2rpx solid #FFFFFF; } } .btn { width: 575rpx; height: 84rpx; background: linear-gradient(270deg, #FF6D20 0%, #F84221 100%); border-radius: 42rpx 42rpx 42rpx 42rpx; display: flex; justify-content: center; align-items: center; font-size: 30rpx; font-family: PingFang SC-Medium, PingFang SC; font-weight: 500; color: #FFFFFF; } } } </style>