Files
dtx_store/pages/store/goods.vue
2022-07-11 15:47:26 +08:00

615 lines
19 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<view>
<!-- 产品封面 -->
<view class="goods-swiper">
<swiper :indicator-dots="false" @change="current = $event.detail.current + 1">
<swiper-item v-for="(item, index) in goods.pictures" :key="index">
<view class="swiper-cover">
<image :src="item" mode="aspectFill" />
</view>
</swiper-item>
</swiper>
<view class="swiper-pages">
{{current}}/{{goods.pictures.length}}
</view>
</view>
<!-- 详情 -->
<view class="main">
<view class="title">{{goods.name}}</view>
<view class="sub-title">{{goods.description}}</view>
<view class="box-flex">
<view class="price">
{{goods.price.show}}<text>DT积分</text>
</view>
<view class="sales" v-if="goods.skus">库存量{{goods.skus[0].stock}}</view>
</view>
<view class="unit" v-if="goods.skus && goods.skus[0].unit !== ''" @click="open()">
<span> 规格 : {{selectSkusValues.unit_text}}</span>
<uni-icons type="right" color="#cacaca" />
</view>
<!-- 店铺信息 -->
<view class="shopInfo" @click="toShop(goods.shop.shop_id)" v-if="goods.shop">
<view class="shopInfo-title-left">
<image class="shop-logo" :src="goods.shop.cover" mode="aspectFill" />
<view class="shop-title">
<view class="shop-titl">{{goods.shop.name}}</view>
<view> 店铺评分:
<span class='no'>5.0</span>
<text style="padding-left: 20rpx;">
服务态度:
<span class='no'>5.0</span>
</text>
</view>
</view>
</view>
<view class="shopInfo-title-right">全部商品 {{goods.shop.goods_count || 0}}
<uni-icons type="right" color="grey" />
</view>
</view>
<view class="imgs">
<block v-for="(item, index) in goods.content" :key="index">
<image :src="item" mode="widthFix"></image>
</block>
</view>
</view>
<!-- 立即购买 -->
<view class="footer">
<view @click="toShop(goods.shop.shop_id)" class=" shop">
<uni-icons type="shop" size="26" color="grey" />店铺
</view>
<button type="default" hover-class="none" @click="buy">立即购买</button>
</view>
<!-- 多规格弹窗 -->
<u-popup :show="skuShow" :round="10" mode="bottom" @close="close" @open="open">
<scroll-view class="skuView" scroll-y="true">
<view class="goods-info">
<image class="goods-cover" :src="selectSkusValues.cover" mode="aspectFill" />
<view class="baseInfo">
<view class="money"> {{selectSkusValues.price}}<span>DT积分</span> </view>
<view class="shop-name" v-if="goods.shop"> {{goods.shop.name}} </view>
<view class="sku-text"> 商品规格{{selectSkusValues.unit_text}} </view>
<view class="stock" v-if="selectSkusValues.stock>0"> 剩余库存{{selectSkusValues.stock}} </view>
<view class="stock" v-else> 当前商品库存不足</view>
</view>
</view>
<view class="sku" v-for="(item,index) in specs" :key="item.spec_id">
<view class="sku-title">{{item.name}}</view>
<view class="sku-list">
<block v-for="it in item.values" :keys='it.value_id'>
<view :class="['sku-item',specselect[index] == it.value_id ? 'sku-active':'']"
@click="clickSkus(index,it.value_id)">
{{it.value}}
</view>
</block>
</view>
</view>
<view class="buy-number">
<view class="buy-title">数量</view>
<uni-number-box :min="1" :max="selectSkusValues.stock" :disabled="selectSkusValues.stock == 0"
@change="qty = $event" />
</view>
<button class="now-buy" type="default" hover-class="none" @click="buy2(selectSkusValues)">立即购买</button>
</scroll-view>
</u-popup>
</view>
</template>
<script>
import {
goods
} from '@/apis/interfaces/store'
import userAuth from '@/public/userAuth'
export default {
data() {
return {
current: 1,
goods: {
pictures: [],
name: "",
description: "",
content: [],
price: {
show: 0
}
},
skus: [],
skuid: '',
skuShow: false,
specs: [],
unitText: '',
specselect: [],
selectSkusValues: {},
qty: 1,
};
},
mounted() {
this.getGoods()
},
methods: {
getGoods() {
let id = this.$Route.query.id
// let id = 61;
goods(id).then(res => {
this.goods = res
this.specs = res.specs
this.skus = res.skus
this.skuid = res.skus[0].sku_id
this.unitText = res.skus[0].unit_text
this.specselect = res.skus[0].unit.split('|')
this.selectSkusValues = res.skus[0]
})
},
open() {
this.skuShow = true
this.qty = 1;
},
close() {
this.skuShow = false
this.qty = 1;
// this.specselect = this.skus[0].unit.split('|')
// this.selectSkusValues = this.skus[0]
},
clickSkus(index, id) {
this.skuid = ''
this.specselect[index] = id;
let newlist = []
let str = ''
for (var i in this.specselect) {
if (i == index) {
newlist.push(id);
if (i == 0) {
str = id
} else {
str = str + '|' + id
}
} else {
newlist.push(this.specselect[i])
if (i == 0) {
str = this.specselect[i]
} else {
str = str + '|' + this.specselect[i]
}
}
}
for (var i in this.skus) {
if (this.skus[i].unit === str) {
this.selectSkusValues = this.skus[i];
break;
}
}
this.specselect = newlist
},
buy() {
if (this.$store.state.token === '') {
const Auth = new userAuth()
Auth.Login()
return
}
if (this.goods.type === 2) {
this.open();
return
}
this.goUrl();
},
buy2(value) {
let {
sku_id,
stock
} = value;
if (stock > 0) {
this.skuid = sku_id;
this.goUrl()
} else {
uni.showToast({
title: '当前商品库存不足',
icon: 'none',
mask: true,
duration: 2000
})
}
},
goUrl() {
this.$Router.push({
name: 'StoreBuy',
params: {
skuId: this.skuid,
qty: this.qty
}
})
this.close()
},
toShop(id) {
this.$Router.push({
name: 'ShopDetail',
params: {
ShopId: id
}
})
},
}
}
</script>
<style lang="scss">
.goods-swiper {
position: relative;
width: 100%;
padding-top: 110%;
background: $window-color;
&>swiper {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
.swiper-cover {
width: 100%;
height: 100%;
image {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
}
}
.swiper-pages {
position: absolute;
bottom: 20rpx;
left: 0;
right: 0;
z-index: 9;
line-height: 90rpx;
text-align: center;
color: white;
font-size: $title-size-m;
text-shadow: 0 5rpx 5rpx rgba($color: #000000, $alpha: .02);
}
}
// 详情
.main {
position: relative;
z-index: 9;
margin-top: -20rpx;
background: white;
border-radius: $radius $radius 0 0;
box-shadow: 0 0 10rpx 10rpx rgba($color: #000000, $alpha: .02);
padding-bottom: ($padding*2) + 90;
.hr {
position: relative;
min-height: 1rpx;
margin: 0 $margin;
text-align: center;
text {
position: relative;
z-index: 1;
color: $text-gray;
font-size: $title-size-m;
background: white;
padding: 0 $padding;
}
&::after {
content: " ";
background: $border-color;
width: 100%;
height: 1rpx;
position: absolute;
left: 0;
top: 50%;
}
}
.title {
padding: $padding;
font-weight: bold;
font-size: $title-size + 14;
}
.sub-title {
padding: 0 $padding;
font-size: $title-size-m;
color: $text-gray;
}
.box-flex {
padding: $padding;
display: flex;
justify-content: space-between;
align-items: center;
.price {
font-weight: bold;
color: $text-price;
font-size: $title-size + 10;
text {
font-size: 60%;
margin-left: 10rpx;
}
}
.sales {
font-size: $title-size-m;
color: $text-gray;
}
}
.unit {
padding: 30rpx;
font-size: $title-size;
color: #333;
border-top: solid 20rpx #f9f9f9;
display: flex;
flex-direction: row;
align-items: center;
justify-content: space-between;
box-sizing: border-box;
}
.imgs {
image {
vertical-align: top;
width: 100%;
}
}
.shopInfo {
border-top: solid $padding #f9f9f9;
display: flex;
flex-direction: row;
align-items: center;
justify-content: space-between;
box-sizing: border-box;
width: 100%;
padding: $padding $padding - 10;
border-bottom: solid 10rpx #f9f9f9;
.shopInfo-title-left {
width: 500rpx;
display: flex;
flex-direction: row;
align-items: center;
justify-content: flex-start;
box-sizing: border-box;
.shop-logo {
width: 100rpx;
height: 100rpx;
border-radius: 10rpx;
border: solid 1rpx #f9f9f9;
}
.shop-title {
display: flex;
flex-direction: column;
align-items: flex-start;
justify-content: flex-start;
box-sizing: border-box;
font-size: 26rpx;
margin-left: $margin;
color: #999;
width: 370rpx;
.no {
color: $text-price;
padding-left: 4rpx;
}
.shop-titl {
font-size: 34rpx;
color: #333;
font-weight: bold;
margin-bottom: 6rpx;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
width: 100%;
}
}
}
.shopInfo-title-right {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
box-sizing: border-box;
font-size: 26rpx;
color: #222;
}
}
}
// 购买
.footer {
position: fixed;
bottom: 0;
left: 0;
right: 0;
padding: $padding;
z-index: 98;
background: white;
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
box-sizing: border-box;
// linear-gradient(to top, white 86%, rgba(255,255,255,.0))
.shop {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
box-sizing: border-box;
font-size: 24rpx;
color: $text-gray;
}
button {
background: $main-color;
margin-left: 60rpx;
flex: 1;
color: white;
border-radius: $radius-lg;
height: 90rpx;
line-height: 90rpx;
font-weight: bold;
font-size: $title-size;
&::after {
display: none;
}
}
}
// 规格弹窗
.skuView {
min-height: 30vh;
max-height: 60vh;
padding: $padding + 10 $padding;
color: $text-color;
box-sizing: border-box;
// 商品信息
.goods-info {
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
box-sizing: border-box;
border-bottom: solid 1rpx #f9f9f9;
padding-bottom: 20rpx;
.goods-cover {
width: 200rpx;
height: 200rpx;
border-radius: 20rpx;
}
.baseInfo {
flex: 1;
padding-left: $padding;
box-sizing: border-box;
.money {
font-size: $title-size + 14;
font-weight: bold;
color: $text-price;
display: flex;
flex-direction: row;
align-items: center;
justify-content: flex-start;
box-sizing: border-box;
span {
font-weight: normal;
font-size: $title-size-m - 4;
padding-left: 10rpx;
padding-top: 12rpx;
display: inline-block;
}
}
.shop-name {
background: linear-gradient(to right, rgba(255, 255, 255, 0), rgba($color: $text-price, $alpha: 0.5));
display: inline-block;
padding: 4rpx 20rpx 4rpx 0;
color: #71440b;
font-size: $title-size-m - 2;
}
.sku-text {
font-size: $title-size-m - 2;
padding-top: 10rpx;
color: $text-gray;
}
.stock {
font-size: $title-size-m - 2;
padding-top: 6rpx;
color: $text-gray;
}
}
}
.buy-number {
display: flex;
flex-direction: row;
align-items: center;
justify-content: space-between;
box-sizing: border-box;
padding: $padding + 20 0 $padding 0;
.buy-title {
font-size: 32rpx;
font-weight: bold;
}
}
// 规格
.sku {
.sku-title {
font-size: 32rpx;
font-weight: bold;
padding-top: 30rpx;
}
.sku-list {
display: flex;
flex-direction: row;
align-items: center;
justify-content: flex-start;
box-sizing: border-box;
flex-wrap: wrap;
.sku-item {
padding: 10rpx 30rpx;
border: solid 1rpx #f9f9f9;
margin-right: 20rpx;
margin-top: 20rpx;
border-radius: 40rpx;
background-color: #f9f9f9;
font-size: 30rpx;
min-width: 70rpx;
text-align: center;
}
.sku-active {
background-color: rgba($color: $main-color, $alpha: 0.2);
color: $main-color;
font-weight: bold;
}
}
}
.now-buy {
background-color: #34ce98;
color: #fff;
border: none;
margin-top: $margin;
}
}
</style>