@stll/folio-core 0.45.0 → 0.47.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (451) hide show
  1. package/dist/ai-edits/apply.js +85 -43
  2. package/dist/ai-edits/headless.js +2 -2
  3. package/dist/ai-edits/read.d.ts +1 -0
  4. package/dist/ai-edits/read.js +1 -0
  5. package/dist/ai-edits/snapshot.js +32 -27
  6. package/dist/ai-edits/table-cell-mutations.js +15 -7
  7. package/dist/ai-edits/table-geometry.js +21 -18
  8. package/dist/ai-edits/table-template.js +2 -2
  9. package/dist/compare/compare.js +2 -5
  10. package/dist/compare/content-alignment.js +108 -12
  11. package/dist/compare/content-types.d.ts +8 -2
  12. package/dist/compare/content.js +2 -11
  13. package/dist/compare/plan.js +7 -4
  14. package/dist/compare/scenario.js +2 -5
  15. package/dist/compare/section-boundary-properties.js +1 -2
  16. package/dist/compare/types.d.ts +9 -1
  17. package/dist/compare/types.js +12 -1
  18. package/dist/compat/eigenpal.d.ts +2 -1
  19. package/dist/compat/eigenpal.js +2 -1
  20. package/dist/content-controls/checkboxDisplay.d.ts +17 -0
  21. package/dist/content-controls/checkboxDisplay.js +46 -0
  22. package/dist/content-controls/findContentControls.js +3 -1
  23. package/dist/content-controls/mutateContentControls.js +57 -43
  24. package/dist/controller/contentControlWidgetController.d.ts +1 -0
  25. package/dist/controller/contentControlWidgetController.js +3 -0
  26. package/dist/controller/hiddenEditorApi.js +3 -1
  27. package/dist/controller/hiddenEditorManager.d.ts +1 -1
  28. package/dist/controller/hiddenEditorManager.js +6 -3
  29. package/dist/controller/layoutPipeline.js +8 -3
  30. package/dist/display-list/build/buildDisplayList.js +20 -1
  31. package/dist/display-list/build/imagePrimitives.d.ts +4 -4
  32. package/dist/display-list/build/imagePrimitives.js +38 -18
  33. package/dist/display-list/build/pageBorderPrimitives.js +2 -1
  34. package/dist/display-list/build/paragraphPrimitives.js +113 -14
  35. package/dist/display-list/build/previewPrimitives.d.ts +10 -0
  36. package/dist/display-list/build/previewPrimitives.js +89 -0
  37. package/dist/display-list/build/strokes.d.ts +177 -8
  38. package/dist/display-list/build/strokes.js +167 -47
  39. package/dist/display-list/build/tablePrimitives.js +4 -2
  40. package/dist/display-list/build/textBoxPrimitives.js +6 -4
  41. package/dist/display-list/build/textDecorations.d.ts +15 -1
  42. package/dist/display-list/build/textDecorations.js +15 -1
  43. package/dist/display-list/dom/renderDisplayListToDom.js +11 -21
  44. package/dist/display-list/primitives.d.ts +13 -2
  45. package/dist/display-list/primitives.js +36 -1
  46. package/dist/display-list/types.d.ts +17 -0
  47. package/dist/document-operations.js +2 -1
  48. package/dist/docx/attributeRemainder.d.ts +76 -0
  49. package/dist/docx/attributeRemainder.js +111 -0
  50. package/dist/docx/blockContentParser.d.ts +3 -1
  51. package/dist/docx/blockContentParser.js +102 -106
  52. package/dist/docx/blockPlainText.d.ts +3 -4
  53. package/dist/docx/blockPlainText.js +3 -0
  54. package/dist/docx/borderParser.js +26 -11
  55. package/dist/docx/builtInStyles.d.ts +8 -16
  56. package/dist/docx/builtInStyles.js +54 -17
  57. package/dist/docx/commentAnchorIndex.d.ts +30 -0
  58. package/dist/docx/commentAnchorIndex.js +50 -0
  59. package/dist/docx/commentParser.d.ts +1 -1
  60. package/dist/docx/commentParser.js +56 -39
  61. package/dist/docx/commentRangeIntegrity.d.ts +16 -1
  62. package/dist/docx/commentRangeIntegrity.js +42 -1
  63. package/dist/docx/commentRangeJoin.d.ts +9 -0
  64. package/dist/docx/commentRangeJoin.js +33 -0
  65. package/dist/docx/commentReferenceCompletion.d.ts +9 -0
  66. package/dist/docx/commentReferenceCompletion.js +47 -0
  67. package/dist/docx/commentReferenceNormalization.js +3 -1
  68. package/dist/docx/commentReplyMarkers.js +11 -19
  69. package/dist/docx/compatibility.js +56 -41
  70. package/dist/docx/containerChildren.d.ts +208 -0
  71. package/dist/docx/containerChildren.gen.d.ts +43 -0
  72. package/dist/docx/containerChildren.gen.js +263 -0
  73. package/dist/docx/containerChildren.js +153 -0
  74. package/dist/docx/diagramPreview.d.ts +14 -2
  75. package/dist/docx/diagramPreview.js +81 -169
  76. package/dist/docx/documentParser.d.ts +1 -1
  77. package/dist/docx/documentParser.js +7 -4
  78. package/dist/docx/drawingAnchor.d.ts +87 -0
  79. package/dist/docx/drawingAnchor.js +201 -0
  80. package/dist/docx/drawingUtils.d.ts +43 -38
  81. package/dist/docx/drawingUtils.js +205 -118
  82. package/dist/docx/ensureParaIds.js +17 -7
  83. package/dist/docx/fieldParser.d.ts +1 -1
  84. package/dist/docx/fieldParser.js +4 -4
  85. package/dist/docx/fieldState.d.ts +26 -0
  86. package/dist/docx/fieldState.js +53 -0
  87. package/dist/docx/fontTableParser.js +102 -41
  88. package/dist/docx/footnoteParser.d.ts +1 -1
  89. package/dist/docx/footnoteParser.js +10 -6
  90. package/dist/docx/graphicFrameLocks.d.ts +16 -4
  91. package/dist/docx/graphicFrameLocks.js +19 -6
  92. package/dist/docx/groupDrawingParser.js +4 -3
  93. package/dist/docx/headerFooterParser.js +1 -1
  94. package/dist/docx/headerFooterReferenceNormalization.js +1 -0
  95. package/dist/docx/hyperlinkParser.d.ts +66 -9
  96. package/dist/docx/hyperlinkParser.js +153 -26
  97. package/dist/docx/imageParser.js +160 -115
  98. package/dist/docx/index.d.ts +2 -1
  99. package/dist/docx/index.js +2 -1
  100. package/dist/docx/inlineContentRemovals.d.ts +28 -0
  101. package/dist/docx/inlineContentRemovals.js +46 -0
  102. package/dist/docx/inlineWrapperContent.d.ts +166 -0
  103. package/dist/docx/inlineWrapperContent.js +165 -0
  104. package/dist/docx/inlineWrapperParser.d.ts +11 -0
  105. package/dist/docx/inlineWrapperParser.js +60 -0
  106. package/dist/docx/nonVisualDrawingProps.d.ts +5 -13
  107. package/dist/docx/normalizeBaseDirection.js +12 -1
  108. package/dist/docx/numberingParser.d.ts +25 -2
  109. package/dist/docx/numberingParser.js +264 -361
  110. package/dist/docx/numberingReference.d.ts +9 -16
  111. package/dist/docx/numberingReference.js +17 -16
  112. package/dist/docx/numberingReferenceNormalization.js +7 -7
  113. package/dist/docx/ooxmlCounterFormatter.d.ts +1 -1
  114. package/dist/docx/ooxmlCounterFormatter.js +4 -1
  115. package/dist/docx/paraIdAttribute.d.ts +111 -0
  116. package/dist/docx/paraIdAttribute.js +142 -0
  117. package/dist/docx/paragraphParser.d.ts +10 -25
  118. package/dist/docx/paragraphParser.js +421 -496
  119. package/dist/docx/paragraphProperties.d.ts +23 -0
  120. package/dist/docx/paragraphProperties.js +279 -0
  121. package/dist/docx/paragraphPropertySource.js +7 -1
  122. package/dist/docx/paragraphTextBoxEnrichment.d.ts +3 -2
  123. package/dist/docx/paragraphTextBoxEnrichment.js +20 -59
  124. package/dist/docx/paragraphTraversal.d.ts +14 -10
  125. package/dist/docx/paragraphTraversal.js +53 -52
  126. package/dist/docx/parseWarningMessage.js +5 -1
  127. package/dist/docx/parserEnums.d.ts +6 -8
  128. package/dist/docx/parserEnums.js +4 -6
  129. package/dist/docx/preservedRunContent.d.ts +32 -0
  130. package/dist/docx/preservedRunContent.js +96 -0
  131. package/dist/docx/previewBudget.d.ts +44 -23
  132. package/dist/docx/previewBudget.js +61 -30
  133. package/dist/docx/propertyElementAttributes.d.ts +178 -0
  134. package/dist/docx/propertyElementAttributes.js +114 -0
  135. package/dist/docx/renderedPageBreakNormalization.js +4 -6
  136. package/dist/docx/rezip.d.ts +28 -2
  137. package/dist/docx/rezip.js +152 -27
  138. package/dist/docx/runConsolidator.d.ts +42 -2
  139. package/dist/docx/runConsolidator.js +60 -6
  140. package/dist/docx/runParser.d.ts +55 -19
  141. package/dist/docx/runParser.js +394 -306
  142. package/dist/docx/runPayload.d.ts +5 -0
  143. package/dist/docx/runPayload.js +4 -0
  144. package/dist/docx/sdtProperties.d.ts +39 -5
  145. package/dist/docx/sdtProperties.js +205 -84
  146. package/dist/docx/sdtPropertiesPatch.d.ts +5 -9
  147. package/dist/docx/sdtPropertiesPatch.js +68 -112
  148. package/dist/docx/sectionParser.d.ts +1 -2
  149. package/dist/docx/sectionParser.js +241 -238
  150. package/dist/docx/selectiveSave.js +3 -2
  151. package/dist/docx/selectiveXmlPatch.d.ts +66 -3
  152. package/dist/docx/selectiveXmlPatch.js +276 -133
  153. package/dist/docx/serializer/blockSdtSerializer.js +2 -96
  154. package/dist/docx/serializer/borderSerializer.d.ts +5 -5
  155. package/dist/docx/serializer/borderSerializer.js +12 -10
  156. package/dist/docx/serializer/commentSerializer.js +5 -7
  157. package/dist/docx/serializer/documentSerializer.js +11 -11
  158. package/dist/docx/serializer/fontTableSerializer.js +31 -3
  159. package/dist/docx/serializer/headerFooterSerializer.js +10 -9
  160. package/dist/docx/serializer/markupRangeAttributes.d.ts +9 -1
  161. package/dist/docx/serializer/markupRangeAttributes.js +9 -1
  162. package/dist/docx/serializer/noteSerializer.js +11 -8
  163. package/dist/docx/serializer/numberingSerializer.d.ts +1 -6
  164. package/dist/docx/serializer/numberingSerializer.js +81 -79
  165. package/dist/docx/serializer/paragraphSerializer.d.ts +1 -9
  166. package/dist/docx/serializer/paragraphSerializer.js +156 -236
  167. package/dist/docx/serializer/runSerializer.d.ts +1 -5
  168. package/dist/docx/serializer/runSerializer.js +134 -75
  169. package/dist/docx/serializer/sdtPropertiesSerializer.d.ts +26 -0
  170. package/dist/docx/serializer/sdtPropertiesSerializer.js +111 -0
  171. package/dist/docx/serializer/sectionPropertiesSerializer.js +42 -49
  172. package/dist/docx/serializer/settingsSerializer.js +6 -4
  173. package/dist/docx/serializer/stylesSerializer.js +8 -11
  174. package/dist/docx/serializer/tableSerializer.js +283 -105
  175. package/dist/docx/serializer/textFormattingSerializer.d.ts +28 -4
  176. package/dist/docx/serializer/textFormattingSerializer.js +111 -101
  177. package/dist/docx/serializer/xmlUtils.d.ts +1 -1
  178. package/dist/docx/serializer/xmlUtils.js +1 -1
  179. package/dist/docx/server/createBilingualDocument.js +20 -16
  180. package/dist/docx/server/materializeYjsDocx.d.ts +1 -1
  181. package/dist/docx/server/materializeYjsDocx.js +9 -1
  182. package/dist/docx/server/migrateYjsAttrSchema.d.ts +55 -0
  183. package/dist/docx/server/migrateYjsAttrSchema.js +95 -0
  184. package/dist/docx/settingsParser.js +7 -4
  185. package/dist/docx/shadingParser.d.ts +2 -1
  186. package/dist/docx/shadingParser.js +43 -7
  187. package/dist/docx/shapeParser.js +13 -8
  188. package/dist/docx/strictNames.d.ts +11 -0
  189. package/dist/docx/strictNames.gen.d.ts +45 -0
  190. package/dist/docx/strictNames.gen.js +50 -0
  191. package/dist/docx/strictNames.js +43 -0
  192. package/dist/docx/strictValueEncodings.gen.js +133 -131
  193. package/dist/docx/styleParser.js +17 -349
  194. package/dist/docx/tableParser.d.ts +11 -2
  195. package/dist/docx/tableParser.js +665 -220
  196. package/dist/docx/textBoxParser.d.ts +28 -3
  197. package/dist/docx/textBoxParser.js +69 -9
  198. package/dist/docx/themeColorAttribute.d.ts +13 -0
  199. package/dist/docx/themeColorAttribute.js +24 -0
  200. package/dist/docx/trackedMoveRangeNormalization.js +2 -1
  201. package/dist/docx/unzip.js +5 -4
  202. package/dist/docx/vmlImageParser.d.ts +30 -5
  203. package/dist/docx/vmlImageParser.js +91 -32
  204. package/dist/docx/vmlPreview.js +2 -2
  205. package/dist/docx/wrapPolygon.d.ts +30 -0
  206. package/dist/docx/wrapPolygon.js +70 -0
  207. package/dist/docx/xmlEncoding.d.ts +5 -0
  208. package/dist/docx/xmlEncoding.js +12 -0
  209. package/dist/docx/xmlParser.d.ts +23 -1
  210. package/dist/docx/xmlParser.js +31 -2
  211. package/dist/fonts/embeddedFonts.js +3 -3
  212. package/dist/headless-layout.js +12 -1
  213. package/dist/i18n/messages/catalogs.gen.d.ts +68 -0
  214. package/dist/i18n/messages/catalogs.gen.js +102 -34
  215. package/dist/i18n/messages/messages.gen.d.ts +4 -0
  216. package/dist/index.d.ts +2 -1
  217. package/dist/index.js +2 -1
  218. package/dist/internal/headlessRevisionResolution.js +9 -0
  219. package/dist/internal/pageBreakRunSourceDescendantIndex.js +7 -2
  220. package/dist/internal/paragraphFormattingSerialization.d.ts +20 -9
  221. package/dist/internal/paragraphFormattingSerialization.js +118 -83
  222. package/dist/layout-bridge/convert/footnoteLayout.d.ts +1 -0
  223. package/dist/layout-bridge/convert/footnoteLayout.js +1 -0
  224. package/dist/layout-bridge/convert/headerFooterLayout.d.ts +1 -0
  225. package/dist/layout-bridge/convert/headerFooterLayout.js +2 -0
  226. package/dist/layout-bridge/convert/toFlowBlocks.d.ts +17 -12
  227. package/dist/layout-bridge/convert/toFlowBlocks.js +267 -101
  228. package/dist/layout-engine/index.d.ts +2 -2
  229. package/dist/layout-engine/index.js +53 -17
  230. package/dist/layout-engine/measure/measureBlocks.d.ts +3 -0
  231. package/dist/layout-engine/measure/measureBlocks.js +6 -10
  232. package/dist/layout-engine/measure/tableCellFloating.d.ts +2 -0
  233. package/dist/layout-engine/measure/tableCellFloating.js +2 -0
  234. package/dist/layout-engine/measure/tableCellGrid.js +2 -1
  235. package/dist/layout-engine/measure/tableFragmentBorderGeometry.js +2 -1
  236. package/dist/layout-engine/measure/tableInlinePlacement.js +2 -5
  237. package/dist/layout-engine/paragraphSequence.js +3 -2
  238. package/dist/layout-engine/renderedBreakReconciliation.js +2 -1
  239. package/dist/layout-engine/section-breaks.d.ts +49 -2
  240. package/dist/layout-engine/section-breaks.js +55 -4
  241. package/dist/layout-engine/types.d.ts +69 -17
  242. package/dist/layout-engine/types.js +16 -1
  243. package/dist/layout-painter/borderStroke.d.ts +18 -4
  244. package/dist/layout-painter/renderImage.d.ts +5 -1
  245. package/dist/layout-painter/renderImage.js +10 -3
  246. package/dist/layout-painter/renderPage.d.ts +2 -0
  247. package/dist/layout-painter/renderPage.js +10 -4
  248. package/dist/layout-painter/renderParagraph.d.ts +14 -1
  249. package/dist/layout-painter/renderParagraph.js +34 -28
  250. package/dist/layout-painter/renderTable.d.ts +4 -1
  251. package/dist/layout-painter/renderTable.js +22 -22
  252. package/dist/layout-painter/renderTextBox.js +5 -3
  253. package/dist/managers/autoSaveCodec.d.ts +9 -1
  254. package/dist/managers/autoSaveCodec.js +12 -4
  255. package/dist/markdown/renderBlock.js +3 -0
  256. package/dist/markdown/renderRuns.d.ts +1 -1
  257. package/dist/markdown/renderRuns.js +34 -6
  258. package/dist/markdown/renderTable.js +24 -6
  259. package/dist/markdown/trailers.js +4 -1
  260. package/dist/model.d.ts +3 -3
  261. package/dist/model.js +2 -2
  262. package/dist/paged-layout/sectionBlockWidths.d.ts +3 -0
  263. package/dist/paged-layout/sectionBlockWidths.js +26 -4
  264. package/dist/pdf/images.js +142 -6
  265. package/dist/prosemirror/attrs/index.d.ts +34 -5
  266. package/dist/prosemirror/attrs/index.js +639 -48
  267. package/dist/prosemirror/authoredTransformAttrs.d.ts +28 -0
  268. package/dist/prosemirror/authoredTransformAttrs.js +64 -0
  269. package/dist/prosemirror/bookmarkBoundaryAttrs.d.ts +9 -1
  270. package/dist/prosemirror/bookmarkBoundaryAttrs.js +22 -3
  271. package/dist/prosemirror/commands/comments.js +68 -53
  272. package/dist/prosemirror/commands/contentControls.js +33 -20
  273. package/dist/prosemirror/commands/image.d.ts +10 -3
  274. package/dist/prosemirror/commands/image.js +46 -29
  275. package/dist/prosemirror/commands/pageBreak.js +1 -1
  276. package/dist/prosemirror/commands/paragraph.d.ts +2 -1
  277. package/dist/prosemirror/commands/propertyChangeScope.d.ts +12 -4
  278. package/dist/prosemirror/commands/propertyChangeScope.js +22 -4
  279. package/dist/prosemirror/commands/sectionBreak.d.ts +33 -1
  280. package/dist/prosemirror/commands/sectionBreak.js +187 -11
  281. package/dist/prosemirror/commentReferenceAttrs.d.ts +8 -0
  282. package/dist/prosemirror/commentReferenceAttrs.js +33 -0
  283. package/dist/prosemirror/commentReferenceIntegrity.d.ts +47 -0
  284. package/dist/prosemirror/commentReferenceIntegrity.js +43 -0
  285. package/dist/prosemirror/conversion/fromProseDoc.d.ts +17 -12
  286. package/dist/prosemirror/conversion/fromProseDoc.js +553 -207
  287. package/dist/prosemirror/conversion/index.d.ts +2 -2
  288. package/dist/prosemirror/conversion/preservedSinkCarriers.d.ts +39 -0
  289. package/dist/prosemirror/conversion/preservedSinkCarriers.js +19 -0
  290. package/dist/prosemirror/conversion/runShadingMark.js +14 -1
  291. package/dist/prosemirror/conversion/sdtAttrs.d.ts +10 -1
  292. package/dist/prosemirror/conversion/sdtAttrs.js +19 -5
  293. package/dist/prosemirror/conversion/toProseDoc.d.ts +7 -9
  294. package/dist/prosemirror/conversion/toProseDoc.js +801 -411
  295. package/dist/prosemirror/emptyRangeAnchor.d.ts +53 -0
  296. package/dist/prosemirror/emptyRangeAnchor.js +158 -0
  297. package/dist/prosemirror/extensions/StarterKit.js +14 -58
  298. package/dist/prosemirror/extensions/core/DocExtension.js +1 -1
  299. package/dist/prosemirror/extensions/core/ParagraphExtension.js +21 -16
  300. package/dist/prosemirror/extensions/features/BaseKeymapExtension.js +48 -29
  301. package/dist/prosemirror/extensions/features/EmptyParagraphFormatExtension.js +3 -1
  302. package/dist/prosemirror/extensions/features/ImagePasteExtension.js +5 -3
  303. package/dist/prosemirror/extensions/features/ListExtension.js +43 -24
  304. package/dist/prosemirror/extensions/features/ParaIdAllocatorExtension.js +1 -0
  305. package/dist/prosemirror/extensions/features/ParagraphChangeTrackerExtension.js +4 -3
  306. package/dist/prosemirror/extensions/features/PasteCleanupExtension.d.ts +3 -3
  307. package/dist/prosemirror/extensions/features/PasteCleanupExtension.js +5 -5
  308. package/dist/prosemirror/extensions/features/pasteCleanup.d.ts +3 -1
  309. package/dist/prosemirror/extensions/features/pasteCleanup.js +56 -2
  310. package/dist/prosemirror/extensions/features/pastedHeadingStyles.js +5 -4
  311. package/dist/prosemirror/extensions/markRegistry.d.ts +65 -0
  312. package/dist/prosemirror/extensions/markRegistry.js +138 -0
  313. package/dist/prosemirror/extensions/marks/InlineWrapperExtension.d.ts +18 -0
  314. package/dist/prosemirror/extensions/marks/InlineWrapperExtension.js +77 -0
  315. package/dist/prosemirror/extensions/marks/RunIdentityExtension.d.ts +26 -0
  316. package/dist/prosemirror/extensions/marks/RunIdentityExtension.js +134 -0
  317. package/dist/prosemirror/extensions/marks/TrackedChangeExtensions.js +2 -1
  318. package/dist/prosemirror/extensions/marks/UnderlineExtension.js +12 -18
  319. package/dist/prosemirror/extensions/marks/markUtils.d.ts +2 -1
  320. package/dist/prosemirror/extensions/marks/markUtils.js +49 -5
  321. package/dist/prosemirror/extensions/nodes/BlockBookmarkBoundaryExtension.d.ts +29 -0
  322. package/dist/prosemirror/extensions/nodes/BlockBookmarkBoundaryExtension.js +46 -0
  323. package/dist/prosemirror/extensions/nodes/BlockSdtExtension.d.ts +4 -3
  324. package/dist/prosemirror/extensions/nodes/BlockSdtExtension.js +18 -13
  325. package/dist/prosemirror/extensions/nodes/BookmarkBoundaryExtension.js +28 -53
  326. package/dist/prosemirror/extensions/nodes/CommentReferenceExtension.d.ts +11 -0
  327. package/dist/prosemirror/extensions/nodes/CommentReferenceExtension.js +97 -0
  328. package/dist/prosemirror/extensions/nodes/FieldExtension.js +9 -7
  329. package/dist/prosemirror/extensions/nodes/ImageExtension.js +24 -1
  330. package/dist/prosemirror/extensions/nodes/MoveRangeBoundaryExtension.d.ts +11 -0
  331. package/dist/prosemirror/extensions/nodes/MoveRangeBoundaryExtension.js +43 -0
  332. package/dist/prosemirror/extensions/nodes/PreservedBlockExtension.d.ts +32 -0
  333. package/dist/prosemirror/extensions/nodes/PreservedBlockExtension.js +67 -0
  334. package/dist/prosemirror/extensions/nodes/PreservedXmlExtension.d.ts +16 -0
  335. package/dist/prosemirror/extensions/nodes/PreservedXmlExtension.js +60 -0
  336. package/dist/prosemirror/extensions/nodes/RangeAnchorExtension.d.ts +13 -0
  337. package/dist/prosemirror/extensions/nodes/RangeAnchorExtension.js +65 -0
  338. package/dist/prosemirror/extensions/nodes/SdtExtension.d.ts +3 -1
  339. package/dist/prosemirror/extensions/nodes/SdtExtension.js +22 -16
  340. package/dist/prosemirror/extensions/nodes/ShapeExtension.js +7 -0
  341. package/dist/prosemirror/extensions/nodes/TableExtension.js +142 -123
  342. package/dist/prosemirror/extensions/nodes/TextBoxExtension.js +9 -1
  343. package/dist/prosemirror/extensions/nodes/bookmarkBoundaryDom.d.ts +23 -0
  344. package/dist/prosemirror/extensions/nodes/bookmarkBoundaryDom.js +57 -0
  345. package/dist/prosemirror/extensions/types.d.ts +12 -3
  346. package/dist/prosemirror/index.d.ts +4 -2
  347. package/dist/prosemirror/index.js +2 -1
  348. package/dist/prosemirror/inlineWrapperStack.d.ts +39 -0
  349. package/dist/prosemirror/inlineWrapperStack.js +92 -0
  350. package/dist/prosemirror/listMarker.d.ts +2 -2
  351. package/dist/prosemirror/listMarker.js +7 -8
  352. package/dist/prosemirror/listRenderingAttrs.js +11 -1
  353. package/dist/prosemirror/listState.d.ts +62 -0
  354. package/dist/prosemirror/listState.js +49 -0
  355. package/dist/prosemirror/moveRangeBoundaryAttrs.d.ts +13 -0
  356. package/dist/prosemirror/moveRangeBoundaryAttrs.js +114 -0
  357. package/dist/prosemirror/numberedRefFields.js +4 -4
  358. package/dist/prosemirror/numberingAttr.d.ts +55 -0
  359. package/dist/prosemirror/numberingAttr.js +74 -0
  360. package/dist/prosemirror/outlineLevelAttr.d.ts +29 -0
  361. package/dist/prosemirror/outlineLevelAttr.js +42 -0
  362. package/dist/prosemirror/pageBreakRunProjection.d.ts +17 -7
  363. package/dist/prosemirror/pageBreakRunProjection.js +19 -9
  364. package/dist/prosemirror/paragraphFormattingProvenance.d.ts +9 -0
  365. package/dist/prosemirror/paragraphFormattingProvenance.js +4 -1
  366. package/dist/prosemirror/plugins/selectionTracker.d.ts +3 -6
  367. package/dist/prosemirror/plugins/selectionTracker.js +3 -10
  368. package/dist/prosemirror/rangeAnchorAttrs.d.ts +14 -0
  369. package/dist/prosemirror/rangeAnchorAttrs.js +101 -0
  370. package/dist/prosemirror/replacedAnnotations.d.ts +59 -0
  371. package/dist/prosemirror/replacedAnnotations.js +183 -0
  372. package/dist/prosemirror/revisionCarriers.d.ts +86 -2
  373. package/dist/prosemirror/revisionCarriers.js +86 -60
  374. package/dist/prosemirror/runFormattingInlineCarriers.d.ts +5 -1
  375. package/dist/prosemirror/runFormattingInlineCarriers.js +7 -1
  376. package/dist/prosemirror/runIdentity.d.ts +28 -0
  377. package/dist/prosemirror/runIdentity.js +36 -0
  378. package/dist/prosemirror/runStyleFormatting.js +1 -1
  379. package/dist/prosemirror/schema/index.d.ts +3 -3
  380. package/dist/prosemirror/schema/marks.d.ts +47 -4
  381. package/dist/prosemirror/schema/nodes.d.ts +309 -26
  382. package/dist/prosemirror/schema/nodes.js +16 -1
  383. package/dist/prosemirror/sectionCarrier.d.ts +37 -0
  384. package/dist/prosemirror/sectionCarrier.js +40 -0
  385. package/dist/prosemirror/selectionState.d.ts +3 -0
  386. package/dist/prosemirror/selectionState.js +4 -1
  387. package/dist/prosemirror/styles/resolvedStyleAttrs.d.ts +5 -4
  388. package/dist/prosemirror/styles/resolvedStyleAttrs.js +15 -13
  389. package/dist/prosemirror/tableResize.js +5 -6
  390. package/dist/prosemirror/trackedRunInlineAtoms.d.ts +4 -0
  391. package/dist/prosemirror/trackedRunInlineAtoms.js +4 -0
  392. package/dist/prosemirror/utils/extractTrackedChanges.d.ts +10 -11
  393. package/dist/prosemirror/utils/extractTrackedChanges.js +109 -92
  394. package/dist/prosemirror/validation.js +31 -6
  395. package/dist/prosemirror/yjsDocumentMetadata.d.ts +73 -0
  396. package/dist/prosemirror/yjsDocumentMetadata.js +592 -0
  397. package/dist/prosemirror/zeroWidthAnchors.js +6 -0
  398. package/dist/render-dom/commentAnchorAttributes.d.ts +37 -0
  399. package/dist/render-dom/commentAnchorAttributes.js +54 -0
  400. package/dist/server.d.ts +3 -1
  401. package/dist/server.js +3 -1
  402. package/dist/style-sets/extract.js +4 -4
  403. package/dist/style-sets/stellaStyle.js +36 -23
  404. package/dist/types/colors.d.ts +2 -2
  405. package/dist/types/content.d.ts +2 -2
  406. package/dist/types/documentEnumValues.d.ts +53 -26
  407. package/dist/types/documentEnumValues.js +72 -174
  408. package/dist/types/formatting.d.ts +2 -2
  409. package/dist/types/index.d.ts +9 -2
  410. package/dist/utils/borderCss.d.ts +246 -0
  411. package/dist/utils/borderCss.js +325 -0
  412. package/dist/utils/clipboard.d.ts +9 -1
  413. package/dist/utils/clipboard.js +27 -1
  414. package/dist/utils/colorResolver.d.ts +4 -3
  415. package/dist/utils/colorResolver.js +45 -76
  416. package/dist/utils/createDocument.js +24 -6
  417. package/dist/utils/findReplace.js +52 -10
  418. package/dist/utils/formatToStyle.d.ts +84 -2
  419. package/dist/utils/formatToStyle.js +133 -52
  420. package/dist/utils/headingCollector.js +3 -2
  421. package/dist/utils/imageLuminance.d.ts +15 -0
  422. package/dist/utils/imageLuminance.js +32 -0
  423. package/dist/utils/mergeDocumentContent.js +12 -20
  424. package/dist/utils/paragraphFormattingMerge.js +27 -6
  425. package/dist/utils/replaceText.js +1 -0
  426. package/dist/utils/tableOperations.d.ts +5 -3
  427. package/dist/utils/tableOperations.js +14 -1
  428. package/dist/utils/tablePlacement.d.ts +7 -0
  429. package/dist/utils/tablePlacement.js +14 -0
  430. package/dist/utils/textDirectionFlow.d.ts +15 -0
  431. package/dist/utils/textDirectionFlow.js +38 -0
  432. package/dist/utils/textFormattingMerge.js +16 -4
  433. package/package.json +10 -10
  434. package/dist/ai-edits/__fixtures__/paragraphs.d.ts +0 -17
  435. package/dist/ai-edits/__fixtures__/paragraphs.js +0 -33
  436. package/dist/compare/__fixtures__/body-sequence.d.ts +0 -119
  437. package/dist/compare/__fixtures__/body-sequence.js +0 -225
  438. package/dist/compare/__fixtures__/nested-table.d.ts +0 -16
  439. package/dist/compare/__fixtures__/nested-table.js +0 -50
  440. package/dist/compare/__fixtures__/numbered-list.d.ts +0 -34
  441. package/dist/compare/__fixtures__/numbered-list.js +0 -85
  442. package/dist/docx/blockRangeMarkers.d.ts +0 -36
  443. package/dist/docx/blockRangeMarkers.js +0 -59
  444. package/dist/docx/bookmarkPlacement.d.ts +0 -9
  445. package/dist/docx/bookmarkPlacement.js +0 -50
  446. package/dist/fonts/embeddedFontTable.d.ts +0 -45
  447. package/dist/fonts/embeddedFontTable.js +0 -80
  448. package/dist/prosemirror/extensions/marks/PageBreakRunOwnerExtension.d.ts +0 -13
  449. package/dist/prosemirror/extensions/marks/PageBreakRunOwnerExtension.js +0 -39
  450. package/dist/prosemirror/yjsParagraphSourceContract.d.ts +0 -9
  451. package/dist/prosemirror/yjsParagraphSourceContract.js +0 -26
