@stll/folio-core 0.53.0 → 0.54.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 (155) hide show
  1. package/dist/ai-edits/apply.js +415 -166
  2. package/dist/ai-edits/batch-claims.d.ts +21 -6
  3. package/dist/ai-edits/batch-claims.js +47 -16
  4. package/dist/ai-edits/headless.d.ts +20 -0
  5. package/dist/ai-edits/headless.js +140 -11
  6. package/dist/ai-edits/pending-suggestions.js +1 -1
  7. package/dist/ai-edits/read.d.ts +5 -3
  8. package/dist/ai-edits/read.js +97 -47
  9. package/dist/ai-edits/revisionStretches.d.ts +17 -0
  10. package/dist/ai-edits/revisionStretches.js +80 -0
  11. package/dist/ai-edits/snapshot.js +3 -2
  12. package/dist/ai-edits/table-cell-mutations.d.ts +3 -1
  13. package/dist/ai-edits/table-cell-mutations.js +2 -1
  14. package/dist/ai-edits/table-row-column-mutations.d.ts +6 -1
  15. package/dist/ai-edits/table-row-column-mutations.js +27 -10
  16. package/dist/compare/content-alignment.d.ts +5 -1
  17. package/dist/compare/content-alignment.js +39 -32
  18. package/dist/compare/inline-provenance.js +1 -1
  19. package/dist/controller/layoutPipeline.js +3 -2
  20. package/dist/docx/archiveInflation.d.ts +127 -0
  21. package/dist/docx/archiveInflation.js +181 -0
  22. package/dist/docx/metadataPrivacy.js +24 -1
  23. package/dist/docx/noteReferenceMark.d.ts +15 -0
  24. package/dist/docx/noteReferenceMark.js +48 -0
  25. package/dist/docx/paragraphParser.js +5 -3
  26. package/dist/docx/paragraphPropertySource.d.ts +1 -1
  27. package/dist/docx/paragraphPropertySource.js +4 -2
  28. package/dist/docx/parser.js +2 -2
  29. package/dist/docx/rezip.js +4 -2
  30. package/dist/docx/selectiveXmlPatch.d.ts +3 -1
  31. package/dist/docx/selectiveXmlPatch.js +81 -3
  32. package/dist/docx/server/boundedArchive.d.ts +8 -13
  33. package/dist/docx/server/boundedArchive.js +70 -59
  34. package/dist/docx/server/extractDocxText.d.ts +8 -2
  35. package/dist/docx/server/extractDocxText.js +2 -2
  36. package/dist/docx/server/validateDocxConformance.d.ts +1 -1
  37. package/dist/docx/server/validateDocxConformance.js +1 -0
  38. package/dist/docx/unzip.d.ts +19 -2
  39. package/dist/docx/unzip.js +135 -24
  40. package/dist/docx/verticalMergeProjection.d.ts +17 -0
  41. package/dist/docx/verticalMergeProjection.js +120 -0
  42. package/dist/fonts/embeddedFonts.js +1 -1
  43. package/dist/i18n/messages/catalogs.gen.d.ts +34 -34
  44. package/dist/i18n/messages/catalogs.gen.js +34 -34
  45. package/dist/i18n/messages/messages.gen.d.ts +2 -2
  46. package/dist/internal/wholeStoryRevisionResolution.js +95 -25
  47. package/dist/layout-engine/measure/measureParagraph.js +2 -2
  48. package/dist/layout-engine/measure/paragraphMeasureShared.d.ts +12 -1
  49. package/dist/layout-engine/measure/paragraphMeasureShared.js +14 -1
  50. package/dist/markdown/escape.d.ts +2 -2
  51. package/dist/markdown/escape.js +4 -5
  52. package/dist/markdown/renderBlock.js +91 -25
  53. package/dist/markdown/renderRuns.d.ts +10 -1
  54. package/dist/markdown/renderRuns.js +320 -59
  55. package/dist/prosemirror/clearRunColor.d.ts +6 -0
  56. package/dist/prosemirror/clearRunColor.js +46 -0
  57. package/dist/prosemirror/commands/comments.js +62 -22
  58. package/dist/prosemirror/commands/formatPainter.js +1 -1
  59. package/dist/prosemirror/commands/hyperlink.js +2 -1
  60. package/dist/prosemirror/commands/propertyChangeScope.d.ts +3 -2
  61. package/dist/prosemirror/commands/propertyChangeScope.js +28 -4
  62. package/dist/prosemirror/commands/resolveAllTableChanges.js +40 -41
  63. package/dist/prosemirror/commands/resolveParagraphProperties.js +33 -8
  64. package/dist/prosemirror/commands/tableCellMergeResolution.d.ts +7 -1
  65. package/dist/prosemirror/commands/tableCellMergeResolution.js +39 -20
  66. package/dist/prosemirror/commands/tableMergeFoldDecisions.d.ts +61 -0
  67. package/dist/prosemirror/commands/tableMergeFoldDecisions.js +79 -0
  68. package/dist/prosemirror/containerFinalParagraph.d.ts +11 -5
  69. package/dist/prosemirror/containerFinalParagraph.js +7 -6
  70. package/dist/prosemirror/conversion/fromProseDoc.d.ts +2 -13
  71. package/dist/prosemirror/conversion/fromProseDoc.js +12 -590
  72. package/dist/prosemirror/conversion/toProseDoc.d.ts +1 -13
  73. package/dist/prosemirror/conversion/toProseDoc.js +28 -262
  74. package/dist/prosemirror/documentSchema.d.ts +8 -0
  75. package/dist/prosemirror/documentSchema.js +18 -0
  76. package/dist/prosemirror/extensions/StarterKit.js +2 -0
  77. package/dist/prosemirror/extensions/core/ParagraphExtension.js +104 -63
  78. package/dist/prosemirror/extensions/features/BaseKeymapExtension.js +1 -1
  79. package/dist/prosemirror/extensions/features/EmptyParagraphFormatExtension.js +24 -3
  80. package/dist/prosemirror/extensions/features/JoinedRunStyleExtension.d.ts +20 -0
  81. package/dist/prosemirror/extensions/features/JoinedRunStyleExtension.js +43 -0
  82. package/dist/prosemirror/extensions/features/ListExtension.js +10 -9
  83. package/dist/prosemirror/extensions/features/pastedHeadingStyles.js +1 -1
  84. package/dist/prosemirror/extensions/features/pastedHtmlLists.js +2 -4
  85. package/dist/prosemirror/extensions/marks/FootnoteRefExtension.js +14 -8
  86. package/dist/prosemirror/extensions/marks/HyperlinkExtension.js +8 -4
  87. package/dist/prosemirror/extensions/marks/StrikeExtension.js +2 -2
  88. package/dist/prosemirror/extensions/marks/SubscriptExtension.js +2 -2
  89. package/dist/prosemirror/extensions/marks/SuperscriptExtension.js +2 -2
  90. package/dist/prosemirror/extensions/marks/TextColorExtension.js +4 -3
  91. package/dist/prosemirror/extensions/marks/markUtils.d.ts +8 -6
  92. package/dist/prosemirror/extensions/marks/markUtils.js +17 -8
  93. package/dist/prosemirror/extensions/marks/noteReferenceDeletion.d.ts +3 -1
  94. package/dist/prosemirror/extensions/marks/noteReferenceDeletion.js +12 -1
  95. package/dist/prosemirror/extensions/nodes/CommentReferenceExtension.js +2 -2
  96. package/dist/prosemirror/extensions/nodes/HardBreakExtension.js +5 -3
  97. package/dist/prosemirror/extensions/nodes/TableExtension.js +104 -210
  98. package/dist/prosemirror/extensions/types.d.ts +7 -0
  99. package/dist/prosemirror/hyperlinkRemoval.d.ts +9 -0
  100. package/dist/prosemirror/hyperlinkRemoval.js +129 -0
  101. package/dist/prosemirror/index.d.ts +2 -1
  102. package/dist/prosemirror/index.js +2 -1
  103. package/dist/prosemirror/listNumbering.d.ts +3 -21
  104. package/dist/prosemirror/listNumbering.js +24 -39
  105. package/dist/prosemirror/listRendering.d.ts +29 -0
  106. package/dist/prosemirror/listRendering.js +26 -0
  107. package/dist/prosemirror/markupViewNotes.d.ts +8 -0
  108. package/dist/prosemirror/markupViewNotes.js +49 -0
  109. package/dist/prosemirror/markupViewProjection.d.ts +3 -1
  110. package/dist/prosemirror/markupViewProjection.js +7 -2
  111. package/dist/prosemirror/noteReferenceReview.d.ts +77 -0
  112. package/dist/prosemirror/noteReferenceReview.js +332 -0
  113. package/dist/prosemirror/paragraphIndentation.js +5 -2
  114. package/dist/prosemirror/paragraphMarkJoin.d.ts +6 -4
  115. package/dist/prosemirror/paragraphMarkJoin.js +21 -19
  116. package/dist/prosemirror/paragraphPropertyCarry.d.ts +64 -0
  117. package/dist/prosemirror/paragraphPropertyCarry.js +155 -0
  118. package/dist/prosemirror/plugins/documentStyleState.d.ts +26 -0
  119. package/dist/prosemirror/plugins/documentStyleState.js +32 -0
  120. package/dist/prosemirror/plugins/documentStyles.d.ts +2 -21
  121. package/dist/prosemirror/plugins/documentStyles.js +66 -29
  122. package/dist/prosemirror/plugins/index.d.ts +2 -1
  123. package/dist/prosemirror/plugins/index.js +2 -1
  124. package/dist/prosemirror/plugins/paragraphStyleResolution.d.ts +15 -0
  125. package/dist/prosemirror/plugins/paragraphStyleResolution.js +230 -0
  126. package/dist/prosemirror/plugins/suggestionMode.d.ts +12 -2
  127. package/dist/prosemirror/plugins/suggestionMode.js +387 -28
  128. package/dist/prosemirror/plugins/templateDirectives.d.ts +6 -0
  129. package/dist/prosemirror/plugins/templateDirectives.js +21 -7
  130. package/dist/prosemirror/plugins/templatePreviewValues.js +14 -21
  131. package/dist/prosemirror/rebaseParagraphRunFormatting.d.ts +22 -2
  132. package/dist/prosemirror/rebaseParagraphRunFormatting.js +39 -13
  133. package/dist/prosemirror/rebaseParagraphRuns.d.ts +36 -0
  134. package/dist/prosemirror/rebaseParagraphRuns.js +99 -0
  135. package/dist/prosemirror/runFormattingFromMarks.d.ts +18 -0
  136. package/dist/prosemirror/runFormattingFromMarks.js +567 -0
  137. package/dist/prosemirror/runFormattingReconciliation.js +10 -9
  138. package/dist/prosemirror/schema/nodes.d.ts +2 -0
  139. package/dist/prosemirror/styles/paragraphStyleCascade.d.ts +59 -0
  140. package/dist/prosemirror/styles/paragraphStyleCascade.js +145 -0
  141. package/dist/prosemirror/styles/resolvedStyleAttrs.d.ts +21 -2
  142. package/dist/prosemirror/styles/resolvedStyleAttrs.js +38 -1
  143. package/dist/prosemirror/styles/tableStyleRegions.d.ts +31 -0
  144. package/dist/prosemirror/styles/tableStyleRegions.js +55 -0
  145. package/dist/prosemirror/tableCellPaste.d.ts +74 -0
  146. package/dist/prosemirror/tableCellPaste.js +525 -0
  147. package/dist/prosemirror/tableGridMutation.d.ts +53 -14
  148. package/dist/prosemirror/tableGridMutation.js +166 -18
  149. package/dist/prosemirror/tableRunIn.d.ts +51 -0
  150. package/dist/prosemirror/tableRunIn.js +165 -0
  151. package/dist/prosemirror/textInput.js +11 -2
  152. package/dist/prosemirror/trackedRevisionPath.d.ts +17 -0
  153. package/dist/prosemirror/trackedRevisionPath.js +32 -0
  154. package/dist/server.d.ts +2 -2
  155. package/package.json +6 -6
