@dxos/plugin-deck 0.8.4-main.3c1ae3b → 0.8.4-main.3eb6e50203

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 (277) hide show
  1. package/dist/lib/browser/app-graph-builder-X7LCO5KE.mjs +121 -0
  2. package/dist/lib/browser/app-graph-builder-X7LCO5KE.mjs.map +7 -0
  3. package/dist/lib/browser/check-app-scheme-PGISDJX7.mjs +32 -0
  4. package/dist/lib/browser/check-app-scheme-PGISDJX7.mjs.map +7 -0
  5. package/dist/lib/browser/{chunk-F3VCCHVL.mjs → chunk-DONG2FYU.mjs} +152 -19
  6. package/dist/lib/browser/chunk-DONG2FYU.mjs.map +7 -0
  7. package/dist/lib/browser/chunk-JGC4ZLG3.mjs +1469 -0
  8. package/dist/lib/browser/chunk-JGC4ZLG3.mjs.map +7 -0
  9. package/dist/lib/browser/{chunk-CNTGBCMK.mjs → chunk-NHABISX2.mjs} +40 -33
  10. package/dist/lib/browser/chunk-NHABISX2.mjs.map +7 -0
  11. package/dist/lib/browser/chunk-YT3AJVUU.mjs +161 -0
  12. package/dist/lib/browser/chunk-YT3AJVUU.mjs.map +7 -0
  13. package/dist/lib/browser/index.mjs +81 -73
  14. package/dist/lib/browser/index.mjs.map +4 -4
  15. package/dist/lib/browser/meta.json +1 -1
  16. package/dist/lib/browser/operation-resolver-XJFR3PNQ.mjs +597 -0
  17. package/dist/lib/browser/operation-resolver-XJFR3PNQ.mjs.map +7 -0
  18. package/dist/lib/browser/react-root-AJFHKHRL.mjs +47 -0
  19. package/dist/lib/browser/react-root-AJFHKHRL.mjs.map +7 -0
  20. package/dist/lib/browser/react-surface-KBRBGEXY.mjs +43 -0
  21. package/dist/lib/browser/react-surface-KBRBGEXY.mjs.map +7 -0
  22. package/dist/lib/browser/settings-ES42FGLG.mjs +38 -0
  23. package/dist/lib/browser/settings-ES42FGLG.mjs.map +7 -0
  24. package/dist/lib/browser/state-YMI6IDEL.mjs +104 -0
  25. package/dist/lib/browser/state-YMI6IDEL.mjs.map +7 -0
  26. package/dist/lib/browser/{toolkit-L5CFXJCF.mjs → toolkit-VRD54KY3.mjs} +17 -15
  27. package/dist/lib/browser/toolkit-VRD54KY3.mjs.map +7 -0
  28. package/dist/lib/browser/types/index.mjs +11 -4
  29. package/dist/lib/browser/url-handler-37UPOB3U.mjs +94 -0
  30. package/dist/lib/browser/url-handler-37UPOB3U.mjs.map +7 -0
  31. package/dist/lib/node-esm/app-graph-builder-US54I64T.mjs +122 -0
  32. package/dist/lib/node-esm/app-graph-builder-US54I64T.mjs.map +7 -0
  33. package/dist/lib/node-esm/check-app-scheme-CK6EVG5D.mjs +33 -0
  34. package/dist/lib/node-esm/check-app-scheme-CK6EVG5D.mjs.map +7 -0
  35. package/dist/lib/node-esm/chunk-7NPS347C.mjs +1470 -0
  36. package/dist/lib/node-esm/chunk-7NPS347C.mjs.map +7 -0
  37. package/dist/lib/node-esm/chunk-ADPMWKLL.mjs +154 -0
  38. package/dist/lib/node-esm/chunk-ADPMWKLL.mjs.map +7 -0
  39. package/dist/lib/node-esm/chunk-CVYHPJIN.mjs +297 -0
  40. package/dist/lib/node-esm/chunk-CVYHPJIN.mjs.map +7 -0
  41. package/dist/lib/node-esm/chunk-ZMJPCZ3V.mjs +162 -0
  42. package/dist/lib/node-esm/chunk-ZMJPCZ3V.mjs.map +7 -0
  43. package/dist/lib/node-esm/index.mjs +183 -0
  44. package/dist/lib/node-esm/index.mjs.map +7 -0
  45. package/dist/lib/node-esm/meta.json +1 -0
  46. package/dist/lib/node-esm/operation-resolver-ZQGNATPX.mjs +598 -0
  47. package/dist/lib/node-esm/operation-resolver-ZQGNATPX.mjs.map +7 -0
  48. package/dist/lib/node-esm/react-root-2S77ABBS.mjs +48 -0
  49. package/dist/lib/node-esm/react-root-2S77ABBS.mjs.map +7 -0
  50. package/dist/lib/node-esm/react-surface-FIHMAFXH.mjs +44 -0
  51. package/dist/lib/node-esm/react-surface-FIHMAFXH.mjs.map +7 -0
  52. package/dist/lib/node-esm/settings-E3TH3FAW.mjs +39 -0
  53. package/dist/lib/node-esm/settings-E3TH3FAW.mjs.map +7 -0
  54. package/dist/lib/node-esm/state-WQEFBQMD.mjs +105 -0
  55. package/dist/lib/node-esm/state-WQEFBQMD.mjs.map +7 -0
  56. package/dist/lib/node-esm/toolkit-ME546G5T.mjs +55 -0
  57. package/dist/lib/node-esm/toolkit-ME546G5T.mjs.map +7 -0
  58. package/dist/lib/node-esm/types/index.mjs +40 -0
  59. package/dist/lib/node-esm/url-handler-2KYHXINK.mjs +95 -0
  60. package/dist/lib/node-esm/url-handler-2KYHXINK.mjs.map +7 -0
  61. package/dist/types/src/DeckPlugin.d.ts +2 -1
  62. package/dist/types/src/DeckPlugin.d.ts.map +1 -1
  63. package/dist/types/src/capabilities/app-graph-builder/app-graph-builder.d.ts +6 -0
  64. package/dist/types/src/capabilities/app-graph-builder/app-graph-builder.d.ts.map +1 -0
  65. package/dist/types/src/capabilities/app-graph-builder/index.d.ts +3 -0
  66. package/dist/types/src/capabilities/app-graph-builder/index.d.ts.map +1 -0
  67. package/dist/types/src/capabilities/check-app-scheme/check-app-scheme.d.ts +5 -0
  68. package/dist/types/src/capabilities/check-app-scheme/check-app-scheme.d.ts.map +1 -0
  69. package/dist/types/src/capabilities/check-app-scheme/index.d.ts +3 -0
  70. package/dist/types/src/capabilities/check-app-scheme/index.d.ts.map +1 -0
  71. package/dist/types/src/capabilities/index.d.ts +8 -13
  72. package/dist/types/src/capabilities/index.d.ts.map +1 -1
  73. package/dist/types/src/capabilities/operation-resolver/index.d.ts +3 -0
  74. package/dist/types/src/capabilities/operation-resolver/index.d.ts.map +1 -0
  75. package/dist/types/src/capabilities/operation-resolver/operation-resolver.d.ts +5 -0
  76. package/dist/types/src/capabilities/operation-resolver/operation-resolver.d.ts.map +1 -0
  77. package/dist/types/src/capabilities/react-root/index.d.ts +6 -0
  78. package/dist/types/src/capabilities/react-root/index.d.ts.map +1 -0
  79. package/dist/types/src/capabilities/react-root/react-root.d.ts +9 -0
  80. package/dist/types/src/capabilities/react-root/react-root.d.ts.map +1 -0
  81. package/dist/types/src/capabilities/react-surface/index.d.ts +3 -0
  82. package/dist/types/src/capabilities/react-surface/index.d.ts.map +1 -0
  83. package/dist/types/src/capabilities/react-surface/react-surface.d.ts +5 -0
  84. package/dist/types/src/capabilities/react-surface/react-surface.d.ts.map +1 -0
  85. package/dist/types/src/capabilities/settings/index.d.ts +19 -0
  86. package/dist/types/src/capabilities/settings/index.d.ts.map +1 -0
  87. package/dist/types/src/capabilities/settings/settings.d.ts +22 -0
  88. package/dist/types/src/capabilities/settings/settings.d.ts.map +1 -0
  89. package/dist/types/src/capabilities/state/index.d.ts +174 -0
  90. package/dist/types/src/capabilities/state/index.d.ts.map +1 -0
  91. package/dist/types/src/capabilities/state/state.d.ts +177 -0
  92. package/dist/types/src/capabilities/state/state.d.ts.map +1 -0
  93. package/dist/types/src/capabilities/toolkit/index.d.ts +3 -0
  94. package/dist/types/src/capabilities/toolkit/index.d.ts.map +1 -0
  95. package/dist/types/src/capabilities/{toolkit.d.ts → toolkit/toolkit.d.ts} +5 -3
  96. package/dist/types/src/capabilities/toolkit/toolkit.d.ts.map +1 -0
  97. package/dist/types/src/capabilities/tools/index.d.ts +3 -0
  98. package/dist/types/src/capabilities/tools/index.d.ts.map +1 -0
  99. package/dist/types/src/capabilities/tools/tools.d.ts +12 -0
  100. package/dist/types/src/capabilities/tools/tools.d.ts.map +1 -0
  101. package/dist/types/src/capabilities/url-handler/index.d.ts +3 -0
  102. package/dist/types/src/capabilities/url-handler/index.d.ts.map +1 -0
  103. package/dist/types/src/capabilities/url-handler/url-handler.d.ts +5 -0
  104. package/dist/types/src/capabilities/url-handler/url-handler.d.ts.map +1 -0
  105. package/dist/types/src/components/DeckLayout/ActiveNode.d.ts.map +1 -1
  106. package/dist/types/src/components/DeckLayout/ContentEmpty.d.ts.map +1 -1
  107. package/dist/types/src/components/DeckLayout/DeckLayout.d.ts.map +1 -1
  108. package/dist/types/src/components/DeckLayout/DeckLayout.stories.d.ts +1 -0
  109. package/dist/types/src/components/DeckLayout/DeckLayout.stories.d.ts.map +1 -1
  110. package/dist/types/src/components/DeckLayout/DeckMain.d.ts.map +1 -1
  111. package/dist/types/src/components/DeckLayout/Dialog.d.ts.map +1 -1
  112. package/dist/types/src/components/DeckLayout/Popover.d.ts.map +1 -1
  113. package/dist/types/src/components/DeckLayout/Toast.d.ts +3 -3
  114. package/dist/types/src/components/DeckLayout/Toast.d.ts.map +1 -1
  115. package/dist/types/src/components/DeckSettings/DeckSettings.d.ts +4 -2
  116. package/dist/types/src/components/DeckSettings/DeckSettings.d.ts.map +1 -1
  117. package/dist/types/src/components/Plank/Plank.d.ts +3 -3
  118. package/dist/types/src/components/Plank/Plank.d.ts.map +1 -1
  119. package/dist/types/src/components/Plank/Plank.stories.d.ts +23 -4
  120. package/dist/types/src/components/Plank/Plank.stories.d.ts.map +1 -1
  121. package/dist/types/src/components/Plank/PlankControls.d.ts +1 -1
  122. package/dist/types/src/components/Plank/PlankControls.d.ts.map +1 -1
  123. package/dist/types/src/components/Plank/PlankError.d.ts +1 -1
  124. package/dist/types/src/components/Plank/PlankError.d.ts.map +1 -1
  125. package/dist/types/src/components/Plank/PlankHeading.d.ts +2 -2
  126. package/dist/types/src/components/Plank/PlankHeading.d.ts.map +1 -1
  127. package/dist/types/src/components/Sidebar/ComplementarySidebar.d.ts.map +1 -1
  128. package/dist/types/src/components/Sidebar/Sidebar.d.ts.map +1 -1
  129. package/dist/types/src/components/Sidebar/SidebarButton.d.ts.map +1 -1
  130. package/dist/types/src/hooks/index.d.ts +1 -0
  131. package/dist/types/src/hooks/index.d.ts.map +1 -1
  132. package/dist/types/src/hooks/useDeckCompanions.d.ts +3 -3
  133. package/dist/types/src/hooks/useDeckCompanions.d.ts.map +1 -1
  134. package/dist/types/src/hooks/useDeckState.d.ts +17 -0
  135. package/dist/types/src/hooks/useDeckState.d.ts.map +1 -0
  136. package/dist/types/src/hooks/useHoistStatusbar.d.ts +1 -1
  137. package/dist/types/src/hooks/useHoistStatusbar.d.ts.map +1 -1
  138. package/dist/types/src/hooks/useNodeActionExpander.d.ts +1 -1
  139. package/dist/types/src/hooks/useNodeActionExpander.d.ts.map +1 -1
  140. package/dist/types/src/index.d.ts +1 -2
  141. package/dist/types/src/index.d.ts.map +1 -1
  142. package/dist/types/src/meta.d.ts +2 -2
  143. package/dist/types/src/meta.d.ts.map +1 -1
  144. package/dist/types/src/translations.d.ts +1 -0
  145. package/dist/types/src/translations.d.ts.map +1 -1
  146. package/dist/types/src/{capabilities → types}/capabilities.d.ts +98 -90
  147. package/dist/types/src/types/capabilities.d.ts.map +1 -0
  148. package/dist/types/src/types/events.d.ts +7 -0
  149. package/dist/types/src/types/events.d.ts.map +1 -0
  150. package/dist/types/src/types/index.d.ts +2 -0
  151. package/dist/types/src/types/index.d.ts.map +1 -1
  152. package/dist/types/src/types/schema.d.ts +88 -27
  153. package/dist/types/src/types/schema.d.ts.map +1 -1
  154. package/dist/types/src/util/set-active.d.ts +18 -3
  155. package/dist/types/src/util/set-active.d.ts.map +1 -1
  156. package/dist/types/tsconfig.tsbuildinfo +1 -1
  157. package/package.json +54 -47
  158. package/src/DeckPlugin.ts +28 -48
  159. package/src/capabilities/app-graph-builder/app-graph-builder.ts +119 -0
  160. package/src/capabilities/app-graph-builder/index.ts +7 -0
  161. package/src/capabilities/check-app-scheme/check-app-scheme.ts +45 -0
  162. package/src/capabilities/check-app-scheme/index.ts +7 -0
  163. package/src/capabilities/index.ts +9 -14
  164. package/src/capabilities/operation-resolver/index.ts +10 -0
  165. package/src/capabilities/operation-resolver/operation-resolver.ts +570 -0
  166. package/src/capabilities/react-root/index.ts +7 -0
  167. package/src/capabilities/react-root/react-root.tsx +47 -0
  168. package/src/capabilities/react-surface/index.ts +7 -0
  169. package/src/capabilities/react-surface/react-surface.tsx +38 -0
  170. package/src/capabilities/settings/index.ts +7 -0
  171. package/src/capabilities/settings/settings.ts +39 -0
  172. package/src/capabilities/state/index.ts +7 -0
  173. package/src/capabilities/state/state.ts +105 -0
  174. package/src/capabilities/toolkit/index.ts +7 -0
  175. package/src/capabilities/{toolkit.ts → toolkit/toolkit.ts} +19 -21
  176. package/src/capabilities/tools/index.ts +7 -0
  177. package/src/capabilities/tools/tools.ts +92 -0
  178. package/src/capabilities/url-handler/index.ts +7 -0
  179. package/src/capabilities/url-handler/url-handler.ts +96 -0
  180. package/src/components/DeckLayout/ActiveNode.tsx +3 -2
  181. package/src/components/DeckLayout/Banner.tsx +6 -6
  182. package/src/components/DeckLayout/ContentEmpty.tsx +4 -5
  183. package/src/components/DeckLayout/DeckLayout.stories.tsx +18 -29
  184. package/src/components/DeckLayout/DeckLayout.tsx +13 -11
  185. package/src/components/DeckLayout/DeckMain.tsx +43 -38
  186. package/src/components/DeckLayout/Dialog.tsx +21 -12
  187. package/src/components/DeckLayout/Fallback.tsx +1 -1
  188. package/src/components/DeckLayout/Popover.tsx +59 -22
  189. package/src/components/DeckLayout/StatusBar.tsx +3 -3
  190. package/src/components/DeckLayout/Toast.tsx +4 -4
  191. package/src/components/DeckSettings/DeckSettings.tsx +39 -29
  192. package/src/components/Plank/Plank.stories.tsx +16 -7
  193. package/src/components/Plank/Plank.tsx +21 -20
  194. package/src/components/Plank/PlankControls.tsx +5 -6
  195. package/src/components/Plank/PlankError.tsx +2 -2
  196. package/src/components/Plank/PlankHeading.tsx +31 -36
  197. package/src/components/Sidebar/ComplementarySidebar.tsx +37 -26
  198. package/src/components/Sidebar/Sidebar.tsx +5 -5
  199. package/src/components/Sidebar/SidebarButton.tsx +30 -24
  200. package/src/components/fragments.ts +1 -1
  201. package/src/hooks/index.ts +1 -0
  202. package/src/hooks/useCompanions.ts +1 -1
  203. package/src/hooks/useDeckCompanions.ts +6 -5
  204. package/src/hooks/useDeckState.ts +82 -0
  205. package/src/hooks/useHoistStatusbar.ts +3 -6
  206. package/src/hooks/useNodeActionExpander.ts +4 -4
  207. package/src/index.ts +1 -2
  208. package/src/meta.ts +2 -2
  209. package/src/translations.ts +1 -0
  210. package/src/types/capabilities.ts +33 -0
  211. package/src/types/events.ts +21 -0
  212. package/src/types/index.ts +2 -0
  213. package/src/types/schema.ts +85 -11
  214. package/src/util/layoutAppliesTopbar.ts +1 -1
  215. package/src/util/set-active.ts +49 -29
  216. package/dist/lib/browser/app-graph-builder-D74NTOMK.mjs +0 -128
  217. package/dist/lib/browser/app-graph-builder-D74NTOMK.mjs.map +0 -7
  218. package/dist/lib/browser/check-app-scheme-HIEVFAAX.mjs +0 -32
  219. package/dist/lib/browser/check-app-scheme-HIEVFAAX.mjs.map +0 -7
  220. package/dist/lib/browser/chunk-5KMJPIQC.mjs +0 -16
  221. package/dist/lib/browser/chunk-5KMJPIQC.mjs.map +0 -7
  222. package/dist/lib/browser/chunk-CNTGBCMK.mjs.map +0 -7
  223. package/dist/lib/browser/chunk-F3VCCHVL.mjs.map +0 -7
  224. package/dist/lib/browser/chunk-QKCGZ45E.mjs +0 -128
  225. package/dist/lib/browser/chunk-QKCGZ45E.mjs.map +0 -7
  226. package/dist/lib/browser/chunk-UXLU6CMW.mjs +0 -16
  227. package/dist/lib/browser/chunk-UXLU6CMW.mjs.map +0 -7
  228. package/dist/lib/browser/chunk-VBYJ664A.mjs +0 -132
  229. package/dist/lib/browser/chunk-VBYJ664A.mjs.map +0 -7
  230. package/dist/lib/browser/chunk-VUJ6UNIJ.mjs +0 -1553
  231. package/dist/lib/browser/chunk-VUJ6UNIJ.mjs.map +0 -7
  232. package/dist/lib/browser/intent-resolver-UA4YQGAC.mjs +0 -524
  233. package/dist/lib/browser/intent-resolver-UA4YQGAC.mjs.map +0 -7
  234. package/dist/lib/browser/react-root-JAMHKYWN.mjs +0 -44
  235. package/dist/lib/browser/react-root-JAMHKYWN.mjs.map +0 -7
  236. package/dist/lib/browser/react-surface-6LW337ZT.mjs +0 -40
  237. package/dist/lib/browser/react-surface-6LW337ZT.mjs.map +0 -7
  238. package/dist/lib/browser/settings-SDPTOCCM.mjs +0 -30
  239. package/dist/lib/browser/settings-SDPTOCCM.mjs.map +0 -7
  240. package/dist/lib/browser/state-7IFAGZQO.mjs +0 -12
  241. package/dist/lib/browser/toolkit-L5CFXJCF.mjs.map +0 -7
  242. package/dist/lib/browser/url-handler-QEYGYE2H.mjs +0 -70
  243. package/dist/lib/browser/url-handler-QEYGYE2H.mjs.map +0 -7
  244. package/dist/types/src/capabilities/app-graph-builder.d.ts +0 -4
  245. package/dist/types/src/capabilities/app-graph-builder.d.ts.map +0 -1
  246. package/dist/types/src/capabilities/capabilities.d.ts.map +0 -1
  247. package/dist/types/src/capabilities/check-app-scheme.d.ts +0 -4
  248. package/dist/types/src/capabilities/check-app-scheme.d.ts.map +0 -1
  249. package/dist/types/src/capabilities/intent-resolver.d.ts +0 -4
  250. package/dist/types/src/capabilities/intent-resolver.d.ts.map +0 -1
  251. package/dist/types/src/capabilities/react-root.d.ts +0 -7
  252. package/dist/types/src/capabilities/react-root.d.ts.map +0 -1
  253. package/dist/types/src/capabilities/react-surface.d.ts +0 -4
  254. package/dist/types/src/capabilities/react-surface.d.ts.map +0 -1
  255. package/dist/types/src/capabilities/settings.d.ts +0 -4
  256. package/dist/types/src/capabilities/settings.d.ts.map +0 -1
  257. package/dist/types/src/capabilities/state.d.ts +0 -104
  258. package/dist/types/src/capabilities/state.d.ts.map +0 -1
  259. package/dist/types/src/capabilities/toolkit.d.ts.map +0 -1
  260. package/dist/types/src/capabilities/tools.d.ts +0 -11
  261. package/dist/types/src/capabilities/tools.d.ts.map +0 -1
  262. package/dist/types/src/capabilities/url-handler.d.ts +0 -4
  263. package/dist/types/src/capabilities/url-handler.d.ts.map +0 -1
  264. package/dist/types/src/events.d.ts +0 -4
  265. package/dist/types/src/events.d.ts.map +0 -1
  266. package/src/capabilities/app-graph-builder.ts +0 -143
  267. package/src/capabilities/capabilities.ts +0 -14
  268. package/src/capabilities/check-app-scheme.ts +0 -40
  269. package/src/capabilities/intent-resolver.ts +0 -471
  270. package/src/capabilities/react-root.tsx +0 -40
  271. package/src/capabilities/react-surface.tsx +0 -30
  272. package/src/capabilities/settings.ts +0 -27
  273. package/src/capabilities/state.ts +0 -113
  274. package/src/capabilities/tools.ts +0 -84
  275. package/src/capabilities/url-handler.ts +0 -60
  276. package/src/events.ts +0 -11
  277. /package/dist/lib/{browser/state-7IFAGZQO.mjs.map → node-esm/types/index.mjs.map} +0 -0
