跳到正文
Hacker News· handfuloflight·· 6 天前AI 评分66

Anatomy:让 Claude Code 把抽象概念画成可交互机械装置的技能

Anatomy · a Skill for Claude Code

AI 导读

作者发布 Anatomy,一个 Claude Code 技能,输入一行想法即可让 Claude 自行发明一台能体现该概念的机械装置,并绘制成可旋转、按压、读取数据的等距交互图。

正文 · AI 翻译

用一行字说出一个想法,Claude 就会画出实现它的机器。

Watch movementDesk computerHash map collisionsTemperatureBloom filter

大多数解释某物如何运作的方式都是用方框和箭头画出来的。它们告诉你各个部件存在,却不告诉你这些部件做什么,读者只能自己想象箭头所代表的运动。我希望 Claude 画出事物本身:一个真实的物体,其运动部件的行为方式与这个想法一致。

Anatomy 是 Claude Code 的一项技能,正是做这件事的。你用一行字说出一个想法,Claude 发明一台实现它的机器,并把它画成一个可实时交互的等轴测图形,你可以旋转、按压和阅读。每个图形都由几十到几百个小实体部件组成,它显示的每一个数字都来自驱动它们运动的同一个模型。

向上拖动表冠上弦S慢速E拆开

这是一个机械表机芯。它来自一行字,/anatomy explain how a mechanical watch keeps time, interactive,以及 Claude 独自工作不到两小时。1活跃时间一小时五十四分钟,一次构建完成,并由同一个智能体检查。

向上拖动表冠给它上弦:棘轮转动,棘爪咔哒作响,动力储备上升。按 S 把时间放慢到二十分之一,再按一次到百分之一,你就能看到擒纵叉让十五齿的擒纵轮一次只过一个半齿。按 E 把夹板抬开,看到下面的轮系,它的轮子按真实传动比切削:四轮每分钟转一圈,中心轮每小时转一圈。

这项技能基于一条规则,写在它指令的最上方,高于一切:

物体本身就是解释。SKILL.md,“唯一重要的想法”

没有方框,没有箭头,没有漂浮在空中的标签。Claude 必须发明一个真实、制作精良的东西,其运作就是这个概念,并用一句话说明什么在动以及这种运动意味着什么。

一个图形会以两种方式失败,在这条规则存在之前,我多次看到它以这两种方式失败。太抽象:堆叠的板、漂浮的块和贴了标签的方框,读起来什么也不像。太扁平:一整块大板,上面画几条线,没有体积,没有部件,没有什么可发现的。两者的解药是一样的:一台由许多小部件构成的可辨认的机器,每个部件都各司其职。2机器从不照参考图复制。参考图可以提供表面处理、材质和氛围;物体是发明出来的。

有些想法几乎能自行对应。队列就是一条弹珠轨道:两个料斗供给一条倾斜的通道,弹珠在一个擒纵机构后面按顺序等待,直到一个定时滚筒把它们带走。一个会遗忘最旧条目的缓存是一个书架,顶部有四个位置,最近使用的在左边。其他的则需要更多发明。布隆过滤器是一台水果机,它的三个转轮就是三个哈希函数,只有当某个词的三面旗标都已竖起时它才会派彩。

这些都不是手绘的。每一个都从一行命名该想法的文字开始。目前共有 33 个,全部在合集中实时运行。

提示词是想法,而不是图画。我几乎从不说该画什么。“解释 LRU 缓存如何逐出条目”就够了,而决定它应该是一个书架,正是要求 Claude 去做的部分。

有三个词会改变你得到的结果,只有当你把它们写进那一行时,Claude 才会去用它们:

interactive图形会响应指针和键盘:拖动、按下、按住某个键。省略这些,你得到的只是一幅静止的图画。
WebGL火焰、水、等离子体、流动的空气和光的着色器,绘制在与部件相同的等距相机内。
3D真正在深度上转动的部件,每一帧都重新投影和重新排序,而不是仅仅看起来是等距的。慢:需要数小时来构建,而不是几分钟。

如果你已经知道这个物体,就说出它的名字,并附上任何重要的真实数字。如果图形要去某个特定的地方,就说明是哪里。该技能会编写不依赖框架的 TypeScript,输出 SVG 和 HTML,或为 Next.js 网站输出 React 组件,支持深色或浅色主题。

你并不总是需要命令。该技能的描述涵盖了任何对解释性图表、技术插图或交互式讲解的请求,即使请求中从未提到“等距”,所以 Claude 会自行使用它。3在请求匹配之前,Claude 只能看到技能的名称和描述。它只在需要时才读取其余部分。

