pmx-canvas 0.8.0 → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (341) hide show
  1. package/.github/extensions/pmx-canvas/runtime.json +1 -1
  2. package/.github/extensions/pmx-canvas/tools.json +601 -22
  3. package/CHANGELOG.md +66 -0
  4. package/Readme.md +131 -532
  5. package/dist/canvas/global.css +2759 -510
  6. package/dist/canvas/index.js +168 -107
  7. package/dist/canvas/mcp-app.html +2936 -632
  8. package/dist/json-render/index.css +81 -1
  9. package/dist/json-render/index.js +20 -20
  10. package/dist/types/client/canvas/BarHint.d.ts +12 -2
  11. package/dist/types/client/canvas/BoardLinkDialog.d.ts +3 -1
  12. package/dist/types/client/canvas/BoardPinButton.d.ts +10 -0
  13. package/dist/types/client/canvas/BoardSwitcher.d.ts +1 -1
  14. package/dist/types/client/canvas/CanvasViewport.d.ts +1 -1
  15. package/dist/types/client/canvas/CommandBar.d.ts +3 -4
  16. package/dist/types/client/canvas/ConnectionBanner.d.ts +2 -1
  17. package/dist/types/client/canvas/ContextChip.d.ts +3 -0
  18. package/dist/types/client/canvas/CrossBoardReferences.d.ts +5 -0
  19. package/dist/types/client/canvas/EdgeLayer.d.ts +14 -3
  20. package/dist/types/client/canvas/EmptyState.d.ts +4 -4
  21. package/dist/types/client/canvas/HomeGraphView.d.ts +2 -0
  22. package/dist/types/client/canvas/HomeMapView.d.ts +1 -0
  23. package/dist/types/client/canvas/HomeReviewView.d.ts +6 -0
  24. package/dist/types/client/canvas/HomeView.d.ts +9 -7
  25. package/dist/types/client/canvas/KnowledgeDialog.d.ts +4 -0
  26. package/dist/types/client/canvas/LifecycleChrome.d.ts +5 -0
  27. package/dist/types/client/canvas/LifecycleFields.d.ts +7 -0
  28. package/dist/types/client/canvas/LifecyclePanel.d.ts +1 -0
  29. package/dist/types/client/canvas/MemoryInspector.d.ts +7 -0
  30. package/dist/types/client/canvas/NearPinLayer.d.ts +14 -0
  31. package/dist/types/client/canvas/NodeContextMark.d.ts +40 -7
  32. package/dist/types/client/canvas/RelationPresetsDialog.d.ts +4 -0
  33. package/dist/types/client/canvas/RelationsPanel.d.ts +4 -0
  34. package/dist/types/client/canvas/SessionPanel.d.ts +2 -0
  35. package/dist/types/client/canvas/canvas-area.d.ts +1 -1
  36. package/dist/types/client/canvas/graph-geometry.d.ts +27 -0
  37. package/dist/types/client/canvas/graph-model.d.ts +37 -0
  38. package/dist/types/client/canvas/memory-layout.d.ts +23 -0
  39. package/dist/types/client/canvas/use-chrome-height.d.ts +2 -0
  40. package/dist/types/client/canvas/use-focus-trap.d.ts +1 -0
  41. package/dist/types/client/canvas/use-memory-graph.d.ts +8 -0
  42. package/dist/types/client/canvas/use-pan-zoom.d.ts +4 -1
  43. package/dist/types/client/icons.d.ts +0 -10
  44. package/dist/types/client/nodes/AxStepControls.d.ts +1 -1
  45. package/dist/types/client/nodes/HtmlNode.d.ts +1 -0
  46. package/dist/types/client/nodes/InlineMarkdownEditor.d.ts +4 -4
  47. package/dist/types/client/nodes/MarkdownNode.d.ts +5 -1
  48. package/dist/types/client/nodes/McpAppNode.d.ts +4 -4
  49. package/dist/types/client/nodes/viewer-runtime-state.d.ts +1 -1
  50. package/dist/types/client/state/boards-store.d.ts +81 -9
  51. package/dist/types/client/state/canvas-store.d.ts +14 -1
  52. package/dist/types/client/state/context-chip-store.d.ts +22 -0
  53. package/dist/types/client/state/context-status-store.d.ts +35 -0
  54. package/dist/types/client/state/intent-bridge.d.ts +11 -8
  55. package/dist/types/client/state/knowledge-store.d.ts +22 -0
  56. package/dist/types/client/state/near-pin-store.d.ts +44 -1
  57. package/dist/types/client/state/presence-store.d.ts +4 -4
  58. package/dist/types/client/state/presentation.d.ts +28 -0
  59. package/dist/types/client/state/relation-store.d.ts +10 -0
  60. package/dist/types/client/state/session-store.d.ts +41 -2
  61. package/dist/types/client/state/workspace-settings.d.ts +7 -0
  62. package/dist/types/client/types.d.ts +13 -1
  63. package/dist/types/client/utils/keyboard.d.ts +2 -0
  64. package/dist/types/client/utils/time-ago.d.ts +4 -0
  65. package/dist/types/mcp/context-uri-template.d.ts +3 -1
  66. package/dist/types/server/agent-presence.d.ts +10 -3
  67. package/dist/types/server/ax-context.d.ts +1 -1
  68. package/dist/types/server/canvas-db.d.ts +30 -7
  69. package/dist/types/server/canvas-operations.d.ts +24 -2
  70. package/dist/types/server/canvas-provenance.d.ts +22 -2
  71. package/dist/types/server/canvas-serialization.d.ts +2 -0
  72. package/dist/types/server/canvas-state.d.ts +93 -15
  73. package/dist/types/server/canvas-validation.d.ts +1 -1
  74. package/dist/types/server/context-brief.d.ts +94 -6
  75. package/dist/types/server/context-reads.d.ts +33 -7
  76. package/dist/types/server/edit-summary.d.ts +20 -0
  77. package/dist/types/server/index.d.ts +71 -10
  78. package/dist/types/server/knowledge-lifecycle.d.ts +221 -0
  79. package/dist/types/server/lifecycle-status.d.ts +10 -0
  80. package/dist/types/server/memory-graph.d.ts +9 -0
  81. package/dist/types/server/mutation-history.d.ts +2 -0
  82. package/dist/types/server/operations/ops/ax-shared.d.ts +1 -1
  83. package/dist/types/server/operations/ops/boards.d.ts +2 -1
  84. package/dist/types/server/operations/ops/lifecycle.d.ts +2 -0
  85. package/dist/types/server/operations/ops/memory-graph.d.ts +2 -0
  86. package/dist/types/server/operations/ops/nodes.d.ts +5 -0
  87. package/dist/types/server/operations/ops/query.d.ts +23 -0
  88. package/dist/types/server/operations/registry.d.ts +1 -0
  89. package/dist/types/server/placement.d.ts +7 -0
  90. package/dist/types/server/scope-fence.d.ts +2 -1
  91. package/dist/types/server/spatial-analysis.d.ts +6 -3
  92. package/dist/types/server/tour-control.d.ts +32 -0
  93. package/dist/types/server/wiki-links.d.ts +14 -0
  94. package/dist/types/server/workbench-auth.d.ts +2 -0
  95. package/dist/types/shared/agent-context.d.ts +2 -0
  96. package/dist/types/shared/agent-presence.d.ts +15 -12
  97. package/dist/types/shared/auto-arrange.d.ts +1 -0
  98. package/dist/types/shared/boards.d.ts +4 -4
  99. package/dist/types/shared/knowledge-lifecycle.d.ts +41 -0
  100. package/dist/types/shared/knowledge-presets.d.ts +6 -0
  101. package/dist/types/shared/lifecycle-status.d.ts +24 -0
  102. package/dist/types/shared/memory-graph.d.ts +53 -0
  103. package/dist/types/shared/relations.d.ts +68 -0
  104. package/dist/types/shared/semantic-attention.d.ts +2 -0
  105. package/dist/types/shared/tour.d.ts +38 -0
  106. package/dist/types/shared/workspace-settings.d.ts +11 -0
  107. package/docs/RELEASE.md +21 -3
  108. package/docs/adr-001-bun-only-runtime.md +7 -1
  109. package/docs/adr-002-shared-product-separate-runtimes.md +93 -0
  110. package/docs/api-reference.md +109 -0
  111. package/docs/ax-host-adapter-contract.md +1 -1
  112. package/docs/ax-state-contract.md +5 -4
  113. package/docs/cli.md +153 -15
  114. package/docs/demos/pmx-canvas-demo.mp4 +0 -0
  115. package/docs/design/AgentContext.dc.html +3 -3
  116. package/docs/design/BoardPins.dc.html +37 -22
  117. package/docs/design/Categories.dc.html +208 -0
  118. package/docs/design/CategoryEditor.dc.html +33 -0
  119. package/docs/design/Chrome.dc.html +55 -9
  120. package/docs/design/ContextChip.dc.html +224 -0
  121. package/docs/design/ContextChip600.dc.html +136 -0
  122. package/docs/design/EmptyState.dc.html +45 -0
  123. package/docs/design/Flows.dc.html +23 -1
  124. package/docs/design/HeaderMarks.dc.html +183 -0
  125. package/docs/design/Home.dc.html +19 -1
  126. package/docs/design/HomeGraph.dc.html +86 -202
  127. package/docs/design/HomeMap.dc.html +23 -1
  128. package/docs/design/HomeTeam.dc.html +32 -14
  129. package/docs/design/Lifecycle.dc.html +22 -0
  130. package/docs/design/Lifecycle600.dc.html +18 -0
  131. package/docs/design/LifecycleVariants.dc.html +157 -0
  132. package/docs/design/LinkAuthorship.dc.html +139 -0
  133. package/docs/design/LinksChanged.dc.html +203 -0
  134. package/docs/design/LinksOptions.dc.html +137 -0
  135. package/docs/design/LinksOptions600.dc.html +134 -0
  136. package/docs/design/NearPin.dc.html +9 -10
  137. package/docs/design/Pane600.dc.html +4 -3
  138. package/docs/design/Relations.dc.html +3 -2
  139. package/docs/design/Restore.dc.html +152 -0
  140. package/docs/design/SeeChange.dc.html +267 -0
  141. package/docs/design/Uses.dc.html +12 -6
  142. package/docs/design/canvas.json +146 -19
  143. package/docs/design.md +454 -18
  144. package/docs/environment.md +0 -1
  145. package/docs/evals/curation-effect.md +128 -0
  146. package/docs/http-api.md +465 -38
  147. package/docs/mcp.md +150 -19
  148. package/docs/node-types.md +58 -3
  149. package/docs/plans/design-gaps-2026-10-08.md +53 -0
  150. package/docs/plans/plan-009-tech-debt-backlog.md +379 -0
  151. package/docs/plans/plan-016-context-made-visible-wave-1.md +150 -5
  152. package/docs/plans/plan-017-knowledge-categories-and-lifecycle.md +175 -0
  153. package/docs/plans/plan-018-connected-memory-wave-2.md +594 -0
  154. package/docs/plans/plan-019-post-0.9-roadmap.md +198 -0
  155. package/docs/product-context-vision-2026-09.md +17 -1
  156. package/docs/product-vision-2026-09.md +1082 -43
  157. package/docs/product-vision-review-2026-09.md +13 -1
  158. package/docs/screenshots/workbench-live-dark.png +0 -0
  159. package/docs/screenshots/workbench-live-light.png +0 -0
  160. package/docs/sdk.md +62 -2
  161. package/package.json +1 -1
  162. package/plugins/pmx-canvas/com.github.copilot/extensions/pmx-canvas/runtime.json +1 -1
  163. package/plugins/pmx-canvas/plugin.json +1 -1
  164. package/plugins/pmx-canvas/runtime.json +1 -1
  165. package/plugins/pmx-canvas/tools.json +601 -22
  166. package/skills/pmx-canvas/SKILL.md +234 -43
  167. package/skills/pmx-canvas/evals/evals.json +62 -0
  168. package/skills/pmx-canvas/references/ax-html-control-surface.md +6 -0
  169. package/skills/pmx-canvas/references/full-reference.md +120 -21
  170. package/skills/pmx-canvas/references/github-copilot-app-adapter.md +2 -2
  171. package/skills/pmx-canvas/references/importing-context.md +132 -0
  172. package/skills/pmx-canvas/references/installing-pmx-canvas.md +6 -6
  173. package/skills/pmx-canvas/references/tours-and-recording.md +16 -1
  174. package/skills/pmx-canvas-testing/SKILL.md +20 -0
  175. package/src/cli/agent.ts +2 -0
  176. package/src/cli/commands/ax.ts +12 -0
  177. package/src/cli/commands/boards.ts +87 -11
  178. package/src/cli/commands/edges.ts +28 -0
  179. package/src/cli/commands/groups.ts +7 -0
  180. package/src/cli/commands/nodes.ts +4 -2
  181. package/src/cli/commands/query.ts +34 -2
  182. package/src/cli/commands/record.ts +199 -48
  183. package/src/cli/index.ts +7 -1
  184. package/src/client/App.tsx +177 -70
  185. package/src/client/canvas/AttentionHistory.tsx +0 -2
  186. package/src/client/canvas/BarHint.tsx +40 -2
  187. package/src/client/canvas/BoardCopyDialog.tsx +1 -1
  188. package/src/client/canvas/BoardFolderDialog.tsx +7 -7
  189. package/src/client/canvas/BoardLinkDialog.tsx +138 -33
  190. package/src/client/canvas/BoardPinButton.tsx +33 -0
  191. package/src/client/canvas/BoardSwitcher.tsx +26 -40
  192. package/src/client/canvas/CanvasNode.tsx +360 -237
  193. package/src/client/canvas/CanvasViewport.tsx +45 -7
  194. package/src/client/canvas/CommandBar.tsx +29 -23
  195. package/src/client/canvas/CommandPalette.tsx +5 -12
  196. package/src/client/canvas/ConnectionBanner.tsx +3 -3
  197. package/src/client/canvas/ContextChip.tsx +296 -0
  198. package/src/client/canvas/ContextMenu.tsx +63 -5
  199. package/src/client/canvas/CrossBoardReferences.tsx +60 -0
  200. package/src/client/canvas/EdgeLayer.tsx +339 -76
  201. package/src/client/canvas/EmptyState.tsx +33 -18
  202. package/src/client/canvas/ExpandedNodeOverlay.tsx +72 -40
  203. package/src/client/canvas/ExternalWriters.tsx +57 -42
  204. package/src/client/canvas/HomeGraphView.tsx +942 -0
  205. package/src/client/canvas/HomeMapView.tsx +641 -0
  206. package/src/client/canvas/HomeReviewView.tsx +167 -0
  207. package/src/client/canvas/HomeView.tsx +687 -160
  208. package/src/client/canvas/IntentLayer.tsx +19 -12
  209. package/src/client/canvas/KnowledgeDialog.tsx +488 -0
  210. package/src/client/canvas/LifecycleChrome.tsx +133 -0
  211. package/src/client/canvas/LifecycleFields.tsx +91 -0
  212. package/src/client/canvas/LifecyclePanel.tsx +533 -0
  213. package/src/client/canvas/MemoryInspector.tsx +104 -0
  214. package/src/client/canvas/Minimap.tsx +3 -3
  215. package/src/client/canvas/NearPinLayer.tsx +187 -0
  216. package/src/client/canvas/NodeContextMark.tsx +175 -97
  217. package/src/client/canvas/Presentation.tsx +23 -57
  218. package/src/client/canvas/RelationPresetsDialog.tsx +413 -0
  219. package/src/client/canvas/RelationsPanel.tsx +82 -0
  220. package/src/client/canvas/SelectionBar.tsx +3 -6
  221. package/src/client/canvas/SessionPanel.tsx +90 -50
  222. package/src/client/canvas/SessionReceipt.tsx +311 -39
  223. package/src/client/canvas/ShortcutOverlay.tsx +1 -1
  224. package/src/client/canvas/SnapshotPanel.tsx +27 -36
  225. package/src/client/canvas/ToolRail.tsx +367 -192
  226. package/src/client/canvas/TopBar.tsx +354 -124
  227. package/src/client/canvas/canvas-area.ts +10 -3
  228. package/src/client/canvas/graph-geometry.ts +195 -0
  229. package/src/client/canvas/graph-model.ts +254 -0
  230. package/src/client/canvas/memory-layout.ts +106 -0
  231. package/src/client/canvas/use-chrome-height.ts +20 -0
  232. package/src/client/canvas/use-focus-trap.ts +31 -5
  233. package/src/client/canvas/use-memory-graph.ts +58 -0
  234. package/src/client/canvas/use-node-drag.ts +2 -1
  235. package/src/client/canvas/use-pan-zoom.ts +64 -7
  236. package/src/client/icons.tsx +0 -63
  237. package/src/client/mcp-app/style.css +0 -6
  238. package/src/client/nodes/AxStepControls.tsx +74 -50
  239. package/src/client/nodes/BoardNode.tsx +5 -1
  240. package/src/client/nodes/ContextNode.tsx +18 -11
  241. package/src/client/nodes/ExtAppFrame.tsx +0 -1
  242. package/src/client/nodes/FileNode.tsx +46 -42
  243. package/src/client/nodes/HtmlNode.tsx +44 -2
  244. package/src/client/nodes/ImageNode.tsx +1 -1
  245. package/src/client/nodes/InlineFormatBar.tsx +6 -9
  246. package/src/client/nodes/InlineMarkdownEditor.tsx +56 -17
  247. package/src/client/nodes/MarkdownNode.tsx +377 -109
  248. package/src/client/nodes/McpAppNode.tsx +50 -20
  249. package/src/client/nodes/MdFormatBar.tsx +21 -18
  250. package/src/client/nodes/PromptNode.tsx +1 -1
  251. package/src/client/nodes/ResponseNode.tsx +1 -1
  252. package/src/client/nodes/viewer-runtime-state.ts +54 -22
  253. package/src/client/state/attention-bridge.ts +64 -15
  254. package/src/client/state/boards-store.ts +193 -39
  255. package/src/client/state/canvas-store.ts +99 -12
  256. package/src/client/state/context-chip-store.ts +70 -0
  257. package/src/client/state/context-status-store.ts +53 -0
  258. package/src/client/state/intent-bridge.ts +51 -30
  259. package/src/client/state/knowledge-store.ts +43 -0
  260. package/src/client/state/near-pin-store.ts +115 -6
  261. package/src/client/state/presence-store.ts +7 -10
  262. package/src/client/state/presentation.ts +91 -0
  263. package/src/client/state/relation-store.ts +81 -0
  264. package/src/client/state/session-store.ts +144 -18
  265. package/src/client/state/sse-bridge.ts +206 -29
  266. package/src/client/state/workspace-settings.ts +11 -0
  267. package/src/client/theme/global.css +2759 -510
  268. package/src/client/types.ts +12 -0
  269. package/src/client/utils/keyboard.ts +10 -0
  270. package/src/client/utils/time-ago.ts +14 -0
  271. package/src/json-render/renderer/index.css +6 -1
  272. package/src/json-render/renderer/index.tsx +31 -1
  273. package/src/mcp/canvas-app.ts +12 -2
  274. package/src/mcp/context-uri-template.ts +7 -4
  275. package/src/mcp/server.ts +63 -41
  276. package/src/mcp/workbench-app.ts +39 -6
  277. package/src/server/agent-presence.ts +128 -28
  278. package/src/server/ax-context.ts +27 -13
  279. package/src/server/board-export.ts +12 -1
  280. package/src/server/canvas-db.ts +331 -42
  281. package/src/server/canvas-operations.ts +196 -84
  282. package/src/server/canvas-provenance.ts +53 -22
  283. package/src/server/canvas-serialization.ts +2 -0
  284. package/src/server/canvas-state.ts +950 -122
  285. package/src/server/canvas-validation.ts +9 -2
  286. package/src/server/context-brief.ts +345 -38
  287. package/src/server/context-reads.ts +179 -30
  288. package/src/server/demo-state.json +355 -24
  289. package/src/server/edit-summary.ts +74 -0
  290. package/src/server/html-surface.ts +8 -1
  291. package/src/server/index.ts +203 -13
  292. package/src/server/knowledge-lifecycle.ts +304 -0
  293. package/src/server/lifecycle-status.ts +232 -0
  294. package/src/server/memory-graph.ts +166 -0
  295. package/src/server/mutation-history.ts +18 -6
  296. package/src/server/operations/composites.ts +32 -11
  297. package/src/server/operations/http.ts +7 -2
  298. package/src/server/operations/index.ts +4 -0
  299. package/src/server/operations/mcp.ts +32 -1
  300. package/src/server/operations/ops/ax-presence.ts +1 -1
  301. package/src/server/operations/ops/ax-read.ts +57 -6
  302. package/src/server/operations/ops/ax-timeline.ts +28 -2
  303. package/src/server/operations/ops/backup.ts +5 -3
  304. package/src/server/operations/ops/batch.ts +35 -4
  305. package/src/server/operations/ops/boards.ts +188 -47
  306. package/src/server/operations/ops/canvas-wire.ts +31 -1
  307. package/src/server/operations/ops/edges.ts +36 -2
  308. package/src/server/operations/ops/groups.ts +6 -1
  309. package/src/server/operations/ops/json-render.ts +5 -1
  310. package/src/server/operations/ops/lifecycle.ts +262 -0
  311. package/src/server/operations/ops/memory-graph.ts +45 -0
  312. package/src/server/operations/ops/nodes.ts +107 -24
  313. package/src/server/operations/ops/query.ts +281 -68
  314. package/src/server/operations/ops/snapshots.ts +73 -1
  315. package/src/server/operations/ops/validate.ts +5 -1
  316. package/src/server/operations/ops/viewport.ts +97 -3
  317. package/src/server/operations/registry.ts +77 -26
  318. package/src/server/placement.ts +29 -0
  319. package/src/server/scope-fence.ts +78 -6
  320. package/src/server/server.ts +115 -16
  321. package/src/server/spatial-analysis.ts +48 -23
  322. package/src/server/tour-control.ts +82 -0
  323. package/src/server/wiki-links.ts +137 -0
  324. package/src/server/workbench-auth.ts +11 -0
  325. package/src/shared/agent-context.ts +3 -0
  326. package/src/shared/agent-presence.ts +15 -15
  327. package/src/shared/auto-arrange.ts +2 -0
  328. package/src/shared/boards.ts +4 -4
  329. package/src/shared/knowledge-lifecycle.ts +22 -0
  330. package/src/shared/knowledge-presets.ts +80 -0
  331. package/src/shared/lifecycle-status.ts +26 -0
  332. package/src/shared/memory-graph.ts +74 -0
  333. package/src/shared/relations.ts +98 -0
  334. package/src/shared/semantic-attention.ts +15 -1
  335. package/src/shared/tour.ts +23 -5
  336. package/src/shared/workspace-settings.ts +13 -0
  337. package/dist/types/client/canvas/ContextPinBar.d.ts +0 -1
  338. package/dist/types/client/canvas/FocusFieldLayer.d.ts +0 -1
  339. package/dist/types/client/canvas/kind-colors.d.ts +0 -3
  340. package/dist/types/server/agent-context.d.ts +0 -22
  341. package/src/client/canvas/ContextPinBar.tsx +0 -25