@@ -0,0 +1,39 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import * as Effect from 'effect/Effect';
6
+
7
+ import { Capability } from '@dxos/app-framework';
8
+ import { AppCapabilities } from '@dxos/app-toolkit';
9
+ import { createKvsStore } from '@dxos/effect';
10
+
11
+ import { meta } from '../../meta';
12
+ import { DeckCapabilities, DeckSettingsSchema } from '../../types';
13
+
14
+ export default Capability.makeModule(() =>
15
+ Effect.sync(() => {
16
+ const settingsAtom = createKvsStore({
17
+ key: meta.id,
18
+ schema: DeckSettingsSchema,
19
+ defaultValue: () => ({
20
+ showHints: false,
21
+ enableDeck: false,
22
+ enableStatusbar: false,
23
+ enableNativeRedirect: false,
24
+ newPlankPositioning: 'start' as const,
25
+ overscroll: 'none' as const,
26
+ encapsulatedPlanks: false,
27
+ }),
28
+ });
29
+
30
+ return [
31
+ Capability.contributes(DeckCapabilities.Settings, settingsAtom),
32
+ Capability.contributes(AppCapabilities.Settings, {
33
+ prefix: meta.id,
34
+ schema: DeckSettingsSchema,
35
+ atom: settingsAtom,
36
+ }),
37
+ ];
38
+ }),
39
+ );
@@ -0,0 +1,7 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { Capability } from '@dxos/app-framework';
6
+
7
+ export const DeckState = Capability.lazy('DeckState', () => import('./state'));
@@ -0,0 +1,105 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { Atom } from '@effect-atom/atom-react';
6
+ import * as Effect from 'effect/Effect';
7
+
8
+ import { Capabilities, Capability } from '@dxos/app-framework';
9
+ import { AppCapabilities } from '@dxos/app-toolkit';
10
+ import { createKvsStore } from '@dxos/effect';
11
+ import { invariant } from '@dxos/invariant';
12
+
13
+ import { meta } from '../../meta';
14
+ import {
15
+ DeckCapabilities,
16
+ type DeckEphemeralStateProps,
17
+ type DeckStateProps,
18
+ DeckStateSchema,
19
+ defaultDeck,
20
+ getMode,
21
+ } from '../../types';
22
+
23
+ /** Default persisted state. */
24
+ const defaultDeckState: DeckStateProps = {
25
+ sidebarState: 'expanded',
26
+ complementarySidebarState: 'collapsed',
27
+ complementarySidebarPanel: undefined,
28
+ activeDeck: 'default',
29
+ previousDeck: 'default',
30
+ decks: {
31
+ default: { ...defaultDeck },
32
+ },
33
+ previousMode: {},
34
+ };
35
+
36
+ /** Default ephemeral state. */
37
+ const defaultDeckEphemeralState: DeckEphemeralStateProps = {
38
+ dialogContent: null,
39
+ dialogOpen: false,
40
+ dialogBlockAlign: undefined,
41
+ dialogType: undefined,
42
+ popoverContent: null,
43
+ popoverAnchor: undefined,
44
+ popoverAnchorId: undefined,
45
+ popoverOpen: false,
46
+ toasts: [],
47
+ currentUndoId: undefined,
48
+ scrollIntoView: undefined,
49
+ };
50
+
51
+ export default Capability.makeModule(
52
+ Effect.fnUntraced(function* () {
53
+ const registry = yield* Capability.get(Capabilities.AtomRegistry);
54
+
55
+ // Persisted state using KVS store.
56
+ const stateAtom = createKvsStore({
57
+ key: `${meta.id}/state`,
58
+ schema: DeckStateSchema,
59
+ defaultValue: () => ({ ...defaultDeckState }),
60
+ });
61
+
62
+ // Ephemeral state (not persisted, but kept alive to prevent GC resets).
63
+ const ephemeralAtom = Atom.make<DeckEphemeralStateProps>({ ...defaultDeckEphemeralState }).pipe(Atom.keepAlive);
64
+
65
+ // Don't allow fullscreen mode to be persisted to prevent getting stuck in it.
66
+ const currentState = registry.get(stateAtom);
67
+ const currentDeck = currentState.decks[currentState.activeDeck];
68
+ if (currentDeck?.fullscreen) {
69
+ registry.set(stateAtom, {
70
+ ...currentState,
71
+ decks: {
72
+ ...currentState.decks,
73
+ [currentState.activeDeck]: {
74
+ ...currentDeck,
75
+ fullscreen: false,
76
+ },
77
+ },
78
+ });
79
+ }
80
+
81
+ // Create derived layout atom (read-only) from both state atoms.
82
+ const layoutAtom = Atom.make((get) => {
83
+ const state = get(stateAtom);
84
+ const ephemeral = get(ephemeralAtom);
85
+ const deck = state.decks[state.activeDeck];
86
+ invariant(deck, `Deck not found: ${state.activeDeck}`);
87
+ return {
88
+ mode: getMode(deck),
89
+ dialogOpen: ephemeral.dialogOpen,
90
+ sidebarOpen: state.sidebarState === 'expanded',
91
+ complementarySidebarOpen: state.complementarySidebarState === 'expanded',
92
+ workspace: state.activeDeck,
93
+ active: deck.solo ? [deck.solo] : deck.active,
94
+ inactive: deck.inactive,
95
+ scrollIntoView: ephemeral.scrollIntoView,
96
+ } satisfies AppCapabilities.Layout;
97
+ }).pipe(Atom.keepAlive);
98
+
99
+ return [
100
+ Capability.contributes(DeckCapabilities.State, stateAtom),
101
+ Capability.contributes(DeckCapabilities.EphemeralState, ephemeralAtom),
102
+ Capability.contributes(AppCapabilities.Layout, layoutAtom),
103
+ ];
104
+ }),
105
+ );
@@ -0,0 +1,7 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { Capability } from '@dxos/app-framework';
6
+
7
+ export const Toolkit = Capability.lazy('Toolkit', () => import('./toolkit'));
@@ -7,20 +7,14 @@ import * as Toolkit from '@effect/ai/Toolkit';
7
7
  import * as Effect from 'effect/Effect';
