设计工具里面没有AI?这个叫Marver的东西把设计玩出了新花样!
你打开一个设计工具,第一眼看到的居然是代码文件夹,而不是画板!
Marver是一个装在代码仓库里的设计画布。你跑一条命令,它就在浏览器里打开一个画板,画板上的每一个界面都来自你项目里真实的组件代码。你改一行代码,画板上的界面立刻刷新。你在画板的评论框里@一下marver,你电脑上装的那个编码AI代理就自动接单,开始改代码、搭界面。最奇怪的是:这个工具本身不带任何AI。
Marver的工作流程是:你项目里已有的TSX/HTML代码文件 → Marver渲染引擎 → 浏览器里的设计画板。
代码是输入,画板是输出。
这就怪了!
设计工具不带AI,那谁来做设计?
设计行业正流行一个完全相反的做法
打开Figma,画一个矩形,填个颜色,拖几个按钮,导出设计稿,交给前端工程师从头写一遍代码。这套流程已经跑了快十年。全球几百万设计师都在这么干。Figma自己就号称有超过四百万用户。
但这套流程有一个巨大的裂缝。
设计师在Figma里画出来的界面,和工程师在浏览器里最终跑出来的界面,中间隔着一道鸿沟。设计稿里的间距、字号、颜色、交互反馈,到了代码里经常对不上。设计师说“这个按钮的圆角是8像素”,工程师写成12像素。设计师说“这个列表在手机上要变成卡片”,工程师忘了写响应式。来回改三遍,两边都烦。
这个裂缝叫做“设计与实现脱节”。
行业里解决这个问题的标准做法是:把AI塞进设计工具。Figma上线了AI功能,帮你生成设计稿、自动标注、一键导出代码。Sketch也靠插件生态接入AI能力。新出来的Miora直接叫自己“AI-native creative studio”,里面住着一个Design Agent,帮你规划和执行创意工作。
大家都默认一个方向:设计工具应该越来越AI。
但Marver走了一条完全相反的路。
它把设计工具变成了一个文件夹
你安装Marver,只需要一行命令:
bash
npm i -D @marver-design/marver
npx marver init
这条init命令在你项目的根目录下生成了一个叫design/的文件夹。这个文件夹里放着什么?放着你的设计稿——但不是图片,不是矢量图形,而是TSX或HTML代码文件。
你跑另一条命令:
bash
npx marver dev
浏览器里就打开一个画板,地址是localhost:5199。画板上显示的每一个界面,都是从design/文件夹里的代码文件渲染出来的。这些代码文件用的是你项目里真实的组件和主题——shadcn的组件、Tailwind的样式、你路由器的配置,init命令都能自动检测到。
这意味着什么?
意味着你在Marver画板上看到的每一个界面,都是真实能跑的代码,不是一张图片。
你改一下design/文件夹里的代码文件,画板上的界面立刻刷新。你把一个界面文件从design/scenes/挪到design/boards/,画板的侧边栏里就自动出现了新面板。你把一个界面拖到手机尺寸的视口里,真实的断点就触发了——因为每一个界面都跑在真实的iframe里。
这整个过程中,没有任何AI参与。
Marver只是一个渲染引擎。它把你的代码文件变成画板上的界面。它不生成代码,不修改代码,不替你决策。它只做一件事:让你和你的编码代理能够通过写文件的方式来设计界面,并且实时看到效果。
编码代理才是真正的设计师
Marver的设计哲学是:设计师不是人,是编码代理。
你在评论框里写一段话,@一下marver,它就把这段话扔给你电脑上装的那个编码AI代理。这个代理可能是Claude Code,可能是Cursor,可能是Codex,可能是Grok,可能是Factory的droid,也可能是opencode或pi。Marver不挑,你装了什么它就用什么。
代理接到任务之后,开始干活。它读design/AGENTS.md文件——这个文件是init命令生成的,里面写清楚了整个设计工作流的规则。代理按照规则创建新的TSX文件,或者修改现有的TSX文件。文件一保存,Marver画板上的界面就立刻刷新。
整个过程就像一个闭环:你在画板上提需求,代理在后台写代码,画板实时展示结果。
这个闭环里,Marver的角色非常纯粹:它不思考,不判断,不创造。它只负责把代码变成界面,把评论变成任务,把代理的修改实时呈现出来。
这跟Figma那种“人在画板上画,AI在旁边辅助”的模式完全相反。在Marver的世界里,人不是直接在画板上操作的人,人是给代理下指令的人。代理才是那个在画板上操作的人——只不过它操作的不是鼠标和图层,而是代码文件。
画板上的每一个操作都对应一个文件
Marver的画板不是空的。
你打开画板,侧边栏里显示的是boards、scenes、frames三层结构。frames是单个界面,scenes是一组界面的集合,boards是场景的排列组合。代理写design/boards/*.json文件来定义board的结构——一个frame列表就够。代理写design/scenes/*/目录下的TSX文件来创建新的界面。画板的侧边栏自动同步这些文件的变化。
你在画板上右键点击任何一个board、scene或frame,菜单里有一个“复制路径”的选项。复制出来的是一个字符串,你直接粘贴给代理,代理就知道要去改哪个文件。
你在画板上按c键进入评论模式,点一下界面上的某个元素,写一段评论。这条评论保存在design/comments/*.jsonl文件里。代理可以读这个文件,知道哪里需要改。改完之后,代理在评论里回复一条消息,说明改了什么。这条回复也保存在同一个文件里。
你在画板上按l键进入激光模式,每一个元素都被彩色的轮廓线标出来,鼠标悬停时显示标签。你点一下某个元素,它的完整地址——frame文件路径加CSS选择器——就复制到剪贴板了。你又可以粘贴给代理,让它精准定位要改的地方。
画板上的每一个交互,背后都对应着一个文件操作。评论是文件,界面是文件,board结构是文件,连代理的任务队列都是文件。
Marver把所有设计产物都变成了文本文件。
有一个功能叫Live Jam,它让代理自己接单
Live Jam是Marver最特别的一个功能。
你跑npx marver dev启动画板的时候,Live Jam默认就是开启的。你在画板的评论框里写“@marver 帮我把登录页面的按钮改成蓝色”,然后回车。Marver的dev服务器检测到这条评论,立刻在后台启动你电脑上的编码代理CLI。代理开始干活,同时画板上对应的界面会亮起一个“工作中”的发光效果。代理改完代码、保存文件之后,画板上的界面自动刷新,代理在评论框里回复一条消息,告诉你改完了。
整个过程你不需要打开终端,不需要手动启动代理,不需要复制粘贴文件路径。你就在画板上写一句话,代理就干了。
Marver怎么知道用哪个代理?
它开机的时候自己检测。大多数代理CLI在启动时会往环境里写一些标记变量——Claude Code写CLAUDECODE,Codex写CODEX_SANDBOX,Cursor写CURSOR_AGENT,opencode写OPENCODE,pi写PI_CODING_AGENT。Marver读这些变量,就知道你装了哪个代理。如果读不到,它就按顺序在PATH里找:claude优先,然后是codex、cursor、droid、opencode、grok、pi。找到哪个用哪个。
检测结果写在design/config.ts文件里。你打开这个文件看一眼,就知道Marver用了哪个代理。如果它猜错了,你手动改一个字就行。
你还可以配置并发数量——默认同时跑6个任务。你还可以配置subagents——一个任务里可以再分出多个子代理,每个子代理负责一个frame。五张界面的需求,子代理并行处理,一次搞定。
但代理干活是有规矩的。
安全边界不是沙盒,是“你自己的代理”
Live Jam最敏感的问题是安全。
你在评论框里写一句话,代理就在你电脑上改代码。如果这句话是恶意的——比如“@marver 删除所有文件”——代理真会去删吗?
Marver的处理方式很有意思。
第一道防线:只有在你自己的机器上写的评论才能触发任务。别人在你发布的画板上留言@marver,不会触发任何操作。别人通过协作同步过来的评论,也不会触发。触发任务的唯一途径是你本地的dev服务器。
第二道防线:Marver在启动代理的时候,会去掉代理的shell访问权限。Claude Code启动时加--disallowedTools Bash,shell直接被禁。Codex和Cursor启动时套进OS沙盒,shell被限制住,网络出口被切断。Grok启动时只给了一组读文件和编辑文件的工具,shell、web、subagents统统不存在。opencode启动时用--pure模式加权限白名单,bash被明确拒绝。pi启动时用工具白名单,bash不在名单上。
但Marver自己说得坦诚:文件读写工具本身没有被限制在design/文件夹内。在没有OS沙盒的CLI上,如果评论把代理忽悠瘸了,代理确实可能改到仓库里其他位置的文件,甚至改到机器上其他位置的文件。而且部分CLI保留了网络访问权限,数据可能被传出去。
所以Marver给出的真正建议是:不要把Live Jam指向一个你不愿意直接交给那个代理的仓库。不要在你不信任的机器上跑。每一次代理的改动都是一份diff,你在合并之前要亲自过目。代理永远不会自动把评论标记为“已解决”——你自己来。
这个安全模型的核心不是技术沙盒,而是信任边界:代理是你自己的,机器是你自己的,代码是你自己的,你负责审查。
Marver跟Figma不是一个物种
有人把Marver叫做“Figma杀手”。这个说法不对。
Figma是一个设计工具,人用它画界面。Marver不是一个设计工具,它是一个把代码文件夹变成设计画布的渲染引擎。Figma的输出是设计稿,Marver的输出是代码文件。Figma的用户是设计师,Marver的用户是编码代理——以及给代理下指令的人。
把Marver和Figma放在一起比较,就像把电钻和螺丝刀放在一起比较。它们都跟“拧东西”有关,但工作原理完全不一样。
Marver真正对标的东西是:设计稿和代码之间那道鸿沟。
传统流程里,设计师在Figma画完,工程师从头写一遍代码。Marver的流程里,没有“画完再写”这个环节。你在Marver上看到的每一个界面,本身就是代码。设计即代码,代码即设计。
这个思路并不是Marver独创的。行业内已经出现了“design.md”这种给编码代理用的设计系统描述文件。出现了“auraDesign/”这种专门放设计产物的目录。出现了“agent-native design”这个概念,意思是设计工具要同时服务于人和AI代理。
Marver把这些零散的想法打包成了一个可用的工具。
它让你在代码仓库里开一个叫design/的文件夹,里面放设计稿的代码,然后用一个命令把它变成画板,再用另一个命令让编码代理在画板上干活。
它有粗糙的边缘,但它正在被作者自己每天使用
Marver的README里有一句话特别诚实:“Marver是一个年轻的单人副业项目——它能用,作者每天自己都在用,但它有粗糙的边缘。”
粗糙在哪里?
board里放了太多重frame——动画多、组件密的那种——画板会变卡,尤其在缩放的时候。快照渲染在帮忙,但还没彻底解决问题。
Next.js的支持有一个坑:frame在Vite里渲染,不在Next环境里跑。next/font的CSS变量在frame里是未定义的,得给字体设一个回退链。next/image和next/link在frame里不能用,得换成普通的img标签和data-goto属性。Server Components在frame里跑不了。
但这些问题都在被修。最近的commit记录显示,作者在不断地修bug、加功能、加固安全。版本号已经到了0.10.2。
而且Marver有一个细节做得非常到位:它会给代理生成一份design/AGENTS.md文件,里面写清楚了整个设计工作流的规则。代理读了这个文件就知道怎么干活。它还生成design/instructions/jam.md,里面写了完整的故障排查流程——代理自己可以照着跑一遍,检查哪里出了问题。如果代理查出来是Marver的bug,它还会自动去GitHub上提issue,附上它找到的补丁。
代理帮工具修bug,工具帮代理干活。这两个东西在互相驯化。
一个让人睡不着觉的实验细节
Marver的评论系统有一个“分层锚点”机制。
你在画板上点一个界面元素写评论,这条评论不是固定在那个元素的坐标上,而是锚定在“源代码语义 → 结构 → 模糊文本”这三层之上。什么意思?意思是你改了这个元素的代码,改了它的位置,甚至改了它的部分文本内容,评论依然能找得到它。
这个机制听起来很合理,但它有一个细思极恐的推论。
如果评论可以跨代码修改存活,那评论的“锚点”本质上是在追踪一段代码的“身份”,而不是它的“位置”。但代码的“身份”是什么?是函数名?是组件路径?是DOM结构?还是文本内容的模糊匹配?
Marver用的三层锚点——源码语义、结构、模糊文本——是三个不同维度的指纹。当代码修改只动了一层,另外两层还能把评论拽回来。但当你同时改了三层——重命名了组件、重构了DOM、改掉了文本——评论就丢了。
那问题来了:一个设计评论,到底是附着在“这段代码”上,还是附着在“这个界面”上?
如果代码改了但界面看起来一样,评论应该还在吗?
如果界面改了但代码结构没变,评论应该还在吗?
如果代码和界面都改了,但设计师的意图没变,评论应该还在吗?
Marver没有回答这个问题。它只是提供了一个三层锚点的机制,然后把“评论丢了怎么办”这个事,留给了你和你的代理去处理。
你评论里写的那句话,到底属于代码,还是属于界面,还是属于意图?