@@ -0,0 +1,203 @@
1
+ <!doctype html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <title>When links change after a read</title>
6
+ <script src="./support.js"></script>
7
+ </head>
8
+ <body>
9
+ <x-dc>
10
+ <helmet>
11
+ <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:wght@400;500&amp;family=IBM+Plex+Sans:wght@400;500;600&amp;display=swap">
12
+ <style>
13
+ body{margin:0}
14
+ </style>
15
+ </helmet>
16
+ <div style="width: 1440px; height: 1580px; box-sizing: border-box; padding: 40px 48px; background: #081524; color: #e6eef7; font-family: 'IBM Plex Sans', system-ui, sans-serif; font-size: 13px; line-height: 1.5; display: flex; flex-direction: column; gap: 22px">
17
+
18
+ <div>
19
+ <h1 style="margin: 0; font-size: 28px; font-weight: 600; letter-spacing: -0.015em">When a card’s links change after the agent read it</h1>
20
+ <p style="margin: 4px 0 0; font-size: 13px; color: #8ea3bd">Decided with the maintainer 2026-10-08 (option C). Connecting cards is the work of a research board, so it must not paint the board amber: the mark sits on what changed — the edge — not on both cards. A links-only change is not “needs a look”: the next brief resends both cards with their new relations by itself. Amber stays for text the agent may be acting on.</p>
21
+ </div>
22
+
23
+ <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 24px">
24
+ <sc-for list="{{top}}" as="sc" hint-placeholder-count="2">
25
+ <section style="display: flex; flex-direction: column; gap: 8px; min-width: 0">
26
+ <span style="{{s.label}}">{{sc.label}}</span>
27
+ <div style="{{sc.frame}}">
28
+ <svg width="640" height="300" viewBox="0 0 640 300" style="position: absolute; left: 0; top: 0; overflow: visible; fill: none; stroke-linecap: round"><path d="{{sc.e.d}}" style="{{sc.e.line}}"></path><path d="{{sc.e.head}}" style="{{sc.e.headSt}}"></path></svg>
29
+ <span style="{{sc.e.pill}}">{{sc.e.label}}<sc-if value="{{sc.e.hasBadge}}" hint-placeholder-val="{{ true }}"><span style="{{sc.e.badgeSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{sc.e.badgeIc}}"></path></svg>{{sc.e.badge}}</span></sc-if></span>
30
+ <sc-for list="{{sc.cards}}" as="c" hint-placeholder-count="2">
31
+ <div style="{{c.node}}"><div style="{{c.head}}"><span style="{{s.title}}">{{c.title}}</span><sc-if value="{{c.hasTag}}" hint-placeholder-val="{{ true }}"><span style="{{c.tagSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{c.tagIc}}"></path></svg>{{c.tag}}</span></sc-if><span style="{{s.pinOn}}"><svg width="10" height="10" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span></div><div style="{{s.body}}">{{c.body}}</div></div>
32
+ </sc-for>
33
+ </div>
34
+ <span style="font-size: 12px; color: #b9c6d6">{{sc.note}}</span>
35
+ </section>
36
+ </sc-for>
37
+ </div>
38
+
39
+ <div style="display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 20px">
40
+ <sc-for list="{{cases}}" as="sc" hint-placeholder-count="3">
41
+ <section style="display: flex; flex-direction: column; gap: 8px; min-width: 0">
42
+ <span style="{{s.label}}">{{sc.label}}</span>
43
+ <div style="{{sc.frame}}">
44
+ <svg width="434" height="290" viewBox="0 0 434 290" style="position: absolute; left: 0; top: 0; overflow: visible; fill: none; stroke-linecap: round"><path d="{{sc.e.d}}" style="{{sc.e.line}}"></path><path d="{{sc.e.head}}" style="{{sc.e.headSt}}"></path></svg>
45
+ <span style="{{sc.e.pill}}">{{sc.e.label}}<sc-if value="{{sc.e.hasBadge}}" hint-placeholder-val="{{ true }}"><span style="{{sc.e.badgeSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{sc.e.badgeIc}}"></path></svg>{{sc.e.badge}}</span></sc-if></span>
46
+ <sc-for list="{{sc.cards}}" as="c" hint-placeholder-count="2">
47
+ <div style="{{c.node}}"><div style="{{c.head}}"><span style="{{s.title}}">{{c.title}}</span><sc-if value="{{c.hasTag}}" hint-placeholder-val="{{ true }}"><span style="{{c.tagSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{c.tagIc}}"></path></svg>{{c.tag}}</span></sc-if><span style="{{s.pinOn}}"><svg width="10" height="10" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span></div><div style="{{s.body}}">{{c.body}}</div></div>
48
+ </sc-for>
49
+ </div>
50
+ <span style="font-size: 12px; color: #b9c6d6">{{sc.note}}</span>
51
+ </section>
52
+ </sc-for>
53
+ </div>
54
+
55
+ <div style="display: grid; grid-template-columns: 600px minmax(0, 1fr); gap: 28px">
56
+ <section style="display: flex; flex-direction: column; gap: 8px">
57
+ <span style="{{s.label}}">At 600 px — the same marks, and the context panel’s rows</span>
58
+ <div style="{{narrow.frame}}">
59
+ <svg width="568" height="250" viewBox="0 0 568 250" style="position: absolute; left: 0; top: 0; overflow: visible; fill: none; stroke-linecap: round"><path d="{{narrow.e.d}}" style="{{narrow.e.line}}"></path><path d="{{narrow.e.head}}" style="{{narrow.e.headSt}}"></path></svg>
60
+ <span style="{{narrow.e.pill}}">{{narrow.e.label}}<span style="{{narrow.e.badgeSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{narrow.e.badgeIc}}"></path></svg>{{narrow.e.badge}}</span></span>
61
+ <sc-for list="{{narrow.cards}}" as="c" hint-placeholder-count="2">
62
+ <div style="{{c.node}}"><div style="{{c.head}}"><span style="{{s.title}}">{{c.title}}</span><span style="{{s.pinOn}}"><svg width="10" height="10" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span></div><div style="{{s.body}}">{{c.body}}</div></div>
63
+ </sc-for>
64
+ </div>
65
+ <div style="{{s.panel}} padding: 10px 12px; gap: 2px">
66
+ <div style="display: flex; align-items: center; padding: 2px 8px 6px; font-size: 11px; font-weight: 600; color: #8ea3bd"><span style="flex: 1">Cards on this board · 3</span><span style="color: #4BBCFF; font-weight: 500">Clear all</span></div>
67
+ <sc-for list="{{rows}}" as="r" hint-placeholder-count="3">
68
+ <div style="display: flex; align-items: center; gap: 8px; min-height: 30px; padding: 0 8px; font-size: 12px"><span style="{{s.pinOn}}"><svg width="9" height="9" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span><span style="{{s.title}}">{{r.t}}</span><span style="{{r.st}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{r.ic}}"></path></svg>{{r.tag}}</span><span style="width: 20px; text-align: center; color: #8ea3bd">×</span></div>
69
+ </sc-for>
70
+ <span style="font-size: 11px; color: #8ea3bd; padding: 4px 8px 0">The panel is the one place a links-only change shows per card, neutral: “links changed” clears when the agent next reads either end.</span>
71
+ </div>
72
+ </section>
73
+
74
+ <section style="display: flex; flex-direction: column; gap: 12px">
75
+ <span style="{{s.label}}">The marks</span>
76
+ <sc-for list="{{marks}}" as="m" hint-placeholder-count="5">
77
+ <div style="display: grid; grid-template-columns: 170px 1fr; gap: 12px; align-items: center"><span style="{{m.st}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{m.ic}}"></path></svg>{{m.t}}</span><span style="font-size: 12px; color: #b9c6d6">{{m.d}}</span></div>
78
+ </sc-for>
79
+ <span style="{{s.label}} margin-top: 8px">In the brief — what the agent receives next</span>
80
+ <div style="{{s.panel}} padding: 12px 14px; gap: 1px; font-family: 'IBM Plex Mono', monospace; font-size: 11.5px; line-height: 1.6">
81
+ <sc-for list="{{brief}}" as="b" hint-placeholder-count="5"><span style="{{b.st}}">{{b.t}}</span></sc-for>
82
+ </div>
83
+ <span style="{{s.label}} margin-top: 8px">Decided — and how it is built</span>
84
+ <sc-for list="{{open}}" as="o" hint-placeholder-count="3"><span style="font-size: 12px; color: #b9c6d6">{{o}}</span></sc-for>
85
+ </section>
86
+ </div>
87
+
88
+ </div>
89
+ </x-dc>
90
+ <script type="text/x-dc" data-dc-script data-props='{"$preview":{"width":1440,"height":1580}}'>
91
+ class Component extends DCLogic {
92
+ renderVals() {
93
+ var i = {
94
+ pin: 'M9 4h6l-.8 5.5 2.8 3H7l2.8-3zM12 12.5V20',
95
+ eye: 'M2 12s3.5-6 10-6 10 6 10 6-3.5 6-10 6S2 12 2 12zM12 9.5a2.5 2.5 0 1 0 0 5a2.5 2.5 0 1 0 0-5',
96
+ eyeOff: 'M3 3l18 18M10.6 6.1A10 10 0 0 1 12 6c6.5 0 10 6 10 6a17 17 0 0 1-3 3.6M6.6 6.6C3.8 8.3 2 12 2 12s3.5 6 10 6a9.6 9.6 0 0 0 4.4-1',
97
+ warn: 'M12 4l9 16H3zM12 10v4M12 17v.5',
98
+ spark: 'M12 3l1.8 5.2L19 10l-5.2 1.8L12 17l-1.8-5.2L5 10l5.2-1.8z',
99
+ link: 'M10 14a4 4 0 0 0 5.7 0l3-3a4 4 0 0 0-5.7-5.7l-1 1M14 10a4 4 0 0 0-5.7 0l-3 3a4 4 0 0 0 5.7 5.7l1-1'
100
+ };
101
+ var INK = '#5FCFC0', V = '#B388FF', W = '#f4c542';
102
+ var chip = 'display:inline-flex;align-items:center;gap:4px;height:20px;box-sizing:border-box;padding:0 7px;border-radius:999px;font-size:11px;font-weight:500;flex-shrink:0;white-space:nowrap;';
103
+ var s = {
104
+ label: 'font-size:11px;font-weight:500;letter-spacing:0.06em;text-transform:uppercase;color:#6b7d94;',
105
+ panel: 'display:flex;flex-direction:column;border-radius:10px;border:1px solid #1b2c44;background:#0f1d31;',
106
+ ic: 'fill:none;stroke:currentColor;stroke-width:1.8;stroke-linecap:round;stroke-linejoin:round;flex-shrink:0;',
107
+ icPin: 'fill:none;stroke:currentColor;stroke-width:2.6;stroke-linecap:round;stroke-linejoin:round;',
108
+ pinOn: 'width:18px;height:18px;border-radius:999px;background:#4BBCFF;color:#081524;display:flex;align-items:center;justify-content:center;flex-shrink:0;',
109
+ title: 'flex:1;min-width:0;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;font-size:12px;font-weight:600;',
110
+ body: 'padding:8px 12px;font-size:12px;color:#b9c6d6;'
111
+ };
112
+ var tags = {
113
+ changed: { tag: 'changed', st: chip + 'color:' + W + ';background:rgba(244,197,66,0.14);', ic: i.warn },
114
+ read: { tag: 'read 2m', st: chip + 'color:' + V + ';background:rgba(179,136,255,0.16);', ic: i.eye },
115
+ links: { tag: 'links changed', st: chip + 'color:#8ea3bd;background:#13243b;', ic: i.link },
116
+ notRead: { tag: 'not read yet', st: chip + 'color:#8ea3bd;background:#13243b;', ic: i.eyeOff }
117
+ };
118
+ var badges = {
119
+ agentCodex: { t: 'by Codex', st: 'display:inline-flex;align-items:center;gap:3px;margin-left:6px;padding-left:6px;border-left:1px solid #2a4566;color:' + V + ';font-weight:500;', ic: i.spark },
120
+ notSeen: { t: 'not seen by Claude', st: 'display:inline-flex;align-items:center;gap:3px;margin-left:6px;padding-left:6px;border-left:1px solid #2a4566;color:#8ea3bd;font-weight:500;', ic: i.eyeOff },
121
+ agent: { t: 'by Claude', st: 'display:inline-flex;align-items:center;gap:3px;margin-left:6px;padding-left:6px;border-left:1px solid #2a4566;color:' + V + ';font-weight:500;', ic: i.spark }
122
+ };
123
+ function card(x, y, w, title, body, tag) {
124
+ var t = tag ? tags[tag] : null;
125
+ return {
126
+ title: title, body: body, hasTag: !!t, tag: t ? t.tag : '', tagSt: t ? t.st : '', tagIc: t ? t.ic : '',
127
+ node: 'position:absolute;left:' + x + 'px;top:' + y + 'px;width:' + w + 'px;height:96px;box-sizing:border-box;border-radius:10px;border:1.5px solid #4BBCFF;background:#0f1d31;box-shadow:0 1px 2px rgba(0,0,0,0.4),0 6px 20px rgba(0,0,0,0.24);overflow:hidden;',
128
+ head: 'display:flex;align-items:center;gap:6px;height:34px;padding:0 8px 0 12px;border-bottom:1px solid #1b2c44;background:rgba(75,188,255,0.10);'
129
+ };
130
+ }
131
+ function edge(x1, y1, x2, y2, label, badge, removed, vertical) {
132
+ var mx = (x1 + x2) / 2, my = (y1 + y2) / 2;
133
+ var b = badge ? badges[badge] : null;
134
+ return {
135
+ d: vertical ? 'M' + x1 + ' ' + y1 + ' C ' + x1 + ' ' + my + ', ' + x2 + ' ' + my + ', ' + x2 + ' ' + y2 : 'M' + x1 + ' ' + y1 + ' C ' + mx + ' ' + y1 + ', ' + mx + ' ' + y2 + ', ' + x2 + ' ' + y2,
136
+ head: removed ? '' : vertical ? 'M' + x2 + ' ' + y2 + ' l-4.5 -9 h9 z' : 'M' + x2 + ' ' + y2 + ' l-9 -4.5 v9 z',
137
+ line: 'stroke:' + INK + ';stroke-width:1.5;' + (removed ? 'opacity:0;' : ''),
138
+ headSt: 'fill:' + INK + ';stroke:none;',
139
+ label: label, hasBadge: !!b, badge: b ? b.t : '', badgeSt: b ? b.st : '', badgeIc: b ? b.ic : '',
140
+ pill: 'position:absolute;left:' + mx + 'px;top:' + ((y1 + y2) / 2) + 'px;transform:translate(-50%,-50%);display:inline-flex;align-items:center;height:22px;box-sizing:border-box;padding:0 9px;border-radius:999px;border:1px solid rgba(95,207,192,0.5);background:#0f1d31;color:' + INK + ';font-size:11px;font-weight:600;white-space:nowrap;' + (removed ? 'display:none;' : '')
141
+ };
142
+ }
143
+ var frameBase = 'position:relative;border-radius:10px;border:1px solid #1b2c44;background-color:#081524;background-image:radial-gradient(rgba(142,163,189,0.14) 1px, transparent 1.2px);background-size:24px 24px;overflow:hidden;';
144
+ var A = 'Raise Pro to $24?', B = 'SMB is price-sensitive';
145
+ var bodyA = 'Question for Q4 pricing.', bodyB = 'Eight of twelve interviews.';
146
+ var top = [
147
+ { label: 'Before — both cards turned amber', frame: frameBase + 'height:300px;',
148
+ cards: [card(20, 40, 262, A, bodyA, 'changed'), card(358, 164, 262, B, bodyB, 'changed')],
149
+ e: edge(282, 88, 358, 212, 'supports', null),
150
+ note: 'You drew one link between two cards the agent had read. Both said “changed”, though neither text changed. Connect five cards and the board is amber everywhere — the warning stops meaning anything.' },
151
+ { label: 'Decided — the edge carries the mark', frame: frameBase + 'height:300px;',
152
+ cards: [card(20, 40, 262, A, bodyA, 'read'), card(358, 164, 262, B, bodyB, 'read')],
153
+ e: edge(282, 88, 358, 212, 'supports', 'notSeen'),
154
+ note: 'The cards keep their read mark. The new link’s pill says “not seen by Claude” (muted, eye-off) — the attached agent’s name — until a brief that carries either end delivers it, then the extra word goes. Nothing to act on: the next brief resends it by itself.' }
155
+ ];
156
+ var cases = [
157
+ { label: 'The agent drew it', frame: frameBase + 'height:290px;',
158
+ cards: [card(12, 16, 236, A, bodyA, 'read'), card(184, 178, 236, B, bodyB, 'read')],
159
+ e: edge(130, 112, 302, 178, 'supports', 'agentCodex', false, true),
160
+ note: 'Agent did it: violet “by Codex” — any agent, named as attached (Claude, Codex, Copilot…) — like a card’s byline, until you edit or relabel the link. An agent’s own link is never “not seen”.' },
161
+ { label: 'Text and links changed', frame: frameBase + 'height:290px;',
162
+ cards: [card(12, 16, 236, A, bodyA, 'read'), card(184, 178, 236, B, bodyB, 'changed')],
163
+ e: edge(130, 112, 302, 178, 'supports', 'notSeen', false, true),
164
+ note: 'Text wins on the card: amber “changed”, because the agent may be acting on old words. The link keeps its own muted mark. Hover on “changed” says “text changed · 1 new link”.' },
165
+ { label: 'A link was removed', frame: frameBase + 'height:290px;',
166
+ cards: [card(12, 16, 236, A, bodyA, 'read'), card(184, 178, 236, B, bodyB, 'read')],
167
+ e: edge(130, 112, 302, 178, 'supports', null, true, true),
168
+ note: 'A removed link has no line left to mark. The board stays quiet; the context panel lists both cards as “links changed” until the next brief, and Updates records the removal.' }
169
+ ];
170
+ var narrow = { frame: frameBase + 'height:250px;', cards: [card(16, 30, 220, A, bodyA), card(332, 130, 220, B, bodyB)], e: edge(236, 78, 332, 178, 'supports', 'notSeen') };
171
+ var rows = [
172
+ { t: A, tag: 'links changed', st: tags.links.st, ic: i.link },
173
+ { t: B, tag: 'changed', st: tags.changed.st, ic: i.warn },
174
+ { t: 'Competitor pricing', tag: 'read 2m', st: tags.read.st, ic: i.eye }
175
+ ];
176
+ var markBase = chip + 'justify-self:start;';
177
+ var marks = [
178
+ { t: 'changed', st: markBase + 'color:' + W + ';background:rgba(244,197,66,0.14);', ic: i.warn, d: 'Card text changed since the agent read it. Amber: it may be acting on old words. Unchanged.' },
179
+ { t: 'not seen by <agent>', st: markBase + 'color:#8ea3bd;border:1px solid #2a4566;', ic: i.eyeOff, d: 'On a link’s pill: changed since the last read that carried either end. Names the attached agent (Claude, Codex, Copilot…); “not seen by the agent” when none is attached. Neutral: the next brief delivers it by itself.' },
180
+ { t: 'by <agent>', st: markBase + 'color:' + V + ';background:rgba(179,136,255,0.16);', ic: i.spark, d: 'On a link’s pill: an agent drew it, named as attached. Violet, like every agent byline.' },
181
+ { t: 'links changed', st: markBase + 'color:#8ea3bd;background:#13243b;', ic: i.link, d: 'Only in the context panel and on hover: this card’s links changed since the agent read it (added, relabelled or removed).' },
182
+ { t: 'supports', st: markBase + 'color:' + INK + ';border:1px solid rgba(95,207,192,0.5);', ic: i.link, d: 'The relation ink itself never changes colour for any of this; inks keep their meaning.' }
183
+ ];
184
+ var m = 'white-space:pre;';
185
+ var brief = [
186
+ { t: '## Changed since your last read', st: m + 'color:#e6eef7;font-weight:500;' },
187
+ { t: '- Raise Pro to $24? links changed', st: m + 'color:#e6eef7;' },
188
+ { t: ' + supported by: SMB is price-sensitive (new, by Pepe)', st: m + 'color:#b9c6d6;' },
189
+ { t: '- SMB is price-sensitive text changed, links changed', st: m + 'color:#e6eef7;' },
190
+ { t: ' + supports: Raise Pro to $24? (new, by Pepe)', st: m + 'color:#b9c6d6;' }
191
+ ];
192
+ var open = [
193
+ 'Option C, decided with the maintainer 2026-10-08. The agent can be any agent: the pill names whichever is attached.',
194
+ 'A link is marked only if it changed since the last read that carried either end. A board no agent has read yet stays quiet.',
195
+ 'Generated code-graph and board-map edges never carry a mark.',
196
+ 'A removed link shows only as “links changed” (neutral, link glyph) in the context panel; a text change stays amber “changed” and wins.'
197
+ ];
198
+ return { i: i, s: s, top: top, cases: cases, narrow: narrow, rows: rows, marks: marks, brief: brief, open: open };
199
+ }
200
+ }
201
+ </script>
202
+ </body>
203
+ </html>
@@ -0,0 +1,137 @@
1
+ <!doctype html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <title>Connections changed after a read — C decided</title>
6
+ <script src="./support.js"></script>
7
+ </head>
8
+ <body>
9
+ <x-dc>
10
+ <helmet>
11
+ <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:wght@400;500&amp;family=IBM+Plex+Sans:wght@400;500;600&amp;display=swap">
12
+ <style>
13
+ body{margin:0}
14
+ </style>
15
+ </helmet>
16
+ <div style="width: 1440px; height: 1320px; box-sizing: border-box; padding: 40px 48px; background: #081524; color: #e6eef7; font-family: 'IBM Plex Sans', system-ui, sans-serif; font-size: 13px; line-height: 1.5; display: flex; flex-direction: column; gap: 24px">
17
+ <div>
18
+ <h1 style="margin: 0; font-size: 28px; font-weight: 600; letter-spacing: -0.015em">Connections changed after a read — C decided</h1>
19
+ <p style="margin: 4px 0 0; font-size: 13px; color: #8ea3bd">The same board drawn three ways. In each: you rewrote one card’s text (SMB is price-sensitive), you drew one link (supports), and the agent drew one link (informs). Marks follow AgentContext (“changed”, read) and Relations (edge pill, relation inks); inks never change colour.</p>
20
+ </div>
21
+ <sc-for list="{{options}}" as="o" hint-placeholder-count="3">
22
+ <section style="display: grid; grid-template-columns: 250px 700px minmax(0, 1fr); gap: 20px; align-items: start">
23
+ <div style="display: flex; flex-direction: column; gap: 8px">
24
+ <div style="display: flex; align-items: center; gap: 10px"><span style="width: 28px; height: 28px; border-radius: 999px; background: #1b2c44; font-size: 14px; font-weight: 600; text-align: center; line-height: 28px; flex-shrink: 0">{{o.k}}</span><span style="{{o.verdictSt}}">{{o.verdict}}</span></div>
25
+ <span style="font-size: 15px; font-weight: 600">{{o.name}}</span>
26
+ <span style="font-size: 12px; color: #b9c6d6">{{o.note}}</span>
27
+ </div>
28
+ <div style="{{o.frame}}">
29
+ <sc-for list="{{o.edges}}" as="e" hint-placeholder-count="2"><svg width="700" height="300" viewBox="0 0 700 300" style="position: absolute; left: 0; top: 0; overflow: visible; fill: none; stroke-linecap: round"><path d="{{e.d}}" style="{{e.line}}"></path><path d="{{e.head}}" style="{{e.headSt}}"></path></svg><span style="{{e.pill}}">{{e.label}}<sc-if value="{{e.hasBadge}}" hint-placeholder-val="{{ true }}"><span style="{{e.badgeSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{e.badgeIc}}"></path></svg>{{e.badge}}</span></sc-if></span></sc-for>
30
+ <sc-for list="{{o.cards}}" as="c" hint-placeholder-count="4"><div style="{{c.node}}"><div style="{{c.head}}"><span style="{{s.title}}">{{c.title}}</span><span style="{{c.tagSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{c.tagIc}}"></path></svg>{{c.tag}}</span><span style="{{s.pinOn}}"><svg width="10" height="10" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span></div><div style="{{s.body}}">{{c.body}}</div></div></sc-for>
31
+ </div>
32
+ <div style="{{s.panel}} padding: 10px 12px; gap: 2px">
33
+ <div style="display: flex; align-items: center; padding: 2px 8px 6px; font-size: 11px; font-weight: 600; color: #8ea3bd"><span style="flex: 1">Context panel · cards on this board · 4</span></div>
34
+ <sc-for list="{{o.rows}}" as="r" hint-placeholder-count="4"><div style="display: flex; align-items: center; gap: 8px; min-height: 30px; padding: 0 8px; font-size: 12px"><span style="{{s.pinOn}}"><svg width="9" height="9" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span><span style="{{s.title}}">{{r.t}}</span><span style="{{r.st}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{r.ic}}"></path></svg>{{r.tag}}</span><span style="width: 20px; text-align: center; color: #8ea3bd">×</span></div></sc-for>
35
+ </div>
36
+ </section>
37
+ </sc-for>
38
+ <section style="display: flex; flex-direction: column; gap: 6px; padding: 16px 18px; border-radius: 10px; border: 1px solid #2a4566; background: #0f1d31">
39
+ <span style="font-size: 13px; font-weight: 600">Decided with the maintainer, 2026-10-08</span>
40
+ <sc-for list="{{decisions}}" as="d" hint-placeholder-count="4"><span style="font-size: 12px; color: #b9c6d6">{{d}}</span></sc-for>
41
+ </section>
42
+ </div>
43
+ </x-dc>
44
+ <script type="text/x-dc" data-dc-script data-props='{"$preview":{"width":1440,"height":1320}}'>
45
+
46
+ class Component extends DCLogic {
47
+ renderVals() {
48
+ var NARROW = false;
49
+ var i = {
50
+ pin: 'M9 4h6l-.8 5.5 2.8 3H7l2.8-3zM12 12.5V20',
51
+ eye: 'M2 12s3.5-6 10-6 10 6 10 6-3.5 6-10 6S2 12 2 12zM12 9.5a2.5 2.5 0 1 0 0 5a2.5 2.5 0 1 0 0-5',
52
+ eyeOff: 'M3 3l18 18M10.6 6.1A10 10 0 0 1 12 6c6.5 0 10 6 10 6a17 17 0 0 1-3 3.6M6.6 6.6C3.8 8.3 2 12 2 12s3.5 6 10 6a9.6 9.6 0 0 0 4.4-1',
53
+ warn: 'M12 4l9 16H3zM12 10v4M12 17v.5',
54
+ spark: 'M12 3l1.8 5.2L19 10l-5.2 1.8L12 17l-1.8-5.2L5 10l5.2-1.8z',
55
+ link: 'M10 14a4 4 0 0 0 5.7 0l3-3a4 4 0 0 0-5.7-5.7l-1 1M14 10a4 4 0 0 0-5.7 0l-3 3a4 4 0 0 0 5.7 5.7l1-1'
56
+ };
57
+ var V = '#B388FF', W = '#f4c542', SUP = '#5FCFC0', INF = '#E58FB0';
58
+ var chip = 'display:inline-flex;align-items:center;gap:4px;height:20px;box-sizing:border-box;padding:0 7px;border-radius:999px;font-size:11px;font-weight:500;flex-shrink:0;white-space:nowrap;';
59
+ var s = {
60
+ label: 'font-size:11px;font-weight:500;letter-spacing:0.06em;text-transform:uppercase;color:#6b7d94;',
61
+ panel: 'display:flex;flex-direction:column;border-radius:10px;border:1px solid #1b2c44;background:#0f1d31;',
62
+ ic: 'fill:none;stroke:currentColor;stroke-width:1.8;stroke-linecap:round;stroke-linejoin:round;flex-shrink:0;',
63
+ icPin: 'fill:none;stroke:currentColor;stroke-width:2.6;stroke-linecap:round;stroke-linejoin:round;',
64
+ pinOn: 'width:18px;height:18px;border-radius:999px;background:#4BBCFF;color:#081524;display:flex;align-items:center;justify-content:center;flex-shrink:0;',
65
+ title: 'flex:1;min-width:0;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;font-size:12px;font-weight:600;',
66
+ body: 'padding:8px 12px;font-size:12px;color:#b9c6d6;'
67
+ };
68
+ var T = {
69
+ changed: { t: 'changed', st: chip + 'color:' + W + ';background:rgba(244,197,66,0.14);', ic: i.warn },
70
+ linksAmber: { t: 'links changed', st: chip + 'color:' + W + ';background:rgba(244,197,66,0.14);', ic: i.link },
71
+ linksNeutral: { t: 'links changed', st: chip + 'color:#8ea3bd;background:#13243b;', ic: i.link },
72
+ read: { t: 'read 2m', st: chip + 'color:' + V + ';background:rgba(179,136,255,0.16);', ic: i.eye }
73
+ };
74
+ var B = {
75
+ notSeen: { t: 'not seen by Codex', st: 'display:inline-flex;align-items:center;gap:3px;margin-left:6px;padding-left:6px;border-left:1px solid #2a4566;color:#8ea3bd;font-weight:500;', ic: i.eyeOff },
76
+ agent: { t: 'by Codex', st: 'display:inline-flex;align-items:center;gap:3px;margin-left:6px;padding-left:6px;border-left:1px solid #2a4566;color:' + V + ';font-weight:500;', ic: i.spark }
77
+ };
78
+ var titles = ['Raise Pro to $24?', 'SMB is price-sensitive', 'Churn flat after last raise', 'Competitor pricing'];
79
+ var bodies = ['Question for Q4 pricing.', 'You rewrote the summary · text change', 'Last raise: churn 2.2% vs 2.1%.', 'Six competitors, September list prices.'];
80
+ var FW = NARROW ? 568 : 700;
81
+ var CW = NARROW ? 262 : 320;
82
+ var X2 = FW - 16 - CW;
83
+ function card(n, x, y, tag) {
84
+ var t = T[tag];
85
+ return {
86
+ title: titles[n], body: bodies[n], tag: t.t, tagSt: t.st, tagIc: t.ic,
87
+ node: 'position:absolute;left:' + x + 'px;top:' + y + 'px;width:' + CW + 'px;height:96px;box-sizing:border-box;border-radius:10px;border:1.5px solid #4BBCFF;background:#0f1d31;box-shadow:0 1px 2px rgba(0,0,0,0.4),0 6px 20px rgba(0,0,0,0.24);overflow:hidden;',
88
+ head: 'display:flex;align-items:center;gap:6px;height:34px;padding:0 8px 0 12px;border-bottom:1px solid #1b2c44;background:rgba(75,188,255,0.10);'
89
+ };
90
+ }
91
+ function edge(x, label, ink, inkA, badge) {
92
+ var b = badge ? B[badge] : null;
93
+ return {
94
+ d: 'M' + x + ' 116 L' + x + ' 182', head: 'M' + x + ' 186 l-4.5 -9 h9 z',
95
+ line: 'stroke:' + ink + ';stroke-width:1.5;', headSt: 'fill:' + ink + ';stroke:none;',
96
+ label: label, hasBadge: !!b, badge: b ? b.t : '', badgeSt: b ? b.st : '', badgeIc: b ? b.ic : '',
97
+ pill: 'position:absolute;left:' + x + 'px;top:151px;transform:translate(-50%,-50%);display:inline-flex;align-items:center;height:22px;box-sizing:border-box;padding:0 9px;border-radius:999px;border:1px solid ' + inkA + ';background:#0f1d31;color:' + ink + ';font-size:11px;font-weight:600;white-space:nowrap;'
98
+ };
99
+ }
100
+ var hx = 16 + CW / 2, ax = X2 + CW / 2;
101
+ function option(k, name, verdict, verdictSt, tags, humanBadge, agentBadge, rowTags, note) {
102
+ return {
103
+ k: k, name: name, verdict: verdict, verdictSt: verdictSt, note: note,
104
+ frame: 'position:relative;width:' + FW + 'px;height:300px;flex-shrink:0;border-radius:10px;border:1px solid #1b2c44;background-color:#081524;background-image:radial-gradient(rgba(142,163,189,0.14) 1px, transparent 1.2px);background-size:24px 24px;overflow:hidden;',
105
+ cards: [card(0, 16, 20, tags[0]), card(1, X2, 20, tags[1]), card(2, 16, 186, tags[2]), card(3, X2, 186, tags[3])],
106
+ edges: [edge(hx, 'supports', SUP, 'rgba(95,207,192,0.5)', humanBadge), edge(ax, 'informs', INF, 'rgba(229,143,176,0.5)', agentBadge)],
107
+ rows: rowTags.map(function (t, n) { return { t: titles[n], tag: T[t].t, st: T[t].st, ic: T[t].ic }; })
108
+ };
109
+ }
110
+ var vBase = 'display:inline-flex;align-items:center;height:22px;padding:0 9px;border-radius:999px;font-size:11px;font-weight:600;';
111
+ var options = [
112
+ option('A', 'Every change is “changed”', 'Not chosen', vBase + 'background:#1b2c44;color:#8ea3bd;',
113
+ ['changed', 'changed', 'changed', 'changed'], null, null,
114
+ ['changed', 'changed', 'changed', 'changed'],
115
+ 'One text edit and two links light all four cards. The two you connected and the two the agent connected look exactly like the card whose words changed. Assumes the agent’s own edge advances both ends too, as the fix does.'),
116
+ option('B', 'A connections mark on the cards', 'Not chosen', vBase + 'background:#1b2c44;color:#8ea3bd;',
117
+ ['linksAmber', 'changed', 'linksAmber', 'read'], null, 'agent',
118
+ ['linksAmber', 'changed', 'linksAmber', 'read'],
119
+ 'Text and links are told apart by glyph and word, both amber. Your link marks both its ends; the agent’s own link marks nothing (it made it) and carries “by Codex”. The board still turns amber wherever you connect cards.'),
120
+ option('C', 'The mark on the connection', 'Decided 2026-10-08', vBase + 'background:rgba(75,188,255,0.14);color:#4BBCFF;',
121
+ ['read', 'changed', 'read', 'read'], 'notSeen', 'agent',
122
+ ['linksNeutral', 'changed', 'linksNeutral', 'read'],
123
+ 'Only the text change is amber. Your new link says “not seen by Codex” on its pill until a brief carrying either end delivers it; the agent’s says “by Codex”. The name is whichever agent is attached — Claude, Codex, Copilot… Cards keep their read marks; the panel lists “links changed” in neutral.')
124
+ ];
125
+ var decisions = [
126
+ 'C, decided 2026-10-08: the mark sits on the connection, neutral; only text changes are amber on the card.',
127
+ 'Any agent: pills read “not seen by <agent>” / “by <agent>” with the attached agent’s name (here Codex); “not seen by the agent” when none is attached.',
128
+ 'Marked only if changed since the last read that carried either end; a board no agent has read stays quiet; generated code-graph and board-map edges never carry a mark.',
129
+ 'A removed link shows only as “links changed” (neutral) in the context panel; a text change stays amber “changed” and wins.'
130
+ ];
131
+ return { i: i, s: s, options: options, decisions: decisions };
132
+ }
133
+ }
134
+
135
+ </script>
136
+ </body>
137
+ </html>
@@ -0,0 +1,134 @@
1
+ <!doctype html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <title>Connections changed — at 600 px, C decided</title>
6
+ <script src="./support.js"></script>
7
+ </head>
8
+ <body>
9
+ <x-dc>
10
+ <helmet>
11
+ <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:wght@400;500&amp;family=IBM+Plex+Sans:wght@400;500;600&amp;display=swap">
12
+ <style>
13
+ body{margin:0}
14
+ </style>
15
+ </helmet>
16
+ <div style="width: 600px; height: 2240px; box-sizing: border-box; padding: 24px 16px; background: #081524; color: #e6eef7; font-family: 'IBM Plex Sans', system-ui, sans-serif; font-size: 13px; line-height: 1.5; display: flex; flex-direction: column; gap: 24px">
17
+ <div>
18
+ <h1 style="margin: 0; font-size: 20px; font-weight: 600; letter-spacing: -0.015em">Connections changed — at 600 px, C decided</h1>
19
+ <p style="margin: 4px 0 0; font-size: 13px; color: #8ea3bd">The same board drawn three ways. In each: you rewrote one card’s text (SMB is price-sensitive), you drew one link (supports), and the agent drew one link (informs). Marks follow AgentContext (“changed”, read) and Relations (edge pill, relation inks); inks never change colour.</p>
20
+ </div>
21
+ <sc-for list="{{options}}" as="o" hint-placeholder-count="3">
22
+ <section style="display: flex; flex-direction: column; gap: 10px">
23
+ <div style="display: flex; align-items: center; gap: 10px"><span style="width: 28px; height: 28px; border-radius: 999px; background: #1b2c44; font-size: 14px; font-weight: 600; text-align: center; line-height: 28px; flex-shrink: 0">{{o.k}}</span><span style="font-size: 15px; font-weight: 600; flex: 1">{{o.name}}</span><span style="{{o.verdictSt}}">{{o.verdict}}</span></div>
24
+ <div style="{{o.frame}}">
25
+ <sc-for list="{{o.edges}}" as="e" hint-placeholder-count="2"><svg width="568" height="300" viewBox="0 0 568 300" style="position: absolute; left: 0; top: 0; overflow: visible; fill: none; stroke-linecap: round"><path d="{{e.d}}" style="{{e.line}}"></path><path d="{{e.head}}" style="{{e.headSt}}"></path></svg><span style="{{e.pill}}">{{e.label}}<sc-if value="{{e.hasBadge}}" hint-placeholder-val="{{ true }}"><span style="{{e.badgeSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{e.badgeIc}}"></path></svg>{{e.badge}}</span></sc-if></span></sc-for>
26
+ <sc-for list="{{o.cards}}" as="c" hint-placeholder-count="4"><div style="{{c.node}}"><div style="{{c.head}}"><span style="{{s.title}}">{{c.title}}</span><span style="{{c.tagSt}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{c.tagIc}}"></path></svg>{{c.tag}}</span><span style="{{s.pinOn}}"><svg width="10" height="10" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span></div><div style="{{s.body}}">{{c.body}}</div></div></sc-for>
27
+ </div>
28
+ <div style="{{s.panel}} padding: 10px 12px; gap: 2px">
29
+ <div style="display: flex; align-items: center; padding: 2px 8px 6px; font-size: 11px; font-weight: 600; color: #8ea3bd"><span style="flex: 1">Context panel · cards on this board · 4</span></div>
30
+ <sc-for list="{{o.rows}}" as="r" hint-placeholder-count="4"><div style="display: flex; align-items: center; gap: 8px; min-height: 30px; padding: 0 8px; font-size: 12px"><span style="{{s.pinOn}}"><svg width="9" height="9" viewBox="0 0 24 24" style="{{s.icPin}}"><path d="{{i.pin}}"></path></svg></span><span style="{{s.title}}">{{r.t}}</span><span style="{{r.st}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ic}}"><path d="{{r.ic}}"></path></svg>{{r.tag}}</span><span style="width: 20px; text-align: center; color: #8ea3bd">×</span></div></sc-for>
31
+ </div>
32
+ <span style="font-size: 12px; color: #b9c6d6">{{o.note}}</span>
33
+ </section>
34
+ </sc-for>
35
+ <section style="display: flex; flex-direction: column; gap: 6px; padding: 16px 18px; border-radius: 10px; border: 1px solid #2a4566; background: #0f1d31">
36
+ <span style="font-size: 13px; font-weight: 600">Decided with the maintainer, 2026-10-08</span>
37
+ <sc-for list="{{decisions}}" as="d" hint-placeholder-count="4"><span style="font-size: 12px; color: #b9c6d6">{{d}}</span></sc-for>
38
+ </section>
39
+ </div>
40
+ </x-dc>
41
+ <script type="text/x-dc" data-dc-script data-props='{"$preview":{"width":600,"height":2240}}'>
42
+
43
+ class Component extends DCLogic {
44
+ renderVals() {
45
+ var NARROW = true;
46
+ var i = {
47
+ pin: 'M9 4h6l-.8 5.5 2.8 3H7l2.8-3zM12 12.5V20',
48
+ eye: 'M2 12s3.5-6 10-6 10 6 10 6-3.5 6-10 6S2 12 2 12zM12 9.5a2.5 2.5 0 1 0 0 5a2.5 2.5 0 1 0 0-5',
49
+ eyeOff: 'M3 3l18 18M10.6 6.1A10 10 0 0 1 12 6c6.5 0 10 6 10 6a17 17 0 0 1-3 3.6M6.6 6.6C3.8 8.3 2 12 2 12s3.5 6 10 6a9.6 9.6 0 0 0 4.4-1',
50
+ warn: 'M12 4l9 16H3zM12 10v4M12 17v.5',
51
+ spark: 'M12 3l1.8 5.2L19 10l-5.2 1.8L12 17l-1.8-5.2L5 10l5.2-1.8z',
52
+ link: 'M10 14a4 4 0 0 0 5.7 0l3-3a4 4 0 0 0-5.7-5.7l-1 1M14 10a4 4 0 0 0-5.7 0l-3 3a4 4 0 0 0 5.7 5.7l1-1'
53
+ };
54
+ var V = '#B388FF', W = '#f4c542', SUP = '#5FCFC0', INF = '#E58FB0';
55
+ var chip = 'display:inline-flex;align-items:center;gap:4px;height:20px;box-sizing:border-box;padding:0 7px;border-radius:999px;font-size:11px;font-weight:500;flex-shrink:0;white-space:nowrap;';
56
+ var s = {
57
+ label: 'font-size:11px;font-weight:500;letter-spacing:0.06em;text-transform:uppercase;color:#6b7d94;',
58
+ panel: 'display:flex;flex-direction:column;border-radius:10px;border:1px solid #1b2c44;background:#0f1d31;',
59
+ ic: 'fill:none;stroke:currentColor;stroke-width:1.8;stroke-linecap:round;stroke-linejoin:round;flex-shrink:0;',
60
+ icPin: 'fill:none;stroke:currentColor;stroke-width:2.6;stroke-linecap:round;stroke-linejoin:round;',
61
+ pinOn: 'width:18px;height:18px;border-radius:999px;background:#4BBCFF;color:#081524;display:flex;align-items:center;justify-content:center;flex-shrink:0;',
62
+ title: 'flex:1;min-width:0;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;font-size:12px;font-weight:600;',
63
+ body: 'padding:8px 12px;font-size:12px;color:#b9c6d6;'
64
+ };
65
+ var T = {
66
+ changed: { t: 'changed', st: chip + 'color:' + W + ';background:rgba(244,197,66,0.14);', ic: i.warn },
67
+ linksAmber: { t: 'links changed', st: chip + 'color:' + W + ';background:rgba(244,197,66,0.14);', ic: i.link },
68
+ linksNeutral: { t: 'links changed', st: chip + 'color:#8ea3bd;background:#13243b;', ic: i.link },
69
+ read: { t: 'read 2m', st: chip + 'color:' + V + ';background:rgba(179,136,255,0.16);', ic: i.eye }
70
+ };
71
+ var B = {
72
+ notSeen: { t: 'not seen by Codex', st: 'display:inline-flex;align-items:center;gap:3px;margin-left:6px;padding-left:6px;border-left:1px solid #2a4566;color:#8ea3bd;font-weight:500;', ic: i.eyeOff },
73
+ agent: { t: 'by Codex', st: 'display:inline-flex;align-items:center;gap:3px;margin-left:6px;padding-left:6px;border-left:1px solid #2a4566;color:' + V + ';font-weight:500;', ic: i.spark }
74
+ };
75
+ var titles = ['Raise Pro to $24?', 'SMB is price-sensitive', 'Churn flat after last raise', 'Competitor pricing'];
76
+ var bodies = ['Question for Q4 pricing.', 'You rewrote the summary · text change', 'Last raise: churn 2.2% vs 2.1%.', 'Six competitors, September list prices.'];
77
+ var FW = NARROW ? 568 : 700;
78
+ var CW = NARROW ? 262 : 320;
79
+ var X2 = FW - 16 - CW;
80
+ function card(n, x, y, tag) {
81
+ var t = T[tag];
82
+ return {
83
+ title: titles[n], body: bodies[n], tag: t.t, tagSt: t.st, tagIc: t.ic,
84
+ node: 'position:absolute;left:' + x + 'px;top:' + y + 'px;width:' + CW + 'px;height:96px;box-sizing:border-box;border-radius:10px;border:1.5px solid #4BBCFF;background:#0f1d31;box-shadow:0 1px 2px rgba(0,0,0,0.4),0 6px 20px rgba(0,0,0,0.24);overflow:hidden;',
85
+ head: 'display:flex;align-items:center;gap:6px;height:34px;padding:0 8px 0 12px;border-bottom:1px solid #1b2c44;background:rgba(75,188,255,0.10);'
86
+ };
87
+ }
88
+ function edge(x, label, ink, inkA, badge) {
89
+ var b = badge ? B[badge] : null;
90
+ return {
91
+ d: 'M' + x + ' 116 L' + x + ' 182', head: 'M' + x + ' 186 l-4.5 -9 h9 z',
92
+ line: 'stroke:' + ink + ';stroke-width:1.5;', headSt: 'fill:' + ink + ';stroke:none;',
93
+ label: label, hasBadge: !!b, badge: b ? b.t : '', badgeSt: b ? b.st : '', badgeIc: b ? b.ic : '',
94
+ pill: 'position:absolute;left:' + x + 'px;top:151px;transform:translate(-50%,-50%);display:inline-flex;align-items:center;height:22px;box-sizing:border-box;padding:0 9px;border-radius:999px;border:1px solid ' + inkA + ';background:#0f1d31;color:' + ink + ';font-size:11px;font-weight:600;white-space:nowrap;'
95
+ };
96
+ }
97
+ var hx = 16 + CW / 2, ax = X2 + CW / 2;
98
+ function option(k, name, verdict, verdictSt, tags, humanBadge, agentBadge, rowTags, note) {
99
+ return {
100
+ k: k, name: name, verdict: verdict, verdictSt: verdictSt, note: note,
101
+ frame: 'position:relative;width:' + FW + 'px;height:300px;flex-shrink:0;border-radius:10px;border:1px solid #1b2c44;background-color:#081524;background-image:radial-gradient(rgba(142,163,189,0.14) 1px, transparent 1.2px);background-size:24px 24px;overflow:hidden;',
102
+ cards: [card(0, 16, 20, tags[0]), card(1, X2, 20, tags[1]), card(2, 16, 186, tags[2]), card(3, X2, 186, tags[3])],
103
+ edges: [edge(hx, 'supports', SUP, 'rgba(95,207,192,0.5)', humanBadge), edge(ax, 'informs', INF, 'rgba(229,143,176,0.5)', agentBadge)],
104
+ rows: rowTags.map(function (t, n) { return { t: titles[n], tag: T[t].t, st: T[t].st, ic: T[t].ic }; })
105
+ };
106
+ }
107
+ var vBase = 'display:inline-flex;align-items:center;height:22px;padding:0 9px;border-radius:999px;font-size:11px;font-weight:600;';
108
+ var options = [
109
+ option('A', 'Every change is “changed”', 'Not chosen', vBase + 'background:#1b2c44;color:#8ea3bd;',
110
+ ['changed', 'changed', 'changed', 'changed'], null, null,
111
+ ['changed', 'changed', 'changed', 'changed'],
112
+ 'One text edit and two links light all four cards. The two you connected and the two the agent connected look exactly like the card whose words changed. Assumes the agent’s own edge advances both ends too, as the fix does.'),
113
+ option('B', 'A connections mark on the cards', 'Not chosen', vBase + 'background:#1b2c44;color:#8ea3bd;',
114
+ ['linksAmber', 'changed', 'linksAmber', 'read'], null, 'agent',
115
+ ['linksAmber', 'changed', 'linksAmber', 'read'],
116
+ 'Text and links are told apart by glyph and word, both amber. Your link marks both its ends; the agent’s own link marks nothing (it made it) and carries “by Codex”. The board still turns amber wherever you connect cards.'),
117
+ option('C', 'The mark on the connection', 'Decided 2026-10-08', vBase + 'background:rgba(75,188,255,0.14);color:#4BBCFF;',
118
+ ['read', 'changed', 'read', 'read'], 'notSeen', 'agent',
119
+ ['linksNeutral', 'changed', 'linksNeutral', 'read'],
120
+ 'Only the text change is amber. Your new link says “not seen by Codex” on its pill until a brief carrying either end delivers it; the agent’s says “by Codex”. The name is whichever agent is attached — Claude, Codex, Copilot… Cards keep their read marks; the panel lists “links changed” in neutral.')
121
+ ];
122
+ var decisions = [
123
+ 'C, decided 2026-10-08: the mark sits on the connection, neutral; only text changes are amber on the card.',
124
+ 'Any agent: pills read “not seen by <agent>” / “by <agent>” with the attached agent’s name (here Codex); “not seen by the agent” when none is attached.',
125
+ 'Marked only if changed since the last read that carried either end; a board no agent has read stays quiet; generated code-graph and board-map edges never carry a mark.',
126
+ 'A removed link shows only as “links changed” (neutral) in the context panel; a text change stays amber “changed” and wins.'
127
+ ];
128
+ return { i: i, s: s, options: options, decisions: decisions };
129
+ }
130
+ }
131
+
132
+ </script>
133
+ </body>
134
+ </html>
@@ -17,7 +17,7 @@ body{margin:0}
17
17
 
