@carlonicora/nextjs-jsonapi 1.98.0 → 1.99.0

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.
@@ -47,7 +47,7 @@ import {
47
47
  TabsList,
48
48
  TabsTrigger,
49
49
  useCurrentUserContext
50
- } from "../chunk-TLTENUI6.mjs";
50
+ } from "../chunk-CDNVUON3.mjs";
51
51
  import {
52
52
  getRoleId,
53
53
  getStripePublishableKey
@@ -6454,6 +6454,71 @@ import * as d3 from "d3";
6454
6454
  import { Loader2 as Loader22 } from "lucide-react";
6455
6455
  import { useCallback as useCallback9, useEffect as useEffect8, useMemo as useMemo8, useRef as useRef8 } from "react";
6456
6456
  import { renderToStaticMarkup } from "react-dom/server";
6457
+
6458
+ // src/hooks/computeLayeredLayout.ts
6459
+ import * as dagre from "dagre";
6460
+ var DEFAULT_RANKDIR = "LR";
6461
+ var DEFAULT_NODESEP = 50;
6462
+ var DEFAULT_RANKSEP = 120;
6463
+ var TITLE_PX_PER_CHAR_16 = 8;
6464
+ var NAME_PX_PER_CHAR_12 = 6.5;
6465
+ var NAME_PX_PER_CHAR_16_BOLD = 8;
6466
+ var SUBTITLE_PX_PER_CHAR_11 = 6;
6467
+ var LABEL_PADDING_PX = 16;
6468
+ function estimateLabelWidth(node) {
6469
+ if (node.subtitle) {
6470
+ const titleWidth = (node.name?.length ?? 0) * TITLE_PX_PER_CHAR_16;
6471
+ const subtitleWidth = node.subtitle.length * SUBTITLE_PX_PER_CHAR_11;
6472
+ return Math.max(titleWidth, subtitleWidth) + LABEL_PADDING_PX;
6473
+ }
6474
+ const perChar = node.bold ? NAME_PX_PER_CHAR_16_BOLD : NAME_PX_PER_CHAR_12;
6475
+ return (node.name?.length ?? 0) * perChar + LABEL_PADDING_PX;
6476
+ }
6477
+ __name(estimateLabelWidth, "estimateLabelWidth");
6478
+ function linkEndpointId(end) {
6479
+ return typeof end === "string" ? end : end.id;
6480
+ }
6481
+ __name(linkEndpointId, "linkEndpointId");
6482
+ function computeLayeredLayout(nodes, links, opts) {
6483
+ if (nodes.length === 0) return /* @__PURE__ */ new Map();
6484
+ const rankdir = opts.rankdir ?? DEFAULT_RANKDIR;
6485
+ const nodesep = opts.nodesep ?? DEFAULT_NODESEP;
6486
+ const ranksep = opts.ranksep ?? DEFAULT_RANKSEP;
6487
+ const g = new dagre.graphlib.Graph({ directed: true });
6488
+ g.setGraph({ rankdir, nodesep, ranksep, marginx: 20, marginy: 20 });
6489
+ g.setDefaultEdgeLabel(() => ({}));
6490
+ for (const node of nodes) {
6491
+ const width = Math.max(opts.minNodeWidth, estimateLabelWidth(node));
6492
+ const height = opts.minNodeHeight;
6493
+ g.setNode(node.id, { width, height });
6494
+ }
6495
+ const seen = /* @__PURE__ */ new Set();
6496
+ for (const link of links) {
6497
+ const sourceId = linkEndpointId(link.source);
6498
+ const targetId = linkEndpointId(link.target);
6499
+ if (!g.hasNode(sourceId) || !g.hasNode(targetId)) continue;
6500
+ const key = `${sourceId}->${targetId}`;
6501
+ if (seen.has(key)) continue;
6502
+ seen.add(key);
6503
+ g.setEdge(sourceId, targetId);
6504
+ }
6505
+ try {
6506
+ dagre.layout(g);
6507
+ } catch {
6508
+ return null;
6509
+ }
6510
+ const positions = /* @__PURE__ */ new Map();
6511
+ for (const node of nodes) {
6512
+ const laid = g.node(node.id);
6513
+ if (laid && Number.isFinite(laid.x) && Number.isFinite(laid.y)) {
6514
+ positions.set(node.id, { x: laid.x, y: laid.y });
6515
+ }
6516
+ }
6517
+ return positions;
6518
+ }
6519
+ __name(computeLayeredLayout, "computeLayeredLayout");
6520
+
6521
+ // src/hooks/useCustomD3Graph.tsx
6457
6522
  import { jsx as jsx49 } from "react/jsx-runtime";
6458
6523
  function useCustomD3Graph(nodes, links, onNodeClick, visibleNodeIds, options, loadingNodeIds, containerKey) {
6459
6524
  const svgRef = useRef8(null);
@@ -6584,117 +6649,167 @@ function useCustomD3Graph(nodes, links, onNodeClick, visibleNodeIds, options, lo
6584
6649
  });
6585
6650
  zoomBehaviorRef.current = zoom2;
6586
6651
  svg.call(zoom2).on("wheel.zoom", null).on("dblclick.zoom", null);
6587
- const childDistanceFromRoot = Math.min(width, height) * 0.4;
6588
- const grandchildDistanceFromChild = nodeRadius * 10;
6589
- const centralNodeId = nodes[0].id;
6590
- const nodeHierarchy = /* @__PURE__ */ new Map();
6591
- nodeHierarchy.set(centralNodeId, {
6592
- depth: 0,
6593
- parent: null,
6594
- children: []
6595
- });
6596
- visibleLinks.forEach((link2) => {
6597
- const sourceId = typeof link2.source === "string" ? link2.source : link2.source.id;
6598
- const targetId = typeof link2.target === "string" ? link2.target : link2.target.id;
6599
- if (sourceId === centralNodeId) {
6600
- nodeHierarchy.set(targetId, { depth: 1, parent: centralNodeId, children: [] });
6601
- const rootNode = nodeHierarchy.get(centralNodeId);
6602
- if (rootNode) {
6603
- rootNode.children.push(targetId);
6604
- }
6605
- }
6606
- });
6607
- visibleLinks.forEach((link2) => {
6608
- const sourceId = typeof link2.source === "string" ? link2.source : link2.source.id;
6609
- const targetId = typeof link2.target === "string" ? link2.target : link2.target.id;
6610
- const sourceNode = nodeHierarchy.get(sourceId);
6611
- if (sourceNode && sourceNode.depth === 1 && !nodeHierarchy.has(targetId)) {
6612
- nodeHierarchy.set(targetId, { depth: 2, parent: sourceId, children: [] });
6613
- sourceNode.children.push(targetId);
6614
- }
6615
- });
6616
- const rootChildren = nodeHierarchy.get(centralNodeId)?.children || [];
6617
- const childAngleStep = 2 * Math.PI / Math.max(rootChildren.length, 1);
6618
- rootChildren.forEach((childId, index) => {
6619
- const childNode = nodeHierarchy.get(childId);
6620
- if (childNode) {
6621
- const angle = index * childAngleStep;
6622
- childNode.angle = angle;
6623
- childNode.x = width / 2 + childDistanceFromRoot * Math.cos(angle);
6624
- childNode.y = height / 2 + childDistanceFromRoot * Math.sin(angle);
6652
+ const layoutMode = options?.layout ?? "radial";
6653
+ let layeredPositionsApplied = false;
6654
+ if (layoutMode === "layered") {
6655
+ const layeredOpts = options?.layered ?? {};
6656
+ const positions = computeLayeredLayout(visibleNodes, visibleLinks, {
6657
+ rankdir: layeredOpts.rankdir ?? "LR",
6658
+ nodesep: layeredOpts.nodesep,
6659
+ ranksep: layeredOpts.ranksep,
6660
+ minNodeWidth: nodeRadius * 2,
6661
+ minNodeHeight: nodeRadius * 2
6662
+ });
6663
+ if (positions) {
6664
+ visibleNodes.forEach((node2) => {
6665
+ const saved = nodePositionsRef.current.get(node2.id);
6666
+ if (saved) {
6667
+ node2.fx = saved.x;
6668
+ node2.fy = saved.y;
6669
+ node2.x = saved.x;
6670
+ node2.y = saved.y;
6671
+ return;
6672
+ }
6673
+ const pos = positions.get(node2.id);
6674
+ if (pos) {
6675
+ node2.fx = pos.x;
6676
+ node2.fy = pos.y;
6677
+ node2.x = pos.x;
6678
+ node2.y = pos.y;
6679
+ nodePositionsRef.current.set(node2.id, { x: pos.x, y: pos.y });
6680
+ }
6681
+ });
6682
+ const nodeById = /* @__PURE__ */ new Map();
6683
+ visibleNodes.forEach((n) => nodeById.set(n.id, n));
6684
+ visibleLinks.forEach((link2) => {
6685
+ if (typeof link2.source === "string") {
6686
+ const src = nodeById.get(link2.source);
6687
+ if (src) link2.source = src;
6688
+ }
6689
+ if (typeof link2.target === "string") {
6690
+ const tgt = nodeById.get(link2.target);
6691
+ if (tgt) link2.target = tgt;
6692
+ }
6693
+ });
6694
+ layeredPositionsApplied = true;
6695
+ } else {
6696
+ console.warn("[useCustomD3Graph] Layered layout failed; falling back to radial.");
6625
6697
  }
6626
- });
6627
- for (const [_nodeId, node2] of nodeHierarchy.entries()) {
6628
- if (node2.depth === 1 && node2.angle !== void 0 && node2.x !== void 0 && node2.y !== void 0) {
6629
- const childAngle = node2.angle;
6630
- const childX = node2.x;
6631
- const childY = node2.y;
6632
- const grandchildren = node2.children;
6633
- if (grandchildren.length === 0) continue;
6634
- const dirX = childX - width / 2;
6635
- const dirY = childY - height / 2;
6636
- const dirLength = Math.sqrt(dirX * dirX + dirY * dirY);
6637
- const normDirX = dirX / dirLength;
6638
- const normDirY = dirY / dirLength;
6639
- if (grandchildren.length === 1) {
6640
- const grandchildId = grandchildren[0];
6641
- const grandchildNode = nodeHierarchy.get(grandchildId);
6642
- if (grandchildNode) {
6643
- grandchildNode.x = childX + normDirX * grandchildDistanceFromChild;
6644
- grandchildNode.y = childY + normDirY * grandchildDistanceFromChild;
6645
- grandchildNode.angle = childAngle;
6698
+ }
6699
+ let simulation = null;
6700
+ if (!layeredPositionsApplied) {
6701
+ const childDistanceFromRoot = Math.min(width, height) * 0.4;
6702
+ const grandchildDistanceFromChild = nodeRadius * 10;
6703
+ const centralNodeId = nodes[0].id;
6704
+ const nodeHierarchy = /* @__PURE__ */ new Map();
6705
+ nodeHierarchy.set(centralNodeId, {
6706
+ depth: 0,
6707
+ parent: null,
6708
+ children: []
6709
+ });
6710
+ visibleLinks.forEach((link2) => {
6711
+ const sourceId = typeof link2.source === "string" ? link2.source : link2.source.id;
6712
+ const targetId = typeof link2.target === "string" ? link2.target : link2.target.id;
6713
+ if (sourceId === centralNodeId) {
6714
+ nodeHierarchy.set(targetId, { depth: 1, parent: centralNodeId, children: [] });
6715
+ const rootNode = nodeHierarchy.get(centralNodeId);
6716
+ if (rootNode) {
6717
+ rootNode.children.push(targetId);
6646
6718
  }
6647
- } else {
6648
- const numChildren = grandchildren.length;
6649
- const minArc = Math.PI / 3;
6650
- const maxArc = Math.PI;
6651
- const arcProgress = Math.min(1, (numChildren - 2) / 5);
6652
- const arcSpan = minArc + arcProgress * (maxArc - minArc);
6653
- const startAngle = childAngle - arcSpan / 2;
6654
- grandchildren.forEach((grandchildId, index) => {
6719
+ }
6720
+ });
6721
+ visibleLinks.forEach((link2) => {
6722
+ const sourceId = typeof link2.source === "string" ? link2.source : link2.source.id;
6723
+ const targetId = typeof link2.target === "string" ? link2.target : link2.target.id;
6724
+ const sourceNode = nodeHierarchy.get(sourceId);
6725
+ if (sourceNode && sourceNode.depth === 1 && !nodeHierarchy.has(targetId)) {
6726
+ nodeHierarchy.set(targetId, { depth: 2, parent: sourceId, children: [] });
6727
+ sourceNode.children.push(targetId);
6728
+ }
6729
+ });
6730
+ const rootChildren = nodeHierarchy.get(centralNodeId)?.children || [];
6731
+ const childAngleStep = 2 * Math.PI / Math.max(rootChildren.length, 1);
6732
+ rootChildren.forEach((childId, index) => {
6733
+ const childNode = nodeHierarchy.get(childId);
6734
+ if (childNode) {
6735
+ const angle = index * childAngleStep;
6736
+ childNode.angle = angle;
6737
+ childNode.x = width / 2 + childDistanceFromRoot * Math.cos(angle);
6738
+ childNode.y = height / 2 + childDistanceFromRoot * Math.sin(angle);
6739
+ }
6740
+ });
6741
+ for (const [_nodeId, node2] of nodeHierarchy.entries()) {
6742
+ if (node2.depth === 1 && node2.angle !== void 0 && node2.x !== void 0 && node2.y !== void 0) {
6743
+ const childAngle = node2.angle;
6744
+ const childX = node2.x;
6745
+ const childY = node2.y;
6746
+ const grandchildren = node2.children;
6747
+ if (grandchildren.length === 0) continue;
6748
+ const dirX = childX - width / 2;
6749
+ const dirY = childY - height / 2;
6750
+ const dirLength = Math.sqrt(dirX * dirX + dirY * dirY);
6751
+ const normDirX = dirX / dirLength;
6752
+ const normDirY = dirY / dirLength;
6753
+ if (grandchildren.length === 1) {
6754
+ const grandchildId = grandchildren[0];
6655
6755
  const grandchildNode = nodeHierarchy.get(grandchildId);
6656
- if (!grandchildNode) return;
6657
- const angleOffset = numChildren > 1 ? index / (numChildren - 1) * arcSpan : 0;
6658
- const angle = startAngle + angleOffset;
6659
- grandchildNode.x = childX + grandchildDistanceFromChild * Math.cos(angle);
6660
- grandchildNode.y = childY + grandchildDistanceFromChild * Math.sin(angle);
6661
- grandchildNode.angle = angle;
6662
- });
6756
+ if (grandchildNode) {
6757
+ grandchildNode.x = childX + normDirX * grandchildDistanceFromChild;
6758
+ grandchildNode.y = childY + normDirY * grandchildDistanceFromChild;
6759
+ grandchildNode.angle = childAngle;
6760
+ }
6761
+ } else {
6762
+ const numChildren = grandchildren.length;
6763
+ const minArc = Math.PI / 3;
6764
+ const maxArc = Math.PI;
6765
+ const arcProgress = Math.min(1, (numChildren - 2) / 5);
6766
+ const arcSpan = minArc + arcProgress * (maxArc - minArc);
6767
+ const startAngle = childAngle - arcSpan / 2;
6768
+ grandchildren.forEach((grandchildId, index) => {
6769
+ const grandchildNode = nodeHierarchy.get(grandchildId);
6770
+ if (!grandchildNode) return;
6771
+ const angleOffset = numChildren > 1 ? index / (numChildren - 1) * arcSpan : 0;
6772
+ const angle = startAngle + angleOffset;
6773
+ grandchildNode.x = childX + grandchildDistanceFromChild * Math.cos(angle);
6774
+ grandchildNode.y = childY + grandchildDistanceFromChild * Math.sin(angle);
6775
+ grandchildNode.angle = angle;
6776
+ });
6777
+ }
6663
6778
  }
6664
6779
  }
6665
- }
6666
- visibleNodes.forEach((node2) => {
6667
- const savedPosition = nodePositionsRef.current.get(node2.id);
6668
- if (savedPosition) {
6669
- node2.fx = savedPosition.x;
6670
- node2.fy = savedPosition.y;
6671
- } else {
6672
- const hierarchyNode = nodeHierarchy.get(node2.id);
6673
- if (hierarchyNode && hierarchyNode.x !== void 0 && hierarchyNode.y !== void 0) {
6674
- node2.fx = hierarchyNode.x;
6675
- node2.fy = hierarchyNode.y;
6676
- nodePositionsRef.current.set(node2.id, { x: hierarchyNode.x, y: hierarchyNode.y });
6677
- } else if (node2.id === centralNodeId) {
6678
- node2.fx = width / 2;
6679
- node2.fy = height / 2;
6680
- nodePositionsRef.current.set(node2.id, { x: width / 2, y: height / 2 });
6780
+ visibleNodes.forEach((node2) => {
6781
+ const savedPosition = nodePositionsRef.current.get(node2.id);
6782
+ if (savedPosition) {
6783
+ node2.fx = savedPosition.x;
6784
+ node2.fy = savedPosition.y;
6785
+ } else {
6786
+ const hierarchyNode = nodeHierarchy.get(node2.id);
6787
+ if (hierarchyNode && hierarchyNode.x !== void 0 && hierarchyNode.y !== void 0) {
6788
+ node2.fx = hierarchyNode.x;
6789
+ node2.fy = hierarchyNode.y;
6790
+ nodePositionsRef.current.set(node2.id, { x: hierarchyNode.x, y: hierarchyNode.y });
6791
+ } else if (node2.id === centralNodeId) {
6792
+ node2.fx = width / 2;
6793
+ node2.fy = height / 2;
6794
+ nodePositionsRef.current.set(node2.id, { x: width / 2, y: height / 2 });
6795
+ }
6681
6796
  }
6797
+ });
6798
+ simulation = d3.forceSimulation(visibleNodes).force(
6799
+ "link",
6800
+ d3.forceLink(visibleLinks).id((d) => d.id).distance(nodeRadius * 3).strength(0.1)
6801
+ ).force("charge", d3.forceManyBody().strength(-500).distanceMax(300)).force("collision", d3.forceCollide().radius(nodeRadius * 1.2)).force("center", d3.forceCenter(width / 2, height / 2).strength(0.1));
6802
+ simulation.stop();
6803
+ for (let i = 0; i < 100; i++) {
6804
+ simulation.tick();
6682
6805
  }
6683
- });
6684
- const simulation = d3.forceSimulation(visibleNodes).force(
6685
- "link",
6686
- d3.forceLink(visibleLinks).id((d) => d.id).distance(nodeRadius * 3).strength(0.1)
6687
- ).force("charge", d3.forceManyBody().strength(-500).distanceMax(300)).force("collision", d3.forceCollide().radius(nodeRadius * 1.2)).force("center", d3.forceCenter(width / 2, height / 2).strength(0.1));
6688
- simulation.stop();
6689
- for (let i = 0; i < 100; i++) {
6690
- simulation.tick();
6691
- }
6692
- visibleNodes.forEach((node2) => {
6693
- if (node2.fx === void 0) {
6694
- node2.fx = node2.x;
6695
- node2.fy = node2.y;
6696
- }
6697
- });
6806
+ visibleNodes.forEach((node2) => {
6807
+ if (node2.fx === void 0) {
6808
+ node2.fx = node2.x;
6809
+ node2.fy = node2.y;
6810
+ }
6811
+ });
6812
+ }
6698
6813
  const linkX2 = /* @__PURE__ */ __name((sx, sy, tx, ty) => {
6699
6814
  if (!directed) return tx;
6700
6815
  const dx = tx - sx;
@@ -6836,9 +6951,21 @@ function useCustomD3Graph(nodes, links, onNodeClick, visibleNodeIds, options, lo
6836
6951
  }
6837
6952
  });
6838
6953
  return () => {
6839
- simulation.stop();
6954
+ simulation?.stop();
6840
6955
  };
6841
- }, [nodes, links, colorScale, visibleNodeIds, options?.directed, loadingNodeIds, onNodeClick]);
6956
+ }, [
6957
+ nodes,
6958
+ links,
6959
+ colorScale,
6960
+ visibleNodeIds,
6961
+ options?.directed,
6962
+ options?.layout,
6963
+ options?.layered?.rankdir,
6964
+ options?.layered?.nodesep,
6965
+ options?.layered?.ranksep,
6966
+ loadingNodeIds,
6967
+ onNodeClick
6968
+ ]);
6842
6969
  const zoomIn = useCallback9(() => {
6843
6970
  if (!svgRef.current || !zoomBehaviorRef.current) return;
6844
6971
  const svg = d3.select(svgRef.current);
@@ -9273,7 +9400,7 @@ import { useRef as useRef15 } from "react";
9273
9400
  import dynamic from "next/dynamic";
9274
9401
  import React14 from "react";
9275
9402
  import { jsx as jsx73 } from "react/jsx-runtime";
9276
- var BlockNoteEditor = dynamic(() => import("./BlockNoteEditor-HWQHTLEB.mjs"), {
9403
+ var BlockNoteEditor = dynamic(() => import("./BlockNoteEditor-IBV3KBQM.mjs"), {
9277
9404
  ssr: false
9278
9405
  });
9279
9406
  var BlockNoteEditorContainer = React14.memo(/* @__PURE__ */ __name(function EditorContainer(props) {
@@ -21687,6 +21814,7 @@ export {
21687
21814
  useDebounce2 as useDebounce,
21688
21815
  registerTableGenerator,
21689
21816
  useTableGenerator,
21817
+ computeLayeredLayout,
21690
21818
  useCustomD3Graph,
21691
21819
  SocketContext,
21692
21820
  SocketProvider,
@@ -22186,4 +22314,4 @@ export {
22186
22314
  useOAuthClients,
22187
22315
  useOAuthClient
22188
22316
  };
22189
- //# sourceMappingURL=chunk-TLTENUI6.mjs.map
22317
+ //# sourceMappingURL=chunk-CDNVUON3.mjs.map