'首页和商品详情页初稿'
This commit is contained in:
+10
@@ -1 +1,11 @@
|
|||||||
|
# uni-app 编译产物
|
||||||
unpackage/
|
unpackage/
|
||||||
|
|
||||||
|
# 依赖
|
||||||
|
node_modules/
|
||||||
|
|
||||||
|
# 本地环境与编辑器
|
||||||
|
.idea/
|
||||||
|
.vscode/
|
||||||
|
.DS_Store
|
||||||
|
*.log
|
||||||
|
|||||||
@@ -0,0 +1,258 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 公司简介 + 底部 -->
|
||||||
|
<view class="company-section">
|
||||||
|
<!-- 背景图 -->
|
||||||
|
<view class="company-bg">
|
||||||
|
<image
|
||||||
|
class="bg-img"
|
||||||
|
src="/static/images/home/公司简介背景_1461_1606.png"
|
||||||
|
mode="widthFix"
|
||||||
|
></image>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="company-content">
|
||||||
|
<!-- 公司简介标题 - 居中 -->
|
||||||
|
<text class="section-title">公司简介</text>
|
||||||
|
|
||||||
|
<!-- 大标题 slogan -->
|
||||||
|
<view class="company-slogan">
|
||||||
|
<text class="slogan-main">用科技重新定义POD供应链</text>
|
||||||
|
<text class="slogan-sub">让每一个创意,都能高效抵达全球</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 公司描述 -->
|
||||||
|
<text class="company-desc">
|
||||||
|
INKREACH印美达全球,一家以AI与智能印花技术驱动的全球化POD柔性供应链公司,致力于成为全球创业者最可靠的成长伙伴。
|
||||||
|
</text>
|
||||||
|
|
||||||
|
<!-- 两栏说明 -->
|
||||||
|
<view class="company-cols">
|
||||||
|
<view class="col-left">
|
||||||
|
<text class="col-title">服务对象与场景</text>
|
||||||
|
<text class="col-text">
|
||||||
|
服务于数千家跨境独立站、TikTok、TEMU、SHEIN等平台商家,提供从海外生产到末端物流的一站式供应链服务,让电商创业者专注增长,无惧后端履约。
|
||||||
|
</text>
|
||||||
|
</view>
|
||||||
|
<view class="col-right">
|
||||||
|
<text class="col-title">愿景</text>
|
||||||
|
<text class="col-text">
|
||||||
|
我们坚信,每一个创意都值得被完美呈现。Inkreach将持续深耕智能供应链生态,用科技消除制造壁垒,让全球创业者专注发挥创造力,共同书写个性化电商的新纪元。
|
||||||
|
</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 4个核心能力卡片 -->
|
||||||
|
<view class="ability-grid">
|
||||||
|
<view class="ability-card" v-for="(item, index) in abilities" :key="index">
|
||||||
|
<view class="ability-icon">
|
||||||
|
<text class="icon-emoji">{{ getAbilityIcon(index) }}</text>
|
||||||
|
</view>
|
||||||
|
<text class="ability-title">{{ item.title }}</text>
|
||||||
|
<text class="ability-desc">{{ item.desc }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 底部橙色CTA区域 -->
|
||||||
|
<view class="cta-footer">
|
||||||
|
<view class="qr-wrap">
|
||||||
|
<image
|
||||||
|
class="qr-img"
|
||||||
|
src="/static/images/home/image_26_1496_1761.png"
|
||||||
|
mode="aspectFit"
|
||||||
|
></image>
|
||||||
|
</view>
|
||||||
|
<text class="cta-text">联系我们,开启你的全球生意新篇</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'CompanyIntro',
|
||||||
|
props: {
|
||||||
|
abilities: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
getAbilityIcon(index) {
|
||||||
|
const icons = ['🎨', '🤖', '🏭', '📦']
|
||||||
|
return icons[index] || ''
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.company-section {
|
||||||
|
position: relative;
|
||||||
|
width: 100%;
|
||||||
|
padding: 0;
|
||||||
|
background: #f8f8f8;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 背景图 */
|
||||||
|
.company-bg {
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
width: 100%;
|
||||||
|
z-index: 0;
|
||||||
|
}
|
||||||
|
.bg-img {
|
||||||
|
width: 100%;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
|
||||||
|
.company-content {
|
||||||
|
position: relative;
|
||||||
|
z-index: 1;
|
||||||
|
padding-top: 40rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 公司简介标题 - 设计稿 20px/400/#000000 居中 */
|
||||||
|
.section-title {
|
||||||
|
display: block;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 38rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 40rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* slogan - 设计稿 18px/400 */
|
||||||
|
.company-slogan {
|
||||||
|
padding: 0 32rpx;
|
||||||
|
margin-bottom: 24rpx;
|
||||||
|
}
|
||||||
|
.slogan-main {
|
||||||
|
display: block;
|
||||||
|
font-size: 34rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
line-height: 1.4;
|
||||||
|
}
|
||||||
|
.slogan-sub {
|
||||||
|
display: block;
|
||||||
|
font-size: 34rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #ff6800;
|
||||||
|
line-height: 1.4;
|
||||||
|
margin-top: 6rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 公司描述 - 设计稿 12px/400/#000000 */
|
||||||
|
.company-desc {
|
||||||
|
display: block;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #666666;
|
||||||
|
line-height: 1.7;
|
||||||
|
margin-bottom: 40rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 两栏 - 设计稿 14px/400/#000000 标题 */
|
||||||
|
.company-cols {
|
||||||
|
display: flex;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
gap: 24rpx;
|
||||||
|
margin-bottom: 50rpx;
|
||||||
|
}
|
||||||
|
.col-left,
|
||||||
|
.col-right {
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
.col-title {
|
||||||
|
display: block;
|
||||||
|
font-size: 26rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 12rpx;
|
||||||
|
}
|
||||||
|
.col-text {
|
||||||
|
display: block;
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #666666;
|
||||||
|
line-height: 1.7;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 核心能力卡片 - 2列网格 */
|
||||||
|
.ability-grid {
|
||||||
|
padding: 0 32rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
justify-content: space-between;
|
||||||
|
margin-bottom: 70rpx;
|
||||||
|
}
|
||||||
|
.ability-card {
|
||||||
|
width: 330rpx;
|
||||||
|
padding: 32rpx 24rpx;
|
||||||
|
background: #ffffff;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
border: 2rpx solid #f0f0f0;
|
||||||
|
margin-bottom: 20rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
.ability-icon {
|
||||||
|
width: 56rpx;
|
||||||
|
height: 56rpx;
|
||||||
|
margin-bottom: 16rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
.icon-emoji {
|
||||||
|
font-size: 40rpx;
|
||||||
|
}
|
||||||
|
.ability-title {
|
||||||
|
font-size: 26rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 8rpx;
|
||||||
|
}
|
||||||
|
.ability-desc {
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #999999;
|
||||||
|
line-height: 1.5;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 底部CTA - 橙色背景 */
|
||||||
|
.cta-footer {
|
||||||
|
position: relative;
|
||||||
|
z-index: 1;
|
||||||
|
width: 100%;
|
||||||
|
padding: 60rpx 32rpx 80rpx;
|
||||||
|
background: #ff6800;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
.qr-wrap {
|
||||||
|
width: 260rpx;
|
||||||
|
height: 260rpx;
|
||||||
|
background: #ffffff;
|
||||||
|
border-radius: 16rpx;
|
||||||
|
padding: 20rpx;
|
||||||
|
margin-bottom: 30rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
.qr-img {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
.cta-text {
|
||||||
|
font-size: 28rpx;
|
||||||
|
color: #ffffff;
|
||||||
|
font-weight: 500;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,138 @@
|
|||||||
|
<template>
|
||||||
|
<!-- Hero 首屏 - 设计稿风格 -->
|
||||||
|
<view class="hero">
|
||||||
|
<!-- 顶部 Logo -->
|
||||||
|
<view class="hero-logo">
|
||||||
|
<text class="logo-en">inkreach</text>
|
||||||
|
<text class="logo-cn">印美达全球</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 大标题 -->
|
||||||
|
<view class="hero-title">
|
||||||
|
<text class="title-main">全球POD供应链平台</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 副标题 -->
|
||||||
|
<text class="hero-subtitle">
|
||||||
|
连接设计、生产、订单与全球物流,助力跨境卖家快速上新、稳定履约
|
||||||
|
</text>
|
||||||
|
|
||||||
|
<!-- 4个指标 -->
|
||||||
|
<view class="hero-stats">
|
||||||
|
<view class="stat-item" v-for="(item, index) in stats" :key="index">
|
||||||
|
<text class="stat-value">{{ item.value }}</text>
|
||||||
|
<text class="stat-label">{{ item.label }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 地球背景图 -->
|
||||||
|
<view class="hero-earth">
|
||||||
|
<image
|
||||||
|
class="earth-img"
|
||||||
|
src="/static/images/home/Rectangle_178_1426_1248.png"
|
||||||
|
mode="widthFix"
|
||||||
|
></image>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'HeroBanner',
|
||||||
|
props: {
|
||||||
|
stats: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.hero {
|
||||||
|
position: relative;
|
||||||
|
width: 100%;
|
||||||
|
padding-top: 30rpx;
|
||||||
|
padding-bottom: 0;
|
||||||
|
background: #ffffff;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Logo */
|
||||||
|
.hero-logo {
|
||||||
|
display: flex;
|
||||||
|
align-items: baseline;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
margin-bottom: 40rpx;
|
||||||
|
}
|
||||||
|
.logo-en {
|
||||||
|
font-size: 36rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #ff6800;
|
||||||
|
letter-spacing: 1rpx;
|
||||||
|
}
|
||||||
|
.logo-cn {
|
||||||
|
margin-left: 12rpx;
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 标题 - 设计稿 28px/400/黑色 */
|
||||||
|
.hero-title {
|
||||||
|
padding: 0 32rpx;
|
||||||
|
margin-bottom: 16rpx;
|
||||||
|
}
|
||||||
|
.title-main {
|
||||||
|
font-size: 54rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
line-height: 1.3;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 副标题 - 设计稿 10px/400/#000000 */
|
||||||
|
.hero-subtitle {
|
||||||
|
display: block;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
font-size: 20rpx;
|
||||||
|
color: #999999;
|
||||||
|
line-height: 1.6;
|
||||||
|
margin-bottom: 36rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 4个指标 - 设计稿 16px/400/#ff6800 */
|
||||||
|
.hero-stats {
|
||||||
|
display: flex;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
gap: 24rpx;
|
||||||
|
margin-bottom: 40rpx;
|
||||||
|
}
|
||||||
|
.stat-item {
|
||||||
|
flex: 1;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: flex-start;
|
||||||
|
}
|
||||||
|
.stat-value {
|
||||||
|
font-size: 32rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #ff6800;
|
||||||
|
line-height: 1.2;
|
||||||
|
}
|
||||||
|
.stat-label {
|
||||||
|
margin-top: 8rpx;
|
||||||
|
font-size: 20rpx;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 地球图 - 全宽 */
|
||||||
|
.hero-earth {
|
||||||
|
width: 100%;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
.earth-img {
|
||||||
|
width: 100%;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,145 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 平台功能 + 集成平台 -->
|
||||||
|
<view class="feature-section">
|
||||||
|
<text class="section-title">用强大的功能,开启盈利快车道</text>
|
||||||
|
|
||||||
|
<!-- 功能卡片横向滚动 -->
|
||||||
|
<scroll-view scroll-x class="feat-scroll" show-scrollbar="false">
|
||||||
|
<view class="feat-list">
|
||||||
|
<view
|
||||||
|
class="feat-card"
|
||||||
|
:class="{ active: activeFeat === index }"
|
||||||
|
v-for="(item, index) in features"
|
||||||
|
:key="index"
|
||||||
|
@tap="onFeatTap(index)"
|
||||||
|
>
|
||||||
|
<text class="feat-num">0{{ index + 1 }}</text>
|
||||||
|
<text class="feat-title">{{ item.title }}</text>
|
||||||
|
<text class="feat-desc">{{ item.desc }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
|
||||||
|
<!-- 集成平台大图 -->
|
||||||
|
<view class="integration-wrap">
|
||||||
|
<view class="integration-box">
|
||||||
|
<image
|
||||||
|
class="integration-img"
|
||||||
|
src="/static/images/home/Rectangle_64_1484_1735.png"
|
||||||
|
mode="widthFix"
|
||||||
|
></image>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'PlatformFeatures',
|
||||||
|
props: {
|
||||||
|
features: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
activeFeat: 3
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
onFeatTap(index) {
|
||||||
|
this.activeFeat = index
|
||||||
|
this.$emit('change', index)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.feature-section {
|
||||||
|
width: 100%;
|
||||||
|
padding: 70rpx 0 0 0;
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.section-title {
|
||||||
|
display: block;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
font-size: 38rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 30rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 功能卡片横向滚动 */
|
||||||
|
.feat-scroll {
|
||||||
|
width: 100%;
|
||||||
|
white-space: nowrap;
|
||||||
|
margin-bottom: 50rpx;
|
||||||
|
}
|
||||||
|
.feat-list {
|
||||||
|
display: inline-flex;
|
||||||
|
gap: 20rpx;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
}
|
||||||
|
.feat-card {
|
||||||
|
flex-shrink: 0;
|
||||||
|
width: 320rpx;
|
||||||
|
padding: 28rpx 24rpx;
|
||||||
|
background: #f8f8f8;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
.feat-card.active {
|
||||||
|
background: #ff6800;
|
||||||
|
}
|
||||||
|
.feat-num {
|
||||||
|
font-size: 32rpx;
|
||||||
|
font-weight: 900;
|
||||||
|
color: #ff6800;
|
||||||
|
line-height: 1;
|
||||||
|
margin-bottom: 12rpx;
|
||||||
|
}
|
||||||
|
.feat-card.active .feat-num {
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
.feat-title {
|
||||||
|
font-size: 28rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 8rpx;
|
||||||
|
}
|
||||||
|
.feat-card.active .feat-title {
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
.feat-desc {
|
||||||
|
font-size: 20rpx;
|
||||||
|
color: #999999;
|
||||||
|
line-height: 1.5;
|
||||||
|
white-space: normal;
|
||||||
|
}
|
||||||
|
.feat-card.active .feat-desc {
|
||||||
|
color: rgba(255, 255, 255, 0.85);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 集成平台大图 */
|
||||||
|
.integration-wrap {
|
||||||
|
padding: 0 32rpx;
|
||||||
|
}
|
||||||
|
.integration-box {
|
||||||
|
width: 100%;
|
||||||
|
background: #ff6800;
|
||||||
|
border-radius: 16rpx;
|
||||||
|
padding: 30rpx;
|
||||||
|
box-sizing: border-box;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
.integration-img {
|
||||||
|
width: 100%;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,171 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 全球POD货盘 -->
|
||||||
|
<view class="pod-section">
|
||||||
|
<text class="section-title">全球POD货盘</text>
|
||||||
|
|
||||||
|
<!-- 国家 tab 横向滚动 -->
|
||||||
|
<scroll-view scroll-x class="country-scroll" show-scrollbar="false">
|
||||||
|
<view class="country-list">
|
||||||
|
<view
|
||||||
|
class="country-tab"
|
||||||
|
:class="{ active: activeCountry === item.id }"
|
||||||
|
v-for="(item, index) in countries"
|
||||||
|
:key="index"
|
||||||
|
@tap="onCountryTap(item.id)"
|
||||||
|
>
|
||||||
|
{{ item.flag }} {{ item.name }}
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
|
||||||
|
<!-- 产品网格 2列 -->
|
||||||
|
<view class="pod-grid">
|
||||||
|
<view
|
||||||
|
class="pod-card"
|
||||||
|
v-for="(item, index) in products"
|
||||||
|
:key="index"
|
||||||
|
@tap="onProductTap(item)"
|
||||||
|
>
|
||||||
|
<view class="pod-img-wrap">
|
||||||
|
<image class="pod-img" :src="item.image" mode="aspectFit"></image>
|
||||||
|
</view>
|
||||||
|
<text class="pod-name">{{ item.name }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 更多产品 -->
|
||||||
|
<view class="more-products" @tap="onMoreTap">
|
||||||
|
<text class="more-text">更多产品</text>
|
||||||
|
<text class="more-arrow">→</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'PodCatalog',
|
||||||
|
props: {
|
||||||
|
countries: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
products: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
activeCountry: 'us'
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
onCountryTap(id) {
|
||||||
|
this.activeCountry = id
|
||||||
|
this.$emit('countryChange', id)
|
||||||
|
},
|
||||||
|
onProductTap(item) {
|
||||||
|
this.$emit('productTap', item)
|
||||||
|
},
|
||||||
|
onMoreTap() {
|
||||||
|
this.$emit('moreTap')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.pod-section {
|
||||||
|
width: 100%;
|
||||||
|
padding: 70rpx 0 0 0;
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 区块标题 - 设计稿 20px/400/#1a1a1a */
|
||||||
|
.section-title {
|
||||||
|
display: block;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
font-size: 38rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 30rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 国家 tab - 设计稿 13px/400, 选中 #ffffff 未选中 #000000 */
|
||||||
|
.country-scroll {
|
||||||
|
width: 100%;
|
||||||
|
white-space: nowrap;
|
||||||
|
margin-bottom: 36rpx;
|
||||||
|
}
|
||||||
|
.country-list {
|
||||||
|
display: inline-flex;
|
||||||
|
gap: 16rpx;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
}
|
||||||
|
.country-tab {
|
||||||
|
flex-shrink: 0;
|
||||||
|
padding: 10rpx 24rpx;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 40rpx;
|
||||||
|
font-size: 25rpx;
|
||||||
|
color: #1a1a1a;
|
||||||
|
}
|
||||||
|
.country-tab.active {
|
||||||
|
background: #ff6800;
|
||||||
|
color: #ffffff;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 产品网格 - 2列 space-between 兼容小程序 */
|
||||||
|
.pod-grid {
|
||||||
|
padding: 0 32rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
.pod-card {
|
||||||
|
width: 330rpx;
|
||||||
|
background: #f8f8f8;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
margin-bottom: 20rpx;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
.pod-img-wrap {
|
||||||
|
width: 100%;
|
||||||
|
height: 340rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
background: #f0f0f0;
|
||||||
|
}
|
||||||
|
.pod-img {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
/* 产品名 - 设计稿 16px/400/#000000 */
|
||||||
|
.pod-name {
|
||||||
|
display: block;
|
||||||
|
padding: 16rpx 20rpx 20rpx;
|
||||||
|
font-size: 26rpx;
|
||||||
|
color: #1a1a1a;
|
||||||
|
line-height: 1.4;
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 更多产品 - 设计稿 12px/400/#ff6800 居中 */
|
||||||
|
.more-products {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
gap: 8rpx;
|
||||||
|
padding: 40rpx 0 20rpx;
|
||||||
|
}
|
||||||
|
.more-text {
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
.more-arrow {
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,149 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 4步开始你的按需定制生意 -->
|
||||||
|
<view class="steps-section">
|
||||||
|
<text class="section-title">4步开始你的按需定制生意</text>
|
||||||
|
|
||||||
|
<!-- 步骤卡片横向滚动 -->
|
||||||
|
<scroll-view scroll-x class="steps-scroll" show-scrollbar="false">
|
||||||
|
<view class="steps-list">
|
||||||
|
<view
|
||||||
|
class="step-card"
|
||||||
|
:class="{ active: activeStep === index }"
|
||||||
|
v-for="(item, index) in steps"
|
||||||
|
:key="index"
|
||||||
|
@tap="onStepTap(index)"
|
||||||
|
>
|
||||||
|
<text class="step-num">{{ item.step }}</text>
|
||||||
|
<text class="step-title">{{ item.title }}</text>
|
||||||
|
<text class="step-desc">{{ item.desc }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
|
||||||
|
<!-- 预览大图 -->
|
||||||
|
<view class="preview-wrap">
|
||||||
|
<view class="preview-img-box">
|
||||||
|
<image
|
||||||
|
class="preview-img"
|
||||||
|
src="/static/images/home/image_25_1484_1689.png"
|
||||||
|
mode="widthFix"
|
||||||
|
></image>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'StepsFlow',
|
||||||
|
props: {
|
||||||
|
steps: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
activeStep: 0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
onStepTap(index) {
|
||||||
|
this.activeStep = index
|
||||||
|
this.$emit('change', index)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.steps-section {
|
||||||
|
width: 100%;
|
||||||
|
padding: 60rpx 0 0 0;
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 区块标题 - 设计稿 20px/400/#1a1a1a */
|
||||||
|
.section-title {
|
||||||
|
display: block;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
font-size: 38rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 32rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 步骤卡片横向滚动 */
|
||||||
|
.steps-scroll {
|
||||||
|
width: 100%;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
.steps-list {
|
||||||
|
display: inline-flex;
|
||||||
|
gap: 20rpx;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
}
|
||||||
|
.step-card {
|
||||||
|
flex-shrink: 0;
|
||||||
|
width: 320rpx;
|
||||||
|
padding: 28rpx 24rpx;
|
||||||
|
background: #f8f8f8;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
.step-card.active {
|
||||||
|
background: #ff6800;
|
||||||
|
}
|
||||||
|
/* 步骤编号 - 设计稿 16px/900/#ff6800 (未选中) / #ffffff (选中) */
|
||||||
|
.step-num {
|
||||||
|
font-size: 32rpx;
|
||||||
|
font-weight: 900;
|
||||||
|
color: #ff6800;
|
||||||
|
line-height: 1;
|
||||||
|
margin-bottom: 12rpx;
|
||||||
|
}
|
||||||
|
.step-card.active .step-num {
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
/* 步骤标题 - 设计稿 16px/400/#1a1a1a (未选中) / #ffffff (选中) */
|
||||||
|
.step-title {
|
||||||
|
font-size: 28rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 8rpx;
|
||||||
|
}
|
||||||
|
.step-card.active .step-title {
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
/* 步骤描述 - 设计稿 10px/400/#ffffff (选中态描述) */
|
||||||
|
.step-desc {
|
||||||
|
font-size: 20rpx;
|
||||||
|
color: #999999;
|
||||||
|
line-height: 1.5;
|
||||||
|
white-space: normal;
|
||||||
|
}
|
||||||
|
.step-card.active .step-desc {
|
||||||
|
color: rgba(255, 255, 255, 0.85);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 预览大图 */
|
||||||
|
.preview-wrap {
|
||||||
|
margin-top: 50rpx;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
}
|
||||||
|
.preview-img-box {
|
||||||
|
width: 100%;
|
||||||
|
background: #ff6800;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
padding: 20rpx;
|
||||||
|
box-sizing: border-box;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
.preview-img {
|
||||||
|
width: 100%;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,97 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 为什么选择 Inkreach -->
|
||||||
|
<view class="why-section">
|
||||||
|
<text class="section-title">为什么选择Inkreach?</text>
|
||||||
|
|
||||||
|
<view class="why-grid">
|
||||||
|
<view class="why-card" v-for="(item, index) in reasons" :key="index">
|
||||||
|
<view class="why-icon">
|
||||||
|
<image class="icon-img" :src="getIcon(index)" mode="aspectFit"></image>
|
||||||
|
</view>
|
||||||
|
<text class="why-title">{{ item.title }}</text>
|
||||||
|
<text class="why-desc">{{ item.desc }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'WhyChoose',
|
||||||
|
props: {
|
||||||
|
reasons: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
getIcon(index) {
|
||||||
|
const icons = [
|
||||||
|
'/static/icons/home/零库存图标.svg',
|
||||||
|
'/static/icons/home/快速生产图标.svg',
|
||||||
|
'/static/icons/home/优质产品图标.svg',
|
||||||
|
'/static/icons/home/全球配送图标.svg'
|
||||||
|
]
|
||||||
|
return icons[index] || ''
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.why-section {
|
||||||
|
width: 100%;
|
||||||
|
padding: 70rpx 0 0 0;
|
||||||
|
background: #f8f8f8;
|
||||||
|
}
|
||||||
|
|
||||||
|
.section-title {
|
||||||
|
display: block;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
font-size: 38rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 30rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 2列网格 - 用 space-between 兼容小程序 */
|
||||||
|
.why-grid {
|
||||||
|
padding: 0 32rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
.why-card {
|
||||||
|
width: 330rpx;
|
||||||
|
padding: 36rpx 28rpx;
|
||||||
|
background: #ffffff;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
margin-bottom: 20rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
.why-icon {
|
||||||
|
width: 52rpx;
|
||||||
|
height: 52rpx;
|
||||||
|
margin-bottom: 20rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
.icon-img {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
.why-title {
|
||||||
|
font-size: 28rpx;
|
||||||
|
font-weight: 500;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 8rpx;
|
||||||
|
}
|
||||||
|
.why-desc {
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #999999;
|
||||||
|
line-height: 1.5;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -1,828 +0,0 @@
|
|||||||
/* 首页样式 - 印美达 Inkreach */
|
|
||||||
|
|
||||||
.home {
|
|
||||||
min-height: 100vh;
|
|
||||||
background: #ffffff;
|
|
||||||
overflow-x: hidden;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 导航栏 */
|
|
||||||
.nav-bar {
|
|
||||||
position: fixed;
|
|
||||||
top: 0;
|
|
||||||
left: 0;
|
|
||||||
right: 0;
|
|
||||||
z-index: 1000;
|
|
||||||
background: #ffffff;
|
|
||||||
box-shadow: 0 1rpx 0 rgba(0, 0, 0, 0.05);
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav-content {
|
|
||||||
height: 88rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: space-between;
|
|
||||||
padding: 0 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav-logo {
|
|
||||||
display: flex;
|
|
||||||
align-items: baseline;
|
|
||||||
gap: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo-text {
|
|
||||||
font-size: 32rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ff6800;
|
|
||||||
font-style: italic;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo-cn {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #333;
|
|
||||||
font-weight: 500;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav-actions {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav-btn {
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #333;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav-login {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #ff6800;
|
|
||||||
border: 2rpx solid #ff6800;
|
|
||||||
padding: 8rpx 24rpx;
|
|
||||||
border-radius: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Hero 首屏 */
|
|
||||||
.hero {
|
|
||||||
position: relative;
|
|
||||||
padding: 60rpx 32rpx 80rpx;
|
|
||||||
overflow: hidden;
|
|
||||||
background: linear-gradient(180deg, #fff5ee 0%, #ffffff 100%);
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-bg {
|
|
||||||
position: absolute;
|
|
||||||
top: -100rpx;
|
|
||||||
right: -200rpx;
|
|
||||||
width: 600rpx;
|
|
||||||
height: 600rpx;
|
|
||||||
background: radial-gradient(circle, rgba(255, 104, 0, 0.06) 0%, transparent 70%);
|
|
||||||
border-radius: 50%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-content {
|
|
||||||
position: relative;
|
|
||||||
z-index: 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-title {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-title-main {
|
|
||||||
font-size: 72rpx;
|
|
||||||
font-weight: 800;
|
|
||||||
color: #1a1a1a;
|
|
||||||
line-height: 1.2;
|
|
||||||
letter-spacing: 2rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-subtitle {
|
|
||||||
font-size: 30rpx;
|
|
||||||
color: #666;
|
|
||||||
margin-top: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-tags {
|
|
||||||
display: flex;
|
|
||||||
gap: 16rpx;
|
|
||||||
margin-top: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-tag {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #ff6800;
|
|
||||||
background: rgba(255, 104, 0, 0.08);
|
|
||||||
padding: 8rpx 20rpx;
|
|
||||||
border-radius: 24rpx;
|
|
||||||
font-weight: 500;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-cta {
|
|
||||||
display: inline-flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
background: #ff6800;
|
|
||||||
color: #ffffff;
|
|
||||||
font-size: 30rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
padding: 24rpx 64rpx;
|
|
||||||
border-radius: 48rpx;
|
|
||||||
margin-top: 48rpx;
|
|
||||||
box-shadow: 0 8rpx 24rpx rgba(255, 104, 0, 0.3);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 3D插画区 */
|
|
||||||
.hero-illustration {
|
|
||||||
position: relative;
|
|
||||||
height: 400rpx;
|
|
||||||
margin-top: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-illust-item {
|
|
||||||
position: absolute;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-illist-tshirt {
|
|
||||||
top: 20rpx;
|
|
||||||
left: 20rpx;
|
|
||||||
transform: rotate(-8deg);
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-illist-bag {
|
|
||||||
top: 60rpx;
|
|
||||||
right: 40rpx;
|
|
||||||
transform: rotate(12deg);
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-illist-box {
|
|
||||||
bottom: 0;
|
|
||||||
left: 50%;
|
|
||||||
transform: translateX(-50%) rotate(-3deg);
|
|
||||||
}
|
|
||||||
|
|
||||||
.illust-placeholder {
|
|
||||||
border-radius: 24rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
font-size: 80rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.illust-placeholder.tshirt {
|
|
||||||
width: 200rpx;
|
|
||||||
height: 220rpx;
|
|
||||||
background: linear-gradient(135deg, #ff6800 0%, #ff8c40 100%);
|
|
||||||
}
|
|
||||||
|
|
||||||
.illust-placeholder.bag {
|
|
||||||
width: 180rpx;
|
|
||||||
height: 200rpx;
|
|
||||||
background: linear-gradient(135deg, #f26522 0%, #ff8855 100%);
|
|
||||||
}
|
|
||||||
|
|
||||||
.illust-placeholder.box {
|
|
||||||
width: 240rpx;
|
|
||||||
height: 180rpx;
|
|
||||||
background: linear-gradient(135deg, #ff6800 0%, #ffa040 100%);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 通用 section */
|
|
||||||
.section-title {
|
|
||||||
font-size: 40rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #1a1a1a;
|
|
||||||
text-align: center;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.section-subtitle {
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #999;
|
|
||||||
text-align: center;
|
|
||||||
margin-top: 12rpx;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.section-title-small {
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #666;
|
|
||||||
text-align: center;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 信任指标 */
|
|
||||||
.trust-section {
|
|
||||||
padding: 64rpx 32rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.trust-grid {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.trust-card {
|
|
||||||
flex: 1;
|
|
||||||
min-width: 160rpx;
|
|
||||||
background: #fff8f3;
|
|
||||||
border-radius: 16rpx;
|
|
||||||
padding: 28rpx 16rpx;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.trust-number {
|
|
||||||
font-size: 40rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ff6800;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.trust-label {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #666;
|
|
||||||
margin-top: 8rpx;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 4步流程 */
|
|
||||||
.steps-section {
|
|
||||||
padding: 64rpx 32rpx;
|
|
||||||
background: #fafafa;
|
|
||||||
}
|
|
||||||
|
|
||||||
.steps-list {
|
|
||||||
margin-top: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-item {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
padding: 24rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 16rpx;
|
|
||||||
margin-bottom: 16rpx;
|
|
||||||
transition: all 0.3s;
|
|
||||||
border: 2rpx solid transparent;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-item.active {
|
|
||||||
border-color: #ff6800;
|
|
||||||
box-shadow: 0 4rpx 16rpx rgba(255, 104, 0, 0.1);
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-number {
|
|
||||||
font-size: 36rpx;
|
|
||||||
font-weight: 800;
|
|
||||||
color: #ddd;
|
|
||||||
width: 80rpx;
|
|
||||||
flex-shrink: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-item.active .step-number {
|
|
||||||
color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-info {
|
|
||||||
flex: 1;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 6rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-title {
|
|
||||||
font-size: 30rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-desc {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #999;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-visual {
|
|
||||||
margin-top: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-visual-card {
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 20rpx;
|
|
||||||
padding: 48rpx 32rpx;
|
|
||||||
text-align: center;
|
|
||||||
border: 2rpx solid #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-visual-icon {
|
|
||||||
width: 120rpx;
|
|
||||||
height: 120rpx;
|
|
||||||
border-radius: 50%;
|
|
||||||
background: #fff0e5;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
margin: 0 auto 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-visual-emoji {
|
|
||||||
font-size: 56rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.step-visual-text {
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #666;
|
|
||||||
line-height: 1.6;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 全球POD货盘 */
|
|
||||||
.catalog-section {
|
|
||||||
padding: 64rpx 0;
|
|
||||||
background: #ffffff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.catalog-section .section-title {
|
|
||||||
padding: 0 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.category-tabs {
|
|
||||||
white-space: nowrap;
|
|
||||||
padding: 24rpx 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cat-tab {
|
|
||||||
display: inline-block;
|
|
||||||
padding: 12rpx 32rpx;
|
|
||||||
margin-right: 16rpx;
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #666;
|
|
||||||
background: #f5f5f5;
|
|
||||||
border-radius: 32rpx;
|
|
||||||
transition: all 0.3s;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cat-tab.active {
|
|
||||||
background: #ff6800;
|
|
||||||
color: #ffffff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-preview-grid {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
padding: 0 32rpx;
|
|
||||||
gap: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-preview-card {
|
|
||||||
width: calc(50% - 12rpx);
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 16rpx;
|
|
||||||
overflow: hidden;
|
|
||||||
box-shadow: 0 2rpx 12rpx rgba(0, 0, 0, 0.04);
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-preview-img {
|
|
||||||
width: 100%;
|
|
||||||
height: 280rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-preview-emoji {
|
|
||||||
font-size: 80rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-preview-info {
|
|
||||||
padding: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-preview-name {
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #333;
|
|
||||||
display: block;
|
|
||||||
overflow: hidden;
|
|
||||||
text-overflow: ellipsis;
|
|
||||||
white-space: nowrap;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-preview-price {
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #ff6800;
|
|
||||||
font-weight: 600;
|
|
||||||
margin-top: 8rpx;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.see-more {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
gap: 8rpx;
|
|
||||||
padding: 24rpx;
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.see-more .arrow {
|
|
||||||
font-size: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 平台功能 */
|
|
||||||
.features-section {
|
|
||||||
padding: 64rpx 32rpx;
|
|
||||||
background: #fafafa;
|
|
||||||
}
|
|
||||||
|
|
||||||
.features-grid {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 24rpx;
|
|
||||||
margin-top: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.feature-card {
|
|
||||||
width: calc(50% - 12rpx);
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 16rpx;
|
|
||||||
padding: 32rpx 24rpx;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
align-items: flex-start;
|
|
||||||
gap: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.feature-icon {
|
|
||||||
width: 80rpx;
|
|
||||||
height: 80rpx;
|
|
||||||
border-radius: 20rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.feature-emoji {
|
|
||||||
font-size: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.feature-title {
|
|
||||||
font-size: 30rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
}
|
|
||||||
|
|
||||||
.feature-desc {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #999;
|
|
||||||
line-height: 1.5;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 为什么选择 */
|
|
||||||
.why-section {
|
|
||||||
padding: 64rpx 32rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.why-grid {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 24rpx;
|
|
||||||
margin-top: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.why-card {
|
|
||||||
width: calc(50% - 12rpx);
|
|
||||||
text-align: center;
|
|
||||||
padding: 32rpx 16rpx;
|
|
||||||
background: #fff8f3;
|
|
||||||
border-radius: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.why-icon {
|
|
||||||
width: 72rpx;
|
|
||||||
height: 72rpx;
|
|
||||||
margin: 0 auto 16rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 50%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.why-emoji {
|
|
||||||
font-size: 36rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.why-title {
|
|
||||||
font-size: 28rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.why-desc {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #999;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 公司简介 */
|
|
||||||
.company-section {
|
|
||||||
padding: 64rpx 32rpx;
|
|
||||||
background: #fafafa;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-card {
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 20rpx;
|
|
||||||
padding: 40rpx 32rpx;
|
|
||||||
margin-top: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-headline {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
font-size: 32rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #1a1a1a;
|
|
||||||
line-height: 1.6;
|
|
||||||
margin-bottom: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-content {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-block-title {
|
|
||||||
font-size: 26rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #ff6800;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-block-text {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #666;
|
|
||||||
line-height: 1.7;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-stats {
|
|
||||||
display: flex;
|
|
||||||
justify-content: space-around;
|
|
||||||
margin-top: 32rpx;
|
|
||||||
padding-top: 32rpx;
|
|
||||||
border-top: 1rpx solid #eee;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-stat {
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-stat-number {
|
|
||||||
font-size: 36rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ff6800;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.company-stat-label {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #999;
|
|
||||||
margin-top: 4rpx;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 用户案例 */
|
|
||||||
.cases-section {
|
|
||||||
padding: 64rpx 0;
|
|
||||||
background: #ffffff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cases-section .section-title {
|
|
||||||
padding: 0 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cases-scroll {
|
|
||||||
white-space: nowrap;
|
|
||||||
padding: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-card {
|
|
||||||
display: inline-block;
|
|
||||||
width: 480rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 20rpx;
|
|
||||||
overflow: hidden;
|
|
||||||
margin-right: 24rpx;
|
|
||||||
box-shadow: 0 4rpx 16rpx rgba(0, 0, 0, 0.06);
|
|
||||||
vertical-align: top;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-image {
|
|
||||||
width: 100%;
|
|
||||||
height: 320rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-emoji {
|
|
||||||
font-size: 80rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-info {
|
|
||||||
padding: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-title {
|
|
||||||
font-size: 28rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-tags {
|
|
||||||
display: flex;
|
|
||||||
gap: 8rpx;
|
|
||||||
margin-bottom: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-tag {
|
|
||||||
font-size: 20rpx;
|
|
||||||
padding: 4rpx 12rpx;
|
|
||||||
background: #fff0e5;
|
|
||||||
color: #ff6800;
|
|
||||||
border-radius: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-metrics {
|
|
||||||
display: flex;
|
|
||||||
gap: 24rpx;
|
|
||||||
padding-top: 16rpx;
|
|
||||||
border-top: 1rpx solid #eee;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-metric-value {
|
|
||||||
font-size: 32rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ff6800;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.case-metric-label {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #999;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 最终CTA */
|
|
||||||
.cta-section {
|
|
||||||
position: relative;
|
|
||||||
padding: 80rpx 32rpx;
|
|
||||||
overflow: hidden;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-bg {
|
|
||||||
position: absolute;
|
|
||||||
top: 0;
|
|
||||||
left: 0;
|
|
||||||
right: 0;
|
|
||||||
bottom: 0;
|
|
||||||
background: linear-gradient(135deg, #ff6800 0%, #ff8c40 100%);
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-content {
|
|
||||||
position: relative;
|
|
||||||
z-index: 2;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-title {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
font-size: 48rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ffffff;
|
|
||||||
line-height: 1.4;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-desc {
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: rgba(255, 255, 255, 0.85);
|
|
||||||
margin-top: 16rpx;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-input-wrap {
|
|
||||||
display: flex;
|
|
||||||
gap: 16rpx;
|
|
||||||
margin-top: 40rpx;
|
|
||||||
padding: 0 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-input {
|
|
||||||
flex: 1;
|
|
||||||
height: 80rpx;
|
|
||||||
background: rgba(255, 255, 255, 0.95);
|
|
||||||
border-radius: 40rpx;
|
|
||||||
padding: 0 32rpx;
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #333;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-placeholder {
|
|
||||||
color: #ccc;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cta-btn {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
background: #1a1a1a;
|
|
||||||
color: #ffffff;
|
|
||||||
font-size: 28rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
padding: 0 40rpx;
|
|
||||||
border-radius: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 底部 */
|
|
||||||
.footer {
|
|
||||||
background: #121212;
|
|
||||||
padding: 48rpx 32rpx;
|
|
||||||
padding-bottom: calc(48rpx + env(safe-area-inset-bottom));
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-top {
|
|
||||||
text-align: center;
|
|
||||||
margin-bottom: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-logo {
|
|
||||||
display: flex;
|
|
||||||
align-items: baseline;
|
|
||||||
justify-content: center;
|
|
||||||
gap: 8rpx;
|
|
||||||
margin-bottom: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-logo-en {
|
|
||||||
font-size: 36rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ff6800;
|
|
||||||
font-style: italic;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-logo-cn {
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #fff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-slogan {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: rgba(255, 255, 255, 0.5);
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-links {
|
|
||||||
display: flex;
|
|
||||||
justify-content: space-around;
|
|
||||||
margin-bottom: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-col {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-col-title {
|
|
||||||
font-size: 26rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #fff;
|
|
||||||
margin-bottom: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-link {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: rgba(255, 255, 255, 0.5);
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-bottom {
|
|
||||||
text-align: center;
|
|
||||||
padding-top: 32rpx;
|
|
||||||
border-top: 1rpx solid rgba(255, 255, 255, 0.1);
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer-copyright {
|
|
||||||
font-size: 20rpx;
|
|
||||||
color: rgba(255, 255, 255, 0.3);
|
|
||||||
}
|
|
||||||
+58
-503
@@ -1,532 +1,87 @@
|
|||||||
<template>
|
<template>
|
||||||
<!-- 首页 - 印美达 Inkreach 按需定制平台 -->
|
<view class="index-page">
|
||||||
<view class="home">
|
|
||||||
<!-- 自定义导航栏 -->
|
|
||||||
<view class="nav-bar" :style="'padding-top: ' + statusBarHeight + 'px;'">
|
|
||||||
<view class="nav-content">
|
|
||||||
<view class="nav-logo" @tap="goHome">
|
|
||||||
<text class="logo-text">inkreach</text>
|
|
||||||
<text class="logo-cn">印美达</text>
|
|
||||||
</view>
|
|
||||||
<view class="nav-actions">
|
|
||||||
<text class="nav-btn" @tap="goProducts">产品中心</text>
|
|
||||||
<view class="nav-login" @tap="goProducts">立即开始</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 占位 -->
|
|
||||||
<view :style="'height: ' + (statusBarHeight + 44) + 'px;'"></view>
|
|
||||||
|
|
||||||
<!-- Hero 首屏 -->
|
<!-- Hero 首屏 -->
|
||||||
<view class="hero">
|
<HeroBanner :stats="trustStats" />
|
||||||
<view class="hero-bg"></view>
|
|
||||||
<view class="hero-content">
|
|
||||||
<view class="hero-title">
|
|
||||||
<text class="hero-title-main">一站定制</text>
|
|
||||||
<text class="hero-title-main">链通全球</text>
|
|
||||||
</view>
|
|
||||||
<text class="hero-subtitle">从定制设计到生产发货如此简单</text>
|
|
||||||
<view class="hero-tags">
|
|
||||||
<view class="hero-tag">0库存</view>
|
|
||||||
<view class="hero-tag">1件起订</view>
|
|
||||||
<view class="hero-tag">全球配送</view>
|
|
||||||
</view>
|
|
||||||
<view class="hero-cta" @tap="goProducts">
|
|
||||||
<text>免费开始</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<!-- 3D插画区域 -->
|
|
||||||
<view class="hero-illustration">
|
|
||||||
<view class="hero-illust-item hero-illist-tshirt">
|
|
||||||
<view class="illust-placeholder tshirt"></view>
|
|
||||||
</view>
|
|
||||||
<view class="hero-illust-item hero-illist-bag">
|
|
||||||
<view class="illust-placeholder bag"></view>
|
|
||||||
</view>
|
|
||||||
<view class="hero-illust-item hero-illist-box">
|
|
||||||
<view class="illust-placeholder box"></view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 信任指标 -->
|
|
||||||
<view class="trust-section">
|
|
||||||
<text class="section-title-small">全球5000+卖家信赖我们的平台</text>
|
|
||||||
<view class="trust-grid">
|
|
||||||
<view class="trust-card">
|
|
||||||
<text class="trust-number">1000万+</text>
|
|
||||||
<text class="trust-label">订单履约</text>
|
|
||||||
</view>
|
|
||||||
<view class="trust-card">
|
|
||||||
<text class="trust-number">20+</text>
|
|
||||||
<text class="trust-label">国家覆盖</text>
|
|
||||||
</view>
|
|
||||||
<view class="trust-card">
|
|
||||||
<text class="trust-number">500+</text>
|
|
||||||
<text class="trust-label">合作工厂</text>
|
|
||||||
</view>
|
|
||||||
<view class="trust-card">
|
|
||||||
<text class="trust-number">24H</text>
|
|
||||||
<text class="trust-label">极速发货</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 4步流程 -->
|
<!-- 4步流程 -->
|
||||||
<view class="steps-section">
|
<StepsFlow :steps="stepList" />
|
||||||
<text class="section-title">4步开始你的按需定制生意</text>
|
|
||||||
<view class="steps-list">
|
|
||||||
<view :class="'step-item ' + (currentStep === 1 ? 'active' : '')" @tap="selectStep" data-step="1">
|
|
||||||
<view class="step-number">01</view>
|
|
||||||
<view class="step-info">
|
|
||||||
<text class="step-title">选择产品</text>
|
|
||||||
<text class="step-desc">从全球POD货盘中选择热销产品</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<view :class="'step-item ' + (currentStep === 2 ? 'active' : '')" @tap="selectStep" data-step="2">
|
|
||||||
<view class="step-number">02</view>
|
|
||||||
<view class="step-info">
|
|
||||||
<text class="step-title">上传设计</text>
|
|
||||||
<text class="step-desc">使用在线设计工具创建专属图案</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<view :class="'step-item ' + (currentStep === 3 ? 'active' : '')" @tap="selectStep" data-step="3">
|
|
||||||
<view class="step-number">03</view>
|
|
||||||
<view class="step-info">
|
|
||||||
<text class="step-title">在线销售</text>
|
|
||||||
<text class="step-desc">一键上架到Shopify等电商平台</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<view :class="'step-item ' + (currentStep === 4 ? 'active' : '')" @tap="selectStep" data-step="4">
|
|
||||||
<view class="step-number">04</view>
|
|
||||||
<view class="step-info">
|
|
||||||
<text class="step-title">生产配送</text>
|
|
||||||
<text class="step-desc">自动生产全球发货履约无忧</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<view class="step-visual">
|
|
||||||
<view class="step-visual-card">
|
|
||||||
<view :class="'step-visual-icon step-icon-' + currentStep">
|
|
||||||
<text class="step-visual-emoji">{{ stepEmoji }}</text>
|
|
||||||
</view>
|
|
||||||
<text class="step-visual-text">{{ stepDesc }}</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 全球POD货盘 -->
|
<!-- 全球POD货盘 -->
|
||||||
<view class="catalog-section">
|
<PodCatalog
|
||||||
<text class="section-title">全球POD货盘</text>
|
:countries="countryTabs"
|
||||||
<text class="section-subtitle">多元化产品选择,满足场景化需求</text>
|
:products="podProducts"
|
||||||
<scroll-view class="category-tabs" :scroll-x="true" :enhanced="true" :show-scrollbar="false">
|
@moreTap="onGoProducts"
|
||||||
<view :class="'cat-tab ' + (activeCategory === item.id ? 'active' : '')" @tap="selectCategory" :data-id="item.id" v-for="(item, index) in categories" :key="index">
|
@productTap="onGoDetail"
|
||||||
{{ item.name }}
|
/>
|
||||||
</view>
|
|
||||||
</scroll-view>
|
|
||||||
<view class="product-preview-grid">
|
|
||||||
<view class="product-preview-card" @tap="goProductDetail" :data-id="item.id" v-for="(item, index) in previewProducts" :key="index">
|
|
||||||
<view class="product-preview-img" :style="'background: ' + item.color + ';'">
|
|
||||||
<text class="product-preview-emoji">{{ item.emoji }}</text>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<view class="product-preview-info">
|
<!-- 平台功能 + 集成平台 -->
|
||||||
<text class="product-preview-name">{{ item.name }}</text>
|
<PlatformFeatures :features="featureList" />
|
||||||
<text class="product-preview-price">¥{{ item.price }}起</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<view class="see-more" @tap="goProducts">
|
|
||||||
<text>查看更多产品</text>
|
|
||||||
<text class="arrow">></text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 平台功能 -->
|
|
||||||
<view class="features-section">
|
|
||||||
<text class="section-title">用强大功能,开启盈利快车道</text>
|
|
||||||
<view class="features-grid">
|
|
||||||
<view class="feature-card" v-for="(item, index) in features" :key="index">
|
|
||||||
<view class="feature-icon" :style="'background: ' + item.bgColor + ';'">
|
|
||||||
<text class="feature-emoji">{{ item.emoji }}</text>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<text class="feature-title">{{ item.title }}</text>
|
|
||||||
|
|
||||||
<text class="feature-desc">{{ item.desc }}</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 为什么选择 -->
|
<!-- 为什么选择 -->
|
||||||
<view class="why-section">
|
<WhyChoose :reasons="reasonList" />
|
||||||
<text class="section-title">为什么选择Inkreach?</text>
|
|
||||||
<view class="why-grid">
|
|
||||||
<view class="why-card" v-for="(item, index) in reasons" :key="index">
|
|
||||||
<view class="why-icon">
|
|
||||||
<text class="why-emoji">{{ item.emoji }}</text>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<text class="why-title">{{ item.title }}</text>
|
<!-- 公司简介 + 底部CTA -->
|
||||||
|
<CompanyIntro :abilities="companyFeatures" />
|
||||||
<text class="why-desc">{{ item.desc }}</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 公司简介 -->
|
|
||||||
<view class="company-section">
|
|
||||||
<text class="section-title">公司简介</text>
|
|
||||||
<view class="company-card">
|
|
||||||
<view class="company-headline">
|
|
||||||
<text>用科技重新定义服装供应链</text>
|
|
||||||
<text>让每一个创意,都能高效抵达全球</text>
|
|
||||||
</view>
|
|
||||||
<view class="company-content">
|
|
||||||
<view class="company-block">
|
|
||||||
<text class="company-block-title">服务对象与场景</text>
|
|
||||||
<text class="company-block-text">
|
|
||||||
服务于数千家跨境独立站、TikTok、TEMU、SHEIN等平台商家,提供从海外生产到末端物流的一站式供应链服务,让电商创业者专注增长,无惧后端履约。
|
|
||||||
</text>
|
|
||||||
</view>
|
|
||||||
<view class="company-block">
|
|
||||||
<text class="company-block-title">愿景</text>
|
|
||||||
<text class="company-block-text">
|
|
||||||
我们坚信,每一个创意都值得被完美呈现。INKREACH将持续深耕智能供应链生态,用科技消除制造壁垒,让全球创业者专注发挥创造力。
|
|
||||||
</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<view class="company-stats">
|
|
||||||
<view class="company-stat" v-for="(item, index) in companyStats" :key="index">
|
|
||||||
<text class="company-stat-number">{{ item.value }}</text>
|
|
||||||
|
|
||||||
<text class="company-stat-label">{{ item.label }}</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 用户案例 -->
|
|
||||||
<view class="cases-section">
|
|
||||||
<text class="section-title">用户案例</text>
|
|
||||||
<scroll-view class="cases-scroll" :scroll-x="true" :enhanced="true" :show-scrollbar="false">
|
|
||||||
<view class="case-card" v-for="(item, index) in cases" :key="index">
|
|
||||||
<view class="case-image" :style="'background: ' + item.bgColor + ';'">
|
|
||||||
<text class="case-emoji">{{ item.emoji }}</text>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<view class="case-info">
|
|
||||||
<text class="case-title">{{ item.title }}</text>
|
|
||||||
<view class="case-tags">
|
|
||||||
<view class="case-tag" v-for="(tag, index1) in item.tags" :key="index1">{{ tag }}</view>
|
|
||||||
</view>
|
|
||||||
<view class="case-metrics">
|
|
||||||
<view class="case-metric">
|
|
||||||
<text class="case-metric-value">{{ item.roi }}</text>
|
|
||||||
<text class="case-metric-label">ROI</text>
|
|
||||||
</view>
|
|
||||||
<view class="case-metric">
|
|
||||||
<text class="case-metric-value">{{ item.revenue }}</text>
|
|
||||||
<text class="case-metric-label">月收入</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</scroll-view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 最终CTA -->
|
|
||||||
<view class="cta-section">
|
|
||||||
<view class="cta-bg"></view>
|
|
||||||
<view class="cta-content">
|
|
||||||
<view class="cta-title">
|
|
||||||
<text>开始你的POD生意</text>
|
|
||||||
<text>现在就行动</text>
|
|
||||||
</view>
|
|
||||||
<text class="cta-desc">加入成千上万的成功卖家,开始你的定制商品生意</text>
|
|
||||||
<view class="cta-input-wrap">
|
|
||||||
<input class="cta-input" placeholder="输入邮箱开始免费试用" placeholder-class="cta-placeholder" />
|
|
||||||
<view class="cta-btn" @tap="goProducts">立即注册</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 底部 -->
|
|
||||||
<view class="footer">
|
|
||||||
<view class="footer-top">
|
|
||||||
<view class="footer-logo">
|
|
||||||
<text class="footer-logo-en">inkreach</text>
|
|
||||||
<text class="footer-logo-cn">印美达</text>
|
|
||||||
</view>
|
|
||||||
<text class="footer-slogan">全球POD定制平台,服务中国卖家出海</text>
|
|
||||||
</view>
|
|
||||||
<view class="footer-links">
|
|
||||||
<view class="footer-col">
|
|
||||||
<text class="footer-col-title">产品</text>
|
|
||||||
<text class="footer-link">定制卫衣</text>
|
|
||||||
<text class="footer-link">定制T恤</text>
|
|
||||||
<text class="footer-link">定制包包</text>
|
|
||||||
</view>
|
|
||||||
<view class="footer-col">
|
|
||||||
<text class="footer-col-title">支持</text>
|
|
||||||
<text class="footer-link">物流说明</text>
|
|
||||||
<text class="footer-link">客服帮助</text>
|
|
||||||
<text class="footer-link">售后客服</text>
|
|
||||||
</view>
|
|
||||||
<view class="footer-col">
|
|
||||||
<text class="footer-col-title">联系</text>
|
|
||||||
<text class="footer-link">联系我们</text>
|
|
||||||
<text class="footer-link">官方公众号</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<view class="footer-bottom">
|
|
||||||
<text class="footer-copyright">© 2026 INKREACH 印美达全球 All Rights Reserved</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
</view>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
|
import HeroBanner from './components/HeroBanner.vue'
|
||||||
|
import StepsFlow from './components/StepsFlow.vue'
|
||||||
|
import PodCatalog from './components/PodCatalog.vue'
|
||||||
|
import PlatformFeatures from './components/PlatformFeatures.vue'
|
||||||
|
import WhyChoose from './components/WhyChoose.vue'
|
||||||
|
import CompanyIntro from './components/CompanyIntro.vue'
|
||||||
|
|
||||||
|
import {
|
||||||
|
trustStats,
|
||||||
|
stepList,
|
||||||
|
countryTabs,
|
||||||
|
podProducts,
|
||||||
|
featureList,
|
||||||
|
reasonList,
|
||||||
|
companyFeatures
|
||||||
|
} from './mock.js'
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
|
components: {
|
||||||
|
HeroBanner,
|
||||||
|
StepsFlow,
|
||||||
|
PodCatalog,
|
||||||
|
PlatformFeatures,
|
||||||
|
WhyChoose,
|
||||||
|
CompanyIntro
|
||||||
|
},
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
statusBarHeight: 20,
|
trustStats,
|
||||||
currentStep: 2,
|
stepList,
|
||||||
stepEmoji: '🎨',
|
countryTabs,
|
||||||
stepDesc: '使用在线设计工具创建你的专属图案,支持上传图片、添加文字、智能排版',
|
podProducts,
|
||||||
activeCategory: 'all',
|
featureList,
|
||||||
|
reasonList,
|
||||||
categories: [
|
companyFeatures
|
||||||
{
|
|
||||||
id: 'all',
|
|
||||||
name: '全部'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 'tshirt',
|
|
||||||
name: 'T恤'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 'hoodie',
|
|
||||||
name: '卫衣'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 'bag',
|
|
||||||
name: '包包'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 'kids',
|
|
||||||
name: '童装'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 'home',
|
|
||||||
name: '家居'
|
|
||||||
}
|
}
|
||||||
],
|
|
||||||
|
|
||||||
previewProducts: [
|
|
||||||
{
|
|
||||||
id: 1,
|
|
||||||
name: '180G牛奶丝T恤 DG120',
|
|
||||||
price: '28.00',
|
|
||||||
color: '#F5F5F5',
|
|
||||||
emoji: '👕'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 2,
|
|
||||||
name: '纯棉连帽卫衣 HD200',
|
|
||||||
price: '59.00',
|
|
||||||
color: '#E8E8E8',
|
|
||||||
emoji: '🧥'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 3,
|
|
||||||
name: '帆布托特包 BG150',
|
|
||||||
price: '15.00',
|
|
||||||
color: '#F0F0F0',
|
|
||||||
emoji: '👜'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 4,
|
|
||||||
name: '儿童纯棉T恤 KD100',
|
|
||||||
price: '22.00',
|
|
||||||
color: '#F8F8F8',
|
|
||||||
emoji: '👶'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
|
|
||||||
features: [
|
|
||||||
{
|
|
||||||
id: 1,
|
|
||||||
title: '设计工具',
|
|
||||||
desc: '在线设计器,海量模板自由创作',
|
|
||||||
emoji: '🎨',
|
|
||||||
bgColor: '#FFF0E5'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 2,
|
|
||||||
title: '自动化履约',
|
|
||||||
desc: '订单自动分配工厂生产发货',
|
|
||||||
emoji: '⚙️',
|
|
||||||
bgColor: '#E5F5FF'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 3,
|
|
||||||
title: '全球配送',
|
|
||||||
desc: '覆盖200+国家地区快速达',
|
|
||||||
emoji: '🌍',
|
|
||||||
bgColor: '#F0FFE5'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 4,
|
|
||||||
title: '店铺集成',
|
|
||||||
desc: '对接Shopify等主流平台',
|
|
||||||
emoji: '🔗',
|
|
||||||
bgColor: '#FFF5E5'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
|
|
||||||
reasons: [
|
|
||||||
{
|
|
||||||
id: 1,
|
|
||||||
title: '零库存',
|
|
||||||
desc: '无需囤货按需生产',
|
|
||||||
emoji: '📦'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 2,
|
|
||||||
title: '快速生产',
|
|
||||||
desc: '48小时极速出货',
|
|
||||||
emoji: '⚡'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 3,
|
|
||||||
title: '优质产品',
|
|
||||||
desc: '严格品质管控',
|
|
||||||
emoji: '✨'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 4,
|
|
||||||
title: '全球配送',
|
|
||||||
desc: '覆盖200+国家',
|
|
||||||
emoji: '🚀'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
|
|
||||||
companyStats: [
|
|
||||||
{
|
|
||||||
value: '5000+',
|
|
||||||
label: '合作卖家'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
value: '500+',
|
|
||||||
label: '合作工厂'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
value: '20+',
|
|
||||||
label: '覆盖国家'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
value: '1000万+',
|
|
||||||
label: '订单履约'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
|
|
||||||
cases: [
|
|
||||||
{
|
|
||||||
id: 1,
|
|
||||||
title: '潮牌T恤定制',
|
|
||||||
tags: ['T恤', '烫画'],
|
|
||||||
roi: '260%',
|
|
||||||
revenue: '$12K',
|
|
||||||
bgColor: '#F5F5F5',
|
|
||||||
emoji: '👕'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 2,
|
|
||||||
title: '连帽卫衣品牌',
|
|
||||||
tags: ['卫衣', '刺绣'],
|
|
||||||
roi: '300%',
|
|
||||||
revenue: '$25K',
|
|
||||||
bgColor: '#E8E8E8',
|
|
||||||
emoji: '🧥'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: 3,
|
|
||||||
title: '环保帆布包',
|
|
||||||
tags: ['包包', '丝印'],
|
|
||||||
roi: '180%',
|
|
||||||
revenue: '$8K',
|
|
||||||
bgColor: '#F0F0F0',
|
|
||||||
emoji: '👜'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
|
|
||||||
tag: ''
|
|
||||||
};
|
|
||||||
},
|
|
||||||
onLoad() {
|
|
||||||
const app = getApp();
|
|
||||||
this.setData({
|
|
||||||
statusBarHeight: app.globalData.statusBarHeight || 20
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
selectStep(e) {
|
onGoProducts() {
|
||||||
const step = e.currentTarget.dataset.step;
|
|
||||||
const stepData = {
|
|
||||||
1: {
|
|
||||||
emoji: '📦',
|
|
||||||
desc: '从全球POD货盘中选择热销产品,涵盖服装、配饰、家居等多品类'
|
|
||||||
},
|
|
||||||
2: {
|
|
||||||
emoji: '🎨',
|
|
||||||
desc: '使用在线设计工具创建你的专属图案,支持上传图片、添加文字、智能排版'
|
|
||||||
},
|
|
||||||
3: {
|
|
||||||
emoji: '🛒',
|
|
||||||
desc: '一键发布到Shopify、TikTok Shop等主流电商平台,自动同步商品信息'
|
|
||||||
},
|
|
||||||
4: {
|
|
||||||
emoji: '🚚',
|
|
||||||
desc: '订单自动分配至最近工厂生产,全球物流配送直达消费者手中'
|
|
||||||
}
|
|
||||||
};
|
|
||||||
this.setData({
|
|
||||||
currentStep: step,
|
|
||||||
stepEmoji: stepData[step].emoji,
|
|
||||||
stepDesc: stepData[step].desc
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
selectCategory(e) {
|
|
||||||
this.setData({
|
|
||||||
activeCategory: e.currentTarget.dataset.id
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
goProducts() {
|
|
||||||
uni.switchTab({
|
uni.switchTab({
|
||||||
url: '/pages/products/products'
|
url: '/pages/products/products'
|
||||||
});
|
})
|
||||||
},
|
},
|
||||||
|
onGoDetail(item) {
|
||||||
goHome() {
|
|
||||||
uni.pageScrollTo({
|
|
||||||
scrollTop: 0,
|
|
||||||
duration: 300
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
goProductDetail(e) {
|
|
||||||
const id = e.currentTarget.dataset.id;
|
|
||||||
uni.navigateTo({
|
uni.navigateTo({
|
||||||
url: `/pages/product-detail/product-detail?id=${id}`
|
url: '/pages/product-detail/product-detail?id=' + item.id
|
||||||
});
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
@import './index.css';
|
.index-page {
|
||||||
|
width: 100%;
|
||||||
|
min-height: 100vh;
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
@@ -0,0 +1,170 @@
|
|||||||
|
// 首页 mock 数据
|
||||||
|
// 设计稿尺寸: 390px 宽度,1px = 750/390 ≈ 1.923rpx
|
||||||
|
|
||||||
|
// Hero 区 4个指标
|
||||||
|
export const trustStats = [
|
||||||
|
{ value: '11国', label: '全球生产工厂' },
|
||||||
|
{ value: '24h', label: '极速发货' },
|
||||||
|
{ value: '1000w+', label: '订单履约' },
|
||||||
|
{ value: '800+', label: '产品SKU' }
|
||||||
|
]
|
||||||
|
|
||||||
|
// 4步流程
|
||||||
|
export const stepList = [
|
||||||
|
{
|
||||||
|
step: '01',
|
||||||
|
title: '选择产品',
|
||||||
|
desc: '海量爆款产品,满足多元化场景需求'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
step: '02',
|
||||||
|
title: '上传设计',
|
||||||
|
desc: '可视化编辑器,轻松实现创意落地'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
step: '03',
|
||||||
|
title: '自动生产',
|
||||||
|
desc: '智能分发工厂,高效品质管控'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
step: '04',
|
||||||
|
title: '全球配送',
|
||||||
|
desc: '多国本地仓,7日极速达'
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
// 全球POD货盘 - 国家tab
|
||||||
|
export const countryTabs = [
|
||||||
|
{ id: 'us', name: '美国', flag: '🇺🇸' },
|
||||||
|
{ id: 'ca', name: '加拿大', flag: '🇨🇦' },
|
||||||
|
{ id: 'mx', name: '墨西哥', flag: '🇲🇽' },
|
||||||
|
{ id: 'br', name: '巴西', flag: '🇧🇷' },
|
||||||
|
{ id: 'ar', name: '阿根廷', flag: '🇦🇷' }
|
||||||
|
]
|
||||||
|
|
||||||
|
// 全球POD货盘 - 产品列表
|
||||||
|
export const podProducts = [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
name: '女士短款露脐T恤',
|
||||||
|
price: '19.00',
|
||||||
|
image: '/static/images/home/Rectangle_181_1455_1450.png'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
name: '女士短款露脐T恤',
|
||||||
|
price: '19.00',
|
||||||
|
image: '/static/images/home/Rectangle_181_1455_1456.png'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
name: '女士短款露脐T恤',
|
||||||
|
price: '19.00',
|
||||||
|
image: '/static/images/home/Rectangle_63_1446_1437.png'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 4,
|
||||||
|
name: '女士短款露脐T恤',
|
||||||
|
price: '19.00',
|
||||||
|
image: '/static/images/home/Rectangle_63_1455_1461.png'
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
// 平台功能卡片
|
||||||
|
export const featureList = [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
title: '在线设计工具',
|
||||||
|
desc: '可视化编辑器,支持图片文字自由创作',
|
||||||
|
icon: '/static/icons/home/Vector_1460_1460.svg',
|
||||||
|
bgColor: '#FFF0E5'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
title: '自动化履约',
|
||||||
|
desc: '订单自动分配工厂生产发货',
|
||||||
|
icon: '/static/icons/home/Vector_1461_1461.svg',
|
||||||
|
bgColor: '#E5F5FF'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
title: '全球配送',
|
||||||
|
desc: '多国本地仓7日达',
|
||||||
|
icon: '/static/icons/home/Vector_1462_1462.svg',
|
||||||
|
bgColor: '#F0FFE5'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 4,
|
||||||
|
title: '店铺集成',
|
||||||
|
desc: '对接主流电商平台',
|
||||||
|
icon: '/static/icons/home/Vector_1463_1463.svg',
|
||||||
|
bgColor: '#FFF5E5'
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
// 集成平台列表
|
||||||
|
export const platformList = [
|
||||||
|
{ id: 1, name: 'Amazon', image: '' },
|
||||||
|
{ id: 2, name: 'Shopify', image: '' },
|
||||||
|
{ id: 3, name: 'TikTok', image: '' },
|
||||||
|
{ id: 4, name: 'Temu', image: '' },
|
||||||
|
{ id: 5, name: 'Shein', image: '' },
|
||||||
|
{ id: 6, name: 'Etsy', image: '' },
|
||||||
|
{ id: 7, name: 'eBay', image: '' }
|
||||||
|
]
|
||||||
|
|
||||||
|
// 为什么选择 - 4个优势
|
||||||
|
export const reasonList = [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
title: '零库存',
|
||||||
|
desc: '按需生产,降低库存风险',
|
||||||
|
icon: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
title: '快速生产',
|
||||||
|
desc: '48小时极速出货',
|
||||||
|
icon: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
title: '优质产品',
|
||||||
|
desc: '严格品质管控',
|
||||||
|
icon: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 4,
|
||||||
|
title: '全球配送',
|
||||||
|
desc: '覆盖200+国家',
|
||||||
|
icon: ''
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
// 公司简介 - 4个核心能力
|
||||||
|
export const companyFeatures = [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
title: '前沿印花技术',
|
||||||
|
desc: '创新数码直喷等工艺,品质与效率兼得',
|
||||||
|
icon: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
title: 'AI 深度AI应用',
|
||||||
|
desc: 'AI设计辅助生产,全链路智能提效',
|
||||||
|
icon: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
title: '全球智能工厂',
|
||||||
|
desc: '11国本土化生产POD工厂,当地产能随时开启',
|
||||||
|
icon: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 4,
|
||||||
|
title: '一站式柔性交付',
|
||||||
|
desc: '覆盖生产到物流,从小品牌到大牌全链路业务落地',
|
||||||
|
icon: ''
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,95 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 颜色选择:第一行 4 个,第二行 2 个;胶囊样式,选中橙色边框+橙色文字 -->
|
||||||
|
<view class="color-wrap">
|
||||||
|
<text class="title">颜色</text>
|
||||||
|
|
||||||
|
<view class="color-list">
|
||||||
|
<view
|
||||||
|
v-for="(item, index) in list"
|
||||||
|
:key="index"
|
||||||
|
class="color-pill"
|
||||||
|
:class="{ active: selectedId === item.id }"
|
||||||
|
@tap="selectColor(item.id)"
|
||||||
|
>
|
||||||
|
<view class="color-dot" :style="{ background: item.value }"></view>
|
||||||
|
<text class="color-name">{{ item.name }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'ColorSelector',
|
||||||
|
props: {
|
||||||
|
list: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
selectedId: {
|
||||||
|
type: [String, Number],
|
||||||
|
default: ''
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
selectColor(id) {
|
||||||
|
this.$emit('select', id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.color-wrap {
|
||||||
|
padding: 30rpx 20rpx; /* 15px 10px */
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 标题 */
|
||||||
|
.title {
|
||||||
|
display: block;
|
||||||
|
font-size: 29rpx; /* 15px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
margin-bottom: 30rpx; /* 15px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 胶囊列表 */
|
||||||
|
.color-list {
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 16rpx; /* 8px 横向 / 纵向 */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 单个胶囊:padding 5px 12px,圆角 60px */
|
||||||
|
.color-pill {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8rpx; /* 4px */
|
||||||
|
padding: 10rpx 24rpx; /* 5px 12px */
|
||||||
|
border: 1rpx solid #f2f2f2;
|
||||||
|
border-radius: 120rpx; /* 60px */
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
.color-pill.active {
|
||||||
|
border-color: #ff6800;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 颜色圆点 15x15,1px 灰色边框 */
|
||||||
|
.color-dot {
|
||||||
|
width: 30rpx; /* 15px */
|
||||||
|
height: 30rpx;
|
||||||
|
border-radius: 50%;
|
||||||
|
border: 1rpx solid #cdcdcd;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 颜色名称 14px 黑,选中橙色 */
|
||||||
|
.color-name {
|
||||||
|
font-size: 27rpx; /* 14px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
.color-pill.active .color-name {
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,91 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 产品图片轮播 + 自定义指示点 -->
|
||||||
|
<view class="detail-swiper">
|
||||||
|
<swiper
|
||||||
|
class="swiper"
|
||||||
|
:circular="true"
|
||||||
|
:indicator-dots="false"
|
||||||
|
@change="onChange"
|
||||||
|
>
|
||||||
|
<swiper-item v-for="(item, index) in images" :key="index">
|
||||||
|
<view class="swiper-item">
|
||||||
|
<image class="swiper-image" :src="item" mode="aspectFill"></image>
|
||||||
|
</view>
|
||||||
|
</swiper-item>
|
||||||
|
</swiper>
|
||||||
|
|
||||||
|
<!-- 自定义指示点:active 16x8 橙色胶囊,inactive 8x8 黑色 20% -->
|
||||||
|
<view class="dots">
|
||||||
|
<view
|
||||||
|
v-for="(item, index) in images"
|
||||||
|
:key="index"
|
||||||
|
class="dot"
|
||||||
|
:class="{ active: current === index }"
|
||||||
|
></view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'DetailSwiper',
|
||||||
|
props: {
|
||||||
|
images: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
current: 0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
onChange(e) {
|
||||||
|
this.current = e.detail.current
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.detail-swiper {
|
||||||
|
position: relative;
|
||||||
|
width: 100%;
|
||||||
|
background: #f2f2f2;
|
||||||
|
}
|
||||||
|
.swiper {
|
||||||
|
width: 100%;
|
||||||
|
height: 500rpx; /* 260px */
|
||||||
|
}
|
||||||
|
.swiper-item {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
.swiper-image {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 指示点:覆盖在图片底部 */
|
||||||
|
.dots {
|
||||||
|
position: absolute;
|
||||||
|
bottom: 20rpx; /* 距图片底部 10px */
|
||||||
|
left: 50%;
|
||||||
|
transform: translateX(-50%);
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 12rpx; /* 6px */
|
||||||
|
}
|
||||||
|
.dot {
|
||||||
|
width: 16rpx; /* 8px */
|
||||||
|
height: 16rpx;
|
||||||
|
background: rgba(0, 0, 0, 0.2);
|
||||||
|
border-radius: 8rpx; /* 4px */
|
||||||
|
}
|
||||||
|
.dot.active {
|
||||||
|
width: 32rpx; /* 16px */
|
||||||
|
height: 16rpx; /* 8px */
|
||||||
|
background: #ff6800;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,146 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 包装规格表:4 列 × 4 行,每个数据单元格双单位(cm + in) -->
|
||||||
|
<view class="pack-wrap">
|
||||||
|
<view class="header-row">
|
||||||
|
<text class="title">包装规格</text>
|
||||||
|
<text class="unit">单位:{{ data.unit }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="table">
|
||||||
|
<!-- 表头:bg #DFDFDF,圆角 6px -->
|
||||||
|
<view class="row header">
|
||||||
|
<text
|
||||||
|
class="cell"
|
||||||
|
v-for="(col, index) in data.columns"
|
||||||
|
:key="index"
|
||||||
|
>{{ col }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 数据行:偶数行 bg #F7F7F7,行高 60px(双行内容) -->
|
||||||
|
<view
|
||||||
|
class="row data-row"
|
||||||
|
:class="{ alt: (index + 1) % 2 === 0 }"
|
||||||
|
v-for="(row, index) in data.rows"
|
||||||
|
:key="index"
|
||||||
|
>
|
||||||
|
<!-- 尺码列:单行居中 -->
|
||||||
|
<view class="cell size-cell">
|
||||||
|
<text class="size-text">{{ row.size }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 尺寸列:cm + in 双行 -->
|
||||||
|
<view class="cell dual-cell">
|
||||||
|
<text class="dual-top">{{ row.dimension.cm }}</text>
|
||||||
|
<text class="dual-bottom">{{ row.dimension.in }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 体积列:cm + in 双行 -->
|
||||||
|
<view class="cell dual-cell">
|
||||||
|
<text class="dual-top">{{ row.volume.cm }}</text>
|
||||||
|
<text class="dual-bottom">{{ row.volume.in }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 重量列:cm + in 双行 -->
|
||||||
|
<view class="cell dual-cell">
|
||||||
|
<text class="dual-top">{{ row.weight.cm }}</text>
|
||||||
|
<text class="dual-bottom">{{ row.weight.in }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'PackagingSpec',
|
||||||
|
props: {
|
||||||
|
data: {
|
||||||
|
type: Object,
|
||||||
|
default: () => ({})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.pack-wrap {
|
||||||
|
padding: 30rpx 20rpx; /* 15px 10px */
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 标题行 */
|
||||||
|
.header-row {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
margin-bottom: 20rpx; /* 10px */
|
||||||
|
}
|
||||||
|
.title {
|
||||||
|
font-size: 29rpx; /* 15px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
.unit {
|
||||||
|
margin-left: 16rpx;
|
||||||
|
font-size: 21rpx; /* 11px */
|
||||||
|
color: rgba(0, 0, 0, 0.5);
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 表格 */
|
||||||
|
.table {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 8rpx; /* 4px 行间距 */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 单行 */
|
||||||
|
.row {
|
||||||
|
display: flex;
|
||||||
|
border-radius: 12rpx; /* 6px */
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
.row.header {
|
||||||
|
height: 77rpx; /* 40px */
|
||||||
|
background: #dfdfdf;
|
||||||
|
}
|
||||||
|
.row.data-row {
|
||||||
|
height: 115rpx; /* 60px 双行内容更高 */
|
||||||
|
}
|
||||||
|
.row.alt {
|
||||||
|
background: #f7f7f7;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 单元格 */
|
||||||
|
.cell {
|
||||||
|
flex: 1;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 表头文字 */
|
||||||
|
.row.header .cell {
|
||||||
|
font-size: 25rpx; /* 13px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 尺码列:单行 13px */
|
||||||
|
.size-text {
|
||||||
|
font-size: 25rpx; /* 13px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 双单位单元格:cm 在上,in 在下 */
|
||||||
|
.dual-cell {
|
||||||
|
gap: 4rpx; /* 2px */
|
||||||
|
}
|
||||||
|
.dual-top,
|
||||||
|
.dual-bottom {
|
||||||
|
font-size: 19rpx; /* 10px */
|
||||||
|
color: rgba(0, 0, 0, 0.6);
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,179 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 产品参数:普通参数行 + 可展开的"补充说明" -->
|
||||||
|
<view class="params-wrap">
|
||||||
|
<text class="title">产品参数</text>
|
||||||
|
|
||||||
|
<!-- 普通参数行 -->
|
||||||
|
<view
|
||||||
|
class="param-row"
|
||||||
|
v-for="(item, index) in normalParams"
|
||||||
|
:key="index"
|
||||||
|
>
|
||||||
|
<text class="param-label">{{ item.label }}</text>
|
||||||
|
<text class="param-value">{{ item.value }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 可展开的"补充说明" -->
|
||||||
|
<view class="param-row expandable-row" v-if="expandableParam">
|
||||||
|
<text class="param-label">{{ expandableParam.label }}</text>
|
||||||
|
<view class="expandable-content">
|
||||||
|
<text class="param-value" :class="{ 'value-collapsed': !expanded }">{{ expandableParam.value }}</text>
|
||||||
|
|
||||||
|
<!-- 渐变遮罩 + 展开按钮(仅收起态显示) -->
|
||||||
|
<view class="expand-overlay" v-if="!expanded">
|
||||||
|
<view class="gradient-mask"></view>
|
||||||
|
<view class="expand-btn" @tap="toggleExpand">
|
||||||
|
<text class="expand-text">展开</text>
|
||||||
|
<view class="arrow-down"></view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 展开后的"收起"按钮 -->
|
||||||
|
<view class="collapse-btn" v-if="expanded" @tap="toggleExpand">
|
||||||
|
<text class="expand-text">收起</text>
|
||||||
|
<view class="arrow-up"></view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'ParamsTable',
|
||||||
|
props: {
|
||||||
|
list: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
expanded: false
|
||||||
|
}
|
||||||
|
},
|
||||||
|
computed: {
|
||||||
|
normalParams() {
|
||||||
|
return this.list.filter((item) => !item.expandable)
|
||||||
|
},
|
||||||
|
expandableParam() {
|
||||||
|
return this.list.find((item) => item.expandable)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
toggleExpand() {
|
||||||
|
this.expanded = !this.expanded
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.params-wrap {
|
||||||
|
padding: 30rpx 20rpx; /* 15px 10px */
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 标题 */
|
||||||
|
.title {
|
||||||
|
display: block;
|
||||||
|
font-size: 29rpx; /* 15px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
margin-bottom: 20rpx; /* 10px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 普通参数行 */
|
||||||
|
.param-row {
|
||||||
|
display: flex;
|
||||||
|
align-items: flex-start;
|
||||||
|
padding: 10rpx 0; /* 5px 上下 */
|
||||||
|
}
|
||||||
|
.param-label {
|
||||||
|
width: 170rpx; /* 给 label 固定宽度对齐 */
|
||||||
|
flex-shrink: 0;
|
||||||
|
font-size: 25rpx; /* 13px */
|
||||||
|
color: rgba(0, 0, 0, 0.5); /* 黑色 50% 透明度 */
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
.param-value {
|
||||||
|
flex: 1;
|
||||||
|
font-size: 25rpx; /* 13px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 可展开的"补充说明"行 */
|
||||||
|
.expandable-row {
|
||||||
|
align-items: flex-start;
|
||||||
|
}
|
||||||
|
.expandable-content {
|
||||||
|
position: relative;
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 收起态:限制高度(约 5 行,留出渐变遮罩空间) */
|
||||||
|
.value-collapsed {
|
||||||
|
display: block;
|
||||||
|
max-height: 165rpx; /* 约 5 行 33rpx */
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 渐变遮罩:绝对定位在容器底部 60px,从透明到白 */
|
||||||
|
.expand-overlay {
|
||||||
|
position: absolute;
|
||||||
|
bottom: 0;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
height: 120rpx; /* 60px */
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
.gradient-mask {
|
||||||
|
position: absolute;
|
||||||
|
inset: 0;
|
||||||
|
background: linear-gradient(
|
||||||
|
180deg,
|
||||||
|
rgba(255, 255, 255, 0) 0%,
|
||||||
|
rgba(255, 255, 255, 1) 52%
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 展开/收起按钮:居中显示,可点击 */
|
||||||
|
.expand-btn,
|
||||||
|
.collapse-btn {
|
||||||
|
position: absolute;
|
||||||
|
bottom: 10rpx;
|
||||||
|
left: 50%;
|
||||||
|
transform: translateX(-50%);
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8rpx; /* 4px */
|
||||||
|
pointer-events: auto;
|
||||||
|
}
|
||||||
|
/* 展开态的"收起"按钮:在文本下方居中 */
|
||||||
|
.collapse-btn {
|
||||||
|
position: relative;
|
||||||
|
margin-top: 16rpx;
|
||||||
|
left: auto;
|
||||||
|
transform: none;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
.expand-text {
|
||||||
|
font-size: 23rpx; /* 12px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* CSS 箭头:12x12,下/上 */
|
||||||
|
.arrow-down,
|
||||||
|
.arrow-up {
|
||||||
|
width: 12rpx;
|
||||||
|
height: 12rpx;
|
||||||
|
border-right: 2rpx solid #000;
|
||||||
|
border-bottom: 2rpx solid #000;
|
||||||
|
transform: rotate(45deg);
|
||||||
|
}
|
||||||
|
.arrow-up {
|
||||||
|
transform: rotate(-135deg);
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,137 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 产品信息:名称 / SKU / 国家 / 价格 / 4 列快捷信息 -->
|
||||||
|
<view class="info-wrap">
|
||||||
|
<!-- 产品名称 18px Bold #1A1A1A -->
|
||||||
|
<text class="name">{{ info.name }}</text>
|
||||||
|
|
||||||
|
<!-- SKU + 国家 同行 12px #979797,值黑色 -->
|
||||||
|
<view class="meta-row">
|
||||||
|
<view class="meta-item">
|
||||||
|
<text class="meta-label">SKU: </text>
|
||||||
|
<text class="meta-value">{{ info.sku }}</text>
|
||||||
|
</view>
|
||||||
|
<view class="meta-item">
|
||||||
|
<text class="meta-label">国家: </text>
|
||||||
|
<text class="meta-value">{{ info.country }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 价格:¥ 和 .00 为 10px,整数 24px,全部红色 -->
|
||||||
|
<view class="price-row">
|
||||||
|
<text class="price-symbol">{{ info.price.symbol }}</text>
|
||||||
|
<text class="price-integer">{{ info.price.integer }}</text>
|
||||||
|
<text class="price-decimal">{{ info.price.decimal }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 分隔线 0.5px #F0F0F0 -->
|
||||||
|
<view class="divider"></view>
|
||||||
|
|
||||||
|
<!-- 4 列快捷信息:label 10px 灰,value 13px 黑 居中 -->
|
||||||
|
<view class="quick-info">
|
||||||
|
<view class="quick-col" v-for="(item, index) in info.quickInfo" :key="index">
|
||||||
|
<text class="quick-label">{{ item.label }}</text>
|
||||||
|
<text class="quick-value">{{ item.value }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'ProductInfo',
|
||||||
|
props: {
|
||||||
|
info: {
|
||||||
|
type: Object,
|
||||||
|
default: () => ({})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.info-wrap {
|
||||||
|
padding: 20rpx 20rpx 24rpx; /* 10px 10px 12px */
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 产品名称 */
|
||||||
|
.name {
|
||||||
|
display: block;
|
||||||
|
font-size: 35rpx; /* 18px */
|
||||||
|
font-weight: 700;
|
||||||
|
color: #1a1a1a;
|
||||||
|
line-height: 50rpx; /* 26px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* SKU / 国家 同行 */
|
||||||
|
.meta-row {
|
||||||
|
display: flex;
|
||||||
|
margin-top: 10rpx;
|
||||||
|
}
|
||||||
|
.meta-item {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
.meta-item + .meta-item {
|
||||||
|
margin-left: 20rpx;
|
||||||
|
}
|
||||||
|
.meta-label {
|
||||||
|
font-size: 23rpx; /* 12px */
|
||||||
|
color: #979797;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
.meta-value {
|
||||||
|
font-size: 23rpx;
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 价格 */
|
||||||
|
.price-row {
|
||||||
|
display: flex;
|
||||||
|
align-items: baseline;
|
||||||
|
margin-top: 16rpx;
|
||||||
|
}
|
||||||
|
.price-symbol,
|
||||||
|
.price-decimal {
|
||||||
|
font-size: 19rpx; /* 10px */
|
||||||
|
color: #ff0000;
|
||||||
|
font-weight: 700;
|
||||||
|
}
|
||||||
|
.price-integer {
|
||||||
|
font-size: 46rpx; /* 24px */
|
||||||
|
color: #ff0000;
|
||||||
|
font-weight: 700;
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 分隔线 */
|
||||||
|
.divider {
|
||||||
|
height: 1rpx; /* 0.5px */
|
||||||
|
background: #f0f0f0;
|
||||||
|
margin-top: 26rpx; /* 13px 间隙 */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 4 列快捷信息 */
|
||||||
|
.quick-info {
|
||||||
|
display: flex;
|
||||||
|
margin-top: 20rpx; /* 10px */
|
||||||
|
}
|
||||||
|
.quick-col {
|
||||||
|
flex: 1;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8rpx;
|
||||||
|
}
|
||||||
|
.quick-label {
|
||||||
|
font-size: 19rpx; /* 10px */
|
||||||
|
color: #979797;
|
||||||
|
line-height: 27rpx;
|
||||||
|
}
|
||||||
|
.quick-value {
|
||||||
|
font-size: 25rpx; /* 13px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,114 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 产品尺码表:5 列 × 4 行,交替行背景 -->
|
||||||
|
<view class="chart-wrap">
|
||||||
|
<view class="header-row">
|
||||||
|
<text class="title">产品尺码</text>
|
||||||
|
<text class="unit">单位:{{ data.unit }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="table">
|
||||||
|
<!-- 表头:bg #DFDFDF,圆角 6px -->
|
||||||
|
<view class="row header">
|
||||||
|
<text
|
||||||
|
class="cell"
|
||||||
|
v-for="(col, index) in data.columns"
|
||||||
|
:key="index"
|
||||||
|
>{{ col }}</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 数据行:偶数行(第 2、4 行)bg #F7F7F7,圆角 6px -->
|
||||||
|
<view
|
||||||
|
class="row"
|
||||||
|
:class="{ alt: (index + 1) % 2 === 0 }"
|
||||||
|
v-for="(row, index) in data.rows"
|
||||||
|
:key="index"
|
||||||
|
>
|
||||||
|
<text class="cell">{{ row.size }}</text>
|
||||||
|
<text class="cell">{{ row.shoulder }}</text>
|
||||||
|
<text class="cell">{{ row.chest }}</text>
|
||||||
|
<text class="cell">{{ row.length }}</text>
|
||||||
|
<text class="cell">{{ row.sleeve }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'SizeChart',
|
||||||
|
props: {
|
||||||
|
data: {
|
||||||
|
type: Object,
|
||||||
|
default: () => ({})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.chart-wrap {
|
||||||
|
padding: 30rpx 20rpx; /* 15px 10px */
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 标题行:产品尺码 + 单位 */
|
||||||
|
.header-row {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
margin-bottom: 20rpx; /* 10px */
|
||||||
|
}
|
||||||
|
.title {
|
||||||
|
font-size: 29rpx; /* 15px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
.unit {
|
||||||
|
margin-left: 16rpx; /* 8px */
|
||||||
|
font-size: 21rpx; /* 11px */
|
||||||
|
color: rgba(0, 0, 0, 0.5);
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 表格 */
|
||||||
|
.table {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 8rpx; /* 行间距 4px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 单行 */
|
||||||
|
.row {
|
||||||
|
display: flex;
|
||||||
|
height: 77rpx; /* 40px */
|
||||||
|
align-items: center;
|
||||||
|
border-radius: 12rpx; /* 6px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 表头行 */
|
||||||
|
.row.header {
|
||||||
|
background: #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 偶数行(交替背景) */
|
||||||
|
.row.alt {
|
||||||
|
background: #f7f7f7;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 单元格:等宽分布 */
|
||||||
|
.cell {
|
||||||
|
flex: 1;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 25rpx; /* 13px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
.row.header .cell {
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
.row:not(.header) .cell {
|
||||||
|
opacity: 0.6;
|
||||||
|
}
|
||||||
|
.row:not(.header) .cell:first-child {
|
||||||
|
opacity: 1; /* 尺码列不透明 */
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,87 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 尺码选择:5 个按钮横排,选中态橙色边框+橙色文字(背景仍为浅灰) -->
|
||||||
|
<view class="size-wrap">
|
||||||
|
<text class="title">尺码</text>
|
||||||
|
|
||||||
|
<view class="size-list">
|
||||||
|
<view
|
||||||
|
v-for="(item, index) in list"
|
||||||
|
:key="index"
|
||||||
|
class="size-item"
|
||||||
|
:class="{ active: selected === item }"
|
||||||
|
@tap="selectSize(item)"
|
||||||
|
>
|
||||||
|
<text class="size-text">{{ item }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'SizeSelector',
|
||||||
|
props: {
|
||||||
|
list: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
selected: {
|
||||||
|
type: String,
|
||||||
|
default: ''
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
selectSize(size) {
|
||||||
|
this.$emit('select', size)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.size-wrap {
|
||||||
|
padding: 30rpx 20rpx; /* 15px 10px */
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 标题 */
|
||||||
|
.title {
|
||||||
|
display: block;
|
||||||
|
font-size: 29rpx; /* 15px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
margin-bottom: 30rpx; /* 15px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 尺码列表横排 */
|
||||||
|
.size-list {
|
||||||
|
display: flex;
|
||||||
|
gap: 12rpx; /* 6px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 单个尺码按钮 44x34,圆角 4px,背景 #F7F7F7 */
|
||||||
|
.size-item {
|
||||||
|
width: 85rpx; /* 44px */
|
||||||
|
height: 65rpx; /* 34px */
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
background: #f7f7f7;
|
||||||
|
border: 1rpx solid transparent;
|
||||||
|
border-radius: 8rpx; /* 4px */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 选中:橙色边框 + 橙色文字(背景保持 #F7F7F7) */
|
||||||
|
.size-item.active {
|
||||||
|
border-color: #ff6800;
|
||||||
|
}
|
||||||
|
|
||||||
|
.size-text {
|
||||||
|
font-size: 25rpx; /* 13px */
|
||||||
|
color: #000000;
|
||||||
|
line-height: 33rpx;
|
||||||
|
}
|
||||||
|
.size-item.active .size-text {
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,100 @@
|
|||||||
|
// 产品详情页 mock 数据(基于 Figma 设计稿 1544:530)
|
||||||
|
|
||||||
|
export const mockProduct = {
|
||||||
|
id: 1,
|
||||||
|
name: '180G牛奶丝T恤 DG120',
|
||||||
|
sku: 'DG120',
|
||||||
|
country: '美国',
|
||||||
|
// 价格:符号/整数/小数 三段不同字号,全部红色 #FF0000
|
||||||
|
price: {
|
||||||
|
symbol: '¥',
|
||||||
|
integer: '19',
|
||||||
|
decimal: '.00'
|
||||||
|
},
|
||||||
|
// 价格下方的 4 列快捷信息
|
||||||
|
quickInfo: [
|
||||||
|
{ label: '生产工艺', value: '白墨烫画' },
|
||||||
|
{ label: '发货时效', value: '48小时' },
|
||||||
|
{ label: '印花', value: '单面印' },
|
||||||
|
{ label: '产品编码', value: 'NS6001152' }
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
// 5 张图片对应 5 个指示点(mock 用同一张图)
|
||||||
|
export const mockImages = [
|
||||||
|
'/static/images/detail/Rectangle_194_1548_574.png',
|
||||||
|
'/static/images/detail/Rectangle_194_1548_574.png',
|
||||||
|
'/static/images/detail/Rectangle_194_1548_574.png',
|
||||||
|
'/static/images/detail/Rectangle_194_1548_574.png',
|
||||||
|
'/static/images/detail/Rectangle_194_1548_574.png'
|
||||||
|
]
|
||||||
|
|
||||||
|
// 6 个颜色:第一行 4 个,第二行 2 个;默认选中"灰色"
|
||||||
|
export const mockColors = [
|
||||||
|
{ id: 1, name: '白色', value: '#FFFFFF' },
|
||||||
|
{ id: 2, name: '黑色', value: '#000000' },
|
||||||
|
{ id: 3, name: '灰色', value: '#838383' },
|
||||||
|
{ id: 4, name: '橙色', value: '#FF6800' },
|
||||||
|
{ id: 5, name: '藏青', value: '#0F215B' },
|
||||||
|
{ id: 6, name: '粉色', value: '#FFB7D2' }
|
||||||
|
]
|
||||||
|
|
||||||
|
// 默认选中 L
|
||||||
|
export const mockSizes = ['S', 'M', 'L', 'XL', '2XL']
|
||||||
|
|
||||||
|
// 产品参数:前 3 项固定行高,"补充说明"可展开/收起
|
||||||
|
export const mockParams = [
|
||||||
|
{ label: '克重', value: '180g' },
|
||||||
|
{ label: '材质', value: '纯棉' },
|
||||||
|
{ label: '定制类型', value: '来图定制' },
|
||||||
|
{
|
||||||
|
label: '补充说明',
|
||||||
|
expandable: true,
|
||||||
|
value:
|
||||||
|
'【 材质说明 】\n97%聚酯纤维 3%氨纶\n【 产品性能 】\n优质材料:这款露背T恤采用优质材料制成,面料柔软、轻薄贴身。 时尚外观:性感T恤设计,时尚性感,简约大方,适合大多数人的体型。 面料轻盈:舒适款式设计为您带来一个更加干净的外观,面料轻盈柔软,让您全天舒适。 轻松百搭:简单搭配外套、长裤、牛仔裤或沙滩休闲短裤,都是非常不错的选择,也可以选择就单穿,让您一直保持凉爽和放松。\n【 适用情景 】\n适用于日常生活、工作、出游、逛街等场合。\n【 洗涤说明 】\n可手洗可机洗,不要长时间浸泡,不可漂白,洗涤液温度不能超过45ºC。\n【 温馨提醒 】\n该图片展示效果仅供参考,最终效果以实物为准!由于生产批次、机器设备、纸样大小不同等客观因素原因,难以避免或将存在微小色差、位置及大小等误差,如遇以上问题均属于正常现象,将不予纳入售后处理范畴。 另外,根据各国本土政策要求,请勿上传科技单、跑水单等非正规来源面单,严禁使用侵权图案及未授权 IP、商标、赛事元素等内容。 违规订单将不予生产发货,已产生费用不予退还,相应风险与责任由下单方自行承担。感谢您的理解与配合。'
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
// 产品尺码表:4 行 5 列
|
||||||
|
export const mockSizeChart = {
|
||||||
|
unit: 'cm',
|
||||||
|
columns: ['尺码', '肩宽', '胸围', '衣长', '袖长'],
|
||||||
|
rows: [
|
||||||
|
{ size: 'S', shoulder: '51', chest: '56', length: '62', sleeve: '48' },
|
||||||
|
{ size: 'M', shoulder: '51', chest: '56', length: '62', sleeve: '48' },
|
||||||
|
{ size: 'L', shoulder: '51', chest: '56', length: '62', sleeve: '48' },
|
||||||
|
{ size: 'XL', shoulder: '51', chest: '56', length: '62', sleeve: '48' }
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
// 包装规格表:4 行 4 列,每个单元格双单位(cm + in)
|
||||||
|
export const mockPackaging = {
|
||||||
|
unit: 'cm',
|
||||||
|
columns: ['尺码', '尺寸', '体积', '重量'],
|
||||||
|
rows: [
|
||||||
|
{
|
||||||
|
size: 'S',
|
||||||
|
dimension: { cm: '31.0*23.0*1.0cm', in: '12.20*9.06*0.39in' },
|
||||||
|
volume: { cm: '713.00cm³', in: '43.51in³' },
|
||||||
|
weight: { cm: '200.00g', in: '0.36lb' }
|
||||||
|
},
|
||||||
|
{
|
||||||
|
size: 'M',
|
||||||
|
dimension: { cm: '31.0*23.0*1.0cm', in: '12.20*9.06*0.39in' },
|
||||||
|
volume: { cm: '713.00cm³', in: '43.51in³' },
|
||||||
|
weight: { cm: '200.00g', in: '0.36lb' }
|
||||||
|
},
|
||||||
|
{
|
||||||
|
size: 'L',
|
||||||
|
dimension: { cm: '31.0*23.0*1.0cm', in: '12.20*9.06*0.39in' },
|
||||||
|
volume: { cm: '713.00cm³', in: '43.51in³' },
|
||||||
|
weight: { cm: '200.00g', in: '0.36lb' }
|
||||||
|
},
|
||||||
|
{
|
||||||
|
size: 'XL',
|
||||||
|
dimension: { cm: '31.0*23.0*1.0cm', in: '12.20*9.06*0.39in' },
|
||||||
|
volume: { cm: '713.00cm³', in: '43.51in³' },
|
||||||
|
weight: { cm: '200.00g', in: '0.36lb' }
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -1,327 +1,14 @@
|
|||||||
/* 产品详情页样式 */
|
/* 产品详情页 - 页面容器样式 */
|
||||||
|
/* 各区块样式在 pages/product-detail/components/ 下对应组件的 <style scoped> 中 */
|
||||||
|
|
||||||
.detail-page {
|
.detail-page {
|
||||||
min-height: 100vh;
|
min-height: 100vh;
|
||||||
background: #f5f5f5;
|
|
||||||
padding-bottom: 140rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 图片区 */
|
|
||||||
.detail-images {
|
|
||||||
position: relative;
|
|
||||||
background: #ffffff;
|
background: #ffffff;
|
||||||
}
|
}
|
||||||
|
|
||||||
.detail-swiper {
|
/* 区块之间的灰色分隔条:390x6px #F5F5F5 */
|
||||||
|
.section-divider {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: 750rpx;
|
height: 12rpx; /* 6px */
|
||||||
}
|
|
||||||
|
|
||||||
.swiper-img {
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.swiper-emoji {
|
|
||||||
font-size: 160rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-badges {
|
|
||||||
position: absolute;
|
|
||||||
top: 24rpx;
|
|
||||||
left: 24rpx;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-badge {
|
|
||||||
font-size: 20rpx;
|
|
||||||
padding: 4rpx 12rpx;
|
|
||||||
border-radius: 6rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 产品信息 */
|
|
||||||
.detail-info-section {
|
|
||||||
background: #ffffff;
|
|
||||||
padding: 32rpx 24rpx;
|
|
||||||
margin-bottom: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-header {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-name {
|
|
||||||
font-size: 36rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #1a1a1a;
|
|
||||||
line-height: 1.4;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-code {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #999;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-price-row {
|
|
||||||
display: flex;
|
|
||||||
align-items: baseline;
|
|
||||||
gap: 8rpx;
|
|
||||||
margin-top: 20rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-price {
|
|
||||||
font-size: 48rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-price-unit {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-price-original {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #ccc;
|
|
||||||
text-decoration: line-through;
|
|
||||||
margin-left: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-meta {
|
|
||||||
display: flex;
|
|
||||||
justify-content: space-between;
|
|
||||||
margin-top: 32rpx;
|
|
||||||
padding-top: 24rpx;
|
|
||||||
border-top: 1rpx solid #f0f0f0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.meta-item {
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.meta-label {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #999;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.meta-value {
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #333;
|
|
||||||
font-weight: 500;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 通用section */
|
|
||||||
.detail-section {
|
|
||||||
background: #ffffff;
|
|
||||||
padding: 32rpx 24rpx;
|
|
||||||
margin-bottom: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.section-label {
|
|
||||||
font-size: 30rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 颜色选择 */
|
|
||||||
.color-options {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 20rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.color-option {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 8rpx;
|
|
||||||
padding: 12rpx 20rpx;
|
|
||||||
border-radius: 32rpx;
|
|
||||||
border: 2rpx solid #eee;
|
|
||||||
background: #fafafa;
|
|
||||||
}
|
|
||||||
|
|
||||||
.color-option.selected {
|
|
||||||
border-color: #ff6800;
|
|
||||||
background: #fff0e5;
|
|
||||||
}
|
|
||||||
|
|
||||||
.color-dot {
|
|
||||||
width: 32rpx;
|
|
||||||
height: 32rpx;
|
|
||||||
border-radius: 50%;
|
|
||||||
border: 2rpx solid #fff;
|
|
||||||
box-shadow: 0 0 0 1rpx rgba(0, 0, 0, 0.1);
|
|
||||||
}
|
|
||||||
|
|
||||||
.color-name {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #666;
|
|
||||||
}
|
|
||||||
|
|
||||||
.color-option.selected .color-name {
|
|
||||||
color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 尺码选择 */
|
|
||||||
.size-options {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.size-option {
|
|
||||||
min-width: 72rpx;
|
|
||||||
text-align: center;
|
|
||||||
padding: 16rpx 24rpx;
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #666;
|
|
||||||
background: #f5f5f5;
|
background: #f5f5f5;
|
||||||
border-radius: 8rpx;
|
|
||||||
border: 2rpx solid transparent;
|
|
||||||
}
|
|
||||||
|
|
||||||
.size-option.selected {
|
|
||||||
background: #fff0e5;
|
|
||||||
color: #ff6800;
|
|
||||||
border-color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 参数表 */
|
|
||||||
.params-table {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
}
|
|
||||||
|
|
||||||
.param-row {
|
|
||||||
display: flex;
|
|
||||||
padding: 16rpx 0;
|
|
||||||
border-bottom: 1rpx solid #f5f5f5;
|
|
||||||
}
|
|
||||||
|
|
||||||
.param-label {
|
|
||||||
width: 200rpx;
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #999;
|
|
||||||
flex-shrink: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.param-value {
|
|
||||||
flex: 1;
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #333;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 工艺说明 */
|
|
||||||
.craft-info {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 20rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.craft-card {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 16rpx;
|
|
||||||
padding: 20rpx;
|
|
||||||
background: #fafafa;
|
|
||||||
border-radius: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.craft-icon {
|
|
||||||
width: 64rpx;
|
|
||||||
height: 64rpx;
|
|
||||||
border-radius: 12rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
flex-shrink: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.craft-emoji {
|
|
||||||
font-size: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.craft-name {
|
|
||||||
font-size: 26rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
flex-shrink: 0;
|
|
||||||
width: 120rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.craft-desc {
|
|
||||||
flex: 1;
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #999;
|
|
||||||
line-height: 1.5;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 底部操作栏 */
|
|
||||||
.detail-bottom-bar {
|
|
||||||
position: fixed;
|
|
||||||
bottom: 0;
|
|
||||||
left: 0;
|
|
||||||
right: 0;
|
|
||||||
height: 120rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
padding: 0 24rpx;
|
|
||||||
gap: 16rpx;
|
|
||||||
box-shadow: 0 -2rpx 12rpx rgba(0, 0, 0, 0.06);
|
|
||||||
z-index: 100;
|
|
||||||
}
|
|
||||||
|
|
||||||
.bottom-btn-icon {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
align-items: center;
|
|
||||||
gap: 4rpx;
|
|
||||||
width: 80rpx;
|
|
||||||
flex-shrink: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.bottom-icon {
|
|
||||||
font-size: 36rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.bottom-icon-text {
|
|
||||||
font-size: 18rpx;
|
|
||||||
color: #999;
|
|
||||||
}
|
|
||||||
|
|
||||||
.bottom-btn-cart {
|
|
||||||
flex: 1;
|
|
||||||
height: 80rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
background: #fff0e5;
|
|
||||||
color: #ff6800;
|
|
||||||
font-size: 28rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
border-radius: 40rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.bottom-btn-design {
|
|
||||||
flex: 1;
|
|
||||||
height: 80rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
background: #ff6800;
|
|
||||||
color: #ffffff;
|
|
||||||
font-size: 28rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
border-radius: 40rpx;
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,303 +1,113 @@
|
|||||||
<template>
|
<template>
|
||||||
<!-- 产品详情页 -->
|
<!-- 产品详情页 - 严格按 Figma 1544:530 实现 -->
|
||||||
<view class="detail-page">
|
<view class="detail-page">
|
||||||
<!-- 产品图片区 -->
|
<!-- 产品图片轮播 + 指示点 -->
|
||||||
<view class="detail-images">
|
<DetailSwiper :images="productImages" />
|
||||||
<swiper class="detail-swiper" :indicator-dots="true" indicator-color="rgba(255,255,255,0.4)" indicator-active-color="#FF6800" :circular="true">
|
|
||||||
<swiper-item v-for="(item, index) in productImages" :key="index">
|
|
||||||
<view class="swiper-img" :style="'background: ' + item.bg + ';'">
|
|
||||||
<text class="swiper-emoji">{{ item.emoji }}</text>
|
|
||||||
</view>
|
|
||||||
</swiper-item>
|
|
||||||
</swiper>
|
|
||||||
<view class="detail-badges">
|
|
||||||
<view class="detail-badge" :style="'background: ' + item.bg + '; color: ' + item.color + ';'" v-for="(item, index) in productTags" :key="index">
|
|
||||||
{{ item.text }}
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 产品信息 -->
|
<!-- 产品信息:名称/SKU/国家/价格/4列快捷信息 -->
|
||||||
<view class="detail-info-section">
|
<ProductInfo :info="product" />
|
||||||
<view class="detail-header">
|
|
||||||
<text class="detail-name">{{ product.name }}</text>
|
<!-- 灰色分隔条 -->
|
||||||
<text class="detail-code">SKU: {{ product.code }}</text>
|
<view class="section-divider"></view>
|
||||||
</view>
|
|
||||||
<view class="detail-price-row">
|
|
||||||
<text class="detail-price">¥{{ product.price }}</text>
|
|
||||||
<text class="detail-price-unit">起</text>
|
|
||||||
<text class="detail-price-original" v-if="product.originalPrice">¥{{ product.originalPrice }}</text>
|
|
||||||
</view>
|
|
||||||
<view class="detail-meta">
|
|
||||||
<view class="meta-item">
|
|
||||||
<text class="meta-label">起订量</text>
|
|
||||||
<text class="meta-value">{{ product.moq }}件</text>
|
|
||||||
</view>
|
|
||||||
<view class="meta-item">
|
|
||||||
<text class="meta-label">生产周期</text>
|
|
||||||
<text class="meta-value">{{ product.leadTime }}</text>
|
|
||||||
</view>
|
|
||||||
<view class="meta-item">
|
|
||||||
<text class="meta-label">工艺</text>
|
|
||||||
<text class="meta-value">{{ product.craft }}</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 颜色选择 -->
|
<!-- 颜色选择 -->
|
||||||
<view class="detail-section">
|
<ColorSelector
|
||||||
<text class="section-label">颜色选择</text>
|
:list="colors"
|
||||||
<view class="color-options">
|
:selected-id="selectedColorId"
|
||||||
<view :class="'color-option ' + (selectedColor === index ? 'selected' : '')" @tap="selectColor" :data-index="index" v-for="(item, index) in colors" :key="index">
|
@select="selectColor"
|
||||||
<view class="color-dot" :style="'background: ' + item.value + ';'"></view>
|
/>
|
||||||
|
|
||||||
<text class="color-name">{{ item.name }}</text>
|
<!-- 灰色分隔条 -->
|
||||||
</view>
|
<view class="section-divider"></view>
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 尺码选择 -->
|
<!-- 尺码选择 -->
|
||||||
<view class="detail-section">
|
<SizeSelector
|
||||||
<text class="section-label">尺码选择</text>
|
:list="sizes"
|
||||||
<view class="size-options">
|
:selected="selectedSize"
|
||||||
<view :class="'size-option ' + (selectedSize === item ? 'selected' : '')" @tap="selectSize" :data-size="item" v-for="(item, index) in sizes" :key="index">
|
@select="selectSize"
|
||||||
{{ item }}
|
/>
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 产品详情 -->
|
<!-- 灰色分隔条 -->
|
||||||
<view class="detail-section">
|
<view class="section-divider"></view>
|
||||||
<text class="section-label">产品参数</text>
|
|
||||||
<view class="params-table">
|
|
||||||
<view class="param-row" v-for="(item, index) in productParams" :key="index">
|
|
||||||
<text class="param-label">{{ item.label }}</text>
|
|
||||||
|
|
||||||
<text class="param-value">{{ item.value }}</text>
|
<!-- 产品参数(含可展开的补充说明) -->
|
||||||
</view>
|
<ParamsTable :list="productParams" />
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 工艺说明 -->
|
<!-- 灰色分隔条 -->
|
||||||
<view class="detail-section">
|
<view class="section-divider"></view>
|
||||||
<text class="section-label">工艺说明</text>
|
|
||||||
<view class="craft-info">
|
|
||||||
<view class="craft-card" v-for="(item, index) in crafts" :key="index">
|
|
||||||
<view class="craft-icon" :style="'background: ' + item.bg + ';'">
|
|
||||||
<text class="craft-emoji">{{ item.emoji }}</text>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<text class="craft-name">{{ item.name }}</text>
|
<!-- 产品尺码表 -->
|
||||||
|
<SizeChart :data="sizeChart" />
|
||||||
|
|
||||||
<text class="craft-desc">{{ item.desc }}</text>
|
<!-- 灰色分隔条 -->
|
||||||
</view>
|
<view class="section-divider"></view>
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 底部操作栏 -->
|
<!-- 包装规格表 -->
|
||||||
<view class="detail-bottom-bar safe-bottom">
|
<PackagingSpec :data="packaging" />
|
||||||
<view class="bottom-btn-icon" @tap="toggleFav">
|
|
||||||
<text class="bottom-icon">{{ isFav ? '❤️' : '🤍' }}</text>
|
|
||||||
<text class="bottom-icon-text">收藏</text>
|
|
||||||
</view>
|
|
||||||
<view class="bottom-btn-icon" @tap="contactService">
|
|
||||||
<text class="bottom-icon">💬</text>
|
|
||||||
<text class="bottom-icon-text">客服</text>
|
|
||||||
</view>
|
|
||||||
<view class="bottom-btn-cart" @tap="addToCart">
|
|
||||||
<text>加入清单</text>
|
|
||||||
</view>
|
|
||||||
<view class="bottom-btn-design" @tap="startDesign">
|
|
||||||
<text>立即定制</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
</view>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
|
import DetailSwiper from './components/DetailSwiper.vue'
|
||||||
|
import ProductInfo from './components/ProductInfo.vue'
|
||||||
|
import ColorSelector from './components/ColorSelector.vue'
|
||||||
|
import SizeSelector from './components/SizeSelector.vue'
|
||||||
|
import ParamsTable from './components/ParamsTable.vue'
|
||||||
|
import SizeChart from './components/SizeChart.vue'
|
||||||
|
import PackagingSpec from './components/PackagingSpec.vue'
|
||||||
|
|
||||||
|
import {
|
||||||
|
mockProduct,
|
||||||
|
mockImages,
|
||||||
|
mockColors,
|
||||||
|
mockSizes,
|
||||||
|
mockParams,
|
||||||
|
mockSizeChart,
|
||||||
|
mockPackaging
|
||||||
|
} from './mock.js'
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
|
components: {
|
||||||
|
DetailSwiper,
|
||||||
|
ProductInfo,
|
||||||
|
ColorSelector,
|
||||||
|
SizeSelector,
|
||||||
|
ParamsTable,
|
||||||
|
SizeChart,
|
||||||
|
PackagingSpec
|
||||||
|
},
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
productId: null,
|
productId: null,
|
||||||
product: {
|
product: mockProduct,
|
||||||
name: '180G牛奶丝T恤 DG120',
|
productImages: mockImages,
|
||||||
code: 'DG120',
|
colors: mockColors,
|
||||||
price: '28.00',
|
// 默认选中"灰色"(id=3),与 Figma 设计稿一致
|
||||||
originalPrice: '35.00',
|
selectedColorId: 3,
|
||||||
moq: 1,
|
sizes: mockSizes,
|
||||||
leadTime: '48小时',
|
// 默认选中 L,与 Figma 设计稿一致
|
||||||
craft: '烫画/数码直喷'
|
selectedSize: 'L',
|
||||||
},
|
productParams: mockParams,
|
||||||
productImages: [
|
sizeChart: mockSizeChart,
|
||||||
{
|
packaging: mockPackaging
|
||||||
bg: '#F5F5F5',
|
|
||||||
emoji: '👕'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
bg: '#E8E8E8',
|
|
||||||
emoji: '👕'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
bg: '#F0F0F0',
|
|
||||||
emoji: '👕'
|
|
||||||
}
|
}
|
||||||
],
|
|
||||||
productTags: [
|
|
||||||
{
|
|
||||||
text: '可定制',
|
|
||||||
bg: '#FFF0E5',
|
|
||||||
color: '#FF6800'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
text: '现货',
|
|
||||||
bg: '#E5F5FF',
|
|
||||||
color: '#1890FF'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
text: '快返',
|
|
||||||
bg: '#F0FFE5',
|
|
||||||
color: '#52C41A'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
colors: [
|
|
||||||
{
|
|
||||||
name: '白色',
|
|
||||||
value: '#FFFFFF'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: '黑色',
|
|
||||||
value: '#1a1a1a'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: '灰色',
|
|
||||||
value: '#999999'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: '橙色',
|
|
||||||
value: '#FF6800'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: '藏青',
|
|
||||||
value: '#1B365D'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: '军绿',
|
|
||||||
value: '#4A5D23'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
selectedColor: 0,
|
|
||||||
sizes: ['XS', 'S', 'M', 'L', 'XL', '2XL', '3XL'],
|
|
||||||
selectedSize: 'M',
|
|
||||||
productParams: [
|
|
||||||
{
|
|
||||||
label: '克重',
|
|
||||||
value: '180g'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: '材质',
|
|
||||||
value: '牛奶丝(改性聚酯纤维)'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: '版型',
|
|
||||||
value: '常规版'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: '领型',
|
|
||||||
value: '圆领'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: '袖型',
|
|
||||||
value: '短袖'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: '适用工艺',
|
|
||||||
value: '烫画、数码直喷、刺绣'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: '可售区域',
|
|
||||||
value: '全球'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: '洗涤说明',
|
|
||||||
value: '冷水机洗,不可漂白'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
crafts: [
|
|
||||||
{
|
|
||||||
name: '烫画',
|
|
||||||
desc: '色彩鲜艳,适合复杂图案,成本低',
|
|
||||||
emoji: '🎨',
|
|
||||||
bg: '#FFF0E5'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: '数码直喷',
|
|
||||||
desc: '触感柔软,透气性好,适合大面积印花',
|
|
||||||
emoji: '🖨️',
|
|
||||||
bg: '#E5F5FF'
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: '刺绣',
|
|
||||||
desc: '质感高级,经久耐用,适合logo',
|
|
||||||
emoji: '🪡',
|
|
||||||
bg: '#F0FFE5'
|
|
||||||
}
|
|
||||||
],
|
|
||||||
isFav: false
|
|
||||||
};
|
|
||||||
},
|
},
|
||||||
onLoad(options) {
|
onLoad(options) {
|
||||||
if (options.id) {
|
if (options && options.id) {
|
||||||
this.setData({
|
this.productId = options.id
|
||||||
productId: options.id
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
selectColor(e) {
|
selectColor(id) {
|
||||||
this.setData({
|
this.selectedColorId = id
|
||||||
selectedColor: e.currentTarget.dataset.index
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
selectSize(size) {
|
||||||
selectSize(e) {
|
this.selectedSize = size
|
||||||
this.setData({
|
|
||||||
selectedSize: e.currentTarget.dataset.size
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
toggleFav() {
|
|
||||||
this.setData({
|
|
||||||
isFav: !this.isFav
|
|
||||||
});
|
|
||||||
uni.showToast({
|
|
||||||
title: this.isFav ? '已收藏' : '已取消',
|
|
||||||
icon: 'none'
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
contactService() {
|
|
||||||
uni.showToast({
|
|
||||||
title: '客服功能开发中',
|
|
||||||
icon: 'none'
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
addToCart() {
|
|
||||||
uni.showToast({
|
|
||||||
title: '已加入清单',
|
|
||||||
icon: 'success'
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
startDesign() {
|
|
||||||
uni.showToast({
|
|
||||||
title: '定制功能开发中',
|
|
||||||
icon: 'none'
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
@import './product-detail.css';
|
@import './product-detail.css';
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
@@ -0,0 +1,62 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 已选筛选标签 -->
|
||||||
|
<view class="active-filters" v-if="list.length > 0">
|
||||||
|
<view class="active-filter-tag" v-for="(item, index) in list" :key="index">
|
||||||
|
<text>{{ item.label }}</text>
|
||||||
|
<text class="filter-remove" @tap="onRemove(item.key)">✕</text>
|
||||||
|
</view>
|
||||||
|
<view class="clear-all" @tap="onClearAll">清除全部</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'ActiveFilters',
|
||||||
|
props: {
|
||||||
|
list: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
onRemove(key) {
|
||||||
|
this.$emit('remove', key)
|
||||||
|
},
|
||||||
|
onClearAll() {
|
||||||
|
this.$emit('clear-all')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.active-filters {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 16rpx;
|
||||||
|
padding: 20rpx 32rpx;
|
||||||
|
background: #ffffff;
|
||||||
|
border-bottom: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.active-filter-tag {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 10rpx;
|
||||||
|
padding: 8rpx 20rpx;
|
||||||
|
background: #fff0e5;
|
||||||
|
border-radius: 24rpx;
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
.filter-remove {
|
||||||
|
font-size: 20rpx;
|
||||||
|
color: #ff6800;
|
||||||
|
opacity: 0.7;
|
||||||
|
}
|
||||||
|
.clear-all {
|
||||||
|
margin-left: auto;
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,91 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 左侧分类侧边栏 -->
|
||||||
|
<scroll-view scroll-y class="sidebar">
|
||||||
|
<view
|
||||||
|
class="sidebar-item"
|
||||||
|
:class="{ active: activeId === item.id }"
|
||||||
|
v-for="(item, index) in list"
|
||||||
|
:key="index"
|
||||||
|
@tap="selectItem(item.id)"
|
||||||
|
>
|
||||||
|
<view class="sidebar-indicator" v-if="activeId === item.id"></view>
|
||||||
|
<text>{{ item.name }}</text>
|
||||||
|
</view>
|
||||||
|
<!-- 促销Banner -->
|
||||||
|
<view class="sidebar-promo">
|
||||||
|
<text class="promo-title">0元拿样</text>
|
||||||
|
<text class="promo-desc">全国包邮</text>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'CategorySidebar',
|
||||||
|
props: {
|
||||||
|
list: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
activeId: {
|
||||||
|
type: [String, Number],
|
||||||
|
default: 'all'
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
selectItem(id) {
|
||||||
|
this.$emit('select', id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.sidebar {
|
||||||
|
width: 160rpx;
|
||||||
|
height: 100%;
|
||||||
|
background: #f8f8f8;
|
||||||
|
}
|
||||||
|
.sidebar-item {
|
||||||
|
position: relative;
|
||||||
|
padding: 28rpx 16rpx;
|
||||||
|
font-size: 26rpx;
|
||||||
|
color: #666666;
|
||||||
|
text-align: center;
|
||||||
|
line-height: 1.4;
|
||||||
|
}
|
||||||
|
.sidebar-item.active {
|
||||||
|
background: #ffffff;
|
||||||
|
color: #1a1a1a;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
.sidebar-indicator {
|
||||||
|
position: absolute;
|
||||||
|
left: 0;
|
||||||
|
top: 50%;
|
||||||
|
transform: translateY(-50%);
|
||||||
|
width: 6rpx;
|
||||||
|
height: 32rpx;
|
||||||
|
background: #ff6800;
|
||||||
|
border-radius: 0 4rpx 4rpx 0;
|
||||||
|
}
|
||||||
|
.sidebar-promo {
|
||||||
|
margin: 24rpx 16rpx;
|
||||||
|
padding: 24rpx 16rpx;
|
||||||
|
background: linear-gradient(135deg, #ff6800 0%, #ff8c3a 100%);
|
||||||
|
border-radius: 16rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
.promo-title {
|
||||||
|
font-size: 26rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
.promo-desc {
|
||||||
|
margin-top: 8rpx;
|
||||||
|
font-size: 20rpx;
|
||||||
|
color: rgba(255, 255, 255, 0.9);
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,74 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 国家选择条 - 横向滚动 -->
|
||||||
|
<scroll-view scroll-x class="country-bar" show-scrollbar="false">
|
||||||
|
<view class="country-inner">
|
||||||
|
<view
|
||||||
|
class="country-item"
|
||||||
|
:class="{ active: selectedId === item.id }"
|
||||||
|
v-for="(item, index) in list"
|
||||||
|
:key="index"
|
||||||
|
@tap="selectItem(item)"
|
||||||
|
>
|
||||||
|
<text class="country-flag">{{ item.flag }}</text>
|
||||||
|
<text class="country-name">{{ item.name }}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'CountryBar',
|
||||||
|
props: {
|
||||||
|
list: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
selectedId: {
|
||||||
|
type: [String, Number],
|
||||||
|
default: ''
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
selectItem(item) {
|
||||||
|
this.$emit('select', item.id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.country-bar {
|
||||||
|
width: 100%;
|
||||||
|
white-space: nowrap;
|
||||||
|
background: #ffffff;
|
||||||
|
padding: 16rpx 0;
|
||||||
|
border-bottom: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.country-inner {
|
||||||
|
display: inline-flex;
|
||||||
|
gap: 16rpx;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
}
|
||||||
|
.country-item {
|
||||||
|
flex-shrink: 0;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 10rpx;
|
||||||
|
padding: 12rpx 24rpx;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 30rpx;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #666666;
|
||||||
|
}
|
||||||
|
.country-item.active {
|
||||||
|
background: #ff6800;
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
.country-flag {
|
||||||
|
font-size: 28rpx;
|
||||||
|
}
|
||||||
|
.country-name {
|
||||||
|
font-size: 24rpx;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,210 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 筛选弹窗 -->
|
||||||
|
<view>
|
||||||
|
<view
|
||||||
|
class="filter-overlay"
|
||||||
|
:class="{ show: visible }"
|
||||||
|
@tap="onClose"
|
||||||
|
></view>
|
||||||
|
<view class="filter-drawer" :class="{ show: visible }">
|
||||||
|
<view class="filter-drawer-header">
|
||||||
|
<text class="filter-drawer-title">筛选条件</text>
|
||||||
|
<text class="filter-drawer-close" @tap="onClose">✕</text>
|
||||||
|
</view>
|
||||||
|
<scroll-view scroll-y class="filter-drawer-body">
|
||||||
|
<!-- 动态标签筛选组 -->
|
||||||
|
<view class="filter-group" v-for="(group, gIdx) in groups" :key="gIdx">
|
||||||
|
<text class="filter-group-title">{{ group.title }}</text>
|
||||||
|
<view class="filter-options">
|
||||||
|
<view
|
||||||
|
class="filter-option"
|
||||||
|
:class="{ selected: isSelected(group, tag.id) }"
|
||||||
|
v-for="(tag, tIdx) in group.tags"
|
||||||
|
:key="tIdx"
|
||||||
|
@tap="onToggle(gIdx, tag.id)"
|
||||||
|
>
|
||||||
|
{{ tag.name }}
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
<!-- 价格区间 -->
|
||||||
|
<view class="filter-group">
|
||||||
|
<text class="filter-group-title">价格区间</text>
|
||||||
|
<view class="filter-price-range">
|
||||||
|
<input class="price-input" placeholder="最低价" type="number" />
|
||||||
|
<text class="price-divider">-</text>
|
||||||
|
<input class="price-input" placeholder="最高价" type="number" />
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
<view class="filter-drawer-footer">
|
||||||
|
<view class="filter-reset" @tap="onReset">重置</view>
|
||||||
|
<view class="filter-confirm" @tap="onConfirm">确定</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'FilterDrawer',
|
||||||
|
props: {
|
||||||
|
visible: {
|
||||||
|
type: Boolean,
|
||||||
|
default: false
|
||||||
|
},
|
||||||
|
groups: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
isSelected(group, tagId) {
|
||||||
|
return (group.selected || []).indexOf(tagId) > -1
|
||||||
|
},
|
||||||
|
onToggle(gIdx, tagId) {
|
||||||
|
this.$emit('toggle-tag', { groupIndex: gIdx, tagId })
|
||||||
|
},
|
||||||
|
onReset() {
|
||||||
|
this.$emit('reset')
|
||||||
|
},
|
||||||
|
onConfirm() {
|
||||||
|
this.$emit('confirm')
|
||||||
|
},
|
||||||
|
onClose() {
|
||||||
|
this.$emit('close')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.filter-overlay {
|
||||||
|
position: fixed;
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
background: rgba(0, 0, 0, 0.5);
|
||||||
|
z-index: 998;
|
||||||
|
opacity: 0;
|
||||||
|
visibility: hidden;
|
||||||
|
transition: all 0.3s;
|
||||||
|
}
|
||||||
|
.filter-overlay.show {
|
||||||
|
opacity: 1;
|
||||||
|
visibility: visible;
|
||||||
|
}
|
||||||
|
.filter-drawer {
|
||||||
|
position: fixed;
|
||||||
|
top: 0;
|
||||||
|
right: -600rpx;
|
||||||
|
width: 600rpx;
|
||||||
|
height: 100%;
|
||||||
|
background: #ffffff;
|
||||||
|
z-index: 999;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
transition: right 0.3s;
|
||||||
|
}
|
||||||
|
.filter-drawer.show {
|
||||||
|
right: 0;
|
||||||
|
}
|
||||||
|
.filter-drawer-header {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
padding: 32rpx;
|
||||||
|
border-bottom: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.filter-drawer-title {
|
||||||
|
font-size: 32rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #1a1a1a;
|
||||||
|
}
|
||||||
|
.filter-drawer-close {
|
||||||
|
font-size: 32rpx;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
.filter-drawer-body {
|
||||||
|
flex: 1;
|
||||||
|
padding: 0 32rpx;
|
||||||
|
}
|
||||||
|
.filter-group {
|
||||||
|
padding: 32rpx 0;
|
||||||
|
border-bottom: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.filter-group-title {
|
||||||
|
display: block;
|
||||||
|
font-size: 28rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #1a1a1a;
|
||||||
|
margin-bottom: 20rpx;
|
||||||
|
}
|
||||||
|
.filter-options {
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 16rpx;
|
||||||
|
}
|
||||||
|
.filter-option {
|
||||||
|
padding: 14rpx 28rpx;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #666666;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 30rpx;
|
||||||
|
border: 2rpx solid transparent;
|
||||||
|
}
|
||||||
|
.filter-option.selected {
|
||||||
|
background: #fff0e5;
|
||||||
|
color: #ff6800;
|
||||||
|
border-color: #ff6800;
|
||||||
|
}
|
||||||
|
.filter-price-range {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 20rpx;
|
||||||
|
}
|
||||||
|
.price-input {
|
||||||
|
flex: 1;
|
||||||
|
height: 72rpx;
|
||||||
|
padding: 0 20rpx;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
font-size: 26rpx;
|
||||||
|
color: #333333;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
.price-divider {
|
||||||
|
font-size: 28rpx;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
.filter-drawer-footer {
|
||||||
|
display: flex;
|
||||||
|
gap: 24rpx;
|
||||||
|
padding: 24rpx 32rpx;
|
||||||
|
border-top: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.filter-reset {
|
||||||
|
flex: 1;
|
||||||
|
height: 80rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 40rpx;
|
||||||
|
font-size: 28rpx;
|
||||||
|
color: #666666;
|
||||||
|
}
|
||||||
|
.filter-confirm {
|
||||||
|
flex: 1;
|
||||||
|
height: 80rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
background: #ff6800;
|
||||||
|
border-radius: 40rpx;
|
||||||
|
font-size: 28rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,307 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 产品网格列表 + 子分类 + 分页 -->
|
||||||
|
<scroll-view scroll-y class="product-list-area" @scrolltolower="onLoadMore">
|
||||||
|
<!-- 子分类 -->
|
||||||
|
<view class="sub-categories" v-if="subCategories.length > 0">
|
||||||
|
<view
|
||||||
|
class="sub-cat-item"
|
||||||
|
:class="{ active: activeSubId === item.id }"
|
||||||
|
v-for="(item, index) in subCategories"
|
||||||
|
:key="index"
|
||||||
|
@tap="selectSub(item.id)"
|
||||||
|
>
|
||||||
|
{{ item.name }}
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 产品网格 -->
|
||||||
|
<view class="product-grid">
|
||||||
|
<view
|
||||||
|
class="product-card"
|
||||||
|
v-for="(item, index) in list"
|
||||||
|
:key="index"
|
||||||
|
@tap="onTapProduct(item)"
|
||||||
|
>
|
||||||
|
<view class="product-img">
|
||||||
|
<image
|
||||||
|
class="product-image"
|
||||||
|
:src="item.image"
|
||||||
|
mode="aspectFill"
|
||||||
|
v-if="item.image"
|
||||||
|
></image>
|
||||||
|
<view class="product-badges">
|
||||||
|
<view
|
||||||
|
class="product-badge"
|
||||||
|
:style="{ background: tag.bg, color: tag.color }"
|
||||||
|
v-for="(tag, tIdx) in item.tags"
|
||||||
|
:key="tIdx"
|
||||||
|
>
|
||||||
|
{{ tag.text }}
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
<view class="product-info">
|
||||||
|
<text class="product-name">{{ item.name }}</text>
|
||||||
|
<view class="product-bottom">
|
||||||
|
<text class="product-price">
|
||||||
|
¥{{ item.price }}
|
||||||
|
<text class="product-price-unit">起</text>
|
||||||
|
</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 分页 -->
|
||||||
|
<view class="pagination" v-if="total > 0">
|
||||||
|
<text class="page-info">显示 {{ start }}-{{ end }} 共 {{ total }} 个产品</text>
|
||||||
|
<view class="page-controls">
|
||||||
|
<view
|
||||||
|
class="page-btn"
|
||||||
|
:class="{ disabled: current === 1 }"
|
||||||
|
@tap="onPrev"
|
||||||
|
>
|
||||||
|
上一页
|
||||||
|
</view>
|
||||||
|
<view
|
||||||
|
class="page-num"
|
||||||
|
:class="{ active: current === item }"
|
||||||
|
v-for="(item, index) in pageNumbers"
|
||||||
|
:key="index"
|
||||||
|
@tap="onGoPage(item)"
|
||||||
|
>
|
||||||
|
{{ item }}
|
||||||
|
</view>
|
||||||
|
<view
|
||||||
|
class="page-btn"
|
||||||
|
:class="{ disabled: current === totalPages }"
|
||||||
|
@tap="onNext"
|
||||||
|
>
|
||||||
|
下一页
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
<view class="page-size">
|
||||||
|
<text>{{ pageSize }}/页</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<!-- 加载更多提示 -->
|
||||||
|
<view class="loading-more" v-if="loading">
|
||||||
|
<text>加载中...</text>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'ProductGrid',
|
||||||
|
props: {
|
||||||
|
list: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
subCategories: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
activeSubId: {
|
||||||
|
type: [String, Number],
|
||||||
|
default: ''
|
||||||
|
},
|
||||||
|
total: {
|
||||||
|
type: Number,
|
||||||
|
default: 0
|
||||||
|
},
|
||||||
|
current: {
|
||||||
|
type: Number,
|
||||||
|
default: 1
|
||||||
|
},
|
||||||
|
pageSize: {
|
||||||
|
type: Number,
|
||||||
|
default: 10
|
||||||
|
},
|
||||||
|
totalPages: {
|
||||||
|
type: Number,
|
||||||
|
default: 1
|
||||||
|
},
|
||||||
|
pageNumbers: {
|
||||||
|
type: Array,
|
||||||
|
default: () => []
|
||||||
|
},
|
||||||
|
start: {
|
||||||
|
type: Number,
|
||||||
|
default: 1
|
||||||
|
},
|
||||||
|
end: {
|
||||||
|
type: Number,
|
||||||
|
default: 10
|
||||||
|
},
|
||||||
|
loading: {
|
||||||
|
type: Boolean,
|
||||||
|
default: false
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
selectSub(id) {
|
||||||
|
this.$emit('sub-select', id)
|
||||||
|
},
|
||||||
|
onTapProduct(item) {
|
||||||
|
this.$emit('product-click', item)
|
||||||
|
},
|
||||||
|
onPrev() {
|
||||||
|
if (this.current > 1) {
|
||||||
|
this.$emit('page-change', this.current - 1)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onNext() {
|
||||||
|
if (this.current < this.totalPages) {
|
||||||
|
this.$emit('page-change', this.current + 1)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onGoPage(page) {
|
||||||
|
this.$emit('page-change', page)
|
||||||
|
},
|
||||||
|
onLoadMore() {
|
||||||
|
this.$emit('load-more')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.product-list-area {
|
||||||
|
flex: 1;
|
||||||
|
height: 100%;
|
||||||
|
background: #ffffff;
|
||||||
|
}
|
||||||
|
.sub-categories {
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 16rpx;
|
||||||
|
padding: 20rpx 24rpx;
|
||||||
|
border-bottom: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.sub-cat-item {
|
||||||
|
padding: 10rpx 24rpx;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #666666;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 24rpx;
|
||||||
|
}
|
||||||
|
.sub-cat-item.active {
|
||||||
|
background: #fff0e5;
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
.product-grid {
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 16rpx;
|
||||||
|
padding: 20rpx 24rpx;
|
||||||
|
}
|
||||||
|
.product-card {
|
||||||
|
width: calc(50% - 8rpx);
|
||||||
|
background: #ffffff;
|
||||||
|
border-radius: 16rpx;
|
||||||
|
overflow: hidden;
|
||||||
|
border: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.product-img {
|
||||||
|
position: relative;
|
||||||
|
width: 100%;
|
||||||
|
height: 260rpx;
|
||||||
|
background: #f5f5f5;
|
||||||
|
}
|
||||||
|
.product-image {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
.product-badges {
|
||||||
|
position: absolute;
|
||||||
|
top: 12rpx;
|
||||||
|
left: 12rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 8rpx;
|
||||||
|
}
|
||||||
|
.product-badge {
|
||||||
|
padding: 4rpx 12rpx;
|
||||||
|
border-radius: 8rpx;
|
||||||
|
font-size: 18rpx;
|
||||||
|
}
|
||||||
|
.product-info {
|
||||||
|
padding: 16rpx;
|
||||||
|
}
|
||||||
|
.product-name {
|
||||||
|
display: block;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #1a1a1a;
|
||||||
|
line-height: 1.4;
|
||||||
|
overflow: hidden;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
.product-bottom {
|
||||||
|
margin-top: 10rpx;
|
||||||
|
}
|
||||||
|
.product-price {
|
||||||
|
font-size: 28rpx;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
.product-price-unit {
|
||||||
|
font-size: 20rpx;
|
||||||
|
font-weight: 400;
|
||||||
|
color: #ff6800;
|
||||||
|
}
|
||||||
|
.pagination {
|
||||||
|
padding: 32rpx 24rpx;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
gap: 20rpx;
|
||||||
|
}
|
||||||
|
.page-info {
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
.page-controls {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 12rpx;
|
||||||
|
}
|
||||||
|
.page-btn {
|
||||||
|
padding: 10rpx 20rpx;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #666666;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 8rpx;
|
||||||
|
}
|
||||||
|
.page-btn.disabled {
|
||||||
|
color: #cccccc;
|
||||||
|
}
|
||||||
|
.page-num {
|
||||||
|
width: 56rpx;
|
||||||
|
height: 56rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #666666;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 8rpx;
|
||||||
|
}
|
||||||
|
.page-num.active {
|
||||||
|
background: #ff6800;
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
.page-size {
|
||||||
|
font-size: 22rpx;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
.loading-more {
|
||||||
|
padding: 32rpx;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,85 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 搜索栏 -->
|
||||||
|
<view class="search-bar">
|
||||||
|
<view class="search-input-wrap">
|
||||||
|
<text class="search-icon">🔍</text>
|
||||||
|
<input
|
||||||
|
class="search-input"
|
||||||
|
placeholder="搜索商品"
|
||||||
|
placeholder-class="search-placeholder"
|
||||||
|
:value="keyword"
|
||||||
|
@input="onInput"
|
||||||
|
/>
|
||||||
|
</view>
|
||||||
|
<view class="filter-btn" @tap="onFilter">
|
||||||
|
<text class="filter-icon">⚙</text>
|
||||||
|
<text class="filter-text">筛选</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
name: 'SearchBar',
|
||||||
|
props: {
|
||||||
|
keyword: {
|
||||||
|
type: String,
|
||||||
|
default: ''
|
||||||
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
onInput(e) {
|
||||||
|
this.$emit('input', e.detail.value)
|
||||||
|
},
|
||||||
|
onFilter() {
|
||||||
|
this.$emit('filter')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.search-bar {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 20rpx;
|
||||||
|
padding: 20rpx 32rpx;
|
||||||
|
background: #ffffff;
|
||||||
|
border-bottom: 2rpx solid #f5f5f5;
|
||||||
|
}
|
||||||
|
.search-input-wrap {
|
||||||
|
flex: 1;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
height: 72rpx;
|
||||||
|
padding: 0 24rpx;
|
||||||
|
background: #f5f5f5;
|
||||||
|
border-radius: 36rpx;
|
||||||
|
}
|
||||||
|
.search-icon {
|
||||||
|
font-size: 28rpx;
|
||||||
|
margin-right: 12rpx;
|
||||||
|
}
|
||||||
|
.search-input {
|
||||||
|
flex: 1;
|
||||||
|
font-size: 26rpx;
|
||||||
|
color: #333333;
|
||||||
|
}
|
||||||
|
.search-placeholder {
|
||||||
|
color: #999999;
|
||||||
|
}
|
||||||
|
.filter-btn {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8rpx;
|
||||||
|
padding: 12rpx 20rpx;
|
||||||
|
font-size: 26rpx;
|
||||||
|
color: #666666;
|
||||||
|
}
|
||||||
|
.filter-icon {
|
||||||
|
font-size: 28rpx;
|
||||||
|
}
|
||||||
|
.filter-text {
|
||||||
|
font-size: 26rpx;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,146 @@
|
|||||||
|
// 货盘页 mock 数据(用于离线预览,实际数据从 API 获取)
|
||||||
|
|
||||||
|
export const mockCountries = [
|
||||||
|
{ id: '45', name: '美国', flag: '🇺🇸' },
|
||||||
|
{ id: '76', name: '日本', flag: '🇯🇵' },
|
||||||
|
{ id: '484', name: '墨西哥', flag: '🇲🇽' },
|
||||||
|
{ id: '826', name: '英国', flag: '🇬🇧' },
|
||||||
|
{ id: '276', name: '德国', flag: '🇩🇪' },
|
||||||
|
{ id: '250', name: '法国', flag: '🇫🇷' },
|
||||||
|
{ id: '380', name: '意大利', flag: '🇮🇹' },
|
||||||
|
{ id: '124', name: '加拿大', flag: '🇨🇦' },
|
||||||
|
{ id: '36', name: '澳大利亚', flag: '🇦🇺' },
|
||||||
|
{ id: '410', name: '韩国', flag: '🇰🇷' },
|
||||||
|
{ id: '152', name: '智利', flag: '🇨🇱' },
|
||||||
|
{ id: '604', name: '秘鲁', flag: '🇵🇪' }
|
||||||
|
]
|
||||||
|
|
||||||
|
export const mockCategories = [
|
||||||
|
{ id: 'all', name: '全部商品', children: [], productCount: 0 },
|
||||||
|
{
|
||||||
|
id: '1',
|
||||||
|
name: '男士服装',
|
||||||
|
productCount: 159,
|
||||||
|
children: [
|
||||||
|
{ id: '101', categoryName: 'T恤' },
|
||||||
|
{ id: '102', categoryName: '卫衣' },
|
||||||
|
{ id: '103', categoryName: 'POLO衫' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: '2',
|
||||||
|
name: '女士服装',
|
||||||
|
productCount: 36,
|
||||||
|
children: [
|
||||||
|
{ id: '201', categoryName: '连衣裙' },
|
||||||
|
{ id: '202', categoryName: 'T恤' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: '3',
|
||||||
|
name: '童装',
|
||||||
|
productCount: 40,
|
||||||
|
children: [
|
||||||
|
{ id: '301', categoryName: '儿童T恤' },
|
||||||
|
{ id: '302', categoryName: '儿童卫衣' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: '4',
|
||||||
|
name: '家居配饰',
|
||||||
|
productCount: 3,
|
||||||
|
children: [
|
||||||
|
{ id: '401', categoryName: '帆布包' },
|
||||||
|
{ id: '402', categoryName: '马克杯' }
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
export const mockFilterGroups = [
|
||||||
|
{
|
||||||
|
id: '1',
|
||||||
|
title: '物流渠道',
|
||||||
|
tags: [
|
||||||
|
{ id: 't1', name: '包邮', color: '#ff6800', fontColor: '#ffffff', productCount: 84 },
|
||||||
|
{ id: 't2', name: '不包邮', color: '#999999', fontColor: '#ffffff', productCount: 154 }
|
||||||
|
],
|
||||||
|
selected: []
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: '2',
|
||||||
|
title: '印刷位置',
|
||||||
|
tags: [
|
||||||
|
{ id: 't3', name: '单面印', color: '#00b894', fontColor: '#ffffff', productCount: 12 },
|
||||||
|
{ id: 't4', name: '双面印', color: '#6c5ce7', fontColor: '#ffffff', productCount: 14 }
|
||||||
|
],
|
||||||
|
selected: []
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: '3',
|
||||||
|
title: '印刷工艺',
|
||||||
|
tags: [
|
||||||
|
{ id: 't5', name: '烫画', color: '#e17055', fontColor: '#ffffff', productCount: 8 },
|
||||||
|
{ id: 't6', name: '直喷', color: '#00cec9', fontColor: '#ffffff', productCount: 3 }
|
||||||
|
],
|
||||||
|
selected: []
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
export const mockProducts = [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
name: '180G牛奶丝T恤 DG120',
|
||||||
|
price: '28.00',
|
||||||
|
image: '/static/images/products/1.png',
|
||||||
|
tags: [
|
||||||
|
{ text: '包邮', bg: '#ff6800', color: '#ffffff' },
|
||||||
|
{ text: '烫画', bg: '#e17055', color: '#ffffff' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
name: '纯棉连帽卫衣 HD200',
|
||||||
|
price: '59.00',
|
||||||
|
image: '/static/images/products/2.png',
|
||||||
|
tags: [
|
||||||
|
{ text: '不包邮', bg: '#999999', color: '#ffffff' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
name: '帆布托特包 BG150',
|
||||||
|
price: '15.00',
|
||||||
|
image: '/static/images/products/3.png',
|
||||||
|
tags: [
|
||||||
|
{ text: '单面印', bg: '#00b894', color: '#ffffff' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 4,
|
||||||
|
name: '儿童纯棉T恤 KD100',
|
||||||
|
price: '22.00',
|
||||||
|
image: '/static/images/products/4.png',
|
||||||
|
tags: [
|
||||||
|
{ text: '包邮', bg: '#ff6800', color: '#ffffff' },
|
||||||
|
{ text: '直喷', bg: '#00cec9', color: '#ffffff' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 5,
|
||||||
|
name: '重磅圆领T恤 DG150',
|
||||||
|
price: '35.00',
|
||||||
|
image: '/static/images/products/5.png',
|
||||||
|
tags: [
|
||||||
|
{ text: '双面印', bg: '#6c5ce7', color: '#ffffff' }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 6,
|
||||||
|
name: '拉链卫衣 HD220',
|
||||||
|
price: '79.00',
|
||||||
|
image: '/static/images/products/6.png',
|
||||||
|
tags: [
|
||||||
|
{ text: '包邮', bg: '#ff6800', color: '#ffffff' }
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
+4
-492
@@ -1,502 +1,14 @@
|
|||||||
/* 产品列表页样式 */
|
/* 货盘页 - 页面容器样式 */
|
||||||
|
/* 各区块样式已移入 pages/products/components/ 下对应组件 */
|
||||||
|
|
||||||
.products-page {
|
.products-page {
|
||||||
min-height: 100vh;
|
|
||||||
background: #f5f5f5;
|
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
|
height: 100vh;
|
||||||
|
background: #f8f8f8;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 搜索栏 */
|
|
||||||
.search-bar {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 16rpx;
|
|
||||||
padding: 16rpx 24rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.search-input-wrap {
|
|
||||||
flex: 1;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
background: #f5f5f5;
|
|
||||||
border-radius: 32rpx;
|
|
||||||
padding: 0 24rpx;
|
|
||||||
height: 64rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.search-icon {
|
|
||||||
font-size: 28rpx;
|
|
||||||
margin-right: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.search-input {
|
|
||||||
flex: 1;
|
|
||||||
font-size: 26rpx;
|
|
||||||
color: #333;
|
|
||||||
}
|
|
||||||
|
|
||||||
.search-placeholder {
|
|
||||||
color: #ccc;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-btn {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 4rpx;
|
|
||||||
padding: 0 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-icon {
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #666;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-text {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #666;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 国家选择条 */
|
|
||||||
.country-bar {
|
|
||||||
white-space: nowrap;
|
|
||||||
background: #ffffff;
|
|
||||||
padding: 16rpx 24rpx;
|
|
||||||
border-bottom: 1rpx solid #eee;
|
|
||||||
}
|
|
||||||
|
|
||||||
.country-item {
|
|
||||||
display: inline-flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 6rpx;
|
|
||||||
padding: 8rpx 20rpx;
|
|
||||||
margin-right: 12rpx;
|
|
||||||
border-radius: 24rpx;
|
|
||||||
background: #f5f5f5;
|
|
||||||
}
|
|
||||||
|
|
||||||
.country-item.active {
|
|
||||||
background: #fff0e5;
|
|
||||||
}
|
|
||||||
|
|
||||||
.country-flag {
|
|
||||||
font-size: 28rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.country-name {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #666;
|
|
||||||
}
|
|
||||||
|
|
||||||
.country-item.active .country-name {
|
|
||||||
color: #ff6800;
|
|
||||||
font-weight: 500;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 已选筛选标签 */
|
|
||||||
.active-filters {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 12rpx;
|
|
||||||
padding: 12rpx 24rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
overflow-x: auto;
|
|
||||||
white-space: nowrap;
|
|
||||||
}
|
|
||||||
|
|
||||||
.active-filter-tag {
|
|
||||||
display: inline-flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 8rpx;
|
|
||||||
background: #f2f2f2;
|
|
||||||
border-radius: 8rpx;
|
|
||||||
padding: 6rpx 16rpx;
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #666;
|
|
||||||
flex-shrink: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-remove {
|
|
||||||
font-size: 20rpx;
|
|
||||||
color: #ccc;
|
|
||||||
}
|
|
||||||
|
|
||||||
.clear-all {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #ff6800;
|
|
||||||
flex-shrink: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 主体内容 */
|
|
||||||
.content-body {
|
.content-body {
|
||||||
flex: 1;
|
flex: 1;
|
||||||
display: flex;
|
display: flex;
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 左侧分类侧边栏 */
|
|
||||||
.sidebar {
|
|
||||||
width: 180rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
border-right: 1rpx solid #eee;
|
|
||||||
height: 100%;
|
|
||||||
flex-shrink: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.sidebar-item {
|
|
||||||
position: relative;
|
|
||||||
padding: 28rpx 20rpx;
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #666;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.sidebar-item.active {
|
|
||||||
background: #f5f5f5;
|
|
||||||
color: #ff6800;
|
|
||||||
font-weight: 600;
|
|
||||||
}
|
|
||||||
|
|
||||||
.sidebar-indicator {
|
|
||||||
position: absolute;
|
|
||||||
left: 0;
|
|
||||||
top: 50%;
|
|
||||||
transform: translateY(-50%);
|
|
||||||
width: 6rpx;
|
|
||||||
height: 32rpx;
|
|
||||||
background: #ff6800;
|
|
||||||
border-radius: 0 4rpx 4rpx 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.sidebar-promo {
|
|
||||||
margin: 24rpx 16rpx;
|
|
||||||
padding: 20rpx 12rpx;
|
|
||||||
background: linear-gradient(135deg, #ff6800 0%, #ff8c40 100%);
|
|
||||||
border-radius: 12rpx;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.promo-title {
|
|
||||||
font-size: 24rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #fff;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.promo-desc {
|
|
||||||
font-size: 20rpx;
|
|
||||||
color: rgba(255, 255, 255, 0.9);
|
|
||||||
display: block;
|
|
||||||
margin-top: 4rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 右侧产品列表区 */
|
|
||||||
.product-list-area {
|
|
||||||
flex: 1;
|
|
||||||
height: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 子分类 */
|
|
||||||
.sub-categories {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 12rpx;
|
|
||||||
padding: 16rpx 20rpx;
|
|
||||||
background: #ffffff;
|
|
||||||
}
|
|
||||||
|
|
||||||
.sub-cat-item {
|
|
||||||
font-size: 22rpx;
|
|
||||||
padding: 8rpx 20rpx;
|
|
||||||
border-radius: 24rpx;
|
|
||||||
background: #f5f5f5;
|
|
||||||
color: #666;
|
|
||||||
}
|
|
||||||
|
|
||||||
.sub-cat-item.active {
|
|
||||||
background: #ff6800;
|
|
||||||
color: #fff;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 产品网格 */
|
|
||||||
.product-grid {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 16rpx;
|
|
||||||
padding: 16rpx 20rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-card {
|
|
||||||
width: calc(50% - 8rpx);
|
|
||||||
background: #ffffff;
|
|
||||||
border-radius: 12rpx;
|
|
||||||
overflow: hidden;
|
|
||||||
box-shadow: 0 2rpx 8rpx rgba(0, 0, 0, 0.04);
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-img {
|
|
||||||
width: 100%;
|
|
||||||
height: 300rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
position: relative;
|
|
||||||
background: #f5f5f5;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-image {
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-badges {
|
|
||||||
position: absolute;
|
|
||||||
top: 12rpx;
|
|
||||||
left: 12rpx;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: 4rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-badge {
|
|
||||||
font-size: 18rpx;
|
|
||||||
padding: 2rpx 8rpx;
|
|
||||||
border-radius: 4rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-info {
|
|
||||||
padding: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-name {
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #333;
|
|
||||||
display: block;
|
|
||||||
overflow: hidden;
|
|
||||||
text-overflow: ellipsis;
|
|
||||||
white-space: nowrap;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-bottom {
|
|
||||||
margin-top: 8rpx;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: space-between;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-price {
|
|
||||||
font-size: 30rpx;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.product-price-unit {
|
|
||||||
font-size: 20rpx;
|
|
||||||
font-weight: 400;
|
|
||||||
margin-left: 2rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 分页 */
|
|
||||||
.pagination {
|
|
||||||
padding: 24rpx 20rpx;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.page-info {
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #999;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.page-controls {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
gap: 8rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.page-btn {
|
|
||||||
padding: 8rpx 20rpx;
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #666;
|
|
||||||
background: #fff;
|
|
||||||
border-radius: 8rpx;
|
|
||||||
border: 1rpx solid #eee;
|
|
||||||
}
|
|
||||||
|
|
||||||
.page-btn.disabled {
|
|
||||||
color: #ccc;
|
|
||||||
}
|
|
||||||
|
|
||||||
.page-num {
|
|
||||||
min-width: 48rpx;
|
|
||||||
height: 48rpx;
|
|
||||||
line-height: 48rpx;
|
|
||||||
text-align: center;
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #666;
|
|
||||||
background: #fff;
|
|
||||||
border-radius: 8rpx;
|
|
||||||
border: 1rpx solid #eee;
|
|
||||||
}
|
|
||||||
|
|
||||||
.page-num.active {
|
|
||||||
background: #ff6800;
|
|
||||||
color: #fff;
|
|
||||||
border-color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.page-size {
|
|
||||||
margin-top: 12rpx;
|
|
||||||
font-size: 22rpx;
|
|
||||||
color: #999;
|
|
||||||
}
|
|
||||||
|
|
||||||
.loading-more {
|
|
||||||
padding: 24rpx;
|
|
||||||
text-align: center;
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #999;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 筛选弹窗 */
|
|
||||||
.filter-overlay {
|
|
||||||
position: fixed;
|
|
||||||
top: 0;
|
|
||||||
left: 0;
|
|
||||||
right: 0;
|
|
||||||
bottom: 0;
|
|
||||||
background: rgba(0, 0, 0, 0.5);
|
|
||||||
z-index: 1000;
|
|
||||||
opacity: 0;
|
|
||||||
visibility: hidden;
|
|
||||||
transition: all 0.3s;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-overlay.show {
|
|
||||||
opacity: 1;
|
|
||||||
visibility: visible;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-drawer {
|
|
||||||
position: fixed;
|
|
||||||
top: 0;
|
|
||||||
right: 0;
|
|
||||||
width: 80%;
|
|
||||||
height: 100%;
|
|
||||||
background: #ffffff;
|
|
||||||
z-index: 1001;
|
|
||||||
transform: translateX(100%);
|
|
||||||
transition: transform 0.3s;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-drawer.show {
|
|
||||||
transform: translateX(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-drawer-header {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: space-between;
|
|
||||||
padding: 32rpx 24rpx;
|
|
||||||
border-bottom: 1rpx solid #eee;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-drawer-title {
|
|
||||||
font-size: 32rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-drawer-close {
|
|
||||||
font-size: 32rpx;
|
|
||||||
color: #999;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-drawer-body {
|
|
||||||
flex: 1;
|
|
||||||
padding: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-group {
|
|
||||||
margin-bottom: 32rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-group-title {
|
|
||||||
font-size: 28rpx;
|
|
||||||
font-weight: 600;
|
|
||||||
color: #333;
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-options {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
gap: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-option {
|
|
||||||
padding: 12rpx 24rpx;
|
|
||||||
font-size: 24rpx;
|
|
||||||
color: #666;
|
|
||||||
background: #f5f5f5;
|
|
||||||
border-radius: 8rpx;
|
|
||||||
border: 2rpx solid transparent;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-option.selected {
|
|
||||||
background: #fff0e5;
|
|
||||||
color: #ff6800;
|
|
||||||
border-color: #ff6800;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-price-range {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 16rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.price-input {
|
|
||||||
flex: 1;
|
|
||||||
height: 64rpx;
|
|
||||||
background: #f5f5f5;
|
|
||||||
border-radius: 8rpx;
|
|
||||||
padding: 0 20rpx;
|
|
||||||
font-size: 24rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.price-divider {
|
|
||||||
color: #ccc;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-drawer-footer {
|
|
||||||
display: flex;
|
|
||||||
gap: 16rpx;
|
|
||||||
padding: 24rpx;
|
|
||||||
border-top: 1rpx solid #eee;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-reset {
|
|
||||||
flex: 1;
|
|
||||||
text-align: center;
|
|
||||||
padding: 24rpx;
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #666;
|
|
||||||
background: #f5f5f5;
|
|
||||||
border-radius: 12rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.filter-confirm {
|
|
||||||
flex: 1;
|
|
||||||
text-align: center;
|
|
||||||
padding: 24rpx;
|
|
||||||
font-size: 28rpx;
|
|
||||||
color: #fff;
|
|
||||||
background: #ff6800;
|
|
||||||
border-radius: 12rpx;
|
|
||||||
}
|
|
||||||
|
|||||||
+224
-413
@@ -2,195 +2,103 @@
|
|||||||
<!-- 产品列表页 - 印美达 Inkreach -->
|
<!-- 产品列表页 - 印美达 Inkreach -->
|
||||||
<view class="products-page">
|
<view class="products-page">
|
||||||
<!-- 搜索栏 -->
|
<!-- 搜索栏 -->
|
||||||
<view class="search-bar">
|
<SearchBar
|
||||||
<view class="search-input-wrap">
|
:keyword="searchKeyword"
|
||||||
<text class="search-icon">🔍</text>
|
@input="onSearchInput"
|
||||||
<input class="search-input" placeholder="搜索商品" placeholder-class="search-placeholder" @input="onSearchInput" :value="searchKeyword" />
|
@filter="toggleFilter"
|
||||||
</view>
|
/>
|
||||||
<view class="filter-btn" @tap="toggleFilter">
|
|
||||||
<text class="filter-icon">⚙</text>
|
|
||||||
<text class="filter-text">筛选</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 国家选择条 -->
|
<!-- 国家选择条 -->
|
||||||
<scroll-view class="country-bar" :scroll-x="true" :enhanced="true" :show-scrollbar="false">
|
<CountryBar
|
||||||
<view :class="'country-item ' + (selectedCountry === item.id ? 'active' : '')" @tap="selectCountry" :data-id="item.id" v-for="(item, index) in countries" :key="index">
|
:list="countries"
|
||||||
<text class="country-flag">{{ item.flag }}</text>
|
:selected-id="selectedCountry"
|
||||||
|
@select="selectCountry"
|
||||||
<text class="country-name">{{ item.name }}</text>
|
/>
|
||||||
</view>
|
|
||||||
</scroll-view>
|
|
||||||
|
|
||||||
<!-- 已选筛选标签 -->
|
<!-- 已选筛选标签 -->
|
||||||
<view class="active-filters" v-if="activeFilters.length > 0">
|
<ActiveFilters
|
||||||
<view class="active-filter-tag" v-for="(item, index) in activeFilters" :key="index">
|
:list="activeFilters"
|
||||||
<text>{{ item.label }}</text>
|
@remove="removeFilter"
|
||||||
|
@clear-all="clearAllFilters"
|
||||||
<text class="filter-remove" @tap="removeFilter" :data-key="item.key">✕</text>
|
/>
|
||||||
</view>
|
|
||||||
<view class="clear-all" @tap="clearAllFilters">清除全部</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 主体内容:侧边栏 + 产品列表 -->
|
<!-- 主体内容:侧边栏 + 产品列表 -->
|
||||||
<view class="content-body">
|
<view class="content-body">
|
||||||
<!-- 左侧分类侧边栏 -->
|
<!-- 左侧分类侧边栏 -->
|
||||||
<scroll-view class="sidebar" :scroll-y="true">
|
<CategorySidebar
|
||||||
<view
|
:list="categories"
|
||||||
:class="'sidebar-item ' + (activeCategory === item.id ? 'active' : '')"
|
:active-id="activeCategory"
|
||||||
@tap="selectCategory"
|
@select="selectCategory"
|
||||||
:data-id="item.id"
|
/>
|
||||||
v-for="(item, index) in categories"
|
|
||||||
:key="index"
|
|
||||||
>
|
|
||||||
<view class="sidebar-indicator" v-if="activeCategory === item.id"></view>
|
|
||||||
|
|
||||||
<text>{{ item.name }}</text>
|
|
||||||
</view>
|
|
||||||
<!-- 促销Banner -->
|
|
||||||
<view class="sidebar-promo">
|
|
||||||
<text class="promo-title">0元拿样</text>
|
|
||||||
<text class="promo-desc">全国包邮</text>
|
|
||||||
</view>
|
|
||||||
</scroll-view>
|
|
||||||
|
|
||||||
<!-- 右侧产品列表 -->
|
<!-- 右侧产品列表 -->
|
||||||
<scroll-view class="product-list-area" :scroll-y="true" @scrolltolower="loadMore">
|
<ProductGrid
|
||||||
<!-- 子分类 -->
|
:list="products"
|
||||||
<view class="sub-categories" v-if="subCategories.length > 0">
|
:sub-categories="subCategories"
|
||||||
<view
|
:active-sub-id="activeSubCategory"
|
||||||
:class="'sub-cat-item ' + (activeSubCategory === item.id ? 'active' : '')"
|
:total="pagination.total"
|
||||||
@tap="selectSubCategory"
|
:current="pagination.current"
|
||||||
:data-id="item.id"
|
:page-size="pagination.pageSize"
|
||||||
v-for="(item, index) in subCategories"
|
:total-pages="pagination.totalPages"
|
||||||
:key="index"
|
:page-numbers="pageNumbers"
|
||||||
>
|
:start="pagination.start"
|
||||||
{{ item.name }}
|
:end="pagination.end"
|
||||||
</view>
|
:loading="loadingMore"
|
||||||
</view>
|
@sub-select="selectSubCategory"
|
||||||
|
@product-click="goDetail"
|
||||||
<!-- 产品网格 -->
|
@page-change="loadGoods"
|
||||||
<view class="product-grid">
|
@load-more="loadMore"
|
||||||
<view class="product-card" @tap="goDetail" :data-id="item.id" v-for="(item, index) in products" :key="index">
|
/>
|
||||||
<view class="product-img">
|
|
||||||
<image class="product-image" :src="item.image" mode="aspectFill" v-if="item.image"></image>
|
|
||||||
<view class="product-badges">
|
|
||||||
<view class="product-badge" :style="'background: ' + tag.bg + '; color: ' + tag.color + ';'" v-for="(tag, index1) in item.tags" :key="index1">
|
|
||||||
{{ tag.text }}
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<view class="product-info">
|
|
||||||
<text class="product-name">{{ item.name }}</text>
|
|
||||||
<view class="product-bottom">
|
|
||||||
<text class="product-price">
|
|
||||||
¥{{ item.price }}
|
|
||||||
<text class="product-price-unit">起</text>
|
|
||||||
</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 分页 -->
|
|
||||||
<view class="pagination">
|
|
||||||
<text class="page-info">显示 {{ pagination.start }}-{{ pagination.end }} 共 {{ pagination.total }} 个产品</text>
|
|
||||||
<view class="page-controls">
|
|
||||||
<view :class="'page-btn ' + (pagination.current === 1 ? 'disabled' : '')" @tap="changePage" data-action="prev">上一页</view>
|
|
||||||
<view
|
|
||||||
:class="'page-num ' + (pagination.current === item ? 'active' : '')"
|
|
||||||
@tap="goToPage"
|
|
||||||
:data-page="item"
|
|
||||||
v-for="(item, index) in pageNumbers"
|
|
||||||
:key="index"
|
|
||||||
>
|
|
||||||
{{ item }}
|
|
||||||
</view>
|
|
||||||
<view :class="'page-btn ' + (pagination.current === pagination.totalPages ? 'disabled' : '')" @tap="changePage" data-action="next">下一页</view>
|
|
||||||
</view>
|
|
||||||
<view class="page-size">
|
|
||||||
<text>{{ pagination.pageSize }}/页</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<!-- 加载更多提示 -->
|
|
||||||
<view class="loading-more" v-if="loadingMore">
|
|
||||||
<text>加载中...</text>
|
|
||||||
</view>
|
|
||||||
</scroll-view>
|
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<!-- 筛选弹窗 -->
|
<!-- 筛选弹窗 -->
|
||||||
<view :class="'filter-overlay ' + (showFilter ? 'show' : '')" @tap="closeFilter"></view>
|
<FilterDrawer
|
||||||
<view :class="'filter-drawer ' + (showFilter ? 'show' : '')">
|
:visible="showFilter"
|
||||||
<view class="filter-drawer-header">
|
:groups="filterGroups"
|
||||||
<text class="filter-drawer-title">筛选条件</text>
|
@close="closeFilter"
|
||||||
<text class="filter-drawer-close" @tap="closeFilter">✕</text>
|
@toggle-tag="toggleFilterTag"
|
||||||
</view>
|
@reset="resetFilters"
|
||||||
<scroll-view class="filter-drawer-body" :scroll-y="true">
|
@confirm="confirmFilters"
|
||||||
<!-- 动态标签筛选组(从 API 获取) -->
|
/>
|
||||||
<view class="filter-group" v-for="(group, gIdx) in filterGroups" :key="gIdx">
|
|
||||||
<text class="filter-group-title">{{ group.title }}</text>
|
|
||||||
<view class="filter-options">
|
|
||||||
<view
|
|
||||||
:class="'filter-option ' + (group.selected.indexOf(tag.id) > -1 ? 'selected' : '')"
|
|
||||||
@tap="toggleFilterTag"
|
|
||||||
:data-group-idx="gIdx"
|
|
||||||
:data-tag-id="tag.id"
|
|
||||||
v-for="(tag, tIdx) in group.tags"
|
|
||||||
:key="tIdx"
|
|
||||||
>
|
|
||||||
{{ tag.name }}
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
<!-- 价格区间 -->
|
|
||||||
<view class="filter-group">
|
|
||||||
<text class="filter-group-title">价格区间</text>
|
|
||||||
<view class="filter-price-range">
|
|
||||||
<input class="price-input" placeholder="最低价" type="number" />
|
|
||||||
<text class="price-divider">-</text>
|
|
||||||
<input class="price-input" placeholder="最高价" type="number" />
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</scroll-view>
|
|
||||||
<view class="filter-drawer-footer">
|
|
||||||
<view class="filter-reset" @tap="resetFilters">重置</view>
|
|
||||||
<view class="filter-confirm" @tap="confirmFilters">确定</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
</view>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
import { getCountries, getCategories, getTagGroups, getGoods } from '@/api/public.js';
|
import SearchBar from './components/SearchBar.vue'
|
||||||
|
import CountryBar from './components/CountryBar.vue'
|
||||||
|
import ActiveFilters from './components/ActiveFilters.vue'
|
||||||
|
import CategorySidebar from './components/CategorySidebar.vue'
|
||||||
|
import ProductGrid from './components/ProductGrid.vue'
|
||||||
|
import FilterDrawer from './components/FilterDrawer.vue'
|
||||||
|
|
||||||
|
import { getCountries, getCategories, getTagGroups, getGoods } from '@/api/public.js'
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
|
components: {
|
||||||
|
SearchBar,
|
||||||
|
CountryBar,
|
||||||
|
ActiveFilters,
|
||||||
|
CategorySidebar,
|
||||||
|
ProductGrid,
|
||||||
|
FilterDrawer
|
||||||
|
},
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
searchKeyword: '',
|
searchKeyword: '',
|
||||||
selectedCountry: '',
|
selectedCountry: '',
|
||||||
|
|
||||||
countries: [],
|
countries: [],
|
||||||
|
|
||||||
activeCategory: 'all',
|
activeCategory: 'all',
|
||||||
|
|
||||||
categories: [
|
categories: [
|
||||||
{
|
{
|
||||||
id: 'all',
|
id: 'all',
|
||||||
name: '全部商品'
|
name: '全部商品'
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
|
|
||||||
subCategories: [],
|
subCategories: [],
|
||||||
activeSubCategory: '',
|
activeSubCategory: '',
|
||||||
|
|
||||||
activeFilters: [],
|
activeFilters: [],
|
||||||
|
|
||||||
showFilter: false,
|
showFilter: false,
|
||||||
filterGroups: [],
|
filterGroups: [],
|
||||||
|
|
||||||
pagination: {
|
pagination: {
|
||||||
start: 1,
|
start: 1,
|
||||||
end: 10,
|
end: 10,
|
||||||
@@ -199,72 +107,65 @@ export default {
|
|||||||
pageSize: 10,
|
pageSize: 10,
|
||||||
totalPages: 0
|
totalPages: 0
|
||||||
},
|
},
|
||||||
|
|
||||||
pageNumbers: [],
|
pageNumbers: [],
|
||||||
loadingMore: false,
|
loadingMore: false,
|
||||||
|
|
||||||
products: []
|
products: []
|
||||||
};
|
}
|
||||||
},
|
},
|
||||||
async onLoad() {
|
async onLoad() {
|
||||||
await this.initData();
|
await this.initData()
|
||||||
this.loadSubCategories('all');
|
this.loadSubCategories('all')
|
||||||
await this.loadGoods(1);
|
await this.loadGoods(1)
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
async initData() {
|
async initData() {
|
||||||
try {
|
try {
|
||||||
// 1. 国家列表(始终全量)
|
// 1. 国家列表
|
||||||
const countriesRes = await getCountries();
|
const countriesRes = await getCountries()
|
||||||
const countriesData = (countriesRes.data && countriesRes.data.data) || [];
|
const countriesData = (countriesRes.data && countriesRes.data.data) || []
|
||||||
const countries = countriesData.map((c) => ({
|
const countries = countriesData.map((c) => ({
|
||||||
id: c.id,
|
id: c.id,
|
||||||
name: c.countryName,
|
name: c.countryName,
|
||||||
flag: this.codeToEmoji(c.countryIcon)
|
flag: this.codeToEmoji(c.countryIcon)
|
||||||
}));
|
}))
|
||||||
|
this.countries = countries
|
||||||
|
|
||||||
this.setData({
|
// 2. 默认不选中任何国家
|
||||||
countries
|
await this.loadCategoryData('')
|
||||||
});
|
|
||||||
|
|
||||||
// 2. 默认不选中任何国家,显示全部国家的数据
|
console.log('=== [Products API Test] ===')
|
||||||
await this.loadCategoryData('');
|
console.log('[1] countries:', countries.length, '条')
|
||||||
|
console.log('=== [Test End] ===')
|
||||||
// 简单检测结构 — 打印到 console 验证
|
|
||||||
console.log('=== [Products API Test] ===');
|
|
||||||
console.log('[1] countries:', countries.length, '条');
|
|
||||||
console.log('=== [Test End] ===');
|
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
console.error('[Products initData Error]', err);
|
console.error('[Products initData Error]', err)
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 加载分类树和标签组(按国家过滤)
|
* 加载分类树和标签组(按国家过滤)
|
||||||
* @param {string} countryId 国家 ID,传空字符串表示全部国家
|
|
||||||
*/
|
*/
|
||||||
async loadCategoryData(countryId) {
|
async loadCategoryData(countryId) {
|
||||||
try {
|
try {
|
||||||
const params = countryId ? { countryId: countryId } : {};
|
const params = countryId ? { countryId: countryId } : {}
|
||||||
const [categoriesRes, tagGroupsRes] = await Promise.all([
|
const [categoriesRes, tagGroupsRes] = await Promise.all([
|
||||||
getCategories(params),
|
getCategories(params),
|
||||||
getTagGroups(params)
|
getTagGroups(params)
|
||||||
]);
|
])
|
||||||
|
|
||||||
// 分类树 → 映射到侧边栏
|
// 分类树
|
||||||
const categoriesData = (categoriesRes.data && categoriesRes.data.data) || [];
|
const categoriesData = (categoriesRes.data && categoriesRes.data.data) || []
|
||||||
const categories = [{ id: 'all', name: '全部商品', children: [], productCount: 0 }];
|
const categories = [{ id: 'all', name: '全部商品', children: [], productCount: 0 }]
|
||||||
categoriesData.forEach((cat) => {
|
categoriesData.forEach((cat) => {
|
||||||
categories.push({
|
categories.push({
|
||||||
id: cat.id,
|
id: cat.id,
|
||||||
name: cat.categoryName,
|
name: cat.categoryName,
|
||||||
children: cat.children || [],
|
children: cat.children || [],
|
||||||
productCount: cat.productCount || 0
|
productCount: cat.productCount || 0
|
||||||
});
|
})
|
||||||
});
|
})
|
||||||
|
|
||||||
// 标签组 → 映射到筛选弹窗
|
// 标签组
|
||||||
const tagGroupsData = (tagGroupsRes.data && tagGroupsRes.data.data) || [];
|
const tagGroupsData = (tagGroupsRes.data && tagGroupsRes.data.data) || []
|
||||||
const filterGroups = tagGroupsData.map((g) => ({
|
const filterGroups = tagGroupsData.map((g) => ({
|
||||||
id: g.id,
|
id: g.id,
|
||||||
title: g.groupName,
|
title: g.groupName,
|
||||||
@@ -276,377 +177,287 @@ export default {
|
|||||||
productCount: t.productCount || 0
|
productCount: t.productCount || 0
|
||||||
})),
|
})),
|
||||||
selected: []
|
selected: []
|
||||||
}));
|
}))
|
||||||
|
|
||||||
this.setData({
|
this.categories = categories
|
||||||
categories,
|
this.filterGroups = filterGroups
|
||||||
filterGroups,
|
this.activeCategory = 'all'
|
||||||
activeCategory: 'all',
|
this.subCategories = []
|
||||||
subCategories: [],
|
this.activeSubCategory = ''
|
||||||
activeSubCategory: ''
|
|
||||||
});
|
|
||||||
|
|
||||||
console.log('[loadCategoryData] countryId=' + (countryId || 'all') +
|
console.log(
|
||||||
|
'[loadCategoryData] countryId=' + (countryId || 'all') +
|
||||||
', categories=' + categories.length +
|
', categories=' + categories.length +
|
||||||
', filterGroups=' + filterGroups.length);
|
', filterGroups=' + filterGroups.length
|
||||||
|
)
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
console.error('[loadCategoryData Error]', err);
|
console.error('[loadCategoryData Error]', err)
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 加载商品列表(分页 + 筛选)
|
* 加载商品列表(分页 + 筛选)
|
||||||
* @param {number} [page] 页码,默认 1
|
|
||||||
*/
|
*/
|
||||||
async loadGoods(page) {
|
async loadGoods(page) {
|
||||||
try {
|
try {
|
||||||
const currentPage = page || this.pagination.current || 1;
|
const currentPage = page || this.pagination.current || 1
|
||||||
const pageSize = this.pagination.pageSize || 10;
|
const pageSize = this.pagination.pageSize || 10
|
||||||
|
|
||||||
var params = {
|
var params = {
|
||||||
page: currentPage,
|
page: currentPage,
|
||||||
pageSize: pageSize
|
pageSize: pageSize
|
||||||
};
|
}
|
||||||
|
|
||||||
// 国家筛选
|
|
||||||
if (this.selectedCountry) {
|
if (this.selectedCountry) {
|
||||||
params.countryId = this.selectedCountry;
|
params.countryId = this.selectedCountry
|
||||||
}
|
}
|
||||||
|
|
||||||
// 分类筛选(排除 "all")
|
|
||||||
if (this.activeCategory && this.activeCategory !== 'all') {
|
if (this.activeCategory && this.activeCategory !== 'all') {
|
||||||
params.categoryId = this.activeCategory;
|
params.categoryId = this.activeCategory
|
||||||
}
|
}
|
||||||
|
|
||||||
// 关键词搜索
|
|
||||||
if (this.searchKeyword && this.searchKeyword.trim()) {
|
if (this.searchKeyword && this.searchKeyword.trim()) {
|
||||||
params.keyword = this.searchKeyword.trim();
|
params.keyword = this.searchKeyword.trim()
|
||||||
}
|
}
|
||||||
|
|
||||||
console.log('[loadGoods] params:', JSON.stringify(params));
|
console.log('[loadGoods] params:', JSON.stringify(params))
|
||||||
|
|
||||||
const res = await getGoods(params);
|
const res = await getGoods(params)
|
||||||
const data = (res.data && res.data.data) || { items: [], total: 0, page: 1, pageSize: 10 };
|
const data = (res.data && res.data.data) || { items: [], total: 0, page: 1, pageSize: 10 }
|
||||||
const items = data.items || [];
|
const items = data.items || []
|
||||||
|
|
||||||
// 映射:API 字段 → 模板字段
|
|
||||||
const products = items.map((item) => ({
|
const products = items.map((item) => ({
|
||||||
id: item.goodId,
|
id: item.goodId,
|
||||||
name: item.goodName,
|
name: item.goodName,
|
||||||
price: item.price,
|
price: item.price,
|
||||||
image: item.image,
|
image: item.image,
|
||||||
bgColor: '#F5F5F5',
|
|
||||||
emoji: '👕',
|
|
||||||
tags: (item.tags || []).map(function (t) {
|
tags: (item.tags || []).map(function (t) {
|
||||||
return {
|
return {
|
||||||
text: t.tagName,
|
text: t.tagName,
|
||||||
bg: t.tagColor,
|
bg: t.tagColor,
|
||||||
color: t.tagFontColor
|
color: t.tagFontColor
|
||||||
};
|
}
|
||||||
})
|
})
|
||||||
}));
|
}))
|
||||||
|
|
||||||
const total = data.total || 0;
|
const total = data.total || 0
|
||||||
const totalPages = Math.ceil(total / pageSize) || 1;
|
const totalPages = Math.ceil(total / pageSize) || 1
|
||||||
var pageNumbers = [];
|
var pageNumbers = []
|
||||||
for (var i = Math.max(1, currentPage - 2); i <= Math.min(totalPages, currentPage + 2); i++) {
|
for (var i = Math.max(1, currentPage - 2); i <= Math.min(totalPages, currentPage + 2); i++) {
|
||||||
pageNumbers.push(i);
|
pageNumbers.push(i)
|
||||||
}
|
}
|
||||||
|
|
||||||
this.setData({
|
this.products = products
|
||||||
products: products,
|
this.pagination = {
|
||||||
pagination: {
|
|
||||||
start: total === 0 ? 0 : (currentPage - 1) * pageSize + 1,
|
start: total === 0 ? 0 : (currentPage - 1) * pageSize + 1,
|
||||||
end: Math.min(currentPage * pageSize, total),
|
end: Math.min(currentPage * pageSize, total),
|
||||||
total: total,
|
total: total,
|
||||||
current: currentPage,
|
current: currentPage,
|
||||||
pageSize: pageSize,
|
pageSize: pageSize,
|
||||||
totalPages: totalPages
|
totalPages: totalPages
|
||||||
},
|
}
|
||||||
pageNumbers: pageNumbers,
|
this.pageNumbers = pageNumbers
|
||||||
loadingMore: false
|
this.loadingMore = false
|
||||||
});
|
|
||||||
|
|
||||||
console.log('[loadGoods] total=' + total +
|
console.log(
|
||||||
|
'[loadGoods] total=' + total +
|
||||||
', page=' + currentPage +
|
', page=' + currentPage +
|
||||||
', items=' + products.length);
|
', items=' + products.length
|
||||||
|
)
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
console.error('[loadGoods Error]', err);
|
console.error('[loadGoods Error]', err)
|
||||||
this.setData({
|
this.products = []
|
||||||
products: [],
|
this.loadingMore = false
|
||||||
loadingMore: false
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
codeToEmoji(iconPath) {
|
codeToEmoji(iconPath) {
|
||||||
if (!iconPath) return '🌐';
|
if (!iconPath) return '🌐'
|
||||||
var match = iconPath.match(/\/([^/]+)\.\w+$/);
|
var match = iconPath.match(/\/([^/]+)\.\w+$/)
|
||||||
if (!match) return '🌐';
|
if (!match) return '🌐'
|
||||||
var code = match[1].toUpperCase();
|
var code = match[1].toUpperCase()
|
||||||
if (code.length !== 2) return '🌐';
|
if (code.length !== 2) return '🌐'
|
||||||
var A = 0x1f1e6;
|
var A = 0x1f1e6
|
||||||
return String.fromCodePoint(A + code.charCodeAt(0) - 65) + String.fromCodePoint(A + code.charCodeAt(1) - 65);
|
return String.fromCodePoint(A + code.charCodeAt(0) - 65) + String.fromCodePoint(A + code.charCodeAt(1) - 65)
|
||||||
},
|
},
|
||||||
|
|
||||||
loadSubCategories(catId) {
|
loadSubCategories(catId) {
|
||||||
var subCats = [];
|
var subCats = []
|
||||||
if (catId !== 'all') {
|
if (catId !== 'all') {
|
||||||
var cat = this.categories.find(function (c) { return c.id === catId; });
|
var cat = this.categories.find(function (c) { return c.id === catId })
|
||||||
if (cat && cat.children && cat.children.length > 0) {
|
if (cat && cat.children && cat.children.length > 0) {
|
||||||
subCats = cat.children.map(function (child) {
|
subCats = cat.children.map(function (child) {
|
||||||
return { id: child.id, name: child.categoryName };
|
return { id: child.id, name: child.categoryName }
|
||||||
});
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
this.setData({
|
this.subCategories = subCats
|
||||||
subCategories: subCats,
|
this.activeSubCategory = subCats.length > 0 ? subCats[0].id : ''
|
||||||
activeSubCategory: subCats.length > 0 ? subCats[0].id : ''
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
onSearchInput(e) {
|
onSearchInput(val) {
|
||||||
this.setData({
|
this.searchKeyword = val
|
||||||
searchKeyword: e.detail.value
|
|
||||||
});
|
|
||||||
// 防抖搜索
|
// 防抖搜索
|
||||||
if (this._searchTimer) clearTimeout(this._searchTimer);
|
if (this._searchTimer) clearTimeout(this._searchTimer)
|
||||||
var self = this;
|
var self = this
|
||||||
this._searchTimer = setTimeout(function () {
|
this._searchTimer = setTimeout(function () {
|
||||||
self.loadGoods(1);
|
self.loadGoods(1)
|
||||||
}, 300);
|
}, 300)
|
||||||
},
|
},
|
||||||
|
|
||||||
async selectCountry(e) {
|
async selectCountry(id) {
|
||||||
const id = e.currentTarget.dataset.id;
|
// 如果点击的是已选中的国家 → 取消选中
|
||||||
|
|
||||||
// 如果点击的是已选中的国家 → 取消选中,重置为全部国家数据
|
|
||||||
if (this.selectedCountry === id) {
|
if (this.selectedCountry === id) {
|
||||||
this.setData({
|
this.selectedCountry = ''
|
||||||
selectedCountry: '',
|
this.activeFilters = this.activeFilters.filter((f) => f.key !== 'country')
|
||||||
activeFilters: this.activeFilters.filter((f) => f.key !== 'country')
|
await this.loadCategoryData('')
|
||||||
});
|
await this.loadGoods(1)
|
||||||
await this.loadCategoryData('');
|
return
|
||||||
await this.loadGoods(1);
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 选中新国家 → 重新请求分类和标签组
|
// 选中新国家
|
||||||
const country = this.countries.find((c) => c.id === id);
|
const country = this.countries.find((c) => c.id === id)
|
||||||
const filters = this.activeFilters.filter((f) => f.key !== 'country');
|
const filters = this.activeFilters.filter((f) => f.key !== 'country')
|
||||||
if (country) {
|
if (country) {
|
||||||
filters.push({
|
filters.push({
|
||||||
key: 'country',
|
key: 'country',
|
||||||
label: country.name
|
label: country.name
|
||||||
});
|
})
|
||||||
}
|
}
|
||||||
this.setData({
|
this.selectedCountry = id
|
||||||
selectedCountry: id,
|
this.activeFilters = filters
|
||||||
activeFilters: filters
|
await this.loadCategoryData(id)
|
||||||
});
|
await this.loadGoods(1)
|
||||||
await this.loadCategoryData(id);
|
|
||||||
await this.loadGoods(1);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
async selectCategory(e) {
|
async selectCategory(id) {
|
||||||
const id = e.currentTarget.dataset.id;
|
this.activeCategory = id
|
||||||
this.setData({
|
this.loadSubCategories(id)
|
||||||
activeCategory: id
|
await this.loadGoods(1)
|
||||||
});
|
|
||||||
this.loadSubCategories(id);
|
|
||||||
await this.loadGoods(1);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
selectSubCategory(e) {
|
selectSubCategory(id) {
|
||||||
this.setData({
|
this.activeSubCategory = id
|
||||||
activeSubCategory: e.currentTarget.dataset.id
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
toggleFilter() {
|
toggleFilter() {
|
||||||
this.setData({
|
this.showFilter = !this.showFilter
|
||||||
showFilter: !this.showFilter
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
closeFilter() {
|
closeFilter() {
|
||||||
this.setData({
|
this.showFilter = false
|
||||||
showFilter: false
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
toggleFilterTag(e) {
|
toggleFilterTag(e) {
|
||||||
const gIdx = e.currentTarget.dataset.groupIdx;
|
const gIdx = e.groupIndex
|
||||||
const tagId = e.currentTarget.dataset.tagId;
|
const tagId = e.tagId
|
||||||
var groups = [...this.filterGroups];
|
var groups = [...this.filterGroups]
|
||||||
var group = groups[gIdx];
|
var group = groups[gIdx]
|
||||||
if (!group) return;
|
if (!group) return
|
||||||
var selected = [...group.selected];
|
var selected = [...group.selected]
|
||||||
var idx = selected.indexOf(tagId);
|
var idx = selected.indexOf(tagId)
|
||||||
if (idx > -1) {
|
if (idx > -1) {
|
||||||
selected.splice(idx, 1);
|
selected.splice(idx, 1)
|
||||||
} else {
|
} else {
|
||||||
selected.push(tagId);
|
selected.push(tagId)
|
||||||
}
|
}
|
||||||
group.selected = selected;
|
group.selected = selected
|
||||||
this.setData({
|
this.filterGroups = groups
|
||||||
filterGroups: groups
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
async removeFilter(e) {
|
async removeFilter(key) {
|
||||||
const key = e.currentTarget.dataset.key;
|
const filters = this.activeFilters.filter((f) => f.key !== key)
|
||||||
const filters = this.activeFilters.filter((f) => f.key !== key);
|
|
||||||
|
|
||||||
// 如果清除的是国家筛选 → 重置分类和标签组为全部国家
|
|
||||||
if (key === 'country') {
|
if (key === 'country') {
|
||||||
this.setData({
|
this.selectedCountry = ''
|
||||||
selectedCountry: '',
|
this.activeFilters = filters
|
||||||
activeFilters: filters
|
await this.loadCategoryData('')
|
||||||
});
|
await this.loadGoods(1)
|
||||||
await this.loadCategoryData('');
|
return
|
||||||
await this.loadGoods(1);
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 清除标签筛选 → 同步更新 filterGroups.selected
|
|
||||||
if (key.indexOf('tag_') === 0) {
|
if (key.indexOf('tag_') === 0) {
|
||||||
var groupId = key.replace('tag_', '');
|
var groupId = key.replace('tag_', '')
|
||||||
var groups = this.filterGroups.map(function (g) {
|
var groups = this.filterGroups.map(function (g) {
|
||||||
if (String(g.id) === String(groupId)) {
|
if (String(g.id) === String(groupId)) {
|
||||||
return Object.assign({}, g, { selected: [] });
|
return Object.assign({}, g, { selected: [] })
|
||||||
}
|
}
|
||||||
return g;
|
return g
|
||||||
});
|
})
|
||||||
this.setData({
|
this.activeFilters = filters
|
||||||
activeFilters: filters,
|
this.filterGroups = groups
|
||||||
filterGroups: groups
|
await this.loadGoods(1)
|
||||||
});
|
return
|
||||||
await this.loadGoods(1);
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
this.setData({
|
this.activeFilters = filters
|
||||||
activeFilters: filters
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
async clearAllFilters() {
|
async clearAllFilters() {
|
||||||
// 是否有国家筛选
|
const hasCountry = this.activeFilters.some((f) => f.key === 'country')
|
||||||
const hasCountry = this.activeFilters.some((f) => f.key === 'country');
|
this.activeFilters = []
|
||||||
this.setData({
|
|
||||||
activeFilters: []
|
|
||||||
});
|
|
||||||
if (hasCountry || this.selectedCountry) {
|
if (hasCountry || this.selectedCountry) {
|
||||||
this.setData({
|
this.selectedCountry = ''
|
||||||
selectedCountry: ''
|
await this.loadCategoryData('')
|
||||||
});
|
|
||||||
await this.loadCategoryData('');
|
|
||||||
}
|
}
|
||||||
// 清空标签选中
|
|
||||||
var groups = this.filterGroups.map(function (g) {
|
var groups = this.filterGroups.map(function (g) {
|
||||||
return Object.assign({}, g, { selected: [] });
|
return Object.assign({}, g, { selected: [] })
|
||||||
});
|
})
|
||||||
this.setData({
|
this.filterGroups = groups
|
||||||
filterGroups: groups
|
await this.loadGoods(1)
|
||||||
});
|
|
||||||
await this.loadGoods(1);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
resetFilters() {
|
resetFilters() {
|
||||||
var groups = this.filterGroups.map(function (g) {
|
var groups = this.filterGroups.map(function (g) {
|
||||||
return Object.assign({}, g, { selected: [] });
|
return Object.assign({}, g, { selected: [] })
|
||||||
});
|
})
|
||||||
this.setData({
|
this.filterGroups = groups
|
||||||
filterGroups: groups
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
async confirmFilters() {
|
async confirmFilters() {
|
||||||
var filters = [];
|
var filters = []
|
||||||
// 保留国家筛选
|
var countryFilter = this.activeFilters.find(function (f) { return f.key === 'country' })
|
||||||
var countryFilter = this.activeFilters.find(function (f) { return f.key === 'country'; });
|
if (countryFilter) filters.push(countryFilter)
|
||||||
if (countryFilter) filters.push(countryFilter);
|
|
||||||
|
|
||||||
this.filterGroups.forEach(function (group) {
|
this.filterGroups.forEach(function (group) {
|
||||||
if (group.selected.length > 0) {
|
if (group.selected.length > 0) {
|
||||||
var labels = group.tags
|
var labels = group.tags
|
||||||
.filter(function (t) { return group.selected.indexOf(t.id) > -1; })
|
.filter(function (t) { return group.selected.indexOf(t.id) > -1 })
|
||||||
.map(function (t) { return t.name; });
|
.map(function (t) { return t.name })
|
||||||
if (labels.length > 0) {
|
if (labels.length > 0) {
|
||||||
filters.push({
|
filters.push({
|
||||||
key: 'tag_' + group.id,
|
key: 'tag_' + group.id,
|
||||||
label: labels.join(',')
|
label: labels.join(',')
|
||||||
});
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
})
|
||||||
this.setData({
|
this.activeFilters = filters
|
||||||
activeFilters: filters,
|
this.showFilter = false
|
||||||
showFilter: false
|
await this.loadGoods(1)
|
||||||
});
|
|
||||||
await this.loadGoods(1);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
goDetail(e) {
|
goDetail(item) {
|
||||||
const id = e.currentTarget.dataset.id;
|
|
||||||
uni.navigateTo({
|
uni.navigateTo({
|
||||||
url: `/pages/product-detail/product-detail?id=${id}`
|
url: `/pages/product-detail/product-detail?id=${item.id}`
|
||||||
});
|
})
|
||||||
},
|
|
||||||
|
|
||||||
async changePage(e) {
|
|
||||||
const action = e.currentTarget.dataset.action;
|
|
||||||
let current = this.pagination.current;
|
|
||||||
if (action === 'prev' && current > 1) {
|
|
||||||
current--;
|
|
||||||
}
|
|
||||||
if (action === 'next' && current < this.pagination.totalPages) {
|
|
||||||
current++;
|
|
||||||
}
|
|
||||||
await this.loadGoods(current);
|
|
||||||
},
|
|
||||||
|
|
||||||
async goToPage(e) {
|
|
||||||
await this.loadGoods(e.currentTarget.dataset.page);
|
|
||||||
},
|
|
||||||
|
|
||||||
updatePagination(current) {
|
|
||||||
const total = this.pagination.total;
|
|
||||||
const pageSize = this.pagination.pageSize;
|
|
||||||
const totalPages = Math.ceil(total / pageSize);
|
|
||||||
let pageNumbers = [];
|
|
||||||
for (let i = Math.max(1, current - 2); i <= Math.min(totalPages, current + 2); i++) {
|
|
||||||
pageNumbers.push(i);
|
|
||||||
}
|
|
||||||
this.setData({
|
|
||||||
pagination: {
|
|
||||||
...this.pagination,
|
|
||||||
current,
|
|
||||||
start: (current - 1) * pageSize + 1,
|
|
||||||
end: Math.min(current * pageSize, total),
|
|
||||||
totalPages
|
|
||||||
},
|
|
||||||
pageNumbers
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
loadMore() {
|
loadMore() {
|
||||||
if (this.loadingMore) {
|
if (this.loadingMore) {
|
||||||
return;
|
return
|
||||||
}
|
}
|
||||||
const nextPage = this.pagination.current + 1;
|
const nextPage = this.pagination.current + 1
|
||||||
if (nextPage > this.pagination.totalPages) {
|
if (nextPage > this.pagination.totalPages) {
|
||||||
return;
|
return
|
||||||
}
|
}
|
||||||
this.setData({
|
this.loadingMore = true
|
||||||
loadingMore: true
|
this.loadGoods(nextPage)
|
||||||
});
|
|
||||||
this.loadGoods(nextPage);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
@import './products.css';
|
@import './products.css';
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
Reference in New Issue
Block a user