18
18
  <div>
19
19
  <h1 style="margin: 0; font-size: 28px; font-weight: 600; letter-spacing: -0.015em">Near a pin</h1>
20
- <p style="margin: 4px 0 0; font-size: 13px; color: #8ea3bd; max-width: 1100px">Each pinned node pulls up to five unpinned nodes whose centres are within 600 px into the agent's brief — each as its title and a short summary, with “near &lt;pin&gt;” as the reason, never its full content. They get their own, weaker mark: a dotted chip with the word “near”. The mark ships in wave 1 together with that brief change, so it claims exactly what the agent receives.</p>
20
+ <p style="margin: 4px 0 0; font-size: 13px; color: #8ea3bd; max-width: 1100px">Each pinned node pulls up to five unpinned nodes whose edge-to-edge gap is at most 600 canvas pixels into the agent's brief — each as its title and a short summary, with “near &lt;pin&gt;” as the reason, after the pinned cards. Updated with the maintainer 2026-10-14: distance follows the whole card, not its centre; diagrams are schematic. A pin puts a card first in the agent’s map (title, summary, relations); the agent pulls full text itself when it needs it. Near nodes get their own, weaker mark: a dotted chip with the word “near”. The mark ships in wave 1 together with that brief change, so it claims exactly what the agent receives.</p>
21
21
  </div>