@@ -1,102 +1,8 @@
1
- import { reconcileRawSdtPr } from "../sdtPropertiesPatch.js";
2
- import { isSingleWellFormedElement } from "./xmlUtils.js";
3
- import { escapeXmlAttribute } from "@stll/docx-core";
1
+ import { serializeSdtWrapper } from "./sdtPropertiesSerializer.js";
4
2
  //#region src/docx/serializer/blockSdtSerializer.ts
5
- /**
6
- * Block-level SDT serializer.
7
- *
8
- * Replays `<w:sdtPr>` (and `<w:sdtEndPr>` when present) verbatim from the
9
- * `rawPropertiesXml` / `rawEndPropertiesXml` strings captured by the parser.
10
- * That keeps OOXML element order intact (`CT_SdtPr` is an `xsd:sequence`,
11
- * ECMA-376 §17.5.2) and round-trips unmodeled features — `w:dataBinding`,
12
- * `w15:repeatingSection`, `@lastValue`, custom XML mappings — without us
13
- * having to enumerate them.
14
- *
15
- * If a `BlockSdt` was constructed programmatically (no parsed snapshot to
16
- * replay), fall back to a minimal projection from the modeled fields so the
17
- * result is still a valid `<w:sdt>`.
18
- *
19
- * Sharing the helper between the document body and the header/footer
20
- * serializers keeps body↔HF parity in one place.
21
- */
22
- function serializeFallbackSdtPr(props) {
23
- const parts = [];
24
- if (props.id !== void 0) parts.push(`<w:id w:val="${props.id}"/>`);
25
- if (props.alias) parts.push(`<w:alias w:val="${escapeXmlAttribute(props.alias)}"/>`);
26
- if (props.tag) parts.push(`<w:tag w:val="${escapeXmlAttribute(props.tag)}"/>`);
27
- if (props.lock) parts.push(`<w:lock w:val="${props.lock}"/>`);
28
- if (props.placeholder) parts.push(`<w:placeholder><w:docPart w:val="${escapeXmlAttribute(props.placeholder)}"/></w:placeholder>`);
29
- if (props.showingPlaceholder) parts.push("<w:showingPlcHdr/>");
30
- switch (props.sdtType) {
31
- case "plainText":
32
- parts.push("<w:text/>");
33
- break;
34
- case "date": {
35
- const fullDateAttr = props.dateValueISO ? ` w:fullDate="${escapeXmlAttribute(props.dateValueISO)}"` : "";
36
- const formatChild = props.dateFormat ? `<w:dateFormat w:val="${escapeXmlAttribute(props.dateFormat)}"/>` : "";
37
- if (fullDateAttr || formatChild) parts.push(`<w:date${fullDateAttr}>${formatChild}</w:date>`);
38
- else parts.push("<w:date/>");
39
- break;
40
- }
41
- case "dropdown":
42
- case "comboBox": {
43
- const tag = props.sdtType === "dropdown" ? "w:dropDownList" : "w:comboBox";
44
- const items = (props.listItems ?? []).map((item) => `<w:listItem w:displayText="${escapeXmlAttribute(item.displayText)}" w:value="${escapeXmlAttribute(item.value)}"/>`).join("");
45
- parts.push(`<${tag}>${items}</${tag}>`);
46
- break;
47
- }
48
- case "checkbox": {
49
- const val = props.checked ? "1" : "0";
50
- parts.push(`<w14:checkbox><w14:checked w14:val="${val}"/></w14:checkbox>`);
51
- break;
52
- }
53
- case "picture":
54
- parts.push("<w:picture/>");
55
- break;
56
- case "buildingBlockGallery":
57
- parts.push("<w:docPartObj/>");
58
- break;
59
- case "group":
60
- parts.push("<w:group/>");
61
- break;
62
- default: break;
63
- }
64
- return `<w:sdtPr>${parts.join("")}</w:sdtPr>`;
65
- }
66
- /**
67
- * `properties.dropdownLastValue` is the only record of what was selected.
68
- *
69
- * The XSD default of `@w:lastValue` is the empty string, so "never selected",
70
- * "cleared" and "selected" are three distinguishable states, and the body's
71
- * display text is evidence for none of them: it is equally the placeholder of
72
- * a dropdown nobody has touched, and a displayText shared by two list items
73
- * picks the wrong sibling. The parser records the authored `@w:lastValue` and
74
- * `setContentControlValue` records a pick; what neither wrote is no selection.
75
- *
76
- * `""` is a value a producer can author (`<w:listItem w:value=""/>`), so
77
- * presence is the test, not truthiness.
78
- */
79
- function extractDropdownLastValue(blockSdt) {
80
- if (blockSdt.properties.sdtType !== "dropdown" && blockSdt.properties.sdtType !== "comboBox") return;
81
- return blockSdt.properties.dropdownLastValue;
82
- }
83
- function extractDateFullDate(blockSdt) {
84
- if (blockSdt.properties.sdtType !== "date") return;
85
- const iso = blockSdt.properties.dateValueISO;
86
- return iso !== void 0 && iso.length > 0 ? iso : void 0;
87
- }
88
3
  function serializeBlockSdt(blockSdt, serializeChild) {
89
4
  const props = blockSdt.properties;
90
- const baseSdtPr = props.rawPropertiesXml && isSingleWellFormedElement(props.rawPropertiesXml, "sdtPr") ? props.rawPropertiesXml : serializeFallbackSdtPr(props);
91
- const dateFullDate = extractDateFullDate(blockSdt);
92
- const dropdownLastValue = extractDropdownLastValue(blockSdt);
93
- const sdtPrXml = reconcileRawSdtPr(baseSdtPr, props, {
94
- ...dateFullDate !== void 0 ? { dateFullDate } : {},
95
- ...dropdownLastValue !== void 0 ? { dropdownLastValue } : {}
96
- });
97
- const sdtEndPrXml = props.rawEndPropertiesXml && isSingleWellFormedElement(props.rawEndPropertiesXml, "sdtEndPr") ? props.rawEndPropertiesXml : "";
98
- const contentXml = blockSdt.content.map(serializeChild).join("");
99
- return `<w:sdt>${sdtPrXml}${sdtEndPrXml}${props.rawSdtChildrenBeforeContent ?? ""}<w:sdtContent>${contentXml}</w:sdtContent>${props.rawSdtChildrenAfterContent ?? ""}</w:sdt>`;
5
+ return serializeSdtWrapper(props, blockSdt.content.map(serializeChild).join(""));
100
6
  }
