@harbour-enterprises/superdoc 1.3.0-next.9 → 1.3.1-next.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -36435,7 +36435,7 @@ Please report this to https://github.com/markedjs/marked.`, e) {
36435
36435
  static getStoredSuperdocVersion(docx) {
36436
36436
  return SuperConverter.getStoredCustomProperty(docx, "SuperdocVersion");
36437
36437
  }
36438
- static setStoredSuperdocVersion(docx = this.convertedXml, version2 = "1.3.0-next.9") {
36438
+ static setStoredSuperdocVersion(docx = this.convertedXml, version2 = "1.3.1-next.1") {
36439
36439
  return SuperConverter.setStoredCustomProperty(docx, "SuperdocVersion", version2, false);
36440
36440
  }
36441
36441
  /**
@@ -47282,6 +47282,105 @@ Please report this to https://github.com/markedjs/marked.`, e) {
47282
47282
  tr.setNodeMarkup(pos, void 0, nextAttrs, node2.marks);
47283
47283
  return true;
47284
47284
  };
47285
+ function findGoverningSectPrParagraph(doc2, selectionPos) {
47286
+ const candidates = [];
47287
+ doc2.descendants((node2, nodePos) => {
47288
+ if (node2.type?.name === "paragraph" && node2.attrs?.paragraphProperties?.sectPr) {
47289
+ candidates.push({ node: node2, pos: nodePos });
47290
+ }
47291
+ });
47292
+ if (!candidates.length) return null;
47293
+ const inside = candidates.find((c2) => selectionPos >= c2.pos && selectionPos < c2.pos + c2.node.nodeSize);
47294
+ if (inside) return inside;
47295
+ const atOrAfter = candidates.find((c2) => c2.pos >= selectionPos);
47296
+ return atOrAfter ?? candidates[candidates.length - 1];
47297
+ }
47298
+ const setSectionPageMarginsAtSelection = ({ topInches, rightInches, bottomInches, leftInches } = {}) => ({ tr, state, editor }) => {
47299
+ if (!state || !editor) {
47300
+ console.warn("[setSectionPageMarginsAtSelection] Missing state or editor");
47301
+ return false;
47302
+ }
47303
+ const hasTop = typeof topInches === "number";
47304
+ const hasRight = typeof rightInches === "number";
47305
+ const hasBottom = typeof bottomInches === "number";
47306
+ const hasLeft = typeof leftInches === "number";
47307
+ if (!hasTop && !hasRight && !hasBottom && !hasLeft) {
47308
+ console.warn("[setSectionPageMarginsAtSelection] No margin values provided");
47309
+ return false;
47310
+ }
47311
+ if (hasTop && topInches < 0 || hasRight && rightInches < 0 || hasBottom && bottomInches < 0 || hasLeft && leftInches < 0) {
47312
+ console.warn("[setSectionPageMarginsAtSelection] Margin values must be >= 0");
47313
+ return false;
47314
+ }
47315
+ const updates = {};
47316
+ if (hasTop) updates.topInches = topInches;
47317
+ if (hasRight) updates.rightInches = rightInches;
47318
+ if (hasBottom) updates.bottomInches = bottomInches;
47319
+ if (hasLeft) updates.leftInches = leftInches;
47320
+ const { from: from2 } = state.selection;
47321
+ const governing = findGoverningSectPrParagraph(state.doc, from2);
47322
+ if (governing) {
47323
+ const { node: node2, pos } = governing;
47324
+ const paraProps = node2.attrs?.paragraphProperties || null;
47325
+ const existingSectPr = paraProps?.sectPr || null;
47326
+ if (!existingSectPr) {
47327
+ console.warn("[setSectionPageMarginsAtSelection] Paragraph found but has no sectPr");
47328
+ return false;
47329
+ }
47330
+ const sectPr2 = JSON.parse(JSON.stringify(existingSectPr));
47331
+ try {
47332
+ updateSectionMargins({ type: "sectPr", sectPr: sectPr2 }, updates);
47333
+ } catch (err) {
47334
+ console.error("[setSectionPageMarginsAtSelection] Failed to update sectPr:", err);
47335
+ return false;
47336
+ }
47337
+ const resolved = getSectPrMargins(sectPr2);
47338
+ const normalizedSectionMargins = {
47339
+ top: resolved.top ?? null,
47340
+ right: resolved.right ?? null,
47341
+ bottom: resolved.bottom ?? null,
47342
+ left: resolved.left ?? null,
47343
+ header: resolved.header ?? null,
47344
+ footer: resolved.footer ?? null
47345
+ };
47346
+ const newParagraphProperties = { ...paraProps || {}, sectPr: sectPr2 };
47347
+ const nextAttrs = {
47348
+ ...node2.attrs,
47349
+ paragraphProperties: newParagraphProperties,
47350
+ sectionMargins: normalizedSectionMargins
47351
+ };
47352
+ tr.setNodeMarkup(pos, void 0, nextAttrs, node2.marks);
47353
+ tr.setMeta("forceUpdatePagination", true);
47354
+ return true;
47355
+ }
47356
+ const docAttrs = state.doc.attrs ?? {};
47357
+ const converter = editor.converter ?? null;
47358
+ const baseBodySectPr = docAttrs.bodySectPr || converter?.bodySectPr || null;
47359
+ const sectPr = baseBodySectPr != null ? JSON.parse(JSON.stringify(baseBodySectPr)) : { type: "element", name: "w:sectPr", elements: [] };
47360
+ try {
47361
+ updateSectionMargins({ type: "sectPr", sectPr }, updates);
47362
+ } catch (err) {
47363
+ console.error("[setSectionPageMarginsAtSelection] Failed to update sectPr:", err);
47364
+ return false;
47365
+ }
47366
+ if (converter) {
47367
+ converter.bodySectPr = sectPr;
47368
+ if (!converter.pageStyles) converter.pageStyles = {};
47369
+ if (!converter.pageStyles.pageMargins) converter.pageStyles.pageMargins = {};
47370
+ const pageMargins = converter.pageStyles.pageMargins;
47371
+ const resolved = getSectPrMargins(sectPr);
47372
+ if (resolved.top != null) pageMargins.top = resolved.top;
47373
+ if (resolved.right != null) pageMargins.right = resolved.right;
47374
+ if (resolved.bottom != null) pageMargins.bottom = resolved.bottom;
47375
+ if (resolved.left != null) pageMargins.left = resolved.left;
47376
+ if (resolved.header != null) pageMargins.header = resolved.header;
47377
+ if (resolved.footer != null) pageMargins.footer = resolved.footer;
47378
+ }
47379
+ const nextDocAttrs = { ...docAttrs, bodySectPr: sectPr };
47380
+ tr.setNodeMarkup(0, void 0, nextDocAttrs);
47381
+ tr.setMeta("forceUpdatePagination", true);
47382
+ return true;
47383
+ };
47285
47384
  const insertSectionBreakAtSelection = ({ headerInches, footerInches } = {}) => ({ tr, state, editor }) => {
47286
47385
  if (!state || !editor) {
47287
47386
  console.warn("[insertSectionBreakAtSelection] Missing state or editor");
@@ -47813,6 +47912,7 @@ Please report this to https://github.com/markedjs/marked.`, e) {
47813
47912
  setMeta,
47814
47913
  setNode,
47815
47914
  setSectionHeaderFooterAtSelection,
47915
+ setSectionPageMarginsAtSelection,
47816
47916
  setTextIndentation,
47817
47917
  setTextSelection,
47818
47918
  skipTab,
@@ -62145,7 +62245,7 @@ Please report this to https://github.com/markedjs/marked.`, e) {
62145
62245
  return false;
62146
62246
  }
62147
62247
  };
62148
- const summaryVersion = "1.3.0-next.9";
62248
+ const summaryVersion = "1.3.1-next.1";
62149
62249
  const nodeKeys = ["group", "content", "marks", "inline", "atom", "defining", "code", "tableRole", "summary"];
62150
62250
  const markKeys = ["group", "inclusive", "excludes", "spanning", "code"];
62151
62251
  function mapAttributes(attrs) {
@@ -64148,9 +64248,8 @@ Please report this to https://github.com/markedjs/marked.`, e) {
64148
64248
  try {
64149
64249
  const jsonObj = json;
64150
64250
  const attrs = jsonObj.attrs;
64151
- const hasBody = attrs && "bodySectPr" in attrs;
64152
64251
  const converter = this.converter;
64153
- if (!hasBody && converter && converter.bodySectPr) {
64252
+ if (converter && converter.bodySectPr) {
64154
64253
  jsonObj.attrs = attrs || {};
64155
64254
  jsonObj.attrs.bodySectPr = converter.bodySectPr;
64156
64255
  }
@@ -64779,7 +64878,7 @@ Please report this to https://github.com/markedjs/marked.`, e) {
64779
64878
  * Process collaboration migrations
64780
64879
  */
64781
64880
  processCollaborationMigrations() {
64782
- console.debug("[checkVersionMigrations] Current editor version", "1.3.0-next.9");
64881
+ console.debug("[checkVersionMigrations] Current editor version", "1.3.1-next.1");
64783
64882
  if (!this.options.ydoc) return;
64784
64883
  const metaMap = this.options.ydoc.getMap("meta");
64785
64884
  let docVersion = metaMap.get("version");
@@ -71644,7 +71743,7 @@ ${l}
71644
71743
  return true;
71645
71744
  }
71646
71745
  const LIST_MARKER_GAP$2 = 8;
71647
- const DEFAULT_TAB_INTERVAL_PX$2 = 48;
71746
+ const DEFAULT_TAB_INTERVAL_PX$1 = 48;
71648
71747
  const DEFAULT_PAGE_HEIGHT_PX = 1056;
71649
71748
  const DEFAULT_VIRTUALIZED_PAGE_GAP$1 = 72;
71650
71749
  const COMMENT_EXTERNAL_COLOR = "#B1124B";
@@ -72678,7 +72777,7 @@ ${l}
72678
72777
  const textStart = paraIndentLeft + firstLine;
72679
72778
  tabWidth = textStart - currentPos;
72680
72779
  if (tabWidth <= 0) {
72681
- tabWidth = DEFAULT_TAB_INTERVAL_PX$2 - currentPos % DEFAULT_TAB_INTERVAL_PX$2;
72780
+ tabWidth = DEFAULT_TAB_INTERVAL_PX$1 - currentPos % DEFAULT_TAB_INTERVAL_PX$1;
72682
72781
  } else if (tabWidth < LIST_MARKER_GAP$2) {
72683
72782
  tabWidth = LIST_MARKER_GAP$2;
72684
72783
  }
@@ -72830,7 +72929,7 @@ ${l}
72830
72929
  const textStart = paraIndentLeft + firstLine;
72831
72930
  tabWidth = textStart - currentPos;
72832
72931
  if (tabWidth <= 0) {
72833
- tabWidth = DEFAULT_TAB_INTERVAL_PX$2 - currentPos % DEFAULT_TAB_INTERVAL_PX$2;
72932
+ tabWidth = DEFAULT_TAB_INTERVAL_PX$1 - currentPos % DEFAULT_TAB_INTERVAL_PX$1;
72834
72933
  } else if (tabWidth < LIST_MARKER_GAP$2) {
72835
72934
  tabWidth = LIST_MARKER_GAP$2;
72836
72935
  }
@@ -74178,6 +74277,13 @@ ${l}
74178
74277
  const trackedConfig = this.resolveTrackedChangesConfig(block);
74179
74278
  if (runsForLine.length === 0) {
74180
74279
  const span = this.doc.createElement("span");
74280
+ span.classList.add("superdoc-empty-run");
74281
+ if (lineRange.pmStart != null) {
74282
+ span.dataset.pmStart = String(lineRange.pmStart);
74283
+ }
74284
+ if (lineRange.pmEnd != null) {
74285
+ span.dataset.pmEnd = String(lineRange.pmEnd);
74286
+ }
74181
74287
  span.innerHTML = "&nbsp;";
74182
74288
  el.appendChild(span);
74183
74289
  }
@@ -77422,7 +77528,6 @@ ${l}
77422
77528
  const DEFAULT_LIST_INDENT_STEP_PX = 24;
77423
77529
  const DEFAULT_LIST_HANGING_PX$1 = 18;
77424
77530
  const SPACE_SUFFIX_GAP_PX = 4;
77425
- const DEFAULT_TAB_INTERVAL_PX$1 = 48;
77426
77531
  function resolveListTextStartPx(wordLayout, indentLeft, firstLine, hanging, measureMarkerText) {
77427
77532
  const marker = wordLayout?.marker;
77428
77533
  if (!marker) {
@@ -77456,9 +77561,13 @@ ${l}
77456
77561
  return markerStartPos + finalMarkerTextWidth;
77457
77562
  }
77458
77563
  const markerJustification = marker.justification ?? "left";
77564
+ const markerWidthEffective = Math.max(
77565
+ typeof marker.markerBoxWidthPx === "number" && Number.isFinite(marker.markerBoxWidthPx) ? marker.markerBoxWidthPx : 0,
77566
+ finalMarkerTextWidth
77567
+ );
77459
77568
  if (markerJustification !== "left") {
77460
- const gutterWidth = typeof marker.gutterWidthPx === "number" && Number.isFinite(marker.gutterWidthPx) && marker.gutterWidthPx > 0 ? marker.gutterWidthPx : LIST_MARKER_GAP$1;
77461
- return markerStartPos + finalMarkerTextWidth + Math.max(gutterWidth, LIST_MARKER_GAP$1);
77569
+ const gutterWidth2 = typeof marker.gutterWidthPx === "number" && Number.isFinite(marker.gutterWidthPx) && marker.gutterWidthPx > 0 ? marker.gutterWidthPx : LIST_MARKER_GAP$1;
77570
+ return markerStartPos + finalMarkerTextWidth + Math.max(gutterWidth2, LIST_MARKER_GAP$1);
77462
77571
  }
77463
77572
  if (wordLayout?.firstLineIndentMode === true) {
77464
77573
  let targetTabStop;
@@ -77470,12 +77579,12 @@ ${l}
77470
77579
  }
77471
77580
  }
77472
77581
  }