22
22
 
23
23
  <section style="display: grid; grid-template-columns: 860px minmax(0, 1fr); gap: 32px">
@@ -50,7 +50,7 @@ body{margin:0}
50
50
  </div>
51
51
  <div style="{{s.card}} gap: 6px">
52
52
  <span style="font-size: 12px; font-weight: 600">What the agent gets (wave 1 brief)</span>
53
- <span style="font-size: 12px; color: #b9c6d6">In the main brief, after the pinned cards: each near node's title and a short summary, nearest first, with the pin it is near as the reason. Never its full content — pin it for that.</span>
53
+ <span style="font-size: 12px; color: #b9c6d6">In the main brief, after the pinned cards: each near node's title and a short summary, nearest first, with the pin it is near as the reason. Pin it to put it first.</span>
54
54
  <div style="padding: 8px 10px; border-radius: 6px; background: #06111e; border: 1px solid #1b2c44; font-family: 'IBM Plex Mono', monospace; font-size: 11px; line-height: 1.6; color: #b9c6d6; white-space: pre-wrap">near “Release runbook” · 240 px
55
55
  Price page copy — Draft copy for the Pro plan page: headline, three benefits, FAQ.</div>
56
56
  </div>
@@ -62,12 +62,11 @@ Price page copy — Draft copy for the Pro plan page: headline, three benefits,
62
62
  <span style="{{s.label}}">2 · Which pin? Hover a pin to see its neighbours</span>
