docx 9.9.0 → 9.11.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.
package/dist/index.cjs CHANGED
@@ -11032,7 +11032,7 @@ var RunProperties = class extends IgnoreIfEmptyXmlComponent {
11032
11032
  if (options.imprint !== void 0) this.push(new OnOffElement("w:imprint", options.imprint));
11033
11033
  if (options.noProof !== void 0) this.push(new OnOffElement("w:noProof", options.noProof));
11034
11034
  if (options.snapToGrid !== void 0) this.push(new OnOffElement("w:snapToGrid", options.snapToGrid));
11035
- if (options.vanish) this.push(new OnOffElement("w:vanish", options.vanish));
11035
+ if (options.vanish !== void 0) this.push(new OnOffElement("w:vanish", options.vanish));
11036
11036
  if (options.color) this.push(new Color(options.color));
11037
11037
  if (options.characterSpacing) this.push(new CharacterSpacing(options.characterSpacing));
11038
11038
  if (options.scale !== void 0) this.push(new NumberValueElement("w:w", options.scale));
@@ -11051,8 +11051,8 @@ var RunProperties = class extends IgnoreIfEmptyXmlComponent {
11051
11051
  if (options.rightToLeft !== void 0) this.push(new OnOffElement("w:rtl", options.rightToLeft));
11052
11052
  if (options.emphasisMark) this.push(createEmphasisMark(options.emphasisMark.type));
11053
11053
  if (options.language) this.push(createLanguageComponent(options.language));
11054
- if (options.specVanish) this.push(new OnOffElement("w:specVanish", options.vanish));
11055
- if (options.math) this.push(new OnOffElement("w:oMath", options.math));
11054
+ if (options.specVanish !== void 0) this.push(new OnOffElement("w:specVanish", options.specVanish));
11055
+ if (options.math !== void 0) this.push(new OnOffElement("w:oMath", options.math));
11056
11056
  if (options.revision) this.push(new RunPropertiesChange(options.revision));
11057
11057
  }
11058
11058
  push(item) {
@@ -12786,7 +12786,7 @@ var import_hash = /* @__PURE__ */ __toESM((/* @__PURE__ */ __commonJSMin(((expor
12786
12786
  hash.sha512 = hash.sha.sha512;
12787
12787
  hash.ripemd160 = hash.ripemd.ripemd160;
12788
12788
  })))(), 1);
12789
- var urlAlphabet = "useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict";
12789
+ var urlAlphabet = "57X6y3wQZNzYjJB2L_10pxbackgroundhimselfUTF-8DEMOGRAPHICSVqvt4KW9";
12790
12790
  //#endregion
12791
12791
  //#region node_modules/nanoid/non-secure/index.js
12792
12792
  var customAlphabet = (alphabet, defaultSize = 21) => {
@@ -14583,48 +14583,6 @@ var ChildNonVisualProperties = class extends XmlComponent {
14583
14583
  }
14584
14584
  };
14585
14585
  //#endregion
14586
- //#region src/file/drawing/doc-properties/doc-properties-children.ts
14587
- /**
14588
- * Child elements for document properties.
14589
- *
14590
- * This module provides hyperlink elements that can be attached to
14591
- * drawing elements for interactive behavior.
14592
- *
14593
- * @module
14594
- */
14595
- /**
14596
- * Creates a click hyperlink element for a drawing.
14597
- *
14598
- * This element defines what happens when a user clicks on a drawing element.
14599
- *
14600
- * ## XSD Schema
14601
- * ```xml
14602
- * <xsd:complexType name="CT_Hyperlink">
14603
- * <xsd:group ref="EG_PContent" minOccurs="0" maxOccurs="unbounded"/>
14604
- * <xsd:attribute name="tgtFrame" type="s:ST_String"/>
14605
- * <xsd:attribute name="tooltip" type="s:ST_String"/>
14606
- * <xsd:attribute name="docLocation" type="s:ST_String"/>
14607
- * <xsd:attribute name="history" type="s:ST_OnOff"/>
14608
- * <xsd:attribute name="anchor" type="s:ST_String"/>
14609
- * <xsd:attribute ref="r:id"/>
14610
- * </xsd:complexType>
14611
- * ```
14612
- *
14613
- * @param linkId - The relationship ID for the hyperlink target
14614
- * @param hasXmlNs - Whether to include the XML namespace declaration
14615
- * @returns An XML component representing the click hyperlink
14616
- */
14617
- var createHyperlinkClick = (linkId, hasXmlNs) => new BuilderElement({
14618
- name: "a:hlinkClick",
14619
- attributes: _objectSpread2(_objectSpread2({}, hasXmlNs ? { xmlns: {
14620
- key: "xmlns:a",
14621
- value: "http://schemas.openxmlformats.org/drawingml/2006/main"
14622
- } } : {}), {}, { id: {
14623
- key: "r:id",
14624
- value: `rId${linkId}`
14625
- } })
14626
- });
14627
- //#endregion
14628
14586
  //#region src/file/drawing/inline/graphic/graphic-data/pic/non-visual-pic-properties/non-visual-properties/non-visual-properties-attributes.ts
14629
14587
  /**
14630
14588
  * Non-visual properties attributes module.
@@ -14705,7 +14663,7 @@ var NonVisualProperties = class extends XmlComponent {
14705
14663
  for (let i = context.stack.length - 1; i >= 0; i--) {
14706
14664
  const element = context.stack[i];
14707
14665
  if (!(element instanceof ConcreteHyperlink)) continue;
14708
- this.root.push(createHyperlinkClick(element.linkId, false));
14666
+ this.root.push(element.createDrawingClick(context, false));
14709
14667
  break;
14710
14668
  }
14711
14669
  const result = super.prepForXml(context);
@@ -15375,6 +15333,48 @@ var createRelationship = (id, type, target, targetMode) => new BuilderElement({
15375
15333
  }
15376
15334
  });
15377
15335
  //#endregion
15336
+ //#region src/file/drawing/doc-properties/doc-properties-children.ts
15337
+ /**
15338
+ * Child elements for document properties.
15339
+ *
15340
+ * This module provides hyperlink elements that can be attached to
15341
+ * drawing elements for interactive behavior.
15342
+ *
15343
+ * @module
15344
+ */
15345
+ /**
15346
+ * Creates a click hyperlink element for a drawing.
15347
+ *
15348
+ * This element defines what happens when a user clicks on a drawing element.
15349
+ *
15350
+ * ## XSD Schema
15351
+ * ```xml
15352
+ * <xsd:complexType name="CT_Hyperlink">
15353
+ * <xsd:group ref="EG_PContent" minOccurs="0" maxOccurs="unbounded"/>
15354
+ * <xsd:attribute name="tgtFrame" type="s:ST_String"/>
15355
+ * <xsd:attribute name="tooltip" type="s:ST_String"/>
15356
+ * <xsd:attribute name="docLocation" type="s:ST_String"/>
15357
+ * <xsd:attribute name="history" type="s:ST_OnOff"/>
15358
+ * <xsd:attribute name="anchor" type="s:ST_String"/>
15359
+ * <xsd:attribute ref="r:id"/>
15360
+ * </xsd:complexType>
15361
+ * ```
15362
+ *
15363
+ * @param linkId - The relationship ID for the hyperlink target
15364
+ * @param hasXmlNs - Whether to include the XML namespace declaration
15365
+ * @returns An XML component representing the click hyperlink
15366
+ */
15367
+ var createHyperlinkClick = (linkId, hasXmlNs) => new BuilderElement({
15368
+ name: "a:hlinkClick",
15369
+ attributes: _objectSpread2(_objectSpread2({}, hasXmlNs ? { xmlns: {
15370
+ key: "xmlns:a",
15371
+ value: "http://schemas.openxmlformats.org/drawingml/2006/main"
15372
+ } } : {}), {}, { id: {
15373
+ key: "r:id",
15374
+ value: `rId${linkId}`
15375
+ } })
15376
+ });
15377
+ //#endregion
15378
15378
  //#region src/file/drawing/doc-properties/non-visual-drawing-properties.ts
15379
15379
  /**
15380
15380
  * Non-visual drawing properties (`CT_NonVisualDrawingProps`) of the shapes, pictures and groups inside a drawing:
@@ -15569,7 +15569,7 @@ var DocProperties = class extends XmlComponent {
15569
15569
  } else for (let i = context.stack.length - 1; i >= 0; i--) {
15570
15570
  const element = context.stack[i];
15571
15571
  if (!(element instanceof ConcreteHyperlink)) continue;
15572
- this.root.push(createHyperlinkClick(element.linkId, true));
15572
+ this.root.push(element.createDrawingClick(context, true));
15573
15573
  break;
15574
15574
  }
15575
15575
  if (this.decorative) this.root.push(createDecorativeExtensionList(true));
@@ -16884,14 +16884,14 @@ var HeadingBookmarkIds = class {
16884
16884
  }
16885
16885
  };
16886
16886
  /** The name of a formatted element, or `_attr` for its parent's attributes */
16887
- var nameOf$2 = (element) => typeof element === "object" && element !== null ? Object.keys(element)[0] : void 0;
16887
+ var nameOf$3 = (element) => typeof element === "object" && element !== null ? Object.keys(element)[0] : void 0;
16888
16888
  /** The children of a formatted element. An element with only attributes has them as its one child */
16889
16889
  var childrenOf = (element) => {
16890
- const name = nameOf$2(element);
16890
+ const name = nameOf$3(element);
16891
16891
  const content = name === void 0 ? void 0 : element[name];
16892
16892
  return Array.isArray(content) ? content : content === void 0 ? [] : [content];
16893
16893
  };
16894
- var childOf = (element, name) => childrenOf(element).find((child) => nameOf$2(child) === name);
16894
+ var childOf = (element, name) => childrenOf(element).find((child) => nameOf$3(child) === name);
16895
16895
  var attributeOf = (element, attribute) => {
16896
16896
  var _childOf;
16897
16897
  return (_childOf = childOf(element, "_attr")) === null || _childOf === void 0 || (_childOf = _childOf._attr) === null || _childOf === void 0 ? void 0 : _childOf[attribute];
@@ -16915,7 +16915,7 @@ var BLOCK_CONTAINERS = /* @__PURE__ */ new Set([
16915
16915
  * so the paragraphs in it aren't taken for headings. Nor are paragraphs in text boxes, as in Word.
16916
16916
  */
16917
16917
  var blocksOf = (elements) => elements.flatMap((element) => {
16918
- const name = nameOf$2(element);
16918
+ const name = nameOf$3(element);
16919
16919
  if (name === "w:p" || writtenTables.has(element)) return [element];
16920
16920
  return name !== void 0 && BLOCK_CONTAINERS.has(name) ? blocksOf(childrenOf(element)) : [];
16921
16921
  });
@@ -16935,7 +16935,7 @@ var TEXT_CONTAINERS = /* @__PURE__ */ new Set([
16935
16935
  ]);
16936
16936
  /** The text an element in a run stands for, such as `\t` for a tab. A page or column break isn't text */
16937
16937
  var textOfRunContent = (element) => {
16938
- switch (nameOf$2(element)) {
16938
+ switch (nameOf$3(element)) {
16939
16939
  case "w:t": return childrenOf(element).filter((child) => typeof child === "string").join("");
16940
16940
  case "w:tab": return " ";
16941
16941
  case "w:br": return [void 0, "textWrapping"].includes(attributeOf(element, "w:type")) ? "\n" : "";
@@ -16948,7 +16948,7 @@ var textOfRunContent = (element) => {
16948
16948
  var textOf = (paragraph) => {
16949
16949
  const fields = [];
16950
16950
  const read = (element) => {
16951
- const name = nameOf$2(element);
16951
+ const name = nameOf$3(element);
16952
16952
  if (name !== void 0 && TEXT_CONTAINERS.has(name)) return childrenOf(element).map(read).join("");
16953
16953
  if (name === "w:fldChar") {
16954
16954
  const type = attributeOf(element, "w:fldCharType");
@@ -16963,7 +16963,7 @@ var textOf = (paragraph) => {
16963
16963
  };
16964
16964
  /** The bookmarks started and ended in an element, in order */
16965
16965
  var bookmarkMarksOf = (element) => {
16966
- const name = nameOf$2(element);
16966
+ const name = nameOf$3(element);
16967
16967
  if (name === "w:bookmarkStart") return [{
16968
16968
  start: true,
16969
16969
  id: attributeOf(element, "w:id"),
@@ -17008,7 +17008,7 @@ var paragraphDetailsOf = (paragraphs, followBookmarks) => {
17008
17008
  var stylesOf = (context) => {
17009
17009
  var _context$file;
17010
17010
  const styles = (_context$file = context.file) === null || _context$file === void 0 || (_context$file = _context$file.Styles) === null || _context$file === void 0 ? void 0 : _context$file.prepForXml(context);
17011
- return new Map(childrenOf(styles).filter((style) => nameOf$2(style) === "w:style" && ["paragraph", void 0].includes(attributeOf(style, "w:type"))).map((style) => [attributeOf(style, "w:styleId"), {
17011
+ return new Map(childrenOf(styles).filter((style) => nameOf$3(style) === "w:style" && ["paragraph", void 0].includes(attributeOf(style, "w:type"))).map((style) => [attributeOf(style, "w:styleId"), {
17012
17012
  name: attributeOf(childOf(style, "w:name"), "w:val"),
17013
17013
  basedOn: attributeOf(childOf(style, "w:basedOn"), "w:val"),
17014
17014
  outlineLevel: numberAttributeOf(childOf(childOf(style, "w:pPr"), "w:outlineLvl"), "w:val")
@@ -17136,7 +17136,7 @@ var contentOf = ({ properties, beginDirty, textWidth }, entries, styles, context
17136
17136
  /** Puts a bookmark around the content of a formatted paragraph */
17137
17137
  var bookmark = (paragraph, name, id, context) => {
17138
17138
  const children = childrenOf(paragraph);
17139
- const start = children.findIndex((child) => nameOf$2(child) === "w:pPr") + 1;
17139
+ const start = children.findIndex((child) => nameOf$3(child) === "w:pPr") + 1;
17140
17140
  paragraph["w:p"] = [
17141
17141
  ...children.slice(0, start),
17142
17142
  new BookmarkStart(name, id).prepForXml(context),
@@ -17157,7 +17157,7 @@ var fillTablesOfContents = (body, context, bookmarkIds) => {
17157
17157
  if (tables.length === 0) return;
17158
17158
  const styles = stylesOf(context);
17159
17159
  const followBookmarks = tables.some(([, { properties }]) => Boolean(properties.entriesFromBookmark));
17160
- const headings = paragraphDetailsOf(blocks.filter((block) => nameOf$2(block) === "w:p"), followBookmarks).map((paragraph) => ({
17160
+ const headings = paragraphDetailsOf(blocks.filter((block) => nameOf$3(block) === "w:p"), followBookmarks).map((paragraph) => ({
17161
17161
  paragraph,
17162
17162
  levels: tables.map(([, { properties }]) => levelIn(properties, paragraph, styles))
17163
17163
  })).filter(({ levels }) => levels.some((level) => level !== void 0)).map((heading, index) => _objectSpread2(_objectSpread2({}, heading), {}, { id: bookmarkIds.get(index) }));
@@ -17172,7 +17172,7 @@ var fillTablesOfContents = (body, context, bookmarkIds) => {
17172
17172
  }];
17173
17173
  });
17174
17174
  if (entries.length === 0) return;
17175
- table["w:sdt"] = childrenOf(table).map((child) => nameOf$2(child) === "w:sdtContent" ? contentOf(options, entries, styles, context) : child);
17175
+ table["w:sdt"] = childrenOf(table).map((child) => nameOf$3(child) === "w:sdtContent" ? contentOf(options, entries, styles, context) : child);
17176
17176
  });
17177
17177
  };
17178
17178
  //#endregion
@@ -17352,21 +17352,21 @@ var sequenceNumbering = (context) => {
17352
17352
  *
17353
17353
  * @module
17354
17354
  */
17355
- var nameOf$1 = (element) => {
17355
+ var nameOf$2 = (element) => {
17356
17356
  const name = typeof element === "object" && element !== null && !Array.isArray(element) ? Object.keys(element)[0] : void 0;
17357
17357
  return name === "_attr" ? void 0 : name;
17358
17358
  };
17359
17359
  var textElement = (text) => ({ "w:t": [{ _attr: { "xml:space": "preserve" } }, text] });
17360
17360
  /** The elements docx formats to write a document */
17361
17361
  var FORMATTED = {
17362
- nameOf: nameOf$1,
17362
+ nameOf: nameOf$2,
17363
17363
  contentOf: (element) => {
17364
- const content = element[nameOf$1(element)];
17364
+ const content = element[nameOf$2(element)];
17365
17365
  return Array.isArray(content) ? content : void 0;
17366
17366
  },
17367
17367
  attributeOf: (element, attribute) => {
17368
17368
  var _holder$_attr;
17369
- const content = element[nameOf$1(element)];
17369
+ const content = element[nameOf$2(element)];
17370
17370
  const holder = Array.isArray(content) ? content.find((child) => typeof child === "object" && child !== null && "_attr" in child) : content;
17371
17371
  return holder === null || holder === void 0 || (_holder$_attr = holder._attr) === null || _holder$_attr === void 0 ? void 0 : _holder$_attr[attribute];
17372
17372
  },
@@ -18495,9 +18495,9 @@ var PageBreakBefore = class extends XmlComponent {
18495
18495
  var LineRuleType = {
18496
18496
  /** Line spacing is at least the specified value */
18497
18497
  AT_LEAST: "atLeast",
18498
- /** Line spacing is exactly the specified value */
18498
+ /** Writes `exactly`, which isn't a value the schema allows, so Word ignores it. Use {@link LineRuleType.EXACT} for an exact line height. */
18499
18499
  EXACTLY: "exactly",
18500
- /** Line spacing is exactly the specified value (alias for EXACTLY) */
18500
+ /** Line spacing is exactly the specified value */
18501
18501
  EXACT: "exact",
18502
18502
  /** Line spacing is automatically determined based on content */
18503
18503
  AUTO: "auto"
@@ -18957,20 +18957,44 @@ var HyperlinkType = {
18957
18957
  * ```
18958
18958
  */
18959
18959
  var ConcreteHyperlink = class extends XmlComponent {
18960
- constructor(children, relationshipId, anchor) {
18960
+ /**
18961
+ * @param children - Inline content of the hyperlink
18962
+ * @param relationshipId - Id of the external relationship, without the rId prefix
18963
+ * @param anchor - Bookmark name or external URL fragment
18964
+ * @param externalLink - The full address of an external hyperlink, so the relationship id is kept alongside its anchor
18965
+ */
18966
+ constructor(children, relationshipId, anchor, externalLink) {
18961
18967
  super("w:hyperlink");
18962
18968
  _defineProperty(this, "linkId", void 0);
18969
+ _defineProperty(this, "drawingLink", void 0);
18963
18970
  this.linkId = relationshipId;
18971
+ this.drawingLink = anchor && externalLink !== void 0 ? new DrawingLink(externalLink) : void 0;
18964
18972
  const attributes = new HyperlinkAttributes({
18965
18973
  history: 1,
18966
18974
  anchor: anchor ? anchor : void 0,
18967
- id: !anchor ? `rId${this.linkId}` : void 0
18975
+ id: !anchor || externalLink !== void 0 ? `rId${this.linkId}` : void 0
18968
18976
  });
18969
18977
  this.root.push(attributes);
18970
18978
  children.forEach((child) => {
18971
18979
  this.root.push(child);
18972
18980
  });
18973
18981
  }
18982
+ /**
18983
+ * Creates the `a:hlinkClick` of a picture in the hyperlink, which links to the same address.
18984
+ *
18985
+ * The hyperlink decides which relationship its pictures use, rather than the pictures reading `linkId`, because only it
18986
+ * knows whether that relationship has lost the fragment to `w:anchor`. The picture's relationship is added as the
18987
+ * picture is written, through the context's relationships, so it lands in the part the picture is in, both when
18988
+ * packing and when patching.
18989
+ *
18990
+ * @param context - The context the picture is written in, whose relationships get the picture's link if it has its own
18991
+ * @param declareNamespace - Declares the DrawingML namespace, for elements outside `a:graphic` such as `wp:docPr`
18992
+ */
18993
+ createDrawingClick(context, declareNamespace) {
18994
+ if (!this.drawingLink) return createHyperlinkClick(this.linkId, declareNamespace);
18995
+ this.drawingLink.addRelationship(context);
18996
+ return this.drawingLink.createClick(declareNamespace);
18997
+ }
18974
18998
  };
18975
18999
  /**
18976
19000
  * Represents an internal hyperlink to a bookmark within the document.
@@ -19019,6 +19043,11 @@ var InternalHyperlink = class extends ConcreteHyperlink {
19019
19043
  * External hyperlinks create a relationship to an external resource (URL).
19020
19044
  * The relationship is created during document preparation and the hyperlink
19021
19045
  * is converted to a ConcreteHyperlink with the relationship ID.
19046
+ * URL fragments of at most 255 UTF-16 units are written as anchors, preserving any additional # characters.
19047
+ * Longer fragments stay in the original relationship URI to avoid exceeding Word's anchor limit;
19048
+ * those links retain the existing limitations for fragments with multiple # characters.
19049
+ * Word appends the anchor to the relationship target as described in MS-OI29500 §17.16.22:
19050
+ * https://learn.microsoft.com/en-us/openspecs/office_standards/ms-oi29500/df06e423-11a6-4a36-bfb3-82139e531781
19022
19051
  *
19023
19052
  * Reference: http://officeopenxml.com/WPhyperlink.php
19024
19053
  *
@@ -19032,6 +19061,7 @@ var InternalHyperlink = class extends ConcreteHyperlink {
19032
19061
  * <xsd:group ref="EG_PContent" minOccurs="0" maxOccurs="unbounded"/>
19033
19062
  * <xsd:attribute ref="r:id"/>
19034
19063
  * <xsd:attribute name="history" type="s:ST_OnOff" use="optional"/>
19064
+ * <xsd:attribute name="anchor" type="s:ST_String" use="optional"/>
19035
19065
  * </xsd:complexType>
19036
19066
  * ```
19037
19067
  *
@@ -19480,6 +19510,29 @@ var PageReference = class extends Run {
19480
19510
  }
19481
19511
  };
19482
19512
  //#endregion
19513
+ //#region src/file/paragraph/links/external-hyperlink-target.ts
19514
+ /**
19515
+ * External hyperlink targets and fragments for WordprocessingML.
19516
+ *
19517
+ * Word appends the anchor to the relationship target, separated by a # character.
19518
+ * Reference: https://learn.microsoft.com/en-us/openspecs/office_standards/ms-oi29500/df06e423-11a6-4a36-bfb3-82139e531781
19519
+ *
19520
+ * @module
19521
+ */
19522
+ var MAX_ANCHOR_LENGTH = 255;
19523
+ /**
19524
+ * Splits a nonempty fragment that fits Word's anchor limit without decoding or normalizing either part.
19525
+ * Longer fragments stay in the original relationship URI, retaining its existing multi-hash limitations.
19526
+ */
19527
+ var externalHyperlinkTarget = (link) => {
19528
+ const index = link.indexOf("#");
19529
+ const fragmentLength = link.length - index - 1;
19530
+ return index > 0 && fragmentLength > 0 && fragmentLength <= MAX_ANCHOR_LENGTH ? {
19531
+ target: link.slice(0, index),
19532
+ anchor: link.slice(index + 1)
19533
+ } : { target: link };
19534
+ };
19535
+ //#endregion
19483
19536
  //#region src/file/fonts/font.ts
19484
19537
  /**
19485
19538
  * Font module for WordprocessingML documents.
@@ -19618,32 +19671,26 @@ var createFont = ({ name, altName, panose1, charset, family, notTrueType, pitch,
19618
19671
  ]
19619
19672
  });
19620
19673
  //#endregion
19621
- //#region src/file/fonts/create-regular-font.ts
19674
+ //#region src/file/fonts/create-embedded-font.ts
19622
19675
  /**
19623
- * Creates a regular embedded font with default settings.
19676
+ * Creates an embedded font with default settings.
19624
19677
  *
19625
19678
  * This helper function creates a font definition with standard font signature
19626
19679
  * values that work for most common fonts. The signature specifies Unicode
19627
19680
  * and code page ranges supported by the font.
19628
19681
  *
19629
- * @param options - Font creation options
19630
- * @param options.name - Font name
19631
- * @param options.index - Font relationship index
19632
- * @param options.fontKey - Unique font key (GUID) for obfuscation
19633
- * @param options.characterSet - Optional character set identifier
19634
- *
19635
19682
  * @returns XmlComponent representing the font definition
19636
19683
  *
19637
19684
  * @example
19638
19685
  * ```typescript
19639
- * const font = createRegularFont({
19686
+ * const font = createEmbeddedFont({
19640
19687
  * name: "Arial",
19641
- * index: 1,
19642
- * fontKey: "12345678-1234-1234-1234-123456789012"
19688
+ * embedRegular: { id: "rId1", fontKey: "12345678-1234-1234-1234-123456789012" },
19689
+ * embedBold: { id: "rId2", fontKey: "12345678-1234-1234-1234-123456789013" },
19643
19690
  * });
19644
19691
  * ```
19645
19692
  */
19646
- var createRegularFont = ({ name, index, fontKey, characterSet }) => createFont({
19693
+ var createEmbeddedFont = ({ name, characterSet, embedRegular, embedBold, embedItalic, embedBoldItalic }) => createFont({
19647
19694
  name,
19648
19695
  sig: {
19649
19696
  usb0: "E0002AFF",
@@ -19656,10 +19703,10 @@ var createRegularFont = ({ name, index, fontKey, characterSet }) => createFont({
19656
19703
  charset: characterSet,
19657
19704
  family: "auto",
19658
19705
  pitch: "variable",
19659
- embedRegular: {
19660
- fontKey,
19661
- id: `rId${index}`
19662
- }
19706
+ embedRegular,
19707
+ embedBold,
19708
+ embedItalic,
19709
+ embedBoldItalic
19663
19710
  });
19664
19711
  //#endregion
19665
19712
  //#region src/file/fonts/font-table.ts
@@ -19737,25 +19784,47 @@ var createFontTable = (fonts) => new BuilderElement({
19737
19784
  value: "w14 w15 w16se w16cid w16 w16cex w16sdtdh"
19738
19785
  }
19739
19786
  },
19740
- children: fonts.map((font, i) => createRegularFont({
19741
- name: font.name,
19742
- index: i + 1,
19743
- fontKey: font.fontKey,
19744
- characterSet: font.characterSet
19745
- }))
19787
+ children: fonts.map(createEmbeddedFont)
19746
19788
  });
19747
19789
  //#endregion
19748
19790
  //#region src/file/fonts/font-wrapper.ts
19791
+ var FACES = [
19792
+ {
19793
+ option: "data",
19794
+ element: "embedRegular",
19795
+ bold: false,
19796
+ italic: false
19797
+ },
19798
+ {
19799
+ option: "bold",
19800
+ element: "embedBold",
19801
+ bold: true,
19802
+ italic: false
19803
+ },
19804
+ {
19805
+ option: "italic",
19806
+ element: "embedItalic",
19807
+ bold: false,
19808
+ italic: true
19809
+ },
19810
+ {
19811
+ option: "boldItalic",
19812
+ element: "embedBoldItalic",
19813
+ bold: true,
19814
+ italic: true
19815
+ }
19816
+ ];
19749
19817
  /**
19750
19818
  * Wrapper class for managing the font table and its relationships.
19751
19819
  *
19752
19820
  * Creates a font table with embedded font files and manages the relationships
19753
- * required for font embedding. Each font is assigned a unique key for obfuscation.
19821
+ * required for font embedding. Each face of a font is embedded as a file of its own,
19822
+ * with a unique key for obfuscation.
19754
19823
  *
19755
19824
  * @example
19756
19825
  * ```typescript
19757
19826
  * const fontWrapper = new FontWrapper([
19758
- * { name: "CustomFont", data: fontBuffer }
19827
+ * { name: "CustomFont", data: fontBuffer, bold: boldFontBuffer }
19759
19828
  * ]);
19760
19829
  * ```
19761
19830
  */
@@ -19764,12 +19833,43 @@ var FontWrapper = class {
19764
19833
  _defineProperty(this, "options", void 0);
19765
19834
  _defineProperty(this, "fontTable", void 0);
19766
19835
  _defineProperty(this, "relationships", void 0);
19767
- _defineProperty(this, "fontOptionsWithKey", []);
19836
+ _defineProperty(
19837
+ this,
19838
+ /** @deprecated Use `files`, which has the file and key of each face a font embeds, not only the regular face's key */
19839
+ "fontOptionsWithKey",
19840
+ []
19841
+ );
19842
+ _defineProperty(
19843
+ this,
19844
+ /** The files of the faces the fonts embed, in order: the Nth is `fonts/font<N>.odttf`, with the relationship `rId<N>` */
19845
+ "files",
19846
+ []
19847
+ );
19768
19848
  this.options = options;
19769
- this.fontOptionsWithKey = options.map((o) => _objectSpread2(_objectSpread2({}, o), {}, { fontKey: uniqueUuid() }));
19770
- this.fontTable = createFontTable(this.fontOptionsWithKey);
19849
+ const faces = options.map((font) => FACES.flatMap(({ option, element, bold, italic }) => {
19850
+ const data = font[option];
19851
+ return data ? [{
19852
+ element,
19853
+ file: {
19854
+ name: font.name,
19855
+ data,
19856
+ bold,
19857
+ italic,
19858
+ fontKey: uniqueUuid()
19859
+ }
19860
+ }] : [];
19861
+ }));
19862
+ this.files = faces.flatMap((ofFont) => ofFont.map(({ file }) => file));
19863
+ this.fontOptionsWithKey = options.map((font, index) => _objectSpread2(_objectSpread2({}, font), {}, { fontKey: faces[index][0].file.fontKey }));
19864
+ this.fontTable = createFontTable(options.map((font, index) => _objectSpread2({
19865
+ name: font.name,
19866
+ characterSet: font.characterSet
19867
+ }, Object.fromEntries(faces[index].map(({ element, file }) => [element, {
19868
+ id: `rId${this.files.indexOf(file) + 1}`,
19869
+ fontKey: file.fontKey
19870
+ }])))));
19771
19871
  this.relationships = new Relationships();
19772
- for (let i = 0; i < options.length; i++) this.relationships.addRelationship(i + 1, "http://schemas.openxmlformats.org/officeDocument/2006/relationships/font", `fonts/font${i + 1}.odttf`);
19872
+ for (let i = 0; i < this.files.length; i++) this.relationships.addRelationship(i + 1, "http://schemas.openxmlformats.org/officeDocument/2006/relationships/font", `fonts/font${i + 1}.odttf`);
19773
19873
  }
19774
19874
  get View() {
19775
19875
  return this.fontTable;
@@ -20129,12 +20229,14 @@ var ParagraphProperties = class extends IgnoreIfEmptyXmlComponent {
20129
20229
  if (options.widowControl !== void 0) this.push(new OnOffElement("w:widowControl", options.widowControl));
20130
20230
  if (options.bullet) this.push(new NumberProperties(1, options.bullet.level));
20131
20231
  if (options.numbering) {
20132
- var _options$numbering$in, _options$numbering$in2;
20232
+ const { reference: list, instance = 0, level } = options.numbering;
20233
+ const reference = typeof list === "string" ? list : list.reference;
20133
20234
  this.numberingReferences.push({
20134
- reference: options.numbering.reference,
20135
- instance: (_options$numbering$in = options.numbering.instance) !== null && _options$numbering$in !== void 0 ? _options$numbering$in : 0
20235
+ reference,
20236
+ instance,
20237
+ definition: typeof list === "string" ? void 0 : list
20136
20238
  });
20137
- this.push(new NumberProperties(`${options.numbering.reference}-${(_options$numbering$in2 = options.numbering.instance) !== null && _options$numbering$in2 !== void 0 ? _options$numbering$in2 : 0}`, options.numbering.level));
20239
+ this.push(new NumberProperties(`${reference}-${instance}`, level));
20138
20240
  } else if (options.numbering === false) this.push(new NumberProperties(0, 0));
20139
20241
  if (options.border) this.push(new Border(options.border));
20140
20242
  if (options.thematicBreak) this.push(new ThematicBreak());
@@ -20214,7 +20316,7 @@ var ParagraphProperties = class extends IgnoreIfEmptyXmlComponent {
20214
20316
  * @returns The prepared XML object, or undefined if the component should be ignored
20215
20317
  */
20216
20318
  prepForXml(context) {
20217
- if (!(context.viewWrapper instanceof FontWrapper)) for (const reference of this.numberingReferences) context.file.Numbering.createConcreteNumberingInstance(reference.reference, reference.instance);
20319
+ if (!(context.viewWrapper instanceof FontWrapper)) for (const { reference, instance, definition } of this.numberingReferences) context.file.Numbering.createConcreteNumberingInstance(reference, instance, definition);
20218
20320
  return super.prepForXml(context);
20219
20321
  }
20220
20322
  };
@@ -20292,8 +20394,9 @@ var Paragraph = class extends FileChild {
20292
20394
  prepForXml(context) {
20293
20395
  for (const element of this.root) if (element instanceof ExternalHyperlink) {
20294
20396
  const index = this.root.indexOf(element);
20295
- const concreteHyperlink = new ConcreteHyperlink(element.options.children, uniqueId());
20296
- context.viewWrapper.Relationships.addRelationship(concreteHyperlink.linkId, "http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink", element.options.link, TargetModeType.EXTERNAL);
20397
+ const { target, anchor } = externalHyperlinkTarget(element.options.link);
20398
+ const concreteHyperlink = new ConcreteHyperlink(element.options.children, uniqueId(), anchor, element.options.link);
20399
+ context.viewWrapper.Relationships.addRelationship(concreteHyperlink.linkId, "http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink", target, TargetModeType.EXTERNAL);
20297
20400
  this.root[index] = concreteHyperlink;
20298
20401
  }
20299
20402
  return super.prepForXml(context);
@@ -26547,6 +26650,35 @@ var EndnotesAttributes = class extends XmlAttributeComponent {
26547
26650
  }
26548
26651
  };
26549
26652
  //#endregion
26653
+ //#region src/file/footnotes/footnote/note-paragraph.ts
26654
+ /**
26655
+ * The first paragraph of a footnote or endnote, written with the run that shows the note's number before its content.
26656
+ *
26657
+ * The run is added to what the paragraph is written as, rather than to the paragraph, so a paragraph in more than one
26658
+ * note, such as the notes of two documents, or two notes with the same content, has one number in each.
26659
+ *
26660
+ * @internal
26661
+ */
26662
+ var FirstNoteParagraph = class extends XmlComponent {
26663
+ constructor(paragraph, mark) {
26664
+ super("w:p");
26665
+ _defineProperty(this, "paragraph", void 0);
26666
+ _defineProperty(this, "mark", void 0);
26667
+ this.paragraph = paragraph;
26668
+ this.mark = mark;
26669
+ }
26670
+ prepForXml(context) {
26671
+ const content = this.paragraph.prepForXml(context)["w:p"];
26672
+ const children = Array.isArray(content) ? content : [];
26673
+ const index = children.length > 0 && "w:pPr" in children[0] ? 1 : 0;
26674
+ return { "w:p": [
26675
+ ...children.slice(0, index),
26676
+ this.mark.prepForXml(context),
26677
+ ...children.slice(index)
26678
+ ] };
26679
+ }
26680
+ };
26681
+ //#endregion
26550
26682
  //#region src/file/endnotes/endnote/endnote-attributes.ts
26551
26683
  var EndnoteAttributes = class extends XmlAttributeComponent {
26552
26684
  constructor(..._args) {
@@ -26578,11 +26710,7 @@ var Endnote = class extends XmlComponent {
26578
26710
  type: options.type,
26579
26711
  id: options.id
26580
26712
  }));
26581
- for (let i = 0; i < options.children.length; i++) {
26582
- const child = options.children[i];
26583
- if (i === 0) child.addRunToFront(new EndnoteRefRun());
26584
- this.root.push(child);
26585
- }
26713
+ for (const [index, child] of options.children.entries()) this.root.push(index === 0 ? new FirstNoteParagraph(child, new EndnoteRefRun()) : child);
26586
26714
  }
26587
26715
  };
26588
26716
  //#endregion
@@ -26701,6 +26829,8 @@ var SeperatorRun = class extends Run {
26701
26829
  var Endnotes = class extends XmlComponent {
26702
26830
  constructor() {
26703
26831
  super("w:endnotes");
26832
+ _defineProperty(this, "ownNotes", /* @__PURE__ */ new Map());
26833
+ _defineProperty(this, "highestId", 0);
26704
26834
  this.root.push(new EndnotesAttributes({
26705
26835
  wpc: "http://schemas.microsoft.com/office/word/2010/wordprocessingCanvas",
26706
26836
  mc: "http://schemas.openxmlformats.org/markup-compatibility/2006",
@@ -26753,6 +26883,27 @@ var Endnotes = class extends XmlComponent {
26753
26883
  children: paragraph
26754
26884
  });
26755
26885
  this.root.push(endnote);
26886
+ if (Number.isFinite(id)) this.highestId = Math.max(this.highestId, Math.floor(id));
26887
+ }
26888
+ /**
26889
+ * The id of the endnote that a reference run brings with it, which is added to the endnotes the first time the run
26890
+ * is written, with an id no other endnote has. Word has endnotes only in a document's body, so a run written
26891
+ * anywhere else, such as in a header, has none, and its endnote isn't added.
26892
+ *
26893
+ * @internal
26894
+ * @param reference - The run, which has the same endnote each time it is written
26895
+ * @param endnote - The endnote's content
26896
+ * @param context - The context the run is written in
26897
+ * @returns The endnote's id, or undefined outside the document's body
26898
+ */
26899
+ idOf(reference, endnote, context) {
26900
+ if (context.viewWrapper !== context.file.Document) return;
26901
+ const existing = this.ownNotes.get(reference);
26902
+ if (existing !== void 0) return existing;
26903
+ const id = this.highestId + 1;
26904
+ this.createEndnote(id, endnote.children);
26905
+ this.ownNotes.set(reference, id);
26906
+ return id;
26756
26907
  }
26757
26908
  /**
26758
26909
  * Formats the endnotes, with the page numbers worked out for their document written into their fields, when the
@@ -27097,11 +27248,7 @@ var Footnote = class extends XmlComponent {
27097
27248
  type: options.type,
27098
27249
  id: options.id
27099
27250
  }));
27100
- for (let i = 0; i < options.children.length; i++) {
27101
- const child = options.children[i];
27102
- if (i === 0) child.addRunToFront(new FootnoteRefRun());
27103
- this.root.push(child);
27104
- }
27251
+ for (const [index, child] of options.children.entries()) this.root.push(index === 0 ? new FirstNoteParagraph(child, new FootnoteRefRun()) : child);
27105
27252
  }
27106
27253
  };
27107
27254
  //#endregion
@@ -27204,6 +27351,8 @@ var FootnotesAttributes = class extends XmlAttributeComponent {
27204
27351
  var FootNotes = class extends XmlComponent {
27205
27352
  constructor() {
27206
27353
  super("w:footnotes");
27354
+ _defineProperty(this, "ownNotes", /* @__PURE__ */ new Map());
27355
+ _defineProperty(this, "highestId", 0);
27207
27356
  this.root.push(new FootnotesAttributes({
27208
27357
  wpc: "http://schemas.microsoft.com/office/word/2010/wordprocessingCanvas",
27209
27358
  mc: "http://schemas.openxmlformats.org/markup-compatibility/2006",
@@ -27262,6 +27411,27 @@ var FootNotes = class extends XmlComponent {
27262
27411
  children: paragraph
27263
27412
  });
27264
27413
  this.root.push(footnote);
27414
+ if (Number.isFinite(id)) this.highestId = Math.max(this.highestId, Math.floor(id));
27415
+ }
27416
+ /**
27417
+ * The id of the footnote that a reference run brings with it, which is added to the footnotes the first time the
27418
+ * run is written, with an id no other footnote has. Word has footnotes only in a document's body, so a run written
27419
+ * anywhere else, such as in a header, has none, and its footnote isn't added.
27420
+ *
27421
+ * @internal
27422
+ * @param reference - The run, which has the same footnote each time it is written
27423
+ * @param footnote - The footnote's content
27424
+ * @param context - The context the run is written in
27425
+ * @returns The footnote's id, or undefined outside the document's body
27426
+ */
27427
+ idOf(reference, footnote, context) {
27428
+ if (context.viewWrapper !== context.file.Document) return;
27429
+ const existing = this.ownNotes.get(reference);
27430
+ if (existing !== void 0) return existing;
27431
+ const id = this.highestId + 1;
27432
+ this.createFootNote(id, footnote.children);
27433
+ this.ownNotes.set(reference, id);
27434
+ return id;
27265
27435
  }
27266
27436
  /**
27267
27437
  * Formats the footnotes, with the page numbers worked out for their document written into their fields, when the
@@ -28470,8 +28640,15 @@ var Numbering = class extends XmlComponent {
28470
28640
  *
28471
28641
  * @param reference - The reference name of the abstract numbering definition
28472
28642
  * @param instance - The instance number for this concrete numbering
28643
+ * @param definition - The list's definition, for a list a paragraph gives its own definition of. It is added with
28644
+ * its reference, unless the numbering already has a list with that reference, such as one of the document's
28645
+ * `numbering` option, which is kept
28473
28646
  */
28474
- createConcreteNumberingInstance(reference, instance) {
28647
+ createConcreteNumberingInstance(reference, instance, definition) {
28648
+ if (definition && !this.abstractNumberingMap.has(definition.reference)) {
28649
+ this.abstractNumberingMap.set(definition.reference, new AbstractNumbering(this.abstractNumUniqueNumericId(), definition.levels));
28650
+ this.referenceConfigMap.set(definition.reference, definition.levels);
28651
+ }
28475
28652
  const abstractNumbering = this.abstractNumberingMap.get(reference);
28476
28653
  if (!abstractNumbering) return;
28477
28654
  const fullReference = `${reference}-${instance}`;
@@ -29571,7 +29748,7 @@ var NormalTableStyle = class extends Style {
29571
29748
  //#endregion
29572
29749
  //#region src/file/styles/styles.ts
29573
29750
  /** The name of a formatted element, such as `w:style`, or `_attr` for its parent's attributes */
29574
- var nameOf = (child) => typeof child === "object" ? Object.keys(child)[0] : void 0;
29751
+ var nameOf$1 = (child) => typeof child === "object" ? Object.keys(child)[0] : void 0;
29575
29752
  /** The attributes of a formatted `w:style` */
29576
29753
  var attributesOf = (style) => {
29577
29754
  var _flat$find;
@@ -29651,16 +29828,16 @@ var Styles = class extends XmlComponent {
29651
29828
  const xml = super.prepForXml(context);
29652
29829
  const children = xml["w:styles"];
29653
29830
  if (!Array.isArray(children)) return xml;
29654
- const named = (name) => children.filter((child) => nameOf(child) === name);
29655
- const ids = children.map((child) => nameOf(child) === "w:style" ? styleIdOf(child) : void 0);
29831
+ const named = (name) => children.filter((child) => nameOf$1(child) === name);
29832
+ const ids = children.map((child) => nameOf$1(child) === "w:style" ? styleIdOf(child) : void 0);
29656
29833
  const kept = children.filter((child, index) => ![
29657
29834
  "_attr",
29658
29835
  "w:docDefaults",
29659
29836
  "w:latentStyles"
29660
- ].includes(nameOf(child)) && (ids[index] === void 0 || ids.lastIndexOf(ids[index]) === index));
29661
- const styles = kept.some((child) => nameOf(child) === "w:style" && isDefaultParagraphStyle(child)) ? kept : kept.map((child) => {
29837
+ ].includes(nameOf$1(child)) && (ids[index] === void 0 || ids.lastIndexOf(ids[index]) === index));
29838
+ const styles = kept.some((child) => nameOf$1(child) === "w:style" && isDefaultParagraphStyle(child)) ? kept : kept.map((child) => {
29662
29839
  var _attributesOf$wType, _attributesOf2;
29663
- return nameOf(child) === "w:style" && styleIdOf(child) === "Normal" && ((_attributesOf$wType = (_attributesOf2 = attributesOf(child)) === null || _attributesOf2 === void 0 ? void 0 : _attributesOf2["w:type"]) !== null && _attributesOf$wType !== void 0 ? _attributesOf$wType : "paragraph") === "paragraph" ? markedAsDefault(child) : child;
29840
+ return nameOf$1(child) === "w:style" && styleIdOf(child) === "Normal" && ((_attributesOf$wType = (_attributesOf2 = attributesOf(child)) === null || _attributesOf2 === void 0 ? void 0 : _attributesOf2["w:type"]) !== null && _attributesOf$wType !== void 0 ? _attributesOf$wType : "paragraph") === "paragraph" ? markedAsDefault(child) : child;
29664
29841
  });
29665
29842
  return { "w:styles": [
29666
29843
  ...named("_attr"),
@@ -31053,16 +31230,6 @@ var Footer = class {
31053
31230
  //#endregion
31054
31231
  //#region src/file/footnotes/footnote/run/reference-run.ts
31055
31232
  /**
31056
- * Footnote reference run module for WordprocessingML documents.
31057
- *
31058
- * This module provides the footnote reference marker that appears in the
31059
- * main document text to indicate a footnote.
31060
- *
31061
- * Reference: http://officeopenxml.com/WPfootnotes.php
31062
- *
31063
- * @module
31064
- */
31065
- /**
31066
31233
  * Represents the attributes for a footnote reference element.
31067
31234
  *
31068
31235
  * @internal
@@ -31102,6 +31269,10 @@ var FootnoteReference = class extends XmlComponent {
31102
31269
  * (typically a superscript number) that appears in the main document text.
31103
31270
  * Clicking this marker navigates to the corresponding footnote content.
31104
31271
  *
31272
+ * It refers to one of the document's `footnotes` by its id, or is given its footnote's content, for a footnote of its
31273
+ * own, which is added to the document's footnotes when the run is written. Content made before the document it goes
31274
+ * in, such as by a function that makes paragraphs, then brings its footnotes with it.
31275
+ *
31105
31276
  * Reference: http://officeopenxml.com/WPfootnotes.php
31106
31277
  *
31107
31278
  * @publicApi
@@ -31115,17 +31286,44 @@ var FootnoteReference = class extends XmlComponent {
31115
31286
  * new FootnoteReferenceRun(1),
31116
31287
  * ],
31117
31288
  * });
31289
+ *
31290
+ * // Or with the footnote's content
31291
+ * new Paragraph({
31292
+ * children: [
31293
+ * new TextRun("This text has a footnote of its own"),
31294
+ * new FootnoteReferenceRun({ children: [new Paragraph("The footnote.")] }),
31295
+ * ],
31296
+ * });
31118
31297
  * ```
31119
31298
  */
31120
31299
  var FootnoteReferenceRun = class extends Run {
31121
31300
  /**
31122
31301
  * Creates a new footnote reference run.
31123
31302
  *
31124
- * @param id - Unique identifier linking to the footnote content
31303
+ * @param footnote - The id of one of the document's `footnotes`, or the footnote's content, for a footnote of the
31304
+ * run's own. Word has footnotes only in a document's body, so a run with its footnote's content is left out of
31305
+ * headers, footers, comments and notes
31125
31306
  */
31126
- constructor(id) {
31307
+ constructor(footnote) {
31127
31308
  super({ style: "FootnoteReference" });
31309
+ _defineProperty(this, "footnote", void 0);
31310
+ if (typeof footnote === "number") this.root.push(new FootnoteReference(footnote));
31311
+ else this.footnote = footnote;
31312
+ }
31313
+ /**
31314
+ * Formats the run, with its own footnote added to the document's footnotes, and referred to by the id it has there.
31315
+ */
31316
+ prepForXml(context) {
31317
+ var _context$file;
31318
+ if (this.footnote === void 0) return super.prepForXml(context);
31319
+ const id = (_context$file = context.file) === null || _context$file === void 0 ? void 0 : _context$file.FootNotes.View.idOf(this, this.footnote, context);
31320
+ if (id === void 0) return;
31128
31321
  this.root.push(new FootnoteReference(id));
31322
+ try {
31323
+ return super.prepForXml(context);
31324
+ } finally {
31325
+ this.root.pop();
31326
+ }
31129
31327
  }
31130
31328
  };
31131
31329
  //#endregion
@@ -31142,10 +31340,47 @@ var EndnoteIdReference = class extends XmlComponent {
31142
31340
  this.root.push(new EndnoteReferenceRunAttributes({ id }));
31143
31341
  }
31144
31342
  };
31343
+ /**
31344
+ * A run with an endnote's reference mark, its number, in the document's text.
31345
+ *
31346
+ * It refers to one of the document's `endnotes` by its id, or is given its endnote's content, for an endnote of its
31347
+ * own, which is added to the document's endnotes when the run is written.
31348
+ *
31349
+ * @publicApi
31350
+ *
31351
+ * @example
31352
+ * ```typescript
31353
+ * new Paragraph({
31354
+ * children: [new TextRun("A claim"), new EndnoteReferenceRun({ children: [new Paragraph("Its source.")] })],
31355
+ * });
31356
+ * ```
31357
+ */
31145
31358
  var EndnoteReferenceRun = class extends Run {
31146
- constructor(id) {
31359
+ /**
31360
+ * @param endnote - The id of one of the document's `endnotes`, or the endnote's content, for an endnote of the run's
31361
+ * own. Word has endnotes only in a document's body, so a run with its endnote's content is left out of headers,
31362
+ * footers, comments and notes
31363
+ */
31364
+ constructor(endnote) {
31147
31365
  super({ style: "EndnoteReference" });
31366
+ _defineProperty(this, "endnote", void 0);
31367
+ if (typeof endnote === "number") this.root.push(new EndnoteIdReference(endnote));
31368
+ else this.endnote = endnote;
31369
+ }
31370
+ /**
31371
+ * Formats the run, with its own endnote added to the document's endnotes, and referred to by the id it has there.
31372
+ */
31373
+ prepForXml(context) {
31374
+ var _context$file;
31375
+ if (this.endnote === void 0) return super.prepForXml(context);
31376
+ const id = (_context$file = context.file) === null || _context$file === void 0 ? void 0 : _context$file.Endnotes.View.idOf(this, this.endnote, context);
31377
+ if (id === void 0) return;
31148
31378
  this.root.push(new EndnoteIdReference(id));
31379
+ try {
31380
+ return super.prepForXml(context);
31381
+ } finally {
31382
+ this.root.pop();
31383
+ }
31149
31384
  }
31150
31385
  };
31151
31386
  //#endregion
@@ -35347,11 +35582,11 @@ var NumberingReplacer = class {
35347
35582
  *
35348
35583
  * @module
35349
35584
  */
35350
- var formatter$3 = new Formatter();
35585
+ var formatter$4 = new Formatter();
35351
35586
  /**
35352
35587
  * Formats a part's XML, with the relationships that anything in it that refers to other parts adds to.
35353
35588
  */
35354
- var xmlifyPart = (file, content, prettify, relationships, standalone = true) => (0, import_xml.default)(formatter$3.format(content, {
35589
+ var xmlifyPart = (file, content, prettify, relationships, standalone = true) => (0, import_xml.default)(formatter$4.format(content, {
35355
35590
  viewWrapper: {
35356
35591
  View: content,
35357
35592
  Relationships: relationships
@@ -35468,7 +35703,7 @@ var Compiler = class {
35468
35703
  zip.file(`word/media/${data.fileName}`, data.data);
35469
35704
  zip.file(`word/media/${data.fallback.fileName}`, data.fallback.data);
35470
35705
  }
35471
- for (const [i, { data: buffer, fontKey }] of file.FontTable.fontOptionsWithKey.entries()) zip.file(`word/fonts/font${i + 1}.odttf`, obfuscate(buffer, fontKey));
35706
+ for (const [i, { data: buffer, fontKey }] of file.FontTable.files.entries()) zip.file(`word/fonts/font${i + 1}.odttf`, obfuscate(buffer, fontKey));
35472
35707
  return zip;
35473
35708
  }
35474
35709
  xmlifyFile(file, prettify) {
@@ -36121,7 +36356,7 @@ var renumberBookmarksAvoiding = (idsInDocument) => {
36121
36356
  *
36122
36357
  * @module
36123
36358
  */
36124
- var formatter$2 = new Formatter();
36359
+ var formatter$3 = new Formatter();
36125
36360
  /**
36126
36361
  * Converts XML string to JSON element structure.
36127
36362
  *
@@ -36161,7 +36396,7 @@ var toJson = (xmlData) => {
36161
36396
  */
36162
36397
  var createTextElementContents = (text) => {
36163
36398
  var _textJson$elements$0$;
36164
- return (_textJson$elements$0$ = toJson((0, import_xml.default)(formatter$2.format(new Text({ text })))).elements[0].elements) !== null && _textJson$elements$0$ !== void 0 ? _textJson$elements$0$ : [];
36399
+ return (_textJson$elements$0$ = toJson((0, import_xml.default)(formatter$3.format(new Text({ text })))).elements[0].elements) !== null && _textJson$elements$0$ !== void 0 ? _textJson$elements$0$ : [];
36165
36400
  };
36166
36401
  /**
36167
36402
  * Adds xml:space="preserve" attribute to an element.
@@ -36277,6 +36512,81 @@ var removeContentTypeOverride = (element, partName) => {
36277
36512
  });
36278
36513
  };
36279
36514
  //#endregion
36515
+ //#region src/patcher/drawing-ids.ts
36516
+ var DRAWINGS = /* @__PURE__ */ new Set(["wp:inline", "wp:anchor"]);
36517
+ var ID_ELEMENTS = /* @__PURE__ */ new Set([
36518
+ "wp:docPr",
36519
+ "wps:cNvPr",
36520
+ "wpg:cNvPr"
36521
+ ]);
36522
+ var REFERENCE_ELEMENTS = /* @__PURE__ */ new Set(["a:stCxn", "a:endCxn"]);
36523
+ var idOf$1 = (element, names) => {
36524
+ var _element$name, _element$attributes;
36525
+ if (!names.has((_element$name = element.name) !== null && _element$name !== void 0 ? _element$name : "")) return;
36526
+ const id = Number((_element$attributes = element.attributes) === null || _element$attributes === void 0 ? void 0 : _element$attributes.id);
36527
+ return Number.isInteger(id) ? id : void 0;
36528
+ };
36529
+ /**
36530
+ * Finds the id of every drawing in an element, at any depth, and of the shapes in them, such as in a group.
36531
+ *
36532
+ * @param element - The element to search, such as a part's root
36533
+ * @returns The ids, once for each element that has one
36534
+ */
36535
+ var findDrawingIds = (element) => {
36536
+ var _element$elements;
36537
+ const id = idOf$1(element, ID_ELEMENTS);
36538
+ return [...id === void 0 ? [] : [id], ...((_element$elements = element.elements) !== null && _element$elements !== void 0 ? _element$elements : []).flatMap(findDrawingIds)];
36539
+ };
36540
+ var ownIdsOf = (drawing) => {
36541
+ const idsIn = (element) => {
36542
+ var _element$elements2;
36543
+ const id = idOf$1(element, ID_ELEMENTS);
36544
+ return [...id === void 0 ? [] : [id], ...((_element$elements2 = element.elements) !== null && _element$elements2 !== void 0 ? _element$elements2 : []).flatMap((child) => {
36545
+ var _child$name;
36546
+ return DRAWINGS.has((_child$name = child.name) !== null && _child$name !== void 0 ? _child$name : "") ? [] : idsIn(child);
36547
+ })];
36548
+ };
36549
+ return idsIn(drawing);
36550
+ };
36551
+ /**
36552
+ * Creates a function that renumbers the drawings in content being inserted, so none has an id another drawing in the
36553
+ * document has. Word finds a document whose drawings share an id unreadable, even when they are in different parts,
36554
+ * such as a header and the body. A drawing's id is chosen when it is created, without knowing which ids the template
36555
+ * has, and content inserted more than once would have the same ids each time.
36556
+ *
36557
+ * A drawing keeps its ids if nothing in the document has them yet, and otherwise gets the next unused ones. The
36558
+ * connectors in a drawing then still join the shapes they did.
36559
+ *
36560
+ * @param idsInDocument - The ids of the drawings already in the document, and of the shapes in them
36561
+ * @returns A function that returns the elements with their drawings renumbered
36562
+ */
36563
+ var renumberDrawingsAvoiding = (idsInDocument) => {
36564
+ const usedIds = new Set(idsInDocument);
36565
+ let highestId = idsInDocument.reduce((highest, id) => Math.max(highest, id), 0);
36566
+ const newIdFor = (id) => {
36567
+ const newId = usedIds.has(id) ? highestId + 1 : id;
36568
+ highestId = Math.max(highestId, newId);
36569
+ usedIds.add(newId);
36570
+ return newId;
36571
+ };
36572
+ const renumberDrawing = (drawing) => {
36573
+ const newIds = new Map([...new Set(ownIdsOf(drawing))].map((id) => [id, newIdFor(id)]));
36574
+ const renumberIn = (element) => {
36575
+ var _element$name2, _idOf;
36576
+ if (element !== drawing && DRAWINGS.has((_element$name2 = element.name) !== null && _element$name2 !== void 0 ? _element$name2 : "")) return renumberDrawing(element);
36577
+ const id = (_idOf = idOf$1(element, ID_ELEMENTS)) !== null && _idOf !== void 0 ? _idOf : idOf$1(element, REFERENCE_ELEMENTS);
36578
+ const newId = id === void 0 ? void 0 : newIds.get(id);
36579
+ return _objectSpread2(_objectSpread2(_objectSpread2({}, element), newId === void 0 ? {} : { attributes: _objectSpread2(_objectSpread2({}, element.attributes), {}, { id: String(newId) }) }), element.elements === void 0 ? {} : { elements: element.elements.map(renumberIn) });
36580
+ };
36581
+ return renumberIn(drawing);
36582
+ };
36583
+ const renumber = (element) => {
36584
+ var _element$name3;
36585
+ return DRAWINGS.has((_element$name3 = element.name) !== null && _element$name3 !== void 0 ? _element$name3 : "") ? renumberDrawing(element) : _objectSpread2(_objectSpread2({}, element), element.elements === void 0 ? {} : { elements: element.elements.map(renumber) });
36586
+ };
36587
+ return (elements) => elements.map(renumber);
36588
+ };
36589
+ //#endregion
36280
36590
  //#region src/patcher/patch-type.ts
36281
36591
  /**
36282
36592
  * The types of patch `patchDocument` applies.
@@ -36620,8 +36930,8 @@ var patchDrawings = ({ parts, binaryParts, file, patches, delimiters }, createCo
36620
36930
  *
36621
36931
  * @module
36622
36932
  */
36623
- var formatter$1 = new Formatter();
36624
- var DOCUMENT_PATH = "word/document.xml";
36933
+ var formatter$2 = new Formatter();
36934
+ var DOCUMENT_PATH$1 = "word/document.xml";
36625
36935
  var FOOTNOTES = {
36626
36936
  path: "word/footnotes.xml",
36627
36937
  rootName: "w:footnotes",
@@ -36656,7 +36966,7 @@ var ENDNOTES = {
36656
36966
  ]
36657
36967
  }
36658
36968
  };
36659
- var formatElement = (component, context) => toJson((0, import_xml.default)(formatter$1.format(component, context))).elements[0];
36969
+ var formatElement$1 = (component, context) => toJson((0, import_xml.default)(formatter$2.format(component, context))).elements[0];
36660
36970
  var findIds = (element, names) => {
36661
36971
  var _element$name, _element$attributes, _element$elements;
36662
36972
  const id = names.includes((_element$name = element.name) !== null && _element$name !== void 0 ? _element$name : "") ? Number((_element$attributes = element.attributes) === null || _element$attributes === void 0 ? void 0 : _element$attributes["w:id"]) : NaN;
@@ -36672,8 +36982,10 @@ var withMark = (paragraph, mark) => {
36672
36982
  ...elements.slice(index)
36673
36983
  ] });
36674
36984
  };
36675
- var patchNotesOfKind = (kind, notes, parts, { createContext, addContentTypeOverride, renumberBookmarks }) => {
36985
+ var patchNotesOfKind = (kind, notes, parts, { createContext, addContentTypeOverride, renumberBookmarks, renumberDrawings, renumberLists, useStyles }) => {
36676
36986
  const givenNotes = new Map(Object.entries(notes).map(([id, note]) => [Number(id), note]));
36987
+ const carriedIds = /* @__PURE__ */ new Map();
36988
+ let highestGivenId = [...givenNotes.keys()].filter(Number.isFinite).reduce((highest, id) => Math.max(highest, Math.floor(id)), 0);
36677
36989
  const noteOfId = /* @__PURE__ */ new Map();
36678
36990
  let highestId;
36679
36991
  const renumber = (element) => {
@@ -36686,11 +36998,11 @@ var patchNotesOfKind = (kind, notes, parts, { createContext, addContentTypeOverr
36686
36998
  };
36687
36999
  const findOrAddPart = () => {
36688
37000
  var _parts$get;
36689
- const relationship = getFirstLevelElements((_parts$get = parts.get(relationshipsPathOf(DOCUMENT_PATH))) !== null && _parts$get !== void 0 ? _parts$get : {}, "Relationships").find((element) => {
37001
+ const relationship = getFirstLevelElements((_parts$get = parts.get(relationshipsPathOf(DOCUMENT_PATH$1))) !== null && _parts$get !== void 0 ? _parts$get : {}, "Relationships").find((element) => {
36690
37002
  var _element$attributes3;
36691
37003
  return ((_element$attributes3 = element.attributes) === null || _element$attributes3 === void 0 ? void 0 : _element$attributes3.Type) === kind.relationshipType;
36692
37004
  });
36693
- const path = relationship ? resolveTarget(DOCUMENT_PATH, String(relationship.attributes.Target)) : kind.path;
37005
+ const path = relationship ? resolveTarget(DOCUMENT_PATH$1, String(relationship.attributes.Target)) : kind.path;
36694
37006
  if (!parts.has(path)) {
36695
37007
  parts.set(path, {
36696
37008
  declaration: { attributes: {
@@ -36698,11 +37010,11 @@ var patchNotesOfKind = (kind, notes, parts, { createContext, addContentTypeOverr
36698
37010
  encoding: "UTF-8",
36699
37011
  standalone: "yes"
36700
37012
  } },
36701
- elements: [formatElement(kind.create.part(), createContext(path))]
37013
+ elements: [formatElement$1(kind.create.part(), createContext(path))]
36702
37014
  });
36703
37015
  addContentTypeOverride(kind.contentType, `/${path}`);
36704
37016
  }
36705
- if (!relationship) createContext(DOCUMENT_PATH).viewWrapper.Relationships.addRelationship(uniqueId(), kind.relationshipType, relativeTarget(DOCUMENT_PATH, path));
37017
+ if (!relationship) createContext(DOCUMENT_PATH$1).viewWrapper.Relationships.addRelationship(uniqueId(), kind.relationshipType, relativeTarget(DOCUMENT_PATH$1, path));
36706
37018
  return path;
36707
37019
  };
36708
37020
  const write = () => {
@@ -36710,14 +37022,14 @@ var patchNotesOfKind = (kind, notes, parts, { createContext, addContentTypeOverr
36710
37022
  const path = findOrAddPart();
36711
37023
  const context = createContext(path);
36712
37024
  const contentOfNote = new Map([...new Set(noteOfId.values())].map((note) => {
36713
- const mark = formatElement(kind.create.mark(), context);
36714
- return [note, renumberBookmarks(note.children.map((paragraph) => formatElement(paragraph, context)).map((paragraph, index) => index === 0 ? withMark(paragraph, mark) : paragraph))];
37025
+ const mark = formatElement$1(kind.create.mark(), context);
37026
+ return [note, useStyles(renumberLists(renumberBookmarks(note.children.map((paragraph) => formatElement$1(paragraph, context)).map((paragraph, index) => index === 0 ? withMark(paragraph, mark) : paragraph))))];
36715
37027
  }));
36716
37028
  getFirstLevelElements(parts.get(path), kind.rootName).push(...[...noteOfId].map(([id, note]) => ({
36717
37029
  type: "element",
36718
37030
  name: kind.noteName,
36719
37031
  attributes: { "w:id": String(id) },
36720
- elements: [...contentOfNote.get(note)]
37032
+ elements: [...renumberDrawings(contentOfNote.get(note))]
36721
37033
  })));
36722
37034
  const stylesPart = parts.get("word/styles.xml");
36723
37035
  if (stylesPart) {
@@ -36726,37 +37038,165 @@ var patchNotesOfKind = (kind, notes, parts, { createContext, addContentTypeOverr
36726
37038
  var _style$attributes;
36727
37039
  return (_style$attributes = style.attributes) === null || _style$attributes === void 0 ? void 0 : _style$attributes["w:styleId"];
36728
37040
  }));
36729
- styles.push(...kind.create.styles().map((style) => formatElement(style, context)).filter((style) => {
37041
+ styles.push(...kind.create.styles().map((style) => formatElement$1(style, context)).filter((style) => {
36730
37042
  var _style$attributes2;
36731
37043
  return !styleIds.has((_style$attributes2 = style.attributes) === null || _style$attributes2 === void 0 ? void 0 : _style$attributes2["w:styleId"]);
36732
37044
  }));
36733
37045
  }
36734
37046
  };
37047
+ const carry = (reference, note) => {
37048
+ const existing = carriedIds.get(reference);
37049
+ if (existing !== void 0) return existing;
37050
+ highestGivenId++;
37051
+ givenNotes.set(highestGivenId, note);
37052
+ carriedIds.set(reference, highestGivenId);
37053
+ return highestGivenId;
37054
+ };
36735
37055
  return {
36736
37056
  renumber: (elements) => elements.map(renumber),
36737
- write
37057
+ write,
37058
+ carry
36738
37059
  };
36739
37060
  };
36740
37061
  /**
36741
37062
  * Creates the writer of the footnotes and endnotes that patches refer to.
36742
37063
  *
36743
37064
  * A patch refers to a note with a reference run, such as `new FootnoteReferenceRun(1)`, whose id is the note's in
36744
- * `footnotes`. Only references to the given notes are renumbered, and only the notes that are referred to are written.
37065
+ * `footnotes`, or with a run that brings its note with it, such as `new FootnoteReferenceRun({ children })`, which is
37066
+ * given an id with `carry` as it is written. Only references to these notes are renumbered, and only the notes that
37067
+ * are referred to are written.
36745
37068
  *
36746
37069
  * @param notes - The footnotes and endnotes, by the id the patches' reference runs are given
36747
37070
  * @param parts - The document's XML parts, parsed, by their paths, which the notes are written to
36748
37071
  * @param helpers - The patcher's helpers for what the notes refer to
36749
37072
  */
36750
37073
  var patchNotes = ({ footnotes = {}, endnotes = {} }, parts, helpers) => {
36751
- const patchers = [patchNotesOfKind(FOOTNOTES, footnotes, parts, helpers), patchNotesOfKind(ENDNOTES, endnotes, parts, helpers)];
37074
+ const patchers = {
37075
+ footnotes: patchNotesOfKind(FOOTNOTES, footnotes, parts, helpers),
37076
+ endnotes: patchNotesOfKind(ENDNOTES, endnotes, parts, helpers)
37077
+ };
36752
37078
  return {
36753
- renumber: (elements) => patchers.reduce((renumbered, patcher) => patcher.renumber(renumbered), elements),
37079
+ carry: (kind, reference, note) => patchers[kind].carry(reference, note),
37080
+ renumber: (elements) => Object.values(patchers).reduce((renumbered, patcher) => patcher.renumber(renumbered), elements),
36754
37081
  write: () => {
36755
- for (const patcher of patchers) patcher.write();
37082
+ for (const patcher of Object.values(patchers)) patcher.write();
36756
37083
  }
36757
37084
  };
36758
37085
  };
36759
37086
  //#endregion
37087
+ //#region src/patcher/numbering.ts
37088
+ /**
37089
+ * Lists in content inserted into an existing document.
37090
+ *
37091
+ * @module
37092
+ */
37093
+ var formatter$1 = new Formatter();
37094
+ var DOCUMENT_PATH = "word/document.xml";
37095
+ var NUMBERING_PATH = "word/numbering.xml";
37096
+ var NUMBERING_CONTENT_TYPE = "application/vnd.openxmlformats-officedocument.wordprocessingml.numbering+xml";
37097
+ var NUMBERING_RELATIONSHIP = "http://schemas.openxmlformats.org/officeDocument/2006/relationships/numbering";
37098
+ var BULLET_REFERENCE = "default-bullet-numbering";
37099
+ var BULLET_NUM_ID = "1";
37100
+ var formatElement = (component, context) => toJson((0, import_xml.default)(formatter$1.format(component, context))).elements[0];
37101
+ var highestOf = (ids) => ids.reduce((highest, id) => Math.max(highest, id), 0);
37102
+ /**
37103
+ * Creates the writer of the lists that patches use.
37104
+ *
37105
+ * A paragraph in a patch is put in a list as in a Document, with `numbering: { reference, level }` for one of the
37106
+ * numbering's references, or with `bullet`. It is written with a placeholder for its list's id, or for a bullet, with
37107
+ * the id a Document's bullet list has, which a template's lists may have too.
37108
+ *
37109
+ * @param numbering - The numbering the patches' paragraphs add their lists to as they are written
37110
+ * @param parts - The document's XML parts, parsed, by their paths, which the lists are written to
37111
+ * @param helpers - The patcher's helpers for the numbering part
37112
+ */
37113
+ var patchNumbering = (numbering, parts, { createContext, addContentTypeOverride }) => {
37114
+ const newNumIds = /* @__PURE__ */ new Map();
37115
+ let highestNumId;
37116
+ const numberingRelationship = () => {
37117
+ var _parts$get;
37118
+ return getFirstLevelElements((_parts$get = parts.get(relationshipsPathOf(DOCUMENT_PATH))) !== null && _parts$get !== void 0 ? _parts$get : {}, "Relationships").find((element) => {
37119
+ var _element$attributes;
37120
+ return ((_element$attributes = element.attributes) === null || _element$attributes === void 0 ? void 0 : _element$attributes.Type) === NUMBERING_RELATIONSHIP;
37121
+ });
37122
+ };
37123
+ const numberingPath = (relationship = numberingRelationship()) => relationship ? resolveTarget(DOCUMENT_PATH, String(relationship.attributes.Target)) : NUMBERING_PATH;
37124
+ const idsInTemplate = (name, attribute) => {
37125
+ var _parts$get2;
37126
+ return getFirstLevelElements((_parts$get2 = parts.get(numberingPath())) !== null && _parts$get2 !== void 0 ? _parts$get2 : {}, "w:numbering").filter((element) => element.name === name).map((element) => Number(element.attributes[attribute]));
37127
+ };
37128
+ const listOf = (numId) => {
37129
+ if (numId === BULLET_NUM_ID) return numbering.ConcreteNumbering.find(({ reference }) => reference === BULLET_REFERENCE);
37130
+ if (!numId.startsWith("{")) return;
37131
+ const list = numbering.ConcreteNumbering.find(({ reference, instance }) => numId === `{${reference}-${instance}}`);
37132
+ if (!list) {
37133
+ const reference = numId.slice(1, -1).replace(/-\d+$/, "");
37134
+ throw new Error(`A paragraph in a patch uses the numbering "${reference}", which isn't in the numbering option of patchDocument. Add it there with its levels, as in a Document`);
37135
+ }
37136
+ return list;
37137
+ };
37138
+ const newNumIdOf = (list) => {
37139
+ var _highestNumId;
37140
+ const knownId = newNumIds.get(list.numId);
37141
+ if (knownId !== void 0) return knownId;
37142
+ highestNumId = ((_highestNumId = highestNumId) !== null && _highestNumId !== void 0 ? _highestNumId : highestOf(idsInTemplate("w:num", "w:numId"))) + 1;
37143
+ newNumIds.set(list.numId, highestNumId);
37144
+ return highestNumId;
37145
+ };
37146
+ const renumber = (element) => {
37147
+ const list = element.name === "w:numId" ? listOf(String(element.attributes["w:val"])) : void 0;
37148
+ if (list === void 0) return element.elements === void 0 ? element : _objectSpread2(_objectSpread2({}, element), {}, { elements: element.elements.map(renumber) });
37149
+ return _objectSpread2(_objectSpread2({}, element), {}, { attributes: _objectSpread2(_objectSpread2({}, element.attributes), {}, { "w:val": String(newNumIdOf(list)) }) });
37150
+ };
37151
+ const findOrAddPart = (written) => {
37152
+ const relationship = numberingRelationship();
37153
+ const path = numberingPath(relationship);
37154
+ if (!parts.has(path)) {
37155
+ parts.set(path, {
37156
+ declaration: { attributes: {
37157
+ version: "1.0",
37158
+ encoding: "UTF-8",
37159
+ standalone: "yes"
37160
+ } },
37161
+ elements: [_objectSpread2(_objectSpread2({}, written), {}, { elements: [] })]
37162
+ });
37163
+ addContentTypeOverride(NUMBERING_CONTENT_TYPE, `/${path}`);
37164
+ }
37165
+ if (!relationship) createContext(DOCUMENT_PATH).viewWrapper.Relationships.addRelationship(uniqueId(), NUMBERING_RELATIONSHIP, relativeTarget(DOCUMENT_PATH, path));
37166
+ return path;
37167
+ };
37168
+ const write = () => {
37169
+ var _root$attributes$mcI, _root$attributes;
37170
+ if (newNumIds.size === 0) return;
37171
+ const written = formatElement(numbering, createContext(numberingPath()));
37172
+ const abstractNumIdOf = (list) => Number(list.elements.find((element) => element.name === "w:abstractNumId").attributes["w:val"]);
37173
+ const lists = written.elements.filter((element) => element.name === "w:num" && newNumIds.has(Number(element.attributes["w:numId"])));
37174
+ const highestAbstractNumId = highestOf(idsInTemplate("w:abstractNum", "w:abstractNumId"));
37175
+ const newAbstractNumIds = new Map([...new Set(lists.map(abstractNumIdOf))].map((id, index) => [id, highestAbstractNumId + index + 1]));
37176
+ const abstractLists = written.elements.flatMap((element) => {
37177
+ const newId = element.name === "w:abstractNum" ? newAbstractNumIds.get(Number(element.attributes["w:abstractNumId"])) : void 0;
37178
+ return newId === void 0 ? [] : [_objectSpread2(_objectSpread2({}, element), {}, { attributes: _objectSpread2(_objectSpread2({}, element.attributes), {}, { "w:abstractNumId": String(newId) }) })];
37179
+ });
37180
+ const path = findOrAddPart(written);
37181
+ const root = parts.get(path).elements.find((element) => element.name === "w:numbering");
37182
+ root.attributes = _objectSpread2(_objectSpread2(_objectSpread2({}, Object.fromEntries(Object.entries(written.attributes).filter(([name]) => name.startsWith("xmlns:")))), root.attributes), {}, { "mc:Ignorable": [.../* @__PURE__ */ new Set([...String((_root$attributes$mcI = (_root$attributes = root.attributes) === null || _root$attributes === void 0 ? void 0 : _root$attributes["mc:Ignorable"]) !== null && _root$attributes$mcI !== void 0 ? _root$attributes$mcI : "").split(" "), ...String(written.attributes["mc:Ignorable"]).split(" ")])].filter((prefix) => prefix !== "").join(" ") });
37183
+ const elements = getFirstLevelElements(parts.get(path), "w:numbering");
37184
+ const firstIndexOf = (names) => {
37185
+ const index = elements.findIndex((element) => names.includes(element.name));
37186
+ return index === -1 ? elements.length : index;
37187
+ };
37188
+ elements.splice(firstIndexOf(["w:num", "w:numIdMacAtCleanup"]), 0, ...abstractLists);
37189
+ elements.splice(firstIndexOf(["w:numIdMacAtCleanup"]), 0, ...lists.map((list) => _objectSpread2(_objectSpread2({}, list), {}, {
37190
+ attributes: _objectSpread2(_objectSpread2({}, list.attributes), {}, { "w:numId": String(newNumIds.get(Number(list.attributes["w:numId"]))) }),
37191
+ elements: list.elements.map((element) => element.name === "w:abstractNumId" ? _objectSpread2(_objectSpread2({}, element), {}, { attributes: { "w:val": String(newAbstractNumIds.get(abstractNumIdOf(list))) } }) : element)
37192
+ })));
37193
+ };
37194
+ return {
37195
+ renumber: (elements) => elements.map(renumber),
37196
+ write
37197
+ };
37198
+ };
37199
+ //#endregion
36760
37200
  //#region src/patcher/page-numbers.ts
36761
37201
  /**
36762
37202
  * Page numbers written into a template's fields once `patchDocument` has patched it, from an estimate of its pages, as
@@ -37184,7 +37624,6 @@ var findLocationOfText = (node, text) => traverse(node).filter((p) => p.text.inc
37184
37624
  *
37185
37625
  * @module
37186
37626
  */
37187
- var formatter = new Formatter();
37188
37627
  var SPLIT_TOKEN = "￿";
37189
37628
  /**
37190
37629
  * Replaces placeholder text in XML with new content from a patch.
@@ -37201,7 +37640,7 @@ var SPLIT_TOKEN = "
37201
37640
  * @param keepOriginalStyles - Whether to preserve original text formatting
37202
37641
  * @param recursive - Whether to replace every occurrence in a paragraph, rather than only the first
37203
37642
  * @param renumberIds - Renumbers the bookmarks and note references the patch inserts, so they don't take an id the
37204
- * document uses
37643
+ * document uses, and records the styles it uses
37205
37644
  * @returns Result containing the modified element and whether a replacement occurred
37206
37645
  */
37207
37646
  var replacer = ({ json, patch, patchText, context, keepOriginalStyles = true, recursive = true, renumberIds = (elements) => elements }) => {
@@ -37257,7 +37696,10 @@ var replacer = ({ json, patch, patchText, context, keepOriginalStyles = true, re
37257
37696
  var formatChildren = (patch, context, renumberIds) => renumberIds(patch.children.flatMap((c) => {
37258
37697
  var _c$writtenAs;
37259
37698
  return (_c$writtenAs = c.writtenAs) !== null && _c$writtenAs !== void 0 ? _c$writtenAs : c;
37260
- }).map((c) => toJson((0, import_xml.default)(formatter.format(c, context)))).map((c) => c.elements[0]));
37699
+ }).flatMap((c) => {
37700
+ const formatted = c.prepForXml(context);
37701
+ return formatted ? [toJson((0, import_xml.default)(formatted)).elements[0]] : [];
37702
+ }));
37261
37703
  /**
37262
37704
  * Replaces the first occurrence of the placeholder from `fromIndex` on, splitting the run it starts in.
37263
37705
  *
@@ -37381,6 +37823,91 @@ var goToElementFromPath = (json, path) => {
37381
37823
  var goToParentElementFromPath = (json, path) => goToElementFromPath(json, path.slice(0, path.length - 1));
37382
37824
  var getLastElementIndexFromPath = (path) => path[path.length - 1];
37383
37825
  //#endregion
37826
+ //#region src/patcher/styles.ts
37827
+ /**
37828
+ * Styles of content inserted into an existing document.
37829
+ *
37830
+ * @module
37831
+ */
37832
+ var formatter = new Formatter();
37833
+ var STYLES_PATH = "word/styles.xml";
37834
+ var REFERENCES = /* @__PURE__ */ new Set([
37835
+ "w:pStyle",
37836
+ "w:rStyle",
37837
+ "w:tblStyle",
37838
+ "w:basedOn",
37839
+ "w:next",
37840
+ "w:link"
37841
+ ]);
37842
+ var idOf = (style) => {
37843
+ var _style$attributes;
37844
+ return String((_style$attributes = style.attributes) === null || _style$attributes === void 0 ? void 0 : _style$attributes["w:styleId"]);
37845
+ };
37846
+ var nameOf = (style) => {
37847
+ var _style$elements;
37848
+ const name = (_style$elements = style.elements) === null || _style$elements === void 0 || (_style$elements = _style$elements.find((element) => element.name === "w:name")) === null || _style$elements === void 0 || (_style$elements = _style$elements.attributes) === null || _style$elements === void 0 ? void 0 : _style$elements["w:val"];
37849
+ return name === void 0 ? void 0 : String(name).toLowerCase();
37850
+ };
37851
+ var formatDefaultStyles = (context) => new Map(Object.values(createDefaultStyles()).map((style) => toJson((0, import_xml.default)(formatter.format(style, context))).elements[0]).filter((style) => style.name === "w:style").map((style) => [idOf(style), style]));
37852
+ /**
37853
+ * Creates the writer of the styles that patches use.
37854
+ *
37855
+ * A paragraph in a patch refers to its style by its id, such as `Heading1` for `HeadingLevel.HEADING_1`, which a
37856
+ * template may not have, as Word only saves the styles that a document uses. Word shows a paragraph whose style the
37857
+ * document doesn't have in the Normal style, and LibreOffice leaves out its number if it is in a list, so the styles of
37858
+ * docx's that the content uses are added to the document.
37859
+ *
37860
+ * @param parts - The document's XML parts, parsed, by their paths, whose styles part the styles are added to
37861
+ * @param createContext - Creates a context to format content for a part with
37862
+ */
37863
+ var patchStyles = (parts, createContext) => {
37864
+ var _parts$get;
37865
+ const templateStyles = getFirstLevelElements((_parts$get = parts.get(STYLES_PATH)) !== null && _parts$get !== void 0 ? _parts$get : {}, "w:styles").filter((element) => element.name === "w:style");
37866
+ const templateIds = new Set(templateStyles.map(idOf));
37867
+ let defaultStyles;
37868
+ const defaultStyleOf = (id) => {
37869
+ var _defaultStyles;
37870
+ (_defaultStyles = defaultStyles) !== null && _defaultStyles !== void 0 || (defaultStyles = formatDefaultStyles(createContext(STYLES_PATH)));
37871
+ return defaultStyles.get(id);
37872
+ };
37873
+ const missingIds = /* @__PURE__ */ new Set();
37874
+ const idsInDocument = /* @__PURE__ */ new Map();
37875
+ const findIdInDocument = (id) => {
37876
+ const style = templateIds.has(id) ? void 0 : defaultStyleOf(id);
37877
+ if (style === void 0) return id;
37878
+ const sameStyle = templateStyles.find((templateStyle) => {
37879
+ var _templateStyle$attrib, _style$attributes2;
37880
+ return ((_templateStyle$attrib = templateStyle.attributes) === null || _templateStyle$attrib === void 0 ? void 0 : _templateStyle$attrib["w:type"]) === ((_style$attributes2 = style.attributes) === null || _style$attributes2 === void 0 ? void 0 : _style$attributes2["w:type"]) && nameOf(templateStyle) === nameOf(style);
37881
+ });
37882
+ if (sameStyle !== void 0) return idOf(sameStyle);
37883
+ missingIds.add(id);
37884
+ return id;
37885
+ };
37886
+ const idInDocument = (id) => {
37887
+ if (!idsInDocument.has(id)) idsInDocument.set(id, findIdInDocument(id));
37888
+ return idsInDocument.get(id);
37889
+ };
37890
+ const withIdsInDocument = (element) => {
37891
+ var _element$name;
37892
+ if (REFERENCES.has((_element$name = element.name) !== null && _element$name !== void 0 ? _element$name : "")) return _objectSpread2(_objectSpread2({}, element), {}, { attributes: _objectSpread2(_objectSpread2({}, element.attributes), {}, { "w:val": idInDocument(String(element.attributes["w:val"])) }) });
37893
+ return element.elements === void 0 ? element : _objectSpread2(_objectSpread2({}, element), {}, { elements: element.elements.map(withIdsInDocument) });
37894
+ };
37895
+ const write = () => {
37896
+ const stylesPart = parts.get(STYLES_PATH);
37897
+ if (!stylesPart) return;
37898
+ const styles = getFirstLevelElements(stylesPart, "w:styles");
37899
+ const ids = new Set(styles.map(idOf));
37900
+ for (const id of missingIds) if (!ids.has(id)) {
37901
+ ids.add(id);
37902
+ styles.push(withIdsInDocument(defaultStyleOf(id)));
37903
+ }
37904
+ };
37905
+ return {
37906
+ use: (elements) => elements.map(withIdsInDocument),
37907
+ write
37908
+ };
37909
+ };
37910
+ //#endregion
37384
37911
  //#region src/patcher/table-rows.ts
37385
37912
  var EMPTY = {
37386
37913
  type: PatchType.PARAGRAPH,
@@ -37395,8 +37922,9 @@ var EMPTY = {
37395
37922
  * @param patch - The rows of data
37396
37923
  * @param delimiters - The placeholders' delimiters
37397
37924
  * @param patchPlaceholder - Patches a field in a copy of the rows, as `patchDocument` patches a placeholder
37925
+ * @param renumberDrawings - Gives the drawings in a copy of the rows ids no other drawing in the document has
37398
37926
  */
37399
- var patchTableRows = ({ json, key, patch, delimiters: { start, end }, patchPlaceholder }) => {
37927
+ var patchTableRows = ({ json, key, patch, delimiters: { start, end }, patchPlaceholder, renumberDrawings }) => {
37400
37928
  const fieldStart = `${start}${key}.`;
37401
37929
  for (const rows of findRowsToRepeat(json, fieldStart)) {
37402
37930
  const fields = fieldsIn(rows.elements, fieldStart, end);
@@ -37404,7 +37932,7 @@ var patchTableRows = ({ json, key, patch, delimiters: { start, end }, patchPlace
37404
37932
  const copy = {
37405
37933
  type: "element",
37406
37934
  name: "w:tbl",
37407
- elements: [...index === 0 ? rows.elements.map(copyOf) : withoutIds(rows.elements)]
37935
+ elements: [...index === 0 ? rows.elements.map(copyOf) : renumberDrawings(withoutIds(rows.elements))]
37408
37936
  };
37409
37937
  const fieldPatches = new Map(Object.entries(row).flatMap(([field, p]) => p === void 0 ? [] : [[field, p]]));
37410
37938
  for (const [field, fieldPatch] of fieldPatches) patchPlaceholder(copy, `${key}.${field}`, fieldPatch);
@@ -37654,14 +38182,17 @@ var patchDocument = function() {
37654
38182
  var _ref = _asyncToGenerator(function* ({ outputType, data, patches, keepOriginalStyles, placeholderDelimiters = {
37655
38183
  start: "{{",
37656
38184
  end: "}}"
37657
- }, recursive = true, footnotes, endnotes, pageNumbers }) {
38185
+ }, recursive = true, footnotes, endnotes, numbering = { config: [] }, pageNumbers }) {
37658
38186
  const zipContent = data instanceof import_jszip_min.default ? data : yield import_jszip_min.default.loadAsync(data);
37659
38187
  const contexts = /* @__PURE__ */ new Map();
37660
38188
  const themeColors = yield readThemeColors(zipContent);
37661
38189
  const contentTypeOverrides = [];
37662
38190
  const file = {
37663
38191
  Media: new Media(),
38192
+ Numbering: new Numbering(numbering),
37664
38193
  Theme: themeColors && { Colors: themeColors },
38194
+ FootNotes: { View: { idOf: (reference, note, context) => carryNote("footnotes", reference, note, context) } },
38195
+ Endnotes: { View: { idOf: (reference, note, context) => carryNote("endnotes", reference, note, context) } },
37665
38196
  PackageParts: new PackageParts({ addOverride: (contentType, partName) => contentTypeOverrides.push({
37666
38197
  contentType,
37667
38198
  partName
@@ -37704,9 +38235,12 @@ var patchDocument = function() {
37704
38235
  map.set(key, json);
37705
38236
  }
37706
38237
  const renumberBookmarks = renumberBookmarksAvoiding([...map.values()].flatMap(findBookmarkIds));
37707
- const createContext = (key) => ({
37708
- file,
37709
- viewWrapper: { Relationships: { addRelationship: (id, type, target, targetMode) => {
38238
+ const renumberDrawings = renumberDrawingsAvoiding([...map.values()].flatMap(findDrawingIds));
38239
+ const viewWrappers = /* @__PURE__ */ new Map();
38240
+ const viewWrapperOf = (key) => {
38241
+ const existing = viewWrappers.get(key);
38242
+ if (existing) return existing;
38243
+ const viewWrapper = { Relationships: { addRelationship: (id, type, target, targetMode) => {
37710
38244
  relationshipAdditions.push({
37711
38245
  key,
37712
38246
  id,
@@ -37714,20 +38248,38 @@ var patchDocument = function() {
37714
38248
  target,
37715
38249
  targetMode
37716
38250
  });
37717
- } } },
38251
+ } } };
38252
+ viewWrappers.set(key, viewWrapper);
38253
+ return viewWrapper;
38254
+ };
38255
+ const createContext = (key) => ({
38256
+ file,
38257
+ viewWrapper: viewWrapperOf(key),
37718
38258
  stack: []
37719
38259
  });
38260
+ const addContentTypeOverride = (contentType, partName) => {
38261
+ contentTypeOverrides.push({
38262
+ contentType,
38263
+ partName
38264
+ });
38265
+ };
38266
+ const styles = patchStyles(map, createContext);
38267
+ const lists = patchNumbering(file.Numbering, map, {
38268
+ createContext,
38269
+ addContentTypeOverride
38270
+ });
37720
38271
  const notes = patchNotes({
37721
38272
  footnotes,
37722
38273
  endnotes
37723
38274
  }, map, {
37724
38275
  createContext,
37725
- addContentTypeOverride: (contentType, partName) => contentTypeOverrides.push({
37726
- contentType,
37727
- partName
37728
- }),
37729
- renumberBookmarks
38276
+ addContentTypeOverride,
38277
+ renumberBookmarks,
38278
+ renumberDrawings,
38279
+ renumberLists: lists.renumber,
38280
+ useStyles: styles.use
37730
38281
  });
38282
+ const carryNote = (kind, reference, note, context) => context.viewWrapper === viewWrapperOf("word/document.xml") ? notes.carry(kind, reference, note) : void 0;
37731
38283
  patchDrawings({
37732
38284
  parts: map,
37733
38285
  binaryParts: binaryContentMap,
@@ -37754,7 +38306,8 @@ var patchDocument = function() {
37754
38306
  start,
37755
38307
  end
37756
38308
  },
37757
- patchPlaceholder
38309
+ patchPlaceholder,
38310
+ renumberDrawings
37758
38311
  });
37759
38312
  return;
37760
38313
  }
@@ -37763,12 +38316,13 @@ var patchDocument = function() {
37763
38316
  json: element,
37764
38317
  patch: _objectSpread2(_objectSpread2({}, patchValue), {}, { children: patchValue.children.flatMap((child) => child instanceof Bookmark ? child.writtenAs : [child]).map((child) => {
37765
38318
  if (child instanceof ExternalHyperlink) {
37766
- const concreteHyperlink = new ConcreteHyperlink(child.options.children, uniqueId());
38319
+ const { target, anchor } = externalHyperlinkTarget(child.options.link);
38320
+ const concreteHyperlink = new ConcreteHyperlink(child.options.children, uniqueId(), anchor, child.options.link);
37767
38321
  hyperlinkRelationships.push({
37768
38322
  key,
37769
38323
  id: concreteHyperlink.linkId,
37770
38324
  type: "http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink",
37771
- target: child.options.link,
38325
+ target,
37772
38326
  targetMode: TargetModeType.EXTERNAL
37773
38327
  });
37774
38328
  return concreteHyperlink;
@@ -37778,13 +38332,15 @@ var patchDocument = function() {
37778
38332
  context,
37779
38333
  keepOriginalStyles,
37780
38334
  recursive,
37781
- renumberIds: (elements) => notes.renumber(renumberBookmarks(elements))
38335
+ renumberIds: (elements) => styles.use(lists.renumber(notes.renumber(renumberBookmarks(renumberDrawings(elements)))))
37782
38336
  });
37783
38337
  if (didFindOccurrence) relationshipAdditions.push(...hyperlinkRelationships);
37784
38338
  };
37785
38339
  for (const [patchKey, patchValue] of patchesInOrder) patchPlaceholder(json, patchKey, patchValue);
37786
38340
  }
37787
38341
  notes.write();
38342
+ lists.write();
38343
+ styles.write();
37788
38344
  for (const [key, json] of map) {
37789
38345
  if (!key.startsWith("word/") || key.endsWith(".xml.rels")) continue;
37790
38346
  const mediaDatas = imageReplacer.getMediaData(JSON.stringify(json), file.Media);