8
8
  import * as Schema from 'effect/Schema';
9
9
 
10
- import {
11
- Capabilities,
12
- type Capability,
13
- LayoutAction,
14
- type PluginContext,
15
- contributes,
16
- createIntent,
17
- } from '@dxos/app-framework';
10
+ import { Capabilities, Capability, type CapabilityManager } from '@dxos/app-framework';
11
+ import { AppCapabilities, LayoutOperation } from '@dxos/app-toolkit';
18
12
  import { GenericToolkit } from '@dxos/assistant';
19
13
  import { ArtifactId } from '@dxos/assistant';
20
14
  import { type SpaceId } from '@dxos/keys';
21
15
  import { trim } from '@dxos/util';
22
16
 
23
- import { DeckCapabilities } from './capabilities';
17
+ import { DeckCapabilities } from '../../types';
24
18
 
25
19
  const Toolkit$ = Toolkit.make(
26
20
  Tool.make('open-item', {
@@ -38,11 +32,13 @@ const Toolkit$ = Toolkit.make(
38
32
  export namespace DeckToolkit {
39
33
  export const Toolkit = Toolkit$;
40
34
 
41
- export const createLayer = (context: PluginContext) =>
35
+ export const createLayer = (capabilityManager: CapabilityManager.CapabilityManager) =>
42
36
  Toolkit$.toLayer({
43
37
  'open-item': ({ id }) =>
44
38
  Effect.gen(function* () {
45
- const state = context.getCapability(DeckCapabilities.DeckState);
39
+ const registry = capabilityManager.get(Capabilities.AtomRegistry);
40
+ const stateAtom = capabilityManager.get(DeckCapabilities.State);
41
+ const state = registry.get(stateAtom);
46
42
  const dxn = ArtifactId.toDXN(id, state.activeDeck as SpaceId).asEchoDXN();
47
43
  if (!dxn) {
48
44
  // TODO(wittjosiah): Support other variants.
@@ -50,17 +46,19 @@ export namespace DeckToolkit {
50
46
  }
51
47
 
52
48
  // TODO(wittjosiah): Get capabilities via layers.
53
- const { dispatch } = context.getCapability(Capabilities.IntentDispatcher);
54
- yield* dispatch(
55
- createIntent(LayoutAction.Open, {
56
- subject: [`${dxn.spaceId!}:${dxn.echoId}`],
57
- part: 'main',
58
- }),
59
- );
49
+ const { invoke } = capabilityManager.get(Capabilities.OperationInvoker);
50
+ yield* invoke(LayoutOperation.Open, { subject: [`${dxn.spaceId!}:${dxn.echoId}`] });
60
51
  }).pipe(Effect.orDie),
61
52
  });
62
53
  }
63
54
 
64
- export default (context: PluginContext): Capability<any>[] => [
65
- contributes(Capabilities.Toolkit, GenericToolkit.make(DeckToolkit.Toolkit, DeckToolkit.createLayer(context))),
66
- ];
55
+ export default Capability.makeModule(
56
+ Effect.fnUntraced(function* () {
57
+ const capabilityManager = yield* Capability.Service;
58
+
59
+ return Capability.contributes(
60
+ AppCapabilities.Toolkit,
61
+ GenericToolkit.make(DeckToolkit.Toolkit, DeckToolkit.createLayer(capabilityManager)),
62
+ );
63
+ }),
64
+ );
@@ -0,0 +1,7 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { Capability } from '@dxos/app-framework';
6
+
7
+ export const Tools = Capability.lazy('Tools', () => import('./tools'));
@@ -0,0 +1,92 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ // ISSUE(burdon): tools
6
+ // @ts-nocheck
7
+
8
+ import * as Effect from 'effect/Effect';
9
+ import * as Schema from 'effect/Schema';
10
+
11
+ import {
12
+ Capabilities,
13
+ Capability,
14
+ LayoutAction,
15
+ type PromiseIntentDispatcher,
16
+ createIntent,
17
+ } from '@dxos/app-framework';
18
+ import { type OperationInvoker } from '@dxos/app-framework/plugin-operation/invoker';
19
+ import { invariant } from '@dxos/invariant';
20
+ import { trim } from '@dxos/util';
21
+
22
+ import { meta } from '../../meta';
23
+ import { DeckOperation } from '../../types';
24
+
25
+ // TODO(burdon): Factor out.
26
+ declare global {
27
+ interface ToolContextExtensions {
28
+ dispatch?: PromiseIntentDispatcher;
29
+ pivotId?: string;
30
+ part?: 'deck' | 'dialog';
31
+ }
32
+ }
33
+
34
+ export default Capability.makeModule(() =>
35
+ Effect.succeed(
36
+ Capability.contributes(Capabilities.Tools, [
37
+ createTool(meta.id, {
38
+ name: 'show',
39
+ description: trim`
40
+ Show an item as a companion to an existing plank.
41
+ When supplying IDs, they must be fully qualified like this: space-key:object-id
42
+ `,
43
+ caption: 'Showing item...',
44
+ // TODO(wittjosiah): Refactor Layout/Navigation/Deck actions so that they can be used directly.
45
+ schema: Schema.Struct({
46
+ id: Schema.String.annotations({
47
+ description: 'The ID of the item to show.',
48
+ }),
49
+ }),
50
+ execute: async ({ id }, { extensions }) => {
51
+ invariant(extensions);
52
+ const { pivotId, dispatch, invokePromise, part } = extensions as {
53
+ pivotId: string;
54
+ dispatch: PromiseIntentDispatcher;
55
+ invokePromise: OperationInvoker['invokePromise'];
56
+ part: string;
57
+ };
58
+ invariant(pivotId, 'No pivot ID');
59
+ invariant(invokePromise, 'No operation invoker');
60
+
61
+ if (part === 'deck') {
62
+ const { error } = await invokePromise(DeckOperation.ChangeCompanion, {
63
+ primary: pivotId,
64
+ companion: id,
65
+ });
66
+ if (error) {
67
+ return ToolResult.Error(error.message);
68
+ }
69
+
70
+ return ToolResult.Success({});
71
+ } else {
72
+ const { data, error } = await dispatch(
73
+ createIntent(LayoutAction.Open, {
74
+ subject: [id],
75
+ part: 'main',
76
+ options: {
77
+ pivotId,
78
+ positioning: 'end',
79
+ },
80
+ }),
81
+ );
82
+ if (error) {
83
+ return ToolResult.Error(error.message);
84
+ }
85
+
86
+ return ToolResult.Success(data);
87
+ }
88
+ },
89
+ }),
90
+ ]),
91
+ ),
92
+ );
@@ -0,0 +1,7 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { Capability } from '@dxos/app-framework';
6
+
7
+ export const UrlHandler = Capability.lazy('UrlHandler', () => import('./url-handler'));
@@ -0,0 +1,96 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import * as Effect from 'effect/Effect';
6
+
7
+ import { Capabilities, Capability } from '@dxos/app-framework';
8
+ import { LayoutOperation } from '@dxos/app-toolkit';
9
+ import { invariant } from '@dxos/invariant';
10
+
11
+ import { DeckCapabilities, type DeckStateProps, defaultDeck } from '../../types';
12
+
13
+ // TODO(wittjosiah): Cleanup the url handling. May justify introducing routing capabilities.
14
+ export default Capability.makeModule(
15
+ Effect.fnUntraced(function* () {
16
+ const { invokeSync } = yield* Capability.get(Capabilities.OperationInvoker);
17
+ const registry = yield* Capability.get(Capabilities.AtomRegistry);
18
+ const stateAtom = yield* Capability.get(DeckCapabilities.State);
19
+
20
+ // Helper to get state.
21
+ const getState = () => registry.get(stateAtom);
22
+
23
+ // Helper to get computed deck from state.
24
+ const getDeck = () => {
25
+ const state = getState();
26
+ const deck = state.decks[state.activeDeck];
27
+ invariant(deck, `Deck not found: ${state.activeDeck}`);
28
+ return deck;
29
+ };
30
+
31
+ // Helper to update state.
32
+ const updateState = (fn: (current: DeckStateProps) => DeckStateProps) => {
33
+ registry.set(stateAtom, fn(getState()));
34
+ };
35
+
36
+ const handleNavigation = () => {
37
+ const pathname = window.location.pathname;
38
+ const state = getState();
39
+ if (pathname === '/reset') {
40
+ updateState((s) => ({
41
+ ...s,
42
+ activeDeck: 'default',
43
+ decks: {
44
+ default: { ...defaultDeck },
45
+ },
46
+ }));
47
+ window.location.pathname = '/';
48
+ return;
49
+ }
50
+
51
+ const [_, nextDeck, nextSolo] = pathname.split('/');
52
+ if (nextDeck && nextDeck !== state.activeDeck) {
53
+ invokeSync(LayoutOperation.SwitchWorkspace, { subject: nextDeck });
54
+ }
55
+
56
+ const deck = getDeck();
57
+ if (nextSolo && nextSolo !== deck.solo) {
58
+ invokeSync(LayoutOperation.SetLayoutMode, { subject: nextSolo, mode: 'solo' });
59
+ } else if (!nextSolo && deck.solo) {
60
+ invokeSync(LayoutOperation.SetLayoutMode, { mode: 'deck' });
61
+ }
62
+ };
63
+
64
+ yield* Effect.sync(() => handleNavigation());
65
+ window.addEventListener('popstate', handleNavigation);
66
+
67
+ // Subscribe to state changes to update the URL.
68
+ let lastSolo: string | undefined;
69
+ let lastActiveDeck: string | undefined;
70
+ const unsubscribe = registry.subscribe(stateAtom, () => {
71
+ const state = getState();
72
+ const deck = getDeck();
73
+ const solo = deck.solo;
74
+ const activeDeck = state.activeDeck;
75
+
76
+ // Only update URL if relevant state changed.
77
+ if (solo !== lastSolo || activeDeck !== lastActiveDeck) {
78
+ lastSolo = solo;
79
+ lastActiveDeck = activeDeck;
80
+
81
+ const path = solo ? `/${activeDeck}/${solo}` : `/${activeDeck}`;
82
+ if (window.location.pathname !== path) {
83
+ // TODO(thure): In some browsers, this only preserves the most recent state change, even though this is not `history.replace`…
84
+ history.pushState(null, '', `${path}${window.location.search}`);
85
+ }
86
+ }
87
+ });
88
+
89
+ return Capability.contributes(Capabilities.Null, null, () =>
90
+ Effect.sync(() => {
91
+ window.removeEventListener('popstate', handleNavigation);
92
+ unsubscribe();
93
+ }),
94
+ );
95
+ }),
96
+ );
@@ -4,7 +4,8 @@
4
4
 
5
5
  import React from 'react';
6
6
 
7
- import { Surface, useAppGraph } from '@dxos/app-framework/react';
7
+ import { Surface } from '@dxos/app-framework/ui';
8
+ import { useAppGraph } from '@dxos/app-toolkit/ui';
8
9
  import { useNode } from '@dxos/plugin-graph';
9
10
  import { useAttended } from '@dxos/react-ui-attention';
10
11
 
@@ -21,7 +22,7 @@ export const ActiveNode = () => {
21
22
  <div role='none' className='sr-only'>
22
23
  {/* TODO(wittjosiah): Weird that this is a surface, feel like it's not really render logic.
23
24
  Probably this lives in React-land currently in order to access translations? */}
24
- <Surface role='document-title' data={{ subject: activeNode }} limit={1} />
25
+ <Surface.Surface role='document-title' data={{ subject: activeNode }} limit={1} />
25
26
  </div>
26
27
  );
27
28
  };
@@ -4,9 +4,9 @@
4
4
 
5
5
  import React from 'react';
6
6
 
7
- import { Surface } from '@dxos/app-framework/react';
7
+ import { Surface } from '@dxos/app-framework/ui';
8
8
  import { type ThemedClassName, useTranslation } from '@dxos/react-ui';
9
- import { mx } from '@dxos/react-ui-theme';
9
+ import { mx, osTranslations } from '@dxos/ui-theme';
10
10
 
11
11
  import { meta } from '../../meta';
12
12
  import { CloseSidebarButton, ToggleSidebarButton } from '../Sidebar';
@@ -23,17 +23,17 @@ export const Banner = ({ variant, classNames }: ThemedClassName<{ variant?: 'top
23
23
  )}
24
24
  >
25
25
  {variant === 'sidebar' ? <CloseSidebarButton /> : <ToggleSidebarButton />}
26
- <span className='self-center grow mis-1'>{t('current app name', { ns: 'appkit' })}</span>
26
+ <span className='self-center grow mis-1'>{t('current app name', { ns: osTranslations })}</span>
27
27
  {variant === 'topbar' && (
28
28
  <div role='none' className='absolute inset-0 pointer-events-none'>
29
29
  <div role='none' className='grid bs-full pointer-fine:p-1 max-is-md mli-auto pointer-events-auto'>
30
- <Surface role='search-input' limit={1} />
30
+ <Surface.Surface role='search-input' limit={1} />
31
31
  </div>
32
32
  </div>
33
33
  )}
34
34
  <span role='none' className='grow' />
35
- <Surface role='header-end' limit={1} />
36
- <Surface role='notch-start' limit={1} />
35
+ <Surface.Surface role='header-end' limit={1} />
36
+ <Surface.Surface role='notch-start' limit={1} />
37
37
  </header>
38
38
  );
39
39
  };
@@ -4,10 +4,9 @@
4
4
 
5
5
  import React from 'react';
6
6
 
7
- import { Surface, useCapability } from '@dxos/app-framework/react';
7
+ import { Surface } from '@dxos/app-framework/ui';
8
8
 
9
- import { DeckCapabilities } from '../../capabilities';
10
- import { useBreakpoints } from '../../hooks';
9
+ import { useBreakpoints, useDeckState } from '../../hooks';
11
10
  import { getMode } from '../../types';
12
11
  import { layoutAppliesTopbar } from '../../util';
13
12
  import { fixedSidebarToggleStyles } from '../fragments';
@@ -15,7 +14,7 @@ import { ToggleSidebarButton } from '../Sidebar';
15
14
 
16
15
  export const ContentEmpty = () => {
17
16
  const breakpoint = useBreakpoints();
18
- const { deck } = useCapability(DeckCapabilities.MutableDeckState);
17
+ const { deck } = useDeckState();
19
18
  const layoutMode = getMode(deck);
20
19
  const topbar = layoutAppliesTopbar(breakpoint, layoutMode);
21
20
  return (
@@ -24,7 +23,7 @@ export const ContentEmpty = () => {
24
23
  className='grid place-items-center p-8 relative bg-deckSurface'
25
24
  data-testid='layoutPlugin.firstRunMessage'
26
25
  >
27
- <Surface role='keyshortcuts' />
26
+ <Surface.Surface role='keyshortcuts' />
28
27
  {!topbar && <ToggleSidebarButton variant='default' classNames={fixedSidebarToggleStyles} />}
29
28
  </div>
30
29
  );
@@ -5,49 +5,38 @@
5
5
  import { type Meta, type StoryObj } from '@storybook/react-vite';
6
6
  import React from 'react';
7
7
 
8
- import { Events, IntentPlugin, SettingsPlugin, defineModule, definePlugin } from '@dxos/app-framework';
8
+ import { Capability, Plugin } from '@dxos/app-framework';
9
9
  import { withPluginManager } from '@dxos/app-framework/testing';
10
- import { AttentionPlugin } from '@dxos/plugin-attention';
11
- import { GraphPlugin } from '@dxos/plugin-graph';
10
+ import { AppActivationEvents, AppPlugin } from '@dxos/app-toolkit';
11
+ import { corePlugins } from '@dxos/plugin-testing';
12
12
  import { withTheme } from '@dxos/react-ui/testing';
13
13
 
14
- import { DeckStateFactory, LayoutIntentResolver } from '../../capabilities';
14
+ import { DeckState, LayoutOperationResolver } from '../../capabilities';
15
15
  import { meta as pluginMeta } from '../../meta';
16
16
  import { translations } from '../../translations';
17
17
 
18
18
  import { DeckLayout } from './DeckLayout';
19
19
 
20
+ const TestPlugin = Plugin.define(pluginMeta).pipe(
21
+ Plugin.addModule({
22
+ id: Capability.getModuleTag(DeckState),
23
+ activatesOn: AppActivationEvents.AppGraphReady,
24
+ activate: () => DeckState(),
25
+ }),
26
+ AppPlugin.addOperationResolverModule({
27
+ activate: LayoutOperationResolver,
28
+ }),
29
+ Plugin.make,
30
+ );
31
+
20
32
  const meta = {
21
33
  title: 'plugins/plugin-deck/DeckLayout',
22
34
  component: DeckLayout,
23
35
  render: (args) => <DeckLayout {...args} />,
24
36
  decorators: [
25
- withTheme,
37
+ withTheme(),
26
38
  withPluginManager({
27
- plugins: [
28
- AttentionPlugin(),
29
- SettingsPlugin(),
30
- IntentPlugin(),
31
- GraphPlugin(),
32
- definePlugin(
33
- {
34
- id: 'example.com/plutin/testing',
35
- name: 'Testing',
36
- },
37
- () => [
38
- defineModule({
39
- id: `${pluginMeta.id}/module/deck-state`,
40
- activatesOn: Events.AppGraphReady,
41
- activate: () => DeckStateFactory(),
42
- }),
43
- defineModule({
44
- id: `${pluginMeta.id}/module/layout-intent-resolver`,
45
- activatesOn: Events.SetupIntentResolver,
46
- activate: LayoutIntentResolver,
47
- }),
48
- ],
49
- )(),
50
- ],
39
+ plugins: [...corePlugins(), TestPlugin()],
51
40
  }),
52
41
  ],
53
42
  parameters: {
@@ -4,9 +4,9 @@
4
4
 
5
5
  import React from 'react';
6
6
 
7
- import { useCapability } from '@dxos/app-framework/react';
7
+ import { Mosaic } from '@dxos/react-ui-mosaic';
8
8
 
9
- import { DeckCapabilities } from '../../capabilities';
9
+ import { useDeckState } from '../../hooks';
10
10
 
11
11
  import { ActiveNode } from './ActiveNode';
12
12
  import { DeckMain } from './DeckMain';
@@ -17,16 +17,18 @@ import { Toaster, type ToasterProps } from './Toast';
17
17
  export type DeckLayoutProps = Pick<ToasterProps, 'onDismissToast'>;
18
18
 
19
19
  export const DeckLayout = ({ onDismissToast }: DeckLayoutProps) => {
20
- const context = useCapability(DeckCapabilities.MutableDeckState);
21
- const { toasts } = context;
20
+ const { state } = useDeckState();
21
+ const { toasts } = state;
22
22
 
23
23
  return (
24
- <PopoverRoot>
25
- <ActiveNode />
26
- <DeckMain />
27
- <PopoverContent />
28
- <Dialog />
29
- <Toaster toasts={toasts} onDismissToast={onDismissToast} />
30
- </PopoverRoot>
24
+ <Mosaic.Root>
25
+ <PopoverRoot>
26
+ <ActiveNode />
27
+ <DeckMain />
28
+ <PopoverContent />
29
+ <Dialog />
30
+ <Toaster toasts={toasts} onDismissToast={onDismissToast} />
31
+ </PopoverRoot>
32
+ </Mosaic.Root>
31
33
  );
32
34
  };