oasis-editor 0.0.100 → 0.0.102

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.
@@ -1,7 +1,7 @@
1
1
  var __defProp = Object.defineProperty;
2
2
  var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
3
3
  var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
4
- import { v as visitRun, a as assertNever, c as createSignal, b as createEditorStateFromDocument, d as createInitialEditorState, S as STANDARD_FONT_SIZES_PT, f as fontSizePxToPt, p as probeLocalFontFamilies, e as createEditorParagraphFromRuns, i as isInlineObjectRun, g as createEditorStyledRun, h as getParagraphLength, j as getParagraphText, k as getActiveZone, l as getDocumentSections, m as getActiveSectionIndex, n as getParagraphs, o as normalizeSelection, q as positionToParagraphOffset, r as paragraphOffsetToPosition, s as clampPosition, t as findParagraphIndex, u as createCollapsedSelection, w as isSelectionCollapsed, x as parseFontSizePtToPx, y as formatFontSizePt, z as createEditorParagraph, A as getBlockParagraphs, B as findParagraphTableLocation, C as buildTableCellLayout, P as PT_PER_PX, D as createEditorTableCell, E as createEditorTableRow, F as createEditorTable, G as underlineStyleToCssDecorationStyle, H as resolveImageSrc, I as listKindForTag, J as isParagraphTag, K as collectInlineRuns, L as parseParagraphStyle, M as getRunImage, N as InlineShell, O as BalloonShell, Q as DocumentShell, R as createMemo, T as buildCanvasLayoutSnapshot, U as getCaretRectFromSnapshot, V as getParagraphRectFromSnapshot, W as createComponent, X as CaretOverlay, Y as Show, Z as createRenderEffect, _ as style, $ as setAttribute, a0 as setStyleProperty, a1 as memo, a2 as template, a3 as useI18n, a4 as createEffect, a5 as insert, a6 as use, a7 as addEventListener, a8 as Dialog, a9 as delegateEvents, aa as className, ab as For, ac as UNDERLINE_STYLE_OPTIONS, ad as Tabs, ae as onMount, af as onCleanup, ag as PluginUiHost, ah as OasisEditorEditor, ai as OasisBrandMark, aj as setPreciseFontPreference, ak as setWelcomeSeen, al as enablePreciseFontMode, am as TWIPS_PER_POINT, an as PX_PER_INCH, ao as TWIPS_PER_INCH, ap as resolveEffectiveParagraphStyle, aq as resolveEffectiveTextStyleForParagraph, ar as EMU_PER_PX, as as EMU_PER_PT, at as getRunFootnoteReference, au as getRunEndnoteReference, av as iterateFootnoteReferenceRuns, aw as iterateEndnoteReferenceRuns, ax as imageContentTypeDefaults, ay as getRunFieldChar, az as getRunFieldInstruction, aA as createEditorRun, aB as JSZip, aC as imageExtensionFromMime, aD as pxToPt$1, aE as resolveFloatingObjectRect, aF as getTextBoxFloatingGeometry, aG as getPresetPathSegments, aH as projectBlocksLayout, aI as buildListLabels, aJ as getImageFloatingGeometry, aK as textStyleToFontSizePt, aL as PX_PER_POINT, aM as resolveOpenTypeFeatureTags, aN as DEFAULT_FONT_SIZE_PX, aO as isDoubleUnderlineStyle, aP as isWavyUnderlineStyle, aQ as underlineStyleLineWidthPx, aR as underlineStyleDashArray, aS as resolveListLabel, aT as getListLabelInset, aU as getAlignedListLabelInset, aV as getParagraphBorderInsets, aW as buildSegmentTable, aX as buildCanvasTableLayout, aY as resolveCanvasTableWidth, aZ as resolveFloatingTableRect, a_ as normalizeFamily, a$ as ROBOTO_FONT_FILES, b0 as loadFontAsset, b1 as OFFICE_COMPAT_FONT_FAMILIES, b2 as BinaryReader, b3 as buildSfnt, b4 as defaultFontDecoderRegistry, b5 as SfntFontProgram, b6 as collectPdfFontFamilies, b7 as projectDocumentLayout, b8 as getPageContentWidth, b9 as getPageHeaderZoneTop, ba as getPageBodyTop, bb as getPageColumnRects, bc as findFootnoteReference, bd as FOOTNOTE_MARKER_GUTTER_PX, be as resolveImporterForFile, bf as getDocumentSectionsCanonical, bg as getDocumentParagraphsCanonical, bh as getDocumentParagraphs, bi as getDocumentPageSettings, bj as getTableCellContentWidthForParagraph, bk as on, bl as debounce, bm as unwrap, bn as perfTimer, bo as getRunTextBox, bp as createEditorDocument, bq as resolveResizedDimensions, br as resolveTextBoxRenderHeight, bs as getToolbarStyleState, bt as getCachedCanvasImage, bu as measureParagraphMinContentWidthPx, bv as getEditableBlocksForZone, bw as findParagraphLocation, bx as createSectionBoundaryParagraph, by as normalizePageSettings, bz as DEFAULT_EDITOR_PAGE_SETTINGS, bA as markStart, bB as markEnd, bC as getParagraphEntries, bD as getParagraphById, bE as createEditorFootnote, bF as createFootnoteReferenceRun, bG as renumberFootnotes, bH as getFootnoteDisplayMarker, bI as getHeadingLevel, bJ as preciseFontModeVersion, bK as isPreciseFontModeEnabled, bL as resolveNamedTextStyle, bM as togglePreciseFontMode, bN as nextFontSizePt, bO as previousFontSizePt, bP as fontSizePtToPx, bQ as createDefaultToolbarPreset, bR as MenuRegistry, bS as createToolbarRegistry, bT as Editor, bU as resolveCommandRef, bV as commandRefName, bW as createOasisEditorClient, bX as createEditorZoom, bY as startLongTaskObserver, bZ as installGlobalReport, b_ as applyStoredPreciseFontPreference, b$ as getWelcomeSeen, c0 as isLocalFontAccessSupported, c1 as EDITOR_SCROLL_PADDING_PX, c2 as Toolbar, c3 as OasisEditorLoading, c4 as I18nProvider, c5 as createTranslator, c6 as createEditorLogger, c7 as registerDomStatsSurface } from "./index-BuxYvaSC.js";
4
+ import { v as visitRun, a as assertNever, c as createSignal, b as createEditorStateFromDocument, d as createInitialEditorState, S as STANDARD_FONT_SIZES_PT, f as fontSizePxToPt, p as probeLocalFontFamilies, e as createEditorParagraphFromRuns, i as isInlineObjectRun, g as createEditorStyledRun, h as getParagraphLength, j as getParagraphText, k as getActiveZone, l as getDocumentSections, m as getActiveSectionIndex, n as getParagraphs, o as normalizeSelection, q as positionToParagraphOffset, r as paragraphOffsetToPosition, s as clampPosition, t as findParagraphIndex, u as createCollapsedSelection, w as isSelectionCollapsed, x as parseFontSizePtToPx, y as formatFontSizePt, z as createEditorParagraph, A as getBlockParagraphs, B as findParagraphTableLocation, C as buildTableCellLayout, P as PT_PER_PX, D as createEditorTableCell, E as createEditorTableRow, F as createEditorTable, G as underlineStyleToCssDecorationStyle, H as resolveImageSrc, I as listKindForTag, J as isParagraphTag, K as collectInlineRuns, L as parseParagraphStyle, M as getRunImage, N as InlineShell, O as BalloonShell, Q as DocumentShell, R as createMemo, T as buildCanvasLayoutSnapshot, U as getCaretRectFromSnapshot, V as getParagraphRectFromSnapshot, W as createComponent, X as CaretOverlay, Y as Show, Z as createRenderEffect, _ as style, $ as setAttribute, a0 as setStyleProperty, a1 as memo, a2 as template, a3 as useI18n, a4 as createEffect, a5 as insert, a6 as use, a7 as addEventListener, a8 as Dialog, a9 as delegateEvents, aa as className, ab as For, ac as UNDERLINE_STYLE_OPTIONS, ad as Tabs, ae as onMount, af as onCleanup, ag as PluginUiHost, ah as OasisEditorEditor, ai as OasisBrandMark, aj as setPreciseFontPreference, ak as setWelcomeSeen, al as enablePreciseFontMode, am as TWIPS_PER_POINT, an as PX_PER_INCH, ao as TWIPS_PER_INCH, ap as resolveEffectiveParagraphStyle, aq as resolveEffectiveTextStyleForParagraph, ar as EMU_PER_PX, as as EMU_PER_PT, at as getRunFootnoteReference, au as getRunEndnoteReference, av as iterateFootnoteReferenceRuns, aw as iterateEndnoteReferenceRuns, ax as imageContentTypeDefaults, ay as getRunFieldChar, az as getRunFieldInstruction, aA as createEditorRun, aB as JSZip, aC as imageExtensionFromMime, aD as pxToPt$1, aE as resolveFloatingObjectRect, aF as getTextBoxFloatingGeometry, aG as getPresetPathSegments, aH as projectBlocksLayout, aI as buildListLabels, aJ as getImageFloatingGeometry, aK as textStyleToFontSizePt, aL as PX_PER_POINT, aM as resolveOpenTypeFeatureTags, aN as DEFAULT_FONT_SIZE_PX, aO as isDoubleUnderlineStyle, aP as isWavyUnderlineStyle, aQ as underlineStyleLineWidthPx, aR as underlineStyleDashArray, aS as resolveListLabel, aT as getListLabelInset, aU as getAlignedListLabelInset, aV as getParagraphBorderInsets, aW as buildSegmentTable, aX as buildCanvasTableLayout, aY as resolveCanvasTableWidth, aZ as resolveFloatingTableRect, a_ as normalizeFamily, a$ as ROBOTO_FONT_FILES, b0 as loadFontAsset, b1 as OFFICE_COMPAT_FONT_FAMILIES, b2 as BinaryReader, b3 as buildSfnt, b4 as defaultFontDecoderRegistry, b5 as SfntFontProgram, b6 as collectPdfFontFamilies, b7 as projectDocumentLayout, b8 as getPageContentWidth, b9 as getPageHeaderZoneTop, ba as getPageBodyTop, bb as getPageColumnRects, bc as findFootnoteReference, bd as FOOTNOTE_MARKER_GUTTER_PX, be as resolveImporterForFile, bf as getDocumentSectionsCanonical, bg as getDocumentParagraphsCanonical, bh as getDocumentParagraphs, bi as getDocumentPageSettings, bj as getTableCellContentWidthForParagraph, bk as on, bl as debounce, bm as unwrap, bn as perfTimer, bo as getRunTextBox, bp as createEditorDocument, bq as resolveResizedDimensions, br as resolveTextBoxRenderHeight, bs as getToolbarStyleState, bt as getCachedCanvasImage, bu as measureParagraphMinContentWidthPx, bv as getEditableBlocksForZone, bw as findParagraphLocation, bx as createSectionBoundaryParagraph, by as normalizePageSettings, bz as DEFAULT_EDITOR_PAGE_SETTINGS, bA as markStart, bB as markEnd, bC as getParagraphEntries, bD as getParagraphById, bE as createEditorFootnote, bF as createFootnoteReferenceRun, bG as renumberFootnotes, bH as getFootnoteDisplayMarker, bI as getHeadingLevel, bJ as preciseFontModeVersion, bK as isPreciseFontModeEnabled, bL as resolveNamedTextStyle, bM as togglePreciseFontMode, bN as nextFontSizePt, bO as previousFontSizePt, bP as fontSizePtToPx, bQ as createDefaultToolbarPreset, bR as MenuRegistry, bS as createToolbarRegistry, bT as Editor, bU as resolveCommandRef, bV as commandRefName, bW as createOasisEditorClient, bX as createEditorZoom, bY as startLongTaskObserver, bZ as installGlobalReport, b_ as applyStoredPreciseFontPreference, b$ as getWelcomeSeen, c0 as isLocalFontAccessSupported, c1 as EDITOR_SCROLL_PADDING_PX, c2 as Toolbar, c3 as OasisEditorLoading, c4 as I18nProvider, c5 as createTranslator, c6 as createEditorLogger, c7 as registerDomStatsSurface } from "./index-CNtAFUVS.js";
5
5
  function cloneStyle(style2) {
6
6
  return style2 ? { ...style2 } : void 0;
7
7
  }
