@pixldocs/canvas-renderer 0.5.63 → 0.5.65

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -12561,7 +12561,7 @@ function PixldocsPreview(props) {
12561
12561
  !canvasSettled && /* @__PURE__ */ jsxRuntime.jsx("div", { style: { position: "absolute", inset: 0, display: "flex", alignItems: "center", justifyContent: "center", minHeight: 200 }, children: /* @__PURE__ */ jsxRuntime.jsx("div", { style: { color: "#888", fontSize: 14 }, children: "Loading preview..." }) })
12562
12562
  ] });
12563
12563
  }
12564
- const PACKAGE_VERSION = "0.5.63";
12564
+ const PACKAGE_VERSION = "0.5.65";
12565
12565
  let __underlineFixInstalled = false;
12566
12566
  function installUnderlineFix(fab) {
12567
12567
  var _a;
@@ -13291,7 +13291,7 @@ class PixldocsRenderer {
13291
13291
  }, 3e4);
13292
13292
  let root = null;
13293
13293
  let mountKey = 0;
13294
- let didAutoShrinkParityRemount = false;
13294
+ let didPreviewParityRemount = false;
13295
13295
  const cleanup = () => {
13296
13296
  clearTimeout(timeout);
13297
13297
  try {
@@ -13300,8 +13300,23 @@ class PixldocsRenderer {
13300
13300
  }
13301
13301
  container.remove();
13302
13302
  };
13303
- const remountForAutoShrinkParity = async () => {
13304
- didAutoShrinkParityRemount = true;
13303
+ const mountPreview = (readyHandler) => {
13304
+ root = client.createRoot(container);
13305
+ root.render(
13306
+ react.createElement(PreviewCanvas2, {
13307
+ key: `svg-capture-${mountKey}`,
13308
+ config,
13309
+ pageIndex,
13310
+ zoom: 1,
13311
+ absoluteZoom: true,
13312
+ skipFontReadyWait: false,
13313
+ onReady: readyHandler
13314
+ })
13315
+ );
13316
+ };
13317
+ const remountForPreviewParity = async () => {
13318
+ if (didPreviewParityRemount) return;
13319
+ didPreviewParityRemount = true;
13305
13320
  mountKey += 1;
13306
13321
  try {
13307
13322
  clearMeasurementCache();
@@ -13315,9 +13330,8 @@ class PixldocsRenderer {
13315
13330
  root == null ? void 0 : root.unmount();
13316
13331
  } catch {
13317
13332
  }
13318
- root = client.createRoot(container);
13319
13333
  await new Promise((settle) => {
13320
- const onReadyOnce = () => {
13334
+ mountPreview(() => {
13321
13335
  this.waitForCanvasScene(container, config, pageIndex).then(async () => {
13322
13336
  const expectedImageCount = this.getExpectedImageCount(config, pageIndex);
13323
13337
  await this.waitForCanvasImages(container, expectedImageCount);
@@ -13325,18 +13339,7 @@ class PixldocsRenderer {
13325
13339
  await this.waitForCanvasScene(container, config, pageIndex);
13326
13340
  settle();
13327
13341
  }).catch(() => settle());
13328
- };
13329
- root.render(
13330
- react.createElement(PreviewCanvas2, {
13331
- key: `svg-auto-shrink-remount-${mountKey}`,
13332
- config,
13333
- pageIndex,
13334
- zoom: 1,
13335
- absoluteZoom: true,
13336
- skipFontReadyWait: false,
13337
- onReady: onReadyOnce
13338
- })
13339
- );
13342
+ });
13340
13343
  });
13341
13344
  };
13342
13345
  const onReady = () => {
@@ -13347,9 +13350,9 @@ class PixldocsRenderer {
13347
13350
  await this.waitForCanvasImages(container, expectedImageCount);
13348
13351
  await this.waitForStableTextMetrics(container, config);
13349
13352
  await this.waitForCanvasScene(container, config, pageIndex);
13350
- if (hasAutoShrink && !didAutoShrinkParityRemount) {
13351
- console.log("[canvas-renderer][svg-parity] remounting auto-shrink text before PDF SVG capture");
13352
- await remountForAutoShrinkParity();
13353
+ if (hasAutoShrink && !didPreviewParityRemount) {
13354
+ console.log("[canvas-renderer][svg-parity] remounting once to match PixldocsPreview auto-shrink stabilization");
13355
+ await remountForPreviewParity();
13353
13356
  }
13354
13357
  const fabricInstance = this.getFabricCanvasFromContainer(container);
13355
13358
  if (!fabricInstance) {
@@ -13369,7 +13372,6 @@ class PixldocsRenderer {
13369
13372
  { width: canvasWidth, height: canvasHeight },
13370
13373
  { cssOnly: false, backstoreOnly: false }
13371
13374
  );
13372
- this.resyncTextMetricsForSvgExport(fabricInstance);
13373
13375
  const rawSvgString = fabricInstance.toSVG();
13374
13376
  const svgString = this.normalizeSvgDimensions(
13375
13377
  rawSvgString,
@@ -13400,18 +13402,7 @@ class PixldocsRenderer {
13400
13402
  }
13401
13403
  });
13402
13404
  };
13403
- root = client.createRoot(container);
13404
- root.render(
13405
- react.createElement(PreviewCanvas2, {
13406
- config,
13407
- pageIndex,
13408
- zoom: 1,
13409
- // 1:1 — no UI scaling for SVG capture
13410
- absoluteZoom: true,
13411
- skipFontReadyWait: false,
13412
- onReady
13413
- })
13414
- );
13405
+ mountPreview(onReady);
13415
13406
  });
13416
13407
  }
13417
13408
  /**
@@ -13480,59 +13471,6 @@ class PixldocsRenderer {
13480
13471
  }
13481
13472
  return null;
13482
13473
  }
13483
- resyncTextMetricsForSvgExport(fabricInstance) {
13484
- if (typeof document === "undefined" || !(fabricInstance == null ? void 0 : fabricInstance.getObjects)) return;
13485
- const ctx = document.createElement("canvas").getContext("2d");
13486
- if (!ctx) return;
13487
- const syncTextbox = (textbox) => {
13488
- const tb = textbox;
13489
- const rawLines = tb._textLines ?? textbox.textLines ?? [];
13490
- if (!Array.isArray(rawLines) || rawLines.length === 0) return;
13491
- const nextCharBounds = [];
13492
- const nextLineWidths = [];
13493
- rawLines.forEach((rawLine, lineIndex) => {
13494
- const graphemes = Array.isArray(rawLine) ? rawLine.map((part) => String(part ?? "")) : Array.from(String(rawLine ?? ""));
13495
- const bounds = [];
13496
- let left = 0;
13497
- graphemes.forEach((grapheme, charIndex) => {
13498
- var _a, _b, _c, _d, _e, _f;
13499
- const fontSize = Number(((_a = tb.getValueOfPropertyAt) == null ? void 0 : _a.call(tb, lineIndex, charIndex, "fontSize")) ?? textbox.fontSize ?? 16);
13500
- const fontStyle = String(((_b = tb.getValueOfPropertyAt) == null ? void 0 : _b.call(tb, lineIndex, charIndex, "fontStyle")) ?? textbox.fontStyle ?? "normal");
13501
- const fontWeight = String(((_c = tb.getValueOfPropertyAt) == null ? void 0 : _c.call(tb, lineIndex, charIndex, "fontWeight")) ?? textbox.fontWeight ?? "400");
13502
- const fontFamily = String(((_d = tb.getValueOfPropertyAt) == null ? void 0 : _d.call(tb, lineIndex, charIndex, "fontFamily")) ?? textbox.fontFamily ?? "sans-serif");
13503
- const charSpacing = Number(((_e = tb.getValueOfPropertyAt) == null ? void 0 : _e.call(tb, lineIndex, charIndex, "charSpacing")) ?? textbox.charSpacing ?? 0);
13504
- const deltaY = Number(((_f = tb.getValueOfPropertyAt) == null ? void 0 : _f.call(tb, lineIndex, charIndex, "deltaY")) ?? 0);
13505
- ctx.font = `${fontStyle} normal ${fontWeight} ${fontSize}px ${fontFamily}`;
13506
- const charWidth = Math.max(0, ctx.measureText(grapheme).width);
13507
- let kernedWidth = charWidth;
13508
- const previous = charIndex > 0 ? graphemes[charIndex - 1] : "";
13509
- if (previous) {
13510
- const pairWidth = ctx.measureText(previous + grapheme).width;
13511
- const previousWidth = ctx.measureText(previous).width;
13512
- if (Number.isFinite(pairWidth) && Number.isFinite(previousWidth)) {
13513
- kernedWidth = Math.max(0, pairWidth - previousWidth);
13514
- }
13515
- }
13516
- if (charIndex < graphemes.length - 1 && charSpacing) {
13517
- kernedWidth += charSpacing / 1e3 * fontSize;
13518
- }
13519
- bounds[charIndex] = { left, width: charWidth, kernedWidth, height: fontSize, deltaY };
13520
- left += kernedWidth;
13521
- });
13522
- bounds[graphemes.length] = { left, width: 0, kernedWidth: 0, height: Number(textbox.fontSize ?? 16), deltaY: 0 };
13523
- nextCharBounds[lineIndex] = bounds;
13524
- nextLineWidths[lineIndex] = Math.max(0, left);
13525
- });
13526
- tb.__charBounds = nextCharBounds;
13527
- tb.__lineWidths = nextLineWidths;
13528
- textbox.dirty = true;
13529
- };
13530
- const visit = (obj) => {
13531
- if (obj instanceof fabric__namespace.Textbox) syncTextbox(obj);
13532
- else if (obj instanceof fabric__namespace.Group) obj.getObjects().forEach(visit);
13533
- };
13534
- fabricInstance.getObjects().forEach(visit);
13535
- }
13536
13474
  async waitForStableTextMetrics(container, config) {
13537
13475
  var _a, _b, _c;
13538
13476
  if (typeof document !== "undefined") {