D2C:前端的自我革命

首页 编程分享 JQUERY丨JS丨VUE 正文

林陌青川 转载 编程分享 2025-06-03 20:13:41

简介 ## 序言 ​ 这半个月一直在专注于 Figma-to-Code 的相关工作,也在不断思考和调研已有的 D2C(Design to Code)方案。 ​ 目前市面上主流的实现方式,大多是基于 **


序言

​ 这半个月一直在专注于 Figma-to-Code 的相关工作,也在不断思考和调研已有的 D2C(Design to Code)方案。

​ 目前市面上主流的实现方式,大多是基于 Figma 插件,通过插件调用 Figma 的 Open API 获取设计稿的结构和样式信息,再转换成对应的 DSL(中间描述语言),最终通过渲染引擎生成各端代码。也有一些方案尝试通过设计稿的截图,结合视觉识别算法实现 0 到 1 的生成,但这种方式在还原度和一致性方面存在明显短板,难以满足生产需求。

​ 这几天阅读了大量相关资料,包括公司内部方案,也参考了外部团队的一些实践。其中印象较深的有:

  • 网易云音乐技术团队的 海豹 D2C:提出了基于 DSL + 引擎驱动的完整设计转码链路,思路清晰,落地程度较高。
  • 字节跳动的 Semi Design:虽然更偏向组件体系,但其设计-开发一体化理念、设计规范约束和配套工具链也对 D2C 体系建设有很强的借鉴意义。

总体来看,D2C 的核心逻辑可以归纳为三步:

  1. 解析设计稿:通过 Figma Open API 提取结构与样式;
  2. 转换为 DSL:构建平台无关的中间描述层;
  3. 生成端代码:通过模板或引擎渲染出对应平台代码(Web / Native / Flutter 等)。

​ 虽然整体流程逐渐清晰,但受限于 Figma 本身的表达能力、设计规范一致性、插件能力边界等因素,还原度始终是当前最大的挑战,尤其在复杂交互、自适应布局、组件语义识别等方面,仍有大量细节需要补齐。

Figma API中的信息

节点类型

节点类型 说明
FRAME 框架,是Figma中最常用的容器节点(也可作为画板)。可嵌套其他节点。
GROUP 分组,用于逻辑上组合多个元素,不具备 Frame 的布局功能。
RECTANGLE 矩形,最常见的形状元素。
ELLIPSE 椭圆或圆形。
LINE 直线。
POLYGON 多边形。
STAR 星形。
VECTOR 矢量路径(Pen 工具画出的路径)。
TEXT 文本元素。

节点属性

🧱 通用基础属性(所有节点都具有)

属性 类型 说明
id string 节点的唯一 ID。
name string 节点的名称。
type string 节点的类型,如 "FRAME""TEXT" 等。
visible boolean 节点是否可见。
locked boolean 是否锁定节点。
parent BaseNode null
removed boolean 是否已从文档中移除。只读。
children SceneNode[] 子节点数组(如果节点支持包含子节点)。

🖼️ 通用场景属性(大多数可视节点具有)

属性 类型 说明
x, y number 节点相对于父节点的位置。
width, height number 节点的尺寸。
rotation number 旋转角度(度)。
relativeTransform Transform 节点相对于父节点的变换矩阵。
absoluteTransform Transform 相对于画布的变换矩阵。
constraints Constraints 自动布局的约束条件。
layoutAlign string 在自动布局中的对齐方式(如 "STRETCH""CENTER")。
layoutGrow number 在自动布局中是否可扩展。

🎨 图形样式属性(大多数图形节点具有)

属性 类型 说明
fills Paint[] 填充颜色、渐变、图片等。
strokes Paint[] 描边样式。
strokeWeight number 描边粗细。
strokeAlign string 描边对齐方式("CENTER""INSIDE""OUTSIDE")。
cornerRadius number mixed
opacity number 不透明度(0~1)。
blendMode BlendMode 混合模式。
effects Effect[] 阴影、模糊等效果。
isMask boolean 是否作为遮罩。
exportSettings ExportSettings[] 导出配置。

🔠 文本节点(TEXT)特有属性

属性 类型 说明
characters string 文本内容。
fontSize number mixed
fontName { family: string, style: string } 字体。
textAlignHorizontal string 水平对齐("LEFT""CENTER""RIGHT")。
textAlignVertical string 垂直对齐("TOP""CENTER""BOTTOM")。
lineHeight LineHeight 行高。
letterSpacing LetterSpacing 字间距。
textAutoResize string 文本自动调整尺寸方式。
textStyleId string 关联的文本样式 ID。

🧱 自动布局属性(如 FRAME, COMPONENT 等)

属性 类型 说明
layoutMode "NONE" "HORIZONTAL"
primaryAxisAlignItems string 主轴对齐方式。
counterAxisAlignItems string 交叉轴对齐方式。
itemSpacing number 子元素间距。
paddingLeft/Right/Top/Bottom number 内边距。

