用户端小程序 首页 / 底部导航 / 缺货订单全局提示 开发设计文档

  • 模块:hugray-user-miniapp(前端 UI 实现,本轮无后端改动)
  • 日期:2026-10-12
  • 需求来源:「参考图片以及 pen 源文件,实现首页以及底部 tab 的 ui 布局和样式,底部的缺货订单是一个全局的 toast,规则如图二,注意 icon 需要按照设计稿一比一还原」
  • 设计稿权威依据:doc/琥歌瑞0928.pen(首页主稿 line 4485 起;底部导航示例 line 14259;待支付/缺货提示体系 line 12839、横向通栏实例 line 17545)
  • 换算基准:设计稿 375pt 宽 → 750rpx(**pt × 2 = rpx**)

已确认决策(用户逐项确认):

序号 待澄清项 采用方案
1 底部 tab 栏如何落地 新建 3 个占位页 + 注册路由(健康方案 / 我的订单 / 个人中心),tab 可真实切换
2 首页顶部沉浸式导航 只自绘品牌 Logo;状态栏、灵动岛、微信原生胶囊由系统与微信渲染,避免重叠
3 首页两张产品大图素材不在仓库 用渐变纯色块占位,素材就绪后替换为 image
4 缺货订单数量数据来源 先本地 mock 数据(utils/stock-order.js 收口)

一、功能概述

序号 功能 说明
1 首页(pages/index/index.vue) 沉浸式导航 + 明星产品展位(大图 / 轮播指示器 / 产品信息与行动区)+ 次席展位
2 底部导航栏(pages.json → tabBar) 原生 tabBar,4 个 Tab(代谢300 / 健康方案 / 我的订单 / 个人中心),选中态、个人中心角标
3 缺货订单全局提示(components/stock-order-toast) 所有页面均弹出;点击跳缺货订单列表页;单笔展示倒计时,多笔仅展示数量

缺货提示落地方式:小程序 App.vue 不支持渲染模板,故采用**全局组件 + 各页面引入**方案(不使用 tabBar 层能力)。

底部导航本轮明确采用**原生 tabBar**(在 pages.json 配置),不自定义组件;因此跳转统一用 uni.switchTab(仅 reLaunch 亦可,navigateTo/redirectTo 不可用)。


二、现状与关键约束

2.1 底部导航采用原生 tabBar

