修复了部分bug,优化了首页和商品列表、商品详情、购物车的UI
This commit is contained in:
1022
pages/home/home.vue
1022
pages/home/home.vue
File diff suppressed because it is too large
Load Diff
@@ -284,11 +284,11 @@
|
||||
}
|
||||
}).then((res) => {
|
||||
if (res.data.errcode == 0) {
|
||||
uni.showToast({
|
||||
title: '切换成功',
|
||||
duration: 2000,
|
||||
icon: "success"
|
||||
});
|
||||
// uni.showToast({
|
||||
// title: '切换成功',
|
||||
// duration: 2000,
|
||||
// icon: "success"
|
||||
// });
|
||||
}
|
||||
})
|
||||
},
|
||||
@@ -646,4 +646,4 @@
|
||||
}
|
||||
|
||||
}
|
||||
</style>
|
||||
</style>
|
||||
|
||||
@@ -1,63 +1,93 @@
|
||||
<template>
|
||||
<view class="container">
|
||||
<!-- 顶部搜索栏 -->
|
||||
<view class="search-section">
|
||||
<u-search
|
||||
v-model="searchKeyword"
|
||||
placeholder="搜索药品名称"
|
||||
:show-action="false"
|
||||
bg-color="#ffffff"
|
||||
shape="square"
|
||||
height="70"
|
||||
@input="handleSearch"
|
||||
@search="handleSearch"
|
||||
@clear="clearSearch"
|
||||
:action-style="{ color: '#4A90E2' }"
|
||||
>
|
||||
<template v-slot:icon>
|
||||
<u-icon name="search" color="#4A90E2" size="32"></u-icon>
|
||||
</template>
|
||||
</u-search>
|
||||
<!-- 顶部搜索栏:保持优化后的结构,但背景色微调融入原风格 -->
|
||||
<view class="search-sticky">
|
||||
<view class="search-section">
|
||||
<!-- 搜索组件配置 -->
|
||||
<u-search
|
||||
v-model="searchKeyword"
|
||||
placeholder="搜索药品 / 症状 / 品牌"
|
||||
:show-action="false"
|
||||
bg-color="#F5F7FA"
|
||||
placeholder-color="#9CA3AF"
|
||||
shape="round"
|
||||
height="72"
|
||||
@input="handleSearch"
|
||||
@search="handleSearch"
|
||||
@clear="clearSearch"
|
||||
>
|
||||
<template v-slot:icon>
|
||||
<u-icon name="search" color="#9CA3AF" size="32"></u-icon>
|
||||
</template>
|
||||
</u-search>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 商品列表 -->
|
||||
<!-- 商品列表区域 -->
|
||||
<view class="list-section">
|
||||
<!-- 列表项卡片:遍历渲染 filteredProducts 数据 -->
|
||||
<view
|
||||
v-for="(item, index) in filteredProducts"
|
||||
:key="item.id"
|
||||
class="list-item"
|
||||
@click="handClickProduct(item)"
|
||||
>
|
||||
<image
|
||||
class="item-image"
|
||||
:src="item.drug.image"
|
||||
mode="aspectFill"
|
||||
lazy-load
|
||||
/>
|
||||
<!-- 左侧:药品图片容器 -->
|
||||
<view class="image-wrapper">
|
||||
<image
|
||||
class="item-image"
|
||||
:src="item.drug.image"
|
||||
mode="aspectFill"
|
||||
lazy-load
|
||||
/>
|
||||
<!-- 预留缺货蒙层位置 -->
|
||||
<!-- <view class="mask" v-if="!item.stock">缺货</view> -->
|
||||
</view>
|
||||
|
||||
<!-- 右侧:商品详细内容区 -->
|
||||
<view class="item-content">
|
||||
<view class="item-title">{{ item.drug.drug_name }}</view>
|
||||
<view class="item-spec">
|
||||
<text class="spec-label">功效</text>
|
||||
<text class="spec-value">{{ item.drug.function }}</text>
|
||||
</view>
|
||||
<view class="item-spec">
|
||||
<text class="spec-label">规格</text>
|
||||
<text class="spec-value">{{ item.drug.specification }}</text>
|
||||
</view>
|
||||
<view class="item-bottom">
|
||||
<view class="price-section">
|
||||
<text class="price-tag">¥{{ item.price }}</text>
|
||||
<text class="stock-tag">库存充足</text>
|
||||
<!-- 上半部分:基础信息(名称、标签、主治) -->
|
||||
<view class="top-info">
|
||||
<!-- 药品名称:加粗强调,限制2行 -->
|
||||
<view class="item-title">{{ item.drug.drug_name }}</view>
|
||||
|
||||
<!-- 标签行:包含OTC标识和规格 -->
|
||||
<view class="tags-row">
|
||||
<!-- OTC/Rx 标签:根据 is_otc 属性动态切换绿/红样式 -->
|
||||
<text class="tag-otc" :class="item.drug.is_otc ? 'green' : 'red'">{{item.drug.is_otc ? 'OTC' : 'Rx'}}</text>
|
||||
<!-- 规格文本:灰色辅助信息 -->
|
||||
<text class="tag-spec">{{ item.drug.specification }}</text>
|
||||
</view>
|
||||
<view class="cart-icon-btn" @click.stop="showCartPopup(item)">
|
||||
<u-icon name="shopping-cart" color="#ffffff" size="40"></u-icon>
|
||||
|
||||
<!-- 主治功能:灰色小字,辅助决策 -->
|
||||
<view class="item-function" v-if="item.drug.function">
|
||||
主治:{{ item.drug.function }}
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 下半部分:价格与操作按钮(固定在底部) -->
|
||||
<view class="item-bottom">
|
||||
<!-- 价格区域:红色强调 -->
|
||||
<view class="price-section">
|
||||
<text class="currency">¥</text>
|
||||
<text class="price-val">{{ item.price }}</text>
|
||||
</view>
|
||||
|
||||
<!-- 购物车按钮:阻止冒泡(@click.stop),防止触发进入详情页 -->
|
||||
<view class="cart-btn" @click.stop="showCartPopup(item)">
|
||||
<u-icon name="plus" color="#ffffff" size="30"></u-icon>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 空状态:当过滤后没有商品时显示 -->
|
||||
<view v-if="filteredProducts.length === 0" class="empty-state">
|
||||
<u-empty text="暂无相关药品" mode="search"></u-empty>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 购物车悬浮球 -->
|
||||
<!-- 购物车悬浮球:固定在页面右下角 -->
|
||||
<view
|
||||
class="cart-float"
|
||||
:style="{ left: cartPosition.x + 'px', top: cartPosition.y + 'px' }"
|
||||
@@ -66,50 +96,47 @@
|
||||
@touchend="onTouchEnd"
|
||||
@click="goToCart"
|
||||
>
|
||||
<u-badge :count="cartCount" :max="99" type="error" class="cart-badge" v-if="cartCount > 0"></u-badge>
|
||||
<u-icon name="shopping-cart" color="#ffffff" size="36"></u-icon>
|
||||
<view class="cart-icon-inner">
|
||||
<u-icon name="shopping-cart" color="#ffffff" size="44"></u-icon>
|
||||
<!-- 角标:显示购物车数量 -->
|
||||
<view class="badge" v-if="cartCount > 0">{{ cartCount > 99 ? '99+' : cartCount }}</view>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 购物车弹窗 -->
|
||||
<!-- 购物车底部弹窗:选择数量 -->
|
||||
<u-popup
|
||||
v-model="showPopup"
|
||||
mode="bottom"
|
||||
border-radius="20"
|
||||
border-radius="24"
|
||||
:closeable="true"
|
||||
@close="closePopup"
|
||||
>
|
||||
<view class="popup-content">
|
||||
<view class="popup-header">
|
||||
<text class="popup-title">选择购买数量</text>
|
||||
</view>
|
||||
|
||||
<view class="product-info">
|
||||
<image class="product-image" :src="getProductImage" mode="aspectFill"></image>
|
||||
<view class="product-details">
|
||||
<text class="product-name">{{ getProductName }}</text>
|
||||
<text class="product-spec">{{ getProductSpec }}</text>
|
||||
<view class="product-price">¥{{ currentProduct.price || '' }}</view>
|
||||
<!-- 弹窗头部:商品简要信息 -->
|
||||
<view class="product-header-row">
|
||||
<image class="popup-img" :src="getProductImage" mode="aspectFill"></image>
|
||||
<view class="popup-info">
|
||||
<view class="price-row">¥<text class="big">{{ currentProduct.price || '' }}</text></view>
|
||||
<view class="stock-row">库存充足</view>
|
||||
<view class="selected-spec">已选: {{ getProductSpec }}</view>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<view class="quantity-selector">
|
||||
<text class="quantity-label">购买数量</text>
|
||||
<view class="quantity-controls">
|
||||
<u-number-box
|
||||
v-model="quantity"
|
||||
:min="1"
|
||||
:max="999"
|
||||
integer
|
||||
:step="1"
|
||||
:disabled-input="false"
|
||||
@change="quantityChange"
|
||||
></u-number-box>
|
||||
</view>
|
||||
<!-- 数量选择器 -->
|
||||
<view class="quantity-section">
|
||||
<text class="label">购买数量</text>
|
||||
<u-number-box
|
||||
v-model="quantity"
|
||||
:min="1"
|
||||
:max="999"
|
||||
integer
|
||||
@change="quantityChange"
|
||||
></u-number-box>
|
||||
</view>
|
||||
|
||||
<view class="popup-actions">
|
||||
<button class="cancel-btn" @click="closePopup">取消</button>
|
||||
<button class="confirm-btn" @click="confirmAddToCart">加入购物车</button>
|
||||
<!-- 底部确认按钮 -->
|
||||
<view class="popup-footer">
|
||||
<button class="action-btn add-cart" @click="confirmAddToCart">加入购物车</button>
|
||||
</view>
|
||||
</view>
|
||||
</u-popup>
|
||||
@@ -117,34 +144,31 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
// 引入API接口
|
||||
import { getStoreDrugListBySalespersonApi } from "@/request/api/product";
|
||||
import { getCartCountsApi, saveCartApi } from "@/request/api/cart";
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
products: [],
|
||||
filteredProducts: [],
|
||||
searchKeyword: "",
|
||||
scrollViewHeight: 0,
|
||||
doctorId: 0,
|
||||
r_type: 0,
|
||||
cartCount: 0,
|
||||
cartPosition: {
|
||||
x: 0,
|
||||
y: 0
|
||||
},
|
||||
cartMove: {
|
||||
startX: 0,
|
||||
startY: 0,
|
||||
moving: false
|
||||
},
|
||||
showPopup: false,
|
||||
currentProduct: {},
|
||||
quantity: 1
|
||||
products: [], // 所有商品原始数据
|
||||
filteredProducts: [], // 搜索过滤后的商品数据
|
||||
searchKeyword: "", // 搜索关键词
|
||||
scrollViewHeight: 0, // 滚动区域高度(预留)
|
||||
doctorId: 0, // 医生ID参数
|
||||
r_type: 0, // 注册类型参数
|
||||
cartCount: 0, // 购物车总数量
|
||||
// 购物车悬浮球位置
|
||||
cartPosition: { x: 0, y: 0 },
|
||||
// 拖拽相关状态
|
||||
cartMove: { startX: 0, startY: 0, moving: false },
|
||||
showPopup: false, // 控制弹窗显示
|
||||
currentProduct: {}, // 当前选中的商品
|
||||
quantity: 1 // 购买数量
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
// 计算属性:安全获取当前选中商品的图片、名称、规格
|
||||
getProductImage() {
|
||||
return this.currentProduct.drug && this.currentProduct.drug.image ? this.currentProduct.drug.image : '';
|
||||
},
|
||||
@@ -160,6 +184,7 @@ export default {
|
||||
this.r_type = e.register_type;
|
||||
},
|
||||
methods: {
|
||||
// 获取商品列表
|
||||
getList() {
|
||||
getStoreDrugListBySalespersonApi({
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
@@ -169,29 +194,34 @@ export default {
|
||||
if (res.data.code == 0) {
|
||||
this.products = res.data.result.records;
|
||||
this.cartCount = res.data.result.cart_count;
|
||||
this.filteredProducts = [...this.products];
|
||||
this.filteredProducts = [...this.products]; // 初始化时显示所有商品
|
||||
}
|
||||
})
|
||||
},
|
||||
// 处理搜索:支持名称和拼音搜索
|
||||
handleSearch() {
|
||||
this.filteredProducts = this.products.filter(item =>
|
||||
item.drug.drug_name.includes(this.searchKeyword) ||
|
||||
(item.drug.pinyin_simple && item.drug.pinyin_simple.includes(this.searchKeyword.toLowerCase()))
|
||||
);
|
||||
},
|
||||
// 清空搜索
|
||||
clearSearch() {
|
||||
this.searchKeyword = "";
|
||||
this.filteredProducts = [...this.products];
|
||||
},
|
||||
// 计算可视区域高度
|
||||
calculateScrollViewHeight() {
|
||||
const systemInfo = uni.getSystemInfoSync();
|
||||
this.scrollViewHeight = systemInfo.windowHeight - 160;
|
||||
},
|
||||
// 点击商品进入详情页
|
||||
handClickProduct(item) {
|
||||
uni.navigateTo({
|
||||
url: `/subPackages/product/symptoms?id=${item.drug.id}&drug_name=${item.drug.drug_name}&is_otc=${item.drug.is_otc}&image=${item.drug.image}&price=${item.price}`
|
||||
});
|
||||
},
|
||||
// 初始化悬浮球位置:右下角
|
||||
initCartPosition() {
|
||||
const systemInfo = uni.getSystemInfoSync();
|
||||
this.cartPosition = {
|
||||
@@ -199,70 +229,59 @@ export default {
|
||||
y: systemInfo.windowHeight - 200
|
||||
};
|
||||
},
|
||||
// 拖拽开始
|
||||
onTouchStart(e) {
|
||||
this.cartMove.startX = e.touches[0].clientX;
|
||||
this.cartMove.startY = e.touches[0].clientY;
|
||||
this.cartMove.moving = false;
|
||||
},
|
||||
// 拖拽中
|
||||
onTouchMove(e) {
|
||||
this.cartMove.moving = true;
|
||||
const moveX = e.touches[0].clientX - this.cartMove.startX;
|
||||
const moveY = e.touches[0].clientY - this.cartMove.startY;
|
||||
|
||||
this.cartPosition.x += moveX;
|
||||
this.cartPosition.y += moveY;
|
||||
|
||||
this.cartMove.startX = e.touches[0].clientX;
|
||||
this.cartMove.startY = e.touches[0].clientY;
|
||||
},
|
||||
// 拖拽结束:吸边处理
|
||||
onTouchEnd() {
|
||||
if (!this.cartMove.moving) return;
|
||||
|
||||
const systemInfo = uni.getSystemInfoSync();
|
||||
const screenWidth = systemInfo.windowWidth;
|
||||
const screenHeight = systemInfo.windowHeight;
|
||||
|
||||
let finalX = this.cartPosition.x;
|
||||
let finalY = this.cartPosition.y;
|
||||
|
||||
// 边界限制
|
||||
finalX = Math.max(10, Math.min(finalX, screenWidth - 70));
|
||||
finalY = Math.max(10, Math.min(finalY, screenHeight - 70));
|
||||
|
||||
// 左右吸附
|
||||
if (finalX < screenWidth / 2) {
|
||||
finalX = 20;
|
||||
} else {
|
||||
finalX = screenWidth - 70;
|
||||
}
|
||||
|
||||
this.cartPosition = {
|
||||
x: finalX,
|
||||
y: finalY
|
||||
};
|
||||
this.cartPosition = { x: finalX, y: finalY };
|
||||
},
|
||||
// 跳转购物车页面
|
||||
goToCart() {
|
||||
uni.navigateTo({
|
||||
url: '/subPackages/shop/shop-cate'
|
||||
});
|
||||
uni.navigateTo({ url: '/subPackages/shop/shop-cate' });
|
||||
},
|
||||
// 显示加购弹窗
|
||||
showCartPopup(item) {
|
||||
this.currentProduct = item;
|
||||
this.quantity = 1;
|
||||
this.showPopup = true;
|
||||
},
|
||||
// 关闭弹窗
|
||||
closePopup() {
|
||||
this.showPopup = false;
|
||||
},
|
||||
quantityChange(value) {
|
||||
console.log('[v0] 数量变化:', value);
|
||||
},
|
||||
quantityChange(value) {},
|
||||
// 确认加入购物车
|
||||
confirmAddToCart() {
|
||||
try {
|
||||
let cart = uni.getStorageSync('cart') || [];
|
||||
|
||||
if (!Array.isArray(cart)) {
|
||||
cart = [];
|
||||
}
|
||||
|
||||
saveCartApi({
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
drug_id: this.currentProduct.drug.id,
|
||||
@@ -270,23 +289,13 @@ export default {
|
||||
}).then(() => {
|
||||
this.updateCartCount();
|
||||
this.closePopup();
|
||||
|
||||
uni.showToast({
|
||||
title: `已加入${this.quantity}件商品`,
|
||||
icon: 'success',
|
||||
duration: 1500
|
||||
});
|
||||
uni.showToast({ title: `已加入购物车`, icon: 'success' });
|
||||
})
|
||||
|
||||
} catch (error) {
|
||||
console.error('[v0] 加入购物车失败:', error);
|
||||
uni.showToast({
|
||||
title: '加入购物车失败',
|
||||
icon: 'none',
|
||||
duration: 1000
|
||||
});
|
||||
uni.showToast({ title: '失败', icon: 'none' });
|
||||
}
|
||||
},
|
||||
// 更新购物车数量
|
||||
updateCartCount() {
|
||||
let that = this;
|
||||
getCartCountsApi({
|
||||
@@ -319,295 +328,252 @@ export default {
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
/* 页面主容器:保留原有品牌色(淡蓝渐变) */
|
||||
.container {
|
||||
padding: 20rpx;
|
||||
background: linear-gradient(180deg, #f0f5ff 0%, #ffffff 100%);
|
||||
min-height: 100vh;
|
||||
box-sizing: border-box;
|
||||
position: relative;
|
||||
padding-bottom: 40rpx;
|
||||
}
|
||||
|
||||
.search-section {
|
||||
padding: 20rpx;
|
||||
background: #ffffff;
|
||||
border-radius: 20rpx;
|
||||
box-shadow: 0 6rpx 24rpx rgba(74,144,226,0.15);
|
||||
margin-bottom: 24rpx;
|
||||
/* 顶部搜索栏:吸顶效果 */
|
||||
.search-sticky {
|
||||
position: sticky;
|
||||
top: 0;
|
||||
z-index: 100;
|
||||
/* 使用高透明度白色背景,既保证文字可读,又透出底部渐变 */
|
||||
background: rgba(255, 255, 255, 0.95);
|
||||
padding: 16rpx 24rpx;
|
||||
box-shadow: 0 2rpx 10rpx rgba(0,0,0,0.02);
|
||||
}
|
||||
|
||||
.list-section {
|
||||
padding-top: 10rpx;
|
||||
padding: 24rpx;
|
||||
}
|
||||
|
||||
/* --- 核心优化:商品卡片样式 --- */
|
||||
.list-item {
|
||||
display: flex;
|
||||
padding: 28rpx;
|
||||
margin-bottom: 24rpx;
|
||||
border-radius: 20rpx;
|
||||
background: linear-gradient(135deg, #ffffff 0%, #f8fbff 100%);
|
||||
box-shadow: 0 6rpx 20rpx rgba(65, 117, 238, 0.12);
|
||||
transition: all 0.3s ease;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
display: flex; /* 使用 Flex 布局实现左图右文 */
|
||||
background: #ffffff; /* 纯白背景突出商品 */
|
||||
border-radius: 20rpx; /* 大圆角,增加亲和力 */
|
||||
padding: 24rpx; /* 内边距,保持呼吸感 */
|
||||
margin-bottom: 20rpx; /* 卡片间距 */
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
height: 4rpx;
|
||||
background: linear-gradient(90deg, #4A90E2, #5B8FF9);
|
||||
opacity: 0;
|
||||
transition: opacity 0.3s ease;
|
||||
}
|
||||
/* 阴影优化:使用品牌蓝色的极淡阴影,清爽不脏 */
|
||||
box-shadow: 0 4rpx 16rpx rgba(65, 117, 238, 0.08);
|
||||
transition: transform 0.1s; /* 添加点击缩放动画 */
|
||||
|
||||
&:active {
|
||||
transform: translateY(4rpx);
|
||||
box-shadow: 0 3rpx 12rpx rgba(65, 117, 238, 0.18);
|
||||
transform: scale(0.99); /* 点击时的微缩反馈 */
|
||||
}
|
||||
}
|
||||
|
||||
&::before {
|
||||
opacity: 1;
|
||||
/* 左侧图片容器 */
|
||||
.image-wrapper {
|
||||
position: relative;
|
||||
margin-right: 24rpx; /* 图片与文字的间距 */
|
||||
|
||||
.item-image {
|
||||
width: 200rpx; /* 固定宽度 */
|
||||
height: 200rpx; /* 固定高度,正方形 */
|
||||
border-radius: 12rpx;
|
||||
background-color: #f8f8f8; /* 图片加载前的占位背景 */
|
||||
}
|
||||
}
|
||||
|
||||
/* 右侧内容区域 */
|
||||
.item-content {
|
||||
flex: 1; /* 占满剩余空间 */
|
||||
display: flex;
|
||||
flex-direction: column; /* 垂直排列 */
|
||||
justify-content: space-between; /* 上下两端对齐:顶部是信息,底部是价格 */
|
||||
overflow: hidden;
|
||||
|
||||
/* 上部信息区 */
|
||||
.top-info {
|
||||
.item-title {
|
||||
font-size: 30rpx;
|
||||
font-weight: 700; /* 标题加粗 */
|
||||
color: #1F2937; /* 深黑灰,易读 */
|
||||
margin-bottom: 10rpx;
|
||||
line-height: 1.4;
|
||||
/* 限制显示两行,超出省略 */
|
||||
display: -webkit-box;
|
||||
-webkit-line-clamp: 2;
|
||||
-webkit-box-orient: vertical;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
/* 标签行布局 */
|
||||
.tags-row {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
margin-bottom: 10rpx;
|
||||
|
||||
/* OTC/Rx 标签样式 */
|
||||
.tag-otc {
|
||||
font-size: 20rpx;
|
||||
padding: 0 8rpx;
|
||||
border-radius: 4rpx;
|
||||
margin-right: 10rpx;
|
||||
border: 1px solid;
|
||||
line-height: 28rpx;
|
||||
|
||||
/* 绿/红 配色方案 */
|
||||
&.green { color: #10B981; border-color: #10B981; }
|
||||
&.red { color: #EF4444; border-color: #EF4444; }
|
||||
}
|
||||
|
||||
/* 规格文本样式 */
|
||||
.tag-spec {
|
||||
font-size: 24rpx;
|
||||
color: #6B7280; /* 灰色 */
|
||||
}
|
||||
}
|
||||
|
||||
/* 主治功能描述 */
|
||||
.item-function {
|
||||
font-size: 22rpx;
|
||||
color: #9CA3AF; /* 浅灰,弱化显示 */
|
||||
/* 限制单行显示 */
|
||||
display: -webkit-box;
|
||||
-webkit-line-clamp: 1;
|
||||
-webkit-box-orient: vertical;
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
|
||||
/* 底部价格与按钮区 */
|
||||
.item-bottom {
|
||||
display: flex;
|
||||
justify-content: space-between; /* 价格在左,按钮在右 */
|
||||
align-items: flex-end; /* 底部对齐 */
|
||||
margin-top: 10rpx;
|
||||
|
||||
/* 价格样式 */
|
||||
.price-section {
|
||||
color: #EF4444; /* 价格红 */
|
||||
font-weight: bold;
|
||||
.currency { font-size: 24rpx; margin-right: 2rpx; }
|
||||
.price-val { font-size: 36rpx; } /* 数字放大 */
|
||||
}
|
||||
|
||||
/* 购物车按钮样式 */
|
||||
.cart-btn {
|
||||
width: 56rpx;
|
||||
height: 56rpx;
|
||||
border-radius: 50%;
|
||||
/* 按钮背景:保持品牌蓝色渐变 */
|
||||
background: linear-gradient(135deg, #4A90E2, #5B8FF9);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
/* 按钮投影 */
|
||||
box-shadow: 0 4rpx 10rpx rgba(74, 144, 226, 0.3);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.item-image {
|
||||
width: 200rpx;
|
||||
height: 200rpx;
|
||||
margin-right: 24rpx;
|
||||
border-radius: 16rpx;
|
||||
border: 3rpx solid #f0f5ff;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.item-content {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.item-title {
|
||||
font-size: 32rpx;
|
||||
font-weight: 600;
|
||||
color: #232323;
|
||||
margin-bottom: 16rpx;
|
||||
line-height: 1.4;
|
||||
display: -webkit-box;
|
||||
-webkit-line-clamp: 2;
|
||||
-webkit-box-orient: vertical;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
|
||||
.item-spec {
|
||||
display: flex;
|
||||
align-items: flex-start;
|
||||
margin-bottom: 10rpx;
|
||||
font-size: 26rpx;
|
||||
}
|
||||
|
||||
.spec-label {
|
||||
background: linear-gradient(135deg, #4A90E2, #5B8FF9);
|
||||
color: #ffffff;
|
||||
padding: 4rpx 12rpx;
|
||||
border-radius: 6rpx;
|
||||
margin-right: 12rpx;
|
||||
flex-shrink: 0;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.spec-value {
|
||||
color: #666;
|
||||
flex: 1;
|
||||
line-height: 1.6;
|
||||
display: -webkit-box;
|
||||
-webkit-line-clamp: 2;
|
||||
-webkit-box-orient: vertical;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
|
||||
.item-bottom {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
padding-top: 16rpx;
|
||||
margin-top: auto;
|
||||
border-top: 2rpx solid #f0f5ff;
|
||||
}
|
||||
|
||||
.price-section {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 6rpx;
|
||||
}
|
||||
|
||||
.price-tag {
|
||||
font-size: 36rpx;
|
||||
font-weight: 700;
|
||||
color: #FF6B6B;
|
||||
}
|
||||
|
||||
.stock-tag {
|
||||
font-size: 24rpx;
|
||||
color: #52C41A;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.cart-icon-btn {
|
||||
width: 80rpx;
|
||||
height: 80rpx;
|
||||
border-radius: 50%;
|
||||
background: linear-gradient(135deg, #4A90E2, #5B8FF9);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
box-shadow: 0 6rpx 20rpx rgba(74,144,226,0.3);
|
||||
transition: all 0.3s ease;
|
||||
|
||||
&:active {
|
||||
transform: scale(0.9);
|
||||
box-shadow: 0 3rpx 12rpx rgba(74,144,226,0.4);
|
||||
}
|
||||
}
|
||||
|
||||
/* 购物车悬浮球样式 */
|
||||
.cart-float {
|
||||
position: fixed;
|
||||
width: 110rpx;
|
||||
height: 110rpx;
|
||||
background: linear-gradient(135deg, #FF6B6B, #FF8E8E);
|
||||
border-radius: 50%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
box-shadow: 0 8rpx 28rpx rgba(255, 107, 107, 0.4);
|
||||
z-index: 999;
|
||||
transition: all 0.3s ease;
|
||||
|
||||
&:active {
|
||||
transform: scale(0.92);
|
||||
.cart-icon-inner {
|
||||
width: 100rpx;
|
||||
height: 100rpx;
|
||||
/* 悬浮球背景:品牌蓝色渐变 */
|
||||
background: linear-gradient(135deg, #4A90E2, #5B8FF9);
|
||||
border-radius: 50%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
box-shadow: 0 8rpx 20rpx rgba(74, 144, 226, 0.4);
|
||||
position: relative;
|
||||
|
||||
/* 数量角标 */
|
||||
.badge {
|
||||
position: absolute;
|
||||
top: -6rpx;
|
||||
right: -6rpx;
|
||||
background: #EF4444;
|
||||
color: #fff;
|
||||
font-size: 20rpx;
|
||||
padding: 2rpx 10rpx;
|
||||
border-radius: 20rpx;
|
||||
border: 2rpx solid #fff;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.cart-badge {
|
||||
position: absolute;
|
||||
top: -8rpx;
|
||||
right: -8rpx;
|
||||
}
|
||||
|
||||
/* 弹窗内容样式 */
|
||||
.popup-content {
|
||||
padding: 40rpx;
|
||||
padding-bottom: calc(60rpx + env(safe-area-inset-bottom));
|
||||
}
|
||||
padding: 30rpx 30rpx 60rpx;
|
||||
background: #fff;
|
||||
|
||||
.popup-header {
|
||||
margin-bottom: 40rpx;
|
||||
text-align: center;
|
||||
padding-bottom: 30rpx;
|
||||
border-bottom: 2rpx solid #f0f5ff;
|
||||
}
|
||||
.product-header-row {
|
||||
display: flex;
|
||||
margin-bottom: 40rpx;
|
||||
|
||||
.popup-title {
|
||||
font-size: 38rpx;
|
||||
font-weight: 700;
|
||||
color: #232323;
|
||||
}
|
||||
.popup-img {
|
||||
width: 180rpx;
|
||||
height: 180rpx;
|
||||
border-radius: 12rpx;
|
||||
margin-right: 24rpx;
|
||||
background: #f8f8f8;
|
||||
}
|
||||
|
||||
.product-info {
|
||||
display: flex;
|
||||
margin-bottom: 50rpx;
|
||||
padding: 30rpx;
|
||||
background: linear-gradient(135deg, #f8fbff, #ffffff);
|
||||
border-radius: 20rpx;
|
||||
border: 2rpx solid #f0f5ff;
|
||||
}
|
||||
.popup-info {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: flex-end;
|
||||
|
||||
.product-image {
|
||||
width: 140rpx;
|
||||
height: 140rpx;
|
||||
border-radius: 16rpx;
|
||||
margin-right: 24rpx;
|
||||
border: 2rpx solid #f0f5ff;
|
||||
}
|
||||
.price-row {
|
||||
color: #EF4444;
|
||||
font-size: 28rpx;
|
||||
font-weight: bold;
|
||||
.big { font-size: 44rpx; margin-left: 4rpx; }
|
||||
}
|
||||
.stock-row { font-size: 22rpx; color: #6B7280; margin: 8rpx 0; }
|
||||
.selected-spec { font-size: 24rpx; color: #374151; }
|
||||
}
|
||||
}
|
||||
|
||||
.product-details {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: space-between;
|
||||
}
|
||||
.quantity-section {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 60rpx;
|
||||
|
||||
.product-name {
|
||||
font-size: 30rpx;
|
||||
font-weight: 600;
|
||||
color: #232323;
|
||||
margin-bottom: 12rpx;
|
||||
line-height: 1.4;
|
||||
}
|
||||
.label {
|
||||
font-size: 30rpx;
|
||||
color: #1F2937;
|
||||
font-weight: 500;
|
||||
}
|
||||
}
|
||||
|
||||
.product-spec {
|
||||
font-size: 26rpx;
|
||||
color: #999;
|
||||
margin-bottom: 16rpx;
|
||||
}
|
||||
.popup-footer {
|
||||
.action-btn {
|
||||
width: 100%;
|
||||
height: 88rpx;
|
||||
line-height: 88rpx;
|
||||
text-align: center;
|
||||
border-radius: 44rpx;
|
||||
font-size: 32rpx;
|
||||
font-weight: 600;
|
||||
|
||||
.product-price {
|
||||
font-size: 36rpx;
|
||||
font-weight: 700;
|
||||
color: #FF6B6B;
|
||||
}
|
||||
&.add-cart {
|
||||
background: linear-gradient(90deg, #4A90E2, #5B8FF9);
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
.quantity-selector {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 60rpx;
|
||||
padding: 35rpx 0;
|
||||
border-top: 2rpx solid #f0f5ff;
|
||||
border-bottom: 2rpx solid #f0f5ff;
|
||||
}
|
||||
|
||||
.quantity-label {
|
||||
font-size: 32rpx;
|
||||
color: #232323;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
.popup-actions {
|
||||
display: flex;
|
||||
gap: 20rpx;
|
||||
}
|
||||
|
||||
.cancel-btn {
|
||||
flex: 1;
|
||||
background: #f5f5f5;
|
||||
color: #666;
|
||||
border: none;
|
||||
border-radius: 50rpx;
|
||||
padding: 28rpx 0;
|
||||
font-size: 32rpx;
|
||||
font-weight: 600;
|
||||
|
||||
&:active {
|
||||
background: #e8e8e8;
|
||||
&:active { opacity: 0.9; }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.confirm-btn {
|
||||
flex: 2;
|
||||
background: linear-gradient(135deg, #4A90E2, #5B8FF9);
|
||||
color: #ffffff;
|
||||
border: none;
|
||||
border-radius: 50rpx;
|
||||
padding: 28rpx 0;
|
||||
font-size: 32rpx;
|
||||
font-weight: 600;
|
||||
box-shadow: 0 6rpx 20rpx rgba(74,144,226,0.3);
|
||||
|
||||
&:active {
|
||||
opacity: 0.85;
|
||||
box-shadow: 0 3rpx 12rpx rgba(74,144,226,0.4);
|
||||
}
|
||||
.empty-state {
|
||||
margin-top: 100rpx;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
autoplay
|
||||
circular
|
||||
indicator-color="rgba(255,255,255,0.6)"
|
||||
indicator-active-color="#536DFE"
|
||||
indicator-active-color="#4175EE"
|
||||
>
|
||||
<swiper-item v-for="(img, index) in productImages" :key="index">
|
||||
<image
|
||||
@@ -19,14 +19,6 @@
|
||||
/>
|
||||
</swiper-item>
|
||||
</swiper>
|
||||
<!-- 收藏按钮 -->
|
||||
<view class="favorite-btn" @click="toggleFavorite">
|
||||
<u-icon
|
||||
:name="isFavorite ? 'heart-fill' : 'heart'"
|
||||
:color="isFavorite ? '#FF5252' : '#fff'"
|
||||
size="24"
|
||||
/>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 商品基本信息 -->
|
||||
@@ -36,11 +28,9 @@
|
||||
<text class="original-price" v-if="productDetail.daijian_price">
|
||||
¥{{ productDetail.daijian_price }}
|
||||
</text>
|
||||
<view class="sales-tag" v-if="productDetail.is_otc === 0">
|
||||
<text>处方药</text>
|
||||
</view>
|
||||
<view class="sales-tag" v-else>
|
||||
<text>非处方药</text>
|
||||
<!-- 优化标签颜色:使用医疗蓝或标准的警告色 -->
|
||||
<view class="sales-tag" :class="productDetail.is_otc === 0 ? 'tag-rx' : 'tag-otc'">
|
||||
<text>{{ productDetail.is_otc === 0 ? '处方药' : 'OTC 非处方药' }}</text>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
@@ -49,7 +39,7 @@
|
||||
|
||||
<view class="meta-info">
|
||||
<view class="meta-item">
|
||||
<u-icon name="file-text" size="16" color="#999"></u-icon>
|
||||
<u-icon name="file-text" size="28" color="#999"></u-icon>
|
||||
<text>规格:{{ productDetail.specification || '暂无' }}</text>
|
||||
</view>
|
||||
</view>
|
||||
@@ -93,7 +83,7 @@
|
||||
@click="previewInstruction"
|
||||
/>
|
||||
<view v-else class="no-instruction">
|
||||
<u-icon name="file-text" size="48" color="#999"></u-icon>
|
||||
<u-icon name="file-text" size="60" color="#999"></u-icon>
|
||||
<text>暂无说明书,详见产品内部的说明书</text>
|
||||
</view>
|
||||
</view>
|
||||
@@ -103,11 +93,11 @@
|
||||
<u-popup
|
||||
v-model="showCartPopup"
|
||||
mode="bottom"
|
||||
border-radius="20"
|
||||
border-radius="24"
|
||||
:closeable="true"
|
||||
@close="closeCartPopup"
|
||||
>
|
||||
<view class="cart-popup">
|
||||
<view class="cart-popup safe-area-bottom">
|
||||
<view class="popup-header">
|
||||
<text class="popup-title">选择购买数量</text>
|
||||
</view>
|
||||
@@ -150,11 +140,11 @@
|
||||
<u-popup
|
||||
v-model="showBuyPopup"
|
||||
mode="bottom"
|
||||
border-radius="20"
|
||||
border-radius="24"
|
||||
:closeable="true"
|
||||
@close="closeBuyPopup"
|
||||
>
|
||||
<view class="cart-popup">
|
||||
<view class="cart-popup safe-area-bottom">
|
||||
<view class="popup-header">
|
||||
<text class="popup-title">选择购买数量</text>
|
||||
</view>
|
||||
@@ -197,11 +187,11 @@
|
||||
<u-popup
|
||||
v-model="showPrescriptionFormPopup"
|
||||
mode="bottom"
|
||||
border-radius="20"
|
||||
border-radius="24"
|
||||
:closeable="true"
|
||||
@close="closePrescriptionFormPopup"
|
||||
>
|
||||
<view class="prescription-popup">
|
||||
<view class="prescription-popup safe-area-bottom">
|
||||
<view class="popup-header">
|
||||
<text class="popup-title">请填写用药信息</text>
|
||||
</view>
|
||||
@@ -234,27 +224,24 @@
|
||||
</view>
|
||||
|
||||
<u-form :model="prescriptionFormData" ref="prescriptionForm">
|
||||
<!-- 是否就诊过 -->
|
||||
<view class="form-item-wrapper">
|
||||
<u-form-item label="是否就诊过" prop="hasVisited" label-width="200">
|
||||
<u-radio-group v-model="prescriptionFormData.hasVisited">
|
||||
<u-radio name="1" style="margin-right: 60rpx;">是</u-radio>
|
||||
<u-radio name="0">否</u-radio>
|
||||
<u-radio name="1" active-color="#4175EE" style="margin-right: 60rpx;">是</u-radio>
|
||||
<u-radio name="0" active-color="#4175EE">否</u-radio>
|
||||
</u-radio-group>
|
||||
</u-form-item>
|
||||
</view>
|
||||
|
||||
<!-- 是否用过此药 -->
|
||||
<view class="form-item-wrapper">
|
||||
<u-form-item label="是否用过此药" prop="hasUsedDrug" label-width="200">
|
||||
<u-radio-group v-model="prescriptionFormData.hasUsedDrug">
|
||||
<u-radio name="1" style="margin-right: 60rpx;">是</u-radio>
|
||||
<u-radio name="0">否</u-radio>
|
||||
<u-radio name="1" active-color="#4175EE" style="margin-right: 60rpx;">是</u-radio>
|
||||
<u-radio name="0" active-color="#4175EE">否</u-radio>
|
||||
</u-radio-group>
|
||||
</u-form-item>
|
||||
</view>
|
||||
|
||||
<!-- 患病信息 -->
|
||||
<view class="form-item-wrapper">
|
||||
<u-form-item label="患病信息" prop="illnessInfo" label-width="200">
|
||||
<u-input
|
||||
@@ -275,7 +262,7 @@
|
||||
</view>
|
||||
</u-popup>
|
||||
|
||||
<!-- 患病信息选择器 - 需要放在最外层避免被弹窗遮挡 -->
|
||||
<!-- 患病信息选择器 -->
|
||||
<u-picker
|
||||
v-model="showIllnessPicker"
|
||||
mode="selector"
|
||||
@@ -283,24 +270,43 @@
|
||||
range-key="label"
|
||||
@confirm="onIllnessConfirm"
|
||||
:mask-close-able="true"
|
||||
confirm-color="#4175EE"
|
||||
></u-picker>
|
||||
|
||||
<!-- 底部操作栏 -->
|
||||
<!-- 底部操作栏:关键优化点 -->
|
||||
<view class="footer">
|
||||
<view class="footer-left">
|
||||
<!-- 购物车入口:增加徽标 Badge -->
|
||||
<view class="action-item" @click="goToCart">
|
||||
<u-icon name="shopping-cart" size="24" color="#666"></u-icon>
|
||||
<view class="icon-wrap">
|
||||
<u-icon name="shopping-cart" size="40" color="#666"></u-icon>
|
||||
<!-- 修复购物车徽标位置,使用绝对定位的u-badge或自定义样式 -->
|
||||
<u-badge
|
||||
:count="cartCount"
|
||||
type="error"
|
||||
size="mini"
|
||||
:offset="[-8, -8]"
|
||||
absolute
|
||||
v-if="cartCount > 0"
|
||||
></u-badge>
|
||||
</view>
|
||||
<text class="action-text">购物车</text>
|
||||
</view>
|
||||
<view class="action-item" @click="goBack">
|
||||
<u-icon name="home" size="24" color="#666"></u-icon>
|
||||
<view class="icon-wrap">
|
||||
<u-icon name="home" size="40" color="#666"></u-icon>
|
||||
</view>
|
||||
<text class="action-text">首页</text>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 按钮组:优化配色 -->
|
||||
<view class="footer-right">
|
||||
<!-- 加入购物车:浅色/辅助色 -->
|
||||
<button class="add-cart-btn" @click="showCartPopup = true">加入购物车</button>
|
||||
<!-- 立即购买:主品牌色 -->
|
||||
<button class="buy-now-btn" @click="handleBuyNow">
|
||||
{{ productDetail.is_otc === 0 ? '立即购买' : '立即下单' }}
|
||||
{{ productDetail.is_otc === 0 ? '立即咨询' : '立即购买' }}
|
||||
</button>
|
||||
</view>
|
||||
</view>
|
||||
@@ -308,6 +314,7 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
// 保持脚本逻辑不变,仅确保API引用正确
|
||||
import {getOrderTextApi, getStoreDrugDetailApi} from "@/request/api/product";
|
||||
import { genOrderApi } from "@/request/api/order";
|
||||
import { getCartCountsApi, saveCartApi } from "@/request/api/cart";
|
||||
@@ -349,16 +356,10 @@ export default {
|
||||
isFavorite: false,
|
||||
cartCount: 0,
|
||||
submitted: false,
|
||||
|
||||
// 购物车弹窗数据
|
||||
showCartPopup: false,
|
||||
cartQuantity: 1,
|
||||
|
||||
// 立即购买弹窗数据(非处方药)
|
||||
showBuyPopup: false,
|
||||
buyQuantity: 1,
|
||||
|
||||
// 处方药表单弹窗数据
|
||||
showPrescriptionFormPopup: false,
|
||||
prescriptionQuantity: 1,
|
||||
prescriptionFormData: {
|
||||
@@ -366,14 +367,12 @@ export default {
|
||||
hasUsedDrug: '1',
|
||||
illnessInfo: '',
|
||||
},
|
||||
|
||||
illnessOptions: [],
|
||||
showIllnessPicker: false,
|
||||
orderText: '本次商品物流配送,由萧康医药提供服务。',
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
// 计算商品价格,优先使用drug_store_drug.price
|
||||
productPrice() {
|
||||
if (this.productDetail.drug_store_drug && this.productDetail.drug_store_drug.price) {
|
||||
return parseFloat(this.productDetail.drug_store_drug.price);
|
||||
@@ -383,7 +382,6 @@ export default {
|
||||
},
|
||||
onLoad(options) {
|
||||
if (options.id) {
|
||||
// 从options中获取传递的参数
|
||||
this.productDetail.id = options.id;
|
||||
this.formData.id = options.id;
|
||||
this.formData.type = options.type || '';
|
||||
@@ -391,17 +389,11 @@ export default {
|
||||
this.formData.price = parseFloat(options.price || 0);
|
||||
this.formData.doctor_id = options.doctor_id || '';
|
||||
this.formData.drug_name = options.drug_name || '';
|
||||
|
||||
// 设置productDetail的基本信息
|
||||
this.productDetail.id = options.id;
|
||||
this.productDetail.drug_name = options.drug_name || '';
|
||||
this.productDetail.image = options.image || '';
|
||||
this.productDetail.price = parseFloat(options.price || 0);
|
||||
|
||||
// 加载商品详情
|
||||
this.getDetail();
|
||||
} else {
|
||||
// 如果没有id参数,尝试从本地存储获取
|
||||
const savedId = uni.getStorageSync('symptoms_id');
|
||||
if (savedId) {
|
||||
this.productDetail.id = savedId;
|
||||
@@ -409,8 +401,6 @@ export default {
|
||||
this.getDetail();
|
||||
}
|
||||
}
|
||||
|
||||
// 更新购物车数量
|
||||
this.updateCartCount();
|
||||
},
|
||||
onShow() {
|
||||
@@ -426,7 +416,6 @@ export default {
|
||||
console.error('获取订单提示失败:', err);
|
||||
})
|
||||
},
|
||||
// 获取商品详情 - 保留原有的getDetail方法
|
||||
getDetail() {
|
||||
let that = this;
|
||||
this.getOrderText();
|
||||
@@ -435,44 +424,22 @@ export default {
|
||||
}).then((res) => {
|
||||
if (res.data.code === 0) {
|
||||
const data = res.data.result;
|
||||
|
||||
// 更新productDetail
|
||||
Object.assign(this.productDetail, data);
|
||||
|
||||
// 处理商品图片
|
||||
this.productImages = data.image ? [data.image] : [];
|
||||
|
||||
// 处理功效信息
|
||||
if (data.indications_array && data.indications_array.length > 0) {
|
||||
this.illnessOptions = data.indications_array.map(item => ({
|
||||
value: item.label || item.value,
|
||||
label: item.label || item.value
|
||||
}));
|
||||
}
|
||||
|
||||
// 如果没有功效信息,使用function字段
|
||||
if (!this.productDetail.indications && data.function) {
|
||||
this.productDetail.indications = data.function;
|
||||
}
|
||||
|
||||
console.log('商品详情加载成功:', this.productDetail);
|
||||
console.log('商品价格:', this.productPrice);
|
||||
}
|
||||
}).catch(error => {
|
||||
console.error('加载商品详情失败:', error);
|
||||
uni.showToast({
|
||||
title: '加载失败',
|
||||
icon: 'none'
|
||||
});
|
||||
});
|
||||
},
|
||||
|
||||
updateTotalPrice() {
|
||||
// 保留原有的更新总价逻辑
|
||||
return (this.productPrice * this.formData.number).toFixed(2);
|
||||
},
|
||||
|
||||
// 图片预览
|
||||
previewImage(index) {
|
||||
if (this.productImages.length > 0) {
|
||||
uni.previewImage({
|
||||
@@ -481,8 +448,6 @@ export default {
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
// 说明书预览
|
||||
previewInstruction() {
|
||||
if (this.productDetail.instruction) {
|
||||
uni.previewImage({
|
||||
@@ -490,17 +455,6 @@ export default {
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
// 收藏功能
|
||||
toggleFavorite() {
|
||||
this.isFavorite = !this.isFavorite;
|
||||
uni.showToast({
|
||||
title: this.isFavorite ? '已收藏' : '已取消收藏',
|
||||
icon: 'none'
|
||||
});
|
||||
},
|
||||
|
||||
// 更新购物车数量
|
||||
updateCartCount() {
|
||||
getCartCountsApi({
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
@@ -512,8 +466,6 @@ export default {
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
// 加入购物车
|
||||
addToCart() {
|
||||
saveCartApi({
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
@@ -522,33 +474,20 @@ export default {
|
||||
}).then(() => {
|
||||
this.updateCartCount();
|
||||
this.closeCartPopup();
|
||||
|
||||
uni.showToast({
|
||||
title: `已加入${this.cartQuantity}件商品`,
|
||||
icon: 'success',
|
||||
duration: 1500
|
||||
});
|
||||
}).catch(error => {
|
||||
console.error('加入购物车失败:', error);
|
||||
uni.showToast({
|
||||
title: '加入购物车失败',
|
||||
icon: 'none'
|
||||
});
|
||||
});
|
||||
})
|
||||
},
|
||||
|
||||
// 处理立即购买
|
||||
handleBuyNow() {
|
||||
if (this.productDetail.is_otc === 0) {
|
||||
// 处方药:显示表单弹窗
|
||||
this.showPrescriptionFormPopup = true;
|
||||
} else {
|
||||
// 非处方药:显示数量选择弹窗
|
||||
this.showBuyPopup = true;
|
||||
}
|
||||
},
|
||||
|
||||
// 非处方药立即下单
|
||||
buyNowConfirm() {
|
||||
genOrderApi({
|
||||
drug_id: this.productDetail.id,
|
||||
@@ -559,105 +498,57 @@ export default {
|
||||
uni.navigateTo({
|
||||
url: `/subPackages/my/my-drug/drug-info?id=${resOrder.data.result.id}&order_type=${resOrder.data.result.order_type}`
|
||||
});
|
||||
}).catch(error => {
|
||||
console.error('下单失败:', error);
|
||||
uni.showToast({
|
||||
title: '下单失败',
|
||||
icon: 'none'
|
||||
});
|
||||
});
|
||||
})
|
||||
},
|
||||
|
||||
// 提交处方药表单
|
||||
submitPrescriptionForm() {
|
||||
// 验证表单
|
||||
if (!this.prescriptionFormData.hasVisited) {
|
||||
if (!this.prescriptionFormData.hasVisited || !this.prescriptionFormData.hasUsedDrug || !this.prescriptionFormData.illnessInfo) {
|
||||
uni.showToast({
|
||||
title: '请选择是否就诊过',
|
||||
title: '请填写完整信息',
|
||||
icon: 'none'
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.prescriptionFormData.hasUsedDrug) {
|
||||
uni.showToast({
|
||||
title: '请选择是否用过此药',
|
||||
icon: 'none'
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.prescriptionFormData.illnessInfo) {
|
||||
uni.showToast({
|
||||
title: '请选择患病信息',
|
||||
icon: 'none'
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
// 设置submitted状态
|
||||
this.submitted = true;
|
||||
|
||||
// 处方药流程
|
||||
uni.showToast({
|
||||
title: '信息提交成功',
|
||||
icon: 'success'
|
||||
});
|
||||
|
||||
// 关闭弹窗
|
||||
this.closePrescriptionFormPopup();
|
||||
|
||||
// 准备跳转数据 - 包含购买数量
|
||||
const rInfo = {
|
||||
id: this.productDetail.id,
|
||||
drug_name: this.productDetail.drug_name,
|
||||
image: this.productDetail.image,
|
||||
price: this.productPrice,
|
||||
number: this.prescriptionQuantity, // 使用处方药弹窗中的购买数量
|
||||
number: this.prescriptionQuantity,
|
||||
hasVisited: this.prescriptionFormData.hasVisited,
|
||||
hasUsedDrug: this.prescriptionFormData.hasUsedDrug,
|
||||
illnessInfo: this.prescriptionFormData.illnessInfo,
|
||||
doctor_id: this.formData.doctor_id,
|
||||
type: this.formData.type
|
||||
};
|
||||
|
||||
// 跳转到医生信息页
|
||||
uni.navigateTo({
|
||||
url: `/subPackages/doctor/doctor-userinfo?id=${this.formData.doctor_id}&r_info=${JSON.stringify(rInfo)}&r_type=${this.formData.type}`
|
||||
});
|
||||
},
|
||||
|
||||
// 跳转购物车
|
||||
goToCart() {
|
||||
uni.navigateTo({
|
||||
url: '/subPackages/shop/shop-cate'
|
||||
});
|
||||
},
|
||||
|
||||
// 返回首页
|
||||
goBack() {
|
||||
uni.navigateBack({
|
||||
delta: 1
|
||||
});
|
||||
},
|
||||
|
||||
// 患病信息选择
|
||||
onIllnessConfirm(e) {
|
||||
const index = e[0];
|
||||
this.prescriptionFormData.illnessInfo = this.illnessOptions[index].value;
|
||||
this.showIllnessPicker = false;
|
||||
},
|
||||
|
||||
closeCartPopup() {
|
||||
this.showCartPopup = false;
|
||||
this.cartQuantity = 1;
|
||||
},
|
||||
|
||||
closeBuyPopup() {
|
||||
this.showBuyPopup = false;
|
||||
this.buyQuantity = 1;
|
||||
},
|
||||
|
||||
closePrescriptionFormPopup() {
|
||||
this.showPrescriptionFormPopup = false;
|
||||
this.prescriptionQuantity = 1;
|
||||
@@ -675,7 +566,9 @@ export default {
|
||||
.container {
|
||||
background-color: #f5f8ff;
|
||||
min-height: 100vh;
|
||||
padding-bottom: 120rpx; // 为底部操作栏留出空间
|
||||
// 底部留白 = 固定操作栏高度 + 安全距离 + 额外间距
|
||||
padding-bottom: calc(120rpx + constant(safe-area-inset-bottom));
|
||||
padding-bottom: calc(120rpx + env(safe-area-inset-bottom));
|
||||
}
|
||||
|
||||
// 轮播图区域
|
||||
@@ -693,20 +586,6 @@ export default {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.favorite-btn {
|
||||
position: absolute;
|
||||
right: 30rpx;
|
||||
top: 30rpx;
|
||||
width: 60rpx;
|
||||
height: 60rpx;
|
||||
background: rgba(0, 0, 0, 0.3);
|
||||
border-radius: 50%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
z-index: 10;
|
||||
}
|
||||
}
|
||||
|
||||
// 基本信息区域
|
||||
@@ -735,11 +614,21 @@ export default {
|
||||
}
|
||||
|
||||
.sales-tag {
|
||||
background: linear-gradient(135deg, #ff7875, #ff4d4f);
|
||||
color: white;
|
||||
padding: 6rpx 16rpx;
|
||||
padding: 4rpx 16rpx;
|
||||
border-radius: 20rpx;
|
||||
font-size: 22rpx;
|
||||
|
||||
&.tag-rx {
|
||||
background: #ffe5e5;
|
||||
color: #ff4d4f;
|
||||
border: 1px solid #ff4d4f;
|
||||
}
|
||||
|
||||
&.tag-otc {
|
||||
background: #e6f7ff;
|
||||
color: #00B578;
|
||||
border: 1px solid #00B578;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -761,27 +650,30 @@ export default {
|
||||
.meta-item {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
font-size: 24rpx;
|
||||
font-size: 26rpx;
|
||||
color: #666;
|
||||
margin-bottom: 8rpx;
|
||||
background: #f9f9f9;
|
||||
padding: 10rpx 20rpx;
|
||||
border-radius: 8rpx;
|
||||
display: inline-flex;
|
||||
|
||||
u-icon {
|
||||
margin-right: 8rpx;
|
||||
margin-right: 12rpx;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* 新增:物流提示样式 */
|
||||
// 物流提示
|
||||
.order-text-tip {
|
||||
background: #e6f3ff;
|
||||
padding: 20rpx 30rpx;
|
||||
margin: 0 20rpx 20rpx 20rpx;
|
||||
border-radius: 8rpx;
|
||||
border-radius: 12rpx;
|
||||
font-size: 26rpx;
|
||||
color: #1890ff;
|
||||
line-height: 1.4;
|
||||
border-left: 6rpx solid #1890ff;
|
||||
color: #4175EE; // 统一为医疗蓝
|
||||
line-height: 1.5;
|
||||
border-left: 8rpx solid #4175EE;
|
||||
}
|
||||
|
||||
// 详情区域
|
||||
@@ -794,9 +686,9 @@ export default {
|
||||
font-size: 32rpx;
|
||||
font-weight: bold;
|
||||
color: #333;
|
||||
margin-bottom: 20rpx;
|
||||
margin-bottom: 24rpx;
|
||||
position: relative;
|
||||
padding-left: 20rpx;
|
||||
padding-left: 24rpx;
|
||||
|
||||
&::before {
|
||||
content: "";
|
||||
@@ -804,106 +696,78 @@ export default {
|
||||
left: 0;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
width: 6rpx;
|
||||
height: 30rpx;
|
||||
background: #536DFE;
|
||||
border-radius: 3rpx;
|
||||
width: 8rpx;
|
||||
height: 32rpx;
|
||||
background: #4175EE; // 统一颜色
|
||||
border-radius: 4rpx;
|
||||
}
|
||||
}
|
||||
|
||||
.section-content {
|
||||
font-size: 28rpx;
|
||||
color: #666;
|
||||
line-height: 1.6;
|
||||
color: #555;
|
||||
line-height: 1.8;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
// 说明书区域
|
||||
.instruction-content {
|
||||
.instruction-image {
|
||||
width: 100%;
|
||||
border-radius: 12rpx;
|
||||
box-shadow: 0 4rpx 12rpx rgba(0,0,0,0.05);
|
||||
}
|
||||
|
||||
.no-instruction {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
padding: 60rpx 0;
|
||||
|
||||
u-icon {
|
||||
margin-bottom: 20rpx;
|
||||
}
|
||||
|
||||
text {
|
||||
font-size: 28rpx;
|
||||
color: #999;
|
||||
text-align: center;
|
||||
}
|
||||
u-icon { margin-bottom: 20rpx; }
|
||||
text { font-size: 28rpx; color: #999; }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 表单区域
|
||||
// 通用表单项间距
|
||||
.form-item-wrapper {
|
||||
margin-bottom: 30rpx;
|
||||
|
||||
&:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
// 购物车/购买弹窗
|
||||
.cart-popup {
|
||||
// 弹窗通用样式
|
||||
.cart-popup, .prescription-popup {
|
||||
padding: 40rpx;
|
||||
padding-bottom: 20rpx; // 基础padding,不含安全距离
|
||||
|
||||
// 弹窗底部增加安全距离
|
||||
&.safe-area-bottom {
|
||||
padding-bottom: calc(20rpx + constant(safe-area-inset-bottom));
|
||||
padding-bottom: calc(20rpx + env(safe-area-inset-bottom));
|
||||
}
|
||||
|
||||
.popup-header {
|
||||
margin-bottom: 40rpx;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.popup-title {
|
||||
font-size: 36rpx;
|
||||
font-weight: 600;
|
||||
color: #2c3e50;
|
||||
.popup-title { font-size: 36rpx; font-weight: 600; color: #333; }
|
||||
}
|
||||
|
||||
.product-info {
|
||||
display: flex;
|
||||
margin-bottom: 40rpx;
|
||||
|
||||
.product-image {
|
||||
width: 120rpx;
|
||||
height: 120rpx;
|
||||
width: 140rpx;
|
||||
height: 140rpx;
|
||||
border-radius: 12rpx;
|
||||
margin-right: 24rpx;
|
||||
border: 1px solid #f0f0f0;
|
||||
}
|
||||
|
||||
.product-details {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: space-between;
|
||||
|
||||
.product-name {
|
||||
font-size: 30rpx;
|
||||
font-weight: 500;
|
||||
color: #2c3e50;
|
||||
margin-bottom: 8rpx;
|
||||
line-height: 1.4;
|
||||
}
|
||||
|
||||
.product-spec {
|
||||
font-size: 24rpx;
|
||||
color: #95a5a6;
|
||||
margin-bottom: 12rpx;
|
||||
}
|
||||
|
||||
.product-price {
|
||||
font-size: 32rpx;
|
||||
font-weight: 600;
|
||||
color: #ff4d4f;
|
||||
}
|
||||
.product-name { font-size: 30rpx; font-weight: bold; color: #333; margin-bottom: 8rpx; }
|
||||
.product-spec { font-size: 24rpx; color: #999; margin-bottom: 12rpx; }
|
||||
.product-price { font-size: 36rpx; font-weight: bold; color: #ff4d4f; }
|
||||
}
|
||||
}
|
||||
|
||||
@@ -912,205 +776,87 @@ export default {
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
padding: 30rpx 0;
|
||||
border-top: 1rpx solid #f0f0f0;
|
||||
border-bottom: 1rpx solid #f0f0f0;
|
||||
|
||||
.quantity-label {
|
||||
font-size: 30rpx;
|
||||
color: #2c3e50;
|
||||
font-weight: 500;
|
||||
}
|
||||
border-top: 1rpx solid #f5f5f5;
|
||||
border-bottom: 1rpx solid #f5f5f5;
|
||||
.quantity-label { font-size: 30rpx; color: #333; font-weight: 500; }
|
||||
}
|
||||
|
||||
.popup-actions {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
margin-top: 40rpx;
|
||||
margin-top: 50rpx;
|
||||
gap: 30rpx;
|
||||
|
||||
.cancel-btn {
|
||||
flex: 1;
|
||||
margin-right: 20rpx;
|
||||
background-color: #f8f9fa;
|
||||
color: #95a5a6;
|
||||
border: none;
|
||||
background-color: #f5f7fa;
|
||||
color: #666;
|
||||
border-radius: 50rpx;
|
||||
padding: 24rpx 0;
|
||||
font-size: 30rpx;
|
||||
font-weight: 500;
|
||||
|
||||
&:active {
|
||||
background-color: #e9ecef;
|
||||
}
|
||||
border: none;
|
||||
}
|
||||
|
||||
.confirm-btn {
|
||||
flex: 1;
|
||||
margin-left: 20rpx;
|
||||
background: linear-gradient(135deg, #4A90E2, #3A86FF);
|
||||
// 统一使用医疗蓝渐变
|
||||
background: linear-gradient(135deg, #4A90E2, #4175EE);
|
||||
color: #ffffff;
|
||||
border: none;
|
||||
border-radius: 50rpx;
|
||||
padding: 24rpx 0;
|
||||
font-size: 30rpx;
|
||||
font-weight: 500;
|
||||
|
||||
&:active {
|
||||
opacity: 0.8;
|
||||
}
|
||||
border: none;
|
||||
box-shadow: 0 6rpx 16rpx rgba(65, 117, 238, 0.3);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 处方药表单弹窗
|
||||
.prescription-popup {
|
||||
padding: 40rpx;
|
||||
max-height: 80vh;
|
||||
overflow-y: auto;
|
||||
|
||||
.popup-header {
|
||||
margin-bottom: 40rpx;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.popup-title {
|
||||
font-size: 36rpx;
|
||||
font-weight: 600;
|
||||
color: #2c3e50;
|
||||
}
|
||||
|
||||
.product-info {
|
||||
display: flex;
|
||||
margin-bottom: 40rpx;
|
||||
|
||||
.product-image {
|
||||
width: 120rpx;
|
||||
height: 120rpx;
|
||||
border-radius: 12rpx;
|
||||
margin-right: 24rpx;
|
||||
}
|
||||
|
||||
.product-details {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: space-between;
|
||||
|
||||
.product-name {
|
||||
font-size: 30rpx;
|
||||
font-weight: 500;
|
||||
color: #2c3e50;
|
||||
margin-bottom: 8rpx;
|
||||
line-height: 1.4;
|
||||
}
|
||||
|
||||
.product-spec {
|
||||
font-size: 24rpx;
|
||||
color: #95a5a6;
|
||||
margin-bottom: 12rpx;
|
||||
}
|
||||
|
||||
.product-price {
|
||||
font-size: 32rpx;
|
||||
font-weight: 600;
|
||||
color: #ff4d4f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.quantity-selector {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
padding: 30rpx 0;
|
||||
border-top: 1rpx solid #f0f0f0;
|
||||
border-bottom: 1rpx solid #f0f0f0;
|
||||
|
||||
.quantity-label {
|
||||
font-size: 30rpx;
|
||||
color: #2c3e50;
|
||||
font-weight: 500;
|
||||
}
|
||||
}
|
||||
|
||||
.popup-actions {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
margin-top: 40rpx;
|
||||
|
||||
.cancel-btn {
|
||||
flex: 1;
|
||||
margin-right: 20rpx;
|
||||
background-color: #f8f9fa;
|
||||
color: #95a5a6;
|
||||
border: none;
|
||||
border-radius: 50rpx;
|
||||
padding: 24rpx 0;
|
||||
font-size: 30rpx;
|
||||
font-weight: 500;
|
||||
|
||||
&:active {
|
||||
background-color: #e9ecef;
|
||||
}
|
||||
}
|
||||
|
||||
.confirm-btn {
|
||||
flex: 1;
|
||||
margin-left: 20rpx;
|
||||
background: linear-gradient(135deg, #4A90E2, #3A86FF);
|
||||
color: #ffffff;
|
||||
border: none;
|
||||
border-radius: 50rpx;
|
||||
padding: 24rpx 0;
|
||||
font-size: 30rpx;
|
||||
font-weight: 500;
|
||||
|
||||
&:active {
|
||||
opacity: 0.8;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 底部操作栏
|
||||
// 底部操作栏 - 固定 + 适配
|
||||
.footer {
|
||||
position: fixed;
|
||||
left: 0;
|
||||
bottom: 0;
|
||||
width: 100%;
|
||||
height: 100rpx;
|
||||
// 高度 = 内容高度(110rpx) + 安全距离
|
||||
height: calc(110rpx + constant(safe-area-inset-bottom));
|
||||
height: calc(110rpx + env(safe-area-inset-bottom));
|
||||
padding-bottom: constant(safe-area-inset-bottom);
|
||||
padding-bottom: env(safe-area-inset-bottom);
|
||||
background: #fff;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
padding: 0 20rpx;
|
||||
box-shadow: 0 -2rpx 20rpx rgba(0, 0, 0, 0.1);
|
||||
padding-left: 30rpx;
|
||||
padding-right: 30rpx;
|
||||
box-shadow: 0 -4rpx 20rpx rgba(0, 0, 0, 0.05);
|
||||
z-index: 1000;
|
||||
box-sizing: border-box; // 关键:包含padding在高度内
|
||||
|
||||
.footer-left {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex: 1;
|
||||
flex: 0 0 auto;
|
||||
margin-right: 30rpx;
|
||||
|
||||
.action-item {
|
||||
position: relative;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
margin-right: 40rpx;
|
||||
position: relative;
|
||||
|
||||
.icon-wrap {
|
||||
position: relative; // 为 Badge 绝对定位提供基准
|
||||
width: 48rpx;
|
||||
height: 48rpx;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.action-text {
|
||||
font-size: 20rpx;
|
||||
color: #666;
|
||||
margin-top: 4rpx;
|
||||
}
|
||||
|
||||
.cart-badge-container {
|
||||
position: absolute;
|
||||
top: -10rpx;
|
||||
right: -10rpx;
|
||||
}
|
||||
|
||||
.cart-badge {
|
||||
position: relative;
|
||||
margin-top: 6rpx;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1118,7 +864,8 @@ export default {
|
||||
.footer-right {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex: 2;
|
||||
flex: 1;
|
||||
gap: 20rpx;
|
||||
|
||||
button {
|
||||
flex: 1;
|
||||
@@ -1126,24 +873,29 @@ export default {
|
||||
line-height: 80rpx;
|
||||
border-radius: 40rpx;
|
||||
font-size: 28rpx;
|
||||
font-weight: 500;
|
||||
font-weight: 600;
|
||||
border: none;
|
||||
padding: 0;
|
||||
|
||||
&.add-cart-btn {
|
||||
background: linear-gradient(135deg, #FF9800, #FFB74D);
|
||||
color: white;
|
||||
margin-right: 20rpx;
|
||||
// 加入购物车:浅色风格,避免视觉争抢
|
||||
background: #EBF3FF;
|
||||
color: #4175EE;
|
||||
border: 2rpx solid #EBF3FF;
|
||||
}
|
||||
|
||||
&.buy-now-btn {
|
||||
background: linear-gradient(135deg, #536DFE, #6C8EFF);
|
||||
// 立即购买:强烈的品牌色
|
||||
background: linear-gradient(135deg, #4A90E2, #4175EE);
|
||||
color: white;
|
||||
box-shadow: 0 6rpx 16rpx rgba(65, 117, 238, 0.3);
|
||||
}
|
||||
|
||||
&:active {
|
||||
opacity: 0.8;
|
||||
transform: scale(0.98);
|
||||
opacity: 0.9;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
</style>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<view class="container safe-area-inset-bottom">
|
||||
<!-- 清空购物车 -->
|
||||
<!-- 头部区域:显示数量和清空按钮 -->
|
||||
<view class="head">
|
||||
<view class="num">
|
||||
购物车(共{{ totalCount }}件商品)
|
||||
@@ -11,28 +11,41 @@
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<!-- 商品列表 -->
|
||||
<!-- 商品列表卡片 -->
|
||||
<view class="card">
|
||||
<!-- 门店 -->
|
||||
<!-- 门店名称 -->
|
||||
<view class="store">
|
||||
<text class="iconfont icon-mendian"></text>
|
||||
{{ cartLists.store_name }}
|
||||
</view>
|
||||
|
||||
<!-- 购物车列表循环 -->
|
||||
<u-checkbox-group>
|
||||
<view class="list" v-for="item in cartLists.data" :key="item.id">
|
||||
|
||||
<!-- 复选框 -->
|
||||
<u-checkbox shape="circle" @change="checkboxChange(item)" v-model="item.checked">
|
||||
</u-checkbox>
|
||||
|
||||
|
||||
<view class="img" @click="checkboxChange(item)">
|
||||
<image :src="item.drug.image" mode=""></image>
|
||||
<!-- 商品图片:点击跳转详情 (使用 .stop 阻止冒泡,避免触发选中) -->
|
||||
<view class="img" @click.stop="goProductDetail(item)">
|
||||
<image :src="item.drug.image" mode="aspectFill"></image>
|
||||
</view>
|
||||
|
||||
<!-- 商品信息区域:点击空白处切换选中状态 -->
|
||||
<view class="it" @click="checkboxChange(item)">
|
||||
<view class="it_name">{{ item.drug.drug_name }}</view>
|
||||
<!-- 商品名称:点击跳转详情 (使用 .stop 阻止冒泡) -->
|
||||
<view class="it_name" @click.stop="goProductDetail(item)">{{ item.drug.drug_name }}</view>
|
||||
|
||||
<!-- 规格/用法信息 -->
|
||||
<view class="it_info">{{ item.drug.usage }}</view>
|
||||
|
||||
<!-- 价格与数量控制器 -->
|
||||
<view class="it_price">
|
||||
<text>{{ item.drug.drugstore_drug.price }}</text>
|
||||
<!-- 显示价格 -->
|
||||
<text>¥{{ item.drug.drugstore_drug ? item.drug.drugstore_drug.price : (item.drug.drug_store_relations ? item.drug.drug_store_relations.price : '0.00') }}</text>
|
||||
|
||||
<!-- 步进器:点击阻止冒泡,防止触发选中 -->
|
||||
<view class="it_num" @click.stop>
|
||||
<uni-number-box :min="1" @change="changeNum($event,item)" :value="item.qty">
|
||||
</uni-number-box>
|
||||
@@ -43,6 +56,7 @@
|
||||
</u-checkbox-group>
|
||||
</view>
|
||||
|
||||
<!-- 底部结算栏 -->
|
||||
<view class="footer">
|
||||
<view class="allselect-left" @click="checkedAll">
|
||||
<u-checkbox-group>
|
||||
@@ -61,12 +75,11 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
// CartList
|
||||
// 引入API接口
|
||||
import {
|
||||
CartList,
|
||||
addCart,
|
||||
clearAll
|
||||
|
||||
} from '../../request/api/api'
|
||||
import {getCartListApi, saveCartApi} from "@/request/api/cart";
|
||||
import {genOrderByCartApi} from "@/request/api/order";
|
||||
@@ -74,7 +87,7 @@ import {genOrderByCartApi} from "@/request/api/order";
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
checked: false,
|
||||
checked: false, // 全选状态
|
||||
allcheck: false,
|
||||
value: 1,
|
||||
numberValue: 0,
|
||||
@@ -83,49 +96,52 @@ export default {
|
||||
checked: false,
|
||||
disabled: false
|
||||
}],
|
||||
selectList: [], //选中的数据
|
||||
cartLists: {
|
||||
selectList: [], // 选中的数据
|
||||
cartLists: { // 购物车列表数据源
|
||||
data: []
|
||||
},
|
||||
drug_ids: [],//药品id,
|
||||
cart_ids: [],//购物车id
|
||||
drug_ids: [], // 药品id集合
|
||||
cart_ids: [], // 购物车id集合
|
||||
qty: '',
|
||||
change_qty: '',
|
||||
true_qty: ''
|
||||
|
||||
}
|
||||
},
|
||||
// onLoad() {
|
||||
// this.getCartList()
|
||||
// },
|
||||
onShow() {
|
||||
this.getCartList()
|
||||
},
|
||||
|
||||
computed: {
|
||||
//全部价格
|
||||
// 计算选中商品的总价格
|
||||
totalPrice: function() {
|
||||
// 添加空值检查
|
||||
// 空值检查,防止报错
|
||||
if (!this.cartLists || !this.cartLists.data || this.cartLists.data.length === 0) {
|
||||
return '0.00';
|
||||
}
|
||||
|
||||
let totalPrice = 0;
|
||||
// 先过滤出已选中的商品,再计算总价
|
||||
// 过滤出已选中的商品
|
||||
const checkedItems = this.cartLists.data.filter(item => item.checked);
|
||||
|
||||
checkedItems.forEach(item => {
|
||||
// 添加价格和数量的有效性检查
|
||||
const price = item.drug?.drug_store_relations?.price || 0;
|
||||
// 兼容不同字段结构获取价格
|
||||
let price = 0;
|
||||
if(item.drug && item.drug.drugstore_drug && item.drug.drugstore_drug.price) {
|
||||
price = item.drug.drugstore_drug.price;
|
||||
} else if (item.drug && item.drug.drug_store_relations && item.drug.drug_store_relations.price) {
|
||||
price = item.drug.drug_store_relations.price;
|
||||
}
|
||||
|
||||
const qty = item.qty || 0;
|
||||
totalPrice += price * qty;
|
||||
});
|
||||
|
||||
return totalPrice.toFixed(2);
|
||||
},
|
||||
//全部件数
|
||||
|
||||
// 计算购物车总件数
|
||||
totalCount: function () {
|
||||
if (!this.cartLists || !this.cartLists.data) return 0;
|
||||
var totalCount = 0;
|
||||
for (var i = 0; i < this.cartLists.data.length; i++) {
|
||||
totalCount += this.cartLists.data[i].qty;
|
||||
@@ -135,73 +151,57 @@ export default {
|
||||
},
|
||||
|
||||
methods: {
|
||||
//清空购物车
|
||||
// 跳转商品详情页
|
||||
goProductDetail(item) {
|
||||
if (!item || !item.drug) return;
|
||||
|
||||
// 获取显示价格,逻辑与模板保持一致
|
||||
let price = '0';
|
||||
if (item.drug.drugstore_drug && item.drug.drugstore_drug.price) {
|
||||
price = item.drug.drugstore_drug.price;
|
||||
} else if (item.drug.drug_store_relations && item.drug.drug_store_relations.price) {
|
||||
price = item.drug.drug_store_relations.price;
|
||||
}
|
||||
|
||||
// 构建参数并跳转
|
||||
uni.navigateTo({
|
||||
url: `/subPackages/product/symptoms?id=${item.drug.id}&drug_name=${item.drug.drug_name}&is_otc=${item.drug.is_otc}&image=${item.drug.image}&price=${price}`
|
||||
});
|
||||
},
|
||||
|
||||
// 清空购物车
|
||||
clearCart() {
|
||||
// const list=this.cartLists.data.map(item=>item.drug_id)
|
||||
// this.drug_id=list
|
||||
// this.true_qty=0
|
||||
// this.addToCart()
|
||||
this.clearAll()
|
||||
},
|
||||
// 搜索
|
||||
toSearch() {
|
||||
// this.getList()
|
||||
},
|
||||
//加减法
|
||||
|
||||
// 步进器数量变化
|
||||
changeNum(e, current) {
|
||||
console.log(e, current);
|
||||
this.cartLists.data.forEach(item => {
|
||||
if (item.id == current.id) {
|
||||
item.qty = e;
|
||||
this.true_qty = e
|
||||
// this.qty=e
|
||||
this.drug_id = current.drug_id
|
||||
this.addToCart()
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
},
|
||||
// 选中某个复选框时,由checkbox时触发
|
||||
|
||||
// 单个商品复选框状态改变
|
||||
checkboxChange(item) {
|
||||
console.log(item);
|
||||
// this.drug_ids.push(item.drug_id)
|
||||
// this.cart_ids.push(item.id)
|
||||
item.checked = !item.checked
|
||||
// 如果存在未选中的项,则取消全选状态
|
||||
if (this.cartLists.data.filter(e => !e.checked).length) {
|
||||
this.checked = false
|
||||
|
||||
} else {
|
||||
this.checked = true
|
||||
}
|
||||
// console.log(item);
|
||||
// item.checked = !item.checked
|
||||
// if (!item.checked) {
|
||||
// this.allChecked = false
|
||||
// } else {
|
||||
// // 判断每一个商品是否是被选择的状态
|
||||
// const cartList = this.list.every(item => {
|
||||
// return item.checked === true
|
||||
// })
|
||||
// if (cartList) {
|
||||
// this.allChecked = true
|
||||
// } else {
|
||||
// this.allChecked = false
|
||||
// }
|
||||
// }
|
||||
},
|
||||
//// 更新购物车中商品的数量
|
||||
|
||||
// 选中任一checkbox时,由checkbox-group触发
|
||||
checkboxGroupChange(item) {
|
||||
console.log(item, 7711117);
|
||||
// console.log(e,c);
|
||||
|
||||
|
||||
},
|
||||
// 全选
|
||||
// 全选/反选
|
||||
checkedAll() {
|
||||
|
||||
// 如果当前已经是全部选中状态,则全部取消
|
||||
if (this.cartLists.data.filter(item => item.checked).length === this.cartLists.data.length) {
|
||||
this.cartLists = {
|
||||
...this.cartLists,
|
||||
@@ -213,6 +213,7 @@ export default {
|
||||
})
|
||||
}
|
||||
} else {
|
||||
// 否则全部选中
|
||||
this.cartLists = {
|
||||
...this.cartLists,
|
||||
data: this.cartLists.data.map(item => {
|
||||
@@ -223,18 +224,26 @@ export default {
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
},
|
||||
|
||||
// 去结算
|
||||
toPay() {
|
||||
const list = this.cartLists.data.filter(item => item.checked).map(item => {
|
||||
return {
|
||||
drug_id: item.drug_id,
|
||||
id: item.id,
|
||||
numbers: item.qty
|
||||
// numbers:item.qty,
|
||||
}
|
||||
})
|
||||
|
||||
if(list.length === 0) {
|
||||
uni.showToast({
|
||||
title: '请先选择商品',
|
||||
icon: 'none'
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
let cart_ids = list.map(item => item.id);
|
||||
genOrderByCartApi({
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
@@ -246,67 +255,56 @@ export default {
|
||||
})
|
||||
}
|
||||
})
|
||||
// uni.navigateTo({
|
||||
// url: `/subPackages/shop/shop-pay?list=${JSON.stringify(list)}`
|
||||
// })
|
||||
},
|
||||
// 清空购物车
|
||||
|
||||
// 调用API清空购物车
|
||||
clearAll() {
|
||||
clearAll({
|
||||
method: "post",
|
||||
data: {
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
|
||||
}
|
||||
}).then((res) => {
|
||||
// console.log(res, 'list');
|
||||
if (res.data.code == 0) {
|
||||
console.log(res);
|
||||
// 提示成功清空购物车
|
||||
uni.showToast({
|
||||
title: '清空成功',
|
||||
icon: 'success',
|
||||
})
|
||||
this.getCartList()
|
||||
}
|
||||
|
||||
})
|
||||
},
|
||||
|
||||
// 更新购物车数量到服务器
|
||||
addToCart() {
|
||||
saveCartApi({
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
drug_id: this.drug_id,
|
||||
quantity: this.true_qty
|
||||
// id:this.id
|
||||
}).then((res) => {
|
||||
// console.log(res, 'list');
|
||||
if (res.data.code == 0) {
|
||||
console.log(res);
|
||||
console.log('数量更新成功');
|
||||
}
|
||||
})
|
||||
},
|
||||
//请求购物车列表数据
|
||||
|
||||
// 获取购物车列表数据
|
||||
getCartList() {
|
||||
getCartListApi({
|
||||
store_id: uni.getStorageSync('store_id') || '11001',
|
||||
}).then((res) => {
|
||||
console.log(res, 'list');
|
||||
if (res.data.code == 0) {
|
||||
// this.drugLists=res.data.data
|
||||
|
||||
this.cartLists = {
|
||||
...res.data.result,
|
||||
data: res.data.result.data.map((item) => {
|
||||
return {
|
||||
...item,
|
||||
checked: false
|
||||
checked: false // 默认不选中
|
||||
};
|
||||
})
|
||||
};
|
||||
console.log(this.cartLists, 666);
|
||||
// console.log(this.cartLists.data[0].drug);
|
||||
}
|
||||
|
||||
})
|
||||
},
|
||||
}
|
||||
@@ -369,7 +367,6 @@ export default {
|
||||
vertical-align: middle;
|
||||
margin-right: 10rpx;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
.list {
|
||||
@@ -435,7 +432,6 @@ export default {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
.footer {
|
||||
@@ -475,7 +471,6 @@ export default {
|
||||
font-family: PingFang SC-Regular, PingFang SC;
|
||||
font-weight: 400;
|
||||
color: #FFFFFF;
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user