77473
- const textStartTarget = typeof marker.textStartX === "number" && Number.isFinite(marker.textStartX) ? marker.textStartX : wordLayout.textStartPx;
77582
+ const textStartTarget2 = typeof marker.textStartX === "number" && Number.isFinite(marker.textStartX) ? marker.textStartX : wordLayout.textStartPx;
77474
77583
  let tabWidth2;
77475
77584
  if (targetTabStop !== void 0) {
77476
77585
  tabWidth2 = targetTabStop - currentPos;
77477
- } else if (textStartTarget !== void 0 && Number.isFinite(textStartTarget) && textStartTarget > currentPos) {
77478
- tabWidth2 = textStartTarget - currentPos;
77586
+ } else if (textStartTarget2 !== void 0 && Number.isFinite(textStartTarget2) && textStartTarget2 > currentPos) {
77587
+ tabWidth2 = textStartTarget2 - currentPos;
77479
77588
  } else {
77480
77589
  tabWidth2 = LIST_MARKER_GAP$1;
77481
77590
  }
@@ -77484,14 +77593,21 @@ ${l}
77484
77593
  }
77485
77594
  return markerStartPos + finalMarkerTextWidth + tabWidth2;
77486
77595
  }
77596
+ const textStartTarget = typeof wordLayout?.textStartPx === "number" && Number.isFinite(wordLayout.textStartPx) ? wordLayout.textStartPx : void 0;
77597
+ const gutterWidth = typeof marker.gutterWidthPx === "number" && Number.isFinite(marker.gutterWidthPx) && marker.gutterWidthPx > 0 ? marker.gutterWidthPx : LIST_MARKER_GAP$1;
77598
+ const currentPosStandard = markerStartPos + markerWidthEffective;
77599
+ if (textStartTarget !== void 0) {
77600
+ const gap = Math.max(textStartTarget - currentPosStandard, gutterWidth);
77601
+ return currentPosStandard + gap;
77602
+ }
77487
77603
  const textStart = indentLeft + firstLine;
77488
- let tabWidth = textStart - currentPos;
77604
+ let tabWidth = textStart - currentPosStandard;
77489
77605
  if (tabWidth <= 0) {
77490
- tabWidth = DEFAULT_TAB_INTERVAL_PX$1 - currentPos % DEFAULT_TAB_INTERVAL_PX$1;
77606
+ tabWidth = gutterWidth;
77491
77607
  } else if (tabWidth < LIST_MARKER_GAP$1) {
77492
- tabWidth = LIST_MARKER_GAP$1;
77608
+ tabWidth = Math.max(tabWidth, gutterWidth);
77493
77609
  }
77494
- return markerStartPos + finalMarkerTextWidth + tabWidth;
77610
+ return currentPosStandard + tabWidth;
77495
77611
  }
