@pixldocs/canvas-renderer 0.5.152 → 0.5.153

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.
@@ -5744,14 +5744,23 @@ function recolorSvgFills(svg, color) {
5744
5744
  return _recolorSvgFills(svg, color);
5745
5745
  }
5746
5746
  function bakeTextSvgToFabricLineStarts(svg, obj, w) {
5747
- var _a, _b, _c;
5747
+ var _a, _b, _c, _d;
5748
5748
  try {
5749
5749
  const lines = (obj == null ? void 0 : obj._textLines) ?? [];
5750
5750
  if (!Array.isArray(lines) || lines.length === 0) return svg;
5751
+ const rawAlign = String((obj == null ? void 0 : obj.textAlign) || "left").toLowerCase();
5752
+ const alignmentAnchor = /right|end/.test(rawAlign) ? "end" : /center/.test(rawAlign) ? "middle" : "start";
5753
+ const hasStyledChars = (() => {
5754
+ const styles = obj == null ? void 0 : obj.styles;
5755
+ if (!styles || typeof styles !== "object") return false;
5756
+ return Object.values(styles).some((line) => line && typeof line === "object" && Object.keys(line).length > 0);
5757
+ })();
5758
+ const canUseAlignmentAnchor = alignmentAnchor !== "start" && !hasStyledChars && !(obj == null ? void 0 : obj.path) && !Number((obj == null ? void 0 : obj.charSpacing) ?? 0);
5751
5759
  const halfW = w / 2;
5752
- const lineXs = [];
5760
+ const lineAnchors = [];
5753
5761
  for (let i = 0; i < lines.length; i++) {
5754
5762
  let lineLeft = 0;
5763
+ let lineW = 0;
5755
5764
  let firstGlyphAdjust = 0;
5756
5765
  try {
5757
5766
  lineLeft = ((_a = obj._getLineLeftOffset) == null ? void 0 : _a.call(obj, i)) ?? 0;
@@ -5759,7 +5768,12 @@ function bakeTextSvgToFabricLineStarts(svg, obj, w) {
5759
5768
  lineLeft = 0;
5760
5769
  }
5761
5770
  try {
5762
- const firstBox = (_c = (_b = obj.__charBounds) == null ? void 0 : _b[i]) == null ? void 0 : _c[0];
5771
+ lineW = ((_b = obj.getLineWidth) == null ? void 0 : _b.call(obj, i)) ?? 0;
5772
+ } catch {
5773
+ lineW = 0;
5774
+ }
5775
+ try {
5776
+ const firstBox = (_d = (_c = obj.__charBounds) == null ? void 0 : _c[i]) == null ? void 0 : _d[0];
5763
5777
  const kerned = Number(firstBox == null ? void 0 : firstBox.kernedWidth);
5764
5778
  const glyphW = Number(firstBox == null ? void 0 : firstBox.width);
5765
5779
  if (Number.isFinite(kerned) && Number.isFinite(glyphW)) {
@@ -5768,9 +5782,18 @@ function bakeTextSvgToFabricLineStarts(svg, obj, w) {
5768
5782
  } catch {
5769
5783
  firstGlyphAdjust = 0;
5770
5784
  }
5771
- lineXs.push(
5772
- -halfW + (Number.isFinite(lineLeft) ? lineLeft : 0) + (Number.isFinite(firstGlyphAdjust) ? firstGlyphAdjust : 0)
5773
- );
5785
+ const baseStart = -halfW + (Number.isFinite(lineLeft) ? lineLeft : 0);
5786
+ if (canUseAlignmentAnchor && Number.isFinite(lineW) && lineW > 0) {
5787
+ lineAnchors.push({
5788
+ x: alignmentAnchor === "end" ? baseStart + lineW : baseStart + lineW / 2,
5789
+ anchor: alignmentAnchor
5790
+ });
5791
+ } else {
5792
+ lineAnchors.push({
5793
+ x: baseStart + (Number.isFinite(firstGlyphAdjust) ? firstGlyphAdjust : 0),
5794
+ anchor: "start"
5795
+ });
5796
+ }
5774
5797
  }
5775
5798
  const textOpenRe = /<text\b([^>]*)>/i;
5776
5799
  const textOpenMatch = svg.match(textOpenRe);
@@ -5786,6 +5809,10 @@ function bakeTextSvgToFabricLineStarts(svg, obj, w) {
5786
5809
  (_m, pre, val, post) => pre + val.replace(/text-align\s*:\s*[^;"']+;?/gi, "").trim() + post
5787
5810
  );
5788
5811
  const newTextOpen = `<text${textAttrs}>`;
5812
+ const stripAnchorAttrs = (attrs) => attrs.replace(/\s+text-anchor\s*=\s*"[^"]*"/gi, "").replace(
5813
+ /(\sstyle=")([^"]*)(")/i,
5814
+ (_m, pre, val, post) => pre + val.replace(/text-anchor\s*:\s*[^;"']+;?/gi, "").trim() + post
5815
+ );
5789
5816
  let lineIdx = 0;
5790
5817
  let lastY = "";
5791
5818
  const newSvg = svg.replace(textOpenMatch[0], newTextOpen).replace(
@@ -5794,13 +5821,15 @@ function bakeTextSvgToFabricLineStarts(svg, obj, w) {
5794
5821
  const attrs = `${pre} ${post}`;
5795
5822
  const yMatch = attrs.match(/\sy\s*=\s*"([^"]*)"/i);
5796
5823
  const y = (yMatch == null ? void 0 : yMatch[1]) ?? "";
5797
- const isLineStart = y !== "" ? y !== lastY : lineIdx < lineXs.length;
5824
+ const isLineStart = y !== "" ? y !== lastY : lineIdx < lineAnchors.length;
5798
5825
  if (!isLineStart) return _m;
5799
5826
  if (y !== "") lastY = y;
5800
- const x = lineXs[lineIdx];
5827
+ const lineAnchor = lineAnchors[lineIdx];
5801
5828
  lineIdx += 1;
5802
- if (typeof x !== "number" || !Number.isFinite(x)) return _m;
5803
- return `<tspan${pre} x="${x.toFixed(3)}"${post}>`;
5829
+ if (!lineAnchor || typeof lineAnchor.x !== "number" || !Number.isFinite(lineAnchor.x)) return _m;
5830
+ const cleanPre = stripAnchorAttrs(pre);
5831
+ const cleanPost = stripAnchorAttrs(post);
5832
+ return `<tspan${cleanPre} x="${lineAnchor.x.toFixed(3)}" text-anchor="${lineAnchor.anchor}" data-pd-line-anchor="1"${cleanPost}>`;
5804
5833
  }
5805
5834
  );
5806
5835
  return newSvg;
@@ -16029,9 +16058,9 @@ function captureFabricCanvasSvgForPdf(fabricInstance, canvasWidth, canvasHeight)
16029
16058
  }
16030
16059
  return svgString;
16031
16060
  }
16032
- const resolvedPackageVersion = "0.5.152";
16061
+ const resolvedPackageVersion = "0.5.153";
16033
16062
  const PACKAGE_VERSION = resolvedPackageVersion;
16034
- const DEPLOYMENT_VERSION_MARKER = "__PIXLDOCS_CANVAS_RENDERER_VERSION__:0.5.152";
16063
+ const DEPLOYMENT_VERSION_MARKER = "__PIXLDOCS_CANVAS_RENDERER_VERSION__:0.5.153";
16035
16064
  const roundParityValue = (value) => {
16036
16065
  if (typeof value !== "number") return value;
16037
16066
  return Number.isFinite(value) ? Number(value.toFixed(3)) : value;
@@ -16466,7 +16495,7 @@ class PixldocsRenderer {
16466
16495
  await this.waitForCanvasScene(container, cloned, i);
16467
16496
  }
16468
16497
  console.log(`[canvas-renderer][pdf-unified] mounted ${cloned.pages.length} page(s), handing off to client exportMultiPagePdf`);
16469
- const { exportMultiPagePdf, preparePagesForExport } = await import("./vectorPdfExport-RiNowoiG.js");
16498
+ const { exportMultiPagePdf, preparePagesForExport } = await import("./vectorPdfExport-DTssH1-U.js");
16470
16499
  const prepared = preparePagesForExport(
16471
16500
  cloned.pages,
16472
16501
  canvasWidth,
@@ -18568,7 +18597,7 @@ async function prepareLiveCanvasSvgForPdf(rawSvg, pageWidth, pageHeight, pageKey
18568
18597
  if (options == null ? void 0 : options.stripPageBackground) stripRootPageBackgroundFromSvg(svgToDraw);
18569
18598
  sanitizeSvgTreeForPdf(svgToDraw);
18570
18599
  try {
18571
- const { bakeTextAnchorPositionsFromLiveSvg, logTextMeasurementDiagnostic } = await import("./vectorPdfExport-RiNowoiG.js");
18600
+ const { bakeTextAnchorPositionsFromLiveSvg, logTextMeasurementDiagnostic } = await import("./vectorPdfExport-DTssH1-U.js");
18572
18601
  try {
18573
18602
  await logTextMeasurementDiagnostic(svgToDraw);
18574
18603
  } catch {
@@ -18703,7 +18732,7 @@ async function assemblePdfFromSvgs(svgResults, options = {}) {
18703
18732
  }
18704
18733
  if (shouldOutlineText) {
18705
18734
  try {
18706
- const { convertAllTextToPath } = await import("./svgTextToPath-BE8TxgiO.js");
18735
+ const { convertAllTextToPath } = await import("./svgTextToPath-BXAzwaaR.js");
18707
18736
  pageSvg = await convertAllTextToPath(pageSvg, fontBaseUrl, { mode: outlineSubMode });
18708
18737
  try {
18709
18738
  dumpSvgTextDiagnostics(pageSvg, i, PARITY_TAG, "STAGE-1b-after-text-to-path-raw");
@@ -18918,4 +18947,4 @@ export {
18918
18947
  collectFontDescriptorsFromConfig as y,
18919
18948
  collectFontsFromConfig as z
18920
18949
  };
18921
- //# sourceMappingURL=index-DjobDQ7X.js.map
18950
+ //# sourceMappingURL=index-CAH9akzI.js.map