101
7
  //#endregion
102
8
  export { serializeBlockSdt };
@@ -1,6 +1,6 @@
1
1
  import { document_d_exports } from "../../types/document.js";
2
2
  //#region src/docx/serializer/borderSerializer.d.ts
3
- type ClassifiedBorderField = "style" | "color" | "size" | "space" | "shadow" | "frame" | "artRelationshipId" | "topLeftArtRelationshipId" | "topRightArtRelationshipId" | "bottomLeftArtRelationshipId" | "bottomRightArtRelationshipId";
3
+ type ClassifiedBorderField = "style" | "color" | "size" | "space" | "shadow" | "frame" | "artRelationshipId" | "topLeftArtRelationshipId" | "topRightArtRelationshipId" | "bottomLeftArtRelationshipId" | "bottomRightArtRelationshipId" | "preservedAttributes";
4
4
  type ExhaustiveBorder = document_d_exports.ExhaustiveFields<document_d_exports.BorderSpec, ClassifiedBorderField>;
5
5
  /**
6
6
  * Serialize a single border element (`<w:top .../>`, `<w:left .../>`, ...).
@@ -16,10 +16,10 @@ type ExhaustiveBorder = document_d_exports.ExhaustiveFields<document_d_exports.B
16
16
  * turned-off side; those are emitted when present so the value survives a
17
17
  * save→parse round-trip and is not otherwise added.
18
18
  *
19
- * `style` and the color values come straight from the parsed DOCX (the parser
20
- * casts `w:val`/`w:color` without validating the enum), so they are
21
- * untrusted and are `escapeXmlAttribute`'d before re-entering XML attributes; for valid
22
- * documents these are enum/hex values, so escaping is a no-op.
19
+ * An unrecognised `w:val` and the color values come straight from the parsed
20
+ * DOCX, so they are untrusted and are `escapeXmlAttribute`'d before re-entering
21
+ * XML attributes; for valid documents these are enum/hex values, so escaping is
22
+ * a no-op.
23
23
  */
