@dxos/plugin-sheet 0.6.11 → 0.6.12-main.15a606f

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 (260) hide show
  1. package/dist/lib/browser/SheetContainer-V4GCCZTX.mjs +261 -0
  2. package/dist/lib/browser/SheetContainer-V4GCCZTX.mjs.map +7 -0
  3. package/dist/lib/browser/{chunk-D5AGLXJP.mjs → chunk-6ZMQVB4Z.mjs} +359 -671
  4. package/dist/lib/browser/chunk-6ZMQVB4Z.mjs.map +7 -0
  5. package/dist/lib/browser/{chunk-JRL5LGCE.mjs → chunk-QILRZNE5.mjs} +2 -5
  6. package/dist/lib/browser/chunk-QILRZNE5.mjs.map +7 -0
  7. package/dist/lib/browser/{chunk-FUAGSXA4.mjs → chunk-T3NJFTD4.mjs} +8 -15
  8. package/dist/lib/browser/chunk-T3NJFTD4.mjs.map +7 -0
  9. package/dist/lib/browser/{SheetContainer-U4H5D34A.mjs → chunk-U2JHW3L6.mjs} +1020 -240
  10. package/dist/lib/browser/chunk-U2JHW3L6.mjs.map +7 -0
  11. package/dist/lib/browser/graph-T27BOBOV.mjs +21 -0
  12. package/dist/lib/browser/graph-T27BOBOV.mjs.map +7 -0
  13. package/dist/lib/browser/index.mjs +68 -56
  14. package/dist/lib/browser/index.mjs.map +3 -3
  15. package/dist/lib/browser/meta.json +1 -1
  16. package/dist/lib/browser/meta.mjs +1 -1
  17. package/dist/lib/browser/types.mjs +4 -6
  18. package/dist/lib/node/SheetContainer-3ZY7MPWJ.cjs +279 -0
  19. package/dist/lib/node/SheetContainer-3ZY7MPWJ.cjs.map +7 -0
  20. package/dist/lib/node/{chunk-BJ6ZD7MN.cjs → chunk-BNARJ5GM.cjs} +5 -18
  21. package/dist/lib/node/chunk-BNARJ5GM.cjs.map +7 -0
  22. package/dist/lib/node/{chunk-5KKJ4NPP.cjs → chunk-DD6FIXWC.cjs} +360 -667
  23. package/dist/lib/node/chunk-DD6FIXWC.cjs.map +7 -0
  24. package/dist/lib/node/{SheetContainer-AXQV3ZT5.cjs → chunk-OTTD7FBK.cjs} +1050 -279
  25. package/dist/lib/node/chunk-OTTD7FBK.cjs.map +7 -0
  26. package/dist/lib/node/{chunk-DSYKOI4E.cjs → chunk-Q3HBHPRL.cjs} +12 -20
  27. package/dist/lib/node/chunk-Q3HBHPRL.cjs.map +7 -0
  28. package/dist/lib/node/graph-SPKGX7W4.cjs +43 -0
  29. package/dist/lib/node/graph-SPKGX7W4.cjs.map +7 -0
  30. package/dist/lib/node/index.cjs +83 -64
  31. package/dist/lib/node/index.cjs.map +3 -3
  32. package/dist/lib/node/meta.cjs +3 -3
  33. package/dist/lib/node/meta.cjs.map +1 -1
  34. package/dist/lib/node/meta.json +1 -1
  35. package/dist/lib/node/types.cjs +10 -12
  36. package/dist/lib/node/types.cjs.map +2 -2
  37. package/dist/lib/node-esm/SheetContainer-PXSJX6XK.mjs +262 -0
  38. package/dist/lib/node-esm/SheetContainer-PXSJX6XK.mjs.map +7 -0
  39. package/dist/lib/node-esm/chunk-7HVSOTGA.mjs +2553 -0
  40. package/dist/lib/node-esm/chunk-7HVSOTGA.mjs.map +7 -0
  41. package/dist/lib/node-esm/chunk-BMNA27EX.mjs +76 -0
  42. package/dist/lib/node-esm/chunk-BMNA27EX.mjs.map +7 -0
  43. package/dist/lib/node-esm/chunk-D6KU5MI7.mjs +2925 -0
  44. package/dist/lib/node-esm/chunk-D6KU5MI7.mjs.map +7 -0
  45. package/dist/lib/node-esm/chunk-IU2L277A.mjs +17 -0
  46. package/dist/lib/node-esm/chunk-IU2L277A.mjs.map +7 -0
  47. package/dist/lib/node-esm/graph-U67IO4UC.mjs +22 -0
  48. package/dist/lib/node-esm/graph-U67IO4UC.mjs.map +7 -0
  49. package/dist/lib/node-esm/index.mjs +261 -0
  50. package/dist/lib/node-esm/index.mjs.map +7 -0
  51. package/dist/lib/node-esm/meta.json +1 -0
  52. package/dist/lib/node-esm/meta.mjs +10 -0
  53. package/dist/lib/node-esm/meta.mjs.map +7 -0
  54. package/dist/lib/node-esm/types.mjs +21 -0
  55. package/dist/lib/node-esm/types.mjs.map +7 -0
  56. package/dist/types/src/SheetPlugin.d.ts.map +1 -1
  57. package/dist/types/src/components/CellEditor/CellEditor.d.ts +23 -3
  58. package/dist/types/src/components/CellEditor/CellEditor.d.ts.map +1 -1
  59. package/dist/types/src/components/CellEditor/CellEditor.stories.d.ts +2 -2
  60. package/dist/types/src/components/CellEditor/CellEditor.stories.d.ts.map +1 -1
  61. package/dist/types/src/components/CellEditor/extension.d.ts +1 -1
  62. package/dist/types/src/components/CellEditor/extension.d.ts.map +1 -1
  63. package/dist/types/src/components/ComputeGraph/ComputeGraphContextProvider.d.ts +11 -0
  64. package/dist/types/src/components/ComputeGraph/ComputeGraphContextProvider.d.ts.map +1 -0
  65. package/dist/types/src/components/ComputeGraph/index.d.ts +1 -3
  66. package/dist/types/src/components/ComputeGraph/index.d.ts.map +1 -1
  67. package/dist/types/src/components/GridSheet/GridSheet.d.ts +10 -0
  68. package/dist/types/src/components/GridSheet/GridSheet.d.ts.map +1 -0
  69. package/dist/types/src/components/GridSheet/GridSheet.stories.d.ts +9 -0
  70. package/dist/types/src/components/GridSheet/GridSheet.stories.d.ts.map +1 -0
  71. package/dist/types/src/components/GridSheet/util.d.ts +6 -0
  72. package/dist/types/src/components/GridSheet/util.d.ts.map +1 -0
  73. package/dist/types/src/components/Sheet/Sheet.d.ts +1 -1
  74. package/dist/types/src/components/Sheet/Sheet.d.ts.map +1 -1
  75. package/dist/types/src/components/Sheet/Sheet.stories.d.ts +5 -6
  76. package/dist/types/src/components/Sheet/Sheet.stories.d.ts.map +1 -1
  77. package/dist/types/src/components/Sheet/decorations.d.ts +24 -0
  78. package/dist/types/src/components/Sheet/decorations.d.ts.map +1 -0
  79. package/dist/types/src/components/Sheet/grid.d.ts +2 -2
  80. package/dist/types/src/components/Sheet/grid.d.ts.map +1 -1
  81. package/dist/types/src/components/Sheet/nav.d.ts +3 -3
  82. package/dist/types/src/components/Sheet/nav.d.ts.map +1 -1
  83. package/dist/types/src/components/Sheet/sheet-context.d.ts +6 -5
  84. package/dist/types/src/components/Sheet/sheet-context.d.ts.map +1 -1
  85. package/dist/types/src/components/Sheet/threads.d.ts +2 -0
  86. package/dist/types/src/components/Sheet/threads.d.ts.map +1 -0
  87. package/dist/types/src/components/SheetContainer.d.ts +2 -3
  88. package/dist/types/src/components/SheetContainer.d.ts.map +1 -1
  89. package/dist/types/src/components/Toolbar/Toolbar.d.ts +19 -3
  90. package/dist/types/src/components/Toolbar/Toolbar.d.ts.map +1 -1
  91. package/dist/types/src/components/Toolbar/Toolbar.stories.d.ts +18 -13
  92. package/dist/types/src/components/Toolbar/Toolbar.stories.d.ts.map +1 -1
  93. package/dist/types/src/components/index.d.ts +2 -2
  94. package/dist/types/src/components/index.d.ts.map +1 -1
  95. package/dist/types/src/defs/index.d.ts +3 -0
  96. package/dist/types/src/defs/index.d.ts.map +1 -0
  97. package/dist/types/src/{model → defs}/types.d.ts +8 -3
  98. package/dist/types/src/defs/types.d.ts.map +1 -0
  99. package/dist/types/src/defs/types.test.d.ts.map +1 -0
  100. package/dist/types/src/defs/util.d.ts +43 -0
  101. package/dist/types/src/defs/util.d.ts.map +1 -0
  102. package/dist/types/src/extensions/compute.d.ts +5 -0
  103. package/dist/types/src/extensions/compute.d.ts.map +1 -0
  104. package/dist/types/src/extensions/compute.stories.d.ts +26 -0
  105. package/dist/types/src/extensions/compute.stories.d.ts.map +1 -0
  106. package/dist/types/src/extensions/index.d.ts +2 -0
  107. package/dist/types/src/extensions/index.d.ts.map +1 -0
  108. package/dist/types/src/{components/ComputeGraph → graph}/async-function.d.ts +1 -1
  109. package/dist/types/src/graph/async-function.d.ts.map +1 -0
  110. package/dist/types/src/graph/compute-graph.browser.test.d.ts +2 -0
  111. package/dist/types/src/graph/compute-graph.browser.test.d.ts.map +1 -0
  112. package/dist/types/src/graph/compute-graph.d.ts +81 -0
  113. package/dist/types/src/graph/compute-graph.d.ts.map +1 -0
  114. package/dist/types/src/graph/compute-graph.stories.d.ts +10 -0
  115. package/dist/types/src/graph/compute-graph.stories.d.ts.map +1 -0
  116. package/dist/types/src/graph/compute-node.d.ts +19 -0
  117. package/dist/types/src/graph/compute-node.d.ts.map +1 -0
  118. package/dist/types/src/{components/ComputeGraph/custom.d.ts → graph/custom-function.d.ts} +1 -1
  119. package/dist/types/src/graph/custom-function.d.ts.map +1 -0
  120. package/dist/types/src/graph/edge-function.d.ts.map +1 -0
  121. package/dist/types/src/{model/functions.d.ts → graph/function-defs.d.ts} +1 -1
  122. package/dist/types/src/graph/function-defs.d.ts.map +1 -0
  123. package/dist/types/src/graph/hyperformula.test.d.ts +2 -0
  124. package/dist/types/src/graph/hyperformula.test.d.ts.map +1 -0
  125. package/dist/types/src/graph/index.d.ts +4 -0
  126. package/dist/types/src/graph/index.d.ts.map +1 -0
  127. package/dist/types/src/graph/util.d.ts +2 -0
  128. package/dist/types/src/graph/util.d.ts.map +1 -0
  129. package/dist/types/src/hooks/hooks.stories.d.ts +11 -0
  130. package/dist/types/src/hooks/hooks.stories.d.ts.map +1 -0
  131. package/dist/types/src/hooks/index.d.ts +4 -0
  132. package/dist/types/src/hooks/index.d.ts.map +1 -0
  133. package/dist/types/src/hooks/useComputeGraph.d.ts +7 -0
  134. package/dist/types/src/hooks/useComputeGraph.d.ts.map +1 -0
  135. package/dist/types/src/hooks/useFormattingModel.d.ts +3 -0
  136. package/dist/types/src/hooks/useFormattingModel.d.ts.map +1 -0
  137. package/dist/types/src/hooks/useSheetModel.d.ts +8 -0
  138. package/dist/types/src/hooks/useSheetModel.d.ts.map +1 -0
  139. package/dist/types/src/meta.d.ts +1 -4
  140. package/dist/types/src/meta.d.ts.map +1 -1
  141. package/dist/types/src/model/formatting-model.d.ts +16 -0
  142. package/dist/types/src/model/formatting-model.d.ts.map +1 -0
  143. package/dist/types/src/model/index.d.ts +2 -3
  144. package/dist/types/src/model/index.d.ts.map +1 -1
  145. package/dist/types/src/model/{model.d.ts → sheet-model.d.ts} +9 -64
  146. package/dist/types/src/model/sheet-model.d.ts.map +1 -0
  147. package/dist/types/src/sanity.test.d.ts +2 -0
  148. package/dist/types/src/sanity.test.d.ts.map +1 -0
  149. package/dist/types/src/testing/index.d.ts +2 -0
  150. package/dist/types/src/testing/index.d.ts.map +1 -0
  151. package/dist/types/src/testing/testing.d.ts +9 -0
  152. package/dist/types/src/testing/testing.d.ts.map +1 -0
  153. package/dist/types/src/translations.d.ts +17 -12
  154. package/dist/types/src/translations.d.ts.map +1 -1
  155. package/dist/types/src/types.d.ts +83 -3
  156. package/dist/types/src/types.d.ts.map +1 -1
  157. package/dist/vendor/hyperformula.mjs +37145 -0
  158. package/package.json +48 -41
  159. package/src/SheetPlugin.tsx +43 -70
  160. package/src/components/CellEditor/CellEditor.stories.tsx +4 -3
  161. package/src/components/CellEditor/CellEditor.tsx +59 -9
  162. package/src/components/CellEditor/extension.test.ts +4 -5
  163. package/src/components/CellEditor/extension.ts +1 -3
  164. package/src/components/ComputeGraph/ComputeGraphContextProvider.tsx +20 -0
  165. package/src/components/ComputeGraph/index.ts +1 -3
  166. package/src/components/GridSheet/GridSheet.stories.tsx +35 -0
  167. package/src/components/GridSheet/GridSheet.tsx +153 -0
  168. package/src/components/GridSheet/util.ts +89 -0
  169. package/src/components/Sheet/Sheet.stories.tsx +45 -82
  170. package/src/components/Sheet/Sheet.tsx +57 -18
  171. package/src/components/Sheet/decorations.ts +62 -0
  172. package/src/components/Sheet/grid.ts +3 -3
  173. package/src/components/Sheet/nav.ts +19 -19
  174. package/src/components/Sheet/sheet-context.tsx +16 -78
  175. package/src/components/Sheet/threads.tsx +205 -0
  176. package/src/components/SheetContainer.tsx +73 -19
  177. package/src/components/Toolbar/Toolbar.tsx +53 -12
  178. package/src/components/index.ts +1 -0
  179. package/src/defs/index.ts +6 -0
  180. package/src/{model → defs}/types.test.ts +8 -9
  181. package/src/{model → defs}/types.ts +23 -14
  182. package/src/defs/util.ts +135 -0
  183. package/src/extensions/compute.stories.tsx +151 -0
  184. package/src/extensions/compute.ts +98 -0
  185. package/src/extensions/index.ts +5 -0
  186. package/src/{components/ComputeGraph → graph}/async-function.ts +3 -1
  187. package/src/graph/compute-graph.browser.test.ts +104 -0
  188. package/src/graph/compute-graph.stories.tsx +92 -0
  189. package/src/graph/compute-graph.ts +290 -0
  190. package/src/graph/compute-node.ts +51 -0
  191. package/src/{components/ComputeGraph/custom.ts → graph/custom-function.ts} +2 -6
  192. package/src/{components/ComputeGraph → graph}/edge-function.ts +2 -1
  193. package/src/graph/hyperformula.test.ts +15 -0
  194. package/src/graph/index.ts +7 -0
  195. package/src/graph/util.ts +8 -0
  196. package/src/hooks/hooks.stories.tsx +50 -0
  197. package/src/hooks/index.ts +7 -0
  198. package/src/hooks/useComputeGraph.ts +20 -0
  199. package/src/hooks/useFormattingModel.ts +11 -0
  200. package/src/hooks/useSheetModel.ts +43 -0
  201. package/src/meta.tsx +1 -5
  202. package/src/{components/Sheet/formatting.ts → model/formatting-model.ts} +20 -13
  203. package/src/model/index.ts +2 -3
  204. package/src/model/sheet-model.ts +399 -0
  205. package/src/sanity.test.ts +40 -0
  206. package/src/testing/index.ts +5 -0
  207. package/src/testing/testing.tsx +66 -0
  208. package/src/translations.ts +6 -1
  209. package/src/types.ts +30 -5
  210. package/dist/lib/browser/SheetContainer-U4H5D34A.mjs.map +0 -7
  211. package/dist/lib/browser/chunk-APHOLYUB.mjs +0 -175
  212. package/dist/lib/browser/chunk-APHOLYUB.mjs.map +0 -7
  213. package/dist/lib/browser/chunk-D5AGLXJP.mjs.map +0 -7
  214. package/dist/lib/browser/chunk-FUAGSXA4.mjs.map +0 -7
  215. package/dist/lib/browser/chunk-JRL5LGCE.mjs.map +0 -7
  216. package/dist/lib/browser/chunk-NU4PBN33.mjs +0 -8
  217. package/dist/lib/browser/chunk-NU4PBN33.mjs.map +0 -7
  218. package/dist/lib/browser/testing.mjs +0 -92
  219. package/dist/lib/browser/testing.mjs.map +0 -7
  220. package/dist/lib/node/SheetContainer-AXQV3ZT5.cjs.map +0 -7
  221. package/dist/lib/node/chunk-5KKJ4NPP.cjs.map +0 -7
  222. package/dist/lib/node/chunk-BJ6ZD7MN.cjs.map +0 -7
  223. package/dist/lib/node/chunk-CN3RPESU.cjs +0 -202
  224. package/dist/lib/node/chunk-CN3RPESU.cjs.map +0 -7
  225. package/dist/lib/node/chunk-DSYKOI4E.cjs.map +0 -7
  226. package/dist/lib/node/chunk-PYXHNAAK.cjs +0 -40
  227. package/dist/lib/node/chunk-PYXHNAAK.cjs.map +0 -7
  228. package/dist/lib/node/testing.cjs +0 -111
  229. package/dist/lib/node/testing.cjs.map +0 -7
  230. package/dist/types/src/components/ComputeGraph/async-function.d.ts.map +0 -1
  231. package/dist/types/src/components/ComputeGraph/custom.d.ts.map +0 -1
  232. package/dist/types/src/components/ComputeGraph/edge-function.d.ts.map +0 -1
  233. package/dist/types/src/components/ComputeGraph/graph-context.d.ts +0 -12
  234. package/dist/types/src/components/ComputeGraph/graph-context.d.ts.map +0 -1
  235. package/dist/types/src/components/ComputeGraph/graph.browser.test.d.ts +0 -2
  236. package/dist/types/src/components/ComputeGraph/graph.browser.test.d.ts.map +0 -1
  237. package/dist/types/src/components/ComputeGraph/graph.d.ts +0 -26
  238. package/dist/types/src/components/ComputeGraph/graph.d.ts.map +0 -1
  239. package/dist/types/src/components/Sheet/formatting.d.ts +0 -14
  240. package/dist/types/src/components/Sheet/formatting.d.ts.map +0 -1
  241. package/dist/types/src/model/functions.d.ts.map +0 -1
  242. package/dist/types/src/model/model.browser.test.d.ts +0 -2
  243. package/dist/types/src/model/model.browser.test.d.ts.map +0 -1
  244. package/dist/types/src/model/model.d.ts.map +0 -1
  245. package/dist/types/src/model/types.d.ts.map +0 -1
  246. package/dist/types/src/model/types.test.d.ts.map +0 -1
  247. package/dist/types/src/model/util.d.ts +0 -15
  248. package/dist/types/src/model/util.d.ts.map +0 -1
  249. package/dist/types/src/testing.d.ts +0 -9
  250. package/dist/types/src/testing.d.ts.map +0 -1
  251. package/src/components/ComputeGraph/graph-context.tsx +0 -50
  252. package/src/components/ComputeGraph/graph.browser.test.ts +0 -50
  253. package/src/components/ComputeGraph/graph.ts +0 -62
  254. package/src/model/model.browser.test.ts +0 -100
  255. package/src/model/model.ts +0 -550
  256. package/src/model/util.ts +0 -36
  257. package/src/testing.ts +0 -50
  258. /package/dist/types/src/{model → defs}/types.test.d.ts +0 -0
  259. /package/dist/types/src/{components/ComputeGraph → graph}/edge-function.d.ts +0 -0
  260. /package/src/{model/functions.ts → graph/function-defs.ts} +0 -0