@@ -4,24 +4,26 @@ import { Command, EditorState } from "prosemirror-state";
4
4
  //#region src/prosemirror/extensions/marks/markUtils.d.ts
5
5
  type MarkAttrs = Record<string, unknown>;
6
6
  declare function marksToTextFormatting(marks: readonly Mark[]): document_d_exports.TextFormatting;
7
- declare function setMark(markType: MarkType, attrs: MarkAttrs): Command;
7
+ declare function setMark(type: MarkType, attrs: MarkAttrs): Command;
8
8
  type PairedToggleProperty = "bold" | "italic";
9
+ /** `toggleMark` for the document's own counterpart of `type`. */
10
+ declare const toggleDocumentMark: (type: MarkType) => Command;
9
11
  /** UI toggle whose direct-formatting contract explicitly targets both script families. */
10
- declare const toggleMarkForAllScripts: (markType: MarkType, property: PairedToggleProperty) => Command;
12
+ declare const toggleMarkForAllScripts: (type: MarkType, property: PairedToggleProperty) => Command;
11
13
  /** UI size command whose direct-formatting contract explicitly targets both script families. */
12
14
  declare const setFontSizeForAllScripts: (markType: MarkType, size: number) => Command;
13
15
  /** Clears both ordinary and complex-script direct size through the UI command boundary. */
