@blocklet/editor 2.2.47 → 2.3.1

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 (51) hide show
  1. package/lib/ext/PostLinkEmbedPlugin/PostLinkNode.d.ts +2 -2
  2. package/lib/ext/PostLinkEmbedPlugin/PostLinkNode.js +3 -3
  3. package/lib/main/editor.js +3 -7
  4. package/lib/main/index.css +16 -18
  5. package/lib/main/markdown-editor/editor.js +1 -1
  6. package/lib/main/markdown-editor/transformers.js +7 -6
  7. package/lib/main/nodes/EmojiNode.d.ts +1 -2
  8. package/lib/main/nodes/EmojiNode.js +4 -9
  9. package/lib/main/nodes/EquationNode.js +14 -7
  10. package/lib/main/nodes/ImageComponent.js +2 -2
  11. package/lib/main/nodes/PlaygroundNodes.js +0 -2
  12. package/lib/main/nodes/StickyComponent.js +1 -1
  13. package/lib/main/plugins/CodeActionMenuPlugin/index.js +24 -28
  14. package/lib/main/plugins/MarkdownTransformers/index.d.ts +1 -4
  15. package/lib/main/plugins/MarkdownTransformers/index.js +48 -79
  16. package/lib/main/plugins/TableActionMenuPlugin/index.js +229 -171
  17. package/lib/main/plugins/TableCellResizer/index.css +8 -2
  18. package/lib/main/plugins/TableCellResizer/index.js +168 -120
  19. package/lib/main/plugins/TableOfContentsPlugin/index.js +2 -2
  20. package/lib/main/plugins/TablePlugin.d.ts +3 -4
  21. package/lib/main/plugins/TablePlugin.js +7 -24
  22. package/lib/main/plugins/ToolbarPlugin/index.js +0 -1
  23. package/lib/main/themes/defaultTheme.js +3 -1
  24. package/lib/main/ui/ContentEditable.d.ts +1 -4
  25. package/lib/main/ui/Modal.css +1 -1
  26. package/lib/main/ui/TextInput.d.ts +4 -3
  27. package/lib/main/ui/TextInput.js +3 -19
  28. package/package.json +23 -24
  29. package/lib/main/nodes/AutocompleteNode.d.ts +0 -34
  30. package/lib/main/nodes/AutocompleteNode.js +0 -52
  31. package/lib/main/nodes/EquationComponent.d.ts +0 -16
  32. package/lib/main/nodes/EquationComponent.js +0 -64
  33. package/lib/main/plugins/ActionsPlugin/index.d.ts +0 -11
  34. package/lib/main/plugins/ActionsPlugin/index.js +0 -129
  35. package/lib/main/plugins/AutocompletePlugin/index.d.ts +0 -10
  36. package/lib/main/plugins/AutocompletePlugin/index.js +0 -2461
  37. package/lib/main/plugins/CodeActionMenuPlugin/components/PrettierButton/index.css +0 -14
  38. package/lib/main/plugins/CodeActionMenuPlugin/components/PrettierButton/index.d.ts +0 -17
  39. package/lib/main/plugins/CodeActionMenuPlugin/components/PrettierButton/index.js +0 -95
  40. package/lib/main/plugins/EquationsPlugin/index.d.ts +0 -21
  41. package/lib/main/plugins/EquationsPlugin/index.js +0 -42
  42. package/lib/main/plugins/SpeechToTextPlugin/index.d.ts +0 -12
  43. package/lib/main/plugins/SpeechToTextPlugin/index.js +0 -87
  44. package/lib/main/ui/EquationEditor.css +0 -38
  45. package/lib/main/ui/EquationEditor.d.ts +0 -19
  46. package/lib/main/ui/EquationEditor.js +0 -26
  47. package/lib/main/ui/KatexEquationAlterer.css +0 -41
  48. package/lib/main/ui/KatexEquationAlterer.d.ts +0 -15
  49. package/lib/main/ui/KatexEquationAlterer.js +0 -34
  50. package/lib/main/ui/KatexRenderer.d.ts +0 -13
  51. package/lib/main/ui/KatexRenderer.js +0 -33
@@ -1,93 +1,125 @@
1
1
  import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import './index.css';
3
3
  import { useLexicalComposerContext } from '@lexical/react/LexicalComposerContext';
