jiuyiUniapp/shop/components/specificationsnew.vue

342 lines
7.9 KiB
Vue
Raw Normal View History

2024-12-18 15:46:27 +08:00
<template>
<view class="content">
<!-- 规格-模态层弹窗 -->
<view class="popup spec" :class="specClass" @touchmove.stop.prevent="stopPrevent" @click="toggleSpec">
<!-- 遮罩层 -->
<view class="mask"></view>
<view class="layer attr-content" @click.stop="stopPrevent">
<view class="a-t">
<image :src="goodsInfoNew.thumb || goodsInfo.thumb"></image>
<view class="right">
<text class="price">¥{{ goodsInfoNew.price || goodsInfo.price }}</text>
<text class="stock">库存{{ goodsInfoNew.stock || goodsInfo.stock }}</text>
<view class="selected">
<text>{{ skutitlename }}</text>
</view>
</view>
</view>
<view v-for="(ProductItem, n) in gspecList.spec_info_list" :key="n" class="attr-list">
<text>{{ ProductItem.spec_name }}</text>
<view class="item-list">
<text
v-for="(oItem, index) in ProductItem.value"
@click="specificationBtn(oItem.spec_value_id, n, index, oItem.isShow, ProductItem.spec_name)"
:key="index"
class="tit"
:class="[oItem.isShow ? '' : 'noneActive', subIndex[n] == index ? 'selected' : '']"
>
{{ oItem.spec_value_name }}
</text>
</view>
</view>
<button class="btn" @click="submitnew">完成</button>
</view>
</view>
</view>
</template>
<script>
export default {
props:{
gspecList:{
},
goodsInfo:{
},
},
data() {
return {
specClass:'none',//规格弹窗是否显示
goodsInfoNew: {},//当规格选择完成时重新覆盖商品信息
skutitlename: '',//提示用户例如:请选择温度,口味;或者提示用户已选择温度,口味
skutitlenamelist: [],//存储规格标题
selectArr: [], //存放被选中的值
shopItemInfo: {}, //存放要和选中的值进行匹配的数据
subIndex: [], //是否选中 因为不确定是多规格还是单规格,所以这里定义数组来判断
skuId:'',//规格id
};
},
mounted() {
var self = this;
var skutitle = [];
for (var i of self.gspecList.goods_spec) {
self.shopItemInfo[i.specs] = i;
//修改数据结构格式,改成键值对的方式,以方便和选中之后的值进行匹配
}
for (var j of self.gspecList.spec_info_list) {
self.skutitlenamelist.push(j.spec_name)
//存储规格标题
}
self.checkItem();
},
methods: {
// 选择规格
specificationBtn: function(id, pindex, index, disable, pname) {
var self = this;
if (!disable) {
return '';
}
if (self.selectArr[pindex] != id) {
self.selectArr[pindex] = id;
self.subIndex[pindex] = index;
self.skutitlenamelist[pindex] = ''; //
} else {
self.selectArr[pindex] = '';
self.subIndex[pindex] = -1; //去掉选中的颜色
self.skutitlenamelist[pindex] = pname; //
}
self.checkItem();
},
// 处理数据
checkItem: function() {
var self = this;
var option = self.gspecList.spec_info_list;
var result = []; //定义数组存储被选中的值
for (let i=0;i<option.length; i++) {
result[i] = self.selectArr[i] ? self.selectArr[i] : '';
}
for (let i=0;i<option.length; i++) {
var last = result[i]; //把选中的值存放到字符串last去
for (var k=0;k<option[i].value.length;k++) {
result[i] = option[i].value[k].spec_value_id; //赋值存在直接覆盖不存在往里面添加id值
option[i].value[k].isShow = self.isMay(result); //在数据里面添加字段isShow来判断是否可以选择
}
result[i] = last; //还原,目的是记录点下去那个值,避免下一次执行循环时避免被覆盖
}
//重绘
self.gspecList.spec_info_list = [];
self.$set(self.gspecList, 'spec_info_list', option);
self.getinfo(this.selectArr);
},
// 获取选择的值
getinfo: function(item) {
var checked = item.join('_');
if (this.shopItemInfo[checked]) {
this.goodsInfoNew = this.shopItemInfo[checked];
this.skutitlename='已选择:'+this.shopItemInfo[checked].title;
this.skuId=this.shopItemInfo[checked].id;
} else {
this.goodsInfoNew = {};
var skutitle = [];
for (var i = 0; i < this.skutitlenamelist.length; i++) {
if (this.skutitlenamelist[i]) {
skutitle.push(this.skutitlenamelist[i]);
}
}
this.skutitlename = '请选择 ' + skutitle.toString(',');
this.skuId='';
}
},
/**
* 判断库存是否为0
*/
isMay: function(result) {
for (var i in result) {
if (result[i] == '') {
return true; //如果数组里有为空的值那直接返回true
}
}
result = result.join('_');
if (!this.shopItemInfo[result]) {
return false;
}
return this.shopItemInfo[result].stock == 0 ? false : true; //匹配选中的数据的库存若不为空返回true反之返回false
},
// 阻止默认事件
stopPrevent() {},
//规格弹窗开关
toggleSpec() {
if (this.specClass === 'show') {
this.specClass = 'hide';
setTimeout(() => {
this.specClass = 'none';
}, 250);
} else if (this.specClass === 'none') {
this.specClass = 'show';
}
},
// 点击完成事件
submitnew:function(){
if(this.skuId){
this.specClass = 'none';
uni.showToast({
title:`规格id为${this.skuId}`,
mask: false,
duration: 1500
});
this.$emit('submitSukid',this.skuId)
}else{
uni.showToast({
title: '请选择规格',
mask: false,
duration: 1500
});
}
}
}
};
</script>
<style lang="scss">
/* 规格选择弹窗 */
.attr-content {
padding: 10upx 30upx;
.a-t {
display: flex;
image {
width: 170upx;
height: 170upx;
flex-shrink: 0;
margin-top: -40upx;
border-radius: 8upx;
}
.right {
display: flex;
flex-direction: column;
padding-left: 24upx;
font-size: $font-sm + 2upx;
color: $font-color-base;
line-height: 42upx;
.price {
font-size: $font-lg;
color: $uni-color-primary;
margin-bottom: 10upx;
}
.selected-text {
margin-right: 10upx;
}
}
}
.attr-list {
display: flex;
flex-direction: column;
font-size: $font-base + 2upx;
color: $font-color-base;
padding-top: 30upx;
padding-left: 10upx;
}
.item-list {
padding: 20upx 0 0;
display: flex;
flex-wrap: wrap;
text {
display: flex;
align-items: center;
justify-content: center;
background: #eee;
margin-right: 20upx;
margin-bottom: 20upx;
border-radius: 100upx;
min-width: 60upx;
height: 60upx;
padding: 0 20upx;
font-size: $font-base;
color: $font-color-dark;
}
.selected {
background: #fbebee;
color: $uni-color-primary;
}
.noneActive {
color: $uni-color-primary;
background-color: rgba(0, 0, 0, 0.8);
}
}
}
/* 弹出层 */
.popup {
position: fixed;
left: 0;
top: 0;
right: 0;
bottom: 0;
z-index: 99;
&.show {
display: block;
.mask {
animation: showPopup 0.2s linear both;
}
.layer {
animation: showLayer 0.2s linear both;
}
}
&.hide {
.mask {
animation: hidePopup 0.2s linear both;
}
.layer {
animation: hideLayer 0.2s linear both;
}
}
&.none {
display: none;
}
.mask {
position: fixed;
top: 0;
width: 100%;
height: 100%;
z-index: 1;
background-color: rgba(0, 0, 0, 0.4);
}
.layer {
position: fixed;
z-index: 99;
bottom: 0;
width: 100%;
min-height: 40vh;
border-radius: 10upx 10upx 0 0;
background-color: #fff;
.btn {
height: 66upx;
line-height: 66upx;
border-radius: 100upx;
width: 80%;
box-sizing: border-box;
background: $uni-color-primary;
font-size: $font-base + 2upx;
color: #fff;
margin: 30upx auto 20upx;
}
}
@keyframes showPopup {
0% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@keyframes hidePopup {
0% {
opacity: 1;
}
100% {
opacity: 0;
}
}
@keyframes showLayer {
0% {
transform: translateY(120%);
}
100% {
transform: translateY(0%);
}
}
@keyframes hideLayer {
0% {
transform: translateY(0);
}
100% {
transform: translateY(120%);
}
}
}
</style>