63
63
  <div style="{{s.scene}} height: 420px">
64
64
  <svg width="860" height="420" viewBox="0 0 860 420" style="position: absolute; left: 0; top: 0; fill: none; stroke-linecap: round">
65
- <circle cx="425" cy="192" r="285" style="stroke: rgba(75,188,255,0.25); stroke-width: 1.5; stroke-dasharray: 3 6"></circle>
65
+ <rect x="15" y="-135" width="820" height="654" rx="285" style="stroke: rgba(75,188,255,0.25); stroke-width: 1.5; stroke-dasharray: 3 6"></rect>
66
66
  <path d="{{tether.a}}" style="stroke: #4BBCFF; stroke-width: 1.5; stroke-dasharray: 2 5"></path>
67
67
  <path d="{{tether.b}}" style="stroke: #4BBCFF; stroke-width: 1.5; stroke-dasharray: 2 5"></path>
68
68
  <path d="{{tether.c}}" style="stroke: #4BBCFF; stroke-width: 1.5; stroke-dasharray: 2 5"></path>
69
69
  </svg>
70
- <span style="position: absolute; left: 640px; top: 392px; font-size: 11px; color: rgba(75,188,255,0.7)">600 px from Release runbook</span>
71
70
  <sc-for list="{{hover}}" as="n" hint-placeholder-count="6">