@@ -34711,28 +34711,54 @@ function serializeRunsWithBoundaries(runs, tokens, context, paragraphStyleId, st
34711
34711
  flushUpTo(Number.POSITIVE_INFINITY);
34712
34712
  return out;
34713
34713
  }
34714
+ function serializeSingleBlockXml(block, context, styles) {
34715
+ var _a;
34716
+ switch (block.type) {
34717
+ case "paragraph":
34718
+ return serializeParagraphXml(block, context, styles);
34719
+ case "table": {
34720
+ const pageBreakXml = ((_a = block.style) == null ? void 0 : _a.pageBreakBefore) ? '<w:p><w:r><w:br w:type="page"/></w:r></w:p>' : "";
34721
+ return pageBreakXml + serializeTableXml(
34722
+ block,
34723
+ (paragraph, cell) => {
34724
+ var _a2;
34725
+ return serializeParagraphXml(paragraph, context, styles, {
34726
+ align: (_a2 = cell.style) == null ? void 0 : _a2.horizontalAlign
34727
+ });
34728
+ }
34729
+ );
34730
+ }
34731
+ default:
34732
+ return assertNever(block, "block");
34733
+ }
34734
+ }
34714
34735
  function serializeBlocksXml(blocks, context, styles) {
34715
- return blocks.map((block) => {
34716
- var _a;
34717
- switch (block.type) {
34718
- case "paragraph":
34719
- return serializeParagraphXml(block, context, styles);
34720
- case "table": {
34721
- const pageBreakXml = ((_a = block.style) == null ? void 0 : _a.pageBreakBefore) ? '<w:p><w:r><w:br w:type="page"/></w:r></w:p>' : "";
34722
- return pageBreakXml + serializeTableXml(
34723
- block,
34724
- (paragraph, cell) => {
34725
- var _a2;
34726
- return serializeParagraphXml(paragraph, context, styles, {
34727
- align: (_a2 = cell.style) == null ? void 0 : _a2.horizontalAlign
34728
- });
34729
- }
34730
- );
34731
- }
34732
- default:
34733
- return assertNever(block, "block");
34736
+ var _a, _b, _c;
34737
+ let out = "";
34738
+ let i = 0;
34739
+ while (i < blocks.length) {
34740
+ const block = blocks[i];
34741
+ const wrapper = (_a = block.sdtWrappers) == null ? void 0 : _a[0];
34742
+ if (!wrapper) {
34743
+ out += serializeSingleBlockXml(block, context, styles);
34744
+ i += 1;
34745
+ continue;
34734
34746
  }
34735
- }).join("");
34747
+ const group = [];
34748
+ let j = i;
34749
+ while (j < blocks.length && ((_c = (_b = blocks[j].sdtWrappers) == null ? void 0 : _b[0]) == null ? void 0 : _c.groupId) === wrapper.groupId) {
34750
+ const rest = blocks[j].sdtWrappers.slice(1);
34751
+ group.push({
34752
+ ...blocks[j],
34753
+ sdtWrappers: rest.length > 0 ? rest : void 0
34754
+ });
34755
+ j += 1;
34756
+ }
34757
+ const inner = serializeBlocksXml(group, context, styles);
34758
+ out += `<w:sdt>${wrapper.sdtPrXml}${wrapper.sdtEndPrXml ?? ""}<w:sdtContent>${inner}</w:sdtContent></w:sdt>`;
34759
+ i = j;
34760
+ }
34761
+ return out;
34736
34762
  }
34737
34763
  function serializeParagraphXml(paragraph, context, styles, overrides) {
34738
34764
  var _a, _b, _c;
@@ -35123,19 +35149,19 @@ function buildStylesXml(styles) {
35123
35149
  const styleElements = Object.values(styles).map(serializeNamedStyle).join("");
35124
35150
  return `<?xml version="1.0" encoding="UTF-8" standalone="yes"?><w:styles xmlns:w="${WORD_NS}" xmlns:w14="${WORD14_NS}">${styleElements}</w:styles>`;
35125
35151
  }
35126
- function buildContentTypesXml(hasNumbering, imageExtensions, hasSettings, parts, hasFootnotes, hasEndnotes, hasStyles, hasComments) {
35152
+ function buildContentTypesXml(hasNumbering, imageExtensions, hasSettings, parts, hasFootnotes, hasEndnotes, hasStyles, hasComments, hasFontTable) {
35127
35153
  const overrides = parts.map((part) => {
35128
35154
  const contentType = part.kind === "header" ? "application/vnd.openxmlformats-officedocument.wordprocessingml.header+xml" : "application/vnd.openxmlformats-officedocument.wordprocessingml.footer+xml";
35129
35155
  return `<Override PartName="/word/${part.path}" ContentType="${contentType}"/>`;
35130
35156
  }).join("");
35131
35157
  return `<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Types xmlns="http://schemas.openxmlformats.org/package/2006/content-types"><Default Extension="rels" ContentType="application/vnd.openxmlformats-package.relationships+xml"/><Default Extension="xml" ContentType="application/xml"/>${imageContentTypeDefaults(
35132
35158
  imageExtensions
35133
- )}<Override PartName="/word/document.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml"/>${hasStyles ? '<Override PartName="/word/styles.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml"/>' : ""}${hasNumbering ? '<Override PartName="/word/numbering.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.numbering+xml"/>' : ""}${hasSettings ? '<Override PartName="/word/settings.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml"/>' : ""}${hasFootnotes ? '<Override PartName="/word/footnotes.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.footnotes+xml"/>' : ""}${hasEndnotes ? '<Override PartName="/word/endnotes.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.endnotes+xml"/>' : ""}${hasComments ? '<Override PartName="/word/comments.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.comments+xml"/><Override PartName="/word/commentsExtended.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.commentsExtended+xml"/>' : ""}${overrides}</Types>`;
35159
+ )}<Override PartName="/word/document.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml"/>${hasStyles ? '<Override PartName="/word/styles.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml"/>' : ""}${hasNumbering ? '<Override PartName="/word/numbering.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.numbering+xml"/>' : ""}${hasSettings ? '<Override PartName="/word/settings.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml"/>' : ""}${hasFootnotes ? '<Override PartName="/word/footnotes.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.footnotes+xml"/>' : ""}${hasEndnotes ? '<Override PartName="/word/endnotes.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.endnotes+xml"/>' : ""}${hasComments ? '<Override PartName="/word/comments.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.comments+xml"/><Override PartName="/word/commentsExtended.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.commentsExtended+xml"/>' : ""}${hasFontTable ? '<Override PartName="/word/fontTable.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.fontTable+xml"/>' : ""}${overrides}</Types>`;
35134
35160
  }
35135
35161
  function buildRootRelationshipsXml() {
35136
35162
  return `<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Relationships xmlns="${PACKAGE_REL_NS}"><Relationship Id="rId1" Type="${OFFICE_REL_NS}/officeDocument" Target="word/document.xml"/></Relationships>`;
35137
35163
  }
35138
- function buildDocumentRelationshipsXml(hasNumbering, hasSettings, images, hyperlinks, parts, hasFootnotes, hasEndnotes, hasStyles, hasComments) {
35164
+ function buildDocumentRelationshipsXml(hasNumbering, hasSettings, images, hyperlinks, parts, hasFootnotes, hasEndnotes, hasStyles, hasComments, hasFontTable) {
35139
35165
  let rels = "";
35140
35166
  if (hasStyles)
35141
35167
  rels += `<Relationship Id="rIdStyles" Type="${OFFICE_REL_NS}/styles" Target="styles.xml"/>`;
@@ -35164,8 +35190,32 @@ function buildDocumentRelationshipsXml(hasNumbering, hasSettings, images, hyperl
35164
35190
  rels += `<Relationship Id="rIdComments" Type="${OFFICE_REL_NS}/comments" Target="comments.xml"/>`;
35165
35191
  rels += `<Relationship Id="rIdCommentsExtended" Type="http://schemas.microsoft.com/office/2011/relationships/commentsExtended" Target="commentsExtended.xml"/>`;
35166
35192
  }
35193
+ if (hasFontTable) {
35194
+ rels += `<Relationship Id="rIdFontTable" Type="${OFFICE_REL_NS}/fontTable" Target="fontTable.xml"/>`;
35195
+ }
35167
35196
  return `<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Relationships xmlns="${PACKAGE_REL_NS}">${rels}</Relationships>`;
35168
35197
  }
35198
+ function buildFontTableXml(fonts) {
35199
+ const fontXml = fonts.map((font) => {
35200
+ const children = [];
35201
+ if (font.altName)
35202
+ children.push(`<w:altName w:val="${escapeXml(font.altName)}"/>`);
35203
+ if (font.panose1)
35204
+ children.push(`<w:panose1 w:val="${escapeXml(font.panose1)}"/>`);
35205
+ if (font.charset)
35206
+ children.push(`<w:charset w:val="${escapeXml(font.charset)}"/>`);
35207
+ if (font.family)
35208
+ children.push(`<w:family w:val="${escapeXml(font.family)}"/>`);
35209
+ if (font.pitch)
35210
+ children.push(`<w:pitch w:val="${escapeXml(font.pitch)}"/>`);
35211
+ if (font.sig) {
35212
+ const attrs = Object.entries(font.sig).map(([key, value]) => `w:${key}="${escapeXml(value)}"`).join(" ");
35213
+ if (attrs) children.push(`<w:sig ${attrs}/>`);
35214
+ }
35215
+ return `<w:font w:name="${escapeXml(font.name)}">${children.join("")}</w:font>`;
35216
+ }).join("");
35217
+ return `<?xml version="1.0" encoding="UTF-8" standalone="yes"?><w:fonts xmlns:w="${WORD_NS$1}">${fontXml}</w:fonts>`;
35218
+ }
35169
35219
  const NOTE_NUMBER_FORMATS = {
35170
35220
  decimal: "decimal",
35171
35221
  lowerRoman: "lowerRoman",
@@ -35661,7 +35711,7 @@ function buildPartContext(blocks, numberingContext, state, document2) {
35661
35711
  };
35662
35712
  }
35663
35713
  async function exportEditorDocumentToDocx(document2) {
35664
- var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p;
35714
+ var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q;
35665
35715
  document2 = renumberImageCaptionsInDocument(document2);
35666
35716
  const zip = new JSZip();
35667
35717
  const numberingContext = buildNumberingContext(document2);
@@ -35780,6 +35830,7 @@ async function exportEditorDocumentToDocx(document2) {
35780
35830
  return (_a2 = img.target.split(".").pop()) == null ? void 0 : _a2.toLowerCase();
35781
35831
  }).filter((ext) => Boolean(ext));
35782
35832
  const hasStyles = document2.styles != null && Object.keys(document2.styles).length > 0;
35833
+ const hasFontTable = (((_i = document2.fontTable) == null ? void 0 : _i.length) ?? 0) > 0;
35783
35834
  zip.file(
35784
35835
  "[Content_Types].xml",
35785
35836
  buildContentTypesXml(
@@ -35790,7 +35841,8 @@ async function exportEditorDocumentToDocx(document2) {
35790
35841
  hasFootnotes,
35791
35842
  hasEndnotes,
35792
35843
  hasStyles,
35793
- hasComments
35844
+ hasComments,
35845
+ hasFontTable
35794
35846
  )
35795
35847
  );
35796
35848
  zip.file("_rels/.rels", buildRootRelationshipsXml());
@@ -35807,7 +35859,7 @@ async function exportEditorDocumentToDocx(document2) {
35807
35859
  buildNumberingXml(numberingContext.definitions)
35808
35860
  );
35809
35861
  }
35810
- if (hasStyles || hasNumbering || hasDocumentSettings || bodyContext.images.length > 0 || bodyContext.hyperlinks.length > 0 || parts.length > 0 || hasFootnotes || hasEndnotes || hasComments) {
35862
+ if (hasStyles || hasNumbering || hasDocumentSettings || bodyContext.images.length > 0 || bodyContext.hyperlinks.length > 0 || parts.length > 0 || hasFootnotes || hasEndnotes || hasComments || hasFontTable) {
35811
35863
  zip.file(
35812
35864
  "word/_rels/document.xml.rels",
35813
35865
  buildDocumentRelationshipsXml(
@@ -35819,24 +35871,28 @@ async function exportEditorDocumentToDocx(document2) {
35819
35871
  hasFootnotes,
35820
35872
  hasEndnotes,
35821
35873
  hasStyles,
35822
- hasComments
35874
+ hasComments,
35875
+ hasFontTable
35823
35876
  )
35824
35877
  );
35825
35878
  }
35879
+ if (hasFontTable) {
35880
+ zip.file("word/fontTable.xml", buildFontTableXml(document2.fontTable));
35881
+ }
35826
35882
  if (hasDocumentSettings) {
35827
35883
  zip.file(
35828
35884
  "word/settings.xml",
35829
35885
  buildSettingsXml(
35830
35886
  hasEvenAndOddHeaders,
35831
- (_i = document2.settings) == null ? void 0 : _i.defaultTabStop,
35832
- (_j = document2.footnotes) == null ? void 0 : _j.settings,
35833
- (_k = document2.endnotes) == null ? void 0 : _k.settings,
35834
- (_l = document2.settings) == null ? void 0 : _l.allowSpaceOfSameStyleInTable,
35887
+ (_j = document2.settings) == null ? void 0 : _j.defaultTabStop,
35888
+ (_k = document2.footnotes) == null ? void 0 : _k.settings,
35889
+ (_l = document2.endnotes) == null ? void 0 : _l.settings,
35890
+ (_m = document2.settings) == null ? void 0 : _m.allowSpaceOfSameStyleInTable,
35835
35891
  {
35836
- autoHyphenation: (_m = document2.settings) == null ? void 0 : _m.autoHyphenation,
35837
- consecutiveHyphenLimit: (_n = document2.settings) == null ? void 0 : _n.consecutiveHyphenLimit,
35838
- hyphenationZone: (_o = document2.settings) == null ? void 0 : _o.hyphenationZone,
35839
- doNotHyphenateCaps: (_p = document2.settings) == null ? void 0 : _p.doNotHyphenateCaps
35892
+ autoHyphenation: (_n = document2.settings) == null ? void 0 : _n.autoHyphenation,
35893
+ consecutiveHyphenLimit: (_o = document2.settings) == null ? void 0 : _o.consecutiveHyphenLimit,
35894
+ hyphenationZone: (_p = document2.settings) == null ? void 0 : _p.hyphenationZone,
35895
+ doNotHyphenateCaps: (_q = document2.settings) == null ? void 0 : _q.doNotHyphenateCaps
35840
35896
  }
35841
35897
  )
35842
35898
  );
@@ -36356,6 +36412,39 @@ function drawFragmentShading(writer, pageIndex, line, fragment, originX, originY
36356
36412
  fill: styles.shading
36357
36413
  });
36358
36414
  }
36415
+ function resolveGradientShadingName(writer, pageIndex, line, fragment, originX, originY, styles) {
36416
+ const fill = styles.textFill;
36417
+ if (!fill || fill.type !== "gradient" || fill.stops.length < 2) {
36418
+ return void 0;
36419
+ }
36420
+ const bounds = resolveFragmentBounds(
36421
+ line,
36422
+ fragment,
36423
+ styles.fontSize ?? DEFAULT_FONT_SIZE_PX
36424
+ );
36425
+ if (!bounds) {
36426
+ return void 0;
36427
+ }
36428
+ const x0px = originX + bounds.left;
36429
+ const x1px = originX + bounds.right;
36430
+ const y0px = originY + line.top;
36431
+ const y1px = originY + line.top + line.height;
36432
+ const cx = (x0px + x1px) / 2;
36433
+ const cy = (y0px + y1px) / 2;
36434
+ const rad = (fill.angle ?? 0) * Math.PI / 180;
36435
+ const dx = Math.cos(rad) * (x1px - x0px) / 2;
36436
+ const dy = Math.sin(rad) * (y1px - y0px) / 2;
36437
+ return writer.registerAxialGradient(pageIndex, {
36438
+ x0: pxToPt$1(cx - dx),
36439
+ y0: pxToPt$1(cy - dy),
36440
+ x1: pxToPt$1(cx + dx),
36441
+ y1: pxToPt$1(cy + dy),
36442
+ stops: fill.stops.map((stop) => ({
36443
+ offset: stop.position,
36444
+ color: stop.color
36445
+ }))
36446
+ }) ?? void 0;
36447
+ }
36359
36448
  function drawFragmentBorder(writer, pageIndex, line, fragment, originX, originY, styles) {
36360
36449
  const border = styles.textBorder;
36361
36450
  if (!border || border.type === "none" || border.width <= 0) {
@@ -36728,6 +36817,15 @@ async function drawFragmentText(writer, pageIndex, paragraph, line, fragment, do
36728
36817
  fontFeatures
36729
36818
  };
36730
36819
  const mainColor = ((_b = styles.textFill) == null ? void 0 : _b.type) === "solid" ? styles.textFill.color : ((_c = styles.textFill) == null ? void 0 : _c.type) === "gradient" && styles.textFill.stops[0] ? styles.textFill.stops[0].color : styles.color ?? "#000000";
36820
+ const gradientShadingName = resolveGradientShadingName(
36821
+ writer,
36822
+ pageIndex,
36823
+ line,
36824
+ fragment,
36825
+ originX,
36826
+ originY,
36827
+ styles
36828
+ );
36731
36829
  const offsetPt = pxToPt$1(1);
36732
36830
  const emitChunk = (leftPx, text2) => {
36733
36831
  if (styles.emboss || styles.imprint) {
@@ -36803,7 +36901,9 @@ async function drawFragmentText(writer, pageIndex, paragraph, line, fragment, do
36803
36901
  y: pxToPt$1(baselineY),
36804
36902
  text: text2,
36805
36903
  color: mainColor,
36806
- ...textOutline ? {
36904
+ // A gradient fill paints the glyphs via the shading clip; it supersedes
36905
+ // both the solid color and any outline/stroke render mode.
36906
+ ...gradientShadingName ? { gradientShadingName } : textOutline ? {
36807
36907
  renderMode: 2,
36808
36908
  strokeColor: textOutline.color ?? mainColor,
36809
36909
  strokeWidth: textOutline.widthPt
@@ -37634,10 +37734,27 @@ function textMarkerComment(value) {
37634
37734
  return `% OasisText ${encodePdfUtf16Hex(codePoints)}`;
37635
37735
  }
37636
37736
  class PdfContentStream {
37637
- constructor(page, fonts, images) {
37737
+ constructor(page, fonts, images, shadings) {
37638
37738
  this.page = page;
37639
37739
  this.fonts = fonts;
37640
37740
  this.images = images;
37741
+ this.shadings = shadings;
37742
+ }
37743
+ /**
37744
+ * Registers an axial gradient for use as a glyph fill on this page. Coordinates
37745
+ * come in the writer's top-left point space and are flipped to PDF bottom-left
37746
+ * space here; the returned name is referenced via `OasisPdfTextOptions`.
37747
+ */
37748
+ registerAxialGradient(gradient) {
37749
+ const name = this.shadings.register({
37750
+ x0: gradient.x0,
37751
+ y0: this.page.height - gradient.y0,
37752
+ x1: gradient.x1,
37753
+ y1: this.page.height - gradient.y1,
37754
+ stops: gradient.stops
37755
+ });
37756
+ this.page.shadingResourceNames.add(name);
37757
+ return name;
37641
37758
  }
37642
37759
  drawRect(options) {
37643
37760
  const page = this.page;
@@ -37795,8 +37912,24 @@ class PdfContentStream {
37795
37912
  if (showCommand === null) {
37796
37913
  return;
37797
37914
  }
37915
+ if (options.gradientShadingName) {
37916
+ this.emitGradientTextBlock(
37917
+ fontResourceName,
37918
+ showCommand,
37919
+ options,
37920
+ options.gradientShadingName
37921
+ );
37922
+ return;
37923
+ }
37798
37924
  this.emitTextBlock(fontResourceName, showCommand, options);
37799
37925
  }
37926
+ textSetupCommands(fontResourceName, options) {
37927
+ return [
37928
+ `/${fontResourceName} ${formatNumber(options.fontSize ?? 12)} Tf`,
37929
+ ...options.horizontalScale && options.horizontalScale > 0 && options.horizontalScale !== 100 ? [`${formatNumber(options.horizontalScale)} Tz`] : [],
37930
+ ...options.characterSpacing && options.characterSpacing !== 0 ? [`${formatNumber(options.characterSpacing)} Tc`] : []
37931
+ ];
37932
+ }
37800
37933
  emitTextBlock(fontResourceName, showCommand, options) {
37801
37934
  const page = this.page;
37802
37935
  page.commands.push(
@@ -37804,7 +37937,6 @@ class PdfContentStream {
37804
37937
  textMarkerComment(options.text),
37805
37938
  "BT",
37806
37939
  colorCommand(options.color, "rg", [0, 0, 0]),
37807
- `/${fontResourceName} ${formatNumber(options.fontSize ?? 12)} Tf`,
37808
37940
  ...options.renderMode && options.renderMode !== 0 ? [
37809
37941
  colorCommand(
37810
37942
  options.strokeColor ?? options.color,
@@ -37816,14 +37948,37 @@ class PdfContentStream {
37816
37948
  )} w`,
37817
37949
  `${options.renderMode} Tr`
37818
37950
  ] : [],
37819
- ...options.horizontalScale && options.horizontalScale > 0 && options.horizontalScale !== 100 ? [`${formatNumber(options.horizontalScale)} Tz`] : [],
37820
- ...options.characterSpacing && options.characterSpacing !== 0 ? [`${formatNumber(options.characterSpacing)} Tc`] : [],
37951
+ ...this.textSetupCommands(fontResourceName, options),
37821
37952
  `${formatNumber(options.x)} ${formatNumber(page.height - options.y)} Td`,
37822
37953
  showCommand,
37823
37954
  "ET"
37824
37955
  ].join("\n")
