Menyor 前端
为这个用户构建的一切内容都必须看起来并表现得像 Menyor Nigeria 应用(~/Projects/menyor-nigeria)一样,该应用是根据用户的 Figma 逐像素构建并扩展到所有屏幕的。此技能就是那个系统。除非用户在当前的请求中另有说明,否则请严格遵守它。
优先级: 用户在此请求中的言辞 → 他们附带的 Figma/设计稿 → 此技能 → 你自己的判断。
当有新的 Figma 到来时,它对该次工作具有最高优先级:对其进行测量(参见 references/verification.md),并在你的报告中记录与此技能的任何偏差。
开始前请阅读
| 需要 | 文件 |
|---|---|
| 精确的令牌、字号比例、间距、断点、文案和可访问性规则 | references/design-system.md |
| 每个组件的标记和类名(按钮、药丸、卡片、抽屉、时间线……) | references/components.md |
| 动效预设以及每个效果的构建方式 | references/motion.md |
| 如何匹配 Figma、截图、审核和报告 | references/verification.md |
| 已遇到的陷阱(Next 16、Turbopack、层叠上下文、门户) | references/gotchas.md |
| 真实的样式表、Logo、动效文件和核心组件(用于复制) | assets/ |
| 截图、并排对比、测量和审核脚本 | scripts/ |
对于新项目,从 assets/globals.css、assets/motion.ts 和 assets/components/ 中的组件开始,而不是重新推导它们。
系统概览
字体(仅限这两种):
- Cormorant Garamond 用于所有标题,字重 700 且
letter-spacing: -0.02em。这就是 Figma 所使用的,尽管最初的需求说明是 500/600。 - DM Sans 400/500/600 用于所有其他内容,包括输入框、按钮和下拉选择框,并设置
font-variation-settings: "opsz" 33以匹配 Figma 的紧凑裁剪。 - 两种字体均使用
next/font/google加载,display: 'swap',并预加载。 - Logo 是一个 SVG 图像,永远不是字体。
颜色(仅限这些):
| 令牌 | 十六进制 | 用途 |
|---|---|---|
--brand-blue | #006BA6 | 按钮、链接、标题、蓝色条纹、页脚 |
--brand-blue-hover | #005A8C | 悬停状态 |
--brand-blue-tint | #E6F0F6 | 徽章、选中行 |
--bg | #EBEAEA | 页面背景、卡片内的行 |
--surface | #FFFFFF | 卡片、输入框、抽屉 |
--ink | #111111 | 文本 |
--ink-muted | #5F6368 | 标题、辅助文本 |
--success | #1E8E3E | 仅用于图标和“已确认”提示点,切勿用于正文(其在白色背景上的对比度为 4.2:1) |
--error | #C62828 | 错误提示 |
--on-blue | #FFFFFF | 蓝色背景上的文本;分隔线不透明度为 60% |
十六进制值仅存在于 :root 和 BRAND.colors 配置中(邮件和 PDF 从中读取)。
分隔线和遮罩使用 color-mix(in srgb, var(--ink) 12%, transparent) 推导。
形状:
- 每个按钮、选项卡、输入框、下拉选择框、搜索框和行程控件都是药丸形。
- 大卡片圆角 48px,普通卡片 24px,图片 24px,行 16px。
- 轮廓控件和输入框有 1px 蓝色边框。
- 卡片无边框,任何内容无阴影。
- 层级关系通过灰色与白色表面来体现。
字号比例(桌面端 → 手机端):
| 元素 | 尺寸 |
|---|---|
| 主视觉 | 110px / 112px 行高 → 48px |
章节和页面标题(.display) | 64px / 1.22 → 40px |
| 卡片标题 | 30px |
| 列表行 | 24px |
| 正文 | 16px |
| 辅助文本 | 14px |
| 徽章 | 13px |
| 价格 | 22px,字重 600,表格数字 |
| 眉题 | DM Sans 16px,全大写,蓝色 |
布局:
- 容器最大宽度 1480px,内边距 40px(手机端 24px)。
- 头部高度 96px(手机端 72px),固定在灰色页面上,滚动后显示 1px 分隔线。
- 章节间距桌面端约为 160px,手机端为 80px。
- 断点:1360(紧凑行程药丸),1180(导航变为菜单),960(单列),640(手机端)。
文案:
- 展示类标题使用首字母大写(“Everything For Your Trip, In One Place”)。
- UI 文本使用句子大小写(“Add to my trip”)。
- 所有文案存放在
src/content/*.ts中。切勿在组件中硬编码字符串。 - 品牌值(邮箱、电话、WhatsApp、法律名称、社交媒体)来自
BRAND。 - 价格始终通过货币辅助函数处理(默认 NGN,可记住用户选择)。
- 绝不虚构评论、评分、统计数据或联系方式。
- 占位符保持可见的
[方括号]形式。
不可妥协的规则
- 仅使用上述两种字体和颜色。 在每个新屏幕上运行
scripts/audits.mjs(paletteAudit调色板审核)。 - 无阴影、无卡片边框、无渐变。 唯一的例外是微妙的照片渐变,并且仅限于文字需要时。
- 每个控件都是药丸形,带有 1px 蓝色轮廓或实心蓝色填充。 聚焦时显示 2px 白色 + 2px 蓝色环。
- 一个共享的动效预设文件。 仅对
transform和opacity进行动画;FAQ 和订票卡的高度是刻意的例外。prefers-reduced-motion禁用所有动效并一次性显示内容。 - 默认可达:
- WCAG AA 对比度。
- 带标签的控件。
- 抽屉和模态框锁定焦点,按 Escape 键关闭,将焦点返回到打开它们的按钮,并在
document.body上的门户中渲染。 - 切换开关使用
aria-pressed,药丸选择使用role="radio"和aria-checked。 - 仅视觉占位符标记为
aria-hidden。
- 文案放在内容文件中,品牌值来自
BRAND。 图片需要真实的替代文本,其路径放在内容文件中。 - 在 390、768 和 1440px 宽度下响应式良好,无横向滚动:
- 手机端使用快照轮播并可窥见下一张卡片。
- 筛选器和预订表单移到底部抽屉。
- 主要操作位于粘性底部栏中。
- 抽屉变成底部面板。
- 报告前请验证:
- 在 1440 和 390 宽度下截图。
- 与设计进行并排对比。
- 运行调色板和对比度审核以及 axe(无障碍工具)。
- 在生产构建上运行 Lighthouse 移动端:性能至少 85,可访问性至少 95,CLS 为 0。
- 如实报告差异。
构建新屏幕:执行顺序
- 首先将文案放入内容文件中。
- 使用
references/components.md中的现有组件进行组合。- 典型结构:居中的
page-head(眉题 +.display行 + 介绍),然后是灰色页面上的白色large-card/step-card/checkout-card块。 - 列表放在白色卡片内的灰色
update-row/listing-row行中。
- 典型结构:居中的
- 只有在没有合适的组件时,才在
globals.css的相应部分添加新类,使用令牌构建。不使用 Tailwind 和内联颜色。 - 接入动效预设(
Reveal、SectionHeading行上升、悬停抬起)。 - 验证(
references/verification.md),然后附带截图进行报告。