77496
77612
  function getWordLayoutConfig(block) {
77497
77613
  if (!block || block.kind !== "paragraph") {
@@ -77520,21 +77636,45 @@ ${l}
77520
77636
  return hasHangingIndentPattern;
77521
77637
  }
77522
77638
  function calculateTextStartIndent(params2) {
77523
- const { isFirstLine, isListItem: isListItem2, markerWidth, paraIndentLeft, firstLineIndent, hangingIndent, wordLayout } = params2;
77639
+ const {
77640
+ isFirstLine,
77641
+ isListItem: isListItem2,
77642
+ markerWidth,
77643
+ markerTextWidth,
77644
+ paraIndentLeft,
77645
+ firstLineIndent,
77646
+ hangingIndent,
77647
+ wordLayout
77648
+ } = params2;
77524
77649
  const firstLineOffset = firstLineIndent - hangingIndent;
77525
- const isFirstLineIndentMode = wordLayout?.firstLineIndentMode === true;
77650
+ const effectiveMarkerTextWidth = typeof markerTextWidth === "number" && Number.isFinite(markerTextWidth) && markerTextWidth > 0 ? markerTextWidth : markerWidth;
77526
77651
  let indentAdjust = paraIndentLeft;
77527
- if (isListItem2 && isFirstLine && isFirstLineIndentMode) {
77652
+ if (isListItem2 && isFirstLine) {
77528
77653
  const resolvedTextStart = resolveListTextStartPx(
77529
77654
  wordLayout,
77530
77655
  paraIndentLeft,
77531
77656
  Math.max(firstLineIndent, 0),
77532
77657
  Math.max(hangingIndent, 0),
77533
- () => markerWidth
77534
- // Use provided markerWidth since we don't have canvas access here
77658
+ () => effectiveMarkerTextWidth
77659
+ // Use measured marker text width when available
77535
77660
  );
77536
- const textStartFallback = paraIndentLeft + Math.max(firstLineIndent, 0) + markerWidth;
77537
- indentAdjust = typeof resolvedTextStart === "number" && Number.isFinite(resolvedTextStart) ? resolvedTextStart : textStartFallback;
77661
+ if (typeof resolvedTextStart === "number" && Number.isFinite(resolvedTextStart)) {
77662
+ indentAdjust = resolvedTextStart;
77663
+ } else {
77664
+ const explicitTextStart = wordLayout?.marker?.textStartX ?? wordLayout?.textStartPx;
77665
+ const isStandardHangingList = hangingIndent > 0 && wordLayout?.firstLineIndentMode !== true;
77666
+ const textStartLooksValid = typeof explicitTextStart === "number" && Number.isFinite(explicitTextStart) && (!isStandardHangingList || explicitTextStart > paraIndentLeft);
77667
+ if (textStartLooksValid) {
77668
+ indentAdjust = explicitTextStart;
77669
+ } else if (wordLayout?.firstLineIndentMode === true) {
77670
+ indentAdjust = paraIndentLeft + Math.max(firstLineIndent, 0) + markerWidth;
77671
+ } else if (isStandardHangingList && effectiveMarkerTextWidth > 0) {
77672
+ const markerStartPos = Math.max(0, paraIndentLeft - hangingIndent + firstLineIndent);
77673
+ const gutterWidthCandidate = wordLayout?.gutterWidthPx;
77674
+ const gutterWidth = typeof gutterWidthCandidate === "number" && Number.isFinite(gutterWidthCandidate) ? gutterWidthCandidate : wordLayout?.marker?.gutterWidthPx ?? LIST_MARKER_GAP$1;
77675
+ indentAdjust = markerStartPos + effectiveMarkerTextWidth + gutterWidth;
77676
+ }
77677
+ }
77538
77678
  } else if (isFirstLine && !isListItem2) {
77539
77679
  indentAdjust += firstLineOffset;
77540
77680
  }
@@ -78385,12 +78525,16 @@ ${l}
78385
78525
  const negativeRightIndent = indentRight < 0 ? indentRight : 0;
78386
78526
  const remeasureWidth = Math.max(1, columnWidth - indentLeft - indentRight);
78387
78527
  let didRemeasureForColumnWidth = false;
78528
+ let remeasuredMarkerInfo;
78388
78529
  if (typeof remeasureParagraph2 === "function" && typeof measurementWidth === "number" && measurementWidth > remeasureWidth) {
78389
78530
  const firstLineIndent = calculateFirstLineIndent(block, measure);
78390
78531
  const newMeasure = remeasureParagraph2(block, columnWidth, firstLineIndent);
78391
78532
  const newLines = normalizeLines(newMeasure);
78392
78533
  lines = newLines;
78393
78534
  didRemeasureForColumnWidth = true;
78535
+ if (newMeasure.marker) {
78536
+ remeasuredMarkerInfo = newMeasure.marker;
78537
+ }
78394
78538
  }
78395
78539
  let fromLine = 0;
78396
78540
  const attrs = getParagraphAttrs(block);
@@ -78429,10 +78573,12 @@ ${l}
78429
78573
  width: fragmentWidth,
78430
78574
  ...computeFragmentPmRange(block, lines, 0, lines.length)
78431
78575
  };
78432
- if (measure.marker) {
78433
- fragment.markerWidth = measure.marker.markerWidth;
78434
- if (measure.marker.markerTextWidth != null) {
78435
- fragment.markerTextWidth = measure.marker.markerTextWidth;
78576
+ if (measure.marker || remeasuredMarkerInfo) {
78577
+ const effectiveMarkerInfo = remeasuredMarkerInfo ?? measure.marker;
78578
+ fragment.markerWidth = effectiveMarkerInfo?.markerWidth ?? measure.marker?.markerWidth ?? 0;
78579
+ const markerTextWidth = remeasuredMarkerInfo?.markerTextWidth ?? measure.marker?.markerTextWidth;
78580
+ if (markerTextWidth != null) {
78581
+ fragment.markerTextWidth = markerTextWidth;
78436
78582
  }
78437
78583
  }
78438
78584
  state.page.fragments.push(fragment);
@@ -78474,6 +78620,9 @@ ${l}
78474
78620
  const newLines = normalizeLines(newMeasure);
78475
78621
  lines = newLines;
78476
78622
  didRemeasureForFloats = true;
78623
+ if (newMeasure.marker) {
78624
+ remeasuredMarkerInfo = newMeasure.marker;
78625
+ }
78477
78626
  }
78478
78627
  }
78479
78628
  while (fromLine < lines.length) {
@@ -78545,13 +78694,16 @@ ${l}
78545
78694
  if (didRemeasureForColumnWidth) {
78546
78695
  fragment.lines = lines.slice(fromLine, slice.toLine);
78547
78696
  }
78548
- if (measure.marker && fromLine === 0) {
78549
- fragment.markerWidth = measure.marker.markerWidth;
78550
- if (measure.marker.markerTextWidth != null) {
78551
- fragment.markerTextWidth = measure.marker.markerTextWidth;
78697
+ if ((measure.marker || remeasuredMarkerInfo) && fromLine === 0) {
78698
+ const effectiveMarkerInfo = remeasuredMarkerInfo ?? measure.marker;
78699
+ fragment.markerWidth = effectiveMarkerInfo?.markerWidth ?? measure.marker?.markerWidth ?? 0;
78700
+ const markerTextWidth = remeasuredMarkerInfo?.markerTextWidth ?? measure.marker?.markerTextWidth;
78701
+ if (markerTextWidth != null) {
78702
+ fragment.markerTextWidth = markerTextWidth;
78552
78703
  }
78553
- if (measure.kind === "paragraph" && measure.marker?.gutterWidth != null) {
78554
- fragment.markerGutter = measure.marker.gutterWidth;
78704
+ const gutterWidth = remeasuredMarkerInfo?.gutterWidth ?? measure.marker?.gutterWidth;
78705
+ if (gutterWidth != null) {
78706
+ fragment.markerGutter = gutterWidth;
78555
78707
  }
78556
78708
  }
78557
78709
  if (fromLine > 0) fragment.continuesFromPrev = true;
@@ -81994,16 +82146,19 @@ ${l}
81994
82146
  const contentWidth = Math.max(1, maxWidth - indentLeft - indentRight);
81995
82147
  const markerTextStartX = wordLayout?.marker?.textStartX;
81996
82148
  const textStartPx = typeof markerTextStartX === "number" && Number.isFinite(markerTextStartX) ? markerTextStartX : typeof wordLayout?.textStartPx === "number" && Number.isFinite(wordLayout.textStartPx) ? wordLayout.textStartPx : void 0;
82149
+ let measuredMarkerTextWidth;
81997
82150
  const resolvedTextStartPx = resolveListTextStartPx(
81998
82151
  wordLayout,
81999
82152
  indentLeft,
82000
82153
  indentFirstLine,
82001
82154
  indentHanging,
82002
- (markerText, marker) => {
82155
+ (markerText, marker2) => {
82003
82156
  const context = getCtx();
82004
82157
  if (!context) return 0;
82005
- context.font = markerFontString(marker.run);
82006
- return context.measureText(markerText).width;
82158
+ context.font = markerFontString(marker2.run);
82159
+ const width = context.measureText(markerText).width;
82160
+ measuredMarkerTextWidth = width;
82161
+ return width;
82007
82162
  }
82008
82163
  );
82009
82164
  const effectiveTextStartPx = resolvedTextStartPx ?? textStartPx;
@@ -82094,7 +82249,14 @@ ${l}
82094
82249
  }
82095
82250
  }
82096
82251
  const totalHeight = lines.reduce((s2, l) => s2 + l.lineHeight, 0);
82097
- return { kind: "paragraph", lines, totalHeight };
82252
+ const marker = wordLayout?.marker;
82253
+ const markerInfo = marker ? {
82254
+ markerWidth: marker.markerBoxWidthPx ?? indentHanging ?? 0,
82255
+ markerTextWidth: measuredMarkerTextWidth ?? 0,
82256
+ indentLeft,
82257
+ gutterWidth: marker.gutterWidthPx
82258
+ } : void 0;
82259
+ return { kind: "paragraph", lines, totalHeight, marker: markerInfo };
82098
82260
  }
82099
82261
  function hasComments(run2) {
82100
82262
  return "comments" in run2 && Array.isArray(run2.comments) && run2.comments.length > 0;
@@ -84146,6 +84308,7 @@ ${l}
84146
84308
  isFirstLine,
84147
84309
  isListItem: isListItemFlag,
84148
84310
  markerWidth,
84311
+ markerTextWidth: fragment.markerTextWidth ?? measure.marker?.markerTextWidth ?? void 0,
84149
84312
  paraIndentLeft: indent2.left,
84150
84313
  firstLineIndent: indent2.firstLine,
84151
84314
  hangingIndent: indent2.hanging,
@@ -84283,6 +84446,7 @@ ${l}
84283
84446
  isFirstLine,
84284
84447
  isListItem: cellIsListItem,
84285
84448
  markerWidth: paragraphMarkerWidth,
84449
+ markerTextWidth: info.measure?.marker?.markerTextWidth ?? void 0,
84286
84450
  paraIndentLeft: cellIndent.left,
84287
84451
  firstLineIndent: cellIndent.firstLine,
84288
84452
  hangingIndent: cellIndent.hanging,
@@ -84534,25 +84698,36 @@ ${l}
84534
84698
  const range2 = computeLinePmRange(block, line);
84535
84699
  if (range2.pmStart == null || range2.pmEnd == null) return null;
84536
84700
  const result = findCharacterAtX(block, line, x2, range2.pmStart, availableWidthOverride, alignmentOverride);
84701
+ let pmPosition = result.pmPosition;
84537
84702
  if (isRTL) {
84538
84703
  const charOffset = result.charOffset;
84539
84704
  const charsInLine = Math.max(1, line.toChar - line.fromChar);
84540
84705
  const reversedOffset = Math.max(0, Math.min(charsInLine, charsInLine - charOffset));
84541
- return charOffsetToPm(block, line, reversedOffset, range2.pmStart);
84706
+ pmPosition = charOffsetToPm(block, line, reversedOffset, range2.pmStart);
84542
84707
  }
84543
- return result.pmPosition;
84708
+ return pmPosition;
84544
84709
  };
84545
84710
  const mapPmToX = (block, line, offset2, fragmentWidth, alignmentOverride) => {
84546
84711
  if (fragmentWidth <= 0 || line.width <= 0) return 0;
84547
84712
  let paraIndentLeft = 0;
84548
84713
  let paraIndentRight = 0;
84714
+ let effectiveLeft = 0;
84549
84715
  if (block.kind === "paragraph") {
84550
84716
  const indentLeft = typeof block.attrs?.indent?.left === "number" ? block.attrs.indent.left : 0;
84551
84717
  const indentRight = typeof block.attrs?.indent?.right === "number" ? block.attrs.indent.right : 0;
84552
84718
  paraIndentLeft = Number.isFinite(indentLeft) ? indentLeft : 0;
84553
84719
  paraIndentRight = Number.isFinite(indentRight) ? indentRight : 0;
84720
+ effectiveLeft = paraIndentLeft;
84721
+ const wl = getWordLayoutConfig(block);
84722
+ const isListParagraph = Boolean(block.attrs?.numberingProperties) || Boolean(wl?.marker);
84723
+ if (isListParagraph) {
84724
+ const explicitTextStart = typeof wl?.marker?.textStartX === "number" && Number.isFinite(wl.marker.textStartX) ? wl.marker.textStartX : typeof wl?.textStartPx === "number" && Number.isFinite(wl.textStartPx) ? wl.textStartPx : void 0;
84725
+ if (typeof explicitTextStart === "number" && explicitTextStart > paraIndentLeft) {
84726
+ effectiveLeft = explicitTextStart;
84727
+ }
84728
+ }
84554
84729
  }
84555
- const totalIndent = paraIndentLeft + paraIndentRight;
84730
+ const totalIndent = effectiveLeft + paraIndentRight;
84556
84731
  const availableWidth = Math.max(0, fragmentWidth - totalIndent);
84557
84732
  if (totalIndent > fragmentWidth) {
84558
84733
  console.warn(
@@ -85884,16 +86059,26 @@ ${l}
85884
86059
  }
85885
86060
  function computeCaretLayoutRectGeometry({ layout, blocks: blocks2, measures, painterHost, viewportHost, visibleHost, zoom }, pos, includeDomFallback = true) {
85886
86061
  if (!layout) return null;
85887
- const hit = getFragmentAtPosition(layout, blocks2, measures, pos);
86062
+ let effectivePos = pos;
86063
+ let hit = getFragmentAtPosition(layout, blocks2, measures, pos);
85888
86064
  if (!hit) {
85889
- return null;
86065
+ const fallbackCandidates = [pos - 1, pos + 1, pos - 2, pos + 2].filter((candidate) => candidate >= 0);
86066
+ for (const candidate of fallbackCandidates) {
86067
+ const fallbackHit = getFragmentAtPosition(layout, blocks2, measures, candidate);
86068
+ if (fallbackHit) {
86069
+ hit = fallbackHit;
86070
+ effectivePos = candidate;
86071
+ break;
86072
+ }
86073
+ }
86074
+ if (!hit) return null;
85890
86075
  }
85891
86076
  const block = hit.block;
85892
86077
  const measure = hit.measure;
85893
86078
  if (hit.fragment.kind === "table" && block?.kind === "table" && measure?.kind === "table") {
85894
86079
  return computeTableCaretLayoutRectFromDom(
85895
86080
  { viewportHost, visibleHost, zoom },
85896
- pos,
86081
+ effectivePos,
85897
86082
  hit.fragment,
85898
86083
  block,
85899
86084
  measure,
@@ -85901,92 +86086,32 @@ ${l}
85901
86086
  );
85902
86087
  }
85903
86088
  if (!block || block.kind !== "paragraph" || measure?.kind !== "paragraph") return null;
85904
- if (hit.fragment.kind !== "para") {
85905
- return null;
85906
- }
86089
+ if (hit.fragment.kind !== "para") return null;
85907
86090
  const fragment = hit.fragment;
85908
- const lineInfo = findLineContainingPos(block, measure, fragment.fromLine, fragment.toLine, pos);
85909
- if (!lineInfo) {
85910
- return null;
85911
- }
86091
+ const lineInfo = findLineContainingPos(block, measure, fragment.fromLine, fragment.toLine, effectivePos);
86092
+ if (!lineInfo) return null;
85912
86093
  const { line, index: index2 } = lineInfo;
85913
86094
  const range2 = computeLinePmRange(block, line);
85914
86095
  if (range2.pmStart == null || range2.pmEnd == null) return null;
85915
- const pmOffset = pmPosToCharOffset(block, line, pos);
86096
+ const pmOffset = pmPosToCharOffset(block, line, effectivePos);
85916
86097
  const markerWidth = fragment.markerWidth ?? measure.marker?.markerWidth ?? 0;
85917
- const indent2 = extractParagraphIndent(block.attrs?.indent);
85918
- const availableWidth = Math.max(0, fragment.width - (indent2.left + indent2.right));
85919
- const charX = measureCharacterX(block, line, pmOffset, availableWidth);
86098
+ const markerTextWidth = fragment.markerTextWidth ?? measure.marker?.markerTextWidth ?? void 0;
85920
86099
  const isFirstLine = index2 === fragment.fromLine;
85921
86100
  const isListItemFlag = isListItem(markerWidth, block);
85922
- const isListFirstLine = isFirstLine && !fragment.continuesFromPrev && isListItemFlag;
85923
86101
  const wordLayout = getWordLayoutConfig(block);
85924
- const isFirstLineIndentMode = wordLayout?.firstLineIndentMode === true;
85925
- if (isListFirstLine && isFirstLineIndentMode) {
85926
- const textStartPx = calculateTextStartIndent({
85927
- isFirstLine,
85928
- isListItem: isListItemFlag,
85929
- markerWidth,
85930
- paraIndentLeft: indent2.left,
85931
- firstLineIndent: indent2.firstLine,
85932
- hangingIndent: indent2.hanging,
85933
- wordLayout
85934
- });
85935
- const localX2 = fragment.x + textStartPx + charX;
85936
- const lineOffset2 = lineHeightBeforeIndex(measure.lines, fragment.fromLine, index2);
85937
- const localY2 = fragment.y + lineOffset2;
85938
- const result2 = {
85939
- pageIndex: hit.pageIndex,
85940
- x: localX2,
85941
- y: localY2,
85942
- height: line.lineHeight
85943
- };
85944
- const pageEl2 = painterHost?.querySelector(
85945
- `.superdoc-page[data-page-index="${hit.pageIndex}"]`
85946
- );
85947
- const pageRect2 = pageEl2?.getBoundingClientRect();
85948
- let domCaretX2 = null;
85949
- let domCaretY2 = null;
85950
- const spanEls2 = pageEl2?.querySelectorAll("span[data-pm-start][data-pm-end]");
85951
- for (const spanEl of Array.from(spanEls2 ?? [])) {
85952
- const pmStart = Number(spanEl.dataset.pmStart);
85953
- const pmEnd = Number(spanEl.dataset.pmEnd);
85954
- if (pos >= pmStart && pos <= pmEnd && spanEl.firstChild?.nodeType === Node.TEXT_NODE) {
85955
- const textNode = spanEl.firstChild;
85956
- const charIndex = Math.min(pos - pmStart, textNode.length);
85957
- const rangeObj = document.createRange();
85958
- rangeObj.setStart(textNode, charIndex);
85959
- rangeObj.setEnd(textNode, charIndex);
85960
- if (typeof rangeObj.getBoundingClientRect !== "function") {
85961
- break;
85962
- }
85963
- const rangeRect = rangeObj.getBoundingClientRect();
85964
- if (pageRect2) {
85965
- domCaretX2 = (rangeRect.left - pageRect2.left) / zoom;
85966
- domCaretY2 = (rangeRect.top - pageRect2.top) / zoom;
85967
- }
85968
- break;
85969
- }
85970
- }
85971
- if (includeDomFallback && domCaretX2 != null && domCaretY2 != null) {
85972
- return {
85973
- pageIndex: hit.pageIndex,
85974
- x: domCaretX2,
85975
- y: domCaretY2,
85976
- height: line.lineHeight
85977
- };
85978
- }
85979
- return result2;
85980
- }
86102
+ const indent2 = extractParagraphIndent(block.attrs?.indent);
85981
86103
  const indentAdjust = calculateTextStartIndent({
85982
86104
  isFirstLine,
85983
86105
  isListItem: isListItemFlag,
85984
86106
  markerWidth,
86107
+ markerTextWidth,
85985
86108
  paraIndentLeft: indent2.left,
85986
86109
  firstLineIndent: indent2.firstLine,
85987
86110
  hangingIndent: indent2.hanging,
85988
86111
  wordLayout
85989
86112
  });
86113
+ const availableWidth = Math.max(0, fragment.width - (indentAdjust + indent2.right));
86114
+ const charX = measureCharacterX(block, line, pmOffset, availableWidth);
85990
86115
  const localX = fragment.x + indentAdjust + charX;
85991
86116
  const lineOffset = lineHeightBeforeIndex(measure.lines, fragment.fromLine, index2);
85992
86117
  const localY = fragment.y + lineOffset;
@@ -86004,9 +86129,9 @@ ${l}
86004
86129
  for (const spanEl of Array.from(spanEls ?? [])) {
86005
86130
  const pmStart = Number(spanEl.dataset.pmStart);
86006
86131
  const pmEnd = Number(spanEl.dataset.pmEnd);
86007
- if (pos >= pmStart && pos <= pmEnd && spanEl.firstChild?.nodeType === Node.TEXT_NODE) {
86132
+ if (effectivePos >= pmStart && effectivePos <= pmEnd && spanEl.firstChild?.nodeType === Node.TEXT_NODE) {
86008
86133
  const textNode = spanEl.firstChild;
86009
- const charIndex = Math.min(pos - pmStart, textNode.length);
86134
+ const charIndex = Math.min(effectivePos - pmStart, textNode.length);
86010
86135
  const rangeObj = document.createRange();
86011
86136
  rangeObj.setStart(textNode, charIndex);
86012
86137
  rangeObj.setEnd(textNode, charIndex);
@@ -87066,6 +87191,13 @@ ${l}
87066
87191
  );
87067
87192
  }
87068
87193
  });
87194
+ if ((config2.mode === "original" || config2.mode === "final") && config2.enabled) {
87195
+ filtered.forEach((run2) => {
87196
+ if (isTextRun$1(run2) && run2.trackedChange && (run2.trackedChange.kind === "insert" || run2.trackedChange.kind === "delete")) {
87197
+ delete run2.trackedChange;
87198
+ }
87199
+ });
87200
+ }
87069
87201
  }
87070
87202
  return filtered;
87071
87203
  };
@@ -90091,7 +90223,16 @@ ${l}
90091
90223
  if (!value || typeof value !== "object") return;
90092
90224
  return normalizePxIndent(value) ?? convertIndentTwipsToPx(value);
90093
90225
  };
90094
- const normalizedIndent = normalizeIndentObject(attrs.indent) ?? convertIndentTwipsToPx(paragraphProps.indent) ?? convertIndentTwipsToPx(hydrated?.indent) ?? normalizeParagraphIndent(attrs.textIndent);
90226
+ const hydratedIndentPx = convertIndentTwipsToPx(hydrated?.indent);
90227
+ const paragraphIndentPx = convertIndentTwipsToPx(paragraphProps.indent);
90228
+ const textIndentPx = normalizeParagraphIndent(attrs.textIndent);
90229
+ const attrsIndentPx = normalizeIndentObject(attrs.indent);
90230
+ const indentChain = [];
90231
+ if (hydratedIndentPx) indentChain.push({ indent: hydratedIndentPx });
90232
+ if (paragraphIndentPx) indentChain.push({ indent: paragraphIndentPx });
90233
+ if (textIndentPx) indentChain.push({ indent: textIndentPx });
90234
+ if (attrsIndentPx) indentChain.push({ indent: attrsIndentPx });
90235
+ const normalizedIndent = indentChain.length ? combineIndentProperties(indentChain).indent : void 0;
90095
90236
  const unwrapTabStops = (tabStops) => {
90096
90237
  if (!Array.isArray(tabStops)) {
90097
90238
  return void 0;
@@ -95370,10 +95511,13 @@ ${l}
95370
95511
  };
95371
95512
  }
95372
95513
  const originX = currentLine.width;
95373
- const { target, nextIndex, stop } = getNextTabStopPx(currentLine.width, tabStops, tabStopCursor);
95514
+ const effectiveIndent = lines.length === 0 ? indentLeft + rawFirstLineOffset : indentLeft;
95515
+ const absCurrentX = currentLine.width + effectiveIndent;
95516
+ const { target, nextIndex, stop } = getNextTabStopPx(absCurrentX, tabStops, tabStopCursor);
95374
95517
  tabStopCursor = nextIndex;
95375
- const clampedTarget = Math.min(target, currentLine.maxWidth);
95376
- const tabAdvance = Math.max(0, clampedTarget - currentLine.width);
95518
+ const maxAbsWidth = currentLine.maxWidth + effectiveIndent;
95519
+ const clampedTarget = Math.min(target, maxAbsWidth);
95520
+ const tabAdvance = Math.max(0, clampedTarget - absCurrentX);
95377
95521
  currentLine.width = roundValue(currentLine.width + tabAdvance);
95378
95522
  run2.width = tabAdvance;
95379
95523
  currentLine.maxFontSize = Math.max(currentLine.maxFontSize, 12);
@@ -95381,8 +95525,9 @@ ${l}
95381
95525
  currentLine.toChar = 1;
95382
95526
  if (stop && stop.leader && stop.leader !== "none") {
95383
95527
  const leaderStyle = stop.leader;
95384
- const from2 = Math.min(originX, clampedTarget);
95385
- const to = Math.max(originX, clampedTarget);
95528
+ const relativeTarget = clampedTarget - effectiveIndent;
95529
+ const from2 = Math.min(originX, relativeTarget);
95530
+ const to = Math.max(originX, relativeTarget);
95386
95531
  if (!currentLine.leaders) currentLine.leaders = [];
95387
95532
  currentLine.leaders.push({ from: from2, to, style: leaderStyle });
95388
95533
  }
@@ -95391,27 +95536,28 @@ ${l}
95391
95536
  if (stop.val === "end" || stop.val === "center" || stop.val === "decimal") {
95392
95537
  const groupMeasure = measureTabAlignmentGroup(runIndex + 1, runsToProcess, ctx2, decimalSeparator);
95393
95538
  if (groupMeasure.totalWidth > 0) {
95539
+ const relativeTarget = clampedTarget - effectiveIndent;
95394
95540
  let groupStartX;
95395
95541
  if (stop.val === "end") {
95396
- groupStartX = Math.max(0, clampedTarget - groupMeasure.totalWidth);
95542
+ groupStartX = Math.max(0, relativeTarget - groupMeasure.totalWidth);
95397
95543
  } else if (stop.val === "center") {
95398
- groupStartX = Math.max(0, clampedTarget - groupMeasure.totalWidth / 2);
95544
+ groupStartX = Math.max(0, relativeTarget - groupMeasure.totalWidth / 2);
95399
95545
  } else {
95400
95546
  const beforeDecimal = groupMeasure.beforeDecimalWidth ?? groupMeasure.totalWidth;
95401
- groupStartX = Math.max(0, clampedTarget - beforeDecimal);
95547
+ groupStartX = Math.max(0, relativeTarget - beforeDecimal);
95402
95548
  }
95403
95549
  activeTabGroup = {
95404
95550
  measure: groupMeasure,
95405
95551
  startX: groupStartX,
95406
95552
  currentX: groupStartX,
95407
- target: clampedTarget,
95553
+ target: relativeTarget,
95408
95554
  val: stop.val
95409
95555
  };
95410
95556
  currentLine.width = roundValue(groupStartX);
95411
95557
  }
95412
95558
  pendingTabAlignment = null;
95413
95559
  } else {
95414
- pendingTabAlignment = { target: clampedTarget, val: stop.val };
95560
+ pendingTabAlignment = { target: clampedTarget - effectiveIndent, val: stop.val };
95415
95561
  }
95416
95562
  } else {
95417
95563
  pendingTabAlignment = null;
@@ -96052,10 +96198,13 @@ ${l}
96052
96198
  };
96053
96199
  }
96054
96200
  const originX = currentLine.width;
96055
- const { target, nextIndex, stop } = getNextTabStopPx(currentLine.width, tabStops, tabStopCursor);
96201
+ const effectiveIndent = lines.length === 0 ? indentLeft + rawFirstLineOffset : indentLeft;
96202
+ const absCurrentX = currentLine.width + effectiveIndent;
96203
+ const { target, nextIndex, stop } = getNextTabStopPx(absCurrentX, tabStops, tabStopCursor);
96056
96204
  tabStopCursor = nextIndex;
96057
- const clampedTarget = Math.min(target, currentLine.maxWidth);
96058
- const tabAdvance = Math.max(0, clampedTarget - currentLine.width);
96205
+ const maxAbsWidth = currentLine.maxWidth + effectiveIndent;
96206
+ const clampedTarget = Math.min(target, maxAbsWidth);
96207
+ const tabAdvance = Math.max(0, clampedTarget - absCurrentX);
96059
96208
  currentLine.width = roundValue(currentLine.width + tabAdvance);
96060
96209
  currentLine.maxFontInfo = updateMaxFontInfo(currentLine.maxFontSize, currentLine.maxFontInfo, run2);
96061
96210
  currentLine.maxFontSize = Math.max(currentLine.maxFontSize, run2.fontSize);
@@ -96064,14 +96213,15 @@ ${l}
96064
96213
  charPosInRun += 1;
96065
96214
  if (stop) {
96066
96215
  validateTabStopVal(stop);
96067
- pendingTabAlignment = { target: clampedTarget, val: stop.val };
96216
+ pendingTabAlignment = { target: clampedTarget - effectiveIndent, val: stop.val };
96068
96217
  } else {
96069
96218
  pendingTabAlignment = null;
96070
96219
  }
96071
96220
  if (stop && stop.leader && stop.leader !== "none" && stop.leader !== "middleDot") {
96072
96221
  const leaderStyle = stop.leader;
96073
- const from2 = Math.min(originX, clampedTarget);
96074
- const to = Math.max(originX, clampedTarget);
96222
+ const relativeTarget = clampedTarget - effectiveIndent;
96223
+ const from2 = Math.min(originX, relativeTarget);
96224
+ const to = Math.max(originX, relativeTarget);
96075
96225
  if (!currentLine.leaders) currentLine.leaders = [];
96076
96226
  currentLine.leaders.push({ from: from2, to, style: leaderStyle });
96077
96227
  }
@@ -96347,7 +96497,11 @@ ${l}
96347
96497
  }