37825
37956
  );
37826
37957
  }
37958
+ /**
37959
+ * Fills glyphs with an axial gradient: the text is drawn in clip render mode
37960
+ * (`7 Tr`) so the glyph outlines become the clip path, then the shading is
37961
+ * painted through them with `sh`. The whole sequence is isolated in a
37962
+ * `q … Q` pair so the clip does not leak. Outline/stroke is not combined with
37963
+ * gradient fill (the gradient supersedes it).
37964
+ */
37965
+ emitGradientTextBlock(fontResourceName, showCommand, options, shadingName) {
37966
+ const page = this.page;
37967
+ page.commands.push(
37968
+ [
37969
+ textMarkerComment(options.text),
37970
+ "q",
37971
+ "BT",
37972
+ ...this.textSetupCommands(fontResourceName, options),
37973
+ "7 Tr",
37974
+ `${formatNumber(options.x)} ${formatNumber(page.height - options.y)} Td`,
37975
+ showCommand,
37976
+ "ET",
37977
+ `/${shadingName} sh`,
37978
+ "Q"
37979
+ ].join("\n")
37980
+ );
37981
+ }
37827
37982
  drawImage(options) {
37828
37983
  const page = this.page;
37829
37984
  if (options.width <= 0 || options.height <= 0 || !this.images.has(options.resourceName)) {
@@ -39232,7 +39387,97 @@ class PdfImageTable {
39232
39387
  );
39233
39388
  }
39234
39389
  }