72
71
  <div style="{{n.box}}">
73
72
  <div style="{{n.head}}"><svg width="14" height="14" viewBox="0 0 24 24" style="{{s.kind}}"><path d="{{i.note}}"></path></svg><span style="{{s.title}}">{{n.title}}</span>
@@ -80,7 +79,7 @@ Price page copy — Draft copy for the Pro plan page: headline, three benefits,
80
79
  </sc-for>
81
80
  <sc-for list="{{nums}}" as="m" hint-placeholder-count="3"><span style="position: absolute; left: {{m.x}}px; top: {{m.y}}px; width: 20px; height: 20px; border-radius: 999px; background: #081524; border: 1px dotted #4BBCFF; color: #4BBCFF; font-size: 11px; font-weight: 600; text-align: center; line-height: 18px">{{m.n}}</span></sc-for>
82
81
  </div>
83
- <span style="font-size: 12px; color: #8ea3bd">Dotted tethers, numbered nearest first, and the 600 px radius while the pin is hovered or selected. Tethers are drawn in screen space, so they still join a pin and its neighbours at fit zoom. Other nodes are untouched.</span>
82
+ <span style="font-size: 12px; color: #8ea3bd">Dotted tethers, numbered by nearest edge gap first, and an unlabeled rounded boundary 600 canvas pixels beyond the pin's edges while it is hovered or selected, only when another card's edges are within range. Tethers are drawn in screen space, so they still join a pin and its neighbours at fit zoom. Other nodes are untouched.</span>
84
83
  </div>