24
24
  declare function serializeBorder(input: ExhaustiveBorder | undefined, elementName: string): string;
25
25
  //#endregion
@@ -1,5 +1,7 @@
1
+ import { serializePreservedAttributes } from "../attributeRemainder.js";
1
2
  import { intAttr } from "./xmlUtils.js";
2
3
  import { escapeXmlAttribute } from "@stll/docx-core";
4
+ import { borderStyleToken, themeColorToken } from "@stll/docx-core/model";
3
5
  //#region src/docx/serializer/borderSerializer.ts
4
6
  /**
5
7
  * Serialize a single border element (`<w:top .../>`, `<w:left .../>`, ...).
@@ -15,33 +17,33 @@ import { escapeXmlAttribute } from "@stll/docx-core";
15
17
  * turned-off side; those are emitted when present so the value survives a
16
18
  * save→parse round-trip and is not otherwise added.
17
19
  *
18
- * `style` and the color values come straight from the parsed DOCX (the parser
19
- * casts `w:val`/`w:color` without validating the enum), so they are
20
- * untrusted and are `escapeXmlAttribute`'d before re-entering XML attributes; for valid
21
- * documents these are enum/hex values, so escaping is a no-op.
20
+ * An unrecognised `w:val` and the color values come straight from the parsed
21
+ * DOCX, so they are untrusted and are `escapeXmlAttribute`'d before re-entering
22
+ * XML attributes; for valid documents these are enum/hex values, so escaping is
23
+ * a no-op.
22
24
  */
