@pixldocs/canvas-renderer 0.5.493 → 0.5.494

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.
@@ -2059,12 +2059,17 @@ const useEditorStore = zustand.create((set, get) => ({
2059
2059
  toggleElementLock: (id) => set((state) => {
2060
2060
  const currentPage = getCurrentPageFromCanvas(state.canvas);
2061
2061
  const node = findNodeById(currentPage.children, id);
2062
- if (!node || isGroup(node)) return {};
2062
+ if (!node) return {};
2063
+ const wasLocked = !!node.locked || node.selectable === false;
2064
+ const nextLocked = !wasLocked;
2063
2065
  const nextCanvas = updateCurrentPageChildren(
2064
2066
  state.canvas,
2065
2067
  (children) => updateNodeInTree(children, id, {
2066
- selectable: !node.selectable,
2067
- evented: !node.evented
2068
+ locked: nextLocked,
2069
+ // Keep legacy selectable/evented in sync with the canonical flag so
2070
+ // fabricObjectCreators (which also honors selectable === false)
2071
+ // stays consistent for elements loaded from older configs.
2072
+ ...isGroup(node) ? {} : { selectable: !nextLocked, evented: !nextLocked }
2068
2073
  })
2069
2074
  );
2070
2075
  const committed = commitFromState(state, nextCanvas);
@@ -12247,7 +12252,7 @@ const PageCanvas = react.forwardRef(
12247
12252
  var _a2;
12248
12253
  const fc = fabricRef.current;
12249
12254
  const groupId = snapshot == null ? void 0 : snapshot.groupSelectionId;
12250
- if (!fc || !groupId || snapshot.memberIds.length < 2 || editingTextIdRef.current) return;
12255
+ if (!fc || !snapshot || snapshot.memberIds.length < 2 || editingTextIdRef.current) return;
12251
12256
  const members = snapshot.memberIds.map((id) => fc.getObjects().find((o) => getObjectId(o) === id)).filter((o) => !!o);
12252
12257
  if (members.length < 2) return;
12253
12258
  const activeBeforeRestore = fc.getActiveObject();
@@ -12256,7 +12261,7 @@ const PageCanvas = react.forwardRef(
12256
12261
  const sameMembers = activeMembers.length === members.length && members.every((member) => activeMembers.includes(member));
12257
12262
  const sameGroup = activeBeforeRestore.__pixldocsGroupSelection === groupId;
12258
12263
  const alreadyAligned = activeBeforeRestore.__pixldocsAlignedAngle != null;
12259
- if (sameMembers && sameGroup && alreadyAligned) {
12264
+ if (sameMembers && (!groupId || sameGroup && alreadyAligned)) {
12260
12265
  ensureCanvaControlRenders(activeBeforeRestore);
12261
12266
  return;
12262
12267
  }
@@ -12265,7 +12270,7 @@ const PageCanvas = react.forwardRef(
12265
12270
  try {
12266
12271
  const active = activeBeforeRestore;
12267
12272
  const selection = active instanceof fabric__namespace.ActiveSelection && members.every((member) => active.getObjects().includes(member)) ? active : new fabric__namespace.ActiveSelection(members, { canvas: fc });
12268
- applyLogicalGroupSelectionVisualState(selection, groupId);
12273
+ if (groupId) applyLogicalGroupSelectionVisualState(selection, groupId);
12269
12274
  ensureCanvaControlRenders(selection);
12270
12275
  fc.setActiveObject(selection);
12271
12276
  try {
@@ -12310,6 +12315,36 @@ const PageCanvas = react.forwardRef(
12310
12315
  react.useEffect(() => {
12311
12316
  selectedIdsRef.current = selectedIds;
12312
12317
  }, [selectedIds]);
12318
+ react.useEffect(() => {
12319
+ const fc = fabricRef.current;
12320
+ if (!fc || !isEditorMode || !currentPage) return;
12321
+ const lockedIds = /* @__PURE__ */ new Set();
12322
+ const walk = (nodes, parentLocked) => {
12323
+ for (const n of nodes) {
12324
+ const nodeLocked = !!n.locked || n.selectable === false;
12325
+ const eff = parentLocked || nodeLocked;
12326
+ if (eff) lockedIds.add(n.id);
12327
+ if (isGroup(n)) walk(n.children ?? [], eff);
12328
+ }
12329
+ };
12330
+ walk(currentPage.children ?? [], false);
12331
+ fc.getObjects().forEach((o) => {
12332
+ const id = getObjectId(o);
12333
+ if (!id || id === "__background__") return;
12334
+ const locked = lockedIds.has(id);
12335
+ o.set({
12336
+ lockMovementX: locked,
12337
+ lockMovementY: locked,
12338
+ lockScalingX: locked,
12339
+ lockScalingY: locked,
12340
+ lockRotation: locked,
12341
+ lockSkewingX: locked,
12342
+ lockSkewingY: locked,
12343
+ hoverCursor: locked ? "not-allowed" : void 0
12344
+ });
12345
+ });
12346
+ fc.requestRenderAll();
12347
+ }, [currentPage == null ? void 0 : currentPage.children, isEditorMode, elements]);
12313
12348
  react.useEffect(() => {
12314
12349
  const fc = fabricRef.current;
12315
12350
  if (!fc || !currentPage) return;
@@ -13775,7 +13810,7 @@ const PageCanvas = react.forwardRef(
13775
13810
  syncLockedRef.current = false;
13776
13811
  }
13777
13812
  const preservedGroupSelection = preserveActiveSelectionAfterTransformRef.current;
13778
- const shouldRestoreGroupSelection = !!((preservedGroupSelection == null ? void 0 : preservedGroupSelection.groupSelectionId) && (!preservedGroupSelection.expiresAt || preservedGroupSelection.expiresAt > Date.now()));
13813
+ const shouldRestoreGroupSelection = !!(preservedGroupSelection && preservedGroupSelection.memberIds.length >= 2 && (!preservedGroupSelection.expiresAt || preservedGroupSelection.expiresAt > Date.now()));
13779
13814
  if (skipSelectionClearOnDiscardRef.current) {
13780
13815
  skipSelectionClearOnDiscardRef.current = false;
13781
13816
  return;
@@ -14029,9 +14064,13 @@ const PageCanvas = react.forwardRef(
14029
14064
  suppressBordersForObjects(memberObjects);
14030
14065
  };
14031
14066
  const restorePreservedGroupSelectionSoon = (snapshot = preserveActiveSelectionAfterTransformRef.current) => {
14032
- if (!(snapshot == null ? void 0 : snapshot.groupSelectionId) || snapshot.memberIds.length < 2) return;
14067
+ if (!snapshot || snapshot.memberIds.length < 2) return;
14033
14068
  const groupId = snapshot.groupSelectionId;
14034
- selectElements([groupId], false, false);
14069
+ if (groupId) {
14070
+ selectElements([groupId], false, false);
14071
+ } else {
14072
+ selectElements(snapshot.memberIds, false, false);
14073
+ }
14035
14074
  requestAnimationFrame(() => {
14036
14075
  setTimeout(() => {
14037
14076
  if (!isActiveRef.current) return;
@@ -14041,7 +14080,7 @@ const PageCanvas = react.forwardRef(
14041
14080
  const sameMembers = activeIds.length === snapshot.memberIds.length && snapshot.memberIds.every((id) => activeIds.includes(id));
14042
14081
  const sameGroup = active.__pixldocsGroupSelection === snapshot.groupSelectionId;
14043
14082
  const alreadyAligned = active.__pixldocsAlignedAngle != null;
14044
- if (sameMembers && sameGroup && alreadyAligned) {
14083
+ if (sameMembers && (!groupId || sameGroup && alreadyAligned)) {
14045
14084
  ensureCanvaControlRenders(active);
14046
14085
  return;
14047
14086
  }
@@ -17439,7 +17478,8 @@ const PageCanvas = react.forwardRef(
17439
17478
  }
17440
17479
  return memberIds.length > 0 ? { ...rawActiveSelectionSnapshot, memberIds, groupSelectionId } : null;
17441
17480
  })() : null;
17442
- if (syncTriggeredByPanelRef.current && !transformSelectionId && !shouldSkipUpdates2 && !isTransforming2) {
17481
+ const hasFreshPreservedActiveSelection = !!(activeSelectionSnapshot && activeSelectionSnapshot.memberIds.length >= 2 && preserveActiveSelectionAfterTransformRef.current && (!preserveActiveSelectionAfterTransformRef.current.expiresAt || preserveActiveSelectionAfterTransformRef.current.expiresAt > Date.now()));
17482
+ if (syncTriggeredByPanelRef.current && !transformSelectionId && !hasFreshPreservedActiveSelection && !shouldSkipUpdates2 && !isTransforming2) {
17443
17483
  const activeObj = fc.getActiveObject();
17444
17484
  const activeObjId = activeObj ? getObjectId(activeObj) : null;
17445
17485
  const isTextBeingEdited = activeObjId && editingTextIdRef.current === activeObjId;
@@ -17455,7 +17495,7 @@ const PageCanvas = react.forwardRef(
17455
17495
  currentFabricObjects.set(id, obj);
17456
17496
  }
17457
17497
  });
17458
- const skipRestoreSelection = syncTriggeredByPanelRef.current && !transformSelectionId;
17498
+ const skipRestoreSelection = syncTriggeredByPanelRef.current && !transformSelectionId && !hasFreshPreservedActiveSelection;
17459
17499
  const activeId = transformSelectionId || (activeBeforeSync ? getObjectId(activeBeforeSync) : null);
17460
17500
  const activeStillOnCanvas = activeBeforeSync && fc.getObjects().includes(activeBeforeSync);
17461
17501
  const replacementById = !activeStillOnCanvas && activeId ? fc.getObjects().find((o) => getObjectId(o) === activeId) ?? null : null;
@@ -18298,6 +18338,11 @@ const PageCanvas = react.forwardRef(
18298
18338
  const recentGroupRestore = recentGroupSelectionRestoreRef.current;
18299
18339
  if ((recentGroupRestore == null ? void 0 : recentGroupRestore.groupSelectionId) && recentGroupRestore.expiresAt > Date.now()) {
18300
18340
  restoreGroupSelectionSnapshot(recentGroupRestore);
18341
+ } else {
18342
+ const preservedActiveSelectionRestore = preserveActiveSelectionAfterTransformRef.current;
18343
+ if (preservedActiveSelectionRestore && preservedActiveSelectionRestore.memberIds.length >= 2 && (!preservedActiveSelectionRestore.expiresAt || preservedActiveSelectionRestore.expiresAt > Date.now())) {
18344
+ restoreGroupSelectionSnapshot(preservedActiveSelectionRestore);
18345
+ }
18301
18346
  }
18302
18347
  preserveSelectionAfterTransformIdRef.current = null;
18303
18348
  preserveActiveSelectionAfterTransformRef.current = null;
@@ -26536,9 +26581,9 @@ function captureFabricCanvasSvgForPdf(fabricInstance, canvasWidth, canvasHeight)
26536
26581
  }
26537
26582
  return svgString;
26538
26583
  }
26539
- const resolvedPackageVersion = "0.5.493";
26584
+ const resolvedPackageVersion = "0.5.494";
26540
26585
  const PACKAGE_VERSION = resolvedPackageVersion;
26541
- const DEPLOYMENT_VERSION_MARKER = "__PIXLDOCS_CANVAS_RENDERER_VERSION__:0.5.493";
26586
+ const DEPLOYMENT_VERSION_MARKER = "__PIXLDOCS_CANVAS_RENDERER_VERSION__:0.5.494";
26542
26587
  const roundParityValue = (value) => {
26543
26588
  if (typeof value !== "number") return value;
26544
26589
  return Number.isFinite(value) ? Number(value.toFixed(3)) : value;
@@ -27352,7 +27397,7 @@ class PixldocsRenderer {
27352
27397
  await this.waitForCanvasScene(container, cloned, i);
27353
27398
  }
27354
27399
  console.log(`[canvas-renderer][pdf-unified] mounted ${cloned.pages.length} page(s), handing off to client exportMultiPagePdf`);
27355
- const { exportMultiPagePdf, preparePagesForExport } = await Promise.resolve().then(() => require("./vectorPdfExport-obFAiUhx.cjs"));
27400
+ const { exportMultiPagePdf, preparePagesForExport } = await Promise.resolve().then(() => require("./vectorPdfExport-BkAhiIFX.cjs"));
27356
27401
  const prepared = preparePagesForExport(
27357
27402
  cloned.pages,
27358
27403
  canvasWidth,
@@ -29672,7 +29717,7 @@ async function prepareLiveCanvasSvgForPdf(rawSvg, pageWidth, pageHeight, pageKey
29672
29717
  if (options == null ? void 0 : options.stripPageBackground) stripRootPageBackgroundFromSvg(svgToDraw);
29673
29718
  sanitizeSvgTreeForPdf(svgToDraw);
29674
29719
  try {
29675
- const { bakeTextAnchorPositionsFromLiveSvg, logTextMeasurementDiagnostic } = await Promise.resolve().then(() => require("./vectorPdfExport-obFAiUhx.cjs"));
29720
+ const { bakeTextAnchorPositionsFromLiveSvg, logTextMeasurementDiagnostic } = await Promise.resolve().then(() => require("./vectorPdfExport-BkAhiIFX.cjs"));
29676
29721
  try {
29677
29722
  await logTextMeasurementDiagnostic(svgToDraw);
29678
29723
  } catch {
@@ -29986,4 +30031,4 @@ exports.setAutoShrinkDebug = setAutoShrinkDebug;
29986
30031
  exports.setBundledAssetPrefixes = setBundledAssetPrefixes;
29987
30032
  exports.warmResolvedTemplateForPreview = warmResolvedTemplateForPreview;
29988
30033
  exports.warmTemplateFromForm = warmTemplateFromForm;
29989
- //# sourceMappingURL=index-CapZsm7x.cjs.map
30034
+ //# sourceMappingURL=index-CCMdTuIr.cjs.map