@@ -0,0 +1,153 @@
1
+ //
2
+ // Copyright 2024 DXOS.org
3
+ //
4
+
5
+ import React, { useCallback, useMemo, useRef } from 'react';
6
+
7
+ import { type Space } from '@dxos/client/echo';
8
+ import {
9
+ type DxGridElement,
10
+ Grid,
11
+ type GridContentProps,
12
+ type GridScopedProps,
13
+ useGridContext,
14
+ } from '@dxos/react-ui-grid';
15
+
16
+ import { dxGridCellIndexToSheetCellAddress, useSheetModelDxGridProps } from './util';
17
+ import { rangeToA1Notation, type CellRange } from '../../defs';
18
+ import { useFormattingModel, useSheetModel, type UseSheetModelOptions } from '../../hooks';
19
+ import { type SheetModel, type FormattingModel } from '../../model';
20
+ import { type SheetType } from '../../types';
21
+ import {
22
+ CellEditor,
23
+ type CellEditorProps,
24
+ type CellRangeNotifier,
25
+ editorKeys,
26
+ type EditorKeysProps,
27
+ rangeExtension,
28
+ sheetExtension,
29
+ } from '../CellEditor';
30
+
31
+ const GridSheetCellEditor = ({
32
+ model,
33
+ extension,
34
+ __gridScope,
35
+ }: GridScopedProps<Pick<CellEditorProps, 'extension'> & { model: SheetModel }>) => {
36
+ const { id, editing, setEditing, editBox } = useGridContext('GridSheetCellEditor', __gridScope);
37
+ const cell = dxGridCellIndexToSheetCellAddress(editing);
38
+
39
+ return editing ? (
40
+ <CellEditor
41
+ variant='grid'
42
+ value={editing.initialContent ?? (cell ? model.getCellText(cell) : undefined)}
43
+ autoFocus
44
+ box={editBox}
45
+ onBlur={() => setEditing(null)}
46
+ extension={extension}
47
+ gridId={id}
48
+ />
49
+ ) : null;
50
+ };
51
+
52
+ const sheetRowDefault = { size: 32, resizeable: true };
53
+ const sheetColDefault = { size: 180, resizeable: true };
54
+
55
+ const GridSheetImpl = ({
56
+ model,
57
+ formatting,
58
+ __gridScope,
59
+ }: GridScopedProps<{ model: SheetModel; formatting: FormattingModel }>) => {
60
+ const { editing, setEditing } = useGridContext('GridSheetCellEditor', __gridScope);
61
+ const dxGrid = useRef<DxGridElement | null>(null);
62
+ const rangeNotifier = useRef<CellRangeNotifier>();
63
+
64
+ // TODO(burdon): Validate formula before closing: hf.validateFormula();
65
+ const handleClose = useCallback<NonNullable<EditorKeysProps['onClose']> | NonNullable<EditorKeysProps['onNav']>>(
66
+ (value, { key, shift }) => {
67
+ if (value !== undefined) {
68
+ model.setValue(dxGridCellIndexToSheetCellAddress(editing)!, value);
69
+ }
70
+ setEditing(null);
71
+ const axis = ['Enter', 'ArrowUp', 'ArrowDown'].includes(key)
72
+ ? 'row'
73
+ : ['Tab', 'ArrowLeft', 'ArrowRight'].includes(key)
74
+ ? 'col'
75
+ : undefined;
76
+ const delta = key.startsWith('Arrow') ? (['ArrowUp', 'ArrowLeft'].includes(key) ? -1 : 1) : shift ? -1 : 1;
77
+ dxGrid.current?.refocus(axis, delta);
78
+ },
79
+ [model, editing, setEditing],
80
+ );
81
+
82
+ const handleAxisResize = useCallback<NonNullable<GridContentProps['onAxisResize']>>(
83
+ ({ axis, size, index: numericIndex }) => {
84
+ if (axis === 'row') {
85
+ const rowId = model.sheet.rows[parseInt(numericIndex)];
86
+ model.sheet.rowMeta[rowId] ??= {};
87
+ model.sheet.rowMeta[rowId].size = size;
88
+ } else {
89
+ const columnId = model.sheet.columns[parseInt(numericIndex)];
90
+ model.sheet.columnMeta[columnId] ??= {};
91
+ model.sheet.columnMeta[columnId].size = size;
92
+ }
93
+ },
94
+ [model],
95
+ );
96
+
97
+ const handleSelect = useCallback<NonNullable<GridContentProps['onSelect']>>(
98
+ ({ minCol, maxCol, minRow, maxRow }) => {
99
+ if (editing) {
100
+ const range: CellRange = { from: { col: minCol, row: minRow } };
101
+ if (minCol !== maxCol || minRow !== maxRow) {
102
+ range.to = { col: maxCol, row: maxRow };
103
+ }
104
+ // Update range selection in formula.
105
+ rangeNotifier.current?.(rangeToA1Notation(range));
106
+ }
107
+ },
108
+ [editing],
109
+ );
110
+
111
+ const { cells, columns, rows } = useSheetModelDxGridProps(model, formatting);
112
+
113
+ const extension = useMemo(
114
+ () => [
115
+ editorKeys({ onClose: handleClose, ...(editing?.initialContent && { onNav: handleClose }) }),
116
+ sheetExtension({ functions: model.graph.getFunctions() }),
117
+ rangeExtension((fn) => (rangeNotifier.current = fn)),
118
+ ],
119
+ [model, handleClose, editing],
120
+ );
121
+
122
+ return (
123
+ <>
124
+ <GridSheetCellEditor model={model} extension={extension} />
125
+ <Grid.Content
126
+ cells={cells}
127
+ columns={columns}
128
+ rows={rows}
129
+ onAxisResize={handleAxisResize}
130
+ onSelect={handleSelect}
131
+ rowDefault={sheetRowDefault}
132
+ columnDefault={sheetColDefault}
133
+ ref={dxGrid}
134
+ />
135
+ </>
136
+ );
137
+ };
138
+
139
+ export type GridSheetProps = { space?: Space; sheet?: SheetType } & UseSheetModelOptions;
140
+
141
+ export const GridSheet = ({ space, sheet, ...options }: GridSheetProps) => {
142
+ const model = useSheetModel(space, sheet, options);
143
+ const formatting = useFormattingModel(model);
144
+ if (!model || !formatting) {
145
+ return null;
146
+ }
147
+
148
+ return (
149
+ <Grid.Root id={model.id}>
150
+ <GridSheetImpl model={model} formatting={formatting} />
151
+ </Grid.Root>
152
+ );
153
+ };
@@ -0,0 +1,89 @@
1
+ //
2
+ // Copyright 2024 DXOS.org
3
+ //
4
+
5
+ import { useEffect, useState } from 'react';
6
+
7
+ import { createDocAccessor } from '@dxos/react-client/echo';
8
+ import { type GridEditing, type GridContentProps } from '@dxos/react-ui-grid';
9
+ import { mx } from '@dxos/react-ui-theme';
10
+
11
+ import { addressFromIndex, type CellAddress } from '../../defs';
12
+ import { type SheetModel, type FormattingModel } from '../../model';
13
+
14
+ export const dxGridCellIndexToSheetCellAddress = (gridEditing: GridEditing): CellAddress | null => {
15
+ if (!gridEditing) {
16
+ return null;
17
+ }
18
+ const [colStr, rowStr] = gridEditing.index.split(',');
19
+ return {
20
+ col: parseInt(colStr),
21
+ row: parseInt(rowStr),
22
+ };
23
+ };
24
+
25
+ const createDxGridCells = (model: SheetModel, formatting: FormattingModel) => {
26
+ return Object.keys(model.sheet.cells).reduce((acc: NonNullable<GridContentProps['cells']>, sheetCellIndex) => {
27
+ const address = addressFromIndex(model.sheet, sheetCellIndex);
28
+ const cell = formatting.getFormatting(address);
29
+ if (cell.value) {
30
+ acc[`${address.col},${address.row}`] = { value: cell.value, className: mx(cell.classNames) };
31
+ }
32
+ return acc;
33
+ }, {});
34
+ };
35
+
36
+ const createDxGridColumns = (model: SheetModel): GridContentProps['columns'] => {
37
+ return model.sheet.columns.reduce((acc: NonNullable<GridContentProps['columns']>, columnId, numericIndex) => {
38
+ if (model.sheet.columnMeta[columnId] && model.sheet.columnMeta[columnId].size) {
39
+ acc[numericIndex] = { size: model.sheet.columnMeta[columnId].size, resizeable: true };
40
+ }
41
+ return acc;
42
+ }, {});
43
+ };
44
+
45
+ const createDxGridRows = (model: SheetModel): GridContentProps['rows'] => {
46
+ return model.sheet.rows.reduce((acc: NonNullable<GridContentProps['rows']>, rowId, numericIndex) => {
47
+ if (model.sheet.rowMeta[rowId] && model.sheet.rowMeta[rowId].size) {
48
+ acc[numericIndex] = { size: model.sheet.rowMeta[rowId].size, resizeable: true };
49
+ }
50
+ return acc;
51
+ }, {});
52
+ };
53
+
54
+ export const useSheetModelDxGridProps = (
55
+ model: SheetModel,
56
+ formatting: FormattingModel,
57
+ ): Pick<GridContentProps, 'cells' | 'columns' | 'rows'> => {
58
+ const [dxGridCells, setDxGridCells] = useState<GridContentProps['cells']>(createDxGridCells(model, formatting));
59
+ const [dxGridColumns, setDxGridColumns] = useState<GridContentProps['columns']>(createDxGridColumns(model));
60
+ const [dxGridRows, setDxGridRows] = useState<GridContentProps['rows']>(createDxGridColumns(model));
61
+
62
+ useEffect(() => {
63
+ const cellsAccessor = createDocAccessor(model.sheet, ['cells']);
64
+ const handleCellsUpdate = () => {
65
+ setDxGridCells(createDxGridCells(model, formatting));
66
+ };
67
+ cellsAccessor.handle.addListener('change', handleCellsUpdate);
68
+ return () => cellsAccessor.handle.removeListener('change', handleCellsUpdate);
69
+ }, [model, formatting]);
70
+
71
+ useEffect(() => {
72
+ const columnMetaAccessor = createDocAccessor(model.sheet, ['columnMeta']);
73
+ const rowMetaAccessor = createDocAccessor(model.sheet, ['rowMeta']);
74
+ const handleColumnMetaUpdate = () => {
75
+ setDxGridColumns(createDxGridColumns(model));
76
+ };
77
+ const handleRowMetaUpdate = () => {
78
+ setDxGridRows(createDxGridRows(model));
79
+ };
80
+ columnMetaAccessor.handle.addListener('change', handleColumnMetaUpdate);
81
+ rowMetaAccessor.handle.addListener('change', handleRowMetaUpdate);
82
+ return () => {
83
+ columnMetaAccessor.handle.removeListener('change', handleColumnMetaUpdate);
84
+ rowMetaAccessor.handle.removeListener('change', handleRowMetaUpdate);
85
+ };
86
+ }, [model]);
87
+
88
+ return { cells: dxGridCells, columns: dxGridColumns, rows: dxGridRows };
89
+ };
@@ -4,31 +4,33 @@
4
4
 
