@agent-native/core 0.85.6 → 0.86.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 (1069) hide show
  1. package/corpus/README.md +2 -2
  2. package/corpus/core/CHANGELOG.md +130 -1
  3. package/corpus/core/README.md +0 -11
  4. package/corpus/core/docs/content/cloneable-saas.mdx +0 -1
  5. package/corpus/core/docs/content/locales/ar-SA/cloneable-saas.mdx +0 -1
  6. package/corpus/core/docs/content/locales/ar-SA/plan-plugin.mdx +10 -9
  7. package/corpus/core/docs/content/locales/ar-SA/sharing.mdx +1 -2
  8. package/corpus/core/docs/content/locales/ar-SA/skills-guide.mdx +2 -3
  9. package/corpus/core/docs/content/locales/ar-SA/template-plan.mdx +23 -7
  10. package/corpus/core/docs/content/locales/ar-SA/tracking.mdx +1 -1
  11. package/corpus/core/docs/content/locales/ar-SA/workspace-connections.mdx +11 -11
  12. package/corpus/core/docs/content/locales/de-DE/cloneable-saas.mdx +0 -1
  13. package/corpus/core/docs/content/locales/de-DE/plan-plugin.mdx +10 -9
  14. package/corpus/core/docs/content/locales/de-DE/sharing.mdx +1 -2
  15. package/corpus/core/docs/content/locales/de-DE/skills-guide.mdx +2 -3
  16. package/corpus/core/docs/content/locales/de-DE/template-plan.mdx +23 -7
  17. package/corpus/core/docs/content/locales/de-DE/tracking.mdx +1 -1
  18. package/corpus/core/docs/content/locales/de-DE/workspace-connections.mdx +1 -1
  19. package/corpus/core/docs/content/locales/es-ES/cloneable-saas.mdx +0 -1
  20. package/corpus/core/docs/content/locales/es-ES/plan-plugin.mdx +10 -9
  21. package/corpus/core/docs/content/locales/es-ES/sharing.mdx +1 -2
  22. package/corpus/core/docs/content/locales/es-ES/skills-guide.mdx +2 -3
  23. package/corpus/core/docs/content/locales/es-ES/template-plan.mdx +23 -7
  24. package/corpus/core/docs/content/locales/es-ES/tracking.mdx +1 -1
  25. package/corpus/core/docs/content/locales/es-ES/workspace-connections.mdx +1 -1
  26. package/corpus/core/docs/content/locales/fr-FR/cloneable-saas.mdx +0 -1
  27. package/corpus/core/docs/content/locales/fr-FR/plan-plugin.mdx +10 -9
  28. package/corpus/core/docs/content/locales/fr-FR/sharing.mdx +1 -2
  29. package/corpus/core/docs/content/locales/fr-FR/skills-guide.mdx +2 -3
  30. package/corpus/core/docs/content/locales/fr-FR/template-plan.mdx +23 -7
  31. package/corpus/core/docs/content/locales/fr-FR/tracking.mdx +1 -1
  32. package/corpus/core/docs/content/locales/fr-FR/workspace-connections.mdx +1 -1
  33. package/corpus/core/docs/content/locales/hi-IN/cloneable-saas.mdx +0 -1
  34. package/corpus/core/docs/content/locales/hi-IN/plan-plugin.mdx +10 -9
  35. package/corpus/core/docs/content/locales/hi-IN/sharing.mdx +1 -2
  36. package/corpus/core/docs/content/locales/hi-IN/skills-guide.mdx +2 -3
  37. package/corpus/core/docs/content/locales/hi-IN/template-plan.mdx +23 -7
  38. package/corpus/core/docs/content/locales/hi-IN/tracking.mdx +1 -1
  39. package/corpus/core/docs/content/locales/hi-IN/workspace-connections.mdx +1 -1
  40. package/corpus/core/docs/content/locales/ja-JP/cloneable-saas.mdx +0 -1
  41. package/corpus/core/docs/content/locales/ja-JP/plan-plugin.mdx +10 -9
  42. package/corpus/core/docs/content/locales/ja-JP/sharing.mdx +1 -2
  43. package/corpus/core/docs/content/locales/ja-JP/skills-guide.mdx +2 -3
  44. package/corpus/core/docs/content/locales/ja-JP/template-plan.mdx +23 -7
  45. package/corpus/core/docs/content/locales/ja-JP/tracking.mdx +1 -1
  46. package/corpus/core/docs/content/locales/ja-JP/workspace-connections.mdx +1 -1
  47. package/corpus/core/docs/content/locales/ko-KR/cloneable-saas.mdx +0 -1
  48. package/corpus/core/docs/content/locales/ko-KR/plan-plugin.mdx +10 -9
  49. package/corpus/core/docs/content/locales/ko-KR/sharing.mdx +1 -2
  50. package/corpus/core/docs/content/locales/ko-KR/skills-guide.mdx +2 -3
  51. package/corpus/core/docs/content/locales/ko-KR/template-plan.mdx +23 -7
  52. package/corpus/core/docs/content/locales/ko-KR/tracking.mdx +1 -1
  53. package/corpus/core/docs/content/locales/ko-KR/workspace-connections.mdx +1 -1
  54. package/corpus/core/docs/content/locales/pt-BR/cloneable-saas.mdx +0 -1
  55. package/corpus/core/docs/content/locales/pt-BR/plan-plugin.mdx +10 -9
  56. package/corpus/core/docs/content/locales/pt-BR/sharing.mdx +1 -2
  57. package/corpus/core/docs/content/locales/pt-BR/skills-guide.mdx +2 -3
  58. package/corpus/core/docs/content/locales/pt-BR/template-plan.mdx +23 -7
  59. package/corpus/core/docs/content/locales/pt-BR/tracking.mdx +1 -1
  60. package/corpus/core/docs/content/locales/pt-BR/workspace-connections.mdx +1 -1
  61. package/corpus/core/docs/content/locales/zh-CN/cloneable-saas.mdx +0 -1
  62. package/corpus/core/docs/content/locales/zh-CN/plan-plugin.mdx +10 -9
  63. package/corpus/core/docs/content/locales/zh-CN/sharing.mdx +1 -2
  64. package/corpus/core/docs/content/locales/zh-CN/skills-guide.mdx +2 -3
  65. package/corpus/core/docs/content/locales/zh-CN/template-plan.mdx +23 -7
  66. package/corpus/core/docs/content/locales/zh-CN/tracking.mdx +1 -1
  67. package/corpus/core/docs/content/locales/zh-CN/workspace-connections.mdx +1 -1
  68. package/corpus/core/docs/content/locales/zh-TW/cloneable-saas.mdx +0 -1
  69. package/corpus/core/docs/content/locales/zh-TW/plan-plugin.mdx +10 -9
  70. package/corpus/core/docs/content/locales/zh-TW/sharing.mdx +1 -2
  71. package/corpus/core/docs/content/locales/zh-TW/skills-guide.mdx +2 -3
  72. package/corpus/core/docs/content/locales/zh-TW/template-plan.mdx +23 -7
  73. package/corpus/core/docs/content/locales/zh-TW/tracking.mdx +1 -1
  74. package/corpus/core/docs/content/locales/zh-TW/workspace-connections.mdx +1 -1
  75. package/corpus/core/docs/content/plan-plugin.mdx +12 -11
  76. package/corpus/core/docs/content/sharing.mdx +1 -2
  77. package/corpus/core/docs/content/skills-guide.mdx +4 -3
  78. package/corpus/core/docs/content/template-plan.mdx +37 -6
  79. package/corpus/core/docs/content/tracking.mdx +1 -1
  80. package/corpus/core/docs/content/workspace-connections.mdx +1 -1
  81. package/corpus/core/package.json +6 -6
  82. package/corpus/core/src/agent/run-store.ts +1 -1
  83. package/corpus/core/src/chat-threads/store.ts +73 -11
  84. package/corpus/core/src/checkpoints/store.ts +13 -2
  85. package/corpus/core/src/cli/create.ts +3 -4
  86. package/corpus/core/src/cli/design-connect.ts +469 -9
  87. package/corpus/core/src/cli/index.ts +13 -0
  88. package/corpus/core/src/cli/plan-local.ts +281 -24
  89. package/corpus/core/src/cli/skills.ts +177 -21
  90. package/corpus/core/src/cli/templates-meta.ts +0 -13
  91. package/corpus/core/src/cli/visualize-repo.ts +715 -0
  92. package/corpus/core/src/client/AssistantChat.tsx +126 -17
  93. package/corpus/core/src/client/agent-chat-adapter.ts +6 -5
  94. package/corpus/core/src/client/app-providers.tsx +2 -2
  95. package/corpus/core/src/client/collab/index.ts +31 -0
  96. package/corpus/core/src/client/components/LiveCursorOverlay.tsx +16 -1
  97. package/corpus/core/src/client/components/PresenceBar.tsx +14 -1
  98. package/corpus/core/src/client/components/RecentEditHighlights.tsx +219 -0
  99. package/corpus/core/src/client/components/RemoteSelectionRings.tsx +40 -6
  100. package/corpus/core/src/client/index.ts +48 -0
  101. package/corpus/core/src/client/org/OrgSwitcher.tsx +0 -4
  102. package/corpus/core/src/client/rich-markdown-editor/SharedRichEditor.tsx +49 -32
  103. package/corpus/core/src/client/rich-markdown-editor/index.ts +6 -0
  104. package/corpus/core/src/client/rich-markdown-editor/surgical-apply.ts +192 -0
  105. package/corpus/core/src/client/rich-markdown-editor/useCollabReconcile.ts +59 -8
  106. package/corpus/core/src/client/session-replay.ts +181 -15
  107. package/corpus/core/src/client/sse-event-processor.ts +90 -1
  108. package/corpus/core/src/client/use-action.ts +123 -25
  109. package/corpus/core/src/client/use-agent-engine-configured.ts +7 -1
  110. package/corpus/core/src/client/use-chat-threads.ts +18 -7
  111. package/corpus/core/src/client/use-db-sync.ts +104 -19
  112. package/corpus/core/src/client/use-pinch-zoom.ts +76 -11
  113. package/corpus/core/src/client/visual-style-controls.tsx +475 -0
  114. package/corpus/core/src/collab/agent-presence.ts +191 -62
  115. package/corpus/core/src/collab/awareness.ts +83 -6
  116. package/corpus/core/src/collab/client.ts +89 -146
  117. package/corpus/core/src/collab/index.ts +34 -0
  118. package/corpus/core/src/collab/presence.ts +63 -3
  119. package/corpus/core/src/collab/recent-edits.ts +171 -0
  120. package/corpus/core/src/collab/undo.ts +432 -0
  121. package/corpus/core/src/collab/ydoc-manager.ts +68 -0
  122. package/corpus/core/src/connections/catalog.ts +2 -3
  123. package/corpus/core/src/db/create-get-db.ts +86 -1
  124. package/corpus/core/src/db/ensure-additive-columns.ts +430 -0
  125. package/corpus/core/src/db/index.ts +6 -0
  126. package/corpus/core/src/db/migrations.ts +236 -35
  127. package/corpus/core/src/jobs/scheduler.ts +17 -14
  128. package/corpus/core/src/observability/traces.ts +182 -1
  129. package/corpus/core/src/org/context.ts +79 -2
  130. package/corpus/core/src/server/agent-chat-plugin.ts +10 -6
  131. package/corpus/core/src/server/auth-marketing.ts +0 -11
  132. package/corpus/core/src/server/auth.ts +11 -4
  133. package/corpus/core/src/server/collab-plugin.ts +56 -13
  134. package/corpus/core/src/server/design-token-utils.ts +1 -1
  135. package/corpus/core/src/server/fusion-app.ts +447 -0
  136. package/corpus/core/src/server/index.ts +13 -0
  137. package/corpus/core/src/server/onboarding-html.ts +3 -4
  138. package/corpus/core/src/server/poll-events.ts +14 -2
  139. package/corpus/core/src/server/poll.ts +219 -12
  140. package/corpus/core/src/server/schema-prompt.ts +28 -9
  141. package/corpus/core/src/settings/store.ts +33 -2
  142. package/corpus/core/src/sharing/actions/set-resource-visibility.ts +2 -0
  143. package/corpus/core/src/sharing/actions/share-resource.ts +3 -0
  144. package/corpus/core/src/sharing/actions/unshare-resource.ts +2 -0
  145. package/corpus/core/src/styles/agent-native.css +0 -5
  146. package/corpus/core/src/templates/default/.agents/skills/real-time-collab/SKILL.md +82 -19
  147. package/corpus/core/src/templates/default/.agents/skills/real-time-sync/SKILL.md +15 -0
  148. package/corpus/core/src/templates/default/.agents/skills/storing-data/SKILL.md +8 -0
  149. package/corpus/core/src/templates/default/package.json +3 -3
  150. package/corpus/core/src/templates/workspace-core/.agents/skills/client-methods/SKILL.md +8 -0
  151. package/corpus/core/src/templates/workspace-core/.agents/skills/observability/SKILL.md +22 -0
  152. package/corpus/core/src/templates/workspace-core/.agents/skills/real-time-collab/SKILL.md +82 -19
  153. package/corpus/core/src/templates/workspace-core/.agents/skills/real-time-sync/SKILL.md +15 -0
  154. package/corpus/core/src/templates/workspace-core/.agents/skills/storing-data/SKILL.md +8 -0
  155. package/corpus/core/src/templates/workspace-core/.agents/skills/tracking/SKILL.md +1 -0
  156. package/corpus/core/src/tracking/providers.ts +22 -1
  157. package/corpus/templates/analytics/.agents/skills/real-time-sync/SKILL.md +15 -0
  158. package/corpus/templates/analytics/.agents/skills/session-replay/SKILL.md +20 -5
  159. package/corpus/templates/analytics/.agents/skills/storing-data/SKILL.md +8 -0
  160. package/corpus/templates/analytics/AGENTS.md +33 -6
  161. package/corpus/templates/analytics/actions/navigate.ts +14 -4
  162. package/corpus/templates/analytics/actions/query-agent-native-analytics.ts +1 -1
  163. package/corpus/templates/analytics/actions/view-screen.ts +57 -0
  164. package/corpus/templates/analytics/app/components/layout/CommandPalette.tsx +23 -1
  165. package/corpus/templates/analytics/app/components/layout/Header.tsx +1 -0
  166. package/corpus/templates/analytics/app/components/layout/Sidebar.tsx +21 -0
  167. package/corpus/templates/analytics/app/hooks/use-navigation-state.ts +7 -0
  168. package/corpus/templates/analytics/app/i18n/zh-TW.ts +15 -1
  169. package/corpus/templates/analytics/app/i18n-data.ts +151 -10
  170. package/corpus/templates/analytics/app/pages/Agents.tsx +118 -0
  171. package/corpus/templates/analytics/app/pages/DataSources.tsx +11 -1
  172. package/corpus/templates/analytics/app/pages/sessions/SessionDevToolsPanel.tsx +76 -40
  173. package/corpus/templates/analytics/app/pages/sessions/session-replay-devtools.ts +5 -0
  174. package/corpus/templates/analytics/app/routes/agents.tsx +10 -0
  175. package/corpus/templates/analytics/changelog/2026-07-03-agent-admin-tools-page.md +6 -0
  176. package/corpus/templates/analytics/changelog/2026-07-03-agent-llm-observability-dashboard.md +6 -0
  177. package/corpus/templates/analytics/changelog/2026-07-03-session-recordings-now-include-response-bodies-for-5xx-error.md +6 -0
  178. package/corpus/templates/analytics/docs/schemas/first-party-analytics.md +34 -0
  179. package/corpus/templates/analytics/docs/schemas/tracked-events.md +6 -0
  180. package/corpus/templates/analytics/package.json +3 -3
  181. package/corpus/templates/analytics/seeds/dashboards/agent-observability-llm.json +173 -0
  182. package/corpus/templates/analytics/server/jobs/analytics-alerts.ts +23 -5
  183. package/corpus/templates/analytics/server/lib/analytics-alerts.ts +58 -13
  184. package/corpus/templates/analytics/server/lib/dashboard-catalog.ts +23 -0
  185. package/corpus/templates/analytics/server/lib/dashboard-seeds.ts +5 -0
  186. package/corpus/templates/analytics/server/lib/session-replay-agent-context.ts +120 -8
  187. package/corpus/templates/analytics/server/lib/session-replay.ts +3 -2
  188. package/corpus/templates/analytics/server/plugins/db.ts +93 -2
  189. package/corpus/templates/analytics/server/routes/api/session-replay/agent-diagnostics.json.get.ts +45 -1
  190. package/corpus/templates/analytics/shared/session-replay-diagnostics.ts +10 -0
  191. package/corpus/templates/assets/.agents/skills/real-time-collab/SKILL.md +82 -19
  192. package/corpus/templates/assets/.agents/skills/real-time-sync/SKILL.md +15 -0
  193. package/corpus/templates/assets/.agents/skills/storing-data/SKILL.md +8 -0
  194. package/corpus/templates/assets/package.json +3 -3
  195. package/corpus/templates/assets/server/plugins/db.ts +63 -2
  196. package/corpus/templates/brain/.agents/skills/real-time-sync/SKILL.md +15 -0
  197. package/corpus/templates/brain/package.json +3 -3
  198. package/corpus/templates/brain/server/plugins/db.ts +75 -2
  199. package/corpus/templates/calendar/.agents/skills/real-time-sync/SKILL.md +15 -0
  200. package/corpus/templates/calendar/.agents/skills/storing-data/SKILL.md +8 -0
  201. package/corpus/templates/calendar/package.json +3 -3
  202. package/corpus/templates/calendar/server/plugins/db.ts +64 -2
  203. package/corpus/templates/chat/.agents/skills/real-time-sync/SKILL.md +15 -0
  204. package/corpus/templates/chat/package.json +3 -3
  205. package/corpus/templates/clips/actions/finalize-recording.ts +50 -40
  206. package/corpus/templates/clips/app/routes/r.$recordingId.tsx +8 -6
  207. package/corpus/templates/clips/app/routes/share.$shareId.tsx +3 -3
  208. package/corpus/templates/clips/changelog/2026-07-03-mobile-recording-pages-keep-videos-in-a-16-9-player-with-act.md +6 -0
  209. package/corpus/templates/clips/desktop/src/lib/recorder.ts +245 -77
  210. package/corpus/templates/clips/package.json +3 -3
  211. package/corpus/templates/clips/server/lib/recording-upload-state.ts +56 -0
  212. package/corpus/templates/clips/server/plugins/db.ts +68 -1
  213. package/corpus/templates/clips/server/routes/api/uploads/[recordingId]/chunk.post.ts +27 -3
  214. package/corpus/templates/content/.agents/skills/real-time-sync/SKILL.md +15 -0
  215. package/corpus/templates/content/.agents/skills/storing-data/SKILL.md +8 -0
  216. package/corpus/templates/content/actions/edit-document.ts +48 -1
  217. package/corpus/templates/content/actions/list-documents.ts +101 -94
  218. package/corpus/templates/content/actions/search-documents.ts +19 -3
  219. package/corpus/templates/content/actions/update-document.ts +54 -1
  220. package/corpus/templates/content/app/components/editor/DocumentEditor.tsx +127 -7
  221. package/corpus/templates/content/app/components/editor/VisualEditor.tsx +97 -2
  222. package/corpus/templates/content/changelog/2026-07-03-agent-document-edits-now-appear-as-a-live-collaborator-prese.md +6 -0
  223. package/corpus/templates/content/changelog/2026-07-03-document-search-and-list-views-load-faster-on-large-workspac.md +6 -0
  224. package/corpus/templates/content/package.json +3 -3
  225. package/corpus/templates/content/server/plugins/db.ts +57 -1
  226. package/corpus/templates/design/.agents/skills/design-generation/SKILL.md +190 -13
  227. package/corpus/templates/design/.agents/skills/design-systems/SKILL.md +16 -4
  228. package/corpus/templates/design/.agents/skills/export-handoff/SKILL.md +46 -3
  229. package/corpus/templates/design/.agents/skills/full-app-build/SKILL.md +140 -0
  230. package/corpus/templates/design/.agents/skills/visual-edit/SKILL.md +20 -0
  231. package/corpus/templates/design/AGENTS.md +83 -13
  232. package/corpus/templates/design/actions/add-fusion-screens.ts +91 -0
  233. package/corpus/templates/design/actions/apply-a11y-fix.ts +5 -1
  234. package/corpus/templates/design/actions/apply-component-prop-edit.ts +24 -69
  235. package/corpus/templates/design/actions/apply-fusion-edits.ts +161 -0
  236. package/corpus/templates/design/actions/apply-motion-edit.ts +29 -2
  237. package/corpus/templates/design/actions/apply-visual-edit.ts +38 -3
  238. package/corpus/templates/design/actions/connect-localhost.ts +25 -18
  239. package/corpus/templates/design/actions/create-component.ts +5 -1
  240. package/corpus/templates/design/actions/create-fusion-app.ts +202 -0
  241. package/corpus/templates/design/actions/deploy-fusion-app.ts +123 -0
  242. package/corpus/templates/design/actions/edit-design.ts +13 -16
  243. package/corpus/templates/design/actions/export-pdf.ts +8 -1
  244. package/corpus/templates/design/actions/export-zip.ts +10 -1
  245. package/corpus/templates/design/actions/get-fusion-deploy-status.ts +86 -0
  246. package/corpus/templates/design/actions/get-motion-timeline.ts +26 -20
  247. package/corpus/templates/design/actions/grant-localhost-write-consent.ts +10 -0
  248. package/corpus/templates/design/actions/insert-asset.ts +190 -7
  249. package/corpus/templates/design/actions/list-fusion-edits.ts +96 -0
  250. package/corpus/templates/design/actions/list-local-files.ts +133 -0
  251. package/corpus/templates/design/actions/open-visual-edit.ts +27 -5
  252. package/corpus/templates/design/actions/present-design-variants.ts +2 -2
  253. package/corpus/templates/design/actions/push-fusion-app.ts +62 -0
  254. package/corpus/templates/design/actions/queue-fusion-edit.ts +112 -0
  255. package/corpus/templates/design/actions/read-local-file.ts +139 -0
  256. package/corpus/templates/design/actions/revoke-localhost-write-consent.ts +18 -14
  257. package/corpus/templates/design/actions/run-design-audit.ts +7 -4
  258. package/corpus/templates/design/actions/send-fusion-message.ts +69 -0
  259. package/corpus/templates/design/actions/sync-fusion-app.ts +196 -0
  260. package/corpus/templates/design/actions/write-local-file.ts +162 -36
  261. package/corpus/templates/design/app/components/design/CanvasContextMenu.tsx +12 -0
  262. package/corpus/templates/design/app/components/design/DesignCanvas.tsx +600 -66
  263. package/corpus/templates/design/app/components/design/EditPanel.tsx +793 -304
  264. package/corpus/templates/design/app/components/design/FusionAppBanner.tsx +328 -0
  265. package/corpus/templates/design/app/components/design/LayersPanel.tsx +671 -154
  266. package/corpus/templates/design/app/components/design/LocalhostWriteConsentDialog.tsx +1 -1
  267. package/corpus/templates/design/app/components/design/MotionDock.tsx +234 -46
  268. package/corpus/templates/design/app/components/design/MultiScreenCanvas.tsx +2070 -420
  269. package/corpus/templates/design/app/components/design/StatesPanel.tsx +25 -2
  270. package/corpus/templates/design/app/components/design/TweaksPanel.tsx +7 -98
  271. package/corpus/templates/design/app/components/design/bridge/editor-chrome.bridge.ts +640 -72
  272. package/corpus/templates/design/app/components/design/bridge/motion-preview.bridge.ts +605 -0
  273. package/corpus/templates/design/app/components/design/canvas-primitive-style.ts +50 -26
  274. package/corpus/templates/design/app/components/design/code-workbench/ActivityBar.tsx +85 -0
  275. package/corpus/templates/design/app/components/design/code-workbench/CodeWorkbench.tsx +466 -0
  276. package/corpus/templates/design/app/components/design/code-workbench/SideBar.tsx +53 -0
  277. package/corpus/templates/design/app/components/design/code-workbench/commands.ts +339 -0
  278. package/corpus/templates/design/app/components/design/code-workbench/editor/Breadcrumbs.tsx +42 -0
  279. package/corpus/templates/design/app/components/design/code-workbench/editor/BufferSync.tsx +128 -0
  280. package/corpus/templates/design/app/components/design/code-workbench/editor/EditorTabs.tsx +363 -0
  281. package/corpus/templates/design/app/components/design/code-workbench/editor/MonacoHost.tsx +268 -0
  282. package/corpus/templates/design/app/components/design/code-workbench/editor/StatusBar.tsx +208 -0
  283. package/corpus/templates/design/app/components/design/code-workbench/editor/monaco-setup.ts +61 -0
  284. package/corpus/templates/design/app/components/design/code-workbench/editor/monaco-theme-palette.ts +191 -0
  285. package/corpus/templates/design/app/components/design/code-workbench/editor/monaco-theme.ts +29 -0
  286. package/corpus/templates/design/app/components/design/code-workbench/editor/status-bar-lang.ts +21 -0
  287. package/corpus/templates/design/app/components/design/code-workbench/editor/tab-drag.ts +27 -0
  288. package/corpus/templates/design/app/components/design/code-workbench/explorer/ExplorerView.tsx +155 -0
  289. package/corpus/templates/design/app/components/design/code-workbench/explorer/FileTree.tsx +551 -0
  290. package/corpus/templates/design/app/components/design/code-workbench/explorer/file-icons.tsx +115 -0
  291. package/corpus/templates/design/app/components/design/code-workbench/format/format-on-open.ts +65 -0
  292. package/corpus/templates/design/app/components/design/code-workbench/format/prettier-format.ts +182 -0
  293. package/corpus/templates/design/app/components/design/code-workbench/model-registry.ts +133 -0
  294. package/corpus/templates/design/app/components/design/code-workbench/quickinput/QuickInput.tsx +563 -0
  295. package/corpus/templates/design/app/components/design/code-workbench/quickinput/fuzzy.ts +170 -0
  296. package/corpus/templates/design/app/components/design/code-workbench/search/SearchView.tsx +508 -0
  297. package/corpus/templates/design/app/components/design/code-workbench/search/search-engine.ts +280 -0
  298. package/corpus/templates/design/app/components/design/code-workbench/store.tsx +734 -0
  299. package/corpus/templates/design/app/components/design/code-workbench/workspace/create-providers.ts +39 -0
  300. package/corpus/templates/design/app/components/design/code-workbench/workspace/inline-provider.ts +196 -0
  301. package/corpus/templates/design/app/components/design/code-workbench/workspace/localhost-provider.ts +177 -0
  302. package/corpus/templates/design/app/components/design/code-workbench/workspace/tree.ts +110 -0
  303. package/corpus/templates/design/app/components/design/code-workbench/workspace/types.ts +103 -0
  304. package/corpus/templates/design/app/components/design/code-workbench-theme.ts +68 -0
  305. package/corpus/templates/design/app/components/design/inspector/AutoLayoutMatrix.tsx +16 -4
  306. package/corpus/templates/design/app/components/design/inspector/DesignColorPicker.tsx +217 -113
  307. package/corpus/templates/design/app/components/design/inspector/GradientEditor.tsx +111 -5
  308. package/corpus/templates/design/app/components/design/inspector/ImageFillControls.tsx +13 -2
  309. package/corpus/templates/design/app/components/design/inspector/ScrubInput.tsx +79 -16
  310. package/corpus/templates/design/app/components/design/inspector/index.ts +9 -0
  311. package/corpus/templates/design/app/components/design/inspector/scrub-input-utils.ts +67 -2
  312. package/corpus/templates/design/app/components/design/types.ts +16 -0
  313. package/corpus/templates/design/app/components/editor/PromptDialog.tsx +80 -1
  314. package/corpus/templates/design/app/components/visual-editor/CanvasCommentPins.tsx +24 -6
  315. package/corpus/templates/design/app/components/visual-editor/DrawOverlay.tsx +15 -1
  316. package/corpus/templates/design/app/components/visual-editor/SaveStatusIndicator.tsx +6 -16
  317. package/corpus/templates/design/app/hooks/useDesignHotkeys.ts +77 -0
  318. package/corpus/templates/design/app/i18n/zh-TW.ts +2 -0
  319. package/corpus/templates/design/app/i18n-data.ts +31 -0
  320. package/corpus/templates/design/app/lib/design-import.ts +95 -0
  321. package/corpus/templates/design/app/pages/DesignEditor.tsx +5586 -1112
  322. package/corpus/templates/design/app/pages/Index.tsx +90 -17
  323. package/corpus/templates/design/changelog/2026-07-03-canvas-interactions-now-match-figma-rotation-aware-resizing-.md +6 -0
  324. package/corpus/templates/design/changelog/2026-07-03-inspector-fixes-mixed-selections-show-mixed-instead-of-wrong.md +6 -0
  325. package/corpus/templates/design/changelog/2026-07-03-keyframe-timeline-works-reliably-drag-keyframes-smoothly-pic.md +6 -0
  326. package/corpus/templates/design/changelog/2026-07-03-layers-panel-matches-figma-top-layer-on-top-drag-with-auto-s.md +6 -0
  327. package/corpus/templates/design/changelog/2026-07-03-much-faster-editor-smooth-dragging-zooming-and-panel-updates.md +6 -0
  328. package/corpus/templates/design/changelog/2026-07-03-pen-tool-refinements-click-the-first-point-to-close-with-a-d.md +6 -0
  329. package/corpus/templates/design/changelog/2026-07-03-text-editing-enter-adds-a-line-break-international-ime-typin.md +6 -0
  330. package/corpus/templates/design/changelog/2026-07-03-the-ai-now-edits-like-a-collaborator-on-canvas-its-cursor-gl.md +6 -0
  331. package/corpus/templates/design/changelog/2026-07-03-the-code-panel-is-now-a-full-vs-code-style-editor-with-a-fil.md +6 -0
  332. package/corpus/templates/design/changelog/2026-07-03-undo-and-redo-are-dependable-across-agent-edits-screen-switc.md +6 -0
  333. package/corpus/templates/design/package.json +4 -3
  334. package/corpus/templates/design/server/db/schema.ts +31 -0
  335. package/corpus/templates/design/server/lib/design-export.ts +43 -1
  336. package/corpus/templates/design/server/lib/fusion-screens.ts +246 -0
  337. package/corpus/templates/design/server/plugins/db.ts +89 -2
  338. package/corpus/templates/design/shared/board-file.ts +25 -5
  339. package/corpus/templates/design/shared/canvas-math.ts +754 -9
  340. package/corpus/templates/design/shared/code-layer.ts +304 -26
  341. package/corpus/templates/design/shared/collab-selection.ts +52 -0
  342. package/corpus/templates/design/shared/color-utils.ts +84 -0
  343. package/corpus/templates/design/shared/design-source-capabilities.ts +16 -7
  344. package/corpus/templates/design/shared/full-app.ts +126 -0
  345. package/corpus/templates/design/shared/motion-compiler.ts +75 -31
  346. package/corpus/templates/design/shared/motion-timeline.ts +335 -0
  347. package/corpus/templates/design/shared/pen-path.ts +496 -23
  348. package/corpus/templates/dispatch/package.json +3 -3
  349. package/corpus/templates/forms/.agents/skills/real-time-sync/SKILL.md +15 -0
  350. package/corpus/templates/forms/.agents/skills/storing-data/SKILL.md +8 -0
  351. package/corpus/templates/forms/package.json +3 -3
  352. package/corpus/templates/forms/server/plugins/db.ts +62 -2
  353. package/corpus/templates/macros/package.json +3 -3
  354. package/corpus/templates/macros/server/plugins/db.ts +63 -2
  355. package/corpus/templates/mail/.agents/skills/real-time-sync/SKILL.md +15 -0
  356. package/corpus/templates/mail/.agents/skills/storing-data/SKILL.md +8 -0
  357. package/corpus/templates/mail/package.json +3 -3
  358. package/corpus/templates/mail/server/lib/contact-frequency.ts +42 -15
  359. package/corpus/templates/mail/server/plugins/db.ts +63 -2
  360. package/corpus/templates/plan/.agents/skills/real-time-sync/SKILL.md +15 -0
  361. package/corpus/templates/plan/.agents/skills/visual-plan/SKILL.md +9 -3
  362. package/corpus/templates/plan/.agents/skills/visualize-repo/SKILL.md +92 -0
  363. package/corpus/templates/plan/actions/export-visual-plan.ts +5 -0
  364. package/corpus/templates/plan/actions/get-local-plan-folder.ts +4 -22
  365. package/corpus/templates/plan/actions/get-plan-version.ts +6 -16
  366. package/corpus/templates/plan/actions/list-plan-versions.ts +48 -20
  367. package/corpus/templates/plan/actions/patch-visual-plan-source.ts +41 -1
  368. package/corpus/templates/plan/actions/promote-local-plan-folder.ts +4 -22
  369. package/corpus/templates/plan/actions/update-local-plan-comments.ts +4 -2
  370. package/corpus/templates/plan/actions/update-local-plan-folder.ts +4 -22
  371. package/corpus/templates/plan/actions/update-visual-plan.ts +60 -1
  372. package/corpus/templates/plan/agent-native.app-skill.json +10 -0
  373. package/corpus/templates/plan/app/components/editor/PlanDocumentEditor.tsx +138 -39
  374. package/corpus/templates/plan/app/components/editor/usePlanUndoStack.ts +165 -23
  375. package/corpus/templates/plan/app/components/plan/PlanContentRenderer.tsx +80 -4
  376. package/corpus/templates/plan/app/global.css +11 -9
  377. package/corpus/templates/plan/app/hooks/use-navigation-state.ts +10 -1
  378. package/corpus/templates/plan/app/hooks/use-plan-presence.ts +66 -0
  379. package/corpus/templates/plan/app/pages/PlansPage.tsx +215 -63
  380. package/corpus/templates/plan/changelog/2026-07-03-local-visual-plans-and-recaps-can-save-comments-without-sign.md +6 -0
  381. package/corpus/templates/plan/changelog/2026-07-03-plan-tabs-render-nested-text-instead-of-raw-json.md +6 -0
  382. package/corpus/templates/plan/changelog/2026-07-03-plans-are-now-fully-real-time-collaborative-multiple-people-.md +6 -0
  383. package/corpus/templates/plan/changelog/2026-07-03-plans-open-and-refresh-faster-especially-long-lived-plans-wi.md +6 -0
  384. package/corpus/templates/plan/changelog/2026-07-03-undo-now-survives-agent-edits-cmd-z-keeps-working-on-your-ow.md +6 -0
  385. package/corpus/templates/plan/package.json +5 -3
  386. package/corpus/templates/plan/server/db/schema.ts +12 -0
  387. package/corpus/templates/plan/server/lib/local-plan-kind.ts +25 -0
  388. package/corpus/templates/plan/server/lib/plan-versions.ts +83 -1
  389. package/corpus/templates/plan/server/lib/public-action-paths.ts +0 -2
  390. package/corpus/templates/plan/server/plans.ts +26 -3
  391. package/corpus/templates/plan/server/plugins/db.ts +105 -2
  392. package/corpus/templates/slides/.agents/skills/slide-editing/SKILL.md +8 -4
  393. package/corpus/templates/slides/AGENTS.md +4 -0
  394. package/corpus/templates/slides/actions/_agent-presence.ts +48 -0
  395. package/corpus/templates/slides/actions/add-slide.ts +16 -18
  396. package/corpus/templates/slides/actions/patch-deck.ts +4 -2
  397. package/corpus/templates/slides/actions/update-slide.ts +114 -77
  398. package/corpus/templates/slides/actions/view-screen.ts +39 -0
  399. package/corpus/templates/slides/app/components/editor/EditorSidebar.tsx +47 -3
  400. package/corpus/templates/slides/app/components/editor/EditorToolbar.tsx +32 -35
  401. package/corpus/templates/slides/app/components/editor/SlideEditor.tsx +625 -199
  402. package/corpus/templates/slides/app/components/editor/SlideStyleInspector.tsx +342 -0
  403. package/corpus/templates/slides/app/components/editor/TweaksPanel.tsx +46 -96
  404. package/corpus/templates/slides/app/components/visual-editor/SaveStatusIndicator.tsx +8 -1
  405. package/corpus/templates/slides/app/context/DeckContext.tsx +589 -176
  406. package/corpus/templates/slides/app/hooks/use-deck-presence.ts +84 -42
  407. package/corpus/templates/slides/app/i18n/ar-SA.ts +46 -0
  408. package/corpus/templates/slides/app/i18n/de-DE.ts +46 -0
  409. package/corpus/templates/slides/app/i18n/en-US.ts +46 -0
  410. package/corpus/templates/slides/app/i18n/es-ES.ts +46 -0
  411. package/corpus/templates/slides/app/i18n/fr-FR.ts +46 -0
  412. package/corpus/templates/slides/app/i18n/hi-IN.ts +46 -0
  413. package/corpus/templates/slides/app/i18n/ja-JP.ts +46 -0
  414. package/corpus/templates/slides/app/i18n/ko-KR.ts +46 -0
  415. package/corpus/templates/slides/app/i18n/pt-BR.ts +46 -0
  416. package/corpus/templates/slides/app/i18n/zh-CN.ts +46 -0
  417. package/corpus/templates/slides/app/i18n/zh-TW.ts +46 -0
  418. package/corpus/templates/slides/app/pages/DeckEditor.tsx +25 -13
  419. package/corpus/templates/slides/changelog/2026-07-03-figma-style-slide-editing.md +6 -0
  420. package/corpus/templates/slides/changelog/2026-07-03-see-the-ai-working-with-you-when-the-agent-edits-a-slide-it-.md +6 -0
  421. package/corpus/templates/slides/changelog/2026-07-03-undo-redo-is-now-precise-and-safe-with-collaborators-it-only.md +6 -0
  422. package/corpus/templates/slides/package.json +3 -3
  423. package/corpus/templates/slides/server/handlers/decks.ts +31 -3
  424. package/corpus/templates/slides/server/plugins/db.ts +65 -2
  425. package/corpus/templates/videos/netlify.toml +1 -12
  426. package/dist/agent/run-store.js +1 -1
  427. package/dist/agent/run-store.js.map +1 -1
  428. package/dist/chat-threads/store.d.ts +9 -1
  429. package/dist/chat-threads/store.d.ts.map +1 -1
  430. package/dist/chat-threads/store.js +63 -11
  431. package/dist/chat-threads/store.js.map +1 -1
  432. package/dist/checkpoints/store.d.ts.map +1 -1
  433. package/dist/checkpoints/store.js +10 -2
  434. package/dist/checkpoints/store.js.map +1 -1
  435. package/dist/cli/create.d.ts.map +1 -1
  436. package/dist/cli/create.js +3 -5
  437. package/dist/cli/create.js.map +1 -1
  438. package/dist/cli/design-connect.d.ts +49 -1
  439. package/dist/cli/design-connect.d.ts.map +1 -1
  440. package/dist/cli/design-connect.js +414 -9
  441. package/dist/cli/design-connect.js.map +1 -1
  442. package/dist/cli/index.js +12 -0
  443. package/dist/cli/index.js.map +1 -1
  444. package/dist/cli/plan-local.d.ts +24 -0
  445. package/dist/cli/plan-local.d.ts.map +1 -1
  446. package/dist/cli/plan-local.js +188 -20
  447. package/dist/cli/plan-local.js.map +1 -1
  448. package/dist/cli/skills.d.ts +3 -1
  449. package/dist/cli/skills.d.ts.map +1 -1
  450. package/dist/cli/skills.js +173 -21
  451. package/dist/cli/skills.js.map +1 -1
  452. package/dist/cli/templates-meta.d.ts.map +1 -1
  453. package/dist/cli/templates-meta.js +0 -14
  454. package/dist/cli/templates-meta.js.map +1 -1
  455. package/dist/cli/visualize-repo.d.ts +49 -0
  456. package/dist/cli/visualize-repo.d.ts.map +1 -0
  457. package/dist/cli/visualize-repo.js +561 -0
  458. package/dist/cli/visualize-repo.js.map +1 -0
  459. package/dist/client/AssistantChat.d.ts.map +1 -1
  460. package/dist/client/AssistantChat.js +120 -15
  461. package/dist/client/AssistantChat.js.map +1 -1
  462. package/dist/client/agent-chat-adapter.d.ts.map +1 -1
  463. package/dist/client/agent-chat-adapter.js +6 -5
  464. package/dist/client/agent-chat-adapter.js.map +1 -1
  465. package/dist/client/app-providers.d.ts +2 -2
  466. package/dist/client/app-providers.js.map +1 -1
  467. package/dist/client/collab/index.d.ts +4 -1
  468. package/dist/client/collab/index.d.ts.map +1 -1
  469. package/dist/client/collab/index.js +3 -0
  470. package/dist/client/collab/index.js.map +1 -1
  471. package/dist/client/components/LiveCursorOverlay.d.ts.map +1 -1
  472. package/dist/client/components/LiveCursorOverlay.js +11 -3
  473. package/dist/client/components/LiveCursorOverlay.js.map +1 -1
  474. package/dist/client/components/PresenceBar.d.ts.map +1 -1
  475. package/dist/client/components/PresenceBar.js +6 -1
  476. package/dist/client/components/PresenceBar.js.map +1 -1
  477. package/dist/client/components/RecentEditHighlights.d.ts +43 -0
  478. package/dist/client/components/RecentEditHighlights.d.ts.map +1 -0
  479. package/dist/client/components/RecentEditHighlights.js +146 -0
  480. package/dist/client/components/RecentEditHighlights.js.map +1 -0
  481. package/dist/client/components/RemoteSelectionRings.d.ts +9 -0
  482. package/dist/client/components/RemoteSelectionRings.d.ts.map +1 -1
  483. package/dist/client/components/RemoteSelectionRings.js +22 -8
  484. package/dist/client/components/RemoteSelectionRings.js.map +1 -1
  485. package/dist/client/index.d.ts +6 -1
  486. package/dist/client/index.d.ts.map +1 -1
  487. package/dist/client/index.js +7 -0
  488. package/dist/client/index.js.map +1 -1
  489. package/dist/client/org/OrgSwitcher.d.ts.map +1 -1
  490. package/dist/client/org/OrgSwitcher.js +1 -3
  491. package/dist/client/org/OrgSwitcher.js.map +1 -1
  492. package/dist/client/rich-markdown-editor/SharedRichEditor.d.ts +8 -1
  493. package/dist/client/rich-markdown-editor/SharedRichEditor.d.ts.map +1 -1
  494. package/dist/client/rich-markdown-editor/SharedRichEditor.js +8 -2
  495. package/dist/client/rich-markdown-editor/SharedRichEditor.js.map +1 -1
  496. package/dist/client/rich-markdown-editor/index.d.ts +1 -0
  497. package/dist/client/rich-markdown-editor/index.d.ts.map +1 -1
  498. package/dist/client/rich-markdown-editor/index.js +1 -0
  499. package/dist/client/rich-markdown-editor/index.js.map +1 -1
  500. package/dist/client/rich-markdown-editor/surgical-apply.d.ts +66 -0
  501. package/dist/client/rich-markdown-editor/surgical-apply.d.ts.map +1 -0
  502. package/dist/client/rich-markdown-editor/surgical-apply.js +147 -0
  503. package/dist/client/rich-markdown-editor/surgical-apply.js.map +1 -0
  504. package/dist/client/rich-markdown-editor/useCollabReconcile.d.ts +18 -2
  505. package/dist/client/rich-markdown-editor/useCollabReconcile.d.ts.map +1 -1
  506. package/dist/client/rich-markdown-editor/useCollabReconcile.js +39 -8
  507. package/dist/client/rich-markdown-editor/useCollabReconcile.js.map +1 -1
  508. package/dist/client/session-replay.d.ts +10 -1
  509. package/dist/client/session-replay.d.ts.map +1 -1
  510. package/dist/client/session-replay.js +134 -7
  511. package/dist/client/session-replay.js.map +1 -1
  512. package/dist/client/sse-event-processor.d.ts.map +1 -1
  513. package/dist/client/sse-event-processor.js +81 -1
  514. package/dist/client/sse-event-processor.js.map +1 -1
  515. package/dist/client/use-action.d.ts +24 -0
  516. package/dist/client/use-action.d.ts.map +1 -1
  517. package/dist/client/use-action.js +109 -27
  518. package/dist/client/use-action.js.map +1 -1
  519. package/dist/client/use-agent-engine-configured.d.ts.map +1 -1
  520. package/dist/client/use-agent-engine-configured.js +7 -1
  521. package/dist/client/use-agent-engine-configured.js.map +1 -1
  522. package/dist/client/use-chat-threads.d.ts.map +1 -1
  523. package/dist/client/use-chat-threads.js +11 -3
  524. package/dist/client/use-chat-threads.js.map +1 -1
  525. package/dist/client/use-db-sync.d.ts +36 -0
  526. package/dist/client/use-db-sync.d.ts.map +1 -1
  527. package/dist/client/use-db-sync.js +68 -12
  528. package/dist/client/use-db-sync.js.map +1 -1
  529. package/dist/client/use-pinch-zoom.d.ts.map +1 -1
  530. package/dist/client/use-pinch-zoom.js +76 -11
  531. package/dist/client/use-pinch-zoom.js.map +1 -1
  532. package/dist/client/visual-style-controls.d.ts +79 -0
  533. package/dist/client/visual-style-controls.d.ts.map +1 -0
  534. package/dist/client/visual-style-controls.js +150 -0
  535. package/dist/client/visual-style-controls.js.map +1 -0
  536. package/dist/collab/agent-presence.d.ts +51 -5
  537. package/dist/collab/agent-presence.d.ts.map +1 -1
  538. package/dist/collab/agent-presence.js +144 -58
  539. package/dist/collab/agent-presence.js.map +1 -1
  540. package/dist/collab/awareness-store.d.ts +32 -0
  541. package/dist/collab/awareness-store.d.ts.map +1 -0
  542. package/dist/collab/awareness-store.js +0 -0
  543. package/dist/collab/awareness-store.js.map +1 -0
  544. package/dist/collab/awareness.d.ts +14 -3
  545. package/dist/collab/awareness.d.ts.map +1 -1
  546. package/dist/collab/awareness.js +53 -5
  547. package/dist/collab/awareness.js.map +1 -1
  548. package/dist/collab/client.d.ts +2 -0
  549. package/dist/collab/client.d.ts.map +1 -1
  550. package/dist/collab/client.js +79 -119
  551. package/dist/collab/client.js.map +1 -1
  552. package/dist/collab/index.d.ts +3 -1
  553. package/dist/collab/index.d.ts.map +1 -1
  554. package/dist/collab/index.js +5 -1
  555. package/dist/collab/index.js.map +1 -1
  556. package/dist/collab/presence.d.ts.map +1 -1
  557. package/dist/collab/presence.js +54 -3
  558. package/dist/collab/presence.js.map +1 -1
  559. package/dist/collab/recent-edits.d.ts +87 -0
  560. package/dist/collab/recent-edits.d.ts.map +1 -0
  561. package/dist/collab/recent-edits.js +116 -0
  562. package/dist/collab/recent-edits.js.map +1 -0
  563. package/dist/collab/undo.d.ts +121 -0
  564. package/dist/collab/undo.d.ts.map +1 -0
  565. package/dist/collab/undo.js +244 -0
  566. package/dist/collab/undo.js.map +1 -0
  567. package/dist/collab/ydoc-manager.d.ts +10 -0
  568. package/dist/collab/ydoc-manager.d.ts.map +1 -1
  569. package/dist/collab/ydoc-manager.js +57 -0
  570. package/dist/collab/ydoc-manager.js.map +1 -1
  571. package/dist/connections/catalog.d.ts +2 -2
  572. package/dist/connections/catalog.d.ts.map +1 -1
  573. package/dist/connections/catalog.js +1 -1
  574. package/dist/connections/catalog.js.map +1 -1
  575. package/dist/db/create-get-db.d.ts +22 -0
  576. package/dist/db/create-get-db.d.ts.map +1 -1
  577. package/dist/db/create-get-db.js +73 -1
  578. package/dist/db/create-get-db.js.map +1 -1
  579. package/dist/db/ensure-additive-columns.d.ts +93 -0
  580. package/dist/db/ensure-additive-columns.d.ts.map +1 -0
  581. package/dist/db/ensure-additive-columns.js +355 -0
  582. package/dist/db/ensure-additive-columns.js.map +1 -0
  583. package/dist/db/index.d.ts +1 -0
  584. package/dist/db/index.d.ts.map +1 -1
  585. package/dist/db/index.js +1 -0
  586. package/dist/db/index.js.map +1 -1
  587. package/dist/db/migrations.d.ts +70 -0
  588. package/dist/db/migrations.d.ts.map +1 -1
  589. package/dist/db/migrations.js +196 -33
  590. package/dist/db/migrations.js.map +1 -1
  591. package/dist/jobs/scheduler.js +17 -10
  592. package/dist/jobs/scheduler.js.map +1 -1
  593. package/dist/notifications/routes.d.ts +3 -3
  594. package/dist/observability/routes.d.ts +5 -5
  595. package/dist/observability/traces.d.ts.map +1 -1
  596. package/dist/observability/traces.js +155 -1
  597. package/dist/observability/traces.js.map +1 -1
  598. package/dist/org/context.d.ts +7 -0
  599. package/dist/org/context.d.ts.map +1 -1
  600. package/dist/org/context.js +54 -2
  601. package/dist/org/context.js.map +1 -1
  602. package/dist/progress/routes.d.ts +1 -1
  603. package/dist/resources/handlers.d.ts +3 -3
  604. package/dist/secrets/routes.d.ts +6 -6
  605. package/dist/server/agent-chat-plugin.d.ts.map +1 -1
  606. package/dist/server/agent-chat-plugin.js +10 -6
  607. package/dist/server/agent-chat-plugin.js.map +1 -1
  608. package/dist/server/auth-marketing.d.ts.map +1 -1
  609. package/dist/server/auth-marketing.js +0 -10
  610. package/dist/server/auth-marketing.js.map +1 -1
  611. package/dist/server/auth.d.ts.map +1 -1
  612. package/dist/server/auth.js +6 -4
  613. package/dist/server/auth.js.map +1 -1
  614. package/dist/server/collab-plugin.d.ts.map +1 -1
  615. package/dist/server/collab-plugin.js +45 -13
  616. package/dist/server/collab-plugin.js.map +1 -1
  617. package/dist/server/design-token-utils.d.ts +1 -1
  618. package/dist/server/design-token-utils.js +1 -1
  619. package/dist/server/design-token-utils.js.map +1 -1
  620. package/dist/server/fusion-app.d.ts +107 -0
  621. package/dist/server/fusion-app.d.ts.map +1 -0
  622. package/dist/server/fusion-app.js +371 -0
  623. package/dist/server/fusion-app.js.map +1 -0
  624. package/dist/server/index.d.ts +1 -0
  625. package/dist/server/index.d.ts.map +1 -1
  626. package/dist/server/index.js +1 -0
  627. package/dist/server/index.js.map +1 -1
  628. package/dist/server/onboarding-html.d.ts.map +1 -1
  629. package/dist/server/onboarding-html.js +3 -4
  630. package/dist/server/onboarding-html.js.map +1 -1
  631. package/dist/server/poll-events.d.ts +2 -0
  632. package/dist/server/poll-events.d.ts.map +1 -1
  633. package/dist/server/poll-events.js +7 -2
  634. package/dist/server/poll-events.js.map +1 -1
  635. package/dist/server/poll.d.ts +47 -3
  636. package/dist/server/poll.d.ts.map +1 -1
  637. package/dist/server/poll.js +176 -10
  638. package/dist/server/poll.js.map +1 -1
  639. package/dist/server/schema-prompt.d.ts.map +1 -1
  640. package/dist/server/schema-prompt.js +24 -7
  641. package/dist/server/schema-prompt.js.map +1 -1
  642. package/dist/settings/store.d.ts.map +1 -1
  643. package/dist/settings/store.js +32 -3
  644. package/dist/settings/store.js.map +1 -1
  645. package/dist/sharing/actions/set-resource-visibility.js +2 -0
  646. package/dist/sharing/actions/set-resource-visibility.js.map +1 -1
  647. package/dist/sharing/actions/share-resource.d.ts.map +1 -1
  648. package/dist/sharing/actions/share-resource.js +3 -0
  649. package/dist/sharing/actions/share-resource.js.map +1 -1
  650. package/dist/sharing/actions/unshare-resource.js +2 -0
  651. package/dist/sharing/actions/unshare-resource.js.map +1 -1
  652. package/dist/styles/agent-native.css +0 -5
  653. package/dist/templates/default/.agents/skills/real-time-collab/SKILL.md +82 -19
  654. package/dist/templates/default/.agents/skills/real-time-sync/SKILL.md +15 -0
  655. package/dist/templates/default/.agents/skills/storing-data/SKILL.md +8 -0
  656. package/dist/templates/default/package.json +3 -3
  657. package/dist/templates/workspace-core/.agents/skills/client-methods/SKILL.md +8 -0
  658. package/dist/templates/workspace-core/.agents/skills/observability/SKILL.md +22 -0
  659. package/dist/templates/workspace-core/.agents/skills/real-time-collab/SKILL.md +82 -19
  660. package/dist/templates/workspace-core/.agents/skills/real-time-sync/SKILL.md +15 -0
  661. package/dist/templates/workspace-core/.agents/skills/storing-data/SKILL.md +8 -0
  662. package/dist/templates/workspace-core/.agents/skills/tracking/SKILL.md +1 -0
  663. package/dist/tracking/providers.d.ts.map +1 -1
  664. package/dist/tracking/providers.js +17 -1
  665. package/dist/tracking/providers.js.map +1 -1
  666. package/docs/content/cloneable-saas.mdx +0 -1
  667. package/docs/content/locales/ar-SA/cloneable-saas.mdx +0 -1
  668. package/docs/content/locales/ar-SA/plan-plugin.mdx +10 -9
  669. package/docs/content/locales/ar-SA/sharing.mdx +1 -2
  670. package/docs/content/locales/ar-SA/skills-guide.mdx +2 -3
  671. package/docs/content/locales/ar-SA/template-plan.mdx +23 -7
  672. package/docs/content/locales/ar-SA/tracking.mdx +1 -1
  673. package/docs/content/locales/ar-SA/workspace-connections.mdx +11 -11
  674. package/docs/content/locales/de-DE/cloneable-saas.mdx +0 -1
  675. package/docs/content/locales/de-DE/plan-plugin.mdx +10 -9
  676. package/docs/content/locales/de-DE/sharing.mdx +1 -2
  677. package/docs/content/locales/de-DE/skills-guide.mdx +2 -3
  678. package/docs/content/locales/de-DE/template-plan.mdx +23 -7
  679. package/docs/content/locales/de-DE/tracking.mdx +1 -1
  680. package/docs/content/locales/de-DE/workspace-connections.mdx +1 -1
  681. package/docs/content/locales/es-ES/cloneable-saas.mdx +0 -1
  682. package/docs/content/locales/es-ES/plan-plugin.mdx +10 -9
  683. package/docs/content/locales/es-ES/sharing.mdx +1 -2
  684. package/docs/content/locales/es-ES/skills-guide.mdx +2 -3
  685. package/docs/content/locales/es-ES/template-plan.mdx +23 -7
  686. package/docs/content/locales/es-ES/tracking.mdx +1 -1
  687. package/docs/content/locales/es-ES/workspace-connections.mdx +1 -1
  688. package/docs/content/locales/fr-FR/cloneable-saas.mdx +0 -1
  689. package/docs/content/locales/fr-FR/plan-plugin.mdx +10 -9
  690. package/docs/content/locales/fr-FR/sharing.mdx +1 -2
  691. package/docs/content/locales/fr-FR/skills-guide.mdx +2 -3
  692. package/docs/content/locales/fr-FR/template-plan.mdx +23 -7
  693. package/docs/content/locales/fr-FR/tracking.mdx +1 -1
  694. package/docs/content/locales/fr-FR/workspace-connections.mdx +1 -1
  695. package/docs/content/locales/hi-IN/cloneable-saas.mdx +0 -1
  696. package/docs/content/locales/hi-IN/plan-plugin.mdx +10 -9
  697. package/docs/content/locales/hi-IN/sharing.mdx +1 -2
  698. package/docs/content/locales/hi-IN/skills-guide.mdx +2 -3
  699. package/docs/content/locales/hi-IN/template-plan.mdx +23 -7
  700. package/docs/content/locales/hi-IN/tracking.mdx +1 -1
  701. package/docs/content/locales/hi-IN/workspace-connections.mdx +1 -1
  702. package/docs/content/locales/ja-JP/cloneable-saas.mdx +0 -1
  703. package/docs/content/locales/ja-JP/plan-plugin.mdx +10 -9
  704. package/docs/content/locales/ja-JP/sharing.mdx +1 -2
  705. package/docs/content/locales/ja-JP/skills-guide.mdx +2 -3
  706. package/docs/content/locales/ja-JP/template-plan.mdx +23 -7
  707. package/docs/content/locales/ja-JP/tracking.mdx +1 -1
  708. package/docs/content/locales/ja-JP/workspace-connections.mdx +1 -1
  709. package/docs/content/locales/ko-KR/cloneable-saas.mdx +0 -1
  710. package/docs/content/locales/ko-KR/plan-plugin.mdx +10 -9
  711. package/docs/content/locales/ko-KR/sharing.mdx +1 -2
  712. package/docs/content/locales/ko-KR/skills-guide.mdx +2 -3
  713. package/docs/content/locales/ko-KR/template-plan.mdx +23 -7
  714. package/docs/content/locales/ko-KR/tracking.mdx +1 -1
  715. package/docs/content/locales/ko-KR/workspace-connections.mdx +1 -1
  716. package/docs/content/locales/pt-BR/cloneable-saas.mdx +0 -1
  717. package/docs/content/locales/pt-BR/plan-plugin.mdx +10 -9
  718. package/docs/content/locales/pt-BR/sharing.mdx +1 -2
  719. package/docs/content/locales/pt-BR/skills-guide.mdx +2 -3
  720. package/docs/content/locales/pt-BR/template-plan.mdx +23 -7
  721. package/docs/content/locales/pt-BR/tracking.mdx +1 -1
  722. package/docs/content/locales/pt-BR/workspace-connections.mdx +1 -1
  723. package/docs/content/locales/zh-CN/cloneable-saas.mdx +0 -1
  724. package/docs/content/locales/zh-CN/plan-plugin.mdx +10 -9
  725. package/docs/content/locales/zh-CN/sharing.mdx +1 -2
  726. package/docs/content/locales/zh-CN/skills-guide.mdx +2 -3
  727. package/docs/content/locales/zh-CN/template-plan.mdx +23 -7
  728. package/docs/content/locales/zh-CN/tracking.mdx +1 -1
  729. package/docs/content/locales/zh-CN/workspace-connections.mdx +1 -1
  730. package/docs/content/locales/zh-TW/cloneable-saas.mdx +0 -1
  731. package/docs/content/locales/zh-TW/plan-plugin.mdx +10 -9
  732. package/docs/content/locales/zh-TW/sharing.mdx +1 -2
  733. package/docs/content/locales/zh-TW/skills-guide.mdx +2 -3
  734. package/docs/content/locales/zh-TW/template-plan.mdx +23 -7
  735. package/docs/content/locales/zh-TW/tracking.mdx +1 -1
  736. package/docs/content/locales/zh-TW/workspace-connections.mdx +1 -1
  737. package/docs/content/plan-plugin.mdx +12 -11
  738. package/docs/content/sharing.mdx +1 -2
  739. package/docs/content/skills-guide.mdx +4 -3
  740. package/docs/content/template-plan.mdx +37 -6
  741. package/docs/content/tracking.mdx +1 -1
  742. package/docs/content/workspace-connections.mdx +1 -1
  743. package/package.json +6 -6
  744. package/src/templates/default/.agents/skills/real-time-collab/SKILL.md +82 -19
  745. package/src/templates/default/.agents/skills/real-time-sync/SKILL.md +15 -0
  746. package/src/templates/default/.agents/skills/storing-data/SKILL.md +8 -0
  747. package/src/templates/default/package.json +3 -3
  748. package/src/templates/workspace-core/.agents/skills/client-methods/SKILL.md +8 -0
  749. package/src/templates/workspace-core/.agents/skills/observability/SKILL.md +22 -0
  750. package/src/templates/workspace-core/.agents/skills/real-time-collab/SKILL.md +82 -19
  751. package/src/templates/workspace-core/.agents/skills/real-time-sync/SKILL.md +15 -0
  752. package/src/templates/workspace-core/.agents/skills/storing-data/SKILL.md +8 -0
  753. package/src/templates/workspace-core/.agents/skills/tracking/SKILL.md +1 -0
  754. package/corpus/core/docs/content/locales/ar-SA/template-videos.mdx +0 -336
  755. package/corpus/core/docs/content/locales/de-DE/template-videos.mdx +0 -336
  756. package/corpus/core/docs/content/locales/es-ES/template-videos.mdx +0 -336
  757. package/corpus/core/docs/content/locales/fr-FR/template-videos.mdx +0 -336
  758. package/corpus/core/docs/content/locales/hi-IN/template-videos.mdx +0 -336
  759. package/corpus/core/docs/content/locales/ja-JP/template-videos.mdx +0 -336
  760. package/corpus/core/docs/content/locales/ko-KR/template-videos.mdx +0 -336
  761. package/corpus/core/docs/content/locales/pt-BR/template-videos.mdx +0 -336
  762. package/corpus/core/docs/content/locales/zh-CN/template-videos.mdx +0 -334
  763. package/corpus/core/docs/content/locales/zh-TW/template-videos.mdx +0 -334
  764. package/corpus/core/docs/content/template-videos.mdx +0 -332
  765. package/corpus/templates/design/app/components/design/CodeWorkbenchHost.tsx +0 -697
  766. package/corpus/templates/slides/app/components/editor/CodeEditor.tsx +0 -49
  767. package/corpus/templates/videos/.agents/skills/actions/SKILL.md +0 -432
  768. package/corpus/templates/videos/.agents/skills/animation-tracks/SKILL.md +0 -99
  769. package/corpus/templates/videos/.agents/skills/capture-learnings/SKILL.md +0 -76
  770. package/corpus/templates/videos/.agents/skills/composition-management/SKILL.md +0 -106
  771. package/corpus/templates/videos/.agents/skills/create-skill/SKILL.md +0 -221
  772. package/corpus/templates/videos/.agents/skills/delegate-to-agent/SKILL.md +0 -263
  773. package/corpus/templates/videos/.agents/skills/frontend-design/SKILL.md +0 -112
  774. package/corpus/templates/videos/.agents/skills/security/SKILL.md +0 -263
  775. package/corpus/templates/videos/.agents/skills/self-modifying-code/SKILL.md +0 -88
  776. package/corpus/templates/videos/.agents/skills/shadcn-ui/SKILL.md +0 -95
  777. package/corpus/templates/videos/.builder/ANIMATED_PROPERTIES.md +0 -335
  778. package/corpus/templates/videos/.builder/KEYFRAME_SYNC.md +0 -166
  779. package/corpus/templates/videos/.builder/SEAMLESS_SYNC.md +0 -211
  780. package/corpus/templates/videos/.builder/rules/deploy-app.mdc +0 -22
  781. package/corpus/templates/videos/.builder/rules/organize-ui.mdc +0 -9
  782. package/corpus/templates/videos/.builder/skills/remotion/SKILL.md +0 -29
  783. package/corpus/templates/videos/.builder/skills/remotion/rules/animations.md +0 -27
  784. package/corpus/templates/videos/.builder/skills/remotion/rules/assets.md +0 -43
  785. package/corpus/templates/videos/.builder/skills/remotion/rules/audio.md +0 -58
  786. package/corpus/templates/videos/.builder/skills/remotion/rules/compositions.md +0 -129
  787. package/corpus/templates/videos/.builder/skills/remotion/rules/fonts.md +0 -47
  788. package/corpus/templates/videos/.builder/skills/remotion/rules/images.md +0 -41
  789. package/corpus/templates/videos/.builder/skills/remotion/rules/parameters.md +0 -59
  790. package/corpus/templates/videos/.builder/skills/remotion/rules/sequencing.md +0 -54
  791. package/corpus/templates/videos/.builder/skills/remotion/rules/tailwind.md +0 -11
  792. package/corpus/templates/videos/.builder/skills/remotion/rules/text-animations.md +0 -18
  793. package/corpus/templates/videos/.builder/skills/remotion/rules/timing.md +0 -103
  794. package/corpus/templates/videos/.builder/skills/remotion/rules/transparent-videos.md +0 -35
  795. package/corpus/templates/videos/.builder/skills/remotion/rules/trimming.md +0 -38
  796. package/corpus/templates/videos/.builder/skills/remotion/rules/videos.md +0 -54
  797. package/corpus/templates/videos/.dockerignore +0 -62
  798. package/corpus/templates/videos/.env.example +0 -4
  799. package/corpus/templates/videos/.oxfmtrc.json +0 -8
  800. package/corpus/templates/videos/AGENTS.md +0 -46
  801. package/corpus/templates/videos/CHANGELOG.md +0 -10
  802. package/corpus/templates/videos/DEVELOPING.md +0 -143
  803. package/corpus/templates/videos/README.md +0 -33
  804. package/corpus/templates/videos/actions/analyze-brand-assets.ts +0 -151
  805. package/corpus/templates/videos/actions/apply-design-system.ts +0 -35
  806. package/corpus/templates/videos/actions/create-design-system.ts +0 -84
  807. package/corpus/templates/videos/actions/create-folder.ts +0 -48
  808. package/corpus/templates/videos/actions/db-connect.ts +0 -45
  809. package/corpus/templates/videos/actions/db-health.ts +0 -24
  810. package/corpus/templates/videos/actions/db-status.ts +0 -28
  811. package/corpus/templates/videos/actions/delete-composition.ts +0 -272
  812. package/corpus/templates/videos/actions/delete-folder.ts +0 -27
  813. package/corpus/templates/videos/actions/generate-animated-component.ts +0 -470
  814. package/corpus/templates/videos/actions/get-composition.ts +0 -36
  815. package/corpus/templates/videos/actions/get-design-system.ts +0 -35
  816. package/corpus/templates/videos/actions/import-code.ts +0 -67
  817. package/corpus/templates/videos/actions/import-design-project.ts +0 -42
  818. package/corpus/templates/videos/actions/import-document.ts +0 -125
  819. package/corpus/templates/videos/actions/import-from-url.ts +0 -18
  820. package/corpus/templates/videos/actions/import-github.ts +0 -182
  821. package/corpus/templates/videos/actions/list-compositions.ts +0 -32
  822. package/corpus/templates/videos/actions/list-design-systems.ts +0 -66
  823. package/corpus/templates/videos/actions/list-folders.ts +0 -61
  824. package/corpus/templates/videos/actions/move-composition-to-folder.ts +0 -59
  825. package/corpus/templates/videos/actions/navigate.ts +0 -40
  826. package/corpus/templates/videos/actions/rename-folder.ts +0 -41
  827. package/corpus/templates/videos/actions/run.ts +0 -2
  828. package/corpus/templates/videos/actions/save-composition.ts +0 -114
  829. package/corpus/templates/videos/actions/set-default-design-system.ts +0 -40
  830. package/corpus/templates/videos/actions/update-composition.ts +0 -81
  831. package/corpus/templates/videos/actions/update-design-system.ts +0 -68
  832. package/corpus/templates/videos/actions/validate-compositions.ts +0 -502
  833. package/corpus/templates/videos/actions/view-screen.ts +0 -48
  834. package/corpus/templates/videos/app/components/CameraControls.tsx +0 -442
  835. package/corpus/templates/videos/app/components/CameraToolbar.tsx +0 -437
  836. package/corpus/templates/videos/app/components/CloudUpgrade.tsx +0 -287
  837. package/corpus/templates/videos/app/components/CollabPresenceBar.tsx +0 -81
  838. package/corpus/templates/videos/app/components/CompSettingsEditor.tsx +0 -107
  839. package/corpus/templates/videos/app/components/ComponentLibrarySidebar.tsx +0 -457
  840. package/corpus/templates/videos/app/components/ComponentPropsPanel.tsx +0 -227
  841. package/corpus/templates/videos/app/components/ComponentsSidebar.tsx +0 -70
  842. package/corpus/templates/videos/app/components/CompositionCard.tsx +0 -147
  843. package/corpus/templates/videos/app/components/CurrentElementPanel.tsx +0 -835
  844. package/corpus/templates/videos/app/components/CursorControls.tsx +0 -664
  845. package/corpus/templates/videos/app/components/CursorPositioningOverlay.tsx +0 -238
  846. package/corpus/templates/videos/app/components/LibraryFolderRow.tsx +0 -235
  847. package/corpus/templates/videos/app/components/MotionCurveSelect.tsx +0 -61
  848. package/corpus/templates/videos/app/components/NewCompositionPopover.tsx +0 -192
  849. package/corpus/templates/videos/app/components/PropsEditor.tsx +0 -210
  850. package/corpus/templates/videos/app/components/QuestionFlow.tsx +0 -40
  851. package/corpus/templates/videos/app/components/Sidebar.tsx +0 -609
  852. package/corpus/templates/videos/app/components/StudioHeader.tsx +0 -109
  853. package/corpus/templates/videos/app/components/Timeline.tsx +0 -2067
  854. package/corpus/templates/videos/app/components/TrackPropertiesPanel.tsx +0 -922
  855. package/corpus/templates/videos/app/components/TweaksPanel.tsx +0 -277
  856. package/corpus/templates/videos/app/components/VideoPlayer.tsx +0 -487
  857. package/corpus/templates/videos/app/components/design-system/DesignSystemCard.tsx +0 -134
  858. package/corpus/templates/videos/app/components/design-system/DesignSystemPreview.tsx +0 -176
  859. package/corpus/templates/videos/app/components/design-system/DesignSystemSetup.tsx +0 -707
  860. package/corpus/templates/videos/app/components/keyframes/KeyframeActionButtons.tsx +0 -78
  861. package/corpus/templates/videos/app/components/keyframes/KeyframeNavigation.tsx +0 -59
  862. package/corpus/templates/videos/app/components/keyframes/PropertyNumberInput.tsx +0 -56
  863. package/corpus/templates/videos/app/components/layout/Header.tsx +0 -64
  864. package/corpus/templates/videos/app/components/layout/HeaderActions.tsx +0 -84
  865. package/corpus/templates/videos/app/components/layout/Layout.tsx +0 -132
  866. package/corpus/templates/videos/app/components/layout/NavSidebar.tsx +0 -180
  867. package/corpus/templates/videos/app/components/ui/accordion.tsx +0 -56
  868. package/corpus/templates/videos/app/components/ui/alert-dialog.tsx +0 -139
  869. package/corpus/templates/videos/app/components/ui/alert.tsx +0 -59
  870. package/corpus/templates/videos/app/components/ui/aspect-ratio.tsx +0 -5
  871. package/corpus/templates/videos/app/components/ui/avatar.tsx +0 -48
  872. package/corpus/templates/videos/app/components/ui/badge.tsx +0 -37
  873. package/corpus/templates/videos/app/components/ui/breadcrumb.tsx +0 -115
  874. package/corpus/templates/videos/app/components/ui/button.tsx +0 -57
  875. package/corpus/templates/videos/app/components/ui/calendar.tsx +0 -68
  876. package/corpus/templates/videos/app/components/ui/card.tsx +0 -86
  877. package/corpus/templates/videos/app/components/ui/carousel.tsx +0 -260
  878. package/corpus/templates/videos/app/components/ui/chart.tsx +0 -375
  879. package/corpus/templates/videos/app/components/ui/checkbox.tsx +0 -28
  880. package/corpus/templates/videos/app/components/ui/collapsible.tsx +0 -9
  881. package/corpus/templates/videos/app/components/ui/command.tsx +0 -154
  882. package/corpus/templates/videos/app/components/ui/context-menu.tsx +0 -202
  883. package/corpus/templates/videos/app/components/ui/dialog.tsx +0 -130
  884. package/corpus/templates/videos/app/components/ui/drawer.tsx +0 -116
  885. package/corpus/templates/videos/app/components/ui/dropdown-menu.tsx +0 -212
  886. package/corpus/templates/videos/app/components/ui/form.tsx +0 -177
  887. package/corpus/templates/videos/app/components/ui/hover-card.tsx +0 -27
  888. package/corpus/templates/videos/app/components/ui/input-otp.tsx +0 -69
  889. package/corpus/templates/videos/app/components/ui/input.tsx +0 -22
  890. package/corpus/templates/videos/app/components/ui/label.tsx +0 -24
  891. package/corpus/templates/videos/app/components/ui/menubar.tsx +0 -234
  892. package/corpus/templates/videos/app/components/ui/navigation-menu.tsx +0 -128
  893. package/corpus/templates/videos/app/components/ui/pagination.tsx +0 -121
  894. package/corpus/templates/videos/app/components/ui/popover.tsx +0 -44
  895. package/corpus/templates/videos/app/components/ui/progress.tsx +0 -26
  896. package/corpus/templates/videos/app/components/ui/radio-group.tsx +0 -42
  897. package/corpus/templates/videos/app/components/ui/resizable.tsx +0 -43
  898. package/corpus/templates/videos/app/components/ui/scroll-area.tsx +0 -46
  899. package/corpus/templates/videos/app/components/ui/select.tsx +0 -158
  900. package/corpus/templates/videos/app/components/ui/separator.tsx +0 -29
  901. package/corpus/templates/videos/app/components/ui/sheet.tsx +0 -160
  902. package/corpus/templates/videos/app/components/ui/sidebar.tsx +0 -782
  903. package/corpus/templates/videos/app/components/ui/skeleton.tsx +0 -15
  904. package/corpus/templates/videos/app/components/ui/slider.tsx +0 -26
  905. package/corpus/templates/videos/app/components/ui/sonner.tsx +0 -58
  906. package/corpus/templates/videos/app/components/ui/spinner.tsx +0 -17
  907. package/corpus/templates/videos/app/components/ui/switch.tsx +0 -27
  908. package/corpus/templates/videos/app/components/ui/table.tsx +0 -117
  909. package/corpus/templates/videos/app/components/ui/tabs.tsx +0 -53
  910. package/corpus/templates/videos/app/components/ui/textarea.tsx +0 -23
  911. package/corpus/templates/videos/app/components/ui/toast.tsx +0 -127
  912. package/corpus/templates/videos/app/components/ui/toaster.tsx +0 -33
  913. package/corpus/templates/videos/app/components/ui/toggle-group.tsx +0 -59
  914. package/corpus/templates/videos/app/components/ui/toggle.tsx +0 -43
  915. package/corpus/templates/videos/app/components/ui/tooltip.tsx +0 -30
  916. package/corpus/templates/videos/app/components/ui/use-toast.ts +0 -3
  917. package/corpus/templates/videos/app/config/constants.ts +0 -204
  918. package/corpus/templates/videos/app/contexts/CompositionContext.tsx +0 -437
  919. package/corpus/templates/videos/app/contexts/CurrentElementContext.tsx +0 -247
  920. package/corpus/templates/videos/app/contexts/PlaybackContext.tsx +0 -65
  921. package/corpus/templates/videos/app/contexts/TimelineContext.tsx +0 -433
  922. package/corpus/templates/videos/app/entry.client.tsx +0 -19
  923. package/corpus/templates/videos/app/entry.server.tsx +0 -10
  924. package/corpus/templates/videos/app/global.css +0 -171
  925. package/corpus/templates/videos/app/hooks/use-composition-collab.ts +0 -269
  926. package/corpus/templates/videos/app/hooks/use-composition-design-system.ts +0 -47
  927. package/corpus/templates/videos/app/hooks/use-database-compositions.ts +0 -144
  928. package/corpus/templates/videos/app/hooks/use-db-status.ts +0 -30
  929. package/corpus/templates/videos/app/hooks/use-design-systems.ts +0 -21
  930. package/corpus/templates/videos/app/hooks/use-folders.ts +0 -199
  931. package/corpus/templates/videos/app/hooks/use-mobile.tsx +0 -21
  932. package/corpus/templates/videos/app/hooks/use-navigation-state.ts +0 -52
  933. package/corpus/templates/videos/app/hooks/use-question-flow.ts +0 -14
  934. package/corpus/templates/videos/app/hooks/use-toast.ts +0 -188
  935. package/corpus/templates/videos/app/hooks/useUnsavedChanges.ts +0 -48
  936. package/corpus/templates/videos/app/i18n/ar-SA.ts +0 -446
  937. package/corpus/templates/videos/app/i18n/de-DE.ts +0 -470
  938. package/corpus/templates/videos/app/i18n/en-US.ts +0 -452
  939. package/corpus/templates/videos/app/i18n/es-ES.ts +0 -468
  940. package/corpus/templates/videos/app/i18n/fr-FR.ts +0 -469
  941. package/corpus/templates/videos/app/i18n/hi-IN.ts +0 -446
  942. package/corpus/templates/videos/app/i18n/index.ts +0 -34
  943. package/corpus/templates/videos/app/i18n/ja-JP.ts +0 -460
  944. package/corpus/templates/videos/app/i18n/ko-KR.ts +0 -453
  945. package/corpus/templates/videos/app/i18n/pt-BR.ts +0 -461
  946. package/corpus/templates/videos/app/i18n/zh-CN.ts +0 -437
  947. package/corpus/templates/videos/app/i18n/zh-TW.ts +0 -437
  948. package/corpus/templates/videos/app/lib/database-compositions.ts +0 -67
  949. package/corpus/templates/videos/app/lib/design-systems.ts +0 -234
  950. package/corpus/templates/videos/app/lib/tab-id.ts +0 -1
  951. package/corpus/templates/videos/app/lib/utils.ts +0 -1
  952. package/corpus/templates/videos/app/pages/ComponentLibrary.tsx +0 -134
  953. package/corpus/templates/videos/app/pages/ComponentLibraryView.tsx +0 -362
  954. package/corpus/templates/videos/app/pages/CompositionView.tsx +0 -715
  955. package/corpus/templates/videos/app/pages/DesignSystems.tsx +0 -180
  956. package/corpus/templates/videos/app/pages/Index.tsx +0 -258
  957. package/corpus/templates/videos/app/pages/NewComposition.tsx +0 -95
  958. package/corpus/templates/videos/app/pages/NotFound.tsx +0 -36
  959. package/corpus/templates/videos/app/remotion/CameraHost.tsx +0 -223
  960. package/corpus/templates/videos/app/remotion/animations/useElementAnimations.ts +0 -231
  961. package/corpus/templates/videos/app/remotion/componentRegistry.ts +0 -473
  962. package/corpus/templates/videos/app/remotion/components/AnimatedElement.tsx +0 -436
  963. package/corpus/templates/videos/app/remotion/components/InteractiveElement.tsx +0 -159
  964. package/corpus/templates/videos/app/remotion/components/InteractiveZoneEditor.tsx +0 -273
  965. package/corpus/templates/videos/app/remotion/compositions/BlankComposition.tsx +0 -204
  966. package/corpus/templates/videos/app/remotion/compositions/index.ts +0 -2
  967. package/corpus/templates/videos/app/remotion/createComponentCursorTrack.ts +0 -132
  968. package/corpus/templates/videos/app/remotion/docs/CURSOR_TRACKS.md +0 -285
  969. package/corpus/templates/videos/app/remotion/easingFunctions.ts +0 -255
  970. package/corpus/templates/videos/app/remotion/hooks/createInteractiveComposition.tsx +0 -283
  971. package/corpus/templates/videos/app/remotion/hooks/useCursorHistory.ts +0 -72
  972. package/corpus/templates/videos/app/remotion/hooks/useCursorTypeFromHover.ts +0 -35
  973. package/corpus/templates/videos/app/remotion/hooks/useEditableZones.tsx +0 -267
  974. package/corpus/templates/videos/app/remotion/hooks/useHoverAnimation.ts +0 -90
  975. package/corpus/templates/videos/app/remotion/hooks/useHoverAnimationSmooth.ts +0 -146
  976. package/corpus/templates/videos/app/remotion/hooks/useInteractiveComponent.ts +0 -711
  977. package/corpus/templates/videos/app/remotion/hooks/useRegisterInteractiveElement.ts +0 -56
  978. package/corpus/templates/videos/app/remotion/library-components/Button.tsx +0 -252
  979. package/corpus/templates/videos/app/remotion/library-components/Card.tsx +0 -241
  980. package/corpus/templates/videos/app/remotion/library-components/CodePanel.tsx +0 -1005
  981. package/corpus/templates/videos/app/remotion/library-components/FileItem.tsx +0 -196
  982. package/corpus/templates/videos/app/remotion/library-components/FolderItem.tsx +0 -199
  983. package/corpus/templates/videos/app/remotion/library-components/PrimaryButton.tsx +0 -177
  984. package/corpus/templates/videos/app/remotion/library-components/SecondaryButton.tsx +0 -167
  985. package/corpus/templates/videos/app/remotion/library-components/SectionHeader.tsx +0 -108
  986. package/corpus/templates/videos/app/remotion/library-components/TEMPLATE.tsx +0 -211
  987. package/corpus/templates/videos/app/remotion/library-components/index.ts +0 -10
  988. package/corpus/templates/videos/app/remotion/registry.ts +0 -91
  989. package/corpus/templates/videos/app/remotion/testing/animationTestUtils.ts +0 -366
  990. package/corpus/templates/videos/app/remotion/trackAnimation.ts +0 -179
  991. package/corpus/templates/videos/app/remotion/trackHelpers.ts +0 -110
  992. package/corpus/templates/videos/app/remotion/ui-components/Cursor.tsx +0 -182
  993. package/corpus/templates/videos/app/remotion/ui-components/InteractiveButton.tsx +0 -116
  994. package/corpus/templates/videos/app/remotion/ui-components/InteractiveCard.tsx +0 -126
  995. package/corpus/templates/videos/app/remotion/ui-components/index.ts +0 -16
  996. package/corpus/templates/videos/app/remotion/utils/animationHelpers.ts +0 -444
  997. package/corpus/templates/videos/app/remotion/utils/interactiveElements.ts +0 -235
  998. package/corpus/templates/videos/app/remotion/utils/springAnimation.ts +0 -76
  999. package/corpus/templates/videos/app/root.tsx +0 -165
  1000. package/corpus/templates/videos/app/routes/$.tsx +0 -10
  1001. package/corpus/templates/videos/app/routes/_index.tsx +0 -25
  1002. package/corpus/templates/videos/app/routes/c.$compositionId.tsx +0 -10
  1003. package/corpus/templates/videos/app/routes/components.tsx +0 -10
  1004. package/corpus/templates/videos/app/routes/design-systems.tsx +0 -10
  1005. package/corpus/templates/videos/app/routes/extensions.$id.$slug.tsx +0 -2
  1006. package/corpus/templates/videos/app/routes/extensions.$id.tsx +0 -5
  1007. package/corpus/templates/videos/app/routes/extensions._index.tsx +0 -5
  1008. package/corpus/templates/videos/app/routes/extensions.tsx +0 -5
  1009. package/corpus/templates/videos/app/routes/settings.tsx +0 -88
  1010. package/corpus/templates/videos/app/routes/team.tsx +0 -11
  1011. package/corpus/templates/videos/app/routes.ts +0 -4
  1012. package/corpus/templates/videos/app/state.ts +0 -77
  1013. package/corpus/templates/videos/app/types/elementAnimations.ts +0 -121
  1014. package/corpus/templates/videos/app/types.ts +0 -200
  1015. package/corpus/templates/videos/app/utils/compositionHelpers.ts +0 -445
  1016. package/corpus/templates/videos/app/utils/debug.ts +0 -63
  1017. package/corpus/templates/videos/app/utils/keyframeUtils.ts +0 -331
  1018. package/corpus/templates/videos/app/utils/timelineCoordinates.ts +0 -79
  1019. package/corpus/templates/videos/app/vite-env.d.ts +0 -6
  1020. package/corpus/templates/videos/changelog/2026-06-24-a-new-settings-page-gives-quick-access-to-language-workspace.md +0 -6
  1021. package/corpus/templates/videos/changelog/2026-06-24-added-a-language-picker-and-localized-app-chrome-for-support.md +0 -6
  1022. package/corpus/templates/videos/changelog/2026-06-27-traditional-chinese-copy-uses-taiwan-terminology.md +0 -6
  1023. package/corpus/templates/videos/changelog/2026-06-28-left-sidebar-collapses-into-an-animated-icon-rail.md +0 -6
  1024. package/corpus/templates/videos/changelog/2026-06-29-video-layouts-adapt-when-the-agent-sidebar-is-open.md +0 -6
  1025. package/corpus/templates/videos/components.json +0 -20
  1026. package/corpus/templates/videos/data/sync-config.json +0 -3
  1027. package/corpus/templates/videos/docs/examples/create-composition.example.ts +0 -128
  1028. package/corpus/templates/videos/drizzle.config.ts +0 -3
  1029. package/corpus/templates/videos/learnings.defaults.md +0 -5
  1030. package/corpus/templates/videos/package.json +0 -114
  1031. package/corpus/templates/videos/public/agent-native-icon-dark.svg +0 -10
  1032. package/corpus/templates/videos/public/agent-native-icon-light.svg +0 -10
  1033. package/corpus/templates/videos/public/agent-native-logo-dark.svg +0 -21
  1034. package/corpus/templates/videos/public/agent-native-logo-light.svg +0 -21
  1035. package/corpus/templates/videos/public/favicon.svg +0 -1
  1036. package/corpus/templates/videos/public/icon-180.svg +0 -1
  1037. package/corpus/templates/videos/public/icon-192.svg +0 -1
  1038. package/corpus/templates/videos/public/icon-512.svg +0 -1
  1039. package/corpus/templates/videos/public/manifest.json +0 -21
  1040. package/corpus/templates/videos/public/placeholder.svg +0 -1
  1041. package/corpus/templates/videos/public/robots.txt +0 -14
  1042. package/corpus/templates/videos/react-router.config.ts +0 -7
  1043. package/corpus/templates/videos/server/db/index.ts +0 -37
  1044. package/corpus/templates/videos/server/db/schema.ts +0 -55
  1045. package/corpus/templates/videos/server/middleware/auth.ts +0 -15
  1046. package/corpus/templates/videos/server/plugins/agent-chat.ts +0 -29
  1047. package/corpus/templates/videos/server/plugins/auth.ts +0 -14
  1048. package/corpus/templates/videos/server/plugins/collab.ts +0 -11
  1049. package/corpus/templates/videos/server/plugins/core-routes.ts +0 -22
  1050. package/corpus/templates/videos/server/plugins/db.ts +0 -160
  1051. package/corpus/templates/videos/server/routes/[...page].get.ts +0 -5
  1052. package/corpus/templates/videos/server/routes/[...page].head.ts +0 -1
  1053. package/corpus/templates/videos/server/routes/api/save-composition-defaults.post.ts +0 -274
  1054. package/corpus/templates/videos/shared/api.ts +0 -75
  1055. package/corpus/templates/videos/ssr-entry.ts +0 -15
  1056. package/corpus/templates/videos/tsconfig.json +0 -21
  1057. package/corpus/templates/videos/vite.config.ts +0 -19
  1058. package/corpus/templates/videos/vitest.config.ts +0 -16
  1059. package/docs/content/locales/ar-SA/template-videos.mdx +0 -336
  1060. package/docs/content/locales/de-DE/template-videos.mdx +0 -336
  1061. package/docs/content/locales/es-ES/template-videos.mdx +0 -336
  1062. package/docs/content/locales/fr-FR/template-videos.mdx +0 -336
  1063. package/docs/content/locales/hi-IN/template-videos.mdx +0 -336
  1064. package/docs/content/locales/ja-JP/template-videos.mdx +0 -336
  1065. package/docs/content/locales/ko-KR/template-videos.mdx +0 -336
  1066. package/docs/content/locales/pt-BR/template-videos.mdx +0 -336
  1067. package/docs/content/locales/zh-CN/template-videos.mdx +0 -334
  1068. package/docs/content/locales/zh-TW/template-videos.mdx +0 -334
  1069. package/docs/content/template-videos.mdx +0 -332