85
84
 
86
85
  <div style="display: flex; flex-direction: column; gap: 12px">
@@ -89,13 +88,13 @@ Price page copy — Draft copy for the Pro plan page: headline, three benefits,
89
88
  <span style="font-size: 12px; font-weight: 600">Near 2 pins</span>
90
89
  <div style="display: flex; justify-content: space-between; font-size: 12px"><span>Release runbook</span><span style="font-family: 'IBM Plex Mono', monospace; font-size: 11px; color: #8ea3bd">240 px</span></div>
91
90
  <div style="display: flex; justify-content: space-between; font-size: 12px"><span>Readability floor</span><span style="font-family: 'IBM Plex Mono', monospace; font-size: 11px; color: #8ea3bd">410 px</span></div>
92
- <span style="font-size: 11px; color: #b9c6d6">The agent gets this node's title and a short summary, not its full content.</span>
93
- <div style="display: flex; gap: 6px"><button style="height: 26px; padding: 0 10px; border: 0; border-radius: 6px; background: #4BBCFF; color: #081524; font-family: inherit; font-size: 11px; font-weight: 600">Pin to send content</button><button style="height: 26px; padding: 0 10px; border-radius: 6px; border: 1px solid #2a4566; background: transparent; color: #e6eef7; font-family: inherit; font-size: 11px">Show pins</button></div>
91
+ <span style="font-size: 11px; color: #b9c6d6">The agent gets its title and a short summary because a pin is nearby. Pin it to put it first.</span>
92
+ <div style="display: flex; gap: 6px"><button style="height: 26px; padding: 0 10px; border: 0; border-radius: 6px; background: #4BBCFF; color: #081524; font-family: inherit; font-size: 11px; font-weight: 600">Pin to put it first</button><button style="height: 26px; padding: 0 10px; border-radius: 6px; border: 1px solid #2a4566; background: transparent; color: #e6eef7; font-family: inherit; font-size: 11px">Show pins</button></div>
94
93
  </div>