5
5
  import '@dxos-theme';
6
6
 
7
- import { type Decorator } from '@storybook/react';
8
- import React, { useContext, useEffect, useState } from 'react';
7
+ import React, { useState } from 'react';
9
8
 
10
- import { Client } from '@dxos/client';
11
- import { type EchoReactiveObject } from '@dxos/echo-schema';
12
9
  import { log } from '@dxos/log';
13
- import { getSpace, type Space } from '@dxos/react-client/echo';
10
+ import { type Space, useSpace } from '@dxos/react-client/echo';
11
+ import { withClientProvider } from '@dxos/react-client/testing';
14
12
  import { Button } from '@dxos/react-ui';
15
13
  import { mx } from '@dxos/react-ui-theme';
16
- import { withTheme, withLayout } from '@dxos/storybook-utils';
14
+ import { withLayout, withTheme } from '@dxos/storybook-utils';
17
15
 
18
16
  import { Sheet } from './Sheet';
19
17
  import { type SizeMap } from './grid';
20
18
  import { useSheetContext } from './sheet-context';
21
- import { createTestSheet, testSheetName } from '../../testing';
22
- import { ValueTypeEnum, SheetType } from '../../types';
23
- import { type ComputeGraph, createComputeGraph } from '../ComputeGraph';
24
- // TODO(wittjosiah): Refactor. This is not exported from ./components due to depending on ECHO.
25
- import { ComputeGraphContext, ComputeGraphContextProvider, useComputeGraph } from '../ComputeGraph/graph-context';
19
+ import { addressToIndex, rangeToIndex } from '../../defs';
20
+ import { useComputeGraph } from '../../hooks';
21
+ import { useTestSheet, withGraphDecorator } from '../../testing';
22
+ import { SheetType, ValueTypeEnum } from '../../types';
26
23
  import { Toolbar, type ToolbarActionHandler } from '../Toolbar';