@@ -54,8 +54,8 @@ export interface AppProvidersProps {
54
54
  queryClient: QueryClient;
55
55
  /**
56
56
  * Default theme passed to next-themes `ThemeProvider`.
57
- * Defaults to `"system"`. Dark-first templates (videos, slides, macros,
58
- * analytics) pass `"dark"`.
57
+ * Defaults to `"system"`. Dark-first templates (slides, macros, analytics)
58
+ * pass `"dark"`.
59
59
  */
60
60
  defaultTheme?: string;
61
61
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"app-providers.js","sourceRoot":"","sources":["../../src/client/app-providers.tsx"],"names":[],"mappings":";AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8CG;AAEH,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAC;AAC1D,OAAO,EAAE,mBAAmB,EAAoB,MAAM,uBAAuB,CAAC;AAC9E,OAAO,EAAE,aAAa,EAAkB,MAAM,aAAa,CAAC;AAE5D,OAAO,EAAE,OAAO,EAAE,MAAM,QAAQ,CAAC;AAEjC,OAAO,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAC7C,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AACrD,OAAO,EACL,uBAAuB,GAExB,MAAM,WAAW,CAAC;AAiEnB,MAAM,eAAe,GAAG,KAAC,OAAO,IAAC,UAAU,QAAC,QAAQ,EAAC,aAAa,GAAG,CAAC;AAEtE,SAAS,cAAc,CAAC,EACtB,WAAW,EACX,YAAY,GAAG,QAAQ,EACvB,cAAc,GAAG,OAAO,EACxB,oBAAoB,EACpB,OAAO,GAAG,eAAe,EACzB,uBAAuB,GAAG,IAAI,EAC9B,IAAI,EACJ,QAAQ,GAUT;IACC,MAAM,iBAAiB,GACrB,IAAI,KAAK,KAAK,CAAC,CAAC,CAAC,CACf,QAAQ,CACT,CAAC,CAAC,CAAC,CACF,KAAC,uBAAuB,OAAK,CAAC,IAAI,IAAI,EAAE,CAAC,YACtC,QAAQ,GACe,CAC3B,CAAC;IAEJ,OAAO,CACL,KAAC,mBAAmB,IAAC,MAAM,EAAE,WAAW,YACtC,KAAC,aAAa,IACZ,SAAS,EAAE,cAAc,EACzB,YAAY,EAAE,YAAY,EAC1B,YAAY,QACZ,yBAAyB,EAAE,uBAAuB,YAElD,MAAC,eAAe,IAAC,aAAa,EAAE,oBAAoB,aACjD,iBAAiB,EACjB,OAAO,IACQ,GACJ,GACI,CACvB,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,YAAY,CAAC,EAC3B,WAAW,EACX,YAAY,GAAG,KAAK,EACpB,kBAAkB,EAClB,YAAY,EACZ,cAAc,EACd,oBAAoB,EACpB,OAAO,EACP,uBAAuB,EACvB,IAAI,EACJ,QAAQ,GACU;IAClB,MAAM,QAAQ,GAAG,kBAAkB,IAAI,KAAC,cAAc,KAAG,CAAC;IAE1D,IAAI,YAAY,EAAE,CAAC;QACjB,OAAO,CACL,KAAC,cAAc,IACb,WAAW,EAAE,WAAW,EACxB,YAAY,EAAE,YAAY,EAC1B,cAAc,EAAE,cAAc,EAC9B,oBAAoB,EAAE,oBAAoB,EAC1C,OAAO,EAAE,OAAO,EAChB,uBAAuB,EAAE,uBAAuB,EAChD,IAAI,EAAE,IAAI,YAET,QAAQ,GACM,CAClB,CAAC;IACJ,CAAC;IAED,OAAO,CACL,KAAC,UAAU,IAAC,QAAQ,EAAE,QAAQ,YAC5B,KAAC,cAAc,IACb,WAAW,EAAE,WAAW,EACxB,YAAY,EAAE,YAAY,EAC1B,cAAc,EAAE,cAAc,EAC9B,oBAAoB,EAAE,oBAAoB,EAC1C,OAAO,EAAE,OAAO,EAChB,uBAAuB,EAAE,uBAAuB,EAChD,IAAI,EAAE,IAAI,YAET,QAAQ,GACM,GACN,CACd,CAAC;AACJ,CAAC","sourcesContent":["/**\n * Shared provider shell for agent-native template roots.\n *\n * Composes the providers every template needs:\n * QueryClientProvider → ThemeProvider → TooltipProvider → Toaster\n *\n * Templates keep their own `createAgentNativeQueryClient(overrides)` call and\n * pass the result in as `queryClient`. AppProviders never creates a client\n * internally so each template can apply its own query defaults (e.g. calendar's\n * `refetchOnWindowFocus: true`, mail's focus-refresh throttle).\n *\n * Public-path SSR pattern (calendar/clips/content):\n * Some templates have routes that must SSR real content for first-visit\n * signed-out users and crawlers, bypassing the `<ClientOnly>` gate.\n * Pass `isPublicPath` and `clientOnlyFallback` to activate this branch:\n *\n * <AppProviders\n * queryClient={queryClient}\n * isPublicPath={isPublicBookingPath(location.pathname)}\n * clientOnlyFallback={<DefaultSpinner />}\n * >\n * ...\n * </AppProviders>\n *\n * When `isPublicPath` is true the providers render without `<ClientOnly>`,\n * streaming real markup to the client. When false (the default) the standard\n * `<ClientOnly fallback={clientOnlyFallback}>` gate wraps everything.\n * When `clientOnlyFallback` is omitted, `<DefaultSpinner />` is used.\n *\n * Customisation props:\n * themeAttribute — passed to next-themes ThemeProvider `attribute`.\n * Defaults to \"class\". Use [\"class\", \"data-theme\"]\n * when CSS variables are also keyed off a data-theme\n * attribute (mail template).\n * tooltipDelayDuration — passed to Radix TooltipProvider `delayDuration`\n * (ms). Omit to use the Radix default (700 ms).\n * toaster — custom Toaster element rendered after children.\n * Pass `null` to suppress the built-in Toaster when\n * children already include a styled one.\n * Defaults to `<Toaster richColors position=\"bottom-left\" />`.\n * disableThemeTransitions — passed to next-themes ThemeProvider\n * `disableTransitionOnChange`. Defaults to `true`\n * (suppresses CSS transitions during theme switches,\n * which is the shadcn recommendation and avoids\n * flash artefacts). Set to `false` when the template\n * intentionally animates theme changes (e.g. content).\n */\n\nimport { TooltipProvider } from \"@radix-ui/react-tooltip\";\nimport { QueryClientProvider, type QueryClient } from \"@tanstack/react-query\";\nimport { ThemeProvider, type Attribute } from \"next-themes\";\nimport React from \"react\";\nimport { Toaster } from \"sonner\";\n\nimport { ClientOnly } from \"./ClientOnly.js\";\nimport { DefaultSpinner } from \"./DefaultSpinner.js\";\nimport {\n AgentNativeI18nProvider,\n type AgentNativeI18nProviderProps,\n} from \"./i18n.js\";\n\nexport interface AppProvidersProps {\n /** QueryClient instance — create with `createAgentNativeQueryClient()`. */\n queryClient: QueryClient;\n\n /**\n * Default theme passed to next-themes `ThemeProvider`.\n * Defaults to `\"system\"`. Dark-first templates (videos, slides, macros,\n * analytics) pass `\"dark\"`.\n */\n defaultTheme?: string;\n\n /**\n * Passed to next-themes ThemeProvider `attribute`.\n * Defaults to \"class\". Pass [\"class\", \"data-theme\"] when your CSS variables\n * are also keyed off a data-theme attribute (mail template).\n */\n themeAttribute?: Attribute | Attribute[];\n\n /**\n * Passed to Radix TooltipProvider `delayDuration` (ms).\n * Omit to use the Radix default (700 ms).\n */\n tooltipDelayDuration?: number;\n\n /**\n * Custom Toaster element rendered after children inside TooltipProvider.\n * Pass `null` to suppress the built-in Toaster when children already\n * include a styled one.\n * Defaults to `<Toaster richColors position=\"bottom-left\" />`.\n */\n toaster?: React.ReactNode | null;\n\n /**\n * Passed to next-themes ThemeProvider `disableTransitionOnChange`.\n * Defaults to `true` (suppresses CSS transitions on theme switch, per the\n * shadcn recommendation). Set to `false` when the template intentionally\n * animates theme changes (e.g. content's 3-way theme cycle).\n */\n disableThemeTransitions?: boolean;\n\n /**\n * Optional localization runtime configuration. When omitted, AppProviders\n * still mounts the i18n provider with an English fallback so templates can\n * call useT/useLocale before they add catalogs. Pass false to opt out.\n */\n i18n?: Omit<AgentNativeI18nProviderProps, \"children\"> | false;\n\n /**\n * When true the providers render without a `<ClientOnly>` gate so SSR\n * streams real markup for public/unauthenticated paths.\n * Defaults to false (authenticated app shell, ClientOnly-gated).\n */\n isPublicPath?: boolean;\n\n /**\n * Fallback rendered by `<ClientOnly>` while JS hydrates on private paths.\n * Defaults to `<DefaultSpinner />`.\n */\n clientOnlyFallback?: React.ReactNode;\n\n children: React.ReactNode;\n}\n\nconst DEFAULT_TOASTER = <Toaster richColors position=\"bottom-left\" />;\n\nfunction ProvidersInner({\n queryClient,\n defaultTheme = \"system\",\n themeAttribute = \"class\",\n tooltipDelayDuration,\n toaster = DEFAULT_TOASTER,\n disableThemeTransitions = true,\n i18n,\n children,\n}: {\n queryClient: QueryClient;\n defaultTheme?: string;\n themeAttribute?: Attribute | Attribute[];\n tooltipDelayDuration?: number;\n toaster?: React.ReactNode | null;\n disableThemeTransitions?: boolean;\n i18n?: Omit<AgentNativeI18nProviderProps, \"children\"> | false;\n children: React.ReactNode;\n}) {\n const localizedChildren =\n i18n === false ? (\n children\n ) : (\n <AgentNativeI18nProvider {...(i18n ?? {})}>\n {children}\n </AgentNativeI18nProvider>\n );\n\n return (\n <QueryClientProvider client={queryClient}>\n <ThemeProvider\n attribute={themeAttribute}\n defaultTheme={defaultTheme}\n enableSystem\n disableTransitionOnChange={disableThemeTransitions}\n >\n <TooltipProvider delayDuration={tooltipDelayDuration}>\n {localizedChildren}\n {toaster}\n </TooltipProvider>\n </ThemeProvider>\n </QueryClientProvider>\n );\n}\n\nexport function AppProviders({\n queryClient,\n isPublicPath = false,\n clientOnlyFallback,\n defaultTheme,\n themeAttribute,\n tooltipDelayDuration,\n toaster,\n disableThemeTransitions,\n i18n,\n children,\n}: AppProvidersProps) {\n const fallback = clientOnlyFallback ?? <DefaultSpinner />;\n\n if (isPublicPath) {\n return (\n <ProvidersInner\n queryClient={queryClient}\n defaultTheme={defaultTheme}\n themeAttribute={themeAttribute}\n tooltipDelayDuration={tooltipDelayDuration}\n toaster={toaster}\n disableThemeTransitions={disableThemeTransitions}\n i18n={i18n}\n >\n {children}\n </ProvidersInner>\n );\n }\n\n return (\n <ClientOnly fallback={fallback}>\n <ProvidersInner\n queryClient={queryClient}\n defaultTheme={defaultTheme}\n themeAttribute={themeAttribute}\n tooltipDelayDuration={tooltipDelayDuration}\n toaster={toaster}\n disableThemeTransitions={disableThemeTransitions}\n i18n={i18n}\n >\n {children}\n </ProvidersInner>\n </ClientOnly>\n );\n}\n"]}
1
+ {"version":3,"file":"app-providers.js","sourceRoot":"","sources":["../../src/client/app-providers.tsx"],"names":[],"mappings":";AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8CG;AAEH,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAC;AAC1D,OAAO,EAAE,mBAAmB,EAAoB,MAAM,uBAAuB,CAAC;AAC9E,OAAO,EAAE,aAAa,EAAkB,MAAM,aAAa,CAAC;AAE5D,OAAO,EAAE,OAAO,EAAE,MAAM,QAAQ,CAAC;AAEjC,OAAO,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAC7C,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AACrD,OAAO,EACL,uBAAuB,GAExB,MAAM,WAAW,CAAC;AAiEnB,MAAM,eAAe,GAAG,KAAC,OAAO,IAAC,UAAU,QAAC,QAAQ,EAAC,aAAa,GAAG,CAAC;AAEtE,SAAS,cAAc,CAAC,EACtB,WAAW,EACX,YAAY,GAAG,QAAQ,EACvB,cAAc,GAAG,OAAO,EACxB,oBAAoB,EACpB,OAAO,GAAG,eAAe,EACzB,uBAAuB,GAAG,IAAI,EAC9B,IAAI,EACJ,QAAQ,GAUT;IACC,MAAM,iBAAiB,GACrB,IAAI,KAAK,KAAK,CAAC,CAAC,CAAC,CACf,QAAQ,CACT,CAAC,CAAC,CAAC,CACF,KAAC,uBAAuB,OAAK,CAAC,IAAI,IAAI,EAAE,CAAC,YACtC,QAAQ,GACe,CAC3B,CAAC;IAEJ,OAAO,CACL,KAAC,mBAAmB,IAAC,MAAM,EAAE,WAAW,YACtC,KAAC,aAAa,IACZ,SAAS,EAAE,cAAc,EACzB,YAAY,EAAE,YAAY,EAC1B,YAAY,QACZ,yBAAyB,EAAE,uBAAuB,YAElD,MAAC,eAAe,IAAC,aAAa,EAAE,oBAAoB,aACjD,iBAAiB,EACjB,OAAO,IACQ,GACJ,GACI,CACvB,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,YAAY,CAAC,EAC3B,WAAW,EACX,YAAY,GAAG,KAAK,EACpB,kBAAkB,EAClB,YAAY,EACZ,cAAc,EACd,oBAAoB,EACpB,OAAO,EACP,uBAAuB,EACvB,IAAI,EACJ,QAAQ,GACU;IAClB,MAAM,QAAQ,GAAG,kBAAkB,IAAI,KAAC,cAAc,KAAG,CAAC;IAE1D,IAAI,YAAY,EAAE,CAAC;QACjB,OAAO,CACL,KAAC,cAAc,IACb,WAAW,EAAE,WAAW,EACxB,YAAY,EAAE,YAAY,EAC1B,cAAc,EAAE,cAAc,EAC9B,oBAAoB,EAAE,oBAAoB,EAC1C,OAAO,EAAE,OAAO,EAChB,uBAAuB,EAAE,uBAAuB,EAChD,IAAI,EAAE,IAAI,YAET,QAAQ,GACM,CAClB,CAAC;IACJ,CAAC;IAED,OAAO,CACL,KAAC,UAAU,IAAC,QAAQ,EAAE,QAAQ,YAC5B,KAAC,cAAc,IACb,WAAW,EAAE,WAAW,EACxB,YAAY,EAAE,YAAY,EAC1B,cAAc,EAAE,cAAc,EAC9B,oBAAoB,EAAE,oBAAoB,EAC1C,OAAO,EAAE,OAAO,EAChB,uBAAuB,EAAE,uBAAuB,EAChD,IAAI,EAAE,IAAI,YAET,QAAQ,GACM,GACN,CACd,CAAC;AACJ,CAAC","sourcesContent":["/**\n * Shared provider shell for agent-native template roots.\n *\n * Composes the providers every template needs:\n * QueryClientProvider → ThemeProvider → TooltipProvider → Toaster\n *\n * Templates keep their own `createAgentNativeQueryClient(overrides)` call and\n * pass the result in as `queryClient`. AppProviders never creates a client\n * internally so each template can apply its own query defaults (e.g. calendar's\n * `refetchOnWindowFocus: true`, mail's focus-refresh throttle).\n *\n * Public-path SSR pattern (calendar/clips/content):\n * Some templates have routes that must SSR real content for first-visit\n * signed-out users and crawlers, bypassing the `<ClientOnly>` gate.\n * Pass `isPublicPath` and `clientOnlyFallback` to activate this branch:\n *\n * <AppProviders\n * queryClient={queryClient}\n * isPublicPath={isPublicBookingPath(location.pathname)}\n * clientOnlyFallback={<DefaultSpinner />}\n * >\n * ...\n * </AppProviders>\n *\n * When `isPublicPath` is true the providers render without `<ClientOnly>`,\n * streaming real markup to the client. When false (the default) the standard\n * `<ClientOnly fallback={clientOnlyFallback}>` gate wraps everything.\n * When `clientOnlyFallback` is omitted, `<DefaultSpinner />` is used.\n *\n * Customisation props:\n * themeAttribute — passed to next-themes ThemeProvider `attribute`.\n * Defaults to \"class\". Use [\"class\", \"data-theme\"]\n * when CSS variables are also keyed off a data-theme\n * attribute (mail template).\n * tooltipDelayDuration — passed to Radix TooltipProvider `delayDuration`\n * (ms). Omit to use the Radix default (700 ms).\n * toaster — custom Toaster element rendered after children.\n * Pass `null` to suppress the built-in Toaster when\n * children already include a styled one.\n * Defaults to `<Toaster richColors position=\"bottom-left\" />`.\n * disableThemeTransitions — passed to next-themes ThemeProvider\n * `disableTransitionOnChange`. Defaults to `true`\n * (suppresses CSS transitions during theme switches,\n * which is the shadcn recommendation and avoids\n * flash artefacts). Set to `false` when the template\n * intentionally animates theme changes (e.g. content).\n */\n\nimport { TooltipProvider } from \"@radix-ui/react-tooltip\";\nimport { QueryClientProvider, type QueryClient } from \"@tanstack/react-query\";\nimport { ThemeProvider, type Attribute } from \"next-themes\";\nimport React from \"react\";\nimport { Toaster } from \"sonner\";\n\nimport { ClientOnly } from \"./ClientOnly.js\";\nimport { DefaultSpinner } from \"./DefaultSpinner.js\";\nimport {\n AgentNativeI18nProvider,\n type AgentNativeI18nProviderProps,\n} from \"./i18n.js\";\n\nexport interface AppProvidersProps {\n /** QueryClient instance — create with `createAgentNativeQueryClient()`. */\n queryClient: QueryClient;\n\n /**\n * Default theme passed to next-themes `ThemeProvider`.\n * Defaults to `\"system\"`. Dark-first templates (slides, macros, analytics)\n * pass `\"dark\"`.\n */\n defaultTheme?: string;\n\n /**\n * Passed to next-themes ThemeProvider `attribute`.\n * Defaults to \"class\". Pass [\"class\", \"data-theme\"] when your CSS variables\n * are also keyed off a data-theme attribute (mail template).\n */\n themeAttribute?: Attribute | Attribute[];\n\n /**\n * Passed to Radix TooltipProvider `delayDuration` (ms).\n * Omit to use the Radix default (700 ms).\n */\n tooltipDelayDuration?: number;\n\n /**\n * Custom Toaster element rendered after children inside TooltipProvider.\n * Pass `null` to suppress the built-in Toaster when children already\n * include a styled one.\n * Defaults to `<Toaster richColors position=\"bottom-left\" />`.\n */\n toaster?: React.ReactNode | null;\n\n /**\n * Passed to next-themes ThemeProvider `disableTransitionOnChange`.\n * Defaults to `true` (suppresses CSS transitions on theme switch, per the\n * shadcn recommendation). Set to `false` when the template intentionally\n * animates theme changes (e.g. content's 3-way theme cycle).\n */\n disableThemeTransitions?: boolean;\n\n /**\n * Optional localization runtime configuration. When omitted, AppProviders\n * still mounts the i18n provider with an English fallback so templates can\n * call useT/useLocale before they add catalogs. Pass false to opt out.\n */\n i18n?: Omit<AgentNativeI18nProviderProps, \"children\"> | false;\n\n /**\n * When true the providers render without a `<ClientOnly>` gate so SSR\n * streams real markup for public/unauthenticated paths.\n * Defaults to false (authenticated app shell, ClientOnly-gated).\n */\n isPublicPath?: boolean;\n\n /**\n * Fallback rendered by `<ClientOnly>` while JS hydrates on private paths.\n * Defaults to `<DefaultSpinner />`.\n */\n clientOnlyFallback?: React.ReactNode;\n\n children: React.ReactNode;\n}\n\nconst DEFAULT_TOASTER = <Toaster richColors position=\"bottom-left\" />;\n\nfunction ProvidersInner({\n queryClient,\n defaultTheme = \"system\",\n themeAttribute = \"class\",\n tooltipDelayDuration,\n toaster = DEFAULT_TOASTER,\n disableThemeTransitions = true,\n i18n,\n children,\n}: {\n queryClient: QueryClient;\n defaultTheme?: string;\n themeAttribute?: Attribute | Attribute[];\n tooltipDelayDuration?: number;\n toaster?: React.ReactNode | null;\n disableThemeTransitions?: boolean;\n i18n?: Omit<AgentNativeI18nProviderProps, \"children\"> | false;\n children: React.ReactNode;\n}) {\n const localizedChildren =\n i18n === false ? (\n children\n ) : (\n <AgentNativeI18nProvider {...(i18n ?? {})}>\n {children}\n </AgentNativeI18nProvider>\n );\n\n return (\n <QueryClientProvider client={queryClient}>\n <ThemeProvider\n attribute={themeAttribute}\n defaultTheme={defaultTheme}\n enableSystem\n disableTransitionOnChange={disableThemeTransitions}\n >\n <TooltipProvider delayDuration={tooltipDelayDuration}>\n {localizedChildren}\n {toaster}\n </TooltipProvider>\n </ThemeProvider>\n </QueryClientProvider>\n );\n}\n\nexport function AppProviders({\n queryClient,\n isPublicPath = false,\n clientOnlyFallback,\n defaultTheme,\n themeAttribute,\n tooltipDelayDuration,\n toaster,\n disableThemeTransitions,\n i18n,\n children,\n}: AppProvidersProps) {\n const fallback = clientOnlyFallback ?? <DefaultSpinner />;\n\n if (isPublicPath) {\n return (\n <ProvidersInner\n queryClient={queryClient}\n defaultTheme={defaultTheme}\n themeAttribute={themeAttribute}\n tooltipDelayDuration={tooltipDelayDuration}\n toaster={toaster}\n disableThemeTransitions={disableThemeTransitions}\n i18n={i18n}\n >\n {children}\n </ProvidersInner>\n );\n }\n\n return (\n <ClientOnly fallback={fallback}>\n <ProvidersInner\n queryClient={queryClient}\n defaultTheme={defaultTheme}\n themeAttribute={themeAttribute}\n tooltipDelayDuration={tooltipDelayDuration}\n toaster={toaster}\n disableThemeTransitions={disableThemeTransitions}\n i18n={i18n}\n >\n {children}\n </ProvidersInner>\n </ClientOnly>\n );\n}\n"]}
@@ -6,5 +6,8 @@ export { useCollaborativeMap, useCollaborativeArray, type UseCollaborativeMapOpt
6
6
  export { PresenceBar, type PresenceBarProps, } from "../components/PresenceBar.js";
7
7
  export { AgentPresenceChip, type AgentPresenceChipProps, } from "../components/AgentPresenceChip.js";
8
8
  export { LiveCursorOverlay, type LiveCursorOverlayProps, type CursorMapFn, } from "../components/LiveCursorOverlay.js";
9
- export { RemoteSelectionRings, type RemoteSelectionRingsProps, } from "../components/RemoteSelectionRings.js";
9
+ export { RemoteSelectionRings, type RemoteSelectionRingsProps, type SelectionDescriptor, } from "../components/RemoteSelectionRings.js";
10
+ export { RecentEditHighlights, type RecentEditHighlightsProps, } from "../components/RecentEditHighlights.js";
11
+ export { appendRecentEdit, collectRecentEdits, publishRecentEdit, useRecentEdits, RECENT_EDITS_MAX, RECENT_EDIT_TTL_MS, type RecentEdit, type RecentEditDescriptor, type AttributedRecentEdit, type UseRecentEditsOptions, } from "../../collab/recent-edits.js";
12
+ export { useCollabUndo, useLocalOpUndo, createLocalOpUndoController, type UseCollabUndoOptions, type UseCollabUndoResult, type CollabUndoScope, type UseLocalOpUndoOptions, type UseLocalOpUndoResult, type LocalOpUndoEntry, type LocalOpUndoController, type CreateLocalOpUndoOptions, type UndoKeyboardOptions, } from "../../collab/undo.js";
10
13
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/client/collab/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,mBAAmB,EACnB,qBAAqB,EACrB,YAAY,EACZ,WAAW,EACX,wBAAwB,EACxB,KAAK,UAAU,EACf,KAAK,0BAA0B,EAC/B,KAAK,yBAAyB,GAC/B,MAAM,wBAAwB,CAAC;AAChC,OAAO,EAAE,eAAe,EAAE,MAAM,gCAAgC,CAAC;AACjE,OAAO,EACL,WAAW,EACX,YAAY,EACZ,cAAc,EACd,KAAK,aAAa,EAClB,KAAK,eAAe,EACpB,KAAK,iBAAiB,EACtB,KAAK,eAAe,GACrB,MAAM,0BAA0B,CAAC;AAClC,OAAO,EACL,aAAa,EACb,KAAK,oBAAoB,EACzB,KAAK,mBAAmB,EACxB,KAAK,kBAAkB,GACxB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EACL,mBAAmB,EACnB,qBAAqB,EACrB,KAAK,0BAA0B,EAC/B,KAAK,yBAAyB,EAC9B,KAAK,4BAA4B,EACjC,KAAK,2BAA2B,GACjC,MAAM,+BAA+B,CAAC;AACvC,OAAO,EACL,WAAW,EACX,KAAK,gBAAgB,GACtB,MAAM,8BAA8B,CAAC;AACtC,OAAO,EACL,iBAAiB,EACjB,KAAK,sBAAsB,GAC5B,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,iBAAiB,EACjB,KAAK,sBAAsB,EAC3B,KAAK,WAAW,GACjB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,oBAAoB,EACpB,KAAK,yBAAyB,GAC/B,MAAM,uCAAuC,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/client/collab/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,mBAAmB,EACnB,qBAAqB,EACrB,YAAY,EACZ,WAAW,EACX,wBAAwB,EACxB,KAAK,UAAU,EACf,KAAK,0BAA0B,EAC/B,KAAK,yBAAyB,GAC/B,MAAM,wBAAwB,CAAC;AAChC,OAAO,EAAE,eAAe,EAAE,MAAM,gCAAgC,CAAC;AACjE,OAAO,EACL,WAAW,EACX,YAAY,EACZ,cAAc,EACd,KAAK,aAAa,EAClB,KAAK,eAAe,EACpB,KAAK,iBAAiB,EACtB,KAAK,eAAe,GACrB,MAAM,0BAA0B,CAAC;AAClC,OAAO,EACL,aAAa,EACb,KAAK,oBAAoB,EACzB,KAAK,mBAAmB,EACxB,KAAK,kBAAkB,GACxB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EACL,mBAAmB,EACnB,qBAAqB,EACrB,KAAK,0BAA0B,EAC/B,KAAK,yBAAyB,EAC9B,KAAK,4BAA4B,EACjC,KAAK,2BAA2B,GACjC,MAAM,+BAA+B,CAAC;AACvC,OAAO,EACL,WAAW,EACX,KAAK,gBAAgB,GACtB,MAAM,8BAA8B,CAAC;AACtC,OAAO,EACL,iBAAiB,EACjB,KAAK,sBAAsB,GAC5B,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,iBAAiB,EACjB,KAAK,sBAAsB,EAC3B,KAAK,WAAW,GACjB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,oBAAoB,EACpB,KAAK,yBAAyB,EAC9B,KAAK,mBAAmB,GACzB,MAAM,uCAAuC,CAAC;AAC/C,OAAO,EACL,oBAAoB,EACpB,KAAK,yBAAyB,GAC/B,MAAM,uCAAuC,CAAC;AAC/C,OAAO,EACL,gBAAgB,EAChB,kBAAkB,EAClB,iBAAiB,EACjB,cAAc,EACd,gBAAgB,EAChB,kBAAkB,EAClB,KAAK,UAAU,EACf,KAAK,oBAAoB,EACzB,KAAK,oBAAoB,EACzB,KAAK,qBAAqB,GAC3B,MAAM,8BAA8B,CAAC;AACtC,OAAO,EACL,aAAa,EACb,cAAc,EACd,2BAA2B,EAC3B,KAAK,oBAAoB,EACzB,KAAK,mBAAmB,EACxB,KAAK,eAAe,EACpB,KAAK,qBAAqB,EAC1B,KAAK,oBAAoB,EACzB,KAAK,gBAAgB,EACrB,KAAK,qBAAqB,EAC1B,KAAK,wBAAwB,EAC7B,KAAK,mBAAmB,GACzB,MAAM,sBAAsB,CAAC"}
@@ -7,4 +7,7 @@ export { PresenceBar, } from "../components/PresenceBar.js";
7
7
  export { AgentPresenceChip, } from "../components/AgentPresenceChip.js";
8
8
  export { LiveCursorOverlay, } from "../components/LiveCursorOverlay.js";
9
9
  export { RemoteSelectionRings, } from "../components/RemoteSelectionRings.js";
10
+ export { RecentEditHighlights, } from "../components/RecentEditHighlights.js";
11
+ export { appendRecentEdit, collectRecentEdits, publishRecentEdit, useRecentEdits, RECENT_EDITS_MAX, RECENT_EDIT_TTL_MS, } from "../../collab/recent-edits.js";
12
+ export { useCollabUndo, useLocalOpUndo, createLocalOpUndoController, } from "../../collab/undo.js";
10
13
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/client/collab/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,mBAAmB,EACnB,qBAAqB,EACrB,YAAY,EACZ,WAAW,EACX,wBAAwB,GAIzB,MAAM,wBAAwB,CAAC;AAChC,OAAO,EAAE,eAAe,EAAE,MAAM,gCAAgC,CAAC;AACjE,OAAO,EACL,WAAW,EACX,YAAY,EACZ,cAAc,GAKf,MAAM,0BAA0B,CAAC;AAClC,OAAO,EACL,aAAa,GAId,MAAM,6BAA6B,CAAC;AACrC,OAAO,EACL,mBAAmB,EACnB,qBAAqB,GAKtB,MAAM,+BAA+B,CAAC;AACvC,OAAO,EACL,WAAW,GAEZ,MAAM,8BAA8B,CAAC;AACtC,OAAO,EACL,iBAAiB,GAElB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,iBAAiB,GAGlB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,oBAAoB,GAErB,MAAM,uCAAuC,CAAC","sourcesContent":["export {\n useCollaborativeDoc,\n isReconcileLeadClient,\n emailToColor,\n emailToName,\n dedupeCollabUsersByEmail,\n type CollabUser,\n type UseCollaborativeDocOptions,\n type UseCollaborativeDocResult,\n} from \"../../collab/client.js\";\nexport { AGENT_CLIENT_ID } from \"../../collab/agent-identity.js\";\nexport {\n usePresence,\n toNormalized,\n fromNormalized,\n type OtherPresence,\n type PresencePayload,\n type UsePresenceResult,\n type NormalizedPoint,\n} from \"../../collab/presence.js\";\nexport {\n useFollowUser,\n type UseFollowUserOptions,\n type UseFollowUserResult,\n type ViewportDescriptor,\n} from \"../../collab/follow-mode.js\";\nexport {\n useCollaborativeMap,\n useCollaborativeArray,\n type UseCollaborativeMapOptions,\n type UseCollaborativeMapResult,\n type UseCollaborativeArrayOptions,\n type UseCollaborativeArrayResult,\n} from \"../../collab/client-struct.js\";\nexport {\n PresenceBar,\n type PresenceBarProps,\n} from \"../components/PresenceBar.js\";\nexport {\n AgentPresenceChip,\n type AgentPresenceChipProps,\n} from \"../components/AgentPresenceChip.js\";\nexport {\n LiveCursorOverlay,\n type LiveCursorOverlayProps,\n type CursorMapFn,\n} from \"../components/LiveCursorOverlay.js\";\nexport {\n RemoteSelectionRings,\n type RemoteSelectionRingsProps,\n} from \"../components/RemoteSelectionRings.js\";\n"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/client/collab/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,mBAAmB,EACnB,qBAAqB,EACrB,YAAY,EACZ,WAAW,EACX,wBAAwB,GAIzB,MAAM,wBAAwB,CAAC;AAChC,OAAO,EAAE,eAAe,EAAE,MAAM,gCAAgC,CAAC;AACjE,OAAO,EACL,WAAW,EACX,YAAY,EACZ,cAAc,GAKf,MAAM,0BAA0B,CAAC;AAClC,OAAO,EACL,aAAa,GAId,MAAM,6BAA6B,CAAC;AACrC,OAAO,EACL,mBAAmB,EACnB,qBAAqB,GAKtB,MAAM,+BAA+B,CAAC;AACvC,OAAO,EACL,WAAW,GAEZ,MAAM,8BAA8B,CAAC;AACtC,OAAO,EACL,iBAAiB,GAElB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,iBAAiB,GAGlB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EACL,oBAAoB,GAGrB,MAAM,uCAAuC,CAAC;AAC/C,OAAO,EACL,oBAAoB,GAErB,MAAM,uCAAuC,CAAC;AAC/C,OAAO,EACL,gBAAgB,EAChB,kBAAkB,EAClB,iBAAiB,EACjB,cAAc,EACd,gBAAgB,EAChB,kBAAkB,GAKnB,MAAM,8BAA8B,CAAC;AACtC,OAAO,EACL,aAAa,EACb,cAAc,EACd,2BAA2B,GAU5B,MAAM,sBAAsB,CAAC","sourcesContent":["export {\n useCollaborativeDoc,\n isReconcileLeadClient,\n emailToColor,\n emailToName,\n dedupeCollabUsersByEmail,\n type CollabUser,\n type UseCollaborativeDocOptions,\n type UseCollaborativeDocResult,\n} from \"../../collab/client.js\";\nexport { AGENT_CLIENT_ID } from \"../../collab/agent-identity.js\";\nexport {\n usePresence,\n toNormalized,\n fromNormalized,\n type OtherPresence,\n type PresencePayload,\n type UsePresenceResult,\n type NormalizedPoint,\n} from \"../../collab/presence.js\";\nexport {\n useFollowUser,\n type UseFollowUserOptions,\n type UseFollowUserResult,\n type ViewportDescriptor,\n} from \"../../collab/follow-mode.js\";\nexport {\n useCollaborativeMap,\n useCollaborativeArray,\n type UseCollaborativeMapOptions,\n type UseCollaborativeMapResult,\n type UseCollaborativeArrayOptions,\n type UseCollaborativeArrayResult,\n} from \"../../collab/client-struct.js\";\nexport {\n PresenceBar,\n type PresenceBarProps,\n} from \"../components/PresenceBar.js\";\nexport {\n AgentPresenceChip,\n type AgentPresenceChipProps,\n} from \"../components/AgentPresenceChip.js\";\nexport {\n LiveCursorOverlay,\n type LiveCursorOverlayProps,\n type CursorMapFn,\n} from \"../components/LiveCursorOverlay.js\";\nexport {\n RemoteSelectionRings,\n type RemoteSelectionRingsProps,\n type SelectionDescriptor,\n} from \"../components/RemoteSelectionRings.js\";\nexport {\n RecentEditHighlights,\n type RecentEditHighlightsProps,\n} from \"../components/RecentEditHighlights.js\";\nexport {\n appendRecentEdit,\n collectRecentEdits,\n publishRecentEdit,\n useRecentEdits,\n RECENT_EDITS_MAX,\n RECENT_EDIT_TTL_MS,\n type RecentEdit,\n type RecentEditDescriptor,\n type AttributedRecentEdit,\n type UseRecentEditsOptions,\n} from \"../../collab/recent-edits.js\";\nexport {\n useCollabUndo,\n useLocalOpUndo,\n createLocalOpUndoController,\n type UseCollabUndoOptions,\n type UseCollabUndoResult,\n type CollabUndoScope,\n type UseLocalOpUndoOptions,\n type UseLocalOpUndoResult,\n type LocalOpUndoEntry,\n type LocalOpUndoController,\n type CreateLocalOpUndoOptions,\n type UndoKeyboardOptions,\n} from \"../../collab/undo.js\";\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"LiveCursorOverlay.d.ts","sourceRoot":"","sources":["../../../src/client/components/LiveCursorOverlay.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAIH,OAAO,KAAK,EAAE,aAAa,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAE/E,MAAM,WAAW,WAAW;IAC1B,+EAA+E;IAC/E,CAAC,IAAI,EAAE,eAAe,GAAG;QAAE,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;CACnD;AAED,MAAM,WAAW,sBAAsB;IACrC,iDAAiD;IACjD,MAAM,EAAE,aAAa,EAAE,CAAC;IACxB;;;;OAIG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB;;;OAGG;IACH,SAAS,CAAC,EAAE,WAAW,CAAC;IACxB;;;OAGG;IACH,YAAY,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IACnD,gDAAgD;IAChD,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAuFD,wBAAgB,iBAAiB,CAAC,EAChC,MAAM,EACN,SAAoB,EACpB,SAAS,EACT,YAAY,EACZ,SAAS,GACV,EAAE,sBAAsB,+BAuFxB"}
1
+ {"version":3,"file":"LiveCursorOverlay.d.ts","sourceRoot":"","sources":["../../../src/client/components/LiveCursorOverlay.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAIH,OAAO,KAAK,EAAE,aAAa,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAE/E,MAAM,WAAW,WAAW;IAC1B,+EAA+E;IAC/E,CAAC,IAAI,EAAE,eAAe,GAAG;QAAE,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;CACnD;AAED,MAAM,WAAW,sBAAsB;IACrC,iDAAiD;IACjD,MAAM,EAAE,aAAa,EAAE,CAAC;IACxB;;;;OAIG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB;;;OAGG;IACH,SAAS,CAAC,EAAE,WAAW,CAAC;IACxB;;;OAGG;IACH,YAAY,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IACnD,gDAAgD;IAChD,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAsGD,wBAAgB,iBAAiB,CAAC,EAChC,MAAM,EACN,SAAoB,EACpB,SAAS,EACT,YAAY,EACZ,SAAS,GACV,EAAE,sBAAsB,+BAuFxB"}
@@ -35,10 +35,13 @@ const CursorLabel = memo(function CursorLabel({ entry, }) {
35
35
  transition: "left 120ms linear, top 120ms linear",
36
36
  width: 0,
37
37
  height: 0,
38
- }, children: [_jsx(CursorPointer, { color: color }), _jsx("div", { style: {
38
+ }, children: [_jsx(CursorPointer, { color: color }), _jsxs("div", { style: {
39
39
  position: "absolute",
40
40
  left: 31,
41
41
  top: 31,
42
+ display: "flex",
43
+ alignItems: "center",
44
+ gap: 5,
42
45
  backgroundColor: color,
43
46
  color: "#fff",
44
47
  fontSize: 12,
@@ -48,10 +51,15 @@ const CursorLabel = memo(function CursorLabel({ entry, }) {
48
51
  borderRadius: 2,
49
52
  whiteSpace: "nowrap",
50
53
  boxShadow: "0 5px 12px rgba(15, 23, 42, 0.16)",
51
- maxWidth: 120,
54
+ maxWidth: 150,
52
55
  overflow: "hidden",
53
56
  textOverflow: "ellipsis",
54
- }, children: label })] }));
57
+ }, children: [other.user.avatarUrl ? (_jsx("img", { src: other.user.avatarUrl, alt: "", style: {
58
+ width: 14,
59
+ height: 14,
60
+ borderRadius: "50%",
61
+ flexShrink: 0,
62
+ } })) : null, label] })] }));
55
63
  });