从你的描述到完成的图形,Claude 会按照固定的顺序进行。大部分质量在前四步就已决定,那时还没有任何几何图形。

  1. 确定规模。 一开始就说明这是 Figure、Hero 还是 Epic,以及大致需要多长时间。

  2. 真实优先。 收集真实的数字和行为,并将它们写成一个小模型,让运动和读数都从中读取。

  3. 发明物体。 一台其机制与想法一一对应的机器。

  4. 列出部件。 至少四十个,分为底座、结构、机制、控制装置和一个被照亮的主题。每个都位于另一个之上。

  5. 规划世界。 世界单位,平面用圆角矩形和圆形表示,一个相机,然后适配到卡片。

  6. 一次性构建几何图形。 每条静态路径都提前计算好。运动部件在静止状态下构建,然后移动。

  7. 从后到前绘制。 按深度排序,包裹部件一分为二,一旦密集就通过审计来证明顺序。

  8. 装框。 一张带有标题、交互提示和实时读数的卡片。文字不进入绘图。

  9. 让它活起来。 平静的、基于时间的运动,空闲巡览,指针和键盘,以及在减少动态效果下保持静止。

  10. 像评论家一样验证。 截图、联系表、四倍裁剪和两次自动检查,直到没有需要修复的地方。

第二步在实践中是这样的。测试装置是该技能的一个示例,它解释了玻璃按钮如何在手指下膨胀和倾斜,其整个行为都存在于一个小型弹簧模型中。部件、读数、屏幕阅读器文本和说明文字都从中读取,因此它们不可能相互矛盾。

rig.ts

function spring(held: Spring, want: number, dt: number, [stiff, drag]: Tuning, calm: boolean) {
  const damping = calm ? 2 * Math.sqrt(stiff) : drag;
  const steps = Math.max(Math.ceil(dt * SUB_RATE), 1);
  const slice = dt / steps;
  for (let step = 0; step < steps; step++) {
    held.rate += (want - held.at) * stiff * slice - held.rate * damping * slice;
    held.at += held.rate * slice;
  }
  if (Math.abs(want - held.at) < QUIET && Math.abs(held.rate) < QUIET) {
    held.at = want;
    held.rate = 0;
  }
}

还有第六步。表盘指示器是最小的示例,从它的底座开始:四个按深度顺序排列的车削支脚,一块带斜面的板,一个距边缘五单位的内嵌凹槽,以及每个角上带环的螺丝。其中每一个都是套件中的实体,而不是手工绘制的线条。

build.mjs

function plate() {
  const out = [`<path class="iso-halo" d="${k.haloOf(PLATE, -PLATE_H - FOOT_H, PLATE_H, P)}"/>`];
  for (const [x, y] of byDepth(k.corners(PLATE, 22))) {
    out.push(S(k.cylinder(x, y, 7, -PLATE_H - FOOT_H, 1.6, P, 28), { tone: "lo" }));
    out.push(S(k.cylinder(x, y, 5.4, -PLATE_H - FOOT_H + 1.6, FOOT_H - 1.6, P, 28), { tone: "mid" }));
  }
  out.push(S(k.slabOf(PLATE, -PLATE_H, PLATE_H, P, 8, 1.6), { tone: "mid" }));
  out.push(L(k.planOutline(k.insetPlan(PLATE, 5), 0, P), { tone: "lo" }));
  const screws = k.corners(PLATE, 10);
  out.push(L(screws.map(([x, y]) => k.ring(x, y, 2.2, 0, P, 16)).join(""), { tone: "lo" }));
  out.push(D(screws.map(([x, y]) => at([x, y, 0])), { size: 0.5 }));
  return out.join("");
}

第一步设定预算。每个请求都属于三种规模之一:

规模包含内容时间
Figure40–80 个部件,SVG,最多一个着色器30–90 分钟
Hero80–150 个部件,多个着色器或一个转动部件2–4 小时
Epic整个车辆、建筑或工厂6 小时或更长

Figure 是直接做出来的。Hero 则先公布,再做出来。Epic 绝不会在没有你的情况下启动:Claude 给出估算,提出一个保留想法核心的 Hero,并列出完整版本会增加什么。4无论规模大小,第一个小时内浏览器里就会有一个可用的页面。剩下的时间都用来深化它。

每个 figure 都遵循相同的绘制规则。正是这些规则让它读起来像一件坚实的、做出来的东西,而不是一张草图。