27
24
 
28
25
  // TODO(burdon): Allow toolbar to access sheet context; provide state for current cursor/range.
29
26
  const SheetWithToolbar = ({ debug, space }: { debug?: boolean; space: Space }) => {
30
27
  const { model, cursor, range } = useSheetContext();
31
28
 
29
+ const graph = useComputeGraph(space);
30
+ const handleRefresh = () => {
31
+ graph?.refresh();
32
+ };
33
+
32
34
  // TODO(burdon): Factor out.
33
35
  const handleAction: ToolbarActionHandler = ({ type }) => {
34
36
  log.info('action', { type, cursor, range });
@@ -36,7 +38,7 @@ const SheetWithToolbar = ({ debug, space }: { debug?: boolean; space: Space }) =
36
38
  return;
37
39
  }
38
40
 
39
- const idx = range ? model.rangeToIndex(range) : model.addressToIndex(cursor);
41
+ const idx = range ? rangeToIndex(model.sheet, range) : addressToIndex(model.sheet, cursor);
40
42
  model.sheet.formatting[idx] ??= {};
41
43
  const format = model.sheet.formatting[idx];
42
44
 
@@ -75,14 +77,12 @@ const SheetWithToolbar = ({ debug, space }: { debug?: boolean; space: Space }) =
75
77
  format.precision = 2;
76
78
  break;
77
79
  }