23
25
  function serializeBorder(input, elementName) {
24
26
  if (!input) return "";
25
- const { style, color, size, space, shadow, frame, artRelationshipId, topLeftArtRelationshipId, topRightArtRelationshipId, bottomLeftArtRelationshipId, bottomRightArtRelationshipId } = input;
26
- const attrs = [`w:val="${escapeXmlAttribute(style)}"`];
27
+ const { style, color, size, space, shadow, frame, artRelationshipId, topLeftArtRelationshipId, topRightArtRelationshipId, bottomLeftArtRelationshipId, bottomRightArtRelationshipId, preservedAttributes } = input;
28
+ const attrs = [`w:val="${escapeXmlAttribute(borderStyleToken(style))}"`];
27
29
  if (size !== void 0) attrs.push(`w:sz="${intAttr(size)}"`);
28
30
  if (space !== void 0) attrs.push(`w:space="${intAttr(space)}"`);
29
31
  if (color) {
30
32
  const { auto, rgb, themeColor, themeTint, themeShade } = color;
31
33
  if (auto) attrs.push("w:color=\"auto\"");
32
34
  else if (rgb) attrs.push(`w:color="${escapeXmlAttribute(rgb)}"`);
33
- if (themeColor) attrs.push(`w:themeColor="${escapeXmlAttribute(themeColor)}"`);
35
+ if (themeColor) attrs.push(`w:themeColor="${escapeXmlAttribute(themeColorToken(themeColor))}"`);
34
36
  if (themeTint) attrs.push(`w:themeTint="${escapeXmlAttribute(themeTint)}"`);
35
37
  if (themeShade) attrs.push(`w:themeShade="${escapeXmlAttribute(themeShade)}"`);
36
38
  }
37
- if (shadow) attrs.push("w:shadow=\"true\"");
38
- if (frame) attrs.push("w:frame=\"true\"");
39
+ if (shadow !== void 0) attrs.push(`w:shadow="${shadow ? "1" : "0"}"`);
40
+ if (frame !== void 0) attrs.push(`w:frame="${frame ? "1" : "0"}"`);
39
41
  if (artRelationshipId) attrs.push(`r:id="${escapeXmlAttribute(artRelationshipId)}"`);
40
42
  if (topLeftArtRelationshipId) attrs.push(`r:topLeft="${escapeXmlAttribute(topLeftArtRelationshipId)}"`);
41
43
  if (topRightArtRelationshipId) attrs.push(`r:topRight="${escapeXmlAttribute(topRightArtRelationshipId)}"`);
42
44
  if (bottomLeftArtRelationshipId) attrs.push(`r:bottomLeft="${escapeXmlAttribute(bottomLeftArtRelationshipId)}"`);
43
45
  if (bottomRightArtRelationshipId) attrs.push(`r:bottomRight="${escapeXmlAttribute(bottomRightArtRelationshipId)}"`);
44
- return `<w:${elementName} ${attrs.join(" ")}/>`;
46
+ return `<w:${elementName} ${serializePreservedAttributes(attrs, preservedAttributes).join(" ")}/>`;
45
47
  }
46
48
  //#endregion
47
49
  export { serializeBorder };
@@ -1,5 +1,6 @@
1
1
  import { deterministicHexId } from "../../utils/hexId.js";
2
2
  import { commentThreadParaId } from "../commentThreadKey.js";
3
+ import { serializeWithPreservedChildren } from "../containerChildren.js";
3
4
  import { serializeParagraph } from "./paragraphSerializer.js";
4
5
  import { serializePartElement } from "./partNamespaces.js";
5
6
  import { serializeTextFormatting } from "./textFormattingSerializer.js";
@@ -30,13 +31,10 @@ function serializeComment(comment) {
30
31
  const attrs = [`w:id="${comment.id}"`, `w:author="${escapeXmlAttribute(comment.author)}"`];
31
32
  if (comment.initials !== void 0) attrs.push(`w:initials="${escapeXmlAttribute(comment.initials)}"`);
32
33
  if (comment.date) attrs.push(`w:date="${escapeXmlAttribute(comment.date)}"`);
33
- let xml = `<w:comment ${attrs.join(" ")}>`;
34
- if (comment.content.length > 0) {
35
- xml += serializeParagraphWithAnnotationRef(comment.content[0], comment.annotationReferenceFormatting);
36
- for (let i = 1; i < comment.content.length; i++) xml += serializeParagraph(comment.content[i]);
37
- } else xml += `<w:p>${serializeAnnotationReference(comment.annotationReferenceFormatting)}</w:p>`;
38
- xml += "</w:comment>";
39
- return xml;
34
+ const paragraphs = comment.content.map((paragraph, index) => index === 0 ? serializeParagraphWithAnnotationRef(paragraph, comment.annotationReferenceFormatting) : serializeParagraph(paragraph));
35
+ if (paragraphs.length === 0 && comment.preserved === void 0) paragraphs.push(`<w:p>${serializeAnnotationReference(comment.annotationReferenceFormatting)}</w:p>`);
36
+ const body = serializeWithPreservedChildren(paragraphs, comment.preserved);
37
+ return `<w:comment ${attrs.join(" ")}>${body}</w:comment>`;
40
38
  }