一台相机
等轴测,从一个角向下看 30°。没有透视,所以平行边保持平行。
实体
每个部分都按顺序填充和上色,所以前面的会遮住后面的。没有透视边缘。
四种色调
每一面根据它朝向光的方式着色,顶部更亮。
一个强调
恰好有一个部分被点亮:读者应该关注的那个。
线条收束
每条线都终止于一个面、另一条线或一个点。没有引线、标注框或箭头。
4× 下的细节
正常尺寸下它读起来像一台机器。放大后,每个区域仍然有真实的东西可发现。
内部无文字
文字围绕在绘图周围,绝不放在图上,最多只有一个微小的雕刻标签。
真实数字
每个读数都来自驱动这些部件的模型。

Figure 也是一个小程序。没人触碰时它会播放一段空闲导览,当你悬停或聚焦时暂停,响应指针和键盘,滚出屏幕时停止,在减少动态效果时保持静止。它的读数在变化时会向屏幕阅读器播报。

在它自己的页面上,figure 位于一张卡片中,四个角分别是它的编号、标题、提示和实时读数。在这个网站上,我把提示和读数移到了每个 figure 旁边的页边距里,这样绘图就能独自立在页面上。

这个合集最好一次读一台机器。每个名字先点出想法,然后是 Claude 为它选择的对象;打开一个来玩一玩。

  • 哈希映射冲突

    分拣台

    哈希映射把每个键归档到一个桶里,落到同一个桶里的键会堆叠起来。一个邮局分拣台。一台编码机打印每个字母的桶号,即其名称哈希值 mod 8,并把它归入那个鸽巢,放在已有字母的上面。

  • 布隆过滤器

    水果机

    布隆过滤器可以确定地说“绝对没有”,但只能说“也许”有。一台水果机。三个转轮是三个哈希函数,一排十六个标志是位数组;只有当某个单词的三个标志都已亮起时它才会出奖。

  • 互斥锁

    水箱与钥匙

    两个写入者同时读取同一个值,都会基于过时的数字行动。一个由两台泵注水的水箱。没有互锁钥匙时,两个控制器读到相同的水位并把它注得过满;有了它,只有持有钥匙的那个才能读取和运行。

  • TCP 握手

    邮件索道

    在任何数据移动之前,两端都必须同意对方在监听。两个站点之间的邮件索道。挂着 SYN、带 ACK 旗的 SYN、然后是 ACK 的罐子沿绳索飞过,每个站点的信号机显示其连接状态。

  • 温度

    轮盘

    温度重塑下一个 token 的概率,但不改变哪些 token 是可能的。一个轮盘,其十六个口袋是最可能的下一个 token,每个的宽度等于其概率。一个恒温器旋钮设定温度并移动档格。

  • 防抖、节流

    八音盒记录器

    防抖等待安静下来;节流在每个窗口内只放行一次调用,无论到达多少次。 一台带旋转销盘的八音盒录音机。旋钮的每一次咔哒都是一次调用;节流和防抖阻尼器各自设定自己的销钉,因此你可以读出每个函数实际运行的时间。

每次的模式都一样。对象必须做出这个想法,而不是代表它,所以你看着移动的东西就是被解释的东西。

小想法造小机器。大想法才是技艺真正体现价值的地方:数百个零件、真实的工程数字,以及存在于绘图内部而非覆盖其上的着色器。

拖动 ↔ 推力空格起飞

一台劳斯莱斯 Trent 970,A380 的发动机,悬挂在地面试车推力架上,其靠近观察者的上四分之一被剖开。拖动操纵杆,风扇、中压和高压转子以各自的速度旋转起来。风扇每秒吞入 1.2 吨空气,其中大部分作为冷涵道射流排出,其余在燃烧室中燃烧,测力传感器显示推力从 14 攀升到 334 kN。按空格键进行起飞滑跑。5审计测量了 541 个实体中 6,320 对重叠对,发现每一对都按正确顺序绘制。

悬停或 ← → 拆解I点火Esc合拢

Raptor 2,SpaceX 的全流量分级燃烧发动机,悬挂在试车台上。它是这门技艺自身的示例之一,也是密集管路的参考。悬停它,它会拆解成十一个组件,从万向架到喷管;按 I 点火。每一滴氧气都经过一个富氧预燃室驱动氧气泵,每一滴甲烷都经过一个富燃预燃室驱动甲烷泵,两股热气在主燃烧室中以 300 bar 相遇。6羽流、激波、飞溅和水蒸气是 WebGL,绘制在背面和正面 SVG 之间,因此试车台从火焰前方经过。