80
+ case 'comment': {
81
+ break;
82
+ }
78
83
  }
79
84
  };
80
85
 
81
- const graph = useComputeGraph(space);
82
- const handleRefresh = () => {
83
- graph.refresh();
84
- };
85
-
86
86
  return (
87
87
  <div className='flex flex-col overflow-hidden'>
88
88
  <Toolbar.Root onAction={handleAction}>
@@ -99,56 +99,43 @@ const SheetWithToolbar = ({ debug, space }: { debug?: boolean; space: Space }) =
99
99
  );
100
100
  };
101
101
 
102
- const withGraphDecorator: Decorator = (Story) => {
103
- const [graphs, setGraphs] = useState<Record<string, ComputeGraph>>({});
104
-
105
- const setGraph = (key: string, graph: ComputeGraph) => {
106
- if (!graph.hf.doesSheetExist(testSheetName)) {
107
- const sheetName = graph.hf.addSheet(testSheetName);
108
- const sheet = graph.hf.getSheetId(sheetName)!;
109
- graph.hf.setCellContents({ sheet, col: 0, row: 0 }, Math.random());
110
- }
111
-
112
- setGraphs((graphs) => ({ ...graphs, [key]: graph }));
113
- };
114
-
115
- return (
116
- <ComputeGraphContextProvider graphs={graphs} setGraph={setGraph}>
117
- <Story />
118
- </ComputeGraphContextProvider>
119
- );
120
- };
121
-
122
102
  export default {
123
103
  title: 'plugin-sheet/Sheet',
124
104
  component: Sheet,
125
- decorators: [withTheme, withLayout({ fullscreen: true, tooltips: true, classNames: 'inset-4' }), withGraphDecorator],
105
+ decorators: [
106
+ withClientProvider({ types: [SheetType], createIdentity: true }),
107
+ withGraphDecorator,
108
+ withTheme,
109
+ withLayout({ fullscreen: true, tooltips: true, classNames: 'inset-4' }),
110
+ ],
126
111
  };
