mcpField
S
screenshot-to-code

screenshot-to-code

github.com/onewave-ai设计与 UI3931.3k 次安装1 周前更新
代码仓库

关于 screenshot-to-code

将 UI 截图转为整洁、响应式且易于访问的代码技能。它会适配现有项目技术栈,并指导实现及与原图的视觉比对。

主要功能

  1. 01匹配现有项目技术栈
  2. 02梳理布局、设计令牌和组件
  3. 03编写语义化、可复用的 UI 代码
  4. 04适配较小屏幕布局
  5. 05渲染并与截图比对

适用场景

  1. 01将截图还原为网页
  2. 02构建响应式定价区块
  3. 03在无现有项目时制作屏幕原型
  4. 04对照参考图检查渲染结果

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/onewave-ai/claude-skills --skill screenshot-to-code

安装后在 Claude Code 中输入/screenshot-to-code确认已加载。

附带文件references/stack-setup.mdreferences/visual-check.md

详细介绍

截图转代码

将图片中的 UI 重建为简洁、响应式且无障碍的代码,然后将渲染结果与图片进行对比。

工作流

  1. 选择目标技术栈。 如果用户在项目中操作,请与项目保持一致:读取 package.json,确认使用 React/Next/Vue 以及 Tailwind 版本,并复用现有组件、设计令牌和图标库。仓库已有答案时不要提问。如果没有项目:

    • 单屏界面或快速原型:使用一个独立的 index.html(通过浏览器构建版引入 Tailwind,参见参考资料/stack-setup.md)。
    • 应用或多屏界面:使用 Vite 上的 React + TypeScript + Tailwind v4。
    • 用户提到 Next.js、SSR 或路由:使用 Next.js App Router。
  2. 编码前先写一份简短规格说明。 查看图片并记录:

    • 从上到下的布局区域(导航栏、主视觉区、侧边栏、网格、页脚),以及每个区域的网格或弹性布局结构
    • 设计令牌:3–6 种十六进制颜色、推测的字体系列和字号比例、间距节奏(通常为 4px 的倍数)、圆角半径、阴影样式
    • 重复组件(卡片、列表行、按钮),这些组件应使用带属性的单个组件
    • 图片无法体现的内容:悬停和焦点状态、移动端布局、真实数据、首屏以下的内容

    根据图片分辨率估算尺寸。如果截图是 2 倍图(例如,宽度为 2880px 的 Retina 截图对应 1440px 的布局),则将像素测量值减半。

  3. 构建。 使用语义化元素(header、nav、main、section、button、a),将重复部分提取为组件,并将设计令牌集中在一处(Tailwind v4 的 @theme 或 CSS 自定义属性),而不是到处散布十六进制颜色。使用图片中的真实文字,不要用 lorem ipsum。对于无法提取的图片和徽标,使用带有描述性 alt 文本的定尺寸占位符。使用项目已有的图标库(默认:lucide-react),不要手绘 SVG 或使用表情符号。

  4. 实现响应式布局。 首先针对截图视口构建,然后定义布局如何收缩:多列网格改为堆叠,导航栏改为菜单按钮,并使用 clamp() 或响应式工具类缩小字号。如果截图是移动端,则反向处理。

  5. 渲染并比较。 如果可以运行浏览器(Playwright、无头浏览器或浏览器工具),请在源图片的视口宽度下截取结果,并排比较。参见参考资料/visual-check.md。先修复最大的差异:布局和对齐,然后是间距,再然后是字号和字重,最后是颜色。通常迭代两三次就足够;当剩余差异仅在字体渲染层面时即可停止。

  6. 交付。 提供文件、运行方式以及简短的假设清单(推测的字体、补充的状态、推断的内容)。注明任何需要真实资源的部分。

技术栈说明

  • React 19:使用带 TypeScript 属性类型的函数组件。React 19 已移除 propTypes 检查;不要添加它们。向函数组件传递 ref 时不需要使用 forwardRef。
  • Tailwind CSS v4:配置位于 CSS 中。使用 @import "tailwindcss"; 和 @theme { --color-brand: #...; },不要使用 tailwind.config.js,也不要使用 v3 的 @tailwind base/components/utilities 指令。自定义令牌会自动成为工具类(bg-brand)。
  • Next.js(App Router):页面位于 app/ 中,组件默认是服务端组件。只有使用状态、效果或事件处理程序的组件才添加 "use client"。
  • Create React App 已弃用。纯 React 项目请使用 Vite。

各技术栈的设置命令请参见参考资料/stack-setup.md。

完整示例

输入:一张宽 1440px 的定价区域截图——居中标题、三张方案卡片(中间一张突出显示)、功能清单,以及每张卡片上的一个按钮。

规格:

  • 区域:标题区块,接着是 3 列卡片网格,最大宽度约 1100px,间距 24px
  • 设计令牌:背景色 #0B1220,卡片色 #111A2E,强调色 #3B82F6,文字色 #E5E7EB,弱化色 #94A3B8;类似 Inter 的无衬线字体;圆角 12px
  • 组件:PlanCard,包含 name、price、features[]、highlighted、cta
  • 未知项:悬停状态、月付/年付切换行为、移动端布局

构建:创建 PricingSection.tsx,将 plans 数组映射为 PlanCard;highlighted 会添加强调色边框和“最受欢迎”标签;使用 grid-cols-1 md:grid-cols-3。勾选图标使用 lucide-react。

比较:首次渲染的卡片高出 40px,原因是按钮内边距过大;标题字重为 600,而截图中是 700。修正两处后重新渲染,并附上假设列表:未实现切换功能,字体按 Inter 处理。

失败模式

  • 猜测技术栈,而仓库已定义技术栈;或在 v4 项目中混用 Tailwind v3 配置。
  • 使用绝对定位强行匹配像素。 窗口一调整大小就会出问题。使用 flex 和 grid,并接受细微差异。
  • 所有内容都塞进一个组件。 任何重复三次的内容都应抽成带 props 的组件。
  • 忽略不可见状态。 即使截图看不到,按钮和链接也需要悬停及 focus-visible 样式。输入框需要标签。
  • 颜色偏差。 从图像的纯色区域取样,而不是从抗锯齿边缘或渐变取样,并检查文字对比度是否符合 WCAG AA(正文文字为 4.5:1)。
  • 没看过效果就声称匹配。 如果无法渲染结果,就说明未进行比较。

评论

支持 Markdown