第一个可运行的版本花了 38 分钟。把它做对又花了十个小时,现在一次审计证明没有任何管路穿过任何东西,无论是在静止状态、拆解状态,还是其间的每一帧。

大多数图形是纯 SVG。当一个想法需要火、水、等离子体或光时,Claude 会添加以同一等距相机绘制的 WebGL 着色器,因此火焰位于绘图内部而非覆盖其上。少数图形更进一步,在真正的 3D 中旋转。

SVG。 手表仅用 SVG:四个音调按朝向区分,以及一个画家顺序,在其桥板拆开时每一帧都重新求解。它只重绘移动的部分。

WebGL。 涡扇添加了一个画布,用于进气条纹、涵道风、燃烧室火焰、涡轮辉光和排气。每个值都遵循一条包络线,因此没有任何跳变,读数也从不与画面矛盾。

3D。 Seasons 在真正的 3D 中旋转 26 个零件,每一帧重新投影,并用两个画布表现灯光。其读数来自 Almanac 的太阳公式:在北纬 50°,六月白昼持续 16 小时 22 分,十二月为 8 小时 04 分。73D 仍处于测试阶段。一个小的旋转图形以 60 fps 运行;一个密集的 380 零件测试手大约以 20 fps 运行。

细节需要时间,我宁愿展示真实数字而不是猜测。这些是 Claude 从第一个提示到最终成品图的活跃时间,包含评审轮次,不含空闲间隔。

Watch movement1 小时 54 分钟一遍完成,由同一个 agent 检查并修复。
Seasons1 小时 57 分钟与手表同时构建,包含 3D 审查。
Raptor engine10 小时 33 分钟38 分钟内完成第一个可用版本。
Turbofan14 小时首次构建用时 4 小时 41 分钟,之后经过五轮评审和修复。

整个系列都遵循这个规律。能运行的第一个版本很快就出来了。大部分时间花在第二遍审视上,以四倍的尺寸,去发现那些缺陷:穿过管道的线缆、分步着色的喷嘴、在切割处折成细条的叶片。

系列中的每个图形也是一个 React 组件,实时可用,可主题化,精细到其最后一条线的颜色。

npm install anatomy-figures

page.tsx

import { Watch } from "anatomy-figures";

export default function Page() {
  return <Watch theme="light" />;
}

每个图形都是独立入口,因此导入一个不会连带引入其他图形:

import Turbofan from "anatomy-figures/turbofan";

随附五种主题:dark、light、paper、blueprint 和 sepia。将其中一个作为 theme 传入,用 AnatomyTheme 为整棵树设置一个主题,或传入你自己的 --anatomy-* 令牌。本站上的图形是 light 主题,卡片颜色设为页面颜色。

page.tsx

import { AnatomyTheme, Turbofan } from "anatomy-figures";

<AnatomyTheme theme="paper">
  <Turbofan />
</AnatomyTheme>

<Turbofan theme={{ base: "light", "--anatomy-card": "#fafafa" }} />

每一个令牌。图形中的每个填充、线条和标签都读取这 26 个变量之一。在 tokens 中传入其中任意一个,或在主题对象中传入。它们设置在图形本身上,因此会覆盖来自外部的 CSS。

page.tsx

<Watch
  theme="light"
  tokens={{
    "--anatomy-card": "#ffffff",
    "--anatomy-lit": "#e5484d",
    "--anatomy-weight": "0.8px",
  }}
/>
LightDark令牌
表面
--anatomy-card图形背后的卡片。
--anatomy-paper每个实体下方的填充。保持与卡片一致。
--anatomy-top每个实体的顶面。
--anatomy-shade-0背向光源最远的侧面。
--anatomy-shade-1略微朝向光源的侧面。
--anatomy-shade-2大部分朝向光源的侧面。
--anatomy-shade-3正对光源的侧面。
--anatomy-face唯一受光部件的主体。
--anatomy-lit-top受光部件的顶部。
--anatomy-lit-shade受光部件的侧面。
线条
--anatomy-hi最强的线条:主体的轮廓。
--anatomy-mid结构、主刻度和雕刻标签。
--anatomy-lo底座、支脚和次要线条。默认线条。
--anatomy-faint凹槽和最淡的辅助线。
--anatomy-dot点阵网格和螺丝头。
--anatomy-halo底座下方和抬起部件下方的柔和阴影。
强调色与颜色
--anatomy-lit唯一的强调色:读者应该关注的部分。
--anatomy-red红色,仅用于颜色本身是主题的地方。
--anatomy-green绿色,同样如此。
--anatomy-blue蓝色,同样如此。
文字
--anatomy-text图形编号和卡片角落的实时读数。
--anatomy-muted角落的标题和提示。
--anatomy-strong图形绘制的最亮文字。
形状
0.6px0.6px--anatomy-weight每条线的宽度。
0.320.9--anatomy-halo-opacity柔和阴影的深浅程度。
ui-monospaceui-monospace--anatomy-mono角落和雕刻标签的字体。