96348
96498
  async function measureImageBlock(block, constraints) {
96349
96499
  const intrinsic = getIntrinsicImageSize(block, constraints.maxWidth);
96350
- const maxWidth = constraints.maxWidth > 0 ? constraints.maxWidth : intrinsic.width;
96500
+ const isBlockBehindDoc = block.anchor?.behindDoc;
96501
+ const isBlockWrapBehindDoc = block.wrap?.type === "None" && block.wrap?.behindDoc;
96502
+ const bypassWidthConstraint = isBlockBehindDoc || isBlockWrapBehindDoc;
96503
+ const isWidthConstraintBypassed = bypassWidthConstraint || constraints.maxWidth <= 0;
96504
+ const maxWidth = isWidthConstraintBypassed ? intrinsic.width : constraints.maxWidth;
96351
96505
  const hasNegativeVerticalPosition = block.anchor?.isAnchored && (typeof block.anchor?.offsetV === "number" && block.anchor.offsetV < 0 || typeof block.margin?.top === "number" && block.margin.top < 0);
96352
96506
  const maxHeight = hasNegativeVerticalPosition || !constraints.maxHeight || constraints.maxHeight <= 0 ? Infinity : constraints.maxHeight;
96353
96507
  const widthScale = maxWidth / intrinsic.width;
@@ -97514,9 +97668,10 @@ ${l}
97514
97668
  throw new TypeError("[PresentationEditor] setTrackedChangesOverrides expects an object or undefined");
97515
97669
  }