pages.json 原本**无 tabBar 配置**,本轮新增顶层 tabBar 字段:

  • 首页 navigationStyle: "custom"(沉浸式,自绘品牌区);
  • 底部导航为**原生 tabBar**(系统渲染于 webview 之上),页面内容区自动排除 tabBar 高度,页面内**无需为 tab 预留底部留白**;
  • 原生 tabBar 仅接受本地图片文件作为图标(不支持 base64 / SVG / 网络图)→ static/tabbar/*.png;
  • 原生 tabBar 无 CSS 角标能力 → 用 uni.setTabBarBadge 设置。

2.2 项目无 UI 库 / 无 lucide 图标库

设计稿使用 lucide 图标库(house / clipboard-check / package / circle-user-round / clipboard-list / chevron-right),项目未引入该库。

  • 方案:**内联 base64 SVG**(background-image: url('data:image/svg+xml;base64,...'))。
  • 例外:**原生 tabBar 图标仅支持本地图片文件**,故 4 个 tab 图标(双态共 8 个)由 lucide SVG 光栅化为 81×81 PNG,落在 static/tabbar/。
  • 先例:pages/login/register.vue 已使用同款 base64 data-URI 图标背景(class .field-icon),风格一致。
  • 图标源:lucide 官方 SVG(stroke-width=2、stroke-linecap/linejoin=round),仅替换 stroke 颜色以适配双态。

2.3 产品大图素材缺失

设计稿引用的产品图(微信图片_20260916202238_115_8451.png 等)不在仓库 → 按决策以**同色系渐变块占位**,DOM 结构保留(便于后续替换为 image)。

2.4 缺货订单数量无后端接口

→ 本轮以本地 mock 收口在 utils/stock-order.js,接口就绪后仅替换 getStockOrderCount() 实现,调用方零改动。

2.5 登录态校验复用

各页面 onShow 统一调用 utils/request.js 的公共守卫 ensureLogin()(无 token 时 uni.reLaunch 至登录页)。


三、页面 / 路由变更(pages.json)

路径 页面 导航样式 说明
pages/index/index 首页 navigationStyle: "custom" 沉浸式,自绘品牌区
pages/health-plan/index 健康方案 原生标题栏「健康方案」 tab 占位页(含 toast)
pages/order/index 我的订单 原生标题栏「我的订单」 占位页
pages/profile/index 个人中心 原生标题栏「个人中心」 占位页
pages/contact/index 联系我们 navigationStyle: "custom" 顶部深蓝品牌区自绘,个人中心「联系我们」菜单跳转的目标页;**不在 tabBar 列表**
pages/address/list 选择地址 原生标题栏「选择地址」(白底黑字) 个人中心「收货地址」菜单跳转的目标页;**不在 tabBar 列表**
pages/stock-order/list 缺货订单 原生标题栏「缺货订单」 缺货提示点击跳转的目标页;**不在 tabBar 列表**

3.1 原生 tabBar 配置(pages.json → tabBar)

{
  "color": "#64748B",
  "selectedColor": "#003E7E",
  "backgroundColor": "#FFFFFF",
  "borderStyle": "white",
  "list": [
    { "pagePath": "pages/index/index",       "text": "代谢300",  "iconPath": "static/tabbar/tab-home.png",    "selectedIconPath": "static/tabbar/tab-home-active.png" },
    { "pagePath": "pages/health-plan/index", "text": "健康方案", "iconPath": "static/tabbar/tab-plan.png",    "selectedIconPath": "static/tabbar/tab-plan-active.png" },
    { "pagePath": "pages/order/index",       "text": "我的订单", "iconPath": "static/tabbar/tab-order.png",   "selectedIconPath": "static/tabbar/tab-order-active.png" },
    { "pagePath": "pages/profile/index",     "text": "个人中心", "iconPath": "static/tabbar/tab-profile.png", "selectedIconPath": "static/tabbar/tab-profile-active.png" }
  ]
}

borderStyle 仅支持 black / white,取 white 对应设计稿 #F1F5F9 淡描边。iconPath 路径不带前导斜杠。


四、视觉还原规格

4.1 首页(375×812pt,fill #F8FAFC)

元素 设计稿规格 实现值
页面底色 #F8FAFC 同左;.page 100%×100vh,overflow: hidden
品牌区(沉浸导航) 位于产品大图视口内左上,状态栏下方 absolute 叠加于大图上方 z-index 2;padding-top = 状态栏高度;左右 24rpx
品牌 Logo metabolism-300-logo.png(蓝「代谢」+ 绿「300」+ 绿波浪) 168×88rpx(aspectFit)
明星展位-大图视口 375×406pt,fill #FFFFFF,mode cover H812rpx,渐变占位 180° #D9E7F7 → #E9F1FB 26% → #FFFFFF 54% → #F4F7FB
轮播指示器(毛玻璃微胶囊) x165 y376,H16 R8,fill #FFFFFFB3,stroke #FFFFFF 0.8,shadow #0F172A12 y2 blur6,gap5 padding 0/7 H32rpx R16rpx,rgba(255,255,255,.7) + 1rpx #FFF 描边 + 0 4rpx 12rpx 阴影;居中、top 752rpx;gap10rpx、padding 0/14rpx
指示条-非激活 4×4 R2 #003E7E30 8×8rpx R4rpx rgba(0,62,126,.19)
指示条-激活 14×4 R2 渐变 90° #003E7E → #1E5EBC W28rpx H8rpx 渐变 90° #003E7E → #1E5EBC
产品信息与行动区 375×58pt,fill #FFFFFF,上下 1 描边 #F1F5F9,shadow #0F172A06 y2 blur8,padding 0/18,space_between H116rpx,同左(描边 1rpx,padding 0/36rpx)
英文型号编码 G&METS-II 11pt 700 #003E7E 字距 1.2 22rpx 700 字距 2.4rpx #003E7E
产品中文主名 超分子基团复合肽 17.5pt 800 #0F172A 字距 -0.2 35rpx 800 字距 -0.4rpx #0F172A
探索更多(胶囊) H34 R17,渐变 90° #82C236 → #639C1F,shadow #6AA02735 y3 blur8,gap6 padding 0/8/0/14 H68rpx R34rpx,同渐变 + 0 6rpx 16rpx rgba(106,160,39,.21);文案 12.5pt 600 → 25rpx
探索更多-箭头底托 20×20 R10 #FFFFFF28,内嵌 lucide chevron-right 12×12 #FFFFFF 40×40rpx R20rpx rgba(255,255,255,.16);箭头 24×24rpx base64
次席展位 x0 y464,375×265pt,clip cover H530rpx,渐变占位 160° #4E3D94 → #6A5AC1 45% → #A99BE0

4.2 底部导航栏(原生 tabBar,375×83pt)

原生 tabBar 由系统渲染,**仅可通过 pages.json 配置有限属性**,以下为设计稿规格与原生能力的映射。

元素 设计稿规格 原生实现 差异说明
容器 fill #FFFFFF backgroundColor: "#FFFFFF" 一致
顶部描边 1 描边 #F1F5F9 borderStyle: "white" 原生仅 black/white 两档,取 white(系统绘制极淡描边)
容器阴影 shadow #0F172A08 y-4 blur16 不支持 原生 tabBar 无阴影配置项
Tab 组 H48pt,4 等分 由系统按 list 数量等分 高度由系统控制(约 50px + 安全区)
图标底托 26×26pt,选中态 fill #003E7E14 不支持 原生 tabBar 无选中底托能力
图标 22×22pt,4 态:house / clipboard-check / package / circle-user-round static/tabbar/*.png(81×81 PNG,系统缩放至 22pt 左右) 未选中 #94A3B8 / 选中 #003E7E
Tab 文案 11pt,选中 #003E7E 700 / 未选中 #64748B 500 color: "#64748B"、selectedColor: "#003E7E" 原生**不支持字重区分**,颜色一致
个人中心角标 14×14 R7 #E53935,白描边,白字 9/700 uni.setTabBarBadge({ index: 3, text })(App.vue onShow 统一设置) 样式由系统绘制,仅可传文本

冲突取舍:pen「首页 frame」与「组件示例」对选中底托不一致 → 因原生 tabBar 无底托能力,**统一以图标 + 文案变色表达选中态**。个人中心角标数量本轮 mock(默认 1)。

4.3 缺货订单全局提示(横向通栏标准态)

元素 设计稿规格 实现值
容器 351×40pt,R20,渐变 135° #FFFFFFF6 → #FFFFFFE0,stroke #FFFFFF 1.2,shadow #0F294222 y4 blur14 左右各 24rpx,H80rpx R40rpx;渐变 135° rgba(255,255,255,.96) → rgba(255,255,255,.88);2rpx #FFF 描边;0 8rpx 28rpx rgba(15,41,66,.13)
容器定位 悬浮于内容之上 position: fixed;bottom: calc(24rpx + 安全区);z-index 85
前置图标 lucide clipboard-list 15×15 30×30rpx base64 #0F172A
主文案 11pt 700 22rpx 700 #0F172A,单行省略
倒计时数字块 16×14 R3,红底白字 32×28rpx R6rpx #E53935,白字 19rpx 700;仅**单笔**缺货时展示
倒计时冒号 红 #E53935 20rpx 700 #E53935
前往支付按钮 H25 R12.5,渐变 90° #EF4444 → #DC2626 H50rpx R25rpx,同渐变 + 0 3rpx 10rpx rgba(220,38,38,.21);文案 21rpx 700
按钮内箭头 lucide chevron-right 9×9 #FFFFFF 18×18rpx base64

五、缺货订单提示规则(按图二 / 需求原文)

原文:「如果有缺货订单,需要所有页面都能弹出提示。点击跳转到缺货订单列表页。有多个情况,展示具体数量,不显示倒计时」

场景 展示规则 文案
无缺货订单 不展示 —
单笔缺货(count = 1) 展示提示 + 支付倒计时(MM:SS) 您有一个缺货订单待支付
多笔缺货(count > 1) 展示提示 + 具体数量,**不展示倒计时** 您有 N 个缺货订单待支付
点击提示条 跳转缺货订单列表页 uni.navigateTo('/pages/stock-order/list')

实现要点(components/stock-order-toast):

  • visible = count > 0;titleText 按 count 分支;
  • 倒计时仅在 count === 1 时启动(setInterval 1s,初始 30 分钟),onUnmounted 清理定时器;
  • 组件在**每个业务页面**模板引入。

六、图标清单(lucide 1:1 还原)

6.1 原生 tabBar 图标(PNG,static/tabbar/)

原生 tabBar 仅支持本地图片文件 → 由 lucide SVG 光栅化为 81×81 PNG(stroke-width=2、round 端点),仅替换 stroke 颜色。

图标 用途 文件(未选中 / 选中) 颜色
house 代谢300 tab-home.png / tab-home-active.png #94A3B8 / #003E7E
clipboard-check 健康方案 tab-plan.png / tab-plan-active.png #94A3B8 / #003E7E
package 我的订单 tab-order.png / tab-order-active.png #94A3B8 / #003E7E
circle-user-round 个人中心 tab-profile.png / tab-profile-active.png #94A3B8 / #003E7E

6.2 内联 base64 SVG 图标

图标 用途 颜色 尺寸(rpx)
clipboard-list 缺货提示-前置图标 #0F172A 30×30
chevron-right 探索更多 / 前往支付 #FFFFFF 24×24 / 18×18

实现:class 背景图 + background-repeat: no-repeat; background-position: center; background-size: 100% 100%。


七、文件清单与影响范围

新增:

  • static/tabbar/*.png(原生 tabBar 图标,4 图标 × 双态 = 8 个 PNG)
  • components/stock-order-toast/stock-order-toast.vue(全局缺货提示组件)
  • utils/stock-order.js(缺货数量 mock 数据源 + 列表页路径常量)
  • pages/health-plan/index.vue、pages/order/index.vue、pages/profile/index.vue(三个 tab 页,已按 pen 稿完整实现,详见第九章)
  • pages/contact/index.vue(联系我们页,个人中心菜单跳转目标,详见 9.6)
  • pages/address/list.vue(选择地址页,个人中心菜单跳转目标,详见 9.7)
  • pages/stock-order/list.vue(缺货订单列表页占位)

修改:

  • pages/index/index.vue(全量重写为沉浸式首页)
  • pages.json(首页与个人中心 navigationStyle: "custom" + 4 条新路由 + 原生 tabBar 配置)
  • App.vue(onShow 用 uni.setTabBarBadge 设置个人中心角标)
  • utils/request.js(新增公共守卫 ensureLogin())

移除:

  • components/app-tab-bar/(自定义 tab 组件,已由原生 tabBar 取代);页面内 <app-tab-bar> 引用与底部留白同步删除

影响:登录 / 注册 / 注册成功页不受影响(仍走各自既有布局)。健康方案 / 我的订单页复用 ensureLogin();个人中心需展示未登录态,不强制跳转。跳转 tab 页须用 uni.switchTab。


八、待办 / 遗留

序号 事项 状态
1 首页两张产品大图素材入仓后替换渐变占位块 待素材
2 缺货订单数量接口 + 支付倒计时截止时间由后端下发 待接口(当前 mock)
3 个人中心角标数量(未读)由后端下发 待接口(当前默认 1)
4 缺货订单列表页真实内容 占位
5 「探索更多」产品详情页 占位(toast 提示)
6 真实数据接口:个人中心「昵称 / 头像 / 等级 / 收益」已由 getMemberInfo 下发;订单列表仍待 getOrderList 部分完成
7 三页图片素材(方案卡、订单缩略图、用户头像)入仓后替换渐变占位 待素材

九、三个 Tab 页实现(健康方案 / 我的订单 / 个人中心)

  • 需求来源:「后面的健康方案、我的订单以及个人中心都结合图片以及根据 pen 源文件中的内容实现」
  • pen 依据:健康方案 19179–19939;我的订单 19946–22330;个人中心已登录 22331–23709、未登录 23710–24963
  • 图片素材(方案卡 3 张 微信图片_*.png、订单缩略图、用户头像)**均不在仓库** → 统一以同色系渐变块占位,DOM 结构保留便于后续替换为 image

9.1 健康方案页(pages/health-plan/index.vue)

区块 设计规格(pt → rpx) 实现要点
分类药丸栏 375×44,padding 0/16,药丸间隙 8 .filter-bar;3 档 G&METS-II / HBBLF-2 / NEARCLC-II
药丸选中态 h28 R14,fill #003E7E,文字 11.5pt 700 #FFFFFF .pill--active;未选中 fill #EDF2F7,文字 #475569
滑动指示条 轨道 28×3 #E2E8F0,滑块 10×3 #C5A566 .slider / .slider-thumb,按档位步进 18rpx
产品标题行 375×48,padding 0/16 副标 11pt 700 #003E7E letterSpacing 1.2 + 主名 17.5pt 800 #0F172A
探索更多按钮 h32 渐变 90° #82C236→#639C1F R16 .explore-btn + 白 chevron 底托(同首页范式)
方案卡片 343×160,R14,间隙 12 3 张渐变占位卡(planList),240rpx 高

9.2 我的订单页(pages/order/index.vue)

区块 设计规格 实现要点
状态 Tab 栏 375×44 白底 + #F1F5F9 底描边 5 项:全部 / 待支付 / 待发货 / 待收货 / 售后;选中为 90° #1E5EBC→#003E7E 胶囊
二级筛选栏 375×44,两个 166×32 下拉 商品类型「全部」+ 时间区间「选择时间」(calendar 图标),未开发 → toast 占位
订单卡片 343 R12 白底,gap 12 padding 14 6 条 mock 覆盖多状态,filteredOrderList 按 Tab 过滤
状态徽章配色 padding [2,7] R4,11.5pt 700 待支付 #FEF2F2/#E05338;履约中 #ECFDF5/#10B981;待发货·待收货 #FFF7ED/#EA580C;已完成·已取消 #F1F5F9/#94A3B8
缩略图与操作 缩略图 40×40 R6,••• 更多指示 待支付:倒计时(16×14 #E53935 白字)+ 去支付按钮;其余:查看订单按钮

9.3 个人中心页(pages/profile/index.vue)

导航栏变更:pages.json 中本页由系统导航栏改为 navigationStyle: "custom" —— 设计稿顶部无标题且页面底色为渐变,白底原生导航会造成视觉割裂;页面以 statusBarHeight + .nav-holder(92rpx)留出状态栏与胶囊区。

区块 设计规格 实现要点
页面底色 175° 渐变 #D6E6F8 0 → #C4DCF6 .18 → #E8F1FC .38 → #F8FAFC .58 → #F8FAFC 1 .page
头部信息区 x20 335×72,居中,头像与文本间隙 14 .header
头像 70×70 R35 fill #F1F5F9 + 2.5 白描边 已登录内嵌 camera 32×32 #94A3B8;未登录内嵌 user 34×34 #CBD5E1
文本信息 昵称 18pt 700 #0F172A 已登录「辉煌G891」+ 等级胶囊(userLevel 动态展示 C/L1~L4);未登录「点击登录 / 注册」+ 副标 12pt #64748B
会员等级胶囊 h22 渐变 90° #FDE68A→#FCD34D→#F59E0B,V 勋章 18×18 渐变 145° .level-pill / .level-medal;等级文字 12.5pt 800 #78350F
主按钮 h32 渐变 90° #1E5EBC→#003E7E R16 已登录「编辑资料」/ 未登录「立即登录」
收益玻璃卡 x16 343×74,180° 半透明白渐变 + blur20,R16 三栏等分:**今日 10.00 / 本月 400.00 / 累计 128000.00**;未登录统一 0.00;**未登录或 C 普通用户不展示该卡**
功能菜单卡 x16 343×408,同款玻璃态,6 行 × 68(未登录 / C 仅 2 行) 行图标 20×20 渐变描边 #3B82F6→#1D4ED8,右箭头 16×16 #94A3B8
菜单项与等级 — L1~L4 且已登录时展示 6 项:share-2 我的邀请码 / crown 会员中心 / file-text 仓库订单 / badge-cent 收入明细 / map-pin 收货地址 / contact 联系我们;**未登录或 C 普通用户仅展示「收货地址」「联系我们」**
仓库订单角标 18×18 #EF4444 R9 文字 1 仅已登录态展示
ICP 区 x16 343×40 居中 京ICP备2026092800号-1X + 版权行;**内容不足一屏时贴页面底部**(.page 为纵向 flex,.icp 用 margin-top: auto 吸收剩余空间)

用户等级与展示规则(C/L1~L4):由 userLevel 控制,isRestrictedView = !isLoggedIn || userLevel === 'C'。**未登录或 C 普通用户**在个人中心仅保留「收货地址」「联系我们」两行菜单,并隐藏收益数据卡;**已登录且 L1~L4** 展示全部内容。昵称、头像、等级、收益均已由 getMemberInfo(GET /miniapp/account/user/info)下发;会员等级空或非法时后端兜底 C。

9.4 新增内联 base64 图标

icon key 用途 颜色 尺寸(rpx)
chevron-down 订单二级筛选下拉 #94A3B8 26×26
calendar 订单时间区间筛选 #94A3B8 24×24
camera 个人中心已登录头像 #94A3B8 64×64
user 个人中心未登录头像 #CBD5E1 68×68
share-2 / crown / file-text / badge-cent / map-pin / contact 个人中心 6 行菜单 渐变 #3B82F6→#1D4ED8 40×40
chevron-right 菜单右箭头 #94A3B8 32×32

9.5 三页公共约定

  • 三页模板均引入 <stock-order-toast />,保证缺货提示全局可见。
  • 首页 / 健康方案 / 我的订单 / 个人中心:**均不校验登录态**,未登录可正常浏览(原 ensureLogin() 守卫已移除,仅缺货订单列表页保留)。
  • 个人中心:onShow 读 getToken() 仅用于切换「已登录 / 未登录」展示态,不做跳转;未登录时点击头像 / 名称 / 主按钮直接 uni.reLaunch 至登录页,**点击菜单项先 uni.showModal 提示登录、确认后跳转**。
  • 订单列表、仓库订单角标仍为本地 mock,待 getOrderList 就绪后替换;收益数值、用户昵称、头像、用户等级已由 getMemberInfo(GET /miniapp/account/user/info,金额单位分,前端 formatYuan 格式化)替换。
  • 「探索更多 / 二级筛选 / 去支付 / 查看订单 / 编辑资料」本轮统一为 toast 占位(菜单项仅在已登录态为占位)。

9.6 联系我们页(pages/contact/index.vue)

  • 需求来源:「联系我们的原型如图,参考 ui 设计风格实现」
  • 入口:个人中心菜单项「联系我们」(menu.key === 'contact')→ uni.navigateTo('/pages/contact/index');**未登录仍先 uni.showModal 提示登录**(沿用个人中心菜单统一拦截规则)
  • 导航:pages.json 注册 navigationStyle: "custom" —— 顶部为深蓝品牌色块,白底原生导航会造成视觉割裂
区块 设计规格 实现要点
顶部深蓝面板 纯色 #0B3F6F(取自 logo.png 底色) .top-panel(paddingTop = statusBarHeight);导航栏与 Hero 区共用底色形成连续色块,且与 Logo 图圆角边缘无缝融合
导航栏 h44,返回箭头左置 x8,标题居中 .nav;返回箭头为**纯 CSS**(左/下边框旋转 45°)避免额外 base64,白色 11pt 700
品牌 Hero 区 h200,居中展示品牌 Logo <image class="brand-logo" src="/static/logo.png" mode="widthFix" />,宽 170pt,高度按原图比例自适应
联系方式列表 x20,列表项纵向间距 44 .info-list(padding: 140rpx 40rpx 0)
单行信息 标签列宽 110pt,右侧数值 .info-label 16pt 600 #1F2937;.info-value 15pt #6B7280;固定标签列宽保证各行数值纵向对齐
平台客服按钮 h30 R15,**pen 标准「微信按钮 WeChat」** 渐变(90°)#07C160→#05A352 + 投影 #07C16040 <button open-type="contact">(微信客服会话)+ 内嵌 /static/wechat-icon.png + 白字 13pt 600;::after { border: none } 重置小程序默认边框
热线文案 城市招商热线 / 合伙人招募 均 400-451-666 客服接口未就绪,先以文件内常量 CITY_INVEST_HOTLINE / PARTNER_RECRUIT_HOTLINE 维护,接口就绪后替换
返回行为 uni.navigateBack() 无上级页面(如直接进入)时兜底 uni.switchTab('/pages/profile/index')

9.7 选择地址页(pages/address/list.vue)

  • 需求来源:「这是收货地址的原型,参考 ui 规范和设计风格实现收货地址的页面」
  • 入口:个人中心菜单项「收货地址」(menu.key === 'address')→ uni.navigateTo('/pages/address/list');未登录仍先 uni.showModal 提示登录
  • 导航:pages.json 注册原生标题栏「选择地址」(白底黑字)
区块 设计规格 实现要点
地址条目 纵向 padding: 36rpx 40rpx,无分割线 .addr-item 横向 flex,文本区 flex: 1; min-width: 0 保证长地址可换行
姓名 + 手机号 姓名 16pt 600 #1F2937;手机号 15pt #374151 .addr-head 横向 flex,gap: 56rpx;手机号按规范脱敏展示(185****0110)
默认标记 蓝框小标签(#1E5EBC,描边 1pt,圆角 3pt) .addr-tag,仅 isDefault 为 true 时渲染
地址详情 14pt #6B7280,行高 1.45,最多两行 .addr-detail
编辑入口 右上角图标 22×22,#1E5EBC 内联 base64 SVG square-pen,点击为 toast 占位(编辑页未实现)
底部操作栏 白色底 + 绿色胶囊按钮(H48 → 96rpx,PILL R24 → 48rpx),白字 + 白色加号 尺寸/圆角/文字与登录页 .btn 完全一致;.add-bar 固定底部,左右 56rpx 内边距 + padding-bottom: calc(32rpx + env(safe-area-inset-bottom))(胶囊不覆盖 Home 指示条);按钮采用 pen 标准「草绿动能行动」 渐变(90°)#82C236→#639C1F + 投影 #6AA02735,与首页 / 健康方案「探索更多」按钮同源
空态占位 无地址时居中展示:灰底圆形(d100 #F1F5F9)+ 灰色 map-pin 图标(48×48 #CBD5E1)+ 主文案「暂无收货地址」15pt 600 #475569 + 副文案「点击下方按钮添加收货地址」13pt #94A3B8 v-if="addressList.length" 渲染列表,v-else 渲染空态;底部「新增地址」按钮两种状态均保留
数据来源 三条 mock 地址(张三为默认 / 李四 / 王五) 地址列表接口就绪后替换 MOCK_ADDRESS_LIST
新增入口 底部「新增地址」按钮 → uni.navigateTo('/pages/address/add') handleAdd 由 toast 占位改为跳转新增地址页(见 9.8)

9.8 新增地址页(pages/address/add.vue)

  • 需求来源:「点击新增地址时跳转地址新增页面,注意我给你的图片只是原型不是真正的ui设计,需要你参考 琥歌瑞0928.pen 的设计风格去设计然后实现」
  • 入口:选择地址页底部「新增地址」按钮 → uni.navigateTo('/pages/address/add')
  • 导航:pages.json 注册原生标题栏「新增地址」(白底黑字),与选择地址页同规格
  • 设计原则:原型图仅提供字段结构(收件人 / 手机号 / 收件地区 / 详细地址 / 设为默认 / 提交);视觉按 pen「FORM」组件规范落地,并按要求做简化——**保留字段前缀图标**、输入框**只保留下边框**
区块 设计规格 实现要点
表单区 左右 56rpx 内边距(与底部提交栏对齐),首项距导航 40rpx,项间距 40rpx .form-area / .field-block,复用 pages/login/register.vue 表单结构
字段标签 12.5pt → 26rpx,600 #334155,与输入框间距 20rpx .field-label(pen「标签」规范)
输入框 高度 H44 → 88rpx;**只保留下边框**:border-bottom: 2rpx solid #CBD5E1,去掉左/右/上三边与圆角,白底、左右内边距 4rpx,视觉更轻 .input-wrap
前缀图标 每个字段左侧 16pt → 40rpx 图标(#64748B,内联 base64 SVG,与输入框间距 20rpx):收件人 user / 手机号 smartphone / 收件地区 map / 详细地址 map-pin .field-icon + .icon-user / .icon-phone / .icon-map / .icon-pin
收件地区 点击行唤起原生省市区选择器,右侧 chevron-right(#94A3B8)暗示可展开;未选择时展示占位文案 #94A3B8 <picker mode="region"> 包裹 .input-wrap;.field-input--placeholder 控制占位色
设为默认 pen 无开关组件规范,取品牌蓝 #003E7E(与 tabBar 选中色同源) <switch :checked color="#003E7E" @change>,默认关闭
底部提交栏 白色底 + 绿色胶囊按钮(H48 → 96rpx,PILL R24 → 48rpx),白字;采用 pen「草绿动能行动」渐变(90°)#82C236→#639C1F,**去掉投影**保持扁平简洁 .submit-bar 固定底部(左右 56rpx + padding-bottom: calc(32rpx + env(safe-area-inset-bottom))),与该页「新增地址」入口按钮、首页/健康方案「探索更多」同源
表单校验 收件人非空 → 手机号非空且匹配 ^1[3-9]\d{9}$ → 地区非空 → 详细地址非空,逐项 toast 提示 _validateForm() 返回失败原因,通过后 _handleSubmit 保存并 uni.navigateBack()
数据来源 地址新增接口未就绪,提交成功后本地 toast「保存成功」并返回列表页 接口就绪后替换 _handleSubmit 内的占位反馈