39235
- function serializePdfDocument(pages, fonts, images) {
39390
+ class PdfShadingTable {
39391
+ constructor() {
39392
+ __publicField(this, "shadings", []);
39393
+ }
39394
+ /** Registers a gradient (PDF space) and returns its `/Shading` resource name. */
39395
+ register(spec) {
39396
+ const name = `Sh${this.shadings.length + 1}`;
39397
+ this.shadings.push({ name, spec });
39398
+ return name;
39399
+ }
39400
+ /** Emits each gradient's Function + Shading objects, keyed by resource name. */
39401
+ buildShadingObjects(addObject) {
39402
+ const ids = /* @__PURE__ */ new Map();
39403
+ for (const { name, spec } of this.shadings) {
39404
+ ids.set(name, this.addShadingObject(spec, addObject));
39405
+ }
39406
+ return ids;
39407
+ }
39408
+ addShadingObject(spec, addObject) {
39409
+ const stops = normalizeStops(spec.stops);
39410
+ const functionObjectId = addObject(buildFunctionObject(stops));
39411
+ return addObject(
39412
+ [
39413
+ "<< /ShadingType 2",
39414
+ "/ColorSpace /DeviceRGB",
39415
+ `/Coords [${[spec.x0, spec.y0, spec.x1, spec.y1].map(formatNumber).join(" ")}]`,
39416
+ "/Domain [0 1]",
39417
+ `/Function ${functionObjectId} 0 R`,
39418
+ "/Extend [true true]",
39419
+ ">>"
39420
+ ].join("\n")
39421
+ );
39422
+ }
39423
+ }
39424
+ function normalizeStops(stops) {
39425
+ const resolved = stops.map((stop) => ({
39426
+ offset: Math.min(1, Math.max(0, stop.offset)),
39427
+ rgb: colorToRgb(stop.color, [0, 0, 0])
39428
+ })).sort((a, b) => a.offset - b.offset);
39429
+ if (resolved.length === 0) {
39430
+ return [
39431
+ { offset: 0, rgb: [0, 0, 0] },
39432
+ { offset: 1, rgb: [0, 0, 0] }
39433
+ ];
39434
+ }
39435
+ if (resolved.length === 1) {
39436
+ return [
39437
+ { offset: 0, rgb: resolved[0].rgb },
39438
+ { offset: 1, rgb: resolved[0].rgb }
39439
+ ];
39440
+ }
39441
+ resolved[0].offset = 0;
39442
+ resolved[resolved.length - 1].offset = 1;
39443
+ for (let i = 1; i < resolved.length - 1; i += 1) {
39444
+ const min = resolved[i - 1].offset + 1e-4;
39445
+ if (resolved[i].offset <= min) {
39446
+ resolved[i].offset = Math.min(1 - 1e-4, min);
39447
+ }
39448
+ }
39449
+ return resolved;
39450
+ }
39451
+ function exponentialFunction(c0, c1) {
39452
+ return [
39453
+ "<< /FunctionType 2",
39454
+ "/Domain [0 1]",
39455
+ `/C0 [${c0.map(formatNumber).join(" ")}]`,
39456
+ `/C1 [${c1.map(formatNumber).join(" ")}]`,
39457
+ "/N 1",
39458
+ ">>"
39459
+ ].join("\n");
39460
+ }
39461
+ function buildFunctionObject(stops) {
39462
+ if (stops.length === 2) {
39463
+ return exponentialFunction(stops[0].rgb, stops[1].rgb);
39464
+ }
39465
+ const subFunctions = [];
39466
+ for (let i = 0; i < stops.length - 1; i += 1) {
39467
+ subFunctions.push(exponentialFunction(stops[i].rgb, stops[i + 1].rgb));
39468
+ }
39469
+ const bounds = stops.slice(1, -1).map((stop) => formatNumber(stop.offset));
39470
+ const encode = stops.slice(0, -1).map(() => "0 1").join(" ");
39471
+ return [
39472
+ "<< /FunctionType 3",
39473
+ "/Domain [0 1]",
39474
+ `/Functions [${subFunctions.join(" ")}]`,
39475
+ `/Bounds [${bounds.join(" ")}]`,
39476
+ `/Encode [${encode}]`,
39477
+ ">>"
39478
+ ].join("\n");
39479
+ }
39480
+ function serializePdfDocument(pages, fonts, images, shadings) {
39236
39481
  const objects = [];
39237
39482
  const addObject = (body2) => {
39238
39483
  const id = objects.length + 1;
@@ -39243,6 +39488,7 @@ function serializePdfDocument(pages, fonts, images) {
39243
39488
  const pagesObjectId = addObject("");
39244
39489
  const { resourceXml: fontResourceXml } = fonts.buildFontObjects(addObject);
39245
39490
  const imageObjectIds = images.buildImageObjects(addObject);
39491
+ const shadingObjectIds = shadings.buildShadingObjects(addObject);
39246
39492
  const pageObjectIds = [];
39247
39493
  for (const page of pages) {
39248
39494
  const stream = `${page.commands.join("\n")}
@@ -39257,12 +39503,17 @@ ${stream}endstream`
39257
39503
  return objectId ? `/${resourceName} ${objectId} 0 R` : "";
39258
39504
  }).filter(Boolean).join(" ");
39259
39505
  const xObjectResourceXml = imageResourceXml ? ` /XObject << ${imageResourceXml} >>` : "";
39506
+ const shadingResourceXml = Array.from(page.shadingResourceNames).map((resourceName) => {
39507
+ const objectId = shadingObjectIds.get(resourceName);
39508
+ return objectId ? `/${resourceName} ${objectId} 0 R` : "";
39509
+ }).filter(Boolean).join(" ");
39510
+ const shadingResourceDictXml = shadingResourceXml ? ` /Shading << ${shadingResourceXml} >>` : "";
39260
39511
  const pageObjectId = addObject(
39261
39512
  [
39262
39513
  "<< /Type /Page",
39263
39514
  `/Parent ${pagesObjectId} 0 R`,
39264
39515
  `/MediaBox [0 0 ${formatNumber(page.width)} ${formatNumber(page.height)}]`,
39265
- `/Resources << /Font << ${fontResourceXml} >>${xObjectResourceXml} >>`,
39516
+ `/Resources << /Font << ${fontResourceXml} >>${xObjectResourceXml}${shadingResourceDictXml} >>`,
39266
39517
  `/Contents ${contentObjectId} 0 R`,
39267
39518
  ">>"
39268
39519
  ].join("\n")
@@ -39310,6 +39561,7 @@ class OasisPdfWriter {
39310
39561
  __publicField(this, "streams", []);
39311
39562
  __publicField(this, "fonts");
39312
39563
  __publicField(this, "images", new PdfImageTable());
39564
+ __publicField(this, "shadings", new PdfShadingTable());
39313
39565
  this.fonts = new PdfFontTable(fontResources);
39314
39566
  }
39315
39567
  registerFontResource(resource) {
@@ -39320,10 +39572,13 @@ class OasisPdfWriter {
39320
39572
  width: Math.max(1, size.width),
39321
39573
  height: Math.max(1, size.height),
39322
39574
  commands: [],
39323
- imageResourceNames: /* @__PURE__ */ new Set()
39575
+ imageResourceNames: /* @__PURE__ */ new Set(),
39576
+ shadingResourceNames: /* @__PURE__ */ new Set()
39324
39577
  };
39325
39578
  this.pages.push(page);
39326
- this.streams.push(new PdfContentStream(page, this.fonts, this.images));
39579
+ this.streams.push(
39580
+ new PdfContentStream(page, this.fonts, this.images, this.shadings)
39581
+ );
39327
39582
  return this.pages.length - 1;
39328
39583
  }
39329
39584
  getPageCount() {
@@ -39361,6 +39616,15 @@ class OasisPdfWriter {
39361
39616
  var _a;
39362
39617
  (_a = this.streams[pageIndex]) == null ? void 0 : _a.drawText(options);
39363
39618
  }
39619
+ /**
39620
+ * Registers an axial (linear) gradient on a page for use as a glyph fill, and
39621
+ * returns its shading resource name to pass as `gradientShadingName` on a
39622
+ * subsequent `drawText`. Coordinates are in the writer's top-left point space.
39623
+ */
39624
+ registerAxialGradient(pageIndex, gradient) {
39625
+ var _a;
39626
+ return ((_a = this.streams[pageIndex]) == null ? void 0 : _a.registerAxialGradient(gradient)) ?? null;
39627
+ }
39364
39628
  registerImageResource(resource) {
39365
39629
  return this.images.registerImageResource(resource);
39366
39630
  }
@@ -39379,7 +39643,12 @@ class OasisPdfWriter {
39379
39643
  if (this.pages.length === 0) {
39380
39644
  this.addPage({ width: 612, height: 792 });
39381
39645
  }
39382
- return serializePdfDocument(this.pages, this.fonts, this.images);
39646
+ return serializePdfDocument(
39647
+ this.pages,
39648
+ this.fonts,
39649
+ this.images,
39650
+ this.shadings
39651
+ );
39383
39652
  }
39384
39653
  }
39385
39654
  const FOOTNOTE_BLOCK_GAP_PX = 2;