97516
97670
  if (overrides !== void 0) {
97517
- if (overrides.mode !== void 0 && !["review", "simple", "original"].includes(overrides.mode)) {
97671
+ const validModes = ["review", "original", "final", "off"];
97672
+ if (overrides.mode !== void 0 && !validModes.includes(overrides.mode)) {
97518
97673
  throw new TypeError(
97519
- `[PresentationEditor] Invalid tracked changes mode "${overrides.mode}". Must be one of: review, simple, original`
97674
+ `[PresentationEditor] Invalid tracked changes mode "${overrides.mode}". Must be one of: ${validModes.join(", ")}`
97520
97675
  );
97521
97676
  }
97522
97677
  if (overrides.enabled !== void 0 && typeof overrides.enabled !== "boolean") {
@@ -99128,7 +99283,12 @@ ${l}
99128
99283
  }
99129
99284
  if (!handledByDepth) {
99130
99285
  try {
99131
- const tr = this.#editor.state.tr.setSelection(TextSelection$1.create(this.#editor.state.doc, hit.pos));
99286
+ const doc22 = this.#editor.state.doc;
99287
+ let nextSelection = TextSelection$1.create(doc22, hit.pos);
99288
+ if (!nextSelection.$from.parent.inlineContent) {
99289
+ nextSelection = Selection.near(doc22.resolve(hit.pos), 1);
99290
+ }
99291
+ const tr = this.#editor.state.tr.setSelection(nextSelection);
99132
99292
  this.#editor.view?.dispatch(tr);
99133
99293
  } catch {
99134
99294
  }
@@ -100106,6 +100266,7 @@ ${l}
100106
100266
  if (!layout) {
100107
100267
  return;
100108
100268
  }
100269
+ const { from: from2, to } = selection;
100109
100270
  const docEpoch = this.#epochMapper.getCurrentEpoch();
100110
100271
  if (this.#layoutEpoch < docEpoch) {
100111
100272
  return;
@@ -100120,7 +100281,6 @@ ${l}
100120
100281
  }
100121
100282
  return;
100122
100283
  }
100123
- const { from: from2, to } = selection;
100124
100284
  if (from2 === to) {
100125
100285
  const caretLayout = this.#computeCaretLayoutRect(from2);
100126
100286
  if (!caretLayout) {
@@ -101423,7 +101583,7 @@ ${l}
101423
101583
  const zoom = this.#layoutOptions.zoom ?? 1;
101424
101584
  const layoutMode = this.#layoutOptions.layoutMode ?? "vertical";
101425
101585
  const pages = this.#layoutState.layout?.pages;
101426
- const pageGap = this.#layoutState.layout?.pageGap ?? this.#getEffectivePageGap();
101586
+ const pageGap = this.#getEffectivePageGap();
101427
101587
  const defaultWidth = this.#layoutOptions.pageSize?.w ?? DEFAULT_PAGE_SIZE.w;
101428
101588
  const defaultHeight = this.#layoutOptions.pageSize?.h ?? DEFAULT_PAGE_SIZE.h;
101429
101589
  let maxWidth = defaultWidth;
@@ -104531,7 +104691,11 @@ ${l}
104531
104691
  */
104532
104692
  clearDocument: () => ({ commands: commands2 }) => {
104533
104693
  return commands2.setContent("<p></p>");
104534
- }
104694
+ },
104695
+ /**
104696
+ * Set section page margins (top/right/bottom/left) for the section at the current selection.
104697
+ */
104698
+ setSectionPageMarginsAtSelection
104535
104699
  };
104536
104700
  }
104537
104701
  });