14
16
  declare const clearFontSizeForAllScripts: (markType: MarkType) => Command;
15
17
  declare function toggleUnderlineMark(markType: MarkType): Command;
16
- declare function removeMark(markType: MarkType): Command;
18
+ declare function removeMark(type: MarkType): Command;
17
19
  /**
18
20
  * Check if a mark is active in the current selection
19
21
  */
20
- declare function isMarkActive(state: EditorState, markType: MarkType, attrs?: Record<string, unknown>): boolean;
22
+ declare function isMarkActive(state: EditorState, type: MarkType, attrs?: Record<string, unknown>): boolean;
21
23
  /**
22
24
  * Get the current value of a mark attribute
23
25
  */
24
- declare function getMarkAttr(state: EditorState, markType: MarkType, attr: string): unknown;
26
+ declare function getMarkAttr(state: EditorState, type: MarkType, attr: string): unknown;
25
27
  type AuthoredRunFormattingCarrier = "preserve" | "reconstruct";
26
28
  /** Builds a mark by type name; a conversion passes one that shares equal marks. */
27
29
  type MarkFactory = (type: string, attrs?: Attrs | null) => Mark;
@@ -56,4 +58,4 @@ declare function createSetMarkCommand(markType: MarkType, attrs?: Record<string,
56
58
  */
57
59
  declare function createRemoveMarkCommand(markType: MarkType): Command;
58
60
  //#endregion
59
- export { AuthoredRunFormattingCarrier, MarkFactory, clearFontSizeForAllScripts, clearFormatting, createRemoveMarkCommand, createSetMarkCommand, getMarkAttr, isMarkActive, marksToTextFormatting, removeMark, setFontSizeForAllScripts, setMark, textFormattingToMarks, toggleMarkForAllScripts, toggleUnderlineMark };
61
+ export { AuthoredRunFormattingCarrier, MarkFactory, clearFontSizeForAllScripts, clearFormatting, createRemoveMarkCommand, createSetMarkCommand, getMarkAttr, isMarkActive, marksToTextFormatting, removeMark, setFontSizeForAllScripts, setMark, textFormattingToMarks, toggleDocumentMark, toggleMarkForAllScripts, toggleUnderlineMark };
@@ -3,6 +3,7 @@ import { mergeFontFamily } from "../../../utils/fontFamilyMerge.js";
3
3
  import { normalizeHorizontalScalePercent } from "../../../utils/horizontalScale.js";
4
4
  import { expectCharacterSpacingMarkAttrs, expectCharacterStyleMarkAttrs, expectEmphasisMarkAttrs, expectFontFamilyMarkAttrs, expectRunFormattingOverrideMarkAttrs, expectRunShadingMarkAttrs, expectStrikeMarkAttrs, expectTextEffectMarkAttrs } from "../../attrs/index.js";
5
5
  import { runShadingAttrsToShading, shadingToRunShadingAttrs } from "../../conversion/runShadingMark.js";
6
+ import { documentMarkType } from "../../documentSchema.js";
6
7
  import { selectRunFormattingCarrierRepresentations } from "../../runFormattingInlineCarriers.js";
7
8
  import { RUN_FORMATTING_MARK_NAMES } from "../../runFormattingMarkNames.js";
8
9
  import { hasRunFormattingOverrideAttrs } from "../../runFormattingProvenance.js";
@@ -178,8 +179,9 @@ function createMarkWithMergedAttrs(markType, currentMark, nextAttrs) {
178
179
  if (!markRequiresAttrMerge(markType)) return markType.create(nextAttrs);
179
180
  return markType.create(mergeMarkAttrs(markType, currentMark, nextAttrs));
180
181
  }
181
- function setMark(markType, attrs) {
182
+ function setMark(type, attrs) {
182
183
  return (state, dispatch) => {
184
+ const markType = documentMarkType(state, type);
183
185
  const { from, to, empty } = state.selection;
184
186
  if (empty) {
185
187
  if (dispatch) {
@@ -201,7 +203,8 @@ function setMark(markType, attrs) {
201
203
  if (!node.isText) return;
202
204
  const start = Math.max(from, pos);
203
205
  const end = Math.min(to, pos + node.nodeSize);
204
- const mark = createMarkWithMergedAttrs(markType, markType.isInSet(node.marks), attrs);
206
+ const currentMark = markType.isInSet(node.marks);
207
+ const mark = createMarkWithMergedAttrs(markType, currentMark, attrs);
205
208
  tr = tr.addMark(start, end, mark);
206
209
  });
207
210
  dispatch(tr.scrollIntoView());
@@ -283,8 +286,11 @@ const updateRunFormattingOverride = (state, tr, update) => {
283
286
  const withRunFormattingOverride = (command, update) => (state, dispatch) => command(state, dispatch ? (tr) => {
284
287
  dispatch(updateRunFormattingOverride(state, tr, update));
285
288
  } : void 0);
289
+ /** `toggleMark` for the document's own counterpart of `type`. */
290
+ const toggleDocumentMark = (type) => (state, dispatch, view) => toggleMark(documentMarkType(state, type))(state, dispatch, view);
286
291
  /** UI toggle whose direct-formatting contract explicitly targets both script families. */
287
- const toggleMarkForAllScripts = (markType, property) => (state, dispatch) => {
292
+ const toggleMarkForAllScripts = (type, property) => (state, dispatch) => {
293
+ const markType = documentMarkType(state, type);
288
294
  const enabled = !isMarkActive(state, markType);
289
295
  return withRunFormattingOverride(toggleMark(markType), (attrs) => updatePairedToggleAttrs(attrs, property, enabled))(state, dispatch);
290
296
  };
@@ -311,10 +317,11 @@ function selectionHasVisibleUnderline(state, markType) {
311
317
  return hasVisibleUnderline;
312
318
  }
313
319
  function toggleUnderlineMark(markType) {
314
- return (state, dispatch) => setMark(markType, { style: selectionHasVisibleUnderline(state, markType) ? "none" : "single" })(state, dispatch);
320
+ return (state, dispatch) => setMark(markType, { style: selectionHasVisibleUnderline(state, documentMarkType(state, markType)) ? "none" : "single" })(state, dispatch);
315
321
  }
316
- function removeMark(markType) {
322
+ function removeMark(type) {
317
323
  return (state, dispatch) => {
324
+ const markType = documentMarkType(state, type);
318
325
  const { from, to, empty } = state.selection;
319
326
  if (empty) {
320
327
  if (dispatch) dispatchStoredMarks(state, dispatch, (state.storedMarks ?? state.selection.$from.marks()).filter((m) => m.type !== markType));
@@ -327,7 +334,8 @@ function removeMark(markType) {
327
334
  /**
328
335
  * Check if a mark is active in the current selection
329
336
  */
330
- function isMarkActive(state, markType, attrs) {
337
+ function isMarkActive(state, type, attrs) {
338
+ const markType = documentMarkType(state, type);
331
339
  const { from, to, empty } = state.selection;
332
340
  if (empty) return (state.storedMarks ?? state.selection.$from.marks()).some((mark) => {
333
341
  if (mark.type !== markType) return false;
@@ -356,7 +364,8 @@ function isMarkActive(state, markType, attrs) {
356
364
  /**
357
365
  * Get the current value of a mark attribute
358
366
  */
359
- function getMarkAttr(state, markType, attr) {
367
+ function getMarkAttr(state, type, attr) {
368
+ const markType = documentMarkType(state, type);
360
369
  const { empty, $from, from, to } = state.selection;
361
370
  if (empty) {
362
371
  const marks = state.storedMarks ?? $from.marks();
@@ -524,4 +533,4 @@ function createRemoveMarkCommand(markType) {
524
533
  return removeMark(markType);
525
534
  }
526
535
  //#endregion
527
- export { clearFontSizeForAllScripts, clearFormatting, createRemoveMarkCommand, createSetMarkCommand, getMarkAttr, isMarkActive, marksToTextFormatting, removeMark, setFontSizeForAllScripts, setMark, textFormattingToMarks, toggleMarkForAllScripts, toggleUnderlineMark };
536
+ export { clearFontSizeForAllScripts, clearFormatting, createRemoveMarkCommand, createSetMarkCommand, getMarkAttr, isMarkActive, marksToTextFormatting, removeMark, setFontSizeForAllScripts, setMark, textFormattingToMarks, toggleDocumentMark, toggleMarkForAllScripts, toggleUnderlineMark };
@@ -6,5 +6,7 @@ type DeletionRange = {
6
6
  };
7
7
  /** Keep the text carrying one OOXML note reference together during deletion. */
8
8
  declare const expandNoteReferenceDeletionRange: (doc: Node, from: number, to: number) => DeletionRange | null;
9
+ /** Each whole note reference [`from`, `to`) of `doc` touches, in document order. */
10
+ declare const noteReferenceRanges: (doc: Node, from: number, to: number) => DeletionRange[];
9
11
  //#endregion
10
- export { expandNoteReferenceDeletionRange };
12
+ export { expandNoteReferenceDeletionRange, noteReferenceRanges };
@@ -31,5 +31,16 @@ const expandNoteReferenceDeletionRange = (doc, from, to) => {
31
31
  to: expandedTo
32
32
  } : null;
33
33
  };
34
+ /** Each whole note reference [`from`, `to`) of `doc` touches, in document order. */
35
+ const noteReferenceRanges = (doc, from, to) => {
36
+ const ranges = [];
37
+ doc.nodesBetween(from, to, (node, pos) => {
38
+ if (!node.isText || !node.marks.some((mark) => mark.type.name === "footnoteRef")) return;
39
+ const whole = expandNoteReferenceDeletionRange(doc, pos, pos + node.nodeSize);
40
+ const last = ranges.at(-1);
41
+ if (whole && (!last || whole.from >= last.to)) ranges.push(whole);
42
+ });
43
+ return ranges;
44
+ };
34
45
  //#endregion
35
- export { expandNoteReferenceDeletionRange };
46
+ export { expandNoteReferenceDeletionRange, noteReferenceRanges };
@@ -80,9 +80,9 @@ const CommentReferenceExtension = createNodeExtension({
80
80
  }];
81
81
  }
82
82
  }),
83
- onSchemaReady: ({ schema }) => ({ plugins: [new Plugin({ appendTransaction(transactions, _oldState, newState) {
83
+ onSchemaReady: () => ({ plugins: [new Plugin({ appendTransaction(transactions, _oldState, newState) {
84
84
  if (!transactions.some(({ docChanged }) => docChanged)) return null;
85
- const referenceType = schema.nodes[COMMENT_REFERENCE_NODE_NAME];
85
+ const referenceType = newState.schema.nodes[COMMENT_REFERENCE_NODE_NAME];
86
86
  if (!referenceType) return null;
87
87
  const repairs = planCommentReferenceRepairs(surveyCommentReferences(newState.doc));
88
88
  if (repairs.length === 0) return null;
@@ -41,10 +41,12 @@ const HardBreakExtension = createNodeExtension({
41
41
  }
42
42
  },
43
43
  onSchemaReady(ctx) {
44
- const hardBreakType = ctx.schema.nodes["hardBreak"];
45
- if (!hardBreakType) panic("Missing node type: hardBreak");
44
+ if (!ctx.schema.nodes["hardBreak"]) panic("Missing node type: hardBreak");
46
45
  return { keyboardShortcuts: { "Shift-Enter": (state, dispatch) => {
47
- if (dispatch) dispatch(state.tr.replaceSelectionWith(hardBreakType.create()).scrollIntoView());
46
+ if (dispatch) {
47
+ const hardBreakType = state.schema.nodes["hardBreak"] ?? panic("Missing node type: hardBreak");
48
+ dispatch(state.tr.replaceSelectionWith(hardBreakType.create()).scrollIntoView());
49
+ }
48
50
  return true;
49
51
  } } };
50
52
  }
@@ -5,11 +5,13 @@ import { isValidHexColor, resolveColor } from "../../../utils/colorResolver.js";
5
5
  import { resolveTablePlacementAlignment } from "../../../utils/tablePlacement.js";
6
6
  import { textFlowCss } from "../../../utils/textDirectionFlow.js";
7
7
  import { expectTableAttrs, expectTableCellAttrs, expectTableRowAttrs, mergeTableAttrs, mergeTableCellAttrs, mergeTableRowAttrs } from "../../attrs/index.js";
8
- import { removeTableRow } from "../../tableGridMutation.js";
8
+ import { makeRevisionInfo } from "../../plugins/suggestionMode.js";
9
+ import { pasteTableCells, pastedSliceWithNewTableCells } from "../../tableCellPaste.js";
10
+ import { insertTableColumn, removeTableColumns, removeTableRow } from "../../tableGridMutation.js";
9
11
  import { createExtension, createNodeExtension } from "../create.js";
10
12
  import { panic } from "better-result";
11
13
  import { statesNoBorder } from "@stll/docx-core/model";
12
- import { CellSelection, TableMap, columnResizing, mergeCells, selectedRect, splitCell, tableEditing } from "prosemirror-tables";
14
+ import { CellSelection, TableMap, columnResizing, mergeCells, selectedRect, splitCell, tableEditing, tableNodeTypes } from "prosemirror-tables";
13
15
  import { Plugin, PluginKey, Selection, TextSelection } from "prosemirror-state";
14
16
  import { Decoration, DecorationSet } from "prosemirror-view";
15
17
  //#region src/prosemirror/extensions/nodes/TableExtension.ts
@@ -277,6 +279,7 @@ const tableRowSpec = {
277
279
  heightRule: { default: null },
278
280
  isHeader: { default: false },
279
281
  hidden: { default: null },
282
+ _batchRowCleanup: { default: null },
280
283
  _resolvedJustification: { default: null },
281
284
  _originalFormatting: { default: null },
282
285
  _tablePropertyExceptions: { default: null },
@@ -518,12 +521,12 @@ function getTableContext(state) {
518
521
  let rowIndex;
519
522
  let columnIndex;
520
523
  let cellNode;
524
+ let cellPos;
521
525
  for (let d = $from.depth; d > 0; d--) {
522
526
  const node = $from.node(d);
523
527
  if (node.type.name === "tableCell" || node.type.name === "tableHeader") {
524
528
  cellNode = node;
525
- const rowNode = $from.node(d - 1);
526
- if (rowNode.type.name === "tableRow") columnIndex = getColumnIndex(rowNode, $from.index(d - 1));
529
+ cellPos = $from.before(d);
527
530
  } else if (node.type.name === "tableRow") {
528
531
  if ($from.node(d - 1).type.name === "table") rowIndex = $from.index(d - 1);
529
532
  } else if (node.type.name === "table") {
@@ -533,18 +536,10 @@ function getTableContext(state) {
533
536
  }
534
537
  }
535
538
  if (!table) return { isInTable: false };
536
- let rowCount = 0;
537
- let columnCount = 0;
538
- table.forEach((row) => {
539
- if (row.type.name === "tableRow") {
540
- rowCount++;
541
- let cols = 0;
542
- row.forEach((cell) => {
543
- cols += Number(cell.attrs["colspan"]) || 1;
544
- });
545
- columnCount = Math.max(columnCount, cols);
546
- }
547
- });
539
+ const map = TableMap.get(table);
540
+ const rowCount = table.childCount;
541
+ const columnCount = map.width;
542
+ if (cellPos !== void 0 && tablePos !== void 0) columnIndex = map.findCell(cellPos - tablePos - 1).left;
548
543
  const canSplitCell = cellNode !== void 0 && ((Number(cellNode.attrs["colspan"]) || 1) > 1 || (Number(cellNode.attrs["rowspan"]) || 1) > 1);
549
544
  let cellBorderColor;
550
545
  let cellBackgroundColor;
@@ -579,19 +574,6 @@ function getTableContext(state) {
579
574
  ...cellBackgroundColor !== void 0 ? { cellBackgroundColor } : {}
580
575
  };
581
576
  }
582
- const getColumnIndex = (rowNode, targetIndex) => {
583
- let columnIndex = 0;
584
- let foundColumnIndex;
585
- rowNode.forEach((child, _offset, index) => {
586
- if (foundColumnIndex !== void 0) return;
587
- if (index === targetIndex) {
588
- foundColumnIndex = columnIndex;
589
- return;
590
- }
591
- columnIndex += Number(child.attrs["colspan"]) || 1;
592
- });
593
- return foundColumnIndex;
594
- };
595
577
  function isInTableCell(state) {
596
578
  const { $from } = state.selection;
597
579
  for (let d = $from.depth; d > 0; d--) {
@@ -689,10 +671,12 @@ const TablePluginExtension = createExtension({
689
671
  if (!schema.nodes["tableCell"]) panic("Missing node type: tableCell");
690
672
  if (!schema.nodes["tableRow"]) panic("Missing node type: tableRow");
691
673
  if (!schema.nodes["table"]) panic("Missing node type: table");
692
- const nodeTypeParagraph = schema.nodes["paragraph"];
693
- const nodeTypeTableCell = schema.nodes["tableCell"];
694
- const nodeTypeTableRow = schema.nodes["tableRow"];
695
- const nodeTypeTable = schema.nodes["table"];
674
+ const documentTableTypes = (documentSchema) => ({
675
+ paragraph: documentSchema.nodes["paragraph"] ?? panic("Missing node type: paragraph"),
676
+ tableCell: documentSchema.nodes["tableCell"] ?? panic("Missing node type: tableCell"),
677
+ tableRow: documentSchema.nodes["tableRow"] ?? panic("Missing node type: tableRow"),
678
+ table: documentSchema.nodes["table"] ?? panic("Missing node type: table")
679
+ });
696
680
  function chainCommands(...commands) {
697
681
  return (state, dispatch, view) => {
698
682
  for (const cmd of commands) if (cmd(state, dispatch, view)) return true;
@@ -717,7 +701,8 @@ const TablePluginExtension = createExtension({
717
701
  ...overrides
718
702
  };
719
703
  }
720
- function createTable(rows, cols, borderColor = "000000", contentWidthTwips = 9360) {
704
+ function createTable(documentSchema, rows, cols, borderColor = "000000", contentWidthTwips = 9360) {
705
+ const types = documentTableTypes(documentSchema);
721
706
  const tableRows = [];
722
707
  const colWidthTwips = Math.floor(contentWidthTwips / cols);
723
708
  const defaultRowHeightTwips = 360;
@@ -736,22 +721,22 @@ const TablePluginExtension = createExtension({
736
721
  for (let r = 0; r < rows; r++) {
737
722
  const cells = [];
738
723
  for (let c = 0; c < cols; c++) {
739
- const paragraph = nodeTypeParagraph.create();
724
+ const paragraph = types.paragraph.create();
740
725
  const cellAttrs = {
741
726
  colspan: 1,
742
727
  rowspan: 1,
743
728
  borders: defaultBorders,
744
729
  ...statedCellWidth(colWidthTwips, "dxa")
745
730
  };
746
- cells.push(nodeTypeTableCell.create(cellAttrs, paragraph));
731
+ cells.push(types.tableCell.create(cellAttrs, paragraph));
747
732
  }
748
- tableRows.push(nodeTypeTableRow.create({
733
+ tableRows.push(types.tableRow.create({
749
734
  height: defaultRowHeightTwips,
750
735
  heightRule: defaultRowHeightRule
751
736
  }, cells));
752
737
  }
753
738
  const columnWidths = Array.from({ length: cols }, () => colWidthTwips);
754
- return nodeTypeTable.create({
739
+ return types.table.create({
755
740
  columnWidths,
756
741
  width: contentWidthTwips,
757
742
  widthType: "dxa"
@@ -784,8 +769,31 @@ const TablePluginExtension = createExtension({
784
769
  break;
785
770
  }
786
771
  }
787
- const table = createTable(rows, cols, borderColor, contentWidthTwips);
788
- const emptyParagraph = nodeTypeParagraph.create();
772
+ let table = createTable(state.schema, rows, cols, borderColor, contentWidthTwips);
773
+ let emptyParagraph = documentTableTypes(state.schema).paragraph.create();
774
+ const revision = makeRevisionInfo(state);
775
+ if (revision) {
776
+ const rowRevision = {
777
+ revisionId: revision.id,
778
+ author: revision.author,
779
+ date: revision.date
780
+ };
781
+ const rowsWithRevision = [];
782
+ table.forEach((row) => {
783
+ rowsWithRevision.push(row.type.create({
784
+ ...row.attrs,
785
+ trIns: rowRevision
786
+ }, row.content));
787
+ });
788
+ table = table.type.create(table.attrs, rowsWithRevision);
789
+ emptyParagraph = emptyParagraph.type.create({
790
+ ...emptyParagraph.attrs,
791
+ pPrMark: {
792
+ kind: "ins",
793
+ info: revision
794
+ }
795
+ });
796
+ }
789
797
  const needsLeadingParagraph = state.doc.resolve(insertPos).nodeBefore?.type.name === "table";
790
798
  const insertContent = needsLeadingParagraph ? [
791
799
  emptyParagraph,
@@ -821,11 +829,13 @@ const TablePluginExtension = createExtension({
821
829
  const context = getTableContext(state);
822
830
  if (!context.isInTable || context.rowIndex === void 0 || !context.table || context.tablePos === void 0 || hasOmittedGridSlots(context.table)) return false;
823
831
  if (!dispatch) return true;
824
- const { table, tablePos, rowIndex } = context;
825
- const boundaryRow = rowIndex + boundaryOffset;
826
- const map = TableMap.get(table);
832
+ const { table, tablePos } = context;
833
+ const rect = selectedRect(state);
834
+ const boundaryRow = boundaryOffset === 0 ? rect.top : rect.bottom;
835
+ const { map } = rect;
827
836
  const tableStart = tablePos + 1;
828
837
  const tr = state.tr;
838
+ const paragraphType = state.schema.nodes["paragraph"];
829
839
  const cells = [];
830
840
  const extended = /* @__PURE__ */ new Set();
831
841
  let lastTemplatePos = -1;
@@ -846,10 +856,11 @@ const TablePluginExtension = createExtension({
846
856
  const templatePos = below ?? above;
847
857
  if (templatePos === void 0 || templatePos === lastTemplatePos) continue;
848
858
  lastTemplatePos = templatePos;
849
- cells.push(nodeTypeTableCell.create(buildCellAttrsFromTemplate(table.nodeAt(templatePos)), nodeTypeParagraph.create()));
859
+ const template = table.nodeAt(templatePos);
860
+ cells.push((template?.type ?? tableNodeTypes(state.schema).cell).create(buildCellAttrsFromTemplate(template), paragraphType?.create() ?? null));
850
861
  }
851
- const rowNode = table.child(rowIndex);
852
- const newRow = nodeTypeTableRow.create({
862
+ const rowNode = table.child(boundaryOffset === 0 ? rect.top : rect.bottom - 1);
863
+ const newRow = rowNode.type.create({
853
864
  height: rowNode.attrs["height"] ?? 360,
854
865
  heightRule: rowNode.attrs["heightRule"] ?? "atLeast"
855
866
  }, cells);
@@ -911,176 +922,58 @@ const TablePluginExtension = createExtension({
911
922
  }
912
923
  return true;
913
924
  }
914
- function addColumnLeft(state, dispatch) {
925
+ /**
926
+ * Insert a column beside the selected cells: left of the first column
927
+ * they cover, or right of the last. The table map places the new cells,
928
+ * so a row whose cell in that column is held by a merge from a row above
929
+ * still gains its cell at the right grid column, and `w:tblGrid` gains
930
+ * one column the width of its neighbour instead of being rebuilt.
931
+ */
932
+ function insertColumnBeside(state, dispatch, side) {
915
933
  const context = getTableContext(state);
916
934
  if (!context.isInTable || context.columnIndex === void 0 || !context.table || context.tablePos === void 0 || hasOmittedGridSlots(context.table)) return false;
917
935
  if (dispatch) {
918
- let tr = state.tr;
919
- const newColumnCount = (context.columnCount ?? 1) + 1;
920
- const newColWidthPercent = Math.floor(100 / newColumnCount);
921
- let rowPos = context.tablePos + 1;
922
- context.table.forEach((row) => {
923
- if (row.type.name === "tableRow") {
924
- let cellPos = rowPos + 1;
925
- let colIdx = 0;
926
- row.forEach((cell) => {
927
- if (colIdx === context.columnIndex) {
928
- const paragraph = nodeTypeParagraph.create();
929
- const cellAttrs = buildCellAttrsFromTemplate(cell, {
930
- colspan: 1,
931
- rowspan: 1
932
- });
933
- Object.assign(cellAttrs, statedCellWidth(newColWidthPercent, "pct"));
934
- const newCell = nodeTypeTableCell.create(cellAttrs, paragraph);
935
- tr = tr.insert(tr.mapping.map(cellPos), newCell);
936
- }
937
- cellPos += cell.nodeSize;
938
- colIdx += Number(cell.attrs["colspan"]) || 1;
936
+ const rect = selectedRect(state);
937
+ const tr = state.tr;
938
+ const paragraphType = state.schema.nodes["paragraph"];
939
+ insertTableColumn({
940
+ tr,
941
+ tablePosition: rect.tableStart - 1,
942
+ column: side === "left" ? rect.left : rect.right,
943
+ templateColumn: side === "left" ? rect.left : rect.right - 1,
944
+ createCell: (template) => {
945
+ const cellType = template?.type ?? tableNodeTypes(state.schema).cell;
946
+ const attrs = buildCellAttrsFromTemplate(template && (Number(template.attrs["colspan"]) || 1) === 1 ? template : null, {
947
+ colspan: 1,
948
+ rowspan: 1
939
949
  });
940
- if (context.columnIndex !== void 0 && colIdx <= context.columnIndex) {
941
- const paragraph = nodeTypeParagraph.create();
942
- const cellAttrs = buildCellAttrsFromTemplate(row.child(row.childCount - 1), {
943
- colspan: 1,
944
- rowspan: 1
945
- });
946
- Object.assign(cellAttrs, statedCellWidth(newColWidthPercent, "pct"));
947
- const newCell = nodeTypeTableCell.create(cellAttrs, paragraph);
948
- tr = tr.insert(tr.mapping.map(cellPos), newCell);
949
- }
950
+ return cellType.create(attrs, paragraphType?.create() ?? null);
950
951
  }
951
- rowPos += row.nodeSize;
952
952
  });
953
- const updatedTable = tr.doc.nodeAt(context.tablePos);
954
- if (updatedTable && updatedTable.type.name === "table") {
955
- const firstRow = updatedTable.child(0);
956
- if (firstRow.type.name === "tableRow") {
957
- let cellPos = context.tablePos + 2;
958
- firstRow.forEach((cell) => {
959
- if (cell.type.name === "tableCell" || cell.type.name === "tableHeader") tr = tr.setNodeMarkup(cellPos, void 0, mergeTableCellAttrs(cell, {
960
- width: newColWidthPercent,
961
- widthType: "pct"
962
- }));
963
- cellPos += cell.nodeSize;
964
- });
965
- }
966
- const colCount = firstRow.childCount;
967
- const tableWidthTwips = expectTableAttrs(updatedTable).width ?? 9360;
968
- const colWidthTwips = Math.floor(tableWidthTwips / Math.max(1, colCount));
969
- tr = tr.setNodeMarkup(context.tablePos, void 0, mergeTableAttrs(updatedTable, { columnWidths: Array.from({ length: colCount }, () => colWidthTwips) }));
970
- }
971
953
  dispatch(tr.scrollIntoView());
972
954
  }
973
955
  return true;
974
956
  }
957
+ function addColumnLeft(state, dispatch) {
958
+ return insertColumnBeside(state, dispatch, "left");
959
+ }
975
960
  function addColumnRight(state, dispatch) {
976
- const context = getTableContext(state);
977
- if (!context.isInTable || context.columnIndex === void 0 || !context.table || context.tablePos === void 0 || hasOmittedGridSlots(context.table)) return false;
978
- if (dispatch) {
979
- let tr = state.tr;
980
- const newColumnCount = (context.columnCount ?? 1) + 1;
981
- const newColWidthPercent = Math.floor(100 / newColumnCount);
982
- let rowPos = context.tablePos + 1;
983
- context.table.forEach((row) => {
984
- if (row.type.name === "tableRow") {
985
- let cellPos = rowPos + 1;
986
- let colIdx = 0;
987
- let insertedCount = 0;
988
- row.forEach((cell) => {
989
- cellPos += cell.nodeSize;
990
- colIdx += Number(cell.attrs["colspan"]) || 1;
991
- if (insertedCount === 0 && context.columnIndex !== void 0 && colIdx > context.columnIndex) {
992
- const paragraph = nodeTypeParagraph.create();
993
- const cellAttrs = buildCellAttrsFromTemplate(cell, {
994
- colspan: 1,
995
- rowspan: 1
996
- });
997
- Object.assign(cellAttrs, statedCellWidth(newColWidthPercent, "pct"));
998
- const newCell = nodeTypeTableCell.create(cellAttrs, paragraph);
999
- tr = tr.insert(tr.mapping.map(cellPos), newCell);
1000
- insertedCount += 1;
1001
- }
1002
- });
1003
- if (insertedCount === 0) {
1004
- const paragraph = nodeTypeParagraph.create();
1005
- const cellAttrs = buildCellAttrsFromTemplate(row.child(row.childCount - 1), {
1006
- colspan: 1,
1007
- rowspan: 1
1008
- });
1009
- Object.assign(cellAttrs, statedCellWidth(newColWidthPercent, "pct"));
1010
- const newCell = nodeTypeTableCell.create(cellAttrs, paragraph);
1011
- tr = tr.insert(tr.mapping.map(cellPos), newCell);
1012
- }
1013
- }
1014
- rowPos += row.nodeSize;
1015
- });
1016
- const updatedTable = tr.doc.nodeAt(context.tablePos);
1017
- if (updatedTable && updatedTable.type.name === "table") {
1018
- const firstRow = updatedTable.child(0);
1019
- if (firstRow.type.name === "tableRow") {
1020
- let cellPos = context.tablePos + 2;
1021
- firstRow.forEach((cell) => {
1022
- if (cell.type.name === "tableCell" || cell.type.name === "tableHeader") tr = tr.setNodeMarkup(cellPos, void 0, mergeTableCellAttrs(cell, {
1023
- width: newColWidthPercent,
1024
- widthType: "pct"
1025
- }));
1026
- cellPos += cell.nodeSize;
1027
- });
1028
- }
1029
- const colCount = firstRow.childCount;
1030
- const tableWidthTwips = expectTableAttrs(updatedTable).width ?? 9360;
1031
- const colWidthTwips = Math.floor(tableWidthTwips / Math.max(1, colCount));
1032
- tr = tr.setNodeMarkup(context.tablePos, void 0, mergeTableAttrs(updatedTable, { columnWidths: Array.from({ length: colCount }, () => colWidthTwips) }));
1033
- }
1034
- dispatch(tr.scrollIntoView());
1035
- }
1036
- return true;
961
+ return insertColumnBeside(state, dispatch, "right");
1037
962
  }
963
+ /**
964
+ * Delete the columns the selected cells cover. The table map finds each
965
+ * row's cell in them, a merged cell reaching past them narrows, a row
966
+ * left with no cell of its own goes, and `w:tblGrid` loses exactly those
967
+ * columns.
968
+ */
1038
969
  function deleteColumn(state, dispatch) {
1039
970
  const context = getTableContext(state);
1040
971
  if (!context.isInTable || context.columnIndex === void 0 || !context.table || context.tablePos === void 0 || (context.columnCount ?? 0) <= 1 || hasOmittedGridSlots(context.table)) return false;
972
+ const rect = selectedRect(state);
973
+ if (rect.right - rect.left >= rect.map.width) return false;
1041
974
  if (dispatch) {
1042
- let tr = state.tr;
1043
- const newColumnCount = (context.columnCount ?? 2) - 1;
1044
- const newColWidthPercent = Math.floor(100 / newColumnCount);
1045
- const deleteOps = [];
1046
- let rowPos = context.tablePos + 1;
1047
- context.table.forEach((row) => {
1048
- if (row.type.name === "tableRow") {
1049
- let cellPos = rowPos + 1;
1050
- let colIdx = 0;
1051
- row.forEach((cell) => {
1052
- const cellStart = cellPos;
1053
- const cellEnd = cellPos + cell.nodeSize;
1054
- const cellColspan = Number(cell.attrs["colspan"]) || 1;
1055
- if (context.columnIndex !== void 0 && colIdx <= context.columnIndex && context.columnIndex < colIdx + cellColspan) deleteOps.push({
1056
- start: cellStart,
1057
- end: cellEnd
1058
- });
1059
- cellPos = cellEnd;
1060
- colIdx += cellColspan;
1061
- });
1062
- }
1063
- rowPos += row.nodeSize;
1064
- });
1065
- for (const { start, end } of deleteOps.toReversed()) tr = tr.delete(start, end);
1066
- const updatedTable = tr.doc.nodeAt(context.tablePos);
1067
- if (updatedTable && updatedTable.type.name === "table") {
1068
- const firstRow = updatedTable.child(0);
1069
- if (firstRow.type.name === "tableRow") {
1070
- let cellPos = context.tablePos + 2;
1071
- firstRow.forEach((cell) => {
1072
- if (cell.type.name === "tableCell" || cell.type.name === "tableHeader") tr = tr.setNodeMarkup(cellPos, void 0, mergeTableCellAttrs(cell, {
1073
- width: newColWidthPercent,
1074
- widthType: "pct"
1075
- }));
1076
- cellPos += cell.nodeSize;
1077
- });
1078
- }
1079
- const colCount = firstRow.childCount;
1080
- const tableWidthTwips = expectTableAttrs(updatedTable).width ?? 9360;
1081
- const colWidthTwips = Math.floor(tableWidthTwips / Math.max(1, colCount));
1082
- tr = tr.setNodeMarkup(context.tablePos, void 0, mergeTableAttrs(updatedTable, { columnWidths: Array.from({ length: colCount }, () => colWidthTwips) }));
1083
- }
975
+ const tr = state.tr;
976
+ removeTableColumns(tr, rect.tableStart - 1, rect.left, rect.right);
1084
977
  dispatch(tr.scrollIntoView());
1085
978
  }
1086
979
  return true;
@@ -1125,16 +1018,9 @@ const TablePluginExtension = createExtension({
1125
1018
  if (!context.isInTable || context.tablePos === void 0 || !context.table || context.columnIndex === void 0) return false;
1126
1019
  if (dispatch) {
1127
1020
  const tableStart = context.tablePos + 1;
1128
- const firstRow = context.table.child(0);
1129
- const lastRow = context.table.child(context.table.childCount - 1);
1130
- let firstCellPos = tableStart + 1;
1131
- for (let c = 0; c < context.columnIndex && c < firstRow.childCount; c++) firstCellPos += firstRow.child(c).nodeSize;
1132
- let lastRowPos = tableStart;
1133
- for (let r = 0; r < context.table.childCount - 1; r++) lastRowPos += context.table.child(r).nodeSize;
1134
- let lastCellPos = lastRowPos + 1;
1135
- for (let c = 0; c < context.columnIndex && c < lastRow.childCount; c++) lastCellPos += lastRow.child(c).nodeSize;
1136
- const cellSel = CellSelection.create(state.doc, firstCellPos, lastCellPos);
1137
- dispatch(state.tr.setSelection(cellSel));
1021
+ const firstCell = TableMap.get(context.table).map[context.columnIndex];
1022
+ if (firstCell === void 0) return false;
1023
+ dispatch(state.tr.setSelection(CellSelection.colSelection(state.doc.resolve(tableStart + firstCell))));
1138
1024
  }
1139
1025
  return true;
1140
1026
  }
@@ -2017,6 +1903,13 @@ const TablePluginExtension = createExtension({
2017
1903
  return DecorationSet.empty;
2018
1904
  } }
2019
1905
  });
1906
+ const tableCellPastePlugin = new Plugin({
1907
+ key: new PluginKey("tableCellPaste"),
1908
+ props: {
1909
+ transformPasted: (slice) => pastedSliceWithNewTableCells(slice),
1910
+ handlePaste: (view, _event, slice) => pasteTableCells(view.state, slice, view.dispatch)
1911
+ }
1912
+ });
2020
1913
  return {
2021
1914
  plugins: [
2022
1915
  columnResizing({
@@ -2024,6 +1917,7 @@ const TablePluginExtension = createExtension({
2024
1917
  cellMinWidth: 25,
2025
1918
  lastColumnResizable: true
2026
1919
  }),
1920
+ tableCellPastePlugin,
2027
1921
  tableEditing(),
2028
1922
  activeCellPlugin
2029
1923
  ],
@@ -63,6 +63,13 @@ declare const Priority: {
63
63
  readonly Lowest: 200;
64
64
  };
65
65
  type ExtensionContext = {
66
+ /**
67
+ * The schema this runtime was built with. The documents the runtime edits
68
+ * may be of another instance of it (header, footer and note editors each
69
+ * build a runtime, and every document is parsed into the shared schema), so
70
+ * commands, key bindings and plugins build and compare nodes and marks with
71
+ * the types of the state they act on, never with types taken from here.
72
+ */
66
73
  schema: Schema;
67
74
  };
68
75
  type FolioCommandArguments = {
@@ -0,0 +1,9 @@
1
+ import { EditorState, Transaction } from "prosemirror-state";
2
+ //#region src/prosemirror/hyperlinkRemoval.d.ts
3
+ /**
4
+ * Remove the hyperlinks from [`from`, `to`) of `tr.doc`: directly, or, with
5
+ * suggestions on, as a tracked replacement of the linked text by plain text.
6
+ */
7
+ declare const removeHyperlinkInRange: (state: EditorState, tr: Transaction, from: number, to: number) => Transaction;
8
+ //#endregion
9
+ export { removeHyperlinkInRange };