4
- import useLexicalEditable from '@lexical/react/useLexicalEditable';
5
- import { $getTableColumnIndexFromTableCellNode, $getTableNodeFromLexicalNodeOrThrow, $getTableRowIndexFromTableCellNode, $isTableCellNode, $isTableRowNode, $isTableSelection, getDOMCellFromTarget, } from '@lexical/table';
6
- import { $getNearestNodeFromDOMNode, $getSelection, COMMAND_PRIORITY_HIGH, SELECTION_CHANGE_COMMAND } from 'lexical';
7
- import { useCallback, useEffect, useMemo, useRef, useState } from 'react';
4
+ import { useLexicalEditable } from '@lexical/react/useLexicalEditable';
5
+ import { $computeTableMapSkipCellCheck, $getTableNodeFromLexicalNodeOrThrow, $getTableRowIndexFromTableCellNode, $isTableCellNode, $isTableRowNode, getDOMCellFromTarget, getTableElement, TableNode, } from '@lexical/table';
6
+ import { calculateZoomLevel, mergeRegister } from '@lexical/utils';
7
+ import { $getNearestNodeFromDOMNode, isHTMLElement } from 'lexical';
8
+ import { useCallback, useEffect, useMemo, useRef, useState, } from 'react';
8
9
  import { createPortal } from 'react-dom';
9
10
  const MIN_ROW_HEIGHT = 33;