41
39
  const COMMENTS_BASELINE_PREFIXES = [
42
40
  "wpc",
@@ -1,5 +1,5 @@
1
- import { withBlockRangeMarkers } from "../blockRangeMarkers.js";
2
1
  import { serializeBlockSdt } from "./blockSdtSerializer.js";
2
+ import { serializeBookmarkMarker } from "./markupRangeAttributes.js";
3
3
  import { serializeParagraph } from "./paragraphSerializer.js";
4
4
  import { serializePartElement } from "./partNamespaces.js";
5
5
  import { resetAutoIdCounter } from "./runSerializer.js";
@@ -37,17 +37,17 @@ const DOCUMENT_BASELINE_PREFIXES = [
37
37
  "wpg",
38
38
  "wps"
39
39
  ];
40
- /**
41
- * Serialize a single block content item (paragraph, table, or block-level SDT).
42
- */
40
+ /** Serialize a single block, whether or not folio models what is in it. */
43
41
  function serializeBlockContent(block) {
44
- return withBlockRangeMarkers(block, serializeBlockBody(block));
45
- }
46
- /** The block itself, without the range markers that stood around it. */
47
- function serializeBlockBody(block) {
48
- if (block.type === "paragraph") return serializeParagraph(block);
49
- if (block.type === "table") return serializeTable(block, serializeParagraph);
50
- return serializeBlockSdt(block, serializeBlockContent);
42
+ switch (block.type) {
43
+ case "paragraph": return serializeParagraph(block);
44
+ case "table": return serializeTable(block, serializeParagraph);
45
+ case "blockSdt": return serializeBlockSdt(block, serializeBlockContent);
46
+ case "preservedBlock": return block.xml;
47
+ case "bookmarkStart":
48
+ case "bookmarkEnd": return serializeBookmarkMarker(block);
49
+ default: return block;
50
+ }
51
51
  }
52
52
  /**
53
53
  * Serialize document body content
@@ -1,18 +1,33 @@
1
+ import { serializePreservedAttributes } from "../attributeRemainder.js";
2
+ import { serializeWithPreservedChildren } from "../containerChildren.js";
1
3
  import { serializePartElement } from "./partNamespaces.js";
2
4
  import { escapeXmlAttribute } from "@stll/docx-core";
3
5
  //#region src/docx/serializer/fontTableSerializer.ts
4
6
  const serializeFontTableXml = (fontTable) => "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\n" + serializePartElement({
5
7
  partPath: "word/fontTable.xml",
6
8
  rootName: "w:fonts",
9
+ rootAttributes: serializePreservedAttributes([], fontTable.preservedAttributes).join(" "),
7
10
  baselinePrefixes: ["w"],
8
11
  sourceBindings: void 0,
9
- body: fontTable.fonts.map(serializeFont).join("")
12
+ body: serializeWithPreservedChildren(fontTable.fonts.map(serializeFont), fontTable.preserved)
10
13
  });
14
+ /**
15
+ * One `w:font`, with its children in the order `CT_Font` declares them.
16
+ *
17
+ * The order is what makes the sink's index mean something: a capture recorded
18
+ * after the third field the reader kept goes back after the third field this
19
+ * writes, so unmodelled markup keeps the neighbours it was authored between.
20
+ */
11
21
  const serializeFont = (font) => {
12
22
  const parts = [];
13
23
  if (font.altName) parts.push(`<w:altName w:val="${escapeXmlAttribute(font.altName)}"/>`);
14
24
  if (font.panose1) parts.push(`<w:panose1 w:val="${escapeXmlAttribute(font.panose1)}"/>`);
15
- if (font.charset) parts.push(`<w:charset w:val="${escapeXmlAttribute(font.charset)}"/>`);
25
+ if (font.charset) {
26
+ const attributes = [];
27
+ if (font.charset.val !== void 0) attributes.push(`w:val="${escapeXmlAttribute(font.charset.val)}"`);
28
+ if (font.charset.characterSet !== void 0) attributes.push(`w:characterSet="${escapeXmlAttribute(font.charset.characterSet)}"`);
29
+ parts.push(attributes.length === 0 ? "<w:charset/>" : `<w:charset ${attributes.join(" ")}/>`);
30
+ }
16
31
  if (font.family) parts.push(`<w:family w:val="${font.family}"/>`);
17
32
  if (font.pitch) parts.push(`<w:pitch w:val="${font.pitch}"/>`);
18
33
  if (font.sig) {
@@ -23,7 +38,20 @@ const serializeFont = (font) => {
23
38
  }
24
39
  if (attrs.length > 0) parts.push(`<w:sig ${attrs.join(" ")}/>`);
25
40
  }
26
- return `<w:font w:name="${escapeXmlAttribute(font.name)}">${parts.join("")}</w:font>`;
41
+ pushEmbed(parts, "embedRegular", font.embedRegular);
42
+ pushEmbed(parts, "embedBold", font.embedBold);
43
+ pushEmbed(parts, "embedItalic", font.embedItalic);
44
+ pushEmbed(parts, "embedBoldItalic", font.embedBoldItalic);
45
+ const attributes = serializePreservedAttributes([`w:name="${escapeXmlAttribute(font.name)}"`], font.preservedAttributes);
46
+ const body = serializeWithPreservedChildren(parts, font.preserved);
47
+ return `<w:font ${attributes.join(" ")}>${body}</w:font>`;
48
+ };
49
+ const pushEmbed = (parts, element, embed) => {
50
+ if (embed === void 0) return;
51
+ const attributes = [`r:id="${escapeXmlAttribute(embed.id)}"`];
52
+ if (embed.fontKey !== void 0) attributes.push(`w:fontKey="${escapeXmlAttribute(embed.fontKey)}"`);
53
+ if (embed.subsetted !== void 0) attributes.push(`w:subsetted="${embed.subsetted ? "1" : "0"}"`);
54
+ parts.push(`<w:${element} ${attributes.join(" ")}/>`);
27
55
  };
28
56
  //#endregion
29
57
  export { serializeFontTableXml };
@@ -1,9 +1,9 @@
1
- import { withBlockRangeMarkers } from "../blockRangeMarkers.js";
2
1
  import { canReplayHeaderFooterVerbatim, getHeaderFooterVerbatimXml } from "../headerFooterVerbatim.js";
3
2
  import { isEmptyParagraph } from "../paragraphParser.js";
4
3
  import { captureVerbatimXml } from "../verbatimCapture.js";
5
4
  import { getLocalName, parseXmlDocument } from "../xmlParser.js";
6
5
  import { serializeBlockSdt } from "./blockSdtSerializer.js";
6
+ import { serializeBookmarkMarker } from "./markupRangeAttributes.js";
7
7
  import { serializeParagraph } from "./paragraphSerializer.js";
8
8
  import { serializePartElement } from "./partNamespaces.js";
9
9
  import { serializeTable } from "./tableSerializer.js";
@@ -37,13 +37,15 @@ const HEADER_FOOTER_BASELINE_PREFIXES = [
37
37
  * header/footer.
38
38
  */
39
39
  function serializeBlock(block) {
40
- return withBlockRangeMarkers(block, serializeBlockBody(block));
41
- }
42
- /** The block itself, without the range markers that stood around it. */
43
- function serializeBlockBody(block) {
44
- if (block.type === "paragraph") return serializeParagraph(block);
45
- if (block.type === "table") return serializeTable(block, serializeParagraph);
46
- return serializeBlockSdt(block, serializeBlock);
40
+ switch (block.type) {
41
+ case "paragraph": return serializeParagraph(block);
42
+ case "table": return serializeTable(block, serializeParagraph);
43
+ case "blockSdt": return serializeBlockSdt(block, serializeBlock);
44
+ case "preservedBlock": return block.xml;
45
+ case "bookmarkStart":
46
+ case "bookmarkEnd": return serializeBookmarkMarker(block);
47
+ default: return block;
48
+ }
47
49
  }
48
50
  /**
49
51
  * Serialize a HeaderFooter object to valid OOXML XML
@@ -71,7 +73,6 @@ function serializeHeaderFooter(hf, source) {
71
73
  });
72
74
  contentXml = blocksXml.slice(0, watermarkInsertIndex).join("") + (mergesIntoRetainedHost ? "" : watermarkXml) + blocksXml.slice(watermarkInsertIndex).join("");
73
75
  } else contentXml = blocksXml.join("");
74
- if (!contentXml) contentXml = "<w:p><w:pPr/></w:p>";
75
76
  return "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\n" + serializePartElement({
76
77
  partPath: source?.path ?? `word/${hf.type}.xml`,
77
78
  rootName: rootTag,
@@ -2,7 +2,15 @@ import { document_d_exports } from "../../types/document.js";
2
2
  //#region src/docx/serializer/markupRangeAttributes.d.ts
3
3
  declare const markupRangeAttributes: (marker: document_d_exports.MarkupRangeMarker) => string[];
4
4
  declare const bookmarkRangeAttributes: (marker: document_d_exports.BookmarkRangeMarker) => string[];
5
+ /**
6
+ * One bookmark marker, wherever it stands.
7
+ *
8
+ * The same element is a paragraph child, a block, a child of `w:tr` and a
9
+ * child of `w:tbl`, so the four serializers share one writer: an attribute
10
+ * added to `CT_Bookmark` reaches every level at once.
11
+ */
12
+ declare const serializeBookmarkMarker: (marker: document_d_exports.BookmarkStart | document_d_exports.BookmarkEnd) => string;
5
13
  /** `w:author` is required, so it is always written; `w:date` only when known. */
6
14
  declare const moveBookmarkAttributes: (marker: document_d_exports.MoveBookmarkMarker) => string[];
7
15
  //#endregion
8
- export { bookmarkRangeAttributes, markupRangeAttributes, moveBookmarkAttributes };
16
+ export { bookmarkRangeAttributes, markupRangeAttributes, moveBookmarkAttributes, serializeBookmarkMarker };
@@ -13,6 +13,14 @@ const bookmarkRangeAttributes = (marker) => {
13
13
  attributes.push(attribute("w:name", marker.name));
14
14
  return attributes;
15
15
  };
16
+ /**
17
+ * One bookmark marker, wherever it stands.
18
+ *
19
+ * The same element is a paragraph child, a block, a child of `w:tr` and a
20
+ * child of `w:tbl`, so the four serializers share one writer: an attribute
21
+ * added to `CT_Bookmark` reaches every level at once.
22
+ */
23
+ const serializeBookmarkMarker = (marker) => marker.type === "bookmarkStart" ? `<w:bookmarkStart ${bookmarkRangeAttributes(marker).join(" ")}/>` : `<w:bookmarkEnd ${markupRangeAttributes(marker).join(" ")}/>`;
16
24
  /** `w:author` is required, so it is always written; `w:date` only when known. */
17
25
  const moveBookmarkAttributes = (marker) => {
18
26
  const attributes = bookmarkRangeAttributes(marker);
@@ -21,4 +29,4 @@ const moveBookmarkAttributes = (marker) => {
21
29
  return attributes;
22
30
  };
23
31
  //#endregion
24
- export { bookmarkRangeAttributes, markupRangeAttributes, moveBookmarkAttributes };
32
+ export { bookmarkRangeAttributes, markupRangeAttributes, moveBookmarkAttributes, serializeBookmarkMarker };
@@ -1,5 +1,5 @@
1
- import { withBlockRangeMarkers } from "../blockRangeMarkers.js";
2
1
  import { serializeBlockSdt } from "./blockSdtSerializer.js";
2
+ import { serializeBookmarkMarker } from "./markupRangeAttributes.js";
3
3
  import { serializeParagraph } from "./paragraphSerializer.js";
4
4
  import { serializePartElement } from "./partNamespaces.js";
5
5
  import { serializeTable } from "./tableSerializer.js";
@@ -39,13 +39,15 @@ const serializeNotePart = (elementName, body) => "<?xml version=\"1.0\" encoding
39
39
  * note body.
40
40
  */
41
41
  function serializeBlock(block) {
42
- return withBlockRangeMarkers(block, serializeBlockBody(block));
43
- }
44
- /** The block itself, without the range markers that stood around it. */
45
- function serializeBlockBody(block) {
46
- if (block.type === "paragraph") return serializeParagraph(block);
47
- if (block.type === "table") return serializeTable(block, serializeParagraph);
48
- return serializeBlockSdt(block, serializeBlock);
42
+ switch (block.type) {
43
+ case "paragraph": return serializeParagraph(block);
44
+ case "table": return serializeTable(block, serializeParagraph);
45
+ case "blockSdt": return serializeBlockSdt(block, serializeBlock);
46
+ case "preservedBlock": return block.xml;
47
+ case "bookmarkStart":
48
+ case "bookmarkEnd": return serializeBookmarkMarker(block);
49
+ default: return block;
50
+ }
49
51
  }
50
52
  /**
51
53
  * Serialize a single note element. Footnotes and endnotes share the same
@@ -63,6 +65,7 @@ function serializeRequiredNoteSeparators(elementName) {
63
65
  return `<w:${elementName} w:type="separator" w:id="-1">${NOTE_SEPARATOR_BODY}<w:r><w:separator/></w:r></w:p></w:${elementName}><w:${elementName} w:type="continuationSeparator" w:id="0">${NOTE_SEPARATOR_BODY}<w:r><w:continuationSeparator/></w:r></w:p></w:${elementName}>`;
64
66
  }
65
67
  function insertNoteReferenceMark(xml, elementName) {
68
+ if (xml.includes(`<w:${elementName}Ref`)) return xml;
66
69
  const paragraphOpen = /<w:p(?=[\s>])[^>]*>/u.exec(xml);
67
70
  if (!paragraphOpen) return `${`<w:p><w:r><w:rPr><w:rStyle w:val="${elementName === "footnote" ? "FootnoteReference" : "EndnoteReference"}"/></w:rPr><w:${elementName}Ref/></w:r></w:p>`}${xml}`;
68
71
  const paragraphStart = paragraphOpen.index + paragraphOpen[0].length;
@@ -1,11 +1,6 @@
1
1
  import { document_d_exports } from "../../types/document.js";
2
2
  //#region src/docx/serializer/numberingSerializer.d.ts
3
- /**
4
- * Serialize {@link NumberingDefinitions} to a complete `word/numbering.xml`
5
- * string. `w:abstractNum` elements precede `w:num` elements as ECMA-376 §17.9
6
- * requires. See the module note: this whole-part output is used only for
7
- * change detection and per-definition splicing, never to overwrite the part.
8
- */
3
+ /** Serialize a complete `word/numbering.xml` part. */
9
4
  declare function serializeNumberingXml(numbering: document_d_exports.NumberingDefinitions): string;
10
5
  //#endregion
11
6
  export { serializeNumberingXml };
@@ -1,99 +1,101 @@
1
+ import { serializeParagraphPropertySet } from "../../internal/paragraphFormattingSerialization.js";
2
+ import { serializePreservedAttributes } from "../attributeRemainder.js";
3
+ import { customNumberFormatOf } from "../numberingParser.js";
1
4
  import { serializePartElement } from "./partNamespaces.js";
2
5
  import { serializeTextFormatting } from "./textFormattingSerializer.js";
3
6
  import { intAttr } from "./xmlUtils.js";
4
- import { escapeXmlAttribute } from "@stll/docx-core";
7
+ import { escapeXmlAttribute, serializeOnOffElement } from "@stll/docx-core";
8
+ import { serializeSequenceChildren } from "@stll/docx-core/schema";
5
9
  //#region src/docx/serializer/numberingSerializer.ts
6
- /**
7
- * Serialize a level's paragraph properties — the modeled subset is indentation
8
- * plus tab stops (see `parseLevelParagraphProps`). Returns "" when neither is
9
- * present so an empty `<w:pPr/>` is not emitted.
10
- */
11
- function serializeLevelParagraphProps(pPr) {
12
- const indAttrs = [];
13
- if (pPr.indentLeft !== void 0) indAttrs.push(`w:left="${intAttr(pPr.indentLeft)}"`);
14
- if (pPr.indentRight !== void 0) indAttrs.push(`w:right="${intAttr(pPr.indentRight)}"`);
15
- if (pPr.indentFirstLine !== void 0) {
16
- if (pPr.hangingIndent) indAttrs.push(`w:hanging="${intAttr(Math.abs(pPr.indentFirstLine))}"`);
17
- else if (pPr.indentFirstLine !== 0) indAttrs.push(`w:firstLine="${intAttr(pPr.indentFirstLine)}"`);
18
- }
19
- const parts = [];
20
- if (pPr.tabs && pPr.tabs.length > 0) {
21
- const tabs = pPr.tabs.map((tab) => {
22
- const attrs = [`w:val="${tab.alignment}"`, `w:pos="${intAttr(tab.position)}"`];
23
- if (tab.leader) attrs.push(`w:leader="${tab.leader}"`);
24
- return `<w:tab ${attrs.join(" ")}/>`;
25
- }).join("");
26
- parts.push(`<w:tabs>${tabs}</w:tabs>`);
27
- }
28
- if (indAttrs.length > 0) parts.push(`<w:ind ${indAttrs.join(" ")}/>`);
29
- if (parts.length === 0) return "";
30
- return `<w:pPr>${parts.join("")}</w:pPr>`;
31
- }
32
- /**
33
- * Serialize one `w:lvl`. Children follow the ECMA-376 §17.9.6 CT_Lvl order
34
- * (start, numFmt, lvlRestart, isLgl, suff, lvlText, legacy, lvlJc, pPr, rPr) so
35
- * a re-emitted level parses back into an equivalent model.
36
- */
10
+ /** Serialize one `w:lvl`. */
37
11
  function serializeLevel(level) {
38
- const parts = [];
39
- if (level.start !== void 0) parts.push(`<w:start w:val="${intAttr(level.start)}"/>`);
40
- parts.push(`<w:numFmt w:val="${escapeXmlAttribute(level.numFmt)}"/>`);
41
- if (level.lvlRestart !== void 0) parts.push(`<w:lvlRestart w:val="${intAttr(level.lvlRestart)}"/>`);
42
- if (level.isLgl) parts.push("<w:isLgl/>");
43
- if (level.suffix) parts.push(`<w:suff w:val="${level.suffix}"/>`);
44
- parts.push(`<w:lvlText w:val="${escapeXmlAttribute(level.lvlText)}"/>`);
45
- if (level.legacy) {
46
- const legacyAttrs = [`w:legacy="${level.legacy.legacy ? 1 : 0}"`];
47
- if (level.legacy.legacySpace !== void 0) legacyAttrs.push(`w:legacySpace="${intAttr(level.legacy.legacySpace)}"`);
48
- if (level.legacy.legacyIndent !== void 0) legacyAttrs.push(`w:legacyIndent="${intAttr(level.legacy.legacyIndent)}"`);
49
- parts.push(`<w:legacy ${legacyAttrs.join(" ")}/>`);
12
+ const customFormat = customNumberFormatOf(level);
13
+ const numFmtFormat = customFormat === void 0 ? "" : ` w:format="${escapeXmlAttribute(customFormat)}"`;
14
+ const pPr = level.pPr === void 0 ? "" : serializeParagraphPropertySet({ formatting: level.pPr }) || "<w:pPr/>";
15
+ const rPr = level.rPr === void 0 ? "" : serializeTextFormatting(level.rPr) || "<w:rPr/>";
16
+ const lvlTextAttrs = [`w:val="${escapeXmlAttribute(level.lvlText)}"`];
17
+ if (level.lvlTextNull !== void 0) lvlTextAttrs.push(`w:null="${level.lvlTextNull ? 1 : 0}"`);
18
+ let legacy = "";
19
+ if (level.legacy !== void 0) {
20
+ const attributes = [];
21
+ if (level.legacy.legacy !== void 0) attributes.push(`w:legacy="${level.legacy.legacy ? 1 : 0}"`);
22
+ if (level.legacy.legacySpace !== void 0) attributes.push(`w:legacySpace="${intAttr(level.legacy.legacySpace)}"`);
23
+ if (level.legacy.legacyIndent !== void 0) attributes.push(`w:legacyIndent="${intAttr(level.legacy.legacyIndent)}"`);
24
+ legacy = attributes.length === 0 ? "<w:legacy/>" : `<w:legacy ${attributes.join(" ")}/>`;
50
25
  }
51
- if (level.lvlJc) parts.push(`<w:lvlJc w:val="${level.lvlJc}"/>`);
52
- if (level.pPr) parts.push(serializeLevelParagraphProps(level.pPr));
53
- parts.push(serializeTextFormatting(level.rPr));
54
- return `<w:lvl w:ilvl="${intAttr(level.ilvl)}">${parts.join("")}</w:lvl>`;
26
+ const children = serializeSequenceChildren({
27
+ container: "w:lvl",
28
+ modelled: [
29
+ ["start", level.start === void 0 ? "" : `<w:start w:val="${intAttr(level.start)}"/>`],
30
+ ["numFmt", `<w:numFmt w:val="${escapeXmlAttribute(level.numFmt)}"${numFmtFormat}/>`],
31
+ ["lvlRestart", level.lvlRestart === void 0 ? "" : `<w:lvlRestart w:val="${intAttr(level.lvlRestart)}"/>`],
32
+ ["pStyle", level.pStyle === void 0 ? "" : `<w:pStyle w:val="${escapeXmlAttribute(level.pStyle)}"/>`],
33
+ ["isLgl", serializeOnOffElement(level.isLgl, "isLgl")],
34
+ ["suff", level.suffix === void 0 ? "" : `<w:suff w:val="${escapeXmlAttribute(level.suffix)}"/>`],
35
+ ["lvlText", `<w:lvlText ${lvlTextAttrs.join(" ")}/>`],
36
+ ["lvlPicBulletId", level.lvlPicBulletId === void 0 ? "" : `<w:lvlPicBulletId w:val="${intAttr(level.lvlPicBulletId)}"/>`],
37
+ ["legacy", legacy],
38
+ ["lvlJc", level.lvlJc === void 0 ? "" : `<w:lvlJc w:val="${escapeXmlAttribute(level.lvlJc)}"/>`],
39
+ ["pPr", pPr],
40
+ ["rPr", rPr]
41
+ ],
42
+ preserved: level.preserved
43
+ });
44
+ const attributes = [`w:ilvl="${intAttr(level.ilvl)}"`];
45
+ if (level.tplc !== void 0) attributes.push(`w:tplc="${escapeXmlAttribute(level.tplc)}"`);
46
+ if (level.tentative !== void 0) attributes.push(`w:tentative="${level.tentative ? 1 : 0}"`);
47
+ return `<w:lvl ${serializePreservedAttributes(attributes, level.preservedAttributes).join(" ")}>${children.join("")}</w:lvl>`;
55
48
  }
56
- /**
57
- * Serialize one `w:abstractNum` (the reusable list template). Children follow
58
- * ECMA-376 §17.9.1 CT_AbstractNum order for the modeled subset (multiLevelType,
59
- * name, styleLink, numStyleLink, lvl+); `w:nsid` / `w:tmpl` are not modeled.
60
- */
49
+ /** Serialize one reusable `w:abstractNum` list template. */
61
50
  function serializeAbstractNum(abstractNum) {
62
- const parts = [];
63
- if (abstractNum.multiLevelType) parts.push(`<w:multiLevelType w:val="${abstractNum.multiLevelType}"/>`);
64
- if (abstractNum.name !== void 0) parts.push(`<w:name w:val="${escapeXmlAttribute(abstractNum.name)}"/>`);
65
- if (abstractNum.styleLink !== void 0) parts.push(`<w:styleLink w:val="${escapeXmlAttribute(abstractNum.styleLink)}"/>`);
66
- if (abstractNum.numStyleLink !== void 0) parts.push(`<w:numStyleLink w:val="${escapeXmlAttribute(abstractNum.numStyleLink)}"/>`);
67
- const levels = [...abstractNum.levels].sort((a, b) => a.ilvl - b.ilvl);
68
- for (const level of levels) parts.push(serializeLevel(level));
69
- return `<w:abstractNum w:abstractNumId="${intAttr(abstractNum.abstractNumId)}">${parts.join("")}</w:abstractNum>`;
51
+ const levels = [...abstractNum.levels].sort((left, right) => left.ilvl - right.ilvl);
52
+ const children = serializeSequenceChildren({
53
+ container: "w:abstractNum",
54
+ modelled: [
55
+ ["nsid", abstractNum.nsid === void 0 ? "" : `<w:nsid w:val="${escapeXmlAttribute(abstractNum.nsid)}"/>`],
56
+ ["multiLevelType", abstractNum.multiLevelType === void 0 ? "" : `<w:multiLevelType w:val="${escapeXmlAttribute(abstractNum.multiLevelType)}"/>`],
57
+ ["tmpl", abstractNum.tmpl === void 0 ? "" : `<w:tmpl w:val="${escapeXmlAttribute(abstractNum.tmpl)}"/>`],
58
+ ["name", abstractNum.name === void 0 ? "" : `<w:name w:val="${escapeXmlAttribute(abstractNum.name)}"/>`],
59
+ ["styleLink", abstractNum.styleLink === void 0 ? "" : `<w:styleLink w:val="${escapeXmlAttribute(abstractNum.styleLink)}"/>`],
60
+ ["numStyleLink", abstractNum.numStyleLink === void 0 ? "" : `<w:numStyleLink w:val="${escapeXmlAttribute(abstractNum.numStyleLink)}"/>`],
61
+ ["lvl", levels.map(serializeLevel).join("")]
62
+ ],
63
+ preserved: abstractNum.preserved
64
+ });
65
+ return `<w:abstractNum ${serializePreservedAttributes([`w:abstractNumId="${intAttr(abstractNum.abstractNumId)}"`], abstractNum.preservedAttributes).join(" ")}>${children.join("")}</w:abstractNum>`;
70
66
  }
71
- /**
72
- * Serialize one `w:num` (a concrete numbering instance referenced by `numId`).
73
- */
67
+ /** Serialize one concrete instance's per-level override. */
68
+ function serializeLevelOverride(override) {
69
+ const children = serializeSequenceChildren({
70
+ container: "w:lvlOverride",
71
+ modelled: [["startOverride", override.startOverride === void 0 ? "" : `<w:startOverride w:val="${intAttr(override.startOverride)}"/>`], ["lvl", override.lvl === void 0 ? "" : serializeLevel(override.lvl)]],
72
+ preserved: override.preserved
73
+ });
74
+ return `<w:lvlOverride ${serializePreservedAttributes([`w:ilvl="${intAttr(override.ilvl)}"`], override.preservedAttributes).join(" ")}>${children.join("")}</w:lvlOverride>`;
75
+ }
76
+ /** Serialize one concrete `w:num` numbering instance. */
74
77
  function serializeNum(instance) {
75
- const parts = [`<w:abstractNumId w:val="${intAttr(instance.abstractNumId)}"/>`];
76
- for (const override of instance.levelOverrides ?? []) {
77
- const overrideParts = [];
78
- if (override.startOverride !== void 0) overrideParts.push(`<w:startOverride w:val="${intAttr(override.startOverride)}"/>`);
79
- if (override.lvl) overrideParts.push(serializeLevel(override.lvl));
80
- parts.push(`<w:lvlOverride w:ilvl="${intAttr(override.ilvl)}">${overrideParts.join("")}</w:lvlOverride>`);
81
- }
82
- return `<w:num w:numId="${intAttr(instance.numId)}">${parts.join("")}</w:num>`;
78
+ const children = serializeSequenceChildren({
79
+ container: "w:num",
80
+ modelled: [["abstractNumId", `<w:abstractNumId w:val="${intAttr(instance.abstractNumId)}"/>`], ["lvlOverride", (instance.levelOverrides ?? []).map(serializeLevelOverride).join("")]],
81
+ preserved: instance.preserved
82
+ });
83
+ return `<w:num ${serializePreservedAttributes([`w:numId="${intAttr(instance.numId)}"`], instance.preservedAttributes).join(" ")}>${children.join("")}</w:num>`;
83
84
  }
84
- /**
85
- * Serialize {@link NumberingDefinitions} to a complete `word/numbering.xml`
86
- * string. `w:abstractNum` elements precede `w:num` elements as ECMA-376 §17.9
87
- * requires. See the module note: this whole-part output is used only for
88
- * change detection and per-definition splicing, never to overwrite the part.
89
- */
85
+ /** Serialize a complete `word/numbering.xml` part. */
90
86
  function serializeNumberingXml(numbering) {
87
+ const children = serializeSequenceChildren({
88
+ container: "w:numbering",
89
+ modelled: [["abstractNum", numbering.abstractNums.map(serializeAbstractNum).join("")], ["num", numbering.nums.map(serializeNum).join("")]],
90
+ preserved: numbering.preserved
91
+ });
91
92
  return "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\n" + serializePartElement({
92
93
  partPath: "word/numbering.xml",
93
94
  rootName: "w:numbering",
95
+ rootAttributes: serializePreservedAttributes([], numbering.preservedAttributes).join(" "),
94
96
  baselinePrefixes: ["w"],
95
97
  sourceBindings: void 0,
96
- body: `${numbering.abstractNums.map(serializeAbstractNum).join("")}${numbering.nums.map(serializeNum).join("")}`
98
+ body: children.join("")
97
99
  });
98
100
  }
99
101
  //#endregion