127
112
 
128
113
  export const Default = () => {
129
114
  const [debug, setDebug] = useState(false);
130
- const sheet = useTestSheet();
131
- const space = getSpace(sheet);
132
- if (!sheet || !space) {
115
+ const space = useSpace();
116
+ const graph = useComputeGraph(space);
117
+ const sheet = useTestSheet(space, graph);
118
+ if (!space || !sheet) {
133
119
  return null;
134
120
  }
135
121
 
136
122
  return (
137
- <Sheet.Root sheet={sheet} space={space} onInfo={() => setDebug((debug) => !debug)}>
123
+ <Sheet.Root space={space} sheet={sheet} onInfo={() => setDebug((debug) => !debug)}>
138
124
  <SheetWithToolbar debug={debug} space={space} />
139
125
  </Sheet.Root>
140
126
  );
141
127
  };
142
128
 
143
129
  export const Debug = () => {
144
- const sheet = useTestSheet();
145
- const space = getSpace(sheet);
130
+ const space = useSpace();
131
+ const graph = useComputeGraph(space);
132
+ const sheet = useTestSheet(space, graph);
146
133
  if (!sheet || !space) {
147
134
  return null;
148
135
  }
149
136
 
150
137
  return (
151
- <Sheet.Root sheet={sheet} space={space}>
138
+ <Sheet.Root space={space} sheet={sheet}>
152
139
  <Sheet.Main />
153
140
  <Sheet.Debug />
154
141
  </Sheet.Root>
@@ -157,14 +144,15 @@ export const Debug = () => {
157
144
 
158
145
  export const Rows = () => {
159
146
  const [rowSizes, setRowSizes] = useState<SizeMap>({});
160
- const sheet = useTestSheet();
161
- const space = getSpace(sheet);
147
+ const space = useSpace();
148
+ const graph = useComputeGraph(space);
149
+ const sheet = useTestSheet(space, graph);
162
150
  if (!sheet || !space) {
163
151
  return null;
164
152
  }
165
153
 
166
154
  return (
167
- <Sheet.Root sheet={sheet} space={space}>
155
+ <Sheet.Root space={space} sheet={sheet}>
168
156
  <Sheet.Rows
169
157
  rows={sheet.rows}
170
158
  sizes={rowSizes}
@@ -176,14 +164,15 @@ export const Rows = () => {
176
164
 
177
165
  export const Columns = () => {
178
166
  const [columnSizes, setColumnSizes] = useState<SizeMap>({});
179
- const sheet = useTestSheet();
180
- const space = getSpace(sheet);
167
+ const space = useSpace();
168
+ const graph = useComputeGraph(space);
169
+ const sheet = useTestSheet(space, graph);
181
170
  if (!sheet || !space) {
182
171
  return null;
183
172
  }
184
173
 
185
174
  return (
186
- <Sheet.Root sheet={sheet} space={space}>
175
+ <Sheet.Root space={space} sheet={sheet}>
187
176
  <Sheet.Columns
188
177
  columns={sheet.columns}
189
178
  sizes={columnSizes}
@@ -194,18 +183,19 @@ export const Columns = () => {
194
183
  };
195
184
 
196
185
  export const Main = () => {
197
- const sheet = useTestSheet();
198
- const space = getSpace(sheet);
186
+ const space = useSpace();
187
+ const graph = useComputeGraph(space);
188
+ const sheet = useTestSheet(space, graph);
199
189
  if (!sheet || !space) {
200
190
  return null;
201
191
  }
202
192
 
203
193
  return (
204
- <Sheet.Root sheet={sheet} space={space}>
194
+ <Sheet.Root space={space} sheet={sheet}>
205
195
  <Sheet.Grid
206
196
  size={{
207
197
  numRows: 50,
208
- numColumns: 26,
198
+ numCols: 26,
209
199
  }}
210
200
  rows={sheet.rows}
211
201
  columns={sheet.columns}
@@ -258,30 +248,3 @@ export const GridLayout = () => {
258
248
  const Cell = ({ className, label }: { className?: string; label: string }) => (
259
249
  <div className={mx('flex items-center justify-center border', className)}>{label}</div>
260
250
  );
261
-
262
- const useTestSheet = () => {
263
- const { graphs, setGraph } = useContext(ComputeGraphContext);
264
- const [sheet, setSheet] = useState<EchoReactiveObject<SheetType>>();
265
- useEffect(() => {
266
- const t = setTimeout(async () => {
267
- const client = new Client();
268
- await client.initialize();
269
- await client.halo.createIdentity();
270
- const space = await client.spaces.create();
271
- client.addTypes([SheetType]);
272
-
273
- const graph = graphs[space.id] ?? createComputeGraph();
274
- if (!graphs[space.id]) {
275
- setGraph(space.id, graph);
276
- }
277
-
278
- const sheet = await createTestSheet({ graph });
279
- space.db.add(sheet);
280
- setSheet(sheet);
281
- });
282
-
283
- return () => clearTimeout(t);
284
- }, []);
285
-
286
- return sheet;
287
- };
@@ -60,6 +60,7 @@ import {
60
60
  } from './grid';
61
61
  import { type GridSize, handleArrowNav, handleNav, useRangeSelect } from './nav';
62
62
  import { type SheetContextProps, SheetContextProvider, useSheetContext } from './sheet-context';
63
+ import { useThreads } from './threads';
63
64
  import { getRectUnion, getRelativeClientRect, scrollIntoView } from './util';
64
65
  import {
65
66
  type CellIndex,
@@ -68,7 +69,9 @@ import {
68
69
  columnLetter,
69
70
  posEquals,
70
71
  rangeToA1Notation,
71
- } from '../../model';
72
+ addressToIndex,
73
+ addressFromIndex,
74
+ } from '../../defs';
72
75
  import {
73
76
  CellEditor,
74
77
  type CellRangeNotifier,
@@ -135,12 +138,16 @@ const SheetRoot = ({ children, ...props }: PropsWithChildren<SheetContextProps>)
135
138
 
136
139
  type SheetMainProps = ThemedClassName<Partial<GridSize>>;
137
140
 
138
- const SheetMain = forwardRef<HTMLDivElement, SheetMainProps>(({ classNames, numRows, numColumns }, forwardRef) => {
141
+ const SheetMain = forwardRef<HTMLDivElement, SheetMainProps>(({ classNames, numRows, numCols }, forwardRef) => {
139
142
  const { model, cursor, setCursor, setRange, setEditing } = useSheetContext();
140
143
 
141
144
  // Scrolling.
142
145
  const { rowsRef, columnsRef, contentRef } = useScrollHandlers();
143
146
 
147
+ // Threads.
148
+ // TODO(Zan): Move this to an extension once we have an extension model.
149
+ useThreads();
150
+
144
151
  //
145
152
  // Order of Row/columns.
146
153
  //
@@ -170,21 +177,21 @@ const SheetMain = forwardRef<HTMLDivElement, SheetMainProps>(({ classNames, numR
170
177
  }, [rows, columns]);
171
178
 
172
179
  const handleMoveRows: SheetRowsProps['onMove'] = (from, to, num = 1) => {
173
- const cursorIdx = cursor ? model.addressToIndex(cursor) : undefined;
180
+ const cursorIdx = cursor ? addressToIndex(model.sheet, cursor) : undefined;
174
181
  const [rows] = model.sheet.rows.splice(from, num);
175
182
  model.sheet.rows.splice(to, 0, rows);
176
183
  if (cursorIdx) {
177
- setCursor(model.addressFromIndex(cursorIdx));
184
+ setCursor(addressFromIndex(model.sheet, cursorIdx));
178
185
  }
179
186
  setRows([...model.sheet.rows]);
180
187
  };
181
188
 
182
189
  const handleMoveColumns: SheetColumnsProps['onMove'] = (from, to, num = 1) => {
183
- const cursorIdx = cursor ? model.addressToIndex(cursor) : undefined;
190
+ const cursorIdx = cursor ? addressToIndex(model.sheet, cursor) : undefined;
184
191
  const columns = model.sheet.columns.splice(from, num);
185
192
  model.sheet.columns.splice(to, 0, ...columns);
186
193
  if (cursorIdx) {
187
- setCursor(model.addressFromIndex(cursorIdx));
194
+ setCursor(addressFromIndex(model.sheet, cursorIdx));
188
195
  }
189
196
  setColumns([...model.sheet.columns]);
190
197
  };
@@ -256,8 +263,8 @@ const SheetMain = forwardRef<HTMLDivElement, SheetMainProps>(({ classNames, numR
256
263
  ref={columnsRef}
257
264
  columns={columns}
258
265
  sizes={columnSizes}
259
- selected={cursor?.column}
260
- onSelect={(column) => setCursor(cursor?.column === column ? undefined : { row: -1, column })}
266
+ selected={cursor?.col}
267
+ onSelect={(col) => setCursor(cursor?.col === col ? undefined : { row: -1, col })}
261
268
  onResize={handleResizeColumn}
262
269
  onMove={handleMoveColumns}
263
270
  />
@@ -267,13 +274,13 @@ const SheetMain = forwardRef<HTMLDivElement, SheetMainProps>(({ classNames, numR
267
274
  rows={rows}
268
275
  sizes={rowSizes}
269
276
  selected={cursor?.row}
270
- onSelect={(row) => setCursor(cursor?.row === row ? undefined : { row, column: -1 })}
277
+ onSelect={(row) => setCursor(cursor?.row === row ? undefined : { row, col: -1 })}
271
278
  onResize={handleResizeRow}
272
279
  onMove={handleMoveRows}
273
280
  />
274
281
  <SheetGrid
275
282
  ref={contentRef}
276
- size={{ numRows: numRows ?? rows.length, numColumns: numColumns ?? columns.length }}
283
+ size={{ numRows: numRows ?? rows.length, numCols: numCols ?? columns.length }}
277
284
  rows={rows}
278
285
  columns={columns}
279
286
  rowSizes={rowSizes}
@@ -878,11 +885,11 @@ const SheetGrid = forwardRef<HTMLDivElement, SheetGridProps>(
878
885
 
879
886
  {/* Grid cells. */}
880
887
  {rowRange.map(({ row, top, height }) => {
881
- return columnRange.map(({ column, left, width }) => {
888
+ return columnRange.map(({ col, left, width }) => {
882
889
  const style: CSSProperties = { position: 'absolute', top, left, width, height };
883
- const cell = { row, column };
890
+ const cell: CellAddress = { row, col };
884
891
  const id = addressToA1Notation(cell);
885
- const idx = model.addressToIndex(cell);
892
+ const idx = addressToIndex(model.sheet, cell);
886
893
  const active = posEquals(cursor, cell);
887
894
  if (active && editing) {
888
895
  const value = initialText.current ?? model.getCellText(cell) ?? '';
@@ -1003,16 +1010,46 @@ type SheetCellProps = {
1003
1010
  };
1004
1011
 
1005
1012
  const SheetCell = ({ id, cell, style, active, onSelect }: SheetCellProps) => {
1006
- const { formatting, editing, setRange } = useSheetContext();
1013
+ const {
1014
+ formatting,
1015
+ editing,
1016
+ setRange,
1017
+ decorations,
1018
+ model: { sheet },
1019
+ } = useSheetContext();
1007
1020
  const { value, classNames } = formatting.getFormatting(cell);
1008
1021
 
1022
+ const decorationsForCell = decorations.getDecorationsForCell(addressToIndex(sheet, cell)) ?? [];
1023
+ const decorationAddedClasses = useMemo(
1024
+ () => decorationsForCell.flatMap((d) => d.classNames ?? []),
1025
+ [decorationsForCell],
1026
+ );
1027
+ const decoratedContent = decorationsForCell.reduce(
1028
+ (children, { decorate }) => {
1029
+ if (!decorate) {
1030
+ return children;
1031
+ }
1032
+ const DecoratorComponent = decorate;
1033
+ return <DecoratorComponent>{children}</DecoratorComponent>;
1034
+ },
1035
+ <div
1036
+ role='none'
1037
+ className={mx(
1038
+ 'flex flex-grow bs-full is-full px-2 items-center truncate cursor-pointer',
1039
+ ...decorationAddedClasses,
1040
+ )}
1041
+ >
1042
+ {value}
1043
+ </div>,
1044
+ );
1045
+
1009
1046
  return (
1010
1047
  <div
1011
1048
  {...{ [`data-${CELL_DATA_KEY}`]: id }}
1012
1049
  role='cell'
1013
1050
  style={style}
1014
1051
  className={mx(
1015
- 'flex w-full h-full px-2 py-1 truncate items-center border border-gridLine cursor-pointer',
1052
+ 'border border-gridLine cursor-pointer',
1016
1053
  fragments.cell,
1017
1054
  active && ['z-20', fragments.cellSelected],
1018
1055
  classNames,
@@ -1026,7 +1063,7 @@ const SheetCell = ({ id, cell, style, active, onSelect }: SheetCellProps) => {
1026
1063
  }}
1027
1064
  onDoubleClick={() => onSelect?.(cell, true)}
1028
1065
  >
1029
- {value}
1066
+ {decoratedContent}
1030
1067
  </div>
1031
1068
  );
1032
1069
  };
@@ -1045,10 +1082,11 @@ const GridCellEditor = ({ style, value, onNav, onClose }: GridCellEditorProps) =
1045
1082
  notifier.current?.(rangeToA1Notation(range));
1046
1083
  }
1047
1084
  }, [range]);
1085
+
1048
1086
  const extension = useMemo(
1049
1087
  () => [
1050
1088
  editorKeys({ onNav, onClose }),
1051
- sheetExtension({ functions: model.functions }),
1089
+ sheetExtension({ functions: model.graph.getFunctions() }),
1052
1090
  rangeExtension((fn) => (notifier.current = fn)),
1053
1091
  ],
1054
1092
  [model],
@@ -1072,12 +1110,13 @@ const GridCellEditor = ({ style, value, onNav, onClose }: GridCellEditorProps) =
1072
1110
 
1073
1111
  const SheetStatusBar = () => {
1074
1112
  const { model, cursor, range } = useSheetContext();
1113
+
1075
1114
  let value;
1076
1115
  let isFormula = false;
1077
1116
  if (cursor) {
1078
1117
  value = model.getCellValue(cursor);
1079
1118
  if (typeof value === 'string' && value.charAt(0) === '=') {
1080
- value = model.mapFormulaBindingFromId(model.mapFormulaIndicesToRefs(value));
1119
+ value = model.graph.mapFunctionBindingFromId(model.mapFormulaIndicesToRefs(value));
1081
1120
  isFormula = true;
1082
1121
  } else if (value != null) {
1083
1122
  value = String(value);