10
- const MIN_COLUMN_WIDTH = 50;
11
+ const MIN_COLUMN_WIDTH = 92;
11
12
  function TableCellResizer({ editor }) {
12
13
  const targetRef = useRef(null);
13
14
  const resizerRef = useRef(null);
14
15
  const tableRectRef = useRef(null);
15
- const mouseStartPosRef = useRef(null);
16
- const [mouseCurrentPos, updateMouseCurrentPos] = useState(null);
16
+ const [hasTable, setHasTable] = useState(false);
17
+ const pointerStartPosRef = useRef(null);
18
+ const [pointerCurrentPos, updatePointerCurrentPos] = useState(null);
17
19
  const [activeCell, updateActiveCell] = useState(null);
18
- const [isSelectingGrid, updateIsSelectingGrid] = useState(false);
19
20
  const [draggingDirection, updateDraggingDirection] = useState(null);
20
- useEffect(() => {
21
- return editor.registerCommand(SELECTION_CHANGE_COMMAND, (payload) => {
22
- const selection = $getSelection();
23
- const isTableSelection = $isTableSelection(selection);
24
- if (isSelectingGrid !== isTableSelection) {
25
- updateIsSelectingGrid(isTableSelection);
26
- }
27
- return false;
28
- }, COMMAND_PRIORITY_HIGH);
29
- });
30
21
  const resetState = useCallback(() => {
31
22
  updateActiveCell(null);
32
23
  targetRef.current = null;
33
24
  updateDraggingDirection(null);
34
- mouseStartPosRef.current = null;
25
+ pointerStartPosRef.current = null;
35
26
  tableRectRef.current = null;
36
27
  }, []);
37
28
  useEffect(() => {
38
- const onMouseMove = (event) => {
39
- setTimeout(() => {
40
- const { target } = event;
41
- if (draggingDirection) {
42
- updateMouseCurrentPos({
43
- x: event.clientX,
44
- y: event.clientY,
45
- });
46
- return;
29
+ const tableKeys = new Set();
30
+ return mergeRegister(editor.registerMutationListener(TableNode, (nodeMutations) => {
31
+ for (const [nodeKey, mutation] of nodeMutations) {
32
+ if (mutation === 'destroyed') {
33
+ tableKeys.delete(nodeKey);
47
34
  }
48
- if (resizerRef.current && resizerRef.current.contains(target)) {
49
- return;
35
+ else {
36
+ tableKeys.add(nodeKey);
50
37
  }
51
- if (targetRef.current !== target) {
52
- targetRef.current = target;
53
- const cell = getDOMCellFromTarget(target);
54
- if (cell && activeCell !== cell) {
55
- editor.update(() => {
56
- const tableCellNode = $getNearestNodeFromDOMNode(cell.elem);
57
- if (!tableCellNode) {
58
- // throw new Error('TableCellResizer: Table cell node not found.');
59
- // eslint-disable-next-line no-console
60
- console.log('TableCellResizer: Table cell node not found.');
61
- // [!] return instead of throwing error to avoid breaking the editor (#2055)
62
- return;
63
- }
64
- const tableNode = $getTableNodeFromLexicalNodeOrThrow(tableCellNode);
65
- const tableElement = editor.getElementByKey(tableNode.getKey());
66
- if (!tableElement) {
67
- throw new Error('TableCellResizer: Table element not found.');
68
- }
69
- targetRef.current = target;
70
- tableRectRef.current = tableElement.getBoundingClientRect();
71
- updateActiveCell(cell);
72
- });
73
- }
74
- else if (cell == null) {
75
- resetState();
76
- }
38
+ }
39
+ setHasTable(tableKeys.size > 0);
40
+ }), editor.registerNodeTransform(TableNode, (tableNode) => {
41
+ if (tableNode.getColWidths()) {
42
+ return tableNode;
43
+ }
44
+ const numColumns = tableNode.getColumnCount();
45
+ const columnWidth = MIN_COLUMN_WIDTH;
46
+ tableNode.setColWidths(Array(numColumns).fill(columnWidth));
47
+ return tableNode;
48
+ }));
49
+ }, [editor]);
50
+ useEffect(() => {
51
+ if (!hasTable) {
52
+ return;
53
+ }
54
+ const onPointerMove = (event) => {
55
+ const { target } = event;
56
+ if (!isHTMLElement(target)) {
57
+ return;
58
+ }
59
+ if (draggingDirection) {
60
+ event.preventDefault();
61
+ event.stopPropagation();
62
+ updatePointerCurrentPos({
63
+ x: event.clientX,
64
+ y: event.clientY,
65
+ });
66
+ return;
67
+ }
68
+ if (resizerRef.current && resizerRef.current.contains(target)) {
69
+ return;
70
+ }
71
+ if (targetRef.current !== target) {
72
+ targetRef.current = target;
73
+ const cell = getDOMCellFromTarget(target);
74
+ if (cell && activeCell !== cell) {
75
+ editor.getEditorState().read(() => {
76
+ const tableCellNode = $getNearestNodeFromDOMNode(cell.elem);
77
+ if (!tableCellNode) {
78
+ throw new Error('TableCellResizer: Table cell node not found.');
79
+ }
80
+ const tableNode = $getTableNodeFromLexicalNodeOrThrow(tableCellNode);
81
+ const tableElement = getTableElement(tableNode, editor.getElementByKey(tableNode.getKey()));
82
+ if (!tableElement) {
83
+ throw new Error('TableCellResizer: Table element not found.');
84
+ }
85
+ targetRef.current = target;
86
+ tableRectRef.current = tableElement.getBoundingClientRect();
87
+ updateActiveCell(cell);
88
+ }, { editor });
77
89
  }
78
- }, 0);
90
+ else if (cell == null) {
91
+ resetState();
92
+ }
93
+ }
79
94
  };
80
- document.addEventListener('mousemove', onMouseMove);
95
+ const onPointerDown = (event) => {
96
+ const isTouchEvent = event.pointerType === 'touch';
97
+ if (isTouchEvent) {
98
+ onPointerMove(event);
99
+ }
100
+ };
101
+ const resizerContainer = resizerRef.current;
102
+ resizerContainer?.addEventListener('pointermove', onPointerMove, {
103
+ capture: true,
104
+ });
105
+ const removeRootListener = editor.registerRootListener((rootElement, prevRootElement) => {
106
+ prevRootElement?.removeEventListener('pointermove', onPointerMove);
107
+ prevRootElement?.removeEventListener('pointerdown', onPointerDown);
108
+ rootElement?.addEventListener('pointermove', onPointerMove);
109
+ rootElement?.addEventListener('pointerdown', onPointerDown);
110
+ });
81
111
  return () => {
82
- document.removeEventListener('mousemove', onMouseMove);
112
+ removeRootListener();
113
+ resizerContainer?.removeEventListener('pointermove', onPointerMove);
83
114
  };
84
- }, [activeCell, draggingDirection, editor, resetState]);
115
+ }, [activeCell, draggingDirection, editor, resetState, hasTable]);
85
116
  const isHeightChanging = (direction) => {
86
- if (direction === 'bottom')
117
+ if (direction === 'bottom') {
87
118
  return true;
119
+ }
88
120
  return false;
89
121
  };
90
- const updateRowHeight = useCallback((newHeight) => {
122
+ const updateRowHeight = useCallback((heightChange) => {
91
123
  if (!activeCell) {
92
124
  throw new Error('TableCellResizer: Expected active cell.');
93
125
  }
@@ -97,8 +129,12 @@ function TableCellResizer({ editor }) {
97
129
  throw new Error('TableCellResizer: Table cell node not found.');
98
130
  }
99
131
  const tableNode = $getTableNodeFromLexicalNodeOrThrow(tableCellNode);
100
- const tableRowIndex = $getTableRowIndexFromTableCellNode(tableCellNode);
132
+ const baseRowIndex = $getTableRowIndexFromTableCellNode(tableCellNode);
101
133
  const tableRows = tableNode.getChildren();
134
+ // Determine if this is a full row merge by checking colspan
135
+ const isFullRowMerge = tableCellNode.getColSpan() === tableNode.getColumnCount();
136
+ // For full row merges, apply to first row. For partial merges, apply to last row
137
+ const tableRowIndex = isFullRowMerge ? baseRowIndex : baseRowIndex + tableCellNode.getRowSpan() - 1;
102
138
  if (tableRowIndex >= tableRows.length || tableRowIndex < 0) {
103
139
  throw new Error('Expected table cell to be inside of table row.');
104
140
  }
@@ -106,10 +142,29 @@ function TableCellResizer({ editor }) {
106
142
  if (!$isTableRowNode(tableRow)) {
107
143
  throw new Error('Expected table row');
108
144
  }
145
+ let height = tableRow.getHeight();
146
+ if (height === undefined) {
147
+ const rowCells = tableRow.getChildren();
148
+ height = Math.min(...rowCells.map((cell) => getCellNodeHeight(cell, editor) ?? Infinity));
149
+ }
150
+ const newHeight = Math.max(height + heightChange, MIN_ROW_HEIGHT);
109
151
  tableRow.setHeight(newHeight);
110
- });
152
+ }, { tag: 'skip-scroll-into-view' });
111
153
  }, [activeCell, editor]);
112
- const updateColumnWidth = useCallback((newWidth) => {
154
+ const getCellNodeHeight = (cell, activeEditor) => {
155
+ const domCellNode = activeEditor.getElementByKey(cell.getKey());
156
+ return domCellNode?.clientHeight;
157
+ };
158
+ const getCellColumnIndex = (tableCellNode, tableMap) => {
159
+ for (let row = 0; row < tableMap.length; row++) {
160
+ for (let column = 0; column < tableMap[row].length; column++) {
161
+ if (tableMap[row][column].cell === tableCellNode) {
162
+ return column;
163
+ }
164
+ }
165
+ }
166
+ };
167
+ const updateColumnWidth = useCallback((widthChange) => {
113
168
  if (!activeCell) {
114
169
  throw new Error('TableCellResizer: Expected active cell.');
115
170
  }
@@ -119,60 +174,48 @@ function TableCellResizer({ editor }) {
119
174
  throw new Error('TableCellResizer: Table cell node not found.');
120
175
  }
121
176
  const tableNode = $getTableNodeFromLexicalNodeOrThrow(tableCellNode);
122
- const tableColumnIndex = $getTableColumnIndexFromTableCellNode(tableCellNode);
123
- const tableRows = tableNode.getChildren();
124
- for (let r = 0; r < tableRows.length; r++) {
125
- const tableRow = tableRows[r];
126
- if (!$isTableRowNode(tableRow)) {
127
- throw new Error('Expected table row');
128
- }
129
- const rowCells = tableRow.getChildren();
130
- const rowCellsSpan = rowCells.map((cell) => cell.getColSpan());
131
- const aggregatedRowSpans = rowCellsSpan.reduce((rowSpans, cellSpan) => {
132
- const previousCell = rowSpans[rowSpans.length - 1] ?? 0;
133
- rowSpans.push(previousCell + cellSpan);
134
- return rowSpans;
135
- }, []);
136
- const rowColumnIndexWithSpan = aggregatedRowSpans.findIndex((cellSpan) => cellSpan > tableColumnIndex);
137
- if (rowColumnIndexWithSpan >= rowCells.length || rowColumnIndexWithSpan < 0) {
138
- throw new Error('Expected table cell to be inside of table row.');
139
- }
140
- const tableCell = rowCells[rowColumnIndexWithSpan];
141
- if (!$isTableCellNode(tableCell)) {
142
- throw new Error('Expected table cell');
143
- }
144
- tableCell.setWidth(newWidth);
177
+ const [tableMap] = $computeTableMapSkipCellCheck(tableNode, null, null);
178
+ const columnIndex = getCellColumnIndex(tableCellNode, tableMap);
179
+ if (columnIndex === undefined) {
180
+ throw new Error('TableCellResizer: Table column not found.');
145
181
  }
146
- });
182
+ const colWidths = tableNode.getColWidths();
183
+ if (!colWidths) {
184
+ return;
185
+ }
186
+ const width = colWidths[columnIndex];
187
+ if (width === undefined) {
188
+ return;
189
+ }
190
+ const newColWidths = [...colWidths];
191
+ const newWidth = Math.max(width + widthChange, MIN_COLUMN_WIDTH);
192
+ newColWidths[columnIndex] = newWidth;
193
+ tableNode.setColWidths(newColWidths);
194
+ }, { tag: 'skip-scroll-into-view' });
147
195
  }, [activeCell, editor]);
148
- const mouseUpHandler = useCallback((direction) => {
196
+ const pointerUpHandler = useCallback((direction) => {
149
197
  const handler = (event) => {
150
198
  event.preventDefault();
151
199
  event.stopPropagation();
152
200
  if (!activeCell) {
153
201
  throw new Error('TableCellResizer: Expected active cell.');
154
202
  }
155
- if (mouseStartPosRef.current) {
156
- const { x, y } = mouseStartPosRef.current;
203
+ if (pointerStartPosRef.current) {
204
+ const { x, y } = pointerStartPosRef.current;
157
205
  if (activeCell === null) {
158
206
  return;
159
207
  }
208
+ const zoom = calculateZoomLevel(event.target);
160
209
  if (isHeightChanging(direction)) {
161
- const { height } = activeCell.elem.getBoundingClientRect();
162
- const heightChange = Math.abs(event.clientY - y);
163
- const isShrinking = direction === 'bottom' && y > event.clientY;
164
- updateRowHeight(Math.max(isShrinking ? height - heightChange : heightChange + height, MIN_ROW_HEIGHT));
210
+ const heightChange = (event.clientY - y) / zoom;
211
+ updateRowHeight(heightChange);
165
212
  }
166
213
  else {
167
- const computedStyle = getComputedStyle(activeCell.elem);
168
- let width = activeCell.elem.clientWidth; // width with padding
169
- width -= parseFloat(computedStyle.paddingLeft) + parseFloat(computedStyle.paddingRight);
170
- const widthChange = Math.abs(event.clientX - x);
171
- const isShrinking = direction === 'right' && x > event.clientX;
172
- updateColumnWidth(Math.max(isShrinking ? width - widthChange : widthChange + width, MIN_COLUMN_WIDTH));
214
+ const widthChange = (event.clientX - x) / zoom;
215
+ updateColumnWidth(widthChange);
173
216
  }
174
217
  resetState();
175
- document.removeEventListener('mouseup', handler);
218
+ document.removeEventListener('pointerup', handler);
176
219
  }
177
220
  };
178
221
  return handler;
@@ -183,50 +226,55 @@ function TableCellResizer({ editor }) {
183
226
  if (!activeCell) {
184
227
  throw new Error('TableCellResizer: Expected active cell.');
185
228
  }
186
- mouseStartPosRef.current = {
229
+ pointerStartPosRef.current = {
187
230
  x: event.clientX,
188
231
  y: event.clientY,
189
232
  };
190
- updateMouseCurrentPos(mouseStartPosRef.current);
233
+ updatePointerCurrentPos(pointerStartPosRef.current);
191
234
  updateDraggingDirection(direction);
192
- document.addEventListener('mouseup', mouseUpHandler(direction));
193
- }, [activeCell, mouseUpHandler]);
235
+ document.addEventListener('pointerup', pointerUpHandler(direction));
236
+ }, [activeCell, pointerUpHandler]);
194
237
  const getResizers = useCallback(() => {
195
238
  if (activeCell) {
196
239
  const { height, width, top, left } = activeCell.elem.getBoundingClientRect();
240
+ const zoom = calculateZoomLevel(activeCell.elem);
241
+ const zoneWidth = 16; // Pixel width of the zone where you can drag the edge
197
242
  const styles = {
198
243
  bottom: {
199
244
  backgroundColor: 'none',
200
245
  cursor: 'row-resize',
201
- height: '16px',
202
- left: `${window.pageXOffset + left}px`,
203
- top: `${window.pageYOffset + top + height - 8}px`,
246
+ height: `${zoneWidth}px`,
247
+ left: `${window.scrollX + left}px`,
248
+ top: `${window.scrollY + top + height - zoneWidth / 2}px`,
249
+ zIndex: 1,
204
250
  width: `${width}px`,
205
251
  },
206
252
  right: {
207
253
  backgroundColor: 'none',
208
254
  cursor: 'col-resize',
209
255
  height: `${height}px`,
210
- left: `${window.pageXOffset + left + width - 8}px`,
211
- top: `${window.pageYOffset + top}px`,
212
- width: '16px',
256
+ left: `${window.scrollX + left + width - zoneWidth / 2}px`,
257
+ top: `${window.scrollY + top}px`,
258
+ zIndex: 1,
259
+ width: `${zoneWidth}px`,
213
260
  },
214
261
  };
215
262
  const tableRect = tableRectRef.current;
216
- if (draggingDirection && mouseCurrentPos && tableRect) {
263
+ if (draggingDirection && pointerCurrentPos && tableRect) {
217
264
  if (isHeightChanging(draggingDirection)) {
218
- styles[draggingDirection].left = `${window.pageXOffset + tableRect.left}px`;
219
- styles[draggingDirection].top = `${window.pageYOffset + mouseCurrentPos.y}px`;
265
+ styles[draggingDirection].left = `${window.scrollX + tableRect.left}px`;
266
+ styles[draggingDirection].top = `${window.scrollY + pointerCurrentPos.y / zoom}px`;
220
267
  styles[draggingDirection].height = '3px';
221
268
  styles[draggingDirection].width = `${tableRect.width}px`;
222
269
  }
223
270
  else {
224
- styles[draggingDirection].top = `${window.pageYOffset + tableRect.top}px`;
225
- styles[draggingDirection].left = `${window.pageXOffset + mouseCurrentPos.x}px`;
271
+ styles[draggingDirection].top = `${window.scrollY + tableRect.top}px`;
272
+ styles[draggingDirection].left = `${window.scrollX + pointerCurrentPos.x / zoom}px`;
226
273
  styles[draggingDirection].width = '3px';
227
274
  styles[draggingDirection].height = `${tableRect.height}px`;
228
275
  }
229
276
  styles[draggingDirection].backgroundColor = '#adf';
277
+ styles[draggingDirection].mixBlendMode = 'unset';
230
278
  }
231
279
  return styles;
232
280
  }
@@ -236,9 +284,9 @@ function TableCellResizer({ editor }) {
236
284
  right: null,
237
285
  top: null,
238
286
  };
239
- }, [activeCell, draggingDirection, mouseCurrentPos]);
287
+ }, [activeCell, draggingDirection, pointerCurrentPos]);
240
288
  const resizerStyles = getResizers();
241
- return (_jsx("div", { ref: resizerRef, children: activeCell != null && !isSelectingGrid && (_jsxs(_Fragment, { children: [_jsx("div", { className: "TableCellResizer__resizer TableCellResizer__ui", style: resizerStyles.right || undefined, onMouseDown: toggleResize('right') }), _jsx("div", { className: "TableCellResizer__resizer TableCellResizer__ui", style: resizerStyles.bottom || undefined, onMouseDown: toggleResize('bottom') })] })) }));
289
+ return (_jsx("div", { ref: resizerRef, children: activeCell != null && (_jsxs(_Fragment, { children: [_jsx("div", { className: "TableCellResizer__resizer TableCellResizer__ui", style: resizerStyles.right || undefined, onPointerDown: toggleResize('right') }), _jsx("div", { className: "TableCellResizer__resizer TableCellResizer__ui", style: resizerStyles.bottom || undefined, onPointerDown: toggleResize('bottom') })] })) }));
242
290
  }
243
291
  export default function TableCellResizerPlugin() {
244
292
  const [editor] = useLexicalComposerContext();
@@ -1,7 +1,7 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import './index.css';
3
3
  import { useLexicalComposerContext } from '@lexical/react/LexicalComposerContext';
4
- import LexicalTableOfContents from '@lexical/react/LexicalTableOfContents';
4
+ import { TableOfContentsPlugin as LexicalTableOfContentsPlugin } from '@lexical/react/LexicalTableOfContentsPlugin';
5
5
  import { useEffect, useRef, useState } from 'react';
6
6
  const MARGIN_ABOVE_EDITOR = 624;
7
7
  const HEADING_WIDTH = 9;
@@ -100,7 +100,7 @@ function TableOfContentsList({ tableOfContents }) {
100
100
  }) }) }));