56
64
  export function LiveCursorOverlay({ others, cursorKey = "cursor", mapCoords, containerRef, className, }) {
57
65
  const overlayRef = useRef(null);
@@ -1 +1 @@
1
- {"version":3,"file":"LiveCursorOverlay.js","sourceRoot":"","sources":["../../../src/client/components/LiveCursorOverlay.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n * LiveCursorOverlay — renders remote users' cursors over an absolutely-\n * positioned container.\n *\n * Cursor positions are expected as normalized coordinates (0–1 relative to\n * the container's content size) so different zoom/scroll positions map\n * correctly. Pass a `mapCoords` prop to handle non-identity transforms\n * (e.g. a zoomed canvas).\n *\n * The agent uses the same pointer shape with an \"AI\" label.\n *\n * Cursors fade out after 10 seconds of no movement.\n */\n\nimport { useState, useEffect, useRef, memo } from \"react\";\n\nimport type { OtherPresence, NormalizedPoint } from \"../../collab/presence.js\";\n\nexport interface CursorMapFn {\n /** Convert normalized coords to pixel offsets within the overlay container. */\n (norm: NormalizedPoint): { x: number; y: number };\n}\n\nexport interface LiveCursorOverlayProps {\n /** Remote participants with presence payload. */\n others: OtherPresence[];\n /**\n * Key inside presence payload that carries the cursor position.\n * Default: \"cursor\"\n * Expected shape: { x: number; y: number } (normalized 0–1).\n */\n cursorKey?: string;\n /**\n * Override coordinate mapping. Default: scale by container clientWidth/Height.\n * Pass this when the container uses transform: scale() or has virtual scroll.\n */\n mapCoords?: CursorMapFn;\n /**\n * Container element ref. Required when mapCoords is not provided —\n * used to compute pixel positions from normalized coords.\n */\n containerRef?: React.RefObject<HTMLElement | null>;\n /** Additional CSS class for the overlay div. */\n className?: string;\n}\n\nconst STALE_MS = 10_000; // Fade out cursors older than 10s\n\nfunction CursorPointer({ color }: { color: string }) {\n return (\n <svg\n xmlns=\"http://www.w3.org/2000/svg\"\n width=\"25\"\n height=\"29\"\n viewBox=\"0 0 25 29\"\n fill=\"none\"\n aria-hidden\n style={{\n display: \"block\",\n filter: \"drop-shadow(0 2px 3px rgba(15, 23, 42, 0.3))\",\n }}\n >\n <path\n d=\"M2.5 2.5L21.5 11L12.6 14.1L8.3 24.5L2.5 2.5Z\"\n fill={color}\n stroke=\"white\"\n strokeLinejoin=\"round\"\n strokeWidth=\"3\"\n />\n </svg>\n );\n}\n\ninterface CursorEntry {\n other: OtherPresence;\n x: number;\n y: number;\n lastSeen: number;\n}\n\nconst CursorLabel = memo(function CursorLabel({\n entry,\n}: {\n entry: CursorEntry;\n}) {\n const { other, x, y } = entry;\n const color = other.user.color || \"#94a3b8\";\n const label = other.isAgent ? \"AI\" : other.user.name || other.user.email;\n\n return (\n <div\n aria-label={`${label} cursor`}\n style={{\n position: \"absolute\",\n left: x,\n top: y,\n pointerEvents: \"none\",\n userSelect: \"none\",\n transform: \"translate(-2px, -2px)\",\n zIndex: 9999,\n transition: \"left 120ms linear, top 120ms linear\",\n width: 0,\n height: 0,\n }}\n >\n <CursorPointer color={color} />\n <div\n style={{\n position: \"absolute\",\n left: 31,\n top: 31,\n backgroundColor: color,\n color: \"#fff\",\n fontSize: 12,\n fontWeight: 500,\n lineHeight: \"16px\",\n padding: \"2px 7px\",\n borderRadius: 2,\n whiteSpace: \"nowrap\",\n boxShadow: \"0 5px 12px rgba(15, 23, 42, 0.16)\",\n maxWidth: 120,\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n }}\n >\n {label}\n </div>\n </div>\n );\n});\n\nexport function LiveCursorOverlay({\n others,\n cursorKey = \"cursor\",\n mapCoords,\n containerRef,\n className,\n}: LiveCursorOverlayProps) {\n const overlayRef = useRef<HTMLDivElement>(null);\n const [, tick] = useState(0); // Force re-render to prune stale cursors\n const entriesRef = useRef<Map<number, CursorEntry>>(new Map());\n\n // Tick every 5s to prune stale cursors (no re-render storm).\n useEffect(() => {\n const id = setInterval(() => tick((n) => n + 1), 5_000);\n return () => clearInterval(id);\n }, []);\n\n // Build entries from others, computing pixel positions.\n const now = Date.now();\n const visible: CursorEntry[] = [];\n\n for (const other of others) {\n const pos = other.presence[cursorKey] as NormalizedPoint | undefined;\n if (!pos || typeof pos.x !== \"number\" || typeof pos.y !== \"number\")\n continue;\n\n // Compute pixel position.\n let px: number;\n let py: number;\n if (mapCoords) {\n const mapped = mapCoords(pos);\n px = mapped.x;\n py = mapped.y;\n } else {\n const container =\n containerRef?.current ?? overlayRef.current?.parentElement;\n const w = container ? container.clientWidth : 0;\n const h = container ? container.clientHeight : 0;\n px = pos.x * w;\n py = pos.y * h;\n }\n\n const prev = entriesRef.current.get(other.clientId);\n const lastSeen =\n prev && prev.x === px && prev.y === py ? prev.lastSeen : now;\n const entry: CursorEntry = { other, x: px, y: py, lastSeen };\n entriesRef.current.set(other.clientId, entry);\n\n if (now - lastSeen < STALE_MS) {\n visible.push(entry);\n }\n }\n\n // Remove entries for participants who left.\n for (const clientId of entriesRef.current.keys()) {\n if (!others.find((o) => o.clientId === clientId)) {\n entriesRef.current.delete(clientId);\n }\n }\n\n if (visible.length === 0) {\n return (\n <div\n ref={overlayRef}\n aria-hidden\n style={{\n position: \"absolute\",\n inset: 0,\n pointerEvents: \"none\",\n overflow: \"hidden\",\n }}\n className={className}\n />\n );\n }\n\n return (\n <div\n ref={overlayRef}\n aria-hidden\n style={{\n position: \"absolute\",\n inset: 0,\n pointerEvents: \"none\",\n overflow: \"hidden\",\n }}\n className={className}\n >\n {visible.map((entry) => (\n <CursorLabel key={entry.other.clientId} entry={entry} />\n ))}\n </div>\n );\n}\n"]}
1
+ {"version":3,"file":"LiveCursorOverlay.js","sourceRoot":"","sources":["../../../src/client/components/LiveCursorOverlay.tsx"],"names":[],"mappings":";AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,OAAO,CAAC;AAgC1D,MAAM,QAAQ,GAAG,MAAM,CAAC,CAAC,kCAAkC;AAE3D,SAAS,aAAa,CAAC,EAAE,KAAK,EAAqB;IACjD,OAAO,CACL,cACE,KAAK,EAAC,4BAA4B,EAClC,KAAK,EAAC,IAAI,EACV,MAAM,EAAC,IAAI,EACX,OAAO,EAAC,WAAW,EACnB,IAAI,EAAC,MAAM,uBAEX,KAAK,EAAE;YACL,OAAO,EAAE,OAAO;YAChB,MAAM,EAAE,8CAA8C;SACvD,YAED,eACE,CAAC,EAAC,8CAA8C,EAChD,IAAI,EAAE,KAAK,EACX,MAAM,EAAC,OAAO,EACd,cAAc,EAAC,OAAO,EACtB,WAAW,EAAC,GAAG,GACf,GACE,CACP,CAAC;AACJ,CAAC;AASD,MAAM,WAAW,GAAG,IAAI,CAAC,SAAS,WAAW,CAAC,EAC5C,KAAK,GAGN;IACC,MAAM,EAAE,KAAK,EAAE,CAAC,EAAE,CAAC,EAAE,GAAG,KAAK,CAAC;IAC9B,MAAM,KAAK,GAAG,KAAK,CAAC,IAAI,CAAC,KAAK,IAAI,SAAS,CAAC;IAC5C,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,IAAI,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC;IAEzE,OAAO,CACL,6BACc,GAAG,KAAK,SAAS,EAC7B,KAAK,EAAE;YACL,QAAQ,EAAE,UAAU;YACpB,IAAI,EAAE,CAAC;YACP,GAAG,EAAE,CAAC;YACN,aAAa,EAAE,MAAM;YACrB,UAAU,EAAE,MAAM;YAClB,SAAS,EAAE,uBAAuB;YAClC,MAAM,EAAE,IAAI;YACZ,UAAU,EAAE,qCAAqC;YACjD,KAAK,EAAE,CAAC;YACR,MAAM,EAAE,CAAC;SACV,aAED,KAAC,aAAa,IAAC,KAAK,EAAE,KAAK,GAAI,EAC/B,eACE,KAAK,EAAE;oBACL,QAAQ,EAAE,UAAU;oBACpB,IAAI,EAAE,EAAE;oBACR,GAAG,EAAE,EAAE;oBACP,OAAO,EAAE,MAAM;oBACf,UAAU,EAAE,QAAQ;oBACpB,GAAG,EAAE,CAAC;oBACN,eAAe,EAAE,KAAK;oBACtB,KAAK,EAAE,MAAM;oBACb,QAAQ,EAAE,EAAE;oBACZ,UAAU,EAAE,GAAG;oBACf,UAAU,EAAE,MAAM;oBAClB,OAAO,EAAE,SAAS;oBAClB,YAAY,EAAE,CAAC;oBACf,UAAU,EAAE,QAAQ;oBACpB,SAAS,EAAE,mCAAmC;oBAC9C,QAAQ,EAAE,GAAG;oBACb,QAAQ,EAAE,QAAQ;oBAClB,YAAY,EAAE,UAAU;iBACzB,aAEC,KAAK,CAAC,IAA+B,CAAC,SAAS,CAAC,CAAC,CAAC,CAClD,cACE,GAAG,EAAG,KAAK,CAAC,IAA+B,CAAC,SAAS,EACrD,GAAG,EAAC,EAAE,EACN,KAAK,EAAE;4BACL,KAAK,EAAE,EAAE;4BACT,MAAM,EAAE,EAAE;4BACV,YAAY,EAAE,KAAK;4BACnB,UAAU,EAAE,CAAC;yBACd,GACD,CACH,CAAC,CAAC,CAAC,IAAI,EACP,KAAK,IACF,IACF,CACP,CAAC;AACJ,CAAC,CAAC,CAAC;AAEH,MAAM,UAAU,iBAAiB,CAAC,EAChC,MAAM,EACN,SAAS,GAAG,QAAQ,EACpB,SAAS,EACT,YAAY,EACZ,SAAS,GACc;IACvB,MAAM,UAAU,GAAG,MAAM,CAAiB,IAAI,CAAC,CAAC;IAChD,MAAM,CAAC,EAAE,IAAI,CAAC,GAAG,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,yCAAyC;IACvE,MAAM,UAAU,GAAG,MAAM,CAA2B,IAAI,GAAG,EAAE,CAAC,CAAC;IAE/D,6DAA6D;IAC7D,SAAS,CAAC,GAAG,EAAE;QACb,MAAM,EAAE,GAAG,WAAW,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,EAAE,KAAK,CAAC,CAAC;QACxD,OAAO,GAAG,EAAE,CAAC,aAAa,CAAC,EAAE,CAAC,CAAC;IACjC,CAAC,EAAE,EAAE,CAAC,CAAC;IAEP,wDAAwD;IACxD,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IACvB,MAAM,OAAO,GAAkB,EAAE,CAAC;IAElC,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;QAC3B,MAAM,GAAG,GAAG,KAAK,CAAC,QAAQ,CAAC,SAAS,CAAgC,CAAC;QACrE,IAAI,CAAC,GAAG,IAAI,OAAO,GAAG,CAAC,CAAC,KAAK,QAAQ,IAAI,OAAO,GAAG,CAAC,CAAC,KAAK,QAAQ;YAChE,SAAS;QAEX,0BAA0B;QAC1B,IAAI,EAAU,CAAC;QACf,IAAI,EAAU,CAAC;QACf,IAAI,SAAS,EAAE,CAAC;YACd,MAAM,MAAM,GAAG,SAAS,CAAC,GAAG,CAAC,CAAC;YAC9B,EAAE,GAAG,MAAM,CAAC,CAAC,CAAC;YACd,EAAE,GAAG,MAAM,CAAC,CAAC,CAAC;QAChB,CAAC;aAAM,CAAC;YACN,MAAM,SAAS,GACb,YAAY,EAAE,OAAO,IAAI,UAAU,CAAC,OAAO,EAAE,aAAa,CAAC;YAC7D,MAAM,CAAC,GAAG,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,WAAW,CAAC,CAAC,CAAC,CAAC,CAAC;YAChD,MAAM,CAAC,GAAG,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC,CAAC;YACjD,EAAE,GAAG,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC;YACf,EAAE,GAAG,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC;QACjB,CAAC;QAED,MAAM,IAAI,GAAG,UAAU,CAAC,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;QACpD,MAAM,QAAQ,GACZ,IAAI,IAAI,IAAI,CAAC,CAAC,KAAK,EAAE,IAAI,IAAI,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC,GAAG,CAAC;QAC/D,MAAM,KAAK,GAAgB,EAAE,KAAK,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,EAAE,EAAE,EAAE,QAAQ,EAAE,CAAC;QAC7D,UAAU,CAAC,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAC;QAE9C,IAAI,GAAG,GAAG,QAAQ,GAAG,QAAQ,EAAE,CAAC;YAC9B,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACtB,CAAC;IACH,CAAC;IAED,4CAA4C;IAC5C,KAAK,MAAM,QAAQ,IAAI,UAAU,CAAC,OAAO,CAAC,IAAI,EAAE,EAAE,CAAC;QACjD,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,KAAK,QAAQ,CAAC,EAAE,CAAC;YACjD,UAAU,CAAC,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;QACtC,CAAC;IACH,CAAC;IAED,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO,CACL,cACE,GAAG,EAAE,UAAU,uBAEf,KAAK,EAAE;gBACL,QAAQ,EAAE,UAAU;gBACpB,KAAK,EAAE,CAAC;gBACR,aAAa,EAAE,MAAM;gBACrB,QAAQ,EAAE,QAAQ;aACnB,EACD,SAAS,EAAE,SAAS,GACpB,CACH,CAAC;IACJ,CAAC;IAED,OAAO,CACL,cACE,GAAG,EAAE,UAAU,uBAEf,KAAK,EAAE;YACL,QAAQ,EAAE,UAAU;YACpB,KAAK,EAAE,CAAC;YACR,aAAa,EAAE,MAAM;YACrB,QAAQ,EAAE,QAAQ;SACnB,EACD,SAAS,EAAE,SAAS,YAEnB,OAAO,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,CACtB,KAAC,WAAW,IAA4B,KAAK,EAAE,KAAK,IAAlC,KAAK,CAAC,KAAK,CAAC,QAAQ,CAAkB,CACzD,CAAC,GACE,CACP,CAAC;AACJ,CAAC","sourcesContent":["/**\n * LiveCursorOverlay — renders remote users' cursors over an absolutely-\n * positioned container.\n *\n * Cursor positions are expected as normalized coordinates (0–1 relative to\n * the container's content size) so different zoom/scroll positions map\n * correctly. Pass a `mapCoords` prop to handle non-identity transforms\n * (e.g. a zoomed canvas).\n *\n * The agent uses the same pointer shape with an \"AI\" label.\n *\n * Cursors fade out after 10 seconds of no movement.\n */\n\nimport { useState, useEffect, useRef, memo } from \"react\";\n\nimport type { OtherPresence, NormalizedPoint } from \"../../collab/presence.js\";\n\nexport interface CursorMapFn {\n /** Convert normalized coords to pixel offsets within the overlay container. */\n (norm: NormalizedPoint): { x: number; y: number };\n}\n\nexport interface LiveCursorOverlayProps {\n /** Remote participants with presence payload. */\n others: OtherPresence[];\n /**\n * Key inside presence payload that carries the cursor position.\n * Default: \"cursor\"\n * Expected shape: { x: number; y: number } (normalized 0–1).\n */\n cursorKey?: string;\n /**\n * Override coordinate mapping. Default: scale by container clientWidth/Height.\n * Pass this when the container uses transform: scale() or has virtual scroll.\n */\n mapCoords?: CursorMapFn;\n /**\n * Container element ref. Required when mapCoords is not provided —\n * used to compute pixel positions from normalized coords.\n */\n containerRef?: React.RefObject<HTMLElement | null>;\n /** Additional CSS class for the overlay div. */\n className?: string;\n}\n\nconst STALE_MS = 10_000; // Fade out cursors older than 10s\n\nfunction CursorPointer({ color }: { color: string }) {\n return (\n <svg\n xmlns=\"http://www.w3.org/2000/svg\"\n width=\"25\"\n height=\"29\"\n viewBox=\"0 0 25 29\"\n fill=\"none\"\n aria-hidden\n style={{\n display: \"block\",\n filter: \"drop-shadow(0 2px 3px rgba(15, 23, 42, 0.3))\",\n }}\n >\n <path\n d=\"M2.5 2.5L21.5 11L12.6 14.1L8.3 24.5L2.5 2.5Z\"\n fill={color}\n stroke=\"white\"\n strokeLinejoin=\"round\"\n strokeWidth=\"3\"\n />\n </svg>\n );\n}\n\ninterface CursorEntry {\n other: OtherPresence;\n x: number;\n y: number;\n lastSeen: number;\n}\n\nconst CursorLabel = memo(function CursorLabel({\n entry,\n}: {\n entry: CursorEntry;\n}) {\n const { other, x, y } = entry;\n const color = other.user.color || \"#94a3b8\";\n const label = other.isAgent ? \"AI\" : other.user.name || other.user.email;\n\n return (\n <div\n aria-label={`${label} cursor`}\n style={{\n position: \"absolute\",\n left: x,\n top: y,\n pointerEvents: \"none\",\n userSelect: \"none\",\n transform: \"translate(-2px, -2px)\",\n zIndex: 9999,\n transition: \"left 120ms linear, top 120ms linear\",\n width: 0,\n height: 0,\n }}\n >\n <CursorPointer color={color} />\n <div\n style={{\n position: \"absolute\",\n left: 31,\n top: 31,\n display: \"flex\",\n alignItems: \"center\",\n gap: 5,\n backgroundColor: color,\n color: \"#fff\",\n fontSize: 12,\n fontWeight: 500,\n lineHeight: \"16px\",\n padding: \"2px 7px\",\n borderRadius: 2,\n whiteSpace: \"nowrap\",\n boxShadow: \"0 5px 12px rgba(15, 23, 42, 0.16)\",\n maxWidth: 150,\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n }}\n >\n {(other.user as { avatarUrl?: string }).avatarUrl ? (\n <img\n src={(other.user as { avatarUrl?: string }).avatarUrl}\n alt=\"\"\n style={{\n width: 14,\n height: 14,\n borderRadius: \"50%\",\n flexShrink: 0,\n }}\n />\n ) : null}\n {label}\n </div>\n </div>\n );\n});\n\nexport function LiveCursorOverlay({\n others,\n cursorKey = \"cursor\",\n mapCoords,\n containerRef,\n className,\n}: LiveCursorOverlayProps) {\n const overlayRef = useRef<HTMLDivElement>(null);\n const [, tick] = useState(0); // Force re-render to prune stale cursors\n const entriesRef = useRef<Map<number, CursorEntry>>(new Map());\n\n // Tick every 5s to prune stale cursors (no re-render storm).\n useEffect(() => {\n const id = setInterval(() => tick((n) => n + 1), 5_000);\n return () => clearInterval(id);\n }, []);\n\n // Build entries from others, computing pixel positions.\n const now = Date.now();\n const visible: CursorEntry[] = [];\n\n for (const other of others) {\n const pos = other.presence[cursorKey] as NormalizedPoint | undefined;\n if (!pos || typeof pos.x !== \"number\" || typeof pos.y !== \"number\")\n continue;\n\n // Compute pixel position.\n let px: number;\n let py: number;\n if (mapCoords) {\n const mapped = mapCoords(pos);\n px = mapped.x;\n py = mapped.y;\n } else {\n const container =\n containerRef?.current ?? overlayRef.current?.parentElement;\n const w = container ? container.clientWidth : 0;\n const h = container ? container.clientHeight : 0;\n px = pos.x * w;\n py = pos.y * h;\n }\n\n const prev = entriesRef.current.get(other.clientId);\n const lastSeen =\n prev && prev.x === px && prev.y === py ? prev.lastSeen : now;\n const entry: CursorEntry = { other, x: px, y: py, lastSeen };\n entriesRef.current.set(other.clientId, entry);\n\n if (now - lastSeen < STALE_MS) {\n visible.push(entry);\n }\n }\n\n // Remove entries for participants who left.\n for (const clientId of entriesRef.current.keys()) {\n if (!others.find((o) => o.clientId === clientId)) {\n entriesRef.current.delete(clientId);\n }\n }\n\n if (visible.length === 0) {\n return (\n <div\n ref={overlayRef}\n aria-hidden\n style={{\n position: \"absolute\",\n inset: 0,\n pointerEvents: \"none\",\n overflow: \"hidden\",\n }}\n className={className}\n />\n );\n }\n\n return (\n <div\n ref={overlayRef}\n aria-hidden\n style={{\n position: \"absolute\",\n inset: 0,\n pointerEvents: \"none\",\n overflow: \"hidden\",\n }}\n className={className}\n >\n {visible.map((entry) => (\n <CursorLabel key={entry.other.clientId} entry={entry} />\n ))}\n </div>\n );\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"PresenceBar.d.ts","sourceRoot":"","sources":["../../../src/client/components/PresenceBar.tsx"],"names":[],"mappings":"AAEA,OAAO,EACL,KAAK,UAAU,EAIhB,MAAM,wBAAwB,CAAC;AAQhC,MAAM,WAAW,gBAAgB;IAC/B,6CAA6C;IAC7C,WAAW,EAAE,UAAU,EAAE,CAAC;IAC1B,sDAAsD;IACtD,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,4DAA4D;IAC5D,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,uDAAuD;IACvD,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,2DAA2D;IAC3D,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,8BAA8B;IAC9B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB;;;OAGG;IACH,aAAa,CAAC,EAAE,CAAC,IAAI,EAAE,UAAU,GAAG,IAAI,KAAK,IAAI,CAAC;IAClD;;;OAGG;IACH,cAAc,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CAChC;AA8ND,wBAAgB,WAAW,CAAC,EAC1B,WAAW,EACX,YAAY,EACZ,WAAW,EACX,gBAAgB,EAChB,UAAc,EACd,SAAS,EACT,aAAa,EACb,cAAc,GACf,EAAE,gBAAgB,sCA+DlB"}
1
+ {"version":3,"file":"PresenceBar.d.ts","sourceRoot":"","sources":["../../../src/client/components/PresenceBar.tsx"],"names":[],"mappings":"AAEA,OAAO,EACL,KAAK,UAAU,EAIhB,MAAM,wBAAwB,CAAC;AAQhC,MAAM,WAAW,gBAAgB;IAC/B,6CAA6C;IAC7C,WAAW,EAAE,UAAU,EAAE,CAAC;IAC1B,sDAAsD;IACtD,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,4DAA4D;IAC5D,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,uDAAuD;IACvD,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,2DAA2D;IAC3D,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,8BAA8B;IAC9B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB;;;OAGG;IACH,aAAa,CAAC,EAAE,CAAC,IAAI,EAAE,UAAU,GAAG,IAAI,KAAK,IAAI,CAAC;IAClD;;;OAGG;IACH,cAAc,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CAChC;AA2OD,wBAAgB,WAAW,CAAC,EAC1B,WAAW,EACX,YAAY,EACZ,WAAW,EACX,gBAAgB,EAChB,UAAc,EACd,SAAS,EACT,aAAa,EACb,cAAc,GACf,EAAE,gBAAgB,sCA+DlB"}
@@ -58,7 +58,12 @@ function UserAvatar({ user, isFirst, onClick, isFollowing, }) {
58
58
  }, "aria-label": `${name} (${user.email})${isFollowing ? " — following" : ""}`, tabIndex: onClick ? 0 : undefined, role: onClick ? "button" : undefined, onClick: onClick, onKeyDown: (e) => {
59
59
  if (e.key === "Enter" || e.key === " ")
60
60
  onClick?.();
61
- }, children: initial }) }), _jsx(TooltipContent, { side: "bottom", children: isFollowing
61
+ }, children: user.avatarUrl ? (_jsx("img", { src: user.avatarUrl, alt: "", style: {
62
+ width: "100%",
63
+ height: "100%",
64
+ borderRadius: "50%",
65
+ objectFit: "cover",
66
+ } })) : (initial) }) }), _jsx(TooltipContent, { side: "bottom", children: isFollowing
62
67
  ? `Following ${name} — click to stop`
63
68
  : onClick
64
69
  ? `${name} — click to follow`
@@ -1 +1 @@
1
- {"version":3,"file":"PresenceBar.js","sourceRoot":"","sources":["../../../src/client/components/PresenceBar.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,OAAO,CAAC;AAEhC,OAAO,EAEL,wBAAwB,EACxB,YAAY,EACZ,WAAW,GACZ,MAAM,wBAAwB,CAAC;AAChC,OAAO,EACL,OAAO,EACP,cAAc,EACd,eAAe,EACf,cAAc,GACf,MAAM,iBAAiB,CAAC;AA2BzB,MAAM,WAAW,GAAG,EAAE,CAAC;AACvB,MAAM,OAAO,GAAG,CAAC,CAAC,CAAC;AACnB,MAAM,YAAY,GAAG,CAAC,CAAC;AACvB,MAAM,SAAS,GAAG,EAAE,CAAC;AACrB,MAAM,WAAW,GAAG,SAAS,CAAC;AAE9B,MAAM,eAAe,GAAwB;IAC3C,KAAK,EAAE,WAAW;IAClB,MAAM,EAAE,WAAW;IACnB,YAAY,EAAE,KAAK;IACnB,OAAO,EAAE,MAAM;IACf,UAAU,EAAE,QAAQ;IACpB,cAAc,EAAE,QAAQ;IACxB,QAAQ,EAAE,SAAS;IACnB,UAAU,EAAE,GAAG;IACf,KAAK,EAAE,MAAM;IACb,MAAM,EAAE,GAAG,YAAY,eAAe;IACtC,UAAU,EAAE,CAAC;IACb,QAAQ,EAAE,UAAU;IACpB,MAAM,EAAE,SAAS;IACjB,SAAS,EAAE,YAAY;CACxB,CAAC;AAEF,MAAM,cAAc,GAAwB;IAC1C,OAAO,EAAE,MAAM;IACf,UAAU,EAAE,QAAQ;IACpB,aAAa,EAAE,KAAK;CACrB,CAAC;AAEF,MAAM,cAAc,GAAG;;;;;CAKtB,CAAC;AAEF,IAAI,aAAa,GAAG,KAAK,CAAC;AAE1B,SAAS,YAAY;IACnB,IAAI,aAAa,IAAI,OAAO,QAAQ,KAAK,WAAW;QAAE,OAAO;IAC7D,MAAM,KAAK,GAAG,QAAQ,CAAC,aAAa,CAAC,OAAO,CAAC,CAAC;IAC9C,KAAK,CAAC,WAAW,GAAG,cAAc,CAAC;IACnC,QAAQ,CAAC,IAAI,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC;IACjC,aAAa,GAAG,IAAI,CAAC;AACvB,CAAC;AAED,SAAS,UAAU,CAAC,EAClB,IAAI,EACJ,OAAO,EACP,OAAO,EACP,WAAW,GAMZ;IACC,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,IAAI,YAAY,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IACrD,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,IAAI,WAAW,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAClD,MAAM,OAAO,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC;IAE7C,OAAO,CACL,MAAC,OAAO,eACN,KAAC,cAAc,IAAC,OAAO,kBACrB,cACE,KAAK,EAAE;wBACL,GAAG,eAAe;wBAClB,eAAe,EAAE,KAAK;wBACtB,UAAU,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO;wBACjC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,SAAS;wBACvC,SAAS,EAAE,WAAW;4BACpB,CAAC,CAAC,mCAAmC;4BACrC,CAAC,CAAC,gBAAgB;qBACrB,gBACW,GAAG,IAAI,KAAK,IAAI,CAAC,KAAK,IAAI,WAAW,CAAC,CAAC,CAAC,cAAc,CAAC,CAAC,CAAC,EAAE,EAAE,EACzE,QAAQ,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,SAAS,EACjC,IAAI,EAAE,OAAO,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,EACpC,OAAO,EAAE,OAAO,EAChB,SAAS,EAAE,CAAC,CAAC,EAAE,EAAE;wBACf,IAAI,CAAC,CAAC,GAAG,KAAK,OAAO,IAAI,CAAC,CAAC,GAAG,KAAK,GAAG;4BAAE,OAAO,EAAE,EAAE,CAAC;oBACtD,CAAC,YAEA,OAAO,GACJ,GACS,EACjB,KAAC,cAAc,IAAC,IAAI,EAAC,QAAQ,YAC1B,WAAW;oBACV,CAAC,CAAC,aAAa,IAAI,kBAAkB;oBACrC,CAAC,CAAC,OAAO;wBACP,CAAC,CAAC,GAAG,IAAI,oBAAoB;wBAC7B,CAAC,CAAC,IAAI,CAAC,KAAK,GACD,IACT,CACX,CAAC;AACJ,CAAC;AAED,SAAS,WAAW,CAAC,EACnB,MAAM,EACN,OAAO,EACP,WAAW,GAKZ;IACC,YAAY,EAAE,CAAC;IAEf,OAAO,CACL,eACE,KAAK,EAAE;YACL,OAAO,EAAE,MAAM;YACf,UAAU,EAAE,QAAQ;YACpB,GAAG,EAAE,CAAC;SACP,aAED,cACE,KAAK,EAAE;oBACL,GAAG,eAAe;oBAClB,eAAe,EAAE,WAAW;oBAC5B,UAAU,EAAE,CAAC;oBACb,SAAS,EAAE,MAAM,CAAC,CAAC,CAAC,8BAA8B,CAAC,CAAC,CAAC,SAAS;oBAC9D,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,SAAS;oBACvC,SAAS,EAAE,WAAW;wBACpB,CAAC,CAAC,mCAAmC;wBACrC,CAAC,CAAC,SAAS;iBACd,EACD,KAAK,EACH,WAAW;oBACT,CAAC,CAAC,8BAA8B;oBAChC,CAAC,CAAC,MAAM;wBACN,CAAC,CAAC,eAAe;wBACjB,CAAC,CAAC,UAAU,EAElB,OAAO,EAAE,OAAO,EAChB,QAAQ,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,SAAS,EACjC,SAAS,EAAE,CAAC,CAAC,EAAE,EAAE;oBACf,IAAI,CAAC,CAAC,GAAG,KAAK,OAAO,IAAI,CAAC,CAAC,GAAG,KAAK,GAAG;wBAAE,OAAO,EAAE,EAAE,CAAC;gBACtD,CAAC,EACD,IAAI,EAAE,OAAO,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,kBAGhC,EACL,MAAM,IAAI,CAAC,WAAW,IAAI,KAAC,gBAAgB,KAAG,EAC9C,WAAW,IAAI,CACd,eACE,KAAK,EAAE;oBACL,OAAO,EAAE,aAAa;oBACtB,UAAU,EAAE,QAAQ;oBACpB,MAAM,EAAE,EAAE;oBACV,OAAO,EAAE,OAAO;oBAChB,YAAY,EAAE,IAAI;oBAClB,eAAe,EAAE,WAAW;oBAC5B,KAAK,EAAE,SAAS;oBAChB,QAAQ,EAAE,EAAE;oBACZ,UAAU,EAAE,GAAG;oBACf,UAAU,EAAE,QAAQ;iBACrB,6BAGI,CACR,IACG,CACP,CAAC;AACJ,CAAC;AAED,SAAS,gBAAgB;IACvB,OAAO,CACL,gBACE,KAAK,EAAE;YACL,OAAO,EAAE,aAAa;YACtB,UAAU,EAAE,QAAQ;YACpB,GAAG,EAAE,CAAC;YACN,MAAM,EAAE,EAAE;YACV,OAAO,EAAE,OAAO;YAChB,YAAY,EAAE,IAAI;YAClB,eAAe,EAAE,GAAG,WAAW,IAAI;YACnC,KAAK,EAAE,WAAW;YAClB,QAAQ,EAAE,EAAE;YACZ,UAAU,EAAE,GAAG;YACf,UAAU,EAAE,QAAQ;SACrB,aAED,eACE,KAAK,EAAE;oBACL,KAAK,EAAE,CAAC;oBACR,MAAM,EAAE,CAAC;oBACT,YAAY,EAAE,KAAK;oBACnB,eAAe,EAAE,WAAW;oBAC5B,SAAS,EAAE,8BAA8B;oBACzC,UAAU,EAAE,CAAC;iBACd,GACD,kBAEG,CACR,CAAC;AACJ,CAAC;AAED,SAAS,aAAa,CAAC,EACrB,KAAK,EACL,OAAO,GAIR;IACC,OAAO,CACL,eACE,KAAK,EAAE;YACL,GAAG,eAAe;YAClB,eAAe,EAAE,uBAAuB;YACxC,KAAK,EAAE,uBAAuB;YAC9B,UAAU,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO;YACjC,QAAQ,EAAE,EAAE;SACb,EACD,KAAK,EAAE,GAAG,KAAK,qBAAqB,KAAK,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,GAAG,EAAE,kBAE1D,KAAK,IACH,CACP,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,EAC1B,WAAW,EACX,YAAY,EACZ,WAAW,EACX,gBAAgB,EAChB,UAAU,GAAG,CAAC,EACd,SAAS,EACT,aAAa,EACb,cAAc,GACG;IACjB,MAAM,EAAE,UAAU,EAAE,SAAS,EAAE,GAAG,OAAO,CAAC,GAAG,EAAE;QAC7C,MAAM,YAAY,GAAG,gBAAgB,EAAE,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC;QAC5D,MAAM,WAAW,GAAG,wBAAwB,CAAC,WAAW,CAAC,CAAC;QAC1D,MAAM,MAAM,GAAG,WAAW,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE;YACtC,MAAM,KAAK,GAAG,CAAC,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC;YAC3C,OAAO,KAAK,KAAK,YAAY,IAAI,KAAK,KAAK,cAAc,CAAC;QAC5D,CAAC,CAAC,CAAC;QACH,MAAM,YAAY,GAAG,WAAW,CAAC,IAAI,CACnC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC,WAAW,EAAE,KAAK,cAAc,CACvD,CAAC;QACF,OAAO;YACL,UAAU,EAAE,MAAM;YAClB,SAAS,EAAE,YAAY,IAAI,WAAW,IAAI,YAAY;SACvD,CAAC;IACJ,CAAC,EAAE,CAAC,WAAW,EAAE,gBAAgB,EAAE,YAAY,EAAE,WAAW,CAAC,CAAC,CAAC;IAE/D,MAAM,YAAY,GAAG,UAAU,CAAC,KAAK,CAAC,CAAC,EAAE,UAAU,CAAC,CAAC;IACrD,MAAM,aAAa,GAAG,UAAU,CAAC,MAAM,GAAG,YAAY,CAAC,MAAM,CAAC;IAE9D,IAAI,CAAC,SAAS,IAAI,UAAU,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IAEvD,MAAM,cAAc,GAAG,cAAc,EAAE,IAAI,EAAE,CAAC,WAAW,EAAE,IAAI,IAAI,CAAC;IACpE,MAAM,gBAAgB,GAAG,cAAc,KAAK,cAAc,CAAC;IAE3D,OAAO,CACL,KAAC,eAAe,IAAC,aAAa,EAAE,GAAG,YACjC,eAAK,KAAK,EAAE,cAAc,EAAE,SAAS,EAAE,SAAS,aAC7C,SAAS,IAAI,CACZ,KAAC,WAAW,IACV,MAAM,EAAE,CAAC,CAAC,WAAW,EACrB,OAAO,EAAE,aAAa,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,SAAS,EAC9D,WAAW,EAAE,gBAAgB,GAC7B,CACH,EACA,YAAY,CAAC,MAAM,GAAG,CAAC,IAAI,CAC1B,eACE,KAAK,EAAE;wBACL,OAAO,EAAE,MAAM;wBACf,UAAU,EAAE,QAAQ;wBACpB,UAAU,EAAE,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;qBAC9B,aAEA,YAAY,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAC1B,KAAC,UAAU,IAET,IAAI,EAAE,CAAC,EACP,OAAO,EAAE,CAAC,KAAK,CAAC,EAChB,OAAO,EAAE,aAAa,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,aAAa,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,SAAS,EAC3D,WAAW,EACT,cAAc,IAAI,IAAI;gCACtB,CAAC,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC,WAAW,EAAE,KAAK,cAAc,IAN5C,CAAC,CAAC,KAAK,CAQZ,CACH,CAAC,EACD,aAAa,GAAG,CAAC,IAAI,CACpB,KAAC,aAAa,IAAC,KAAK,EAAE,aAAa,EAAE,OAAO,EAAE,KAAK,GAAI,CACxD,IACG,CACP,IACG,GACU,CACnB,CAAC;AACJ,CAAC","sourcesContent":["import { useMemo } from \"react\";\n\nimport {\n type CollabUser,\n dedupeCollabUsersByEmail,\n emailToColor,\n emailToName,\n} from \"../../collab/client.js\";\nimport {\n Tooltip,\n TooltipContent,\n TooltipProvider,\n TooltipTrigger,\n} from \"./ui/tooltip.js\";\n\nexport interface PresenceBarProps {\n /** Active collaborators on this document. */\n activeUsers: CollabUser[];\n /** Whether the agent has a durable presence entry. */\n agentPresent?: boolean;\n /** Whether the agent is actively making edits right now. */\n agentActive?: boolean;\n /** Current user's email (to exclude from the list). */\n currentUserEmail?: string;\n /** Max visible avatars before \"+N\" overflow. Default: 5 */\n maxVisible?: number;\n /** Additional CSS classes. */\n className?: string;\n /**\n * Called when an avatar is clicked. Receives the user being clicked\n * (or null for the agent avatar). Use this to start/stop follow mode.\n */\n onAvatarClick?: (user: CollabUser | null) => void;\n /**\n * The email of the user currently being followed. Highlighted with a\n * blue ring to indicate active follow mode.\n */\n followingEmail?: string | null;\n}\n\nconst AVATAR_SIZE = 28;\nconst OVERLAP = -8;\nconst BORDER_WIDTH = 2;\nconst FONT_SIZE = 12;\nconst AGENT_COLOR = \"#00B5FF\";\n\nconst baseAvatarStyle: React.CSSProperties = {\n width: AVATAR_SIZE,\n height: AVATAR_SIZE,\n borderRadius: \"50%\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: FONT_SIZE,\n fontWeight: 700,\n color: \"#fff\",\n border: `${BORDER_WIDTH}px solid #fff`,\n flexShrink: 0,\n position: \"relative\",\n cursor: \"default\",\n boxSizing: \"border-box\",\n};\n\nconst containerStyle: React.CSSProperties = {\n display: \"flex\",\n alignItems: \"center\",\n flexDirection: \"row\",\n};\n\nconst pulseKeyframes = `\n@keyframes _anPresencePulse {\n 0%, 100% { opacity: 1; }\n 50% { opacity: 0.6; }\n}\n`;\n\nlet styleInjected = false;\n\nfunction injectStyles() {\n if (styleInjected || typeof document === \"undefined\") return;\n const style = document.createElement(\"style\");\n style.textContent = pulseKeyframes;\n document.head.appendChild(style);\n styleInjected = true;\n}\n\nfunction UserAvatar({\n user,\n isFirst,\n onClick,\n isFollowing,\n}: {\n user: CollabUser;\n isFirst: boolean;\n onClick?: () => void;\n isFollowing?: boolean;\n}) {\n const color = user.color || emailToColor(user.email);\n const name = user.name || emailToName(user.email);\n const initial = name.charAt(0).toUpperCase();\n\n return (\n <Tooltip>\n <TooltipTrigger asChild>\n <div\n style={{\n ...baseAvatarStyle,\n backgroundColor: color,\n marginLeft: isFirst ? 0 : OVERLAP,\n cursor: onClick ? \"pointer\" : \"default\",\n boxShadow: isFollowing\n ? `0 0 0 2px #3b82f6, 0 0 0 4px #fff`\n : `0 0 0 2px #fff`,\n }}\n aria-label={`${name} (${user.email})${isFollowing ? \" — following\" : \"\"}`}\n tabIndex={onClick ? 0 : undefined}\n role={onClick ? \"button\" : undefined}\n onClick={onClick}\n onKeyDown={(e) => {\n if (e.key === \"Enter\" || e.key === \" \") onClick?.();\n }}\n >\n {initial}\n </div>\n </TooltipTrigger>\n <TooltipContent side=\"bottom\">\n {isFollowing\n ? `Following ${name} — click to stop`\n : onClick\n ? `${name} — click to follow`\n : user.email}\n </TooltipContent>\n </Tooltip>\n );\n}\n\nfunction AgentAvatar({\n active,\n onClick,\n isFollowing,\n}: {\n active: boolean;\n onClick?: () => void;\n isFollowing?: boolean;\n}) {\n injectStyles();\n\n return (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n gap: 4,\n }}\n >\n <div\n style={{\n ...baseAvatarStyle,\n backgroundColor: AGENT_COLOR,\n marginLeft: 0,\n animation: active ? \"_anPresencePulse 2s infinite\" : undefined,\n cursor: onClick ? \"pointer\" : \"default\",\n boxShadow: isFollowing\n ? `0 0 0 2px #3b82f6, 0 0 0 4px #fff`\n : undefined,\n }}\n title={\n isFollowing\n ? \"Following AI — click to stop\"\n : active\n ? \"AI is editing\"\n : \"AI agent\"\n }\n onClick={onClick}\n tabIndex={onClick ? 0 : undefined}\n onKeyDown={(e) => {\n if (e.key === \"Enter\" || e.key === \" \") onClick?.();\n }}\n role={onClick ? \"button\" : undefined}\n >\n A\n </div>\n {active && !isFollowing && <AgentEditingChip />}\n {isFollowing && (\n <span\n style={{\n display: \"inline-flex\",\n alignItems: \"center\",\n height: 20,\n padding: \"0 8px\",\n borderRadius: 9999,\n backgroundColor: `#3b82f620`,\n color: \"#3b82f6\",\n fontSize: 11,\n fontWeight: 600,\n whiteSpace: \"nowrap\",\n }}\n >\n Following AI\n </span>\n )}\n </div>\n );\n}\n\nfunction AgentEditingChip() {\n return (\n <span\n style={{\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: 4,\n height: 20,\n padding: \"0 8px\",\n borderRadius: 9999,\n backgroundColor: `${AGENT_COLOR}20`,\n color: AGENT_COLOR,\n fontSize: 11,\n fontWeight: 600,\n whiteSpace: \"nowrap\",\n }}\n >\n <span\n style={{\n width: 6,\n height: 6,\n borderRadius: \"50%\",\n backgroundColor: AGENT_COLOR,\n animation: \"_anPresencePulse 2s infinite\",\n flexShrink: 0,\n }}\n />\n AI editing\n </span>\n );\n}\n\nfunction OverflowBadge({\n count,\n isFirst,\n}: {\n count: number;\n isFirst: boolean;\n}) {\n return (\n <div\n style={{\n ...baseAvatarStyle,\n backgroundColor: \"rgba(255,255,255,0.1)\",\n color: \"rgba(255,255,255,0.5)\",\n marginLeft: isFirst ? 0 : OVERLAP,\n fontSize: 10,\n }}\n title={`${count} more collaborator${count === 1 ? \"\" : \"s\"}`}\n >\n +{count}\n </div>\n );\n}\n\nexport function PresenceBar({\n activeUsers,\n agentPresent,\n agentActive,\n currentUserEmail,\n maxVisible = 5,\n className,\n onAvatarClick,\n followingEmail,\n}: PresenceBarProps) {\n const { humanUsers, showAgent } = useMemo(() => {\n const currentEmail = currentUserEmail?.trim().toLowerCase();\n const uniqueUsers = dedupeCollabUsersByEmail(activeUsers);\n const humans = uniqueUsers.filter((u) => {\n const email = u.email.trim().toLowerCase();\n return email !== currentEmail && email !== \"agent@system\";\n });\n const hasAgentUser = uniqueUsers.some(\n (u) => u.email.trim().toLowerCase() === \"agent@system\",\n );\n return {\n humanUsers: humans,\n showAgent: agentPresent || agentActive || hasAgentUser,\n };\n }, [activeUsers, currentUserEmail, agentPresent, agentActive]);\n\n const visibleUsers = humanUsers.slice(0, maxVisible);\n const overflowCount = humanUsers.length - visibleUsers.length;\n\n if (!showAgent && humanUsers.length === 0) return null;\n\n const followingLower = followingEmail?.trim().toLowerCase() ?? null;\n const isFollowingAgent = followingLower === \"agent@system\";\n\n return (\n <TooltipProvider delayDuration={150}>\n <div style={containerStyle} className={className}>\n {showAgent && (\n <AgentAvatar\n active={!!agentActive}\n onClick={onAvatarClick ? () => onAvatarClick(null) : undefined}\n isFollowing={isFollowingAgent}\n />\n )}\n {visibleUsers.length > 0 && (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n marginLeft: showAgent ? 6 : 0,\n }}\n >\n {visibleUsers.map((u, i) => (\n <UserAvatar\n key={u.email}\n user={u}\n isFirst={i === 0}\n onClick={onAvatarClick ? () => onAvatarClick(u) : undefined}\n isFollowing={\n followingLower != null &&\n u.email.trim().toLowerCase() === followingLower\n }\n />\n ))}\n {overflowCount > 0 && (\n <OverflowBadge count={overflowCount} isFirst={false} />\n )}\n </div>\n )}\n </div>\n </TooltipProvider>\n );\n}\n"]}
1
+ {"version":3,"file":"PresenceBar.js","sourceRoot":"","sources":["../../../src/client/components/PresenceBar.tsx"],"names":[],"mappings":"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","sourcesContent":["import { useMemo } from \"react\";\n\nimport {\n type CollabUser,\n dedupeCollabUsersByEmail,\n emailToColor,\n emailToName,\n} from \"../../collab/client.js\";\nimport {\n Tooltip,\n TooltipContent,\n TooltipProvider,\n TooltipTrigger,\n} from \"./ui/tooltip.js\";\n\nexport interface PresenceBarProps {\n /** Active collaborators on this document. */\n activeUsers: CollabUser[];\n /** Whether the agent has a durable presence entry. */\n agentPresent?: boolean;\n /** Whether the agent is actively making edits right now. */\n agentActive?: boolean;\n /** Current user's email (to exclude from the list). */\n currentUserEmail?: string;\n /** Max visible avatars before \"+N\" overflow. Default: 5 */\n maxVisible?: number;\n /** Additional CSS classes. */\n className?: string;\n /**\n * Called when an avatar is clicked. Receives the user being clicked\n * (or null for the agent avatar). Use this to start/stop follow mode.\n */\n onAvatarClick?: (user: CollabUser | null) => void;\n /**\n * The email of the user currently being followed. Highlighted with a\n * blue ring to indicate active follow mode.\n */\n followingEmail?: string | null;\n}\n\nconst AVATAR_SIZE = 28;\nconst OVERLAP = -8;\nconst BORDER_WIDTH = 2;\nconst FONT_SIZE = 12;\nconst AGENT_COLOR = \"#00B5FF\";\n\nconst baseAvatarStyle: React.CSSProperties = {\n width: AVATAR_SIZE,\n height: AVATAR_SIZE,\n borderRadius: \"50%\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: FONT_SIZE,\n fontWeight: 700,\n color: \"#fff\",\n border: `${BORDER_WIDTH}px solid #fff`,\n flexShrink: 0,\n position: \"relative\",\n cursor: \"default\",\n boxSizing: \"border-box\",\n};\n\nconst containerStyle: React.CSSProperties = {\n display: \"flex\",\n alignItems: \"center\",\n flexDirection: \"row\",\n};\n\nconst pulseKeyframes = `\n@keyframes _anPresencePulse {\n 0%, 100% { opacity: 1; }\n 50% { opacity: 0.6; }\n}\n`;\n\nlet styleInjected = false;\n\nfunction injectStyles() {\n if (styleInjected || typeof document === \"undefined\") return;\n const style = document.createElement(\"style\");\n style.textContent = pulseKeyframes;\n document.head.appendChild(style);\n styleInjected = true;\n}\n\nfunction UserAvatar({\n user,\n isFirst,\n onClick,\n isFollowing,\n}: {\n user: CollabUser;\n isFirst: boolean;\n onClick?: () => void;\n isFollowing?: boolean;\n}) {\n const color = user.color || emailToColor(user.email);\n const name = user.name || emailToName(user.email);\n const initial = name.charAt(0).toUpperCase();\n\n return (\n <Tooltip>\n <TooltipTrigger asChild>\n <div\n style={{\n ...baseAvatarStyle,\n backgroundColor: color,\n marginLeft: isFirst ? 0 : OVERLAP,\n cursor: onClick ? \"pointer\" : \"default\",\n boxShadow: isFollowing\n ? `0 0 0 2px #3b82f6, 0 0 0 4px #fff`\n : `0 0 0 2px #fff`,\n }}\n aria-label={`${name} (${user.email})${isFollowing ? \" — following\" : \"\"}`}\n tabIndex={onClick ? 0 : undefined}\n role={onClick ? \"button\" : undefined}\n onClick={onClick}\n onKeyDown={(e) => {\n if (e.key === \"Enter\" || e.key === \" \") onClick?.();\n }}\n >\n {user.avatarUrl ? (\n <img\n src={user.avatarUrl}\n alt=\"\"\n style={{\n width: \"100%\",\n height: \"100%\",\n borderRadius: \"50%\",\n objectFit: \"cover\",\n }}\n />\n ) : (\n initial\n )}\n </div>\n </TooltipTrigger>\n <TooltipContent side=\"bottom\">\n {isFollowing\n ? `Following ${name} — click to stop`\n : onClick\n ? `${name} — click to follow`\n : user.email}\n </TooltipContent>\n </Tooltip>\n );\n}\n\nfunction AgentAvatar({\n active,\n onClick,\n isFollowing,\n}: {\n active: boolean;\n onClick?: () => void;\n isFollowing?: boolean;\n}) {\n injectStyles();\n\n return (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n gap: 4,\n }}\n >\n <div\n style={{\n ...baseAvatarStyle,\n backgroundColor: AGENT_COLOR,\n marginLeft: 0,\n animation: active ? \"_anPresencePulse 2s infinite\" : undefined,\n cursor: onClick ? \"pointer\" : \"default\",\n boxShadow: isFollowing\n ? `0 0 0 2px #3b82f6, 0 0 0 4px #fff`\n : undefined,\n }}\n title={\n isFollowing\n ? \"Following AI — click to stop\"\n : active\n ? \"AI is editing\"\n : \"AI agent\"\n }\n onClick={onClick}\n tabIndex={onClick ? 0 : undefined}\n onKeyDown={(e) => {\n if (e.key === \"Enter\" || e.key === \" \") onClick?.();\n }}\n role={onClick ? \"button\" : undefined}\n >\n A\n </div>\n {active && !isFollowing && <AgentEditingChip />}\n {isFollowing && (\n <span\n style={{\n display: \"inline-flex\",\n alignItems: \"center\",\n height: 20,\n padding: \"0 8px\",\n borderRadius: 9999,\n backgroundColor: `#3b82f620`,\n color: \"#3b82f6\",\n fontSize: 11,\n fontWeight: 600,\n whiteSpace: \"nowrap\",\n }}\n >\n Following AI\n </span>\n )}\n </div>\n );\n}\n\nfunction AgentEditingChip() {\n return (\n <span\n style={{\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: 4,\n height: 20,\n padding: \"0 8px\",\n borderRadius: 9999,\n backgroundColor: `${AGENT_COLOR}20`,\n color: AGENT_COLOR,\n fontSize: 11,\n fontWeight: 600,\n whiteSpace: \"nowrap\",\n }}\n >\n <span\n style={{\n width: 6,\n height: 6,\n borderRadius: \"50%\",\n backgroundColor: AGENT_COLOR,\n animation: \"_anPresencePulse 2s infinite\",\n flexShrink: 0,\n }}\n />\n AI editing\n </span>\n );\n}\n\nfunction OverflowBadge({\n count,\n isFirst,\n}: {\n count: number;\n isFirst: boolean;\n}) {\n return (\n <div\n style={{\n ...baseAvatarStyle,\n backgroundColor: \"rgba(255,255,255,0.1)\",\n color: \"rgba(255,255,255,0.5)\",\n marginLeft: isFirst ? 0 : OVERLAP,\n fontSize: 10,\n }}\n title={`${count} more collaborator${count === 1 ? \"\" : \"s\"}`}\n >\n +{count}\n </div>\n );\n}\n\nexport function PresenceBar({\n activeUsers,\n agentPresent,\n agentActive,\n currentUserEmail,\n maxVisible = 5,\n className,\n onAvatarClick,\n followingEmail,\n}: PresenceBarProps) {\n const { humanUsers, showAgent } = useMemo(() => {\n const currentEmail = currentUserEmail?.trim().toLowerCase();\n const uniqueUsers = dedupeCollabUsersByEmail(activeUsers);\n const humans = uniqueUsers.filter((u) => {\n const email = u.email.trim().toLowerCase();\n return email !== currentEmail && email !== \"agent@system\";\n });\n const hasAgentUser = uniqueUsers.some(\n (u) => u.email.trim().toLowerCase() === \"agent@system\",\n );\n return {\n humanUsers: humans,\n showAgent: agentPresent || agentActive || hasAgentUser,\n };\n }, [activeUsers, currentUserEmail, agentPresent, agentActive]);\n\n const visibleUsers = humanUsers.slice(0, maxVisible);\n const overflowCount = humanUsers.length - visibleUsers.length;\n\n if (!showAgent && humanUsers.length === 0) return null;\n\n const followingLower = followingEmail?.trim().toLowerCase() ?? null;\n const isFollowingAgent = followingLower === \"agent@system\";\n\n return (\n <TooltipProvider delayDuration={150}>\n <div style={containerStyle} className={className}>\n {showAgent && (\n <AgentAvatar\n active={!!agentActive}\n onClick={onAvatarClick ? () => onAvatarClick(null) : undefined}\n isFollowing={isFollowingAgent}\n />\n )}\n {visibleUsers.length > 0 && (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n marginLeft: showAgent ? 6 : 0,\n }}\n >\n {visibleUsers.map((u, i) => (\n <UserAvatar\n key={u.email}\n user={u}\n isFirst={i === 0}\n onClick={onAvatarClick ? () => onAvatarClick(u) : undefined}\n isFollowing={\n followingLower != null &&\n u.email.trim().toLowerCase() === followingLower\n }\n />\n ))}\n {overflowCount > 0 && (\n <OverflowBadge count={overflowCount} isFirst={false} />\n )}\n </div>\n )}\n </div>\n </TooltipProvider>\n );\n}\n"]}
@@ -0,0 +1,43 @@
1
+ /**
2
+ * RecentEditHighlights — lingering, fading highlights over regions another
3
+ * participant (human or agent) just edited, with their name/avatar flag.
4
+ *
5
+ * The Google-Docs/Figma feel: when a collaborator or the AI edits something,
6
+ * the changed region glows in their color and the flag identifies them; the
7
+ * highlight fades out over the last portion of its lifetime instead of
8
+ * vanishing.
9
+ *
10
+ * Feed it `useRecentEdits(others)` (which reads participants' `recentEdits`
11
+ * awareness rings) and a `resolveRect` that maps an edit descriptor to a
12
+ * viewport DOMRect for your surface:
13
+ *
14
+ * const others = usePresence(awareness, ydoc?.clientID).others;
15
+ * const edits = useRecentEdits(others);
16
+ * <RecentEditHighlights
17
+ * edits={edits}
18
+ * resolveRect={(edit) =>
19
+ * edit.descriptor.kind === "selector"
20
+ * ? container.querySelector(edit.descriptor.selector)?.getBoundingClientRect() ?? null
21
+ * : null
22
+ * }
23
+ * containerRef={containerRef}
24
+ * />
25
+ */
26
+ import type { AttributedRecentEdit } from "../../collab/recent-edits.js";
27
+ export interface RecentEditHighlightsProps {
28
+ /** Attributed recent edits (from `useRecentEdits`). */
29
+ edits: AttributedRecentEdit[];
30
+ /**
31
+ * Resolver: maps an edit to a viewport-relative DOMRect, or null when the
32
+ * region can't be located (the edit is skipped).
33
+ */
34
+ resolveRect: (edit: AttributedRecentEdit) => DOMRect | null;
35
+ /** Container the highlights are positioned within (position: relative). */
36
+ containerRef: React.RefObject<HTMLElement | null>;
37
+ /** Highlight lifetime; should match useRecentEdits ttlMs. Default 6000. */
38
+ ttlMs?: number;
39
+ /** Additional CSS class for the overlay div. */
40
+ className?: string;
41
+ }
42
+ export declare function RecentEditHighlights({ edits, resolveRect, containerRef, ttlMs, className, }: RecentEditHighlightsProps): import("react").JSX.Element;
43
+ //# sourceMappingURL=RecentEditHighlights.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"RecentEditHighlights.d.ts","sourceRoot":"","sources":["../../../src/client/components/RecentEditHighlights.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AAIH,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,8BAA8B,CAAC;AAGzE,MAAM,WAAW,yBAAyB;IACxC,uDAAuD;IACvD,KAAK,EAAE,oBAAoB,EAAE,CAAC;IAC9B;;;OAGG;IACH,WAAW,EAAE,CAAC,IAAI,EAAE,oBAAoB,KAAK,OAAO,GAAG,IAAI,CAAC;IAC5D,2EAA2E;IAC3E,YAAY,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IAClD,2EAA2E;IAC3E,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,gDAAgD;IAChD,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAuED,wBAAgB,oBAAoB,CAAC,EACnC,KAAK,EACL,WAAW,EACX,YAAY,EACZ,KAA0B,EAC1B,SAAS,GACV,EAAE,yBAAyB,+BAgG3B"}
@@ -0,0 +1,146 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ /**
3
+ * RecentEditHighlights — lingering, fading highlights over regions another
4
+ * participant (human or agent) just edited, with their name/avatar flag.
5
+ *
6
+ * The Google-Docs/Figma feel: when a collaborator or the AI edits something,
7
+ * the changed region glows in their color and the flag identifies them; the
8
+ * highlight fades out over the last portion of its lifetime instead of
9
+ * vanishing.
10
+ *
11
+ * Feed it `useRecentEdits(others)` (which reads participants' `recentEdits`
12
+ * awareness rings) and a `resolveRect` that maps an edit descriptor to a
13
+ * viewport DOMRect for your surface:
14
+ *
15
+ * const others = usePresence(awareness, ydoc?.clientID).others;
16
+ * const edits = useRecentEdits(others);
17
+ * <RecentEditHighlights
18
+ * edits={edits}
19
+ * resolveRect={(edit) =>
20
+ * edit.descriptor.kind === "selector"
21
+ * ? container.querySelector(edit.descriptor.selector)?.getBoundingClientRect() ?? null
22
+ * : null
23
+ * }
24
+ * containerRef={containerRef}
25
+ * />
26
+ */
27
+ import { memo, useEffect, useLayoutEffect, useRef, useState } from "react";
28
+ import { RECENT_EDIT_TTL_MS } from "../../collab/recent-edits.js";
29
+ const HighlightItem = memo(function HighlightItem({ h }) {
30
+ return (_jsx("div", { "aria-label": `${h.label} edited this`, style: {
31
+ position: "absolute",
32
+ top: h.rect.top,
33
+ left: h.rect.left,
34
+ width: h.rect.width,
35
+ height: h.rect.height,
36
+ borderRadius: 4,
37
+ pointerEvents: "none",
38
+ zIndex: 9997,
39
+ opacity: h.opacity,
40
+ transition: "opacity 400ms ease-out",
41
+ outline: `2px solid ${h.color}`,
42
+ outlineOffset: 2,
43
+ backgroundColor: `${h.color}1A`,
44
+ boxShadow: `0 0 0 1px ${h.color}33, 0 0 12px ${h.color}40`,
45
+ }, children: _jsxs("div", { style: {
46
+ position: "absolute",
47
+ top: -22,
48
+ left: 0,
49
+ display: "flex",
50
+ alignItems: "center",
51
+ gap: 4,
52
+ backgroundColor: h.color,
53
+ color: "#fff",
54
+ fontSize: 10,
55
+ fontWeight: 600,
56
+ padding: "2px 6px",
57
+ borderRadius: 3,
58
+ whiteSpace: "nowrap",
59
+ maxWidth: 180,
60
+ overflow: "hidden",
61
+ textOverflow: "ellipsis",
62
+ }, children: [h.avatarUrl ? (_jsx("img", { src: h.avatarUrl, alt: "", style: {
63
+ width: 12,
64
+ height: 12,
65
+ borderRadius: "50%",
66
+ flexShrink: 0,
67
+ } })) : null, h.label] }) }));
68
+ });
69
+ export function RecentEditHighlights({ edits, resolveRect, containerRef, ttlMs = RECENT_EDIT_TTL_MS, className, }) {
70
+ const [highlights, setHighlights] = useState([]);
71
+ const editsRef = useRef(edits);
72
+ editsRef.current = edits;
73
+ const resolveRef = useRef(resolveRect);
74
+ resolveRef.current = resolveRect;
75
+ const recompute = () => {
76
+ const container = containerRef.current;
77
+ if (!container) {
78
+ setHighlights([]);
79
+ return;
80
+ }
81
+ const containerRect = container.getBoundingClientRect();
82
+ const now = Date.now();
83
+ const next = [];
84
+ for (const edit of editsRef.current) {
85
+ const domRect = resolveRef.current(edit);
86
+ if (!domRect)
87
+ continue;
88
+ const top = domRect.top - containerRect.top;
89
+ const left = domRect.left - containerRect.left;
90
+ if (left + domRect.width < 0 ||
91
+ top + domRect.height < 0 ||
92
+ left > containerRect.width ||
93
+ top > containerRect.height) {
94
+ continue;
95
+ }
96
+ // Fade over the final 40% of the lifetime.
97
+ const age = now - edit.at;
98
+ const fadeStart = ttlMs * 0.6;
99
+ const opacity = age <= fadeStart
100
+ ? 1
101
+ : Math.max(0, 1 - (age - fadeStart) / (ttlMs - fadeStart));
102
+ next.push({
103
+ key: `${edit.clientId}:${edit.at}`,
104
+ color: edit.user.color || "#94a3b8",
105
+ label: edit.isAgent
106
+ ? edit.label
107
+ ? `AI — ${edit.label}`
108
+ : "AI edited"
109
+ : edit.label
110
+ ? `${edit.user.name} — ${edit.label}`
111
+ : edit.user.name,
112
+ avatarUrl: edit.user.avatarUrl,
113
+ isAgent: edit.isAgent,
114
+ opacity,
115
+ rect: { top, left, width: domRect.width, height: domRect.height },
116
+ });
117
+ }
118
+ setHighlights(next);
119
+ };
120
+ useLayoutEffect(() => {
121
+ recompute();
122
+ // eslint-disable-next-line react-hooks/exhaustive-deps
123
+ }, [edits, ttlMs]);
124
+ useEffect(() => {
125
+ const container = containerRef.current;
126
+ if (!container)
127
+ return;
128
+ const observer = new ResizeObserver(() => recompute());
129
+ observer.observe(container);
130
+ container.addEventListener("scroll", recompute, { passive: true });
131
+ window.addEventListener("scroll", recompute, { passive: true });
132
+ return () => {
133
+ observer.disconnect();
134
+ container.removeEventListener("scroll", recompute);
135
+ window.removeEventListener("scroll", recompute);
136
+ };
137
+ // eslint-disable-next-line react-hooks/exhaustive-deps
138
+ }, [containerRef]);
139
+ return (_jsx("div", { "aria-hidden": true, style: {
140
+ position: "absolute",
141
+ inset: 0,
142
+ pointerEvents: "none",
143
+ overflow: "hidden",
144
+ }, className: className, children: highlights.map((h) => (_jsx(HighlightItem, { h: h }, h.key))) }));
145
+ }
146
+ //# sourceMappingURL=RecentEditHighlights.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"RecentEditHighlights.js","sourceRoot":"","sources":["../../../src/client/components/RecentEditHighlights.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n * RecentEditHighlights — lingering, fading highlights over regions another\n * participant (human or agent) just edited, with their name/avatar flag.\n *\n * The Google-Docs/Figma feel: when a collaborator or the AI edits something,\n * the changed region glows in their color and the flag identifies them; the\n * highlight fades out over the last portion of its lifetime instead of\n * vanishing.\n *\n * Feed it `useRecentEdits(others)` (which reads participants' `recentEdits`\n * awareness rings) and a `resolveRect` that maps an edit descriptor to a\n * viewport DOMRect for your surface:\n *\n * const others = usePresence(awareness, ydoc?.clientID).others;\n * const edits = useRecentEdits(others);\n * <RecentEditHighlights\n * edits={edits}\n * resolveRect={(edit) =>\n * edit.descriptor.kind === \"selector\"\n * ? container.querySelector(edit.descriptor.selector)?.getBoundingClientRect() ?? null\n * : null\n * }\n * containerRef={containerRef}\n * />\n */\n\nimport { memo, useEffect, useLayoutEffect, useRef, useState } from \"react\";\n\nimport type { AttributedRecentEdit } from \"../../collab/recent-edits.js\";\nimport { RECENT_EDIT_TTL_MS } from \"../../collab/recent-edits.js\";\n\nexport interface RecentEditHighlightsProps {\n /** Attributed recent edits (from `useRecentEdits`). */\n edits: AttributedRecentEdit[];\n /**\n * Resolver: maps an edit to a viewport-relative DOMRect, or null when the\n * region can't be located (the edit is skipped).\n */\n resolveRect: (edit: AttributedRecentEdit) => DOMRect | null;\n /** Container the highlights are positioned within (position: relative). */\n containerRef: React.RefObject<HTMLElement | null>;\n /** Highlight lifetime; should match useRecentEdits ttlMs. Default 6000. */\n ttlMs?: number;\n /** Additional CSS class for the overlay div. */\n className?: string;\n}\n\ninterface Highlight {\n key: string;\n color: string;\n label: string;\n avatarUrl?: string;\n isAgent: boolean;\n opacity: number;\n rect: { top: number; left: number; width: number; height: number };\n}\n\nconst HighlightItem = memo(function HighlightItem({ h }: { h: Highlight }) {\n return (\n <div\n aria-label={`${h.label} edited this`}\n style={{\n position: \"absolute\",\n top: h.rect.top,\n left: h.rect.left,\n width: h.rect.width,\n height: h.rect.height,\n borderRadius: 4,\n pointerEvents: \"none\",\n zIndex: 9997,\n opacity: h.opacity,\n transition: \"opacity 400ms ease-out\",\n outline: `2px solid ${h.color}`,\n outlineOffset: 2,\n backgroundColor: `${h.color}1A`,\n boxShadow: `0 0 0 1px ${h.color}33, 0 0 12px ${h.color}40`,\n }}\n >\n <div\n style={{\n position: \"absolute\",\n top: -22,\n left: 0,\n display: \"flex\",\n alignItems: \"center\",\n gap: 4,\n backgroundColor: h.color,\n color: \"#fff\",\n fontSize: 10,\n fontWeight: 600,\n padding: \"2px 6px\",\n borderRadius: 3,\n whiteSpace: \"nowrap\",\n maxWidth: 180,\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n }}\n >\n {h.avatarUrl ? (\n <img\n src={h.avatarUrl}\n alt=\"\"\n style={{\n width: 12,\n height: 12,\n borderRadius: \"50%\",\n flexShrink: 0,\n }}\n />\n ) : null}\n {h.label}\n </div>\n </div>\n );\n});\n\nexport function RecentEditHighlights({\n edits,\n resolveRect,\n containerRef,\n ttlMs = RECENT_EDIT_TTL_MS,\n className,\n}: RecentEditHighlightsProps) {\n const [highlights, setHighlights] = useState<Highlight[]>([]);\n const editsRef = useRef(edits);\n editsRef.current = edits;\n const resolveRef = useRef(resolveRect);\n resolveRef.current = resolveRect;\n\n const recompute = () => {\n const container = containerRef.current;\n if (!container) {\n setHighlights([]);\n return;\n }\n const containerRect = container.getBoundingClientRect();\n const now = Date.now();\n const next: Highlight[] = [];\n\n for (const edit of editsRef.current) {\n const domRect = resolveRef.current(edit);\n if (!domRect) continue;\n\n const top = domRect.top - containerRect.top;\n const left = domRect.left - containerRect.left;\n if (\n left + domRect.width < 0 ||\n top + domRect.height < 0 ||\n left > containerRect.width ||\n top > containerRect.height\n ) {\n continue;\n }\n\n // Fade over the final 40% of the lifetime.\n const age = now - edit.at;\n const fadeStart = ttlMs * 0.6;\n const opacity =\n age <= fadeStart\n ? 1\n : Math.max(0, 1 - (age - fadeStart) / (ttlMs - fadeStart));\n\n next.push({\n key: `${edit.clientId}:${edit.at}`,\n color: edit.user.color || \"#94a3b8\",\n label: edit.isAgent\n ? edit.label\n ? `AI — ${edit.label}`\n : \"AI edited\"\n : edit.label\n ? `${edit.user.name} — ${edit.label}`\n : edit.user.name,\n avatarUrl: (edit.user as { avatarUrl?: string }).avatarUrl,\n isAgent: edit.isAgent,\n opacity,\n rect: { top, left, width: domRect.width, height: domRect.height },\n });\n }\n\n setHighlights(next);\n };\n\n useLayoutEffect(() => {\n recompute();\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [edits, ttlMs]);\n\n useEffect(() => {\n const container = containerRef.current;\n if (!container) return;\n const observer = new ResizeObserver(() => recompute());\n observer.observe(container);\n container.addEventListener(\"scroll\", recompute, { passive: true });\n window.addEventListener(\"scroll\", recompute, { passive: true });\n return () => {\n observer.disconnect();\n container.removeEventListener(\"scroll\", recompute);\n window.removeEventListener(\"scroll\", recompute);\n };\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [containerRef]);\n\n return (\n <div\n aria-hidden\n style={{\n position: \"absolute\",\n inset: 0,\n pointerEvents: \"none\",\n overflow: \"hidden\",\n }}\n className={className}\n >\n {highlights.map((h) => (\n <HighlightItem key={h.key} h={h} />\n ))}\n </div>\n );\n}\n"]}
@@ -18,6 +18,15 @@
18
18
  * </div>
19
19
  */
20
20
  import type { OtherPresence } from "../../collab/presence.js";
21
+ /**
22
+ * Selection descriptors may be a plain string (treated as the resolver
23
+ * input) or an object carrying a resolver input plus a human label
24
+ * ("Editing hero section").
25
+ */
26
+ export type SelectionDescriptor = string | {
27
+ selector: string;
28
+ label?: string;
29
+ };
21
30
  export interface RemoteSelectionRingsProps {
22
31
  /** Remote participants. */
23
32
  others: OtherPresence[];
@@ -1 +1 @@
1
- {"version":3,"file":"RemoteSelectionRings.d.ts","sourceRoot":"","sources":["../../../src/client/components/RemoteSelectionRings.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;GAkBG;AAIH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAE9D,MAAM,WAAW,yBAAyB;IACxC,2BAA2B;IAC3B,MAAM,EAAE,aAAa,EAAE,CAAC;IACxB;;;OAGG;IACH,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB;;;OAGG;IACH,WAAW,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,OAAO,GAAG,IAAI,CAAC;IACpD;;;OAGG;IACH,YAAY,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IAClD,gDAAgD;IAChD,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAoDD,wBAAgB,oBAAoB,CAAC,EACnC,MAAM,EACN,YAA0B,EAC1B,WAAW,EACX,YAAY,EACZ,SAAS,GACV,EAAE,yBAAyB,+BAmF3B"}
1
+ {"version":3,"file":"RemoteSelectionRings.d.ts","sourceRoot":"","sources":["../../../src/client/components/RemoteSelectionRings.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;GAkBG;AAIH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAE9D;;;;GAIG;AACH,MAAM,MAAM,mBAAmB,GAAG,MAAM,GAAG;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC;AAEhF,MAAM,WAAW,yBAAyB;IACxC,2BAA2B;IAC3B,MAAM,EAAE,aAAa,EAAE,CAAC;IACxB;;;OAGG;IACH,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB;;;OAGG;IACH,WAAW,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,OAAO,GAAG,IAAI,CAAC;IACpD;;;OAGG;IACH,YAAY,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IAClD,gDAAgD;IAChD,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAoED,wBAAgB,oBAAoB,CAAC,EACnC,MAAM,EACN,YAA0B,EAC1B,WAAW,EACX,YAAY,EACZ,SAAS,GACV,EAAE,yBAAyB,+BA8F3B"}