@@ -104703,6 +104867,28 @@ ${l}
104703
104867
  }
104704
104868
  return markDefs;
104705
104869
  };
104870
+ const normalizeSelectionIntoRun = (tr, runType) => {
104871
+ const selection = tr.selection;
104872
+ if (!(selection instanceof TextSelection$1)) return;
104873
+ if (selection.from !== selection.to) return;
104874
+ const $pos = tr.doc.resolve(selection.from);
104875
+ if ($pos.parent.type === runType) return;
104876
+ const nodeAfter = $pos.nodeAfter;
104877
+ if (nodeAfter?.type === runType && nodeAfter.content.size > 0) {
104878
+ const nextPos = selection.from + 1;
104879
+ if (nextPos <= tr.doc.content.size) {
104880
+ tr.setSelection(TextSelection$1.create(tr.doc, nextPos));
104881
+ }
104882
+ return;
104883
+ }
104884
+ const nodeBefore = $pos.nodeBefore;
104885
+ if (nodeBefore?.type === runType && nodeBefore.content.size > 0) {
104886
+ const prevPos = selection.from - 1;
104887
+ if (prevPos >= 0) {
104888
+ tr.setSelection(TextSelection$1.create(tr.doc, prevPos));
104889
+ }
104890
+ }
104891
+ };
104706
104892
  const buildWrapTransaction = (state, ranges, runType, editor, markDefsFromMeta = []) => {
104707
104893
  if (!ranges.length) return null;
104708
104894
  const replacements = [];
@@ -104736,6 +104922,7 @@ ${l}
104736
104922
  if (!replacements.length) return null;
104737
104923
  const tr = state.tr;
104738
104924
  replacements.sort((a2, b2) => b2.from - a2.from).forEach(({ from: from2, to, runNode }) => tr.replaceWith(from2, to, runNode));
104925
+ normalizeSelectionIntoRun(tr, runType);
104739
104926
  return tr.docChanged ? tr : null;
104740
104927
  };
104741
104928
  const wrapTextInRunsPlugin = (editor) => {
@@ -105185,12 +105372,18 @@ ${l}
105185
105372
  return null;
105186
105373
  }