95
94
  <span style="{{s.label}}">The context chip</span>
96
95
  <div style="padding: 12px; border-radius: 12px; border: 1px solid #2a4566; background: #13243b; display: flex; flex-direction: column; gap: 6px">
97
96
  <div style="display: flex; align-items: center; justify-content: space-between"><span style="font-size: 12px; font-weight: 600">In the agent's context</span><span style="font-size: 11px; color: #8ea3bd">2 cards · 3 near</span></div>
98
- <span style="font-size: 11px; color: #8ea3bd">Pinned · full content</span>
97
+ <span style="font-size: 11px; color: #8ea3bd">Pinned · first in the map</span>
99
98
  <span style="font-size: 12px">Release runbook · Readability floor</span>
100
99
  <span style="font-size: 11px; color: #8ea3bd">Near your pins · title and summary</span>
101
100
  <span style="font-size: 12px; color: #b9c6d6">Price page copy · Churn deep-dive · Pricing notes</span>
@@ -109,7 +108,7 @@ Price page copy — Draft copy for the Pro plan page: headline, three benefits,
109
108
  <sc-for list="{{moments}}" as="mo" hint-placeholder-count="3">
110
109
  <div style="display: flex; flex-direction: column; gap: 8px">
111
110
  <div style="{{s.scene}} height: 190px">
112
- <sc-if value="{{mo.ring}}" hint-placeholder-val="{{ false }}"><svg width="420" height="190" viewBox="0 0 420 190" style="position: absolute; left: 0; top: 0; fill: none"><circle cx="110" cy="95" r="150" style="stroke: rgba(75,188,255,0.35); stroke-width: 1.5; stroke-dasharray: 3 6"></circle></svg></sc-if>
111
+ <sc-if value="{{mo.ring}}" hint-placeholder-val="{{ false }}"><svg width="420" height="190" viewBox="0 0 420 190" style="position: absolute; left: 0; top: 0; fill: none"><rect x="-130" y="-90" width="480" height="332" rx="150" style="stroke: rgba(75,188,255,0.35); stroke-width: 1.5; stroke-dasharray: 3 6"></rect></svg></sc-if>
113
112
  <div style="{{s.pinnedBox}} left: 20px; top: 60px"><div style="{{s.pinnedHead}}"><span style="{{s.title}}">Release runbook</span><span style="{{s.pinOn}}"><svg width="9" height="9" viewBox="0 0 24 24" style="{{s.ic2}}"><path d="{{i.pin}}"></path></svg></span></div></div>
114
113
  <div style="{{mo.box}}"><div style="{{s.plainHead}}"><span style="{{s.title}}">Price page copy</span><sc-if value="{{mo.chip}}" hint-placeholder-val="{{ false }}"><span style="{{mo.chipStyle}}"><svg width="11" height="11" viewBox="0 0 24 24" style="{{s.ring}}"><circle cx="12" cy="12" r="8"></circle><circle cx="12" cy="12" r="2.4" style="fill: currentColor; stroke: none"></circle></svg>near</span></sc-if></div></div>
115
114
  </div>
@@ -227,7 +226,7 @@ class Component extends DCLogic {
227
226
  { k: 'Agent editing', v: 'violet bar across the top' }
228
227
  ];
229
228
  var moments = [
230
- { t: 'Dragging toward a pin', d: 'The nearest pin shows its 600 px radius while you drag; the chip previews “near” once the centre is inside.', ring: true, chip: true, chipStyle: chip + 'opacity:0.6;', update: 'Release runbook · 600 px',
229
+ { t: 'Dragging toward a pin', d: 'The nearest pin by edge gap shows its boundary while you drag; the chip previews “near” once the edge-to-edge gap is at most 600 canvas pixels, subject to the five-card cap.', ring: true, chip: true, chipStyle: chip + 'opacity:0.6;', update: 'Release runbook · 600 px edge gap',
231
230
  box: boxBase + 'border:1px solid #1b2c44;left:220px;top:110px;width:180px;' },
232
231
  { t: 'Dropped inside', d: 'The chip pulses once. One Updates entry names the node and the pin — no generic toast.', ring: false, chip: true, chipStyle: chipPulse, update: '“Price page copy” is now near “Release runbook” — the agent gets its title and summary.',
233
232
  box: boxBase + 'border:1px solid #1b2c44;left:220px;top:110px;width:180px;' },