@harbour-enterprises/superdoc 1.3.0-next.4 → 1.3.0-next.6

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.
@@ -36366,7 +36366,7 @@ Please report this to https://github.com/markedjs/marked.`, e) {
36366
36366
  static getStoredSuperdocVersion(docx) {
36367
36367
  return SuperConverter.getStoredCustomProperty(docx, "SuperdocVersion");
36368
36368
  }
36369
- static setStoredSuperdocVersion(docx = this.convertedXml, version2 = "1.3.0-next.4") {
36369
+ static setStoredSuperdocVersion(docx = this.convertedXml, version2 = "1.3.0-next.6") {
36370
36370
  return SuperConverter.setStoredCustomProperty(docx, "SuperdocVersion", version2, false);
36371
36371
  }
36372
36372
  /**
@@ -62076,7 +62076,7 @@ Please report this to https://github.com/markedjs/marked.`, e) {
62076
62076
  return false;
62077
62077
  }
62078
62078
  };
62079
- const summaryVersion = "1.3.0-next.4";
62079
+ const summaryVersion = "1.3.0-next.6";
62080
62080
  const nodeKeys = ["group", "content", "marks", "inline", "atom", "defining", "code", "tableRole", "summary"];
62081
62081
  const markKeys = ["group", "inclusive", "excludes", "spanning", "code"];
62082
62082
  function mapAttributes(attrs) {
@@ -64710,7 +64710,7 @@ Please report this to https://github.com/markedjs/marked.`, e) {
64710
64710
  * Process collaboration migrations
64711
64711
  */
64712
64712
  processCollaborationMigrations() {
64713
- console.debug("[checkVersionMigrations] Current editor version", "1.3.0-next.4");
64713
+ console.debug("[checkVersionMigrations] Current editor version", "1.3.0-next.6");
64714
64714
  if (!this.options.ydoc) return;
64715
64715
  const metaMap = this.options.ydoc.getMap("meta");
64716
64716
  let docVersion = metaMap.get("version");
@@ -77585,8 +77585,7 @@ ${l}
77585
77585
  const titlePgEnabled = sectionTitlePg === true;
77586
77586
  const isFirstPageOfSection = sectionPageNumber === 1;
77587
77587
  if (isFirstPageOfSection && titlePgEnabled) {
77588
- if (hasFirst) return "first";
77589
- if (!hasDefault && !hasEven && !hasOdd) return null;
77588
+ if (hasFirst || hasDefault || hasEven || hasOdd) return "first";
77590
77589
  return null;
77591
77590
  }
77592
77591
  if (identifier.alternateHeaders) {
@@ -79643,6 +79642,45 @@ ${l}
79643
79642
  return height;
79644
79643
  };
79645
79644
  const headerContentHeights = options.headerContentHeights;
79645
+ const footerContentHeights = options.footerContentHeights;
79646
+ const headerContentHeightsByRId = options.headerContentHeightsByRId;
79647
+ const footerContentHeightsByRId = options.footerContentHeightsByRId;
79648
+ const getVariantTypeForPage = (sectionPageNumber, titlePgEnabled, alternateHeaders) => {
79649
+ if (sectionPageNumber === 1 && titlePgEnabled) {
79650
+ return "first";
79651
+ }
79652
+ return "default";
79653
+ };
79654
+ const getHeaderHeightForPage = (variantType, headerRef) => {
79655
+ if (headerRef && headerContentHeightsByRId?.has(headerRef)) {
79656
+ return validateContentHeight(headerContentHeightsByRId.get(headerRef));
79657
+ }
79658
+ if (headerContentHeights) {
79659
+ return validateContentHeight(headerContentHeights[variantType]);
79660
+ }
79661
+ return 0;
79662
+ };
79663
+ const getFooterHeightForPage = (variantType, footerRef) => {
79664
+ if (footerRef && footerContentHeightsByRId?.has(footerRef)) {
79665
+ return validateContentHeight(footerContentHeightsByRId.get(footerRef));
79666
+ }
79667
+ if (footerContentHeights) {
79668
+ return validateContentHeight(footerContentHeights[variantType]);
79669
+ }
79670
+ return 0;
79671
+ };
79672
+ const calculateEffectiveTopMargin = (headerContentHeight, currentHeaderDistance, baseTopMargin) => {
79673
+ if (headerContentHeight > 0) {
79674
+ return Math.max(baseTopMargin, currentHeaderDistance + headerContentHeight);
79675
+ }
79676
+ return baseTopMargin;
79677
+ };
79678
+ const calculateEffectiveBottomMargin = (footerContentHeight, currentFooterDistance, baseBottomMargin) => {
79679
+ if (footerContentHeight > 0) {
79680
+ return Math.max(baseBottomMargin, currentFooterDistance + footerContentHeight);
79681
+ }
79682
+ return baseBottomMargin;
79683
+ };
79646
79684
  const maxHeaderContentHeight = headerContentHeights ? Math.max(
79647
79685
  0,
79648
79686
  validateContentHeight(headerContentHeights.default),
@@ -79650,9 +79688,6 @@ ${l}
79650
79688
  validateContentHeight(headerContentHeights.even),
79651
79689
  validateContentHeight(headerContentHeights.odd)
79652
79690
  ) : 0;
79653
- const headerDistance = margins.header ?? margins.top;
79654
- const effectiveTopMargin = maxHeaderContentHeight > 0 ? Math.max(margins.top, headerDistance + maxHeaderContentHeight) : margins.top;
79655
- const footerContentHeights = options.footerContentHeights;
79656
79691
  const maxFooterContentHeight = footerContentHeights ? Math.max(
79657
79692
  0,
79658
79693
  validateContentHeight(footerContentHeights.default),
@@ -79660,8 +79695,12 @@ ${l}
79660
79695
  validateContentHeight(footerContentHeights.even),
79661
79696
  validateContentHeight(footerContentHeights.odd)
79662
79697
  ) : 0;
79698
+ const headerDistance = margins.header ?? margins.top;
79663
79699
  const footerDistance = margins.footer ?? margins.bottom;
79664
- const effectiveBottomMargin = maxFooterContentHeight > 0 ? Math.max(margins.bottom, footerDistance + maxFooterContentHeight) : margins.bottom;
79700
+ const defaultHeaderHeight = getHeaderHeightForPage("default", void 0);
79701
+ const defaultFooterHeight = getFooterHeightForPage("default", void 0);
79702
+ const effectiveTopMargin = calculateEffectiveTopMargin(defaultHeaderHeight, headerDistance, margins.top);
79703
+ const effectiveBottomMargin = calculateEffectiveBottomMargin(defaultFooterHeight, footerDistance, margins.bottom);
79665
79704
  let activeTopMargin = effectiveTopMargin;
79666
79705
  let activeBottomMargin = effectiveBottomMargin;
79667
79706
  let activeLeftMargin = margins.left;
@@ -79670,6 +79709,10 @@ ${l}
79670
79709
  let pendingBottomMargin = null;
79671
79710
  let pendingLeftMargin = null;
79672
79711
  let pendingRightMargin = null;
79712
+ let activeSectionBaseTopMargin = margins.top;
79713
+ let activeSectionBaseBottomMargin = margins.bottom;
79714
+ let pendingSectionBaseTopMargin = null;
79715
+ let pendingSectionBaseBottomMargin = null;
79673
79716
  let activeHeaderDistance = margins.header ?? margins.top;
79674
79717
  let pendingHeaderDistance = null;
79675
79718
  let activeFooterDistance = margins.footer ?? margins.bottom;
@@ -79875,6 +79918,7 @@ ${l}
79875
79918
  }
79876
79919
  let activeSectionIndex = initialSectionMetadata?.sectionIndex ?? 0;
79877
79920
  let pendingSectionIndex = null;
79921
+ const sectionFirstPageNumbers = /* @__PURE__ */ new Map();
79878
79922
  const paginator = createPaginator({
79879
79923
  margins: paginatorMargins,
79880
79924
  getActiveTopMargin: () => activeTopMargin,
@@ -79888,6 +79932,7 @@ ${l}
79888
79932
  createPage,
79889
79933
  onNewPage: (state) => {
79890
79934
  if (!state) {
79935
+ const isEnteringNewSection = pendingSectionIndex !== null;
79891
79936
  const applied = applyPendingToActive({
79892
79937
  activeTopMargin,
79893
79938
  activeBottomMargin,
@@ -79955,7 +80000,69 @@ ${l}
79955
80000
  activeVAlign = pendingVAlign;
79956
80001
  pendingVAlign = null;
79957
80002
  }
80003
+ if (pendingSectionBaseTopMargin !== null) {
80004
+ activeSectionBaseTopMargin = pendingSectionBaseTopMargin;
80005
+ pendingSectionBaseTopMargin = null;
80006
+ }
80007
+ if (pendingSectionBaseBottomMargin !== null) {
80008
+ activeSectionBaseBottomMargin = pendingSectionBaseBottomMargin;
80009
+ pendingSectionBaseBottomMargin = null;
80010
+ }
79958
80011
  pageCount += 1;
80012
+ const newPageNumber = pageCount;
80013
+ if (isEnteringNewSection || !sectionFirstPageNumbers.has(activeSectionIndex)) {
80014
+ sectionFirstPageNumbers.set(activeSectionIndex, newPageNumber);
80015
+ }
80016
+ const firstPageInSection = sectionFirstPageNumbers.get(activeSectionIndex) ?? newPageNumber;
80017
+ const sectionPageNumber = newPageNumber - firstPageInSection + 1;
80018
+ const sectionMetadata = sectionMetadataList[activeSectionIndex];
80019
+ const titlePgEnabled = sectionMetadata?.titlePg ?? false;
80020
+ const variantType = getVariantTypeForPage(sectionPageNumber, titlePgEnabled);
80021
+ let headerRef = activeSectionRefs?.headerRefs?.[variantType];
80022
+ let footerRef = activeSectionRefs?.footerRefs?.[variantType];
80023
+ let effectiveVariantType = variantType;
80024
+ if (!headerRef && variantType !== "default" && activeSectionIndex > 0) {
80025
+ const prevSectionMetadata = sectionMetadataList[activeSectionIndex - 1];
80026
+ if (prevSectionMetadata?.headerRefs?.[variantType]) {
80027
+ headerRef = prevSectionMetadata.headerRefs[variantType];
80028
+ layoutLog(
80029
+ `[Layout] Page ${newPageNumber}: Inheriting header '${variantType}' from section ${activeSectionIndex - 1}: ${headerRef}`
80030
+ );
80031
+ }
80032
+ }
80033
+ if (!footerRef && variantType !== "default" && activeSectionIndex > 0) {
80034
+ const prevSectionMetadata = sectionMetadataList[activeSectionIndex - 1];
80035
+ if (prevSectionMetadata?.footerRefs?.[variantType]) {
80036
+ footerRef = prevSectionMetadata.footerRefs[variantType];
80037
+ layoutLog(
80038
+ `[Layout] Page ${newPageNumber}: Inheriting footer '${variantType}' from section ${activeSectionIndex - 1}: ${footerRef}`
80039
+ );
80040
+ }
80041
+ }
80042
+ if (!headerRef && variantType !== "default" && activeSectionRefs?.headerRefs?.default) {
80043
+ headerRef = activeSectionRefs.headerRefs.default;
80044
+ effectiveVariantType = "default";
80045
+ }
80046
+ if (!footerRef && variantType !== "default" && activeSectionRefs?.footerRefs?.default) {
80047
+ footerRef = activeSectionRefs.footerRefs.default;
80048
+ }
80049
+ const headerHeight = getHeaderHeightForPage(effectiveVariantType, headerRef);
80050
+ const footerHeight = getFooterHeightForPage(
80051
+ variantType !== "default" && !activeSectionRefs?.footerRefs?.[variantType] ? "default" : variantType,
80052
+ footerRef
80053
+ );
80054
+ activeTopMargin = calculateEffectiveTopMargin(headerHeight, activeHeaderDistance, activeSectionBaseTopMargin);
80055
+ activeBottomMargin = calculateEffectiveBottomMargin(
80056
+ footerHeight,
80057
+ activeFooterDistance,
80058
+ activeSectionBaseBottomMargin
80059
+ );
80060
+ layoutLog(
80061
+ `[Layout] Page ${newPageNumber}: Using variant '${variantType}' - headerHeight: ${headerHeight}, footerHeight: ${footerHeight}`
80062
+ );
80063
+ layoutLog(
80064
+ `[Layout] Page ${newPageNumber}: Adjusted margins - top: ${activeTopMargin}, bottom: ${activeBottomMargin} (base: ${activeSectionBaseTopMargin}, ${activeSectionBaseBottomMargin})`
80065
+ );
79959
80066
  return;
79960
80067
  }
79961
80068
  if (state?.page) {
@@ -80161,6 +80268,20 @@ ${l}
80161
80268
  pendingColumns = updatedState.pendingColumns;
80162
80269
  activeOrientation = updatedState.activeOrientation;
80163
80270
  pendingOrientation = updatedState.pendingOrientation;
80271
+ const isFirstSection = effectiveBlock.attrs?.isFirstSection && states.length === 0;
80272
+ const blockTopMargin = effectiveBlock.margins?.top;
80273
+ const blockBottomMargin = effectiveBlock.margins?.bottom;
80274
+ if (isFirstSection) {
80275
+ activeSectionBaseTopMargin = typeof blockTopMargin === "number" ? blockTopMargin : margins.top;
80276
+ activeSectionBaseBottomMargin = typeof blockBottomMargin === "number" ? blockBottomMargin : margins.bottom;
80277
+ } else if (blockTopMargin !== void 0 || blockBottomMargin !== void 0) {
80278
+ if (blockTopMargin !== void 0) {
80279
+ pendingSectionBaseTopMargin = typeof blockTopMargin === "number" ? blockTopMargin : margins.top;
80280
+ }
80281
+ if (blockBottomMargin !== void 0) {
80282
+ pendingSectionBaseBottomMargin = typeof blockBottomMargin === "number" ? blockBottomMargin : margins.bottom;
80283
+ }
80284
+ }
80164
80285
  if (effectiveBlock.vAlign) {
80165
80286
  const isFirstSection2 = effectiveBlock.attrs?.isFirstSection && states.length === 0;
80166
80287
  if (isFirstSection2) {
@@ -80179,7 +80300,6 @@ ${l}
80179
80300
  }
80180
80301
  const sectionIndexRaw = effectiveBlock.attrs?.sectionIndex;
80181
80302
  const metadataIndex = typeof sectionIndexRaw === "number" ? sectionIndexRaw : Number(sectionIndexRaw ?? NaN);
80182
- const isFirstSection = effectiveBlock.attrs?.isFirstSection && states.length === 0;
80183
80303
  if (Number.isFinite(metadataIndex)) {
80184
80304
  if (isFirstSection) {
80185
80305
  activeSectionIndex = metadataIndex;
@@ -82369,6 +82489,7 @@ ${l}
82369
82489
  `[Perf] 4.1 Measure all blocks: ${(measureEnd - measureStart).toFixed(2)}ms (${cacheMisses} measured, ${cacheHits} cached)`
82370
82490
  );
82371
82491
  let headerContentHeights;
82492
+ let headerContentHeightsByRId;
82372
82493
  const hasHeaderBlocks = headerFooter?.headerBlocks && Object.keys(headerFooter.headerBlocks).length > 0;
82373
82494
  const hasHeaderBlocksByRId = headerFooter?.headerBlocksByRId && headerFooter.headerBlocksByRId.size > 0;
82374
82495
  if (headerFooter?.constraints && (hasHeaderBlocks || hasHeaderBlocksByRId)) {
@@ -82408,7 +82529,8 @@ ${l}
82408
82529
  }
82409
82530
  }
82410
82531
  if (hasHeaderBlocksByRId && headerFooter.headerBlocksByRId) {
82411
- for (const [_rId, blocks2] of headerFooter.headerBlocksByRId) {
82532
+ headerContentHeightsByRId = /* @__PURE__ */ new Map();
82533
+ for (const [rId, blocks2] of headerFooter.headerBlocksByRId) {
82412
82534
  if (!blocks2 || blocks2.length === 0) continue;
82413
82535
  const measureConstraints = {
82414
82536
  maxWidth: headerFooter.constraints.width,
@@ -82420,8 +82542,7 @@ ${l}
82420
82542
  height: headerFooter.constraints.height
82421
82543
  });
82422
82544
  if (layout2.height > 0) {
82423
- const currentDefault = headerContentHeights.default ?? 0;
82424
- headerContentHeights.default = Math.max(currentDefault, layout2.height);
82545
+ headerContentHeightsByRId.set(rId, layout2.height);
82425
82546
  }
82426
82547
  }
82427
82548
  }
@@ -82429,6 +82550,7 @@ ${l}
82429
82550
  perfLog(`[Perf] 4.1.5 Pre-layout headers for height: ${(hfPreEnd - hfPreStart).toFixed(2)}ms`);
82430
82551
  }
82431
82552
  let footerContentHeights;
82553
+ let footerContentHeightsByRId;
82432
82554
  const hasFooterBlocks = headerFooter?.footerBlocks && Object.keys(headerFooter.footerBlocks).length > 0;
82433
82555
  const hasFooterBlocksByRId = headerFooter?.footerBlocksByRId && headerFooter.footerBlocksByRId.size > 0;
82434
82556
  if (headerFooter?.constraints && (hasFooterBlocks || hasFooterBlocksByRId)) {
@@ -82471,7 +82593,8 @@ ${l}
82471
82593
  }
82472
82594
  }
82473
82595
  if (hasFooterBlocksByRId && headerFooter.footerBlocksByRId) {
82474
- for (const [_rId, blocks2] of headerFooter.footerBlocksByRId) {
82596
+ footerContentHeightsByRId = /* @__PURE__ */ new Map();
82597
+ for (const [rId, blocks2] of headerFooter.footerBlocksByRId) {
82475
82598
  if (!blocks2 || blocks2.length === 0) continue;
82476
82599
  const measureConstraints = {
82477
82600
  maxWidth: headerFooter.constraints.width,
@@ -82483,8 +82606,7 @@ ${l}
82483
82606
  height: headerFooter.constraints.height
82484
82607
  });
82485
82608
  if (layout2.height > 0) {
82486
- const currentDefault = footerContentHeights.default ?? 0;
82487
- footerContentHeights.default = Math.max(currentDefault, layout2.height);
82609
+ footerContentHeightsByRId.set(rId, layout2.height);
82488
82610
  }
82489
82611
  }
82490
82612
  }
@@ -82499,9 +82621,13 @@ ${l}
82499
82621
  let layout = layoutDocument(nextBlocks, measures, {
82500
82622
  ...options,
82501
82623
  headerContentHeights,
82502
- // Pass header heights to prevent overlap
82624
+ // Pass header heights to prevent overlap (per-variant)
82503
82625
  footerContentHeights,
82504
- // Pass footer heights to prevent overlap
82626
+ // Pass footer heights to prevent overlap (per-variant)
82627
+ headerContentHeightsByRId,
82628
+ // Pass header heights by rId for per-page margin calculation
82629
+ footerContentHeightsByRId,
82630
+ // Pass footer heights by rId for per-page margin calculation
82505
82631
  remeasureParagraph: (block, maxWidth, firstLineIndent) => remeasureParagraph(block, maxWidth, firstLineIndent)
82506
82632
  });
82507
82633
  const layoutEnd = performance.now();
@@ -82549,9 +82675,13 @@ ${l}
82549
82675
  layout = layoutDocument(currentBlocks, currentMeasures, {
82550
82676
  ...options,
82551
82677
  headerContentHeights,
82552
- // Pass header heights to prevent overlap
82678
+ // Pass header heights to prevent overlap (per-variant)
82553
82679
  footerContentHeights,
82554
- // Pass footer heights to prevent overlap
82680
+ // Pass footer heights to prevent overlap (per-variant)
82681
+ headerContentHeightsByRId,
82682
+ // Pass header heights by rId for per-page margin calculation
82683
+ footerContentHeightsByRId,
82684
+ // Pass footer heights by rId for per-page margin calculation
82555
82685
  remeasureParagraph: (block, maxWidth, firstLineIndent) => remeasureParagraph(block, maxWidth, firstLineIndent)
82556
82686
  });
82557
82687
  const relayoutEnd = performance.now();
@@ -87920,6 +88050,19 @@ ${l}
87920
88050
  const effectiveMarks = nodeMarks.length > 0 ? nodeMarks : marksAsAttrs;
87921
88051
  const marks = [...effectiveMarks, ...inheritedMarks ?? []];
87922
88052
  applyMarksToRun(run2, marks, hyperlinkConfig, themeColors);
88053
+ if (marksAsAttrs.length > 0) {
88054
+ run2._explicitFont = true;
88055
+ }
88056
+ console.debug("[token-debug] tokenNodeToRun", {
88057
+ token,
88058
+ fontFamily: run2.fontFamily,
88059
+ fontSize: run2.fontSize,
88060
+ defaultFont,
88061
+ defaultSize,
88062
+ nodeMarksCount: nodeMarks.length,
88063
+ marksAsAttrsCount: marksAsAttrs.length,
88064
+ inheritedMarksCount: inheritedMarks?.length ?? 0
88065
+ });
87923
88066
  return run2;
87924
88067
  }
87925
88068
  const EIGHTHS_PER_POINT = 8;
@@ -91668,6 +91811,10 @@ ${l}
91668
91811
  if (TOKEN_INLINE_TYPES.has(node2.type)) {
91669
91812
  const tokenKind = TOKEN_INLINE_TYPES.get(node2.type);
91670
91813
  if (tokenKind) {
91814
+ const marksAsAttrs = Array.isArray(node2.attrs?.marksAsAttrs) ? node2.attrs.marksAsAttrs : [];
91815
+ const nodeMarks = node2.marks ?? [];
91816
+ const effectiveMarks = nodeMarks.length > 0 ? nodeMarks : marksAsAttrs;
91817
+ const mergedMarks = [...effectiveMarks, ...inheritedMarks ?? []];
91671
91818
  const tokenRun = tokenNodeToRun(
91672
91819
  node2,
91673
91820
  positions,
@@ -91684,6 +91831,23 @@ ${l}
91684
91831
  const inlineStyleId = getInlineStyleId(inheritedMarks);
91685
91832
  applyRunStyles2(tokenRun, inlineStyleId, activeRunStyleId);
91686
91833
  applyBaseRunDefaults(tokenRun, baseRunDefaults, defaultFont, defaultSize);
91834
+ if (mergedMarks.length > 0) {
91835
+ applyMarksToRun(
91836
+ tokenRun,
91837
+ mergedMarks,
91838
+ hyperlinkConfig,
91839
+ themeColors,
91840
+ converterContext?.backgroundColor
91841
+ );
91842
+ }
91843
+ console.debug("[token-debug] paragraph-token-run", {
91844
+ token: tokenRun.token,
91845
+ fontFamily: tokenRun.fontFamily,
91846
+ fontSize: tokenRun.fontSize,
91847
+ inlineStyleId,
91848
+ runStyleId: activeRunStyleId,
91849
+ mergedMarksCount: mergedMarks.length
91850
+ });
91687
91851
  currentRuns.push(tokenRun);
91688
91852
  }
91689
91853
  return;
@@ -94668,6 +94832,77 @@ ${l}
94668
94832
  function isFieldAnnotationRun(run2) {
94669
94833
  return run2.kind === "fieldAnnotation";
94670
94834
  }
94835
+ function measureTabAlignmentGroup(startRunIndex, runs2, ctx2, decimalSeparator = ".") {
94836
+ const result = {
94837
+ totalWidth: 0,
94838
+ runs: [],
94839
+ endRunIndex: runs2.length
94840
+ };
94841
+ let foundDecimal = false;
94842
+ for (let i2 = startRunIndex; i2 < runs2.length; i2++) {
94843
+ const run2 = runs2[i2];
94844
+ if (isTabRun(run2)) {
94845
+ result.endRunIndex = i2;
94846
+ break;
94847
+ }
94848
+ if (isLineBreakRun(run2) || run2.kind === "break" && run2.breakType === "line") {
94849
+ result.endRunIndex = i2;
94850
+ break;
94851
+ }
94852
+ if (run2.kind === "text" || run2.kind === void 0) {
94853
+ const textRun = run2;
94854
+ const text2 = textRun.text || "";
94855
+ if (text2.length > 0) {
94856
+ const { font } = buildFontString(textRun);
94857
+ const width = measureRunWidth(text2, font, ctx2, textRun, 0);
94858
+ let beforeDecimalWidth;
94859
+ if (!foundDecimal) {
94860
+ const decimalIdx = text2.indexOf(decimalSeparator);
94861
+ if (decimalIdx >= 0) {
94862
+ foundDecimal = true;
94863
+ const beforeText = text2.slice(0, decimalIdx);
94864
+ beforeDecimalWidth = beforeText.length > 0 ? measureRunWidth(beforeText, font, ctx2, textRun, 0) : 0;
94865
+ result.beforeDecimalWidth = result.totalWidth + beforeDecimalWidth;
94866
+ }
94867
+ }
94868
+ result.runs.push({
94869
+ runIndex: i2,
94870
+ width,
94871
+ text: text2,
94872
+ beforeDecimalWidth
94873
+ });
94874
+ result.totalWidth += width;
94875
+ } else {
94876
+ result.runs.push({ runIndex: i2, width: 0, text: "" });
94877
+ }
94878
+ continue;
94879
+ }
94880
+ if (isImageRun(run2)) {
94881
+ const leftSpace = run2.distLeft ?? 0;
94882
+ const rightSpace = run2.distRight ?? 0;
94883
+ const imageWidth = run2.width + leftSpace + rightSpace;
94884
+ result.runs.push({ runIndex: i2, width: imageWidth });
94885
+ result.totalWidth += imageWidth;
94886
+ continue;
94887
+ }
94888
+ if (isFieldAnnotationRun(run2)) {
94889
+ const fontSize2 = run2.fontSize ?? DEFAULT_FIELD_ANNOTATION_FONT_SIZE;
94890
+ const { font } = buildFontString({
94891
+ fontFamily: run2.fontFamily ?? "Arial",
94892
+ fontSize: fontSize2,
94893
+ bold: run2.bold,
94894
+ italic: run2.italic
94895
+ });
94896
+ const textWidth = run2.displayLabel ? measureRunWidth(run2.displayLabel, font, ctx2, run2, 0) : 0;
94897
+ const pillWidth = textWidth + FIELD_ANNOTATION_PILL_PADDING;
94898
+ result.runs.push({ runIndex: i2, width: pillWidth });
94899
+ result.totalWidth += pillWidth;
94900
+ continue;
94901
+ }
94902
+ result.runs.push({ runIndex: i2, width: 0 });
94903
+ }
94904
+ return result;
94905
+ }
94671
94906
  async function measureBlock(block, constraints) {
94672
94907
  const normalized = normalizeConstraints(constraints);
94673
94908
  if (block.kind === "drawing") {
@@ -94791,6 +95026,7 @@ ${l}
94791
95026
  let pendingTabAlignment = null;
94792
95027
  let lastAppliedTabAlign = null;
94793
95028
  const warnedTabVals = /* @__PURE__ */ new Set();
95029
+ let activeTabGroup = null;
94794
95030
  const validateTabStopVal = (stop) => {
94795
95031
  if (!ALLOWED_TAB_VALS.has(stop.val) && !warnedTabVals.has(stop.val)) {
94796
95032
  warnedTabVals.add(stop.val);
@@ -94970,6 +95206,7 @@ ${l}
94970
95206
  continue;
94971
95207
  }
94972
95208
  if (isTabRun(run2)) {
95209
+ activeTabGroup = null;
94973
95210
  if (!currentLine) {
94974
95211
  currentLine = {
94975
95212
  fromRun: runIndex,
@@ -94994,12 +95231,6 @@ ${l}
94994
95231
  currentLine.maxFontSize = Math.max(currentLine.maxFontSize, 12);
94995
95232
  currentLine.toRun = runIndex;
94996
95233
  currentLine.toChar = 1;
94997
- if (stop) {
94998
- validateTabStopVal(stop);
94999
- pendingTabAlignment = { target: clampedTarget, val: stop.val };
95000
- } else {
95001
- pendingTabAlignment = null;
95002
- }
95003
95234
  if (stop && stop.leader && stop.leader !== "none") {
95004
95235
  const leaderStyle = stop.leader;
95005
95236
  const from2 = Math.min(originX, clampedTarget);
@@ -95007,6 +95238,36 @@ ${l}
95007
95238
  if (!currentLine.leaders) currentLine.leaders = [];
95008
95239
  currentLine.leaders.push({ from: from2, to, style: leaderStyle });
95009
95240
  }
95241
+ if (stop) {
95242
+ validateTabStopVal(stop);
95243
+ if (stop.val === "end" || stop.val === "center" || stop.val === "decimal") {
95244
+ const groupMeasure = measureTabAlignmentGroup(runIndex + 1, runsToProcess, ctx2, decimalSeparator);
95245
+ if (groupMeasure.totalWidth > 0) {
95246
+ let groupStartX;
95247
+ if (stop.val === "end") {
95248
+ groupStartX = Math.max(0, clampedTarget - groupMeasure.totalWidth);
95249
+ } else if (stop.val === "center") {
95250
+ groupStartX = Math.max(0, clampedTarget - groupMeasure.totalWidth / 2);
95251
+ } else {
95252
+ const beforeDecimal = groupMeasure.beforeDecimalWidth ?? groupMeasure.totalWidth;
95253
+ groupStartX = Math.max(0, clampedTarget - beforeDecimal);
95254
+ }
95255
+ activeTabGroup = {
95256
+ measure: groupMeasure,
95257
+ startX: groupStartX,
95258
+ currentX: groupStartX,
95259
+ target: clampedTarget,
95260
+ val: stop.val
95261
+ };
95262
+ currentLine.width = roundValue(groupStartX);
95263
+ }
95264
+ pendingTabAlignment = null;
95265
+ } else {
95266
+ pendingTabAlignment = { target: clampedTarget, val: stop.val };
95267
+ }
95268
+ } else {
95269
+ pendingTabAlignment = null;
95270
+ }
95010
95271
  continue;
95011
95272
  }
95012
95273
  if (isImageRun(run2)) {
@@ -95017,7 +95278,10 @@ ${l}
95017
95278
  const bottomSpace = run2.distBottom ?? 0;
95018
95279
  const imageHeight = run2.height + topSpace + bottomSpace;
95019
95280
  let imageStartX;
95020
- if (pendingTabAlignment && currentLine) {
95281
+ if (activeTabGroup && currentLine) {
95282
+ imageStartX = activeTabGroup.currentX;
95283
+ activeTabGroup.currentX = roundValue(activeTabGroup.currentX + imageWidth);
95284
+ } else if (pendingTabAlignment && currentLine) {
95021
95285
  imageStartX = alignPendingTabForWidth(imageWidth);
95022
95286
  }
95023
95287
  if (!currentLine) {
@@ -95042,10 +95306,14 @@ ${l}
95042
95306
  }
95043
95307
  ]
95044
95308
  };
95309
+ if (activeTabGroup && runIndex + 1 >= activeTabGroup.measure.endRunIndex) {
95310
+ activeTabGroup = null;
95311
+ }
95045
95312
  continue;
95046
95313
  }
95047
95314
  const appliedTabAlign = lastAppliedTabAlign;
95048
- if (currentLine.width + imageWidth > currentLine.maxWidth && currentLine.width > 0) {
95315
+ const skipFitCheck = activeTabGroup !== null;
95316
+ if (!skipFitCheck && currentLine.width + imageWidth > currentLine.maxWidth && currentLine.width > 0) {
95049
95317
  trimTrailingWrapSpaces(currentLine);
95050
95318
  const metrics = calculateTypographyMetrics(currentLine.maxFontSize, spacing, currentLine.maxFontInfo);
95051
95319
  const lineBase = currentLine;
@@ -95058,6 +95326,7 @@ ${l}
95058
95326
  tabStopCursor = 0;
95059
95327
  pendingTabAlignment = null;
95060
95328
  lastAppliedTabAlign = null;
95329
+ activeTabGroup = null;
95061
95330
  currentLine = {
95062
95331
  fromRun: runIndex,
95063
95332
  fromChar: 0,
@@ -95090,6 +95359,9 @@ ${l}
95090
95359
  ...imageStartX !== void 0 ? { x: imageStartX } : {}
95091
95360
  });
95092
95361
  }
95362
+ if (activeTabGroup && runIndex + 1 >= activeTabGroup.measure.endRunIndex) {
95363
+ activeTabGroup = null;
95364
+ }
95093
95365
  const tabAlign = appliedTabAlign;
95094
95366
  if (tabAlign && currentLine && tabAlign.val === "end") {
95095
95367
  currentLine.width = roundValue(tabAlign.target);
@@ -95265,7 +95537,11 @@ ${l}
95265
95537
  }
95266
95538
  }
95267
95539
  let segmentStartX;
95268
- if (currentLine && pendingTabAlignment) {
95540
+ let inActiveTabGroup = false;
95541
+ if (activeTabGroup && currentLine) {
95542
+ segmentStartX = activeTabGroup.currentX;
95543
+ inActiveTabGroup = true;
95544
+ } else if (currentLine && pendingTabAlignment) {
95269
95545
  segmentStartX = alignSegmentAtTab(segment, font, run2, charPosInRun);
95270
95546
  if (segmentStartX == null) {
95271
95547
  segmentStartX = currentLine.width;
@@ -95302,6 +95578,7 @@ ${l}
95302
95578
  tabStopCursor = 0;
95303
95579
  pendingTabAlignment = null;
95304
95580
  lastAppliedTabAlign = null;
95581
+ activeTabGroup = null;
95305
95582
  currentLine = {
95306
95583
  fromRun: runIndex,
95307
95584
  fromChar: spaceStartChar,
@@ -95320,7 +95597,19 @@ ${l}
95320
95597
  currentLine.width = roundValue(currentLine.width + boundarySpacing2 + singleSpaceWidth);
95321
95598
  currentLine.maxFontInfo = updateMaxFontInfo(currentLine.maxFontSize, currentLine.maxFontInfo, run2);
95322
95599
  currentLine.maxFontSize = Math.max(currentLine.maxFontSize, run2.fontSize);
95323
- appendSegment(currentLine.segments, runIndex, spaceStartChar, spaceEndChar, singleSpaceWidth);
95600
+ let spaceExplicitX;
95601
+ if (inActiveTabGroup && activeTabGroup) {
95602
+ spaceExplicitX = activeTabGroup.currentX;
95603
+ activeTabGroup.currentX = roundValue(activeTabGroup.currentX + singleSpaceWidth);
95604
+ }
95605
+ appendSegment(
95606
+ currentLine.segments,
95607
+ runIndex,
95608
+ spaceStartChar,
95609
+ spaceEndChar,
95610
+ singleSpaceWidth,
95611
+ spaceExplicitX
95612
+ );
95324
95613
  currentLine.spaceCount += 1;
95325
95614
  }
95326
95615
  }
@@ -95468,7 +95757,7 @@ ${l}
95468
95757
  const totalWidthWithWord = currentLine.width + boundarySpacing + wordCommitWidth + // Safe cast: only TextRuns produce word segments from split(), other run types are handled earlier
95469
95758
  (shouldIncludeDelimiterSpace ? run2.letterSpacing ?? 0 : 0);
95470
95759
  const availableWidth = currentLine.maxWidth - WIDTH_FUDGE_PX2;
95471
- let shouldBreak = currentLine.width + boundarySpacing + wordOnlyWidth > availableWidth && currentLine.width > 0 && !isTocEntry;
95760
+ let shouldBreak = !inActiveTabGroup && currentLine.width + boundarySpacing + wordOnlyWidth > availableWidth && currentLine.width > 0 && !isTocEntry;
95472
95761
  let compressedWidth = null;
95473
95762
  if (shouldBreak && justifyAlignment) {
95474
95763
  const isLastNonEmptyWordInSegment = wordIndex === lastNonEmptyWordIndex;
@@ -95533,15 +95822,14 @@ ${l}
95533
95822
  currentLine.width = roundValue(currentLine.width + boundarySpacing + wordOnlyWidth);
95534
95823
  currentLine.maxFontInfo = updateMaxFontInfo(currentLine.maxFontSize, currentLine.maxFontInfo, run2);
95535
95824
  currentLine.maxFontSize = Math.max(currentLine.maxFontSize, run2.fontSize);
95536
- const useExplicitXHere = wordIndex === 0 && segmentStartX !== void 0;
95537
- appendSegment(
95538
- currentLine.segments,
95539
- runIndex,
95540
- wordStartChar,
95541
- wordEndNoSpace,
95542
- wordOnlyWidth,
95543
- useExplicitXHere ? segmentStartX : void 0
95544
- );
95825
+ let explicitXHere;
95826
+ if (inActiveTabGroup && activeTabGroup) {
95827
+ explicitXHere = activeTabGroup.currentX;
95828
+ activeTabGroup.currentX = roundValue(activeTabGroup.currentX + wordOnlyWidth);
95829
+ } else if (wordIndex === 0 && segmentStartX !== void 0) {
95830
+ explicitXHere = segmentStartX;
95831
+ }
95832
+ appendSegment(currentLine.segments, runIndex, wordStartChar, wordEndNoSpace, wordOnlyWidth, explicitXHere);
95545
95833
  trimTrailingWrapSpaces(currentLine);
95546
95834
  const metrics = calculateTypographyMetrics(currentLine.maxFontSize, spacing, currentLine.maxFontInfo);
95547
95835
  const lineBase = currentLine;
@@ -95556,8 +95844,13 @@ ${l}
95556
95844
  }
95557
95845
  const newToChar = shouldIncludeDelimiterSpace ? wordEndWithSpace : wordEndNoSpace;
95558
95846
  currentLine.toChar = newToChar;
95559
- const useExplicitX = wordIndex === 0 && segmentStartX !== void 0;
95560
- const explicitX = useExplicitX ? segmentStartX : void 0;
95847
+ let explicitX;
95848
+ if (inActiveTabGroup && activeTabGroup) {
95849
+ explicitX = activeTabGroup.currentX;
95850
+ activeTabGroup.currentX = roundValue(activeTabGroup.currentX + wordCommitWidth);
95851
+ } else if (wordIndex === 0 && segmentStartX !== void 0) {
95852
+ explicitX = segmentStartX;
95853
+ }
95561
95854
  const targetWidth = compressedWidth != null ? compressedWidth : currentLine.width + boundarySpacing + wordCommitWidth + (shouldIncludeDelimiterSpace ? run2.letterSpacing ?? 0 : 0);
95562
95855
  if (compressedWidth != null) {
95563
95856
  currentLine.naturalWidth = roundValue(totalWidthWithWord);
@@ -95579,6 +95872,12 @@ ${l}
95579
95872
  }
95580
95873
  }
95581
95874
  lastAppliedTabAlign = null;
95875
+ if (activeTabGroup && runIndex + 1 >= activeTabGroup.measure.endRunIndex) {
95876
+ if (currentLine && activeTabGroup.val === "end") {
95877
+ currentLine.width = roundValue(activeTabGroup.target);
95878
+ }
95879
+ activeTabGroup = null;
95880
+ }
95582
95881
  if (!isLastSegment) {
95583
95882
  pendingTabAlignment = null;
95584
95883
  if (!currentLine) {
@@ -99867,7 +100166,26 @@ ${l}
99867
100166
  const firstPageInSection = sectionFirstPageNumbers.get(sectionIndex);
99868
100167
  const sectionPageNumber = typeof firstPageInSection === "number" ? pageNumber - firstPageInSection + 1 : pageNumber;
99869
100168
  const headerFooterType = multiSectionId ? getHeaderFooterTypeForSection(pageNumber, sectionIndex, multiSectionId, { kind, sectionPageNumber }) : getHeaderFooterType(pageNumber, legacyIdentifier, { kind });
99870
- const sectionRId = page?.sectionRefs && kind === "header" ? page.sectionRefs.headerRefs?.[headerFooterType] ?? void 0 : page?.sectionRefs && kind === "footer" ? page.sectionRefs.footerRefs?.[headerFooterType] ?? void 0 : void 0;
100169
+ let sectionRId;
100170
+ if (page?.sectionRefs && kind === "header") {
100171
+ sectionRId = page.sectionRefs.headerRefs?.[headerFooterType];
100172
+ if (!sectionRId && headerFooterType && headerFooterType !== "default" && sectionIndex > 0 && multiSectionId) {
100173
+ const prevSectionIds = multiSectionId.sectionHeaderIds.get(sectionIndex - 1);
100174
+ sectionRId = prevSectionIds?.[headerFooterType] ?? void 0;
100175
+ }
100176
+ if (!sectionRId && headerFooterType !== "default") {
100177
+ sectionRId = page.sectionRefs.headerRefs?.default;
100178
+ }
100179
+ } else if (page?.sectionRefs && kind === "footer") {
100180
+ sectionRId = page.sectionRefs.footerRefs?.[headerFooterType];
100181
+ if (!sectionRId && headerFooterType && headerFooterType !== "default" && sectionIndex > 0 && multiSectionId) {
100182
+ const prevSectionIds = multiSectionId.sectionFooterIds.get(sectionIndex - 1);
100183
+ sectionRId = prevSectionIds?.[headerFooterType] ?? void 0;
100184
+ }
100185
+ if (!sectionRId && headerFooterType !== "default") {
100186
+ sectionRId = page.sectionRefs.footerRefs?.default;
100187
+ }
100188
+ }
99871
100189
  if (!headerFooterType) {
99872
100190
  return null;
99873
100191
  }
@@ -143695,7 +144013,7 @@ ${reason}`);
143695
144013
  this.config.colors = shuffleArray(this.config.colors);
143696
144014
  this.userColorMap = /* @__PURE__ */ new Map();
143697
144015
  this.colorIndex = 0;
143698
- this.version = "1.3.0-next.4";
144016
+ this.version = "1.3.0-next.6";
143699
144017
  this.#log("🦋 [superdoc] Using SuperDoc version:", this.version);
143700
144018
  this.superdocId = config2.superdocId || v4();
143701
144019
  this.colors = this.config.colors;