🧩 组件相关属性(COMPONENT, INSTANCE

属性 类型 说明
mainComponent ComponentNode INSTANCE 实例对应的组件定义。
componentPropertyReferences Record<string, string> 实例中引用的属性。
variantProperties Record<string, string> 组件变体中的属性值(在 COMPONENT_SET 中)。

全链路跑通

​ 大概用了半个月的时间,我们基于 Dify + MCP + LLM 的组合,成功打通了 D2C 的完整链路。相比市面上不少公司繁琐复杂的方案,我们的目标很简单:只做一件事——输入一个设计稿,输出所需的组件。

​ 是的,这就是我们第一阶段的 MVP。看似简单,但我们确实做到了端到端的打通。

​ 不过,现实也没有那么理想。由于底层技术方案还存在一些限制,尤其是在解析复杂结构、还原视觉细节等方面,当前方案在设计稿还原度上依然存在较大提升空间。这也是接下来需要重点攻克的方向。

​ Figma 在布局结构上的表达方式与传统 HTML 有着明显差异,尤其是在自动布局、约束关系等方面。因此,Figma API 提供的节点信息,往往无法直接映射为标准的 HTML 布局结构。

​ 在第一阶段,我们完成了从 Figma 设计稿到初步 HTML 结构的转换。随后在 HTML 向 React 组件的规范化转换中,我们进行了多轮迭代,并测试了多种大模型的表现。

​ 对比结果显示,Claude 4Gemini 2.5 Pro 在生成准确性和结构还原方面表现最优,明显优于其他同类模型。这也解释了为何一些 D2C 工具会选择集成 Claude 模型作为其底层能力——更强的代码结构理解力带来了更高的还原度和更少的人工干预。

D2C 已知痛点

1. 设计稿中存在无用图层

UI 设计师在设计过程中,往往会隐藏一些暂不使用或用于参考的图层。这些隐藏元素在视觉交付时无影响,但在解析 Figma 设计稿时仍然会被包含,导致我们在判断其是否应渲染时需额外处理层级、可见性等逻辑,增加了解析成本。

针对无用节点的排除问题,主要有两种可行方案:

  1. 人工标注:通过人工方式对设计稿中的无效元素进行标注与筛选,从源头减少冗余结构,但是会增加设计师工作量;
  2. 自动对比优化:结合大模型的图像理解能力,在 dify 流程中将设计稿作为图片输入,并与生成的 HTML 页面进行结构和视觉对比,从而自动调整 HTML 布局,优化输出结果。

2. 图层是否需要整体导出为图片

在遇到复杂图层结构(如多个图层交错、遮罩、混合模式等)时,直接还原为代码会增加实现难度和不确定性。此类场景下,若能自动识别并将其作为整体导出为一张图片,会显著简化开发流程。

graph TD
    A[开始 isSVG node] --> A1{是否有子节点};
    A1 -- 否 --> Z1[返回 false];
    A1 -- 是 --> B{是否有可见子孙节点};
    B -- 否 --> C[返回 false];
    B -- 是 --> D{isSVGOld 判断};
    D -- 是 --> E[返回 true - 作为 SVG 导出];
    D -- 否 --> F[返回 false - 不作为 SVG 导出];

    subgraph isSVGOld
        G[开始 isSVGOld node] --> H{名称包含 #no-merge#};
        H -- 是 --> I[返回 false];
        H -- 否 --> J{名称包含 #merge#};
        J -- 是 --> K[返回 true];
        J -- 否 --> L{是否基本图形类型};
        L -- 是 --> K;
        L -- 否 --> M{是否容器类型};
        M -- 否 --> I;
        M -- 是 --> N{子节点是否完全相交};
        N -- 是 --> O{所有子节点 isSVGOld 也为 true};
        O -- 是 --> K;
        O -- 否 --> I;
        N -- 否 --> P{所有子节点为 VECTOR 或 ASSET};
        P -- 是 --> K;
        P -- 否 --> I;
    end

    Z1 --> Z[结束];
    C --> Z;
    E --> Z;
    F --> Z;


3. 无响应式布局信息

Figma 原生输出的信息大多是基于绝对像素(px)的定位和尺寸,没有包含响应式布局的语义。这对需要适配不同屏幕的 Web 端开发非常不友好,若无后续处理,将导致导出的代码缺乏灵活性和扩展性。

总结

​ 周参与了公司内部关于 Figma 的邀请制会议。Figma 官方计划在未来几个月正式发布 MCP,这意味着相较于我们当前基于第三方方案所开发的 MCP,官方版本在还原度、交互细节及整体稳定性方面将具有显著优势。这也意味着,我们近期投入的相关工作很可能在未来被替代。

​ 尽管如此,这段过程依然收获颇丰。通过实践,我不仅深入理解了设计到代码转换的技术路径,也重新激发了初学时那种不断探索与攻克难点的热情。某种程度上,这段经历更像是一场自我打磨与能力进阶。

转载链接:https://juejin.cn/post/7510151175678296079


Tags:


本篇评论 —— 揽流光,涤眉霜,清露烈酒一口话苍茫。


    声明:参照站内规则,不文明言论将会删除,谢谢合作。


      最新评论




ABOUT ME

Blogger:袅袅牧童 | Arkin

Ido:PHP攻城狮

WeChat:nnmutong

Email:nnmutong@icloud.com

标签云