不使用 React 时,每个图形也是一个自定义元素:

index.html

import { define } from "anatomy-figures/element/turbofan";

define();

<anatomy-turbofan theme="dark"></anatomy-turbofan>

用一条命令将技能添加到 Claude Code:

npx skills add wheresryan22/anatomy

或者下载该技能并解压到你的 skills 文件夹:

unzip anatomy.zip -d ~/.claude/skills

然后在你的项目中打开 Claude Code,请求任何能用的东西。说出想法,而不是画法。8该技能附带六个完整示例,从约 300 行的表盘量规到 Raptor engine,Claude 在开始前会打开最接近的那个。

Claude 非常擅长构建这些,但并不总是擅长看出它们的问题。它会针对一个数字上成立的图形进行优化,而一个部件可能每个数字都对,看起来却仍然不对。最重要的修正来自观看一个图形运转,并描述哪里感觉不对。

它做得好的时候很慢。这项技能要求每个图形至少四十个部件,并且不会自行为了速度而牺牲细节。如果你需要快速完成,请说明,并预期得到一个 Figure 而不是 Hero。

3D 是测试版。它一次只转动一个主体,而对一个转动图形进行完整审查需要十五到二十分钟,所以只有当某个部件确实需要在深度上移动时才值得要求它。

参考图用于营造氛围。给它一张照片,它会取用其质感,而不是其物体。忠实复制别人的画作并不是它的用途。

所以把第一个图形当作草稿。把玩它,注意哪里不对,说出来,然后再次要求。 我是如何构建它的 展示了这项技能本身的这个循环是什么样子。

它需要 React 吗?

不需要。这项技能编写无框架的 TypeScript,为任何页面输出 SVG 和 HTML,或者为 React 或 Next.js 站点输出 React 组件。集合中的每个图形也是一个自定义元素,你可以将其放入纯 HTML 中。

图形制作完成后我可以修改它吗?

可以。图形是你项目中的普通代码。要求 Claude 进行更改,或者自己编辑模型:部件、读数显示和运动都读取同一个模型,所以更改一个数字会带动所有内容随之改变。

它会让我的页面变慢吗?

图形在滚出屏幕时会停止,并且只重绘移动的部分。着色器仅在其效果处于活动且可见时渲染,设备像素比上限为 1.5,并且在减少动态效果模式下只绘制一帧静止画面。

它是否可访问?

每个图形都接受键盘焦点,并响应按键和指针。它的读数显示在变化时会被朗读给屏幕阅读器,并且在减少动态效果模式下会静止,同时仍然响应输入。

浅色还是深色?

两者皆可。无框架图形可在任一主题下构建,React 组件自带五种主题,或者采用你自己的颜色令牌。

我怎样才能获得最佳结果?

说出想法,添加你在意的真实数字,并在需要时使用那三个词。然后把玩第一个图形,说出哪里感觉不对,然后再次要求。大部分质量来自第二次审视。

许可证是什么?

MIT,适用于这项技能和这些图形。

  1. 1一小时五十四分钟的活跃时间,一次构建完成,并由同一个智能体检查。
  2. 2机器从不从参考图片复制。参考图可以提供质感、材料和氛围;物体是虚构的。
  3. 3在请求匹配之前,Claude 只看到技能的名称及其描述。它只在需要时才读取其余内容。
  4. 4无论规模大小,第一个小时内浏览器中都会有一个可运行的页面。其余时间用于深化它。
  5. 5该审查测量了 541 个实体之间的 6,320 对重叠,并发现每一对都按正确顺序绘制。
  6. 6羽流、冲击、飞溅和蒸汽是 WebGL,绘制在后置和前置 SVG 之间,因此支架会从火焰前方经过。
  7. 73D 仍是测试版。一个小型转动图形以 60 fps 运行;一个密集的 380 部件测试手大约以 20 运行。
  8. 8该技能附带六个完整示例,从约 300 行的千分表到 Raptor 发动机,Claude 在开始前会打开最接近的一个。
《创造亚当》,米开朗基罗,约 1512 年

来源:Hacker News · skills.wheresryan.sh