TakeOutShop/shopProDetail/detail/detail.vue

275 lines
8.9 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>
<page-meta :page-style="'overflow:'+(show?'hidden':'visible')"></page-meta>
<view class="mian">
<view class="head" :class="headShow?'head_show':''" :style="{'opacity':headShow?opacity:'1','padding-top':statusBartop+'px'}">
<view class="head_back" @click="handleBack()" :style="{'width': statusHeight+'px','height':statusHeight+'px'}">
<image class="head_back_img" src="https://zhkj1.oss-cn-shanghai.aliyuncs.com/newPD/zhBack.png" mode="widthFix"></image>
</view>
<block v-if="headShow">
<view class="head_nav" :style="{'height':statusHeight+'px'}">
<view class="head_item" v-for="(item,index) in navList" :key="index" :class="currentTab === index ? 'head_item_active':''" @click="switchTab(index)">
<view class="head_item_name">{{item}}</view>
<view class="head_item_img"></view>
</view>
</view>
<view class="head_search" :style="{'width': statusHeight+'px','height':statusHeight+'px'}" @click="onSearch">
<image :style="{'width': statusHeight-15+'px','height':statusHeight-15+'px'}" src="../../static/search_img.png" mode="widthFix"></image>
</view>
</block>
</view>
<!-- 轮播图区域 -->
<view class="item">
<view class="shop_swiper" :style="{'height':swiperHeight+'rpx'}" >
<swiper class="shop_swiper_wrap" interval="3000" :current="currentIndex" circular @change="onSwiperChange" :style="{'height':swiperHeight+'rpx'}">
<swiper-item class="shop_swiper_marquees" v-if="sliderImages.length" v-for="(item,index) in sliderImages" :key="index">
<view class="shop_swiper_img" :style="{'height':swiperHeight+'rpx'}">
<image class="shop_swiper_imgUrl" :src="item" lazy-load @load="onImageLoad" @click="previewImage(index)" :style="{'height':swiperHeight+'rpx'}"></image>
</view>
</swiper-item>
</swiper>
<view class="currentNumber" v-if="sliderImages.length > 1">
<view class="item_currentNumber item_currentNumber_width"><text>{{currentIndex+1}}/{{sliderImages.length}}</text></view>
</view>
<image @click="Openqc" class="shop_qc" src="../../static/shopdetail/qc.png" mode="widthFix"></image>
</view>
<!-- 价格标题区域 -->
<view class="shop_head" v-if="productInfo.price">
<view class="shop_price price">{{productInfo.price}}<text class="market_name prices">{{productInfo.otPrice}}</text></view>
<view class="shop_title">{{productInfo.storeName}}</view>
<view class="shop_desc">{{productInfo.storeInfo}}</view>
</view>
</view>
<!-- 评论区域 -->
<view class="item">
<comment v-if="productId" :apiType="productId"></comment>
</view>
<!-- 图文详情 -->
<view class="shop_detail item">
<view class="shop_detail_title">图文详情</view>
<view class="shop_detail_img">
<rich-text :nodes="content" class='product-imgs'></rich-text>
</view>
</view>
<view class="item">
<recomGoods :apiType="5"></recomGoods>
</view>
<view style="height: 200rpx;"></view>
<!-- 底部 -->
<view class="footer">
<view class="footer_cont">
<view class="footer_l">
<view class="footer_li">
<view class="footer_icon">
<image class="footer_icon_img" src="../../static/shopdetail/collect.png" mode="widthFix"></image>
</view>
<view class="footer_name">收藏</view>
</view>
<view class="footer_li" @click="goCart()">
<view class="footer_icon">
<view class="footer_amount">45</view>
<image class="footer_icon_img" src="../../static/shopdetail/cart.png" mode="widthFix"></image>
</view>
<view class="footer_name">购物车</view>
</view>
</view>
<view class="footer_r">
<view class="footer_btn border_l">加入购物车</view>
<view class="footer_btn footer_btn_bcg border_r" @click="orderConfirm">立即下单</view>
</view>
</view>
</view>
<uni-popup ref="qcPopup" type="bottom" @change="changeQc">
<view class="cont_qc">
<view class="cont_open_title">质检报告<view class="cont_open_close" @click="Openqc()"><image src="../../static/order/close.png" mode="widthFix"></image></view></view>
<view class="cont_image">
</view>
</view>
</uni-popup>
</view>
</template>
<script setup>
import { loads } from '@/utils/index.js'
import recomGoods from '@/components/recomGoods/recomGoods.vue';
import comment from '@/components/comment/comment.vue';
import { computed,ref,onMounted,onUnmounted,getCurrentInstance,nextTick } from 'vue';
import { useCounterStore } from '@/store/counter'; // 引入 Pinia Store
import { storeToRefs } from 'pinia';//实现解构付值
import { onLoad,onShow,onPullDownRefresh,onPageScroll,onReachBottom,onReady } from "@dcloudio/uni-app"
const counterStore = useCounterStore(); // 使用 Store
const { proxy } = getCurrentInstance();
const qcPopup = ref(null);
const qcShow = ref(false);
const show = ref(false);
const swiperHeight = ref(750);
const imgheights = ref([]);
const currentIndex = ref(0);
const showBack = ref(false);
const headShow = ref(false);
const opacity = ref(1);
const navList = ref(['商品','评论','详情','推荐']);
const currentTab = ref(0); // 当前选中的tab
const scrollTop = ref(0); // 页面滚动的距离
const scrollTimer = ref(null);
const sectionHeights = ref([0]);
const productAttr = ref([]);
const productInfo = ref({});
const productValue = ref({});
const sliderImages = ref([]);
const content = ref('');
const productId = ref('');
//使用piniastoreToRefs方法包裹(保持响应式更新,不使用视图无法更新)
const {statusHeight,headerHeight,statusBartop,token } = storeToRefs(counterStore);
import { frontdetail } from '@/server/api'
const Openqc =() =>{
qcShow.value ? qcPopup.value.close():qcPopup.value.open()
};
const changeQc = (e)=>{
qcShow.value = e.show;
show.value = e.show;
};
//获取图片真实宽度
const onImageLoad = (event) => {
const { width, height } = event.detail;
const imageHeight = 750 / (height / width);
swiperHeight.value = imageHeight;
};
const onSwiperChange=(event)=>{
currentIndex.value = event.detail.current;
};
const previewImage=(i)=>{
uni.previewImage({
current: i,
urls:sliderImages.value
});
};
// 判断是否有上一页
const getPages = () => {
const pages = getCurrentPages();
return pages.length > 1;
};
const goCart=()=>{
uni.switchTab({
url:`/pages/cart/cart`
})
};
const handleBack = () => {
if (getPages()) {
// 如果有上一页,返回上一页
uni.navigateBack();
} else {
// 如果没有上一页,返回首页
uni.switchTab({
url: '/pages/index/index',
});
}
};
const getSectionHeights = async (e)=>{
let sections = []
let sectionHeight = [0]
let rect = await new Promise(resolve => {
const query = uni.createSelectorQuery();
query.selectAll('.item').boundingClientRect((res) => {
resolve(res)
}).exec();
})
sections = rect
for (let i = 0; i < sections.length; i++) {
sectionHeight.push(sectionHeight[i] + sections[i].height - statusBartop.value - statusHeight.value)
}
sectionHeights.value = sectionHeight;
if(e == 1){
let len = sectionHeight.length;
let currentTabs = 0;
for (let i = 0; i < len - 1; i++) {
if (scrollTop.value >= sectionHeight[i] && scrollTop.value < sectionHeight[i + 1]) {
currentTabs = i
break
}
}
currentTab.value = currentTabs;
}
};
const switchTab = (index) =>{
if(currentTab.value == index) return false;
currentTab.value = index;
nextTick(() => {
uni.pageScrollTo({
scrollTop: sectionHeights.value[currentTab.value],
duration: 200,
});
});
};
const orderConfirm = ()=>{
uni.navigateTo({
url:`/order/orderConfirm/orderConfirm`
})
}
const api_detail=(id)=>{
loads('', true);
return frontdetail(id).then(({data}) => {
uni.hideLoading();
productAttr.value = data.productAttr;
productInfo.value = data;
productValue.value = data.productValue;
sliderImages.value = data.sliderImages;
if(data.content){
content.value = data.content.replace(/\<img|\width:[^;]+;/gi,'<img style="width:100%;height:auto;display:block;" ');
}
}).catch(({message}) => {
uni.hideLoading();
uni.showModal({
content:message,
showCancel: false
})
})
}
const onSearch=()=>{
uni.navigateTo({
url:`/userserve/SearchProduct/SearchProduct`
})
}
onLoad((options) => {
const { id } = options;
//初始化时判断是否显示返回按钮
showBack.value = getPages();
if(id){
productId.value = id;
api_detail(id)
}
});
onShow(() => {});
onPageScroll((e)=>{
const top = e.scrollTop;
// 导航条颜色透明渐变
if (top <= 50) {
headShow.value = false
} else {
if( 50 < top && top <= 200 ){
opacity.value = top / 200
}else{
opacity.value = 1
}
headShow.value = true
}
if (scrollTimer.value) {
clearTimeout(scrollTimer.value)
}
scrollTimer.value = setTimeout(() => {
scrollTop.value = e.scrollTop;
getSectionHeights(1);
}, 300)
}),
onReady(()=>{getSectionHeights()})
onPullDownRefresh(()=>{})
onReachBottom(()=>{})
</script>
<style lang="scss">
@import './style.scss';
</style>