101
101
  }
102
102
  export default function TableOfContentsPlugin() {
103
- return (_jsx(LexicalTableOfContents, { children: (tableOfContents) => {
103
+ return (_jsx(LexicalTableOfContentsPlugin, { children: (tableOfContents) => {
104
104
  return _jsx(TableOfContentsList, { tableOfContents: tableOfContents });
105
105
  } }));
106
106
  }
@@ -5,8 +5,8 @@
5
5
  * LICENSE file in the root directory of this source tree.
6
6
  *
7
7
  */
8
- import { EditorThemeClasses, Klass, LexicalCommand, LexicalEditor, LexicalNode } from 'lexical';
9
- import * as React from 'react';
8
+ import type { JSX } from 'react';
9
+ import { EditorThemeClasses, Klass, LexicalEditor, LexicalNode } from 'lexical';
10
10
  export type InsertTableCommandPayload = Readonly<{
11
11
  columns: string;
12
12
  rows: string;
@@ -24,8 +24,7 @@ export type CellEditorConfig = Readonly<{
24
24
  readOnly?: boolean;
25
25
  theme?: EditorThemeClasses;
26
26
  }>;
27
- export declare const INSERT_NEW_TABLE_COMMAND: LexicalCommand<InsertTableCommandPayload>;
28
- export declare const CellContext: React.Context<CellContextShape>;
27
+ export declare const CellContext: import("react").Context<CellContextShape>;
29
28
  export declare function TableContext({ children }: {
30
29
  children: JSX.Element;
31
30
  }): import("react/jsx-runtime").JSX.Element;
@@ -1,20 +1,10 @@
1
1
  import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
2
- /**
3
- * Copyright (c) Meta Platforms, Inc. and affiliates.
4
- *
5
- * This source code is licensed under the MIT license found in the
6
- * LICENSE file in the root directory of this source tree.
7
- *
8
- */
9
2
  import { useLexicalComposerContext } from '@lexical/react/LexicalComposerContext';
10
- import { $createTableNodeWithDimensions, INSERT_TABLE_COMMAND, TableNode } from '@lexical/table';
11
- import { $insertNodes, COMMAND_PRIORITY_EDITOR, createCommand, } from 'lexical';
3
+ import { INSERT_TABLE_COMMAND, TableCellNode, TableNode, TableRowNode } from '@lexical/table';
12
4
  import { createContext, useContext, useEffect, useMemo, useState } from 'react';
13
- import invariant from '../../shared/invariant';
14
5
  import Button from '../ui/Button';
15
6
  import { DialogActions } from '../ui/Dialog';
16
7
  import TextInput from '../ui/TextInput';
17
- export const INSERT_NEW_TABLE_COMMAND = createCommand('INSERT_NEW_TABLE_COMMAND');
18
8
  export const CellContext = createContext({
19
9
  cellEditorConfig: null,
20
10
  cellEditorPlugins: null,
@@ -56,25 +46,18 @@ export function InsertTableDialog({ activeEditor, onClose, }) {
56
46
  });
57
47
  onClose();
58
48
  };
59
- return (_jsxs(_Fragment, { children: [_jsx(TextInput, { placeholder: "# of rows (1-500)", label: "Rows", onChange: setRows, value: rows, "data-test-id": "table-modal-rows",
60
- // @ts-ignore
61
- type: "number" }), _jsx(TextInput, { placeholder: "# of columns (1-50)", label: "Columns", onChange: setColumns, value: columns, "data-test-id": "table-modal-columns",
62
- // @ts-ignore
63
- type: "number" }), _jsx(DialogActions, { "data-test-id": "table-model-confirm-insert", children: _jsx(Button, { disabled: isDisabled, onClick: onClick, children: "Confirm" }) })] }));
49
+ return (_jsxs(_Fragment, { children: [_jsx(TextInput, { placeholder: "# of rows (1-500)", label: "Rows", onChange: setRows, value: rows, "data-test-id": "table-modal-rows", type: "number" }), _jsx(TextInput, { placeholder: "# of columns (1-50)", label: "Columns", onChange: setColumns, value: columns, "data-test-id": "table-modal-columns", type: "number" }), _jsx(DialogActions, { "data-test-id": "table-model-confirm-insert", children: _jsx(Button, { disabled: isDisabled, onClick: onClick, children: "Confirm" }) })] }));
64
50
  }
65
51
  export function TablePlugin({ cellEditorConfig, children, }) {
66
52
  const [editor] = useLexicalComposerContext();
67
53
  const cellContext = useContext(CellContext);
68
54
  useEffect(() => {
69
- if (!editor.hasNodes([TableNode])) {
70
- invariant(false, 'TablePlugin: TableNode is not registered on editor');
55
+ if (!editor.hasNodes([TableNode, TableRowNode, TableCellNode])) {
56
+ throw new Error('TablePlugin: TableNode, TableRowNode, or TableCellNode is not registered on editor');
71
57
  }
58
+ }, [editor]);
59
+ useEffect(() => {
72
60
  cellContext.set(cellEditorConfig, children);
73
- return editor.registerCommand(INSERT_NEW_TABLE_COMMAND, ({ columns, rows, includeHeaders }) => {
74
- const tableNode = $createTableNodeWithDimensions(Number(rows), Number(columns), includeHeaders);
75
- $insertNodes([tableNode]);
76
- return true;
77
- }, COMMAND_PRIORITY_EDITOR);
78
- }, [cellContext, cellEditorConfig, children, editor]);
61
+ }, [cellContext, cellEditorConfig, children]);
79
62
  return null;
80
63
  }
@@ -22,7 +22,6 @@ import { getSelectedNode } from '../../utils/getSelectedNode';
22
22
  import { sanitizeUrl } from '../../utils/sanitizeUrl';
23
23
  // import { EmbedConfigs } from "../AutoEmbedPlugin";
24
24
  // import { INSERT_COLLAPSIBLE_COMMAND } from "../CollapsiblePlugin";
25
- // import { InsertEquationDialog } from "../EquationsPlugin";
26
25
  // import { INSERT_EXCALIDRAW_COMMAND } from "../ExcalidrawPlugin";
27
26
  import { INSERT_IMAGE_COMMAND } from '../ImagesPlugin';
28
27
  import { uploadFile, INSERT_COMPONENT_COMMAND } from '../ComponentPickerPlugin';
@@ -143,7 +143,7 @@ const table = css `
143
143
  border-collapse: collapse;
144
144
  border-spacing: 0;
145
145
  table-layout: fixed;
146
- width: auto;
146
+ width: fit-content;
147
147
 
148
148
  p {
149
149
  margin: 0;
@@ -157,6 +157,7 @@ const tableSelection = css `
157
157
  const tableSelected = css `
158
158
  outline: 2px solid rgb(60, 132, 244);
159
159
  `;
160
+ const tableScrollableWrapper = css ``;
160
161
  const tableCell = css `
161
162
  border: 1px solid #bbb;
162
163
  min-width: 75px;
@@ -676,6 +677,7 @@ const defaultTheme = {
676
677
  tableCellSortedIndicator,
677
678
  tableResizeRuler,
678
679
  tableSelected,
680
+ tableScrollableWrapper,
679
681
  characterLimit,
680
682
  list: {
681
683
  listitem: listItem,
@@ -1,5 +1,2 @@
1
- import { ContentEditable as LexicalContentEditable } from '@lexical/react/LexicalContentEditable';
2
- import React from 'react';
3
- export interface ContentEditableProps extends React.ComponentProps<typeof LexicalContentEditable> {
4
- }
1
+ import { ContentEditableProps } from '@lexical/react/LexicalContentEditable';
5
2
  export default function ContentEditable(props: ContentEditableProps): import("react/jsx-runtime").JSX.Element;
@@ -58,5 +58,5 @@
58
58
  background-color: #ddd;
59
59
  }
60
60
  .Modal__content {
61
- /* padding-top: 20px; */
61
+ padding-top: 20px;
62
62
  }
@@ -5,15 +5,16 @@
5
5
  * LICENSE file in the root directory of this source tree.
6
6
  *
7
7
  */
8
- /// <reference types="react" />
8
+ import type { JSX } from 'react';
9
9
  import './Input.css';
10
+ import { HTMLInputTypeAttribute } from 'react';
10
11
  type Props = Readonly<{
11
12
  'data-test-id'?: string;
12
13
  label: string;
13
14
  onChange: (val: string) => void;
14
15
  placeholder?: string;
15
16
  value: string;
16
- autoFocus?: boolean;
17
+ type?: HTMLInputTypeAttribute;
17
18
  }>;
18
- export default function TextInput({ label, value, onChange, placeholder, 'data-test-id': dataTestId, autoFocus, }: Props): JSX.Element;
19
+ export default function TextInput({ label, value, onChange, placeholder, 'data-test-id': dataTestId, type, }: Props): JSX.Element;
19
20
  export {};
@@ -1,23 +1,7 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
- /**
3
- * Copyright (c) Meta Platforms, Inc. and affiliates.
4
- *
5
- * This source code is licensed under the MIT license found in the
6
- * LICENSE file in the root directory of this source tree.
7
- *
8
- */
9
- import { useEffect, useRef } from 'react';
10
2
  import './Input.css';
11
- export default function TextInput({ label, value, onChange, placeholder = '', 'data-test-id': dataTestId, autoFocus, }) {
12
- const input = useRef(null);
13
- useEffect(() => {
14
- if (autoFocus) {
15
- setTimeout(() => {
16
- input.current?.focus();
17
- });
18
- }
19
- }, [autoFocus]);
20
- return (_jsxs("div", { className: "Input__wrapper", children: [_jsx("label", { className: "Input__label", children: label }), _jsx("input", { ref: input, type: "text", className: "Input__input", placeholder: placeholder, value: value, onChange: (e) => {
3
+ export default function TextInput({ label, value, onChange, placeholder = '', 'data-test-id': dataTestId, type = 'text', }) {
4
+ return (_jsxs("div", { className: "Input__wrapper", children: [_jsx("label", { className: "Input__label", children: label }), _jsx("input", { type: type, className: "Input__input", placeholder: placeholder, value: value, onChange: (e) => {
21
5
  onChange(e.target.value);
22
- }, "data-test-id": dataTestId, autoFocus: autoFocus })] }));
6
+ }, "data-test-id": dataTestId })] }));
23
7
  }