105187
105374
  function extractParagraphContext(node2, startPos, helpers2, depth = 0) {
105188
- const paragraphProperties = getResolvedParagraphProperties(node2) ?? {};
105375
+ const paragraphProperties = getResolvedParagraphProperties(node2) ?? node2.attrs?.paragraphProperties ?? {};
105189
105376
  const alignmentAliases = { left: "start", right: "end" };
105190
105377
  let tabStops = [];
105191
105378
  if (Array.isArray(paragraphProperties.tabStops)) {
105192
105379
  tabStops = paragraphProperties.tabStops.map((stop) => {
105193
105380
  const ref2 = stop?.tab;
105381
+ if (!ref2 && stop?.pos != null) {
105382
+ return {
105383
+ ...stop,
105384
+ pos: twipsToPixels(Number(stop.pos) || 0)
105385
+ };
105386
+ }
105194
105387
  if (!ref2) return stop || null;
105195
105388
  const rawType = ref2.tabType || "start";
105196
105389
  const mappedVal = alignmentAliases[rawType] || rawType;
@@ -106456,6 +106649,13 @@ ${l}
106456
106649
  pos: entry.pos,
106457
106650
  nodeSize: node2.nodeSize
106458
106651
  });
106652
+ } else if (node2.type.name === "lineBreak" || node2.type.name === "hardBreak") {
106653
+ spans.push({
106654
+ type: node2.type.name,
106655
+ spanId,
106656
+ pos: entry.pos,
106657
+ nodeSize: node2.nodeSize
106658
+ });
106459
106659
  } else if (node2.type.name === "text") {
106460
106660
  spans.push({
106461
106661
  type: "text",
@@ -106505,6 +106705,7 @@ ${l}
106505
106705
  paragraphNode
106506
106706
  } = request;
106507
106707
  const tabs = {};
106708
+ const leftIndentPx = request.indents?.left ?? 0;
106508
106709
  let currentX = indentWidth;
106509
106710
  const measureText2 = (span) => {
106510
106711
  if (view && typeof span.from === "number" && typeof span.to === "number") {
@@ -106517,6 +106718,8 @@ ${l}
106517
106718
  const span = spans[i2];
106518
106719
  if (span.type === "text") {
106519
106720
  currentX += measureText2(span);
106721
+ } else if (span.type === "lineBreak" || span.type === "hardBreak") {
106722
+ currentX = leftIndentPx;
106520
106723
  } else if (span.type === "tab") {
106521
106724
  const followingText = collectFollowingText(spans, i2 + 1);
106522
106725
  let measureTextCallback;
@@ -106612,7 +106815,7 @@ ${l}
106612
106815
  let text2 = "";
106613
106816
  for (let i2 = startIndex; i2 < spans.length; i2++) {
106614
106817
  const span = spans[i2];
106615
- if (span.type === "tab") break;
106818
+ if (span.type === "tab" || span.type === "lineBreak" || span.type === "hardBreak") break;
106616
106819
  if (span.type === "text") text2 += span.text || "";
106617
106820
  }
106618
106821
  return text2;
@@ -106622,7 +106825,7 @@ ${l}
106622
106825
  let to = null;
106623
106826
  for (let i2 = startIndex; i2 < spans.length; i2++) {
106624
106827
  const span = spans[i2];
106625
- if (span.type === "tab") break;
106828
+ if (span.type === "tab" || span.type === "lineBreak" || span.type === "hardBreak") break;
106626
106829
  if (span.type === "text" && typeof span.from === "number" && typeof span.to === "number") {
106627
106830
  if (from2 === null) from2 = span.from;
106628
106831
  to = span.to;
@@ -111040,6 +111243,10 @@ ${l}
111040
111243
  }
111041
111244
  const hasAnchorData = Boolean(anchorData);
111042
111245
  const hasMarginOffsets = marginOffset?.horizontal != null || marginOffset?.top != null;
111246
+ const isWrapBehindDoc = wrap2?.attrs?.behindDoc;
111247
+ const isAnchorBehindDoc = anchorData?.behindDoc;
111248
+ const isBehindDocAnchor = wrap2?.type === "None" && (isWrapBehindDoc || isAnchorBehindDoc);
111249
+ const isAbsolutelyPositioned = style2.includes("position: absolute;");
111043
111250
  if (hasAnchorData) {
111044
111251
  switch (anchorData.hRelativeFrom) {
111045
111252
  case "page":
@@ -111067,7 +111274,6 @@ ${l}
111067
111274
  style2 += "float: left;";
111068
111275
  }
111069
111276
  } else if (!anchorData.alignH && marginOffset?.horizontal != null) {
111070
- const isAbsolutelyPositioned = style2.includes("position: absolute;");
111071
111277
  if (isAbsolutelyPositioned) {
111072
111278
  style2 += `left: ${baseHorizontal}px;`;
111073
111279
  style2 += "max-width: none;";
@@ -111081,7 +111287,8 @@ ${l}
111081
111287
  const relativeFromPageV = anchorData?.vRelativeFrom === "page";
111082
111288
  const relativeFromMarginV = anchorData?.vRelativeFrom === "margin";
111083
111289
  const maxMarginV = 500;
111084
- const baseTop = Math.max(0, marginOffset?.top ?? 0);
111290
+ const allowNegativeTopOffset = isBehindDocAnchor;
111291
+ const baseTop = allowNegativeTopOffset ? marginOffset?.top ?? 0 : Math.max(0, marginOffset?.top ?? 0);
111085
111292
  let rotationHorizontal = 0;
111086
111293
  let rotationTop = 0;
111087
111294
  const { rotation: rotation2 } = transformData ?? {};
@@ -111100,7 +111307,10 @@ ${l}
111100
111307
  margin.left += horizontal;
111101
111308
  }
111102
111309
  }
111103
- if (top2 && !relativeFromMarginV) {
111310
+ const appliedTopViaStyle = isAbsolutelyPositioned && allowNegativeTopOffset && !relativeFromMarginV;
111311
+ if (appliedTopViaStyle) {
111312
+ style2 += `top: ${top2}px;`;
111313
+ } else if (top2 && !relativeFromMarginV) {
111104
111314
  if (relativeFromPageV && top2 >= maxMarginV) margin.top += maxMarginV;
111105
111315
  else margin.top += top2;
111106
111316
  }
@@ -111113,6 +111323,9 @@ ${l}
111113
111323
  }
111114
111324
  if (margin.top) style2 += `margin-top: ${margin.top}px;`;
111115
111325
  if (margin.bottom) style2 += `margin-bottom: ${margin.bottom}px;`;
111326
+ if (isBehindDocAnchor) {
111327
+ style2 += "max-width: none;";
111328
+ }
111116
111329
  const finalAttributes = { ...htmlAttributes };
111117
111330
  if (style2) {
111118
111331
  const existingStyle = finalAttributes.style || "";
@@ -119658,6 +119871,7 @@ ${l}
119658
119871
  const parentItem = ref(null);
119659
119872
  const iconColor = ref(options.iconColor);
119660
119873
  const hasCaret = ref(options.hasCaret);
119874
+ const restoreEditorFocus = Boolean(options.restoreEditorFocus);
119661
119875
  const dropdownStyles = ref(options.dropdownStyles);
119662
119876
  const tooltip = ref(options.tooltip);
119663
119877
  const tooltipVisible = ref(options.tooltipVisible);
@@ -119733,6 +119947,7 @@ ${l}
119733
119947
  hideLabel,
119734
119948
  inlineTextInputVisible,
119735
119949
  hasInlineTextInput,
119950
+ restoreEditorFocus,
119736
119951
  markName,
119737
119952
  labelAttr,
119738
119953
  childItem,
@@ -122046,6 +122261,7 @@ ${l}
122046
122261
  command: "toggleBulletList",
122047
122262
  icon: toolbarIcons2.bulletList,
122048
122263
  tooltip: toolbarTexts2.bulletList,
122264
+ restoreEditorFocus: true,
122049
122265
  attributes: {
122050
122266
  ariaLabel: "Bullet list"
122051
122267
  }
@@ -122056,6 +122272,7 @@ ${l}
122056
122272
  command: "toggleOrderedList",
122057
122273
  icon: toolbarIcons2.numberedList,
122058
122274
  tooltip: toolbarTexts2.numberedList,
122275
+ restoreEditorFocus: true,
122059
122276
  attributes: {
122060
122277
  ariaLabel: "Numbered list"
122061
122278
  }
@@ -125601,7 +125818,7 @@ ${style2}
125601
125818
  };
125602
125819
  return ResizeObserverController2;
125603
125820
  })();
125604
- var ResizeObserver = (function() {
125821
+ var ResizeObserver$1 = (function() {
125605
125822
  function ResizeObserver2(callback) {
125606
125823
  if (arguments.length === 0) {
125607
125824
  throw new TypeError("Failed to construct 'ResizeObserver': 1 argument required, but only 0 present.");
@@ -125640,7 +125857,7 @@ ${style2}
125640
125857
  class ResizeObserverDelegate {
125641
125858
  constructor() {
125642
125859
  this.handleResize = this.handleResize.bind(this);
125643
- this.observer = new (typeof window !== "undefined" && window.ResizeObserver || ResizeObserver)(this.handleResize);
125860
+ this.observer = new (typeof window !== "undefined" && window.ResizeObserver || ResizeObserver$1)(this.handleResize);
125644
125861
  this.elHandlersMap = /* @__PURE__ */ new Map();
125645
125862
  }
125646
125863
  handleResize(entries) {
@@ -134955,6 +135172,7 @@ ${style2}
134955
135172
  selectionUpdate: null,
134956
135173
  focus: null
134957
135174
  };
135175
+ this._restoreFocusTimeoutId = null;
134958
135176
  if (!this.config.selector && this.config.element) {
134959
135177
  this.config.selector = this.config.element;
134960
135178
  }
@@ -135620,6 +135838,7 @@ ${style2}
135620
135838
  const wasFocused = Boolean(typeof hasFocusFn === "function" && hasFocusFn.call(this.activeEditor.view));
135621
135839
  const { command: command2 } = item;
135622
135840
  const isMarkToggle = this.isMarkToggle(item);
135841
+ const shouldRestoreFocus = Boolean(item?.restoreEditorFocus);
135623
135842
  if (!wasFocused && isMarkToggle) {
135624
135843
  this.pendingMarkCommands.push({ command: command2, argument, item });
135625
135844
  item?.activate?.();
@@ -135650,6 +135869,13 @@ ${style2}
135650
135869
  }
135651
135870
  if (isMarkToggle) this.#syncStickyMarksFromState();
135652
135871
  this.updateToolbarState();
135872
+ if (shouldRestoreFocus && this.activeEditor && !this.activeEditor.options.isHeaderOrFooter) {
135873
+ this._restoreFocusTimeoutId = setTimeout(() => {
135874
+ this._restoreFocusTimeoutId = null;
135875
+ if (!this.activeEditor || this.activeEditor.options.isHeaderOrFooter) return;
135876
+ this.activeEditor.focus();
135877
+ }, 0);
135878
+ }
135653
135879
  }
135654
135880
  /**
135655
135881
  * Processes and executes pending mark commands when editor selection updates.
@@ -135792,6 +136018,17 @@ ${style2}
135792
136018
  const tr = state.tr.setStoredMarks([mark2]);
135793
136019
  view.dispatch(tr);
135794
136020
  }
136021
+ /**
136022
+ * Cleans up resources when the toolbar is destroyed.
136023
+ * Clears any pending timeouts to prevent callbacks firing after unmount.
136024
+ * @returns {void}
136025
+ */
136026
+ destroy() {
136027
+ if (this._restoreFocusTimeoutId !== null) {
136028
+ clearTimeout(this._restoreFocusTimeoutId);
136029
+ this._restoreFocusTimeoutId = null;
136030
+ }
136031
+ }
135795
136032
  }
135796
136033
  async function createZip(blobs, fileNames) {
135797
136034
  const zip = new JSZip();
@@ -138553,6 +138790,31 @@ ${style2}
138553
138790
  },
138554
138791
  { immediate: true, deep: true }
138555
138792
  );
138793
+ watch(
138794
+ () => props.options?.rulerContainer,
138795
+ () => {
138796
+ nextTick(() => {
138797
+ syncRulerOffset();
138798
+ setupRulerObservers();
138799
+ });
138800
+ },
138801
+ { immediate: true }
138802
+ );
138803
+ watch(
138804
+ rulersVisible,
138805
+ (visible) => {
138806
+ nextTick(() => {
138807
+ if (visible) {
138808
+ syncRulerOffset();
138809
+ setupRulerObservers();
138810
+ } else {
138811
+ rulerHostStyle.value = {};
138812
+ cleanupRulerObservers();
138813
+ }
138814
+ });
138815
+ },
138816
+ { immediate: true }
138817
+ );
138556
138818
  const containerStyle = computed(() => {
138557
138819
  let maxWidth = 8.5 * 96;
138558
138820
  const ed = editor.value;
@@ -138577,6 +138839,71 @@ ${style2}
138577
138839
  minWidth: `${scaledWidth}px`
138578
138840
  };
138579
138841
  });
138842
+ const rulerHostStyle = ref({});
138843
+ const rulerContainerEl = ref(null);
138844
+ let editorResizeObserver = null;
138845
+ let rulerContainerResizeObserver = null;
138846
+ let layoutUpdatedHandler = null;
138847
+ const resolveRulerContainer = () => {
138848
+ const container = props.options?.rulerContainer;
138849
+ if (!container) return null;
138850
+ if (typeof container === "string") {
138851
+ const doc2 = editorWrapper.value?.ownerDocument ?? document;
138852
+ return doc2.querySelector(container);
138853
+ }
138854
+ return container instanceof HTMLElement ? container : null;
138855
+ };
138856
+ const getViewportRect2 = () => {
138857
+ const host = editorWrapper.value;
138858
+ if (!host) return null;
138859
+ const viewport2 = host.querySelector(".presentation-editor__viewport");
138860
+ const target = viewport2 ?? host;
138861
+ return target.getBoundingClientRect();
138862
+ };
138863
+ const syncRulerOffset = () => {
138864
+ if (!rulersVisible.value) {
138865
+ rulerHostStyle.value = {};
138866
+ return;
138867
+ }
138868
+ rulerContainerEl.value = resolveRulerContainer();
138869
+ if (!rulerContainerEl.value) {
138870
+ rulerHostStyle.value = {};
138871
+ return;
138872
+ }
138873
+ const viewportRect = getViewportRect2();
138874
+ if (!viewportRect) return;
138875
+ const hostRect = rulerContainerEl.value.getBoundingClientRect();
138876
+ const paddingLeft = Math.max(0, viewportRect.left - hostRect.left);
138877
+ const paddingRight = Math.max(0, hostRect.right - viewportRect.right);
138878
+ rulerHostStyle.value = {
138879
+ paddingLeft: `${paddingLeft}px`,
138880
+ paddingRight: `${paddingRight}px`
138881
+ };
138882
+ };
138883
+ const cleanupRulerObservers = () => {
138884
+ if (editorResizeObserver) {
138885
+ editorResizeObserver.disconnect();
138886
+ editorResizeObserver = null;
138887
+ }
138888
+ if (rulerContainerResizeObserver) {
138889
+ rulerContainerResizeObserver.disconnect();
138890
+ rulerContainerResizeObserver = null;
138891
+ }
138892
+ };
138893
+ const setupRulerObservers = () => {
138894
+ cleanupRulerObservers();
138895
+ if (typeof ResizeObserver === "undefined") return;
138896
+ const viewportHost = editorWrapper.value;
138897
+ const rulerHost = resolveRulerContainer();
138898
+ if (viewportHost) {
138899
+ editorResizeObserver = new ResizeObserver(() => syncRulerOffset());
138900
+ editorResizeObserver.observe(viewportHost);
138901
+ }
138902
+ if (rulerHost) {
138903
+ rulerContainerResizeObserver = new ResizeObserver(() => syncRulerOffset());
138904
+ rulerContainerResizeObserver.observe(rulerHost);
138905
+ }
138906
+ };
138580
138907
  const message = useMessage();
138581
138908
  const editorWrapper = ref(null);
138582
138909
  const editorElem = ref(null);
@@ -138888,7 +139215,7 @@ ${style2}
138888
139215
  presentationEditor.on("imageDeselected", () => {
138889
139216
  clearSelectedImage();
138890
139217
  });
138891
- presentationEditor.on("layoutUpdated", () => {
139218
+ layoutUpdatedHandler = () => {
138892
139219
  if (imageResizeState.visible && imageResizeState.blockId) {
138893
139220
  const escapedBlockId = CSS.escape(imageResizeState.blockId);
138894
139221
  const newElement = editorElem.value?.querySelector(
@@ -138921,13 +139248,17 @@ ${style2}
138921
139248
  clearSelectedImage();
138922
139249
  }
138923
139250
  }
138924
- });
139251
+ nextTick(() => syncRulerOffset());
139252
+ };
139253
+ presentationEditor.on("layoutUpdated", layoutUpdatedHandler);
138925
139254
  zoomChangeHandler = ({ zoom }) => {
138926
139255
  currentZoom.value = zoom;
139256
+ nextTick(() => syncRulerOffset());
138927
139257
  };
138928
139258
  presentationEditor.on("zoomChange", zoomChangeHandler);
138929
139259
  if (typeof presentationEditor.zoom === "number") {
138930
139260
  currentZoom.value = presentationEditor.zoom;
139261
+ nextTick(() => syncRulerOffset());
138931
139262
  }
138932
139263
  }
138933
139264
  editor.value.on("paginationUpdate", () => {
@@ -138987,6 +139318,11 @@ ${style2}
138987
139318
  onMounted(() => {
138988
139319
  initializeData();
138989
139320
  if (props.options?.suppressSkeletonLoader || !props.options?.collaborationProvider) editorReady.value = true;
139321
+ window.addEventListener("resize", syncRulerOffset, { passive: true });
139322
+ nextTick(() => {
139323
+ syncRulerOffset();
139324
+ setupRulerObservers();
139325
+ });
138990
139326
  });
138991
139327
  const handleMarginClick = (event) => {
138992
139328
  if (event.button !== 0) {
@@ -139001,10 +139337,14 @@ ${style2}
139001
139337
  const handleMarginChange = ({ side, value }) => {
139002
139338
  const base2 = activeEditor.value;
139003
139339
  if (!base2) return;
139004
- const pageStyles2 = base2.getPageStyles();
139005
- const { pageMargins } = pageStyles2;
139006
- const update = { ...pageMargins, [side]: value };
139007
- base2?.updatePageStyle({ pageMargins: update });
139340
+ const payload = side === "left" ? { leftInches: value } : side === "right" ? { rightInches: value } : side === "top" ? { topInches: value } : side === "bottom" ? { bottomInches: value } : {};
139341
+ const didUpdateSection = typeof base2.commands?.setSectionPageMarginsAtSelection === "function" ? base2.commands.setSectionPageMarginsAtSelection(payload) : false;
139342
+ if (!didUpdateSection) {
139343
+ const pageStyles2 = base2.getPageStyles();
139344
+ const { pageMargins } = pageStyles2;
139345
+ const update = { ...pageMargins, [side]: value };
139346
+ base2?.updatePageStyle({ pageMargins: update });
139347
+ }
139008
139348
  };
139009
139349
  onBeforeUnmount(() => {
139010
139350
  stopPolling();
@@ -139013,6 +139353,12 @@ ${style2}
139013
139353
  editor.value.off("zoomChange", zoomChangeHandler);
139014
139354
  zoomChangeHandler = null;
139015
139355
  }
139356
+ if (editor.value instanceof PresentationEditor && layoutUpdatedHandler) {
139357
+ editor.value.off("layoutUpdated", layoutUpdatedHandler);
139358
+ layoutUpdatedHandler = null;
139359
+ }
139360
+ cleanupRulerObservers();
139361
+ window.removeEventListener("resize", syncRulerOffset);
139016
139362
  editor.value?.destroy();
139017
139363
  editor.value = null;
139018
139364
  });
@@ -139024,18 +139370,28 @@ ${style2}
139024
139370
  __props.options.rulerContainer && rulersVisible.value && !!activeEditor.value ? (openBlock(), createBlock(Teleport, {
139025
139371
  key: 0,
139026
139372
  to: __props.options.rulerContainer
139373
+ }, [
139374
+ createBaseVNode("div", {
139375
+ class: "ruler-host",
139376
+ style: normalizeStyle(rulerHostStyle.value)
139377
+ }, [
139378
+ createVNode(Ruler, {
139379
+ class: "ruler superdoc-ruler",
139380
+ editor: activeEditor.value,
139381
+ onMarginChange: handleMarginChange
139382
+ }, null, 8, ["editor"])
139383
+ ], 4)
139384
+ ], 8, ["to"])) : rulersVisible.value && !!activeEditor.value ? (openBlock(), createElementBlock("div", {
139385
+ key: 1,
139386
+ class: "ruler-host",
139387
+ style: normalizeStyle(rulerHostStyle.value)
139027
139388
  }, [
139028
139389
  createVNode(Ruler, {
139029
- class: "ruler superdoc-ruler",
139390
+ class: "ruler",
139030
139391
  editor: activeEditor.value,
139031
139392
  onMarginChange: handleMarginChange
139032
139393
  }, null, 8, ["editor"])
139033
- ], 8, ["to"])) : rulersVisible.value && !!activeEditor.value ? (openBlock(), createBlock(Ruler, {
139034
- key: 1,
139035
- class: "ruler",
139036
- editor: activeEditor.value,
139037
- onMarginChange: handleMarginChange
139038
- }, null, 8, ["editor"])) : createCommentVNode("", true),
139394
+ ], 4)) : createCommentVNode("", true),
139039
139395
  createBaseVNode("div", {
139040
139396
  class: "super-editor",
139041
139397
  ref_key: "editorWrapper",
@@ -139140,7 +139496,7 @@ ${style2}
139140
139496
  };
139141
139497
  }
139142
139498
  });
139143
- const SuperEditor = /* @__PURE__ */ _export_sfc(_sfc_main$j, [["__scopeId", "data-v-8dd4cf59"]]);
139499
+ const SuperEditor = /* @__PURE__ */ _export_sfc(_sfc_main$j, [["__scopeId", "data-v-f5c4f915"]]);
139144
139500
  const _hoisted_1$h = ["innerHTML"];
139145
139501
  const _sfc_main$i = {
139146
139502
  __name: "SuperInput",
@@ -143313,6 +143669,7 @@ ${reason}`);
143313
143669
  commentsStore.proxy = proxy;
143314
143670
  const { isHighContrastMode: isHighContrastMode2 } = useHighContrastMode();
143315
143671
  const { uiFontFamily } = useUiFontFamily();
143672
+ const isViewingMode = () => proxy?.$superdoc?.config?.documentMode === "viewing";
143316
143673
  const commentsModuleConfig = computed(() => {
143317
143674
  const config2 = modules.comments;
143318
143675
  if (config2 === false || config2 == null) return null;
@@ -143407,6 +143764,10 @@ ${reason}`);
143407
143764
  const commentsConfig = proxy.$superdoc.config.modules?.comments;
143408
143765
  if (!commentsConfig || commentsConfig === false) return;
143409
143766
  if (!positions || Object.keys(positions).length === 0) return;
143767
+ if (isViewingMode()) {
143768
+ commentsStore.clearEditorCommentPositions?.();
143769
+ return;
143770
+ }
143410
143771
  const mappedPositions = presentationEditor.getCommentBounds(positions, layers.value);
143411
143772
  handleEditorLocationsUpdate(mappedPositions);
143412
143773
  });
@@ -143426,6 +143787,13 @@ ${reason}`);
143426
143787
  const onEditorSelectionChange = ({ editor, transaction }) => {
143427
143788
  if (skipSelectionUpdate.value) {
143428
143789
  skipSelectionUpdate.value = false;
143790
+ if (isViewingMode()) {
143791
+ resetSelection();
143792
+ }
143793
+ return;
143794
+ }
143795
+ if (isViewingMode()) {
143796
+ resetSelection();
143429
143797
  return;
143430
143798
  }
143431
143799
  const { documentId } = editor.options;
@@ -143604,6 +143972,10 @@ ${reason}`);
143604
143972
  const onEditorCommentLocationsUpdate = (doc2, { allCommentIds: activeThreadId, allCommentPositions } = {}) => {
143605
143973
  const commentsConfig = proxy.$superdoc.config.modules?.comments;
143606
143974
  if (!commentsConfig || commentsConfig === false) return;
143975
+ if (isViewingMode()) {
143976
+ commentsStore.clearEditorCommentPositions?.();
143977
+ return;
143978
+ }
143607
143979
  const presentation = PresentationEditor.getInstance(doc2.id);
143608
143980
  if (!presentation) {
143609
143981
  handleEditorLocationsUpdate(allCommentPositions, activeThreadId);
@@ -143659,11 +144031,12 @@ ${reason}`);
143659
144031
  };
143660
144032
  const isCommentsEnabled = computed(() => Boolean(commentsModuleConfig.value));
143661
144033
  const showCommentsSidebar = computed(() => {
144034
+ if (isViewingMode()) return false;
143662
144035
  return pendingComment.value || getFloatingComments.value?.length > 0 && isReady.value && layers.value && isCommentsEnabled.value && !isCommentsListVisible.value;
143663
144036
  });
143664
144037
  const showToolsFloatingMenu = computed(() => {
143665
144038
  if (!isCommentsEnabled.value) return false;
143666
- return toolsMenuPosition.top && !getConfig2.value?.readOnly;
144039
+ return selectionPosition.value && toolsMenuPosition.top && !getConfig2.value?.readOnly;
143667
144040
  });
143668
144041
  computed(() => {
143669
144042
  if (!isCommentsEnabled.value) return false;
@@ -143711,6 +144084,10 @@ ${reason}`);
143711
144084
  return style2;
143712
144085
  });
143713
144086
  const handleSelectionChange = (selection) => {
144087
+ if (isViewingMode()) {
144088
+ resetSelection();
144089
+ return;
144090
+ }
143714
144091
  if (!selection.selectionBounds || !isCommentsEnabled.value) return;
143715
144092
  resetSelection();
143716
144093
  const isMobileView = window.matchMedia("(max-width: 768px)").matches;
@@ -143736,12 +144113,14 @@ ${reason}`);
143736
144113
  };
143737
144114
  const resetSelection = () => {
143738
144115
  selectionPosition.value = null;
144116
+ toolsMenuPosition.top = null;
143739
144117
  };
143740
144118
  const updateSelection2 = ({ startX, startY, x: x2, y: y2, source }) => {
143741
144119
  const hasStartCoords = typeof startX === "number" || typeof startY === "number";
143742
144120
  const hasEndCoords = typeof x2 === "number" || typeof y2 === "number";
143743
144121
  if (!hasStartCoords && !hasEndCoords) {
143744
- return selectionPosition.value = null;
144122
+ resetSelection();
144123
+ return;
143745
144124
  }
143746
144125
  if (!selectionPosition.value) {
143747
144126
  if (startY == null || startX == null) return;
@@ -143994,7 +144373,7 @@ ${reason}`);
143994
144373
  };
143995
144374
  }
143996
144375
  };
143997
- const App = /* @__PURE__ */ _export_sfc(_sfc_main$1, [["__scopeId", "data-v-1e96f708"]]);
144376
+ const App = /* @__PURE__ */ _export_sfc(_sfc_main$1, [["__scopeId", "data-v-5196811d"]]);
143998
144377
  const createSuperdocVueApp = () => {
143999
144378
  const app = createApp(App);
144000
144379
  const pinia = createPinia();
@@ -144178,7 +144557,7 @@ ${reason}`);
144178
144557
  this.config.colors = shuffleArray(this.config.colors);
144179
144558
  this.userColorMap = /* @__PURE__ */ new Map();
144180
144559
  this.colorIndex = 0;
144181
- this.version = "1.3.0-next.9";
144560
+ this.version = "1.3.1-next.1";
144182
144561
  this.#log("🦋 [superdoc] Using SuperDoc version:", this.version);
144183
144562
  this.superdocId = config2.superdocId || v4();
144184
144563
  this.colors = this.config.colors;