@diagrammo/dgmo 0.45.0 → 0.47.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.
Files changed (250) hide show
  1. package/dist/advanced.cjs +31 -25
  2. package/dist/advanced.d.cts +3 -855
  3. package/dist/advanced.d.ts +3 -855
  4. package/dist/advanced.js +541 -70101
  5. package/dist/analyzer-UYKBXAKR.js +15 -0
  6. package/dist/auto.cjs +500 -341
  7. package/dist/auto.css +342 -159
  8. package/dist/auto.d.cts +10 -8
  9. package/dist/auto.d.ts +10 -8
  10. package/dist/auto.js +373 -265
  11. package/dist/auto.mjs +500 -341
  12. package/dist/block.cjs +31 -25
  13. package/dist/block.js +83 -69411
  14. package/dist/calculator-LDYQCDDY.js +11 -0
  15. package/dist/charts-d3-QOZHKTCT.js +25 -0
  16. package/dist/chunk-2DXMZRWJ.js +800 -0
  17. package/dist/chunk-2LACINWN.js +786 -0
  18. package/dist/chunk-33LCUH4H.js +893 -0
  19. package/dist/chunk-3CIOJ5YJ.js +35 -0
  20. package/dist/chunk-3HDBAXF5.js +86 -0
  21. package/dist/chunk-3JLKYGBQ.js +290 -0
  22. package/dist/chunk-3MQQNXPD.js +415 -0
  23. package/dist/chunk-3R5POCTZ.js +967 -0
  24. package/dist/chunk-3SMGIJDD.js +112 -0
  25. package/dist/chunk-44CM72SQ.js +409 -0
  26. package/dist/chunk-4GRI7MEB.js +1604 -0
  27. package/dist/chunk-4OHACBGX.js +606 -0
  28. package/dist/chunk-5DH3KYFH.js +21 -0
  29. package/dist/chunk-5MLYVTYM.js +76 -0
  30. package/dist/chunk-5QXL4NYS.js +553 -0
  31. package/dist/chunk-5WRI5ZAA.js +31 -0
  32. package/dist/chunk-6EK55ART.js +117 -0
  33. package/dist/chunk-6FZYCKXB.js +2065 -0
  34. package/dist/chunk-6HO5ZTXK.js +277 -0
  35. package/dist/chunk-6KFWC4CO.js +7 -0
  36. package/dist/chunk-6MTWIQVO.js +121 -0
  37. package/dist/chunk-6NYWYNBI.js +329 -0
  38. package/dist/chunk-6SM5NJQH.js +620 -0
  39. package/dist/chunk-725LDASD.js +422 -0
  40. package/dist/chunk-76OWZ3BA.js +130 -0
  41. package/dist/chunk-7JEGTRLD.js +338 -0
  42. package/dist/chunk-A44USUV7.js +923 -0
  43. package/dist/chunk-A4GOY3PE.js +25 -0
  44. package/dist/chunk-A4VFQH5G.js +251 -0
  45. package/dist/chunk-AELOBFW5.js +375 -0
  46. package/dist/chunk-AN2MOO5T.js +522 -0
  47. package/dist/chunk-BMR4CIEO.js +41 -0
  48. package/dist/chunk-BS7SV7C3.js +51 -0
  49. package/dist/chunk-BUPDIHML.js +613 -0
  50. package/dist/chunk-BUVJFRPY.js +887 -0
  51. package/dist/chunk-C3Z4DX3V.js +112 -0
  52. package/dist/chunk-CI2G3OEB.js +1818 -0
  53. package/dist/chunk-CKNVO24D.js +54 -0
  54. package/dist/chunk-CUVHQHZ7.js +391 -0
  55. package/dist/chunk-CXK4DZH3.js +114 -0
  56. package/dist/chunk-DKEPS5LH.js +315 -0
  57. package/dist/chunk-DU7W62N5.js +487 -0
  58. package/dist/chunk-DZAQBW35.js +751 -0
  59. package/dist/chunk-EB6FPQUP.js +316 -0
  60. package/dist/chunk-EMS2SK26.js +376 -0
  61. package/dist/chunk-ERLBPDGU.js +510 -0
  62. package/dist/chunk-EVCVDTXE.js +732 -0
  63. package/dist/chunk-FCIIHT24.js +384 -0
  64. package/dist/chunk-FFUN5D66.js +97 -0
  65. package/dist/chunk-FITOLXSX.js +714 -0
  66. package/dist/chunk-FMDSF3OV.js +68 -0
  67. package/dist/chunk-FNB3PNGF.js +410 -0
  68. package/dist/chunk-G2H74XJZ.js +2104 -0
  69. package/dist/chunk-GMR5MFHJ.js +339 -0
  70. package/dist/chunk-H6PI3KJT.js +305 -0
  71. package/dist/chunk-I46X5VUA.js +59 -0
  72. package/dist/chunk-I5IGB56C.js +255 -0
  73. package/dist/chunk-IH6ZMVQ5.js +3950 -0
  74. package/dist/chunk-IJZFN3HM.js +463 -0
  75. package/dist/chunk-IPWPWM6R.js +3079 -0
  76. package/dist/chunk-IYULMRBE.js +23 -0
  77. package/dist/chunk-IZMRON6C.js +167 -0
  78. package/dist/chunk-J5FIXQRT.js +813 -0
  79. package/dist/chunk-JED6ZDEE.js +73 -0
  80. package/dist/chunk-JEUJOX5X.js +136 -0
  81. package/dist/chunk-JM4LEPY3.js +436 -0
  82. package/dist/chunk-L3UHP6TD.js +101 -0
  83. package/dist/chunk-L66GEFB6.js +524 -0
  84. package/dist/chunk-LIOHW36Z.js +469 -0
  85. package/dist/chunk-LP7EC4MI.js +16 -0
  86. package/dist/chunk-MITI6NOL.js +548 -0
  87. package/dist/chunk-MO5YHHMQ.js +168 -0
  88. package/dist/chunk-MZSBFAPJ.js +885 -0
  89. package/dist/chunk-NNAAJVBU.js +9 -0
  90. package/dist/chunk-NOTA6TEI.js +47 -0
  91. package/dist/chunk-NURGB5Z4.js +335 -0
  92. package/dist/chunk-NX4EQS3U.js +1062 -0
  93. package/dist/chunk-NXMESY4J.js +1 -0
  94. package/dist/chunk-OJR3MQYV.js +1458 -0
  95. package/dist/chunk-OURHMODR.js +454 -0
  96. package/dist/chunk-P235SVAH.js +1057 -0
  97. package/dist/chunk-P4RH4OSP.js +1038 -0
  98. package/dist/chunk-P6T66CCZ.js +226 -0
  99. package/dist/chunk-PBAHEPLQ.js +223 -0
  100. package/dist/chunk-PBHE5UG6.js +1530 -0
  101. package/dist/chunk-PDKUANDZ.js +35 -0
  102. package/dist/chunk-PWIHZ6NJ.js +296 -0
  103. package/dist/chunk-QEBUY5NY.js +1685 -0
  104. package/dist/chunk-QLCCJEJI.js +253 -0
  105. package/dist/chunk-QOOUC2J5.js +52 -0
  106. package/dist/chunk-QYTPPDAO.js +402 -0
  107. package/dist/chunk-R3XI2VC7.js +801 -0
  108. package/dist/chunk-RCERWOJR.js +154 -0
  109. package/dist/chunk-RJE5JTVK.js +362 -0
  110. package/dist/chunk-RTLBSQ3G.js +1155 -0
  111. package/dist/chunk-RUNNI6VE.js +448 -0
  112. package/dist/chunk-RVMRZAPB.js +354 -0
  113. package/dist/chunk-RYEGFMUO.js +955 -0
  114. package/dist/chunk-RZCF2VVM.js +528 -0
  115. package/dist/chunk-SML67VPV.js +1025 -0
  116. package/dist/chunk-SQ7IY53Q.js +44 -0
  117. package/dist/chunk-SQAG3UXH.js +161 -0
  118. package/dist/chunk-SRTU6HMQ.js +1851 -0
  119. package/dist/chunk-T2OE3YQB.js +550 -0
  120. package/dist/chunk-T3UBLACL.js +299 -0
  121. package/dist/chunk-TLVIHFRO.js +296 -0
  122. package/dist/chunk-TYS6CSS5.js +52 -0
  123. package/dist/chunk-U6EQI3U6.js +130 -0
  124. package/dist/chunk-UJ4FJLBF.js +86 -0
  125. package/dist/chunk-ULOEATBZ.js +347 -0
  126. package/dist/chunk-UNCCZ3NU.js +127 -0
  127. package/dist/chunk-USZW2HHU.js +197 -0
  128. package/dist/chunk-UWN33VNX.js +1610 -0
  129. package/dist/chunk-UZ7EZW3B.js +40 -0
  130. package/dist/chunk-VOKGH627.js +37 -0
  131. package/dist/chunk-WBRZJOEC.js +204 -0
  132. package/dist/chunk-WCSOJFU3.js +380 -0
  133. package/dist/chunk-WCT3NYCV.js +160 -0
  134. package/dist/chunk-WVAJFAIA.js +529 -0
  135. package/dist/chunk-X5LCYCL5.js +394 -0
  136. package/dist/chunk-XAKEUMEJ.js +1256 -0
  137. package/dist/chunk-Y2ZE3MSG.js +590 -0
  138. package/dist/chunk-Y3J7VR52.js +646 -0
  139. package/dist/chunk-Y5QGVTVC.js +33 -0
  140. package/dist/chunk-YAA6IID3.js +548 -0
  141. package/dist/chunk-YGJTDXVR.js +692 -0
  142. package/dist/chunk-YRYKTYMQ.js +186 -0
  143. package/dist/chunk-YYVTBZZC.js +61 -0
  144. package/dist/chunk-Z5CGSFJB.js +647 -0
  145. package/dist/chunk-Z72XRXD4.js +787 -0
  146. package/dist/chunk-ZGR7ULFJ.js +978 -0
  147. package/dist/chunk-ZJEL4H2R.js +851 -0
  148. package/dist/chunk-ZO27FGJS.js +554 -0
  149. package/dist/cli.cjs +112 -112
  150. package/dist/collapse-CLPJD2RL.js +11 -0
  151. package/dist/collapse-SLINJQW6.js +9 -0
  152. package/dist/collapse-ZWUFFCK2.js +9 -0
  153. package/dist/compute-G55RG53N.js +8 -0
  154. package/dist/dgmo-router-DZCIDUO5.js +73 -0
  155. package/dist/dimensions-J3FHIMJ6.js +22 -0
  156. package/dist/element.cjs +492 -325
  157. package/dist/element.js +367 -259
  158. package/dist/element.mjs +492 -325
  159. package/dist/flowchart-parser-ZNSKIBVR.js +21 -0
  160. package/dist/flowchart-renderer-ZAEOL4DX.js +35 -0
  161. package/dist/index.cjs +34 -28
  162. package/dist/index.d.cts +3 -469
  163. package/dist/index.d.ts +3 -469
  164. package/dist/index.js +137 -69679
  165. package/dist/layout-46N4JJYK.js +17 -0
  166. package/dist/layout-5RA6QWR6.js +26 -0
  167. package/dist/layout-5T6RH5M6.js +14 -0
  168. package/dist/layout-7QXCNOVS.js +13 -0
  169. package/dist/layout-EE6GE46Y.js +17 -0
  170. package/dist/layout-G23F7LDH.js +9 -0
  171. package/dist/layout-HRBZPFCN.js +23 -0
  172. package/dist/layout-HWDSRX5E.js +20 -0
  173. package/dist/layout-HYZPWAK5.js +18 -0
  174. package/dist/layout-N76NR4ZO.js +19 -0
  175. package/dist/layout-OB3RI63S.js +14 -0
  176. package/dist/layout-S2QBYSK2.js +15 -0
  177. package/dist/layout-UM5F4DJB.js +15 -0
  178. package/dist/layout-search-OYV77HHS.js +1655 -0
  179. package/dist/load-data-EHDDZ5ZS.js +8 -0
  180. package/dist/palettes-PRJ2RI6D.js +56 -0
  181. package/dist/parser-2MFP2H2E.js +11 -0
  182. package/dist/parser-3STE62GB.js +21 -0
  183. package/dist/parser-4FL2CMDG.js +18 -0
  184. package/dist/parser-4OGOBJJ4.js +13 -0
  185. package/dist/parser-6BTRLKRZ.js +15 -0
  186. package/dist/parser-AQETEVRW.js +21 -0
  187. package/dist/parser-CFZD5IBL.js +12 -0
  188. package/dist/parser-FUSKFGZN.js +16 -0
  189. package/dist/parser-I6KXEYFK.js +13 -0
  190. package/dist/parser-IXSZZQHY.js +18 -0
  191. package/dist/parser-JAL2HD4I.js +13 -0
  192. package/dist/parser-KNSQSKQO.js +20 -0
  193. package/dist/parser-N5O4IHUN.js +13 -0
  194. package/dist/parser-NGU3ETO6.js +16 -0
  195. package/dist/parser-NRAI6O25.js +19 -0
  196. package/dist/parser-O5J4VBII.js +11 -0
  197. package/dist/parser-OV7NOBW6.js +21 -0
  198. package/dist/parser-PQ3POX45.js +23 -0
  199. package/dist/parser-TFZFBVWN.js +11 -0
  200. package/dist/parser-TRTHDFPP.js +18 -0
  201. package/dist/parser-VQP2UJ6W.js +11 -0
  202. package/dist/parser-XDVELHRK.js +13 -0
  203. package/dist/parser-XKRP7QKP.js +11 -0
  204. package/dist/parser-Y6WTBU76.js +14 -0
  205. package/dist/parser-ZSDPZYQP.js +12 -0
  206. package/dist/renderer-2XQQQ6QR.js +28 -0
  207. package/dist/renderer-5NDVNDAZ.js +26 -0
  208. package/dist/renderer-6EEZHMH4.js +26 -0
  209. package/dist/renderer-6W5462RB.js +43 -0
  210. package/dist/renderer-7MVLWWQD.js +22 -0
  211. package/dist/renderer-AWWAF6XD.js +33 -0
  212. package/dist/renderer-BYCNMBF7.js +34 -0
  213. package/dist/renderer-CLJHQPBJ.js +29 -0
  214. package/dist/renderer-GHPZMFU2.js +15 -0
  215. package/dist/renderer-JGBKUCZD.js +16 -0
  216. package/dist/renderer-KQB7UGDS.js +19 -0
  217. package/dist/renderer-PGX2TKVS.js +24 -0
  218. package/dist/renderer-QIWVHWZO.js +15 -0
  219. package/dist/renderer-RPOA5YPZ.js +35 -0
  220. package/dist/renderer-SMIBCRVB.js +24 -0
  221. package/dist/renderer-T7YKC5VP.js +28 -0
  222. package/dist/renderer-TOCOVLHS.js +37 -0
  223. package/dist/renderer-UWA5XS74.js +39 -0
  224. package/dist/renderer-VACVQYML.js +25 -0
  225. package/dist/renderer-W4M6QLIJ.js +37 -0
  226. package/dist/renderer-WZRREQ2P.js +23 -0
  227. package/dist/renderer-YY2OSF6E.js +27 -0
  228. package/dist/renderer-Z7I3W2PP.js +24 -0
  229. package/dist/renderer-ZGNTUWC4.js +22 -0
  230. package/dist/renderer-ZTR3DER3.js +19 -0
  231. package/dist/renderer-radial-C32GPJQ7.js +21 -0
  232. package/dist/resolver-NOAA7ID7.js +13 -0
  233. package/dist/state-collapse-HCGD6IVJ.js +8 -0
  234. package/dist/state-parser-Z2V23ATR.js +18 -0
  235. package/dist/state-renderer-RFYHSP4K.js +34 -0
  236. package/dist/themes-1-CuKpeH.d.cts +908 -0
  237. package/dist/themes-1-CuKpeH.d.ts +908 -0
  238. package/package.json +1 -1
  239. package/src/auto/index.ts +55 -57
  240. package/src/auto/shared.ts +142 -142
  241. package/src/auto/styles.ts +44 -199
  242. package/src/c4/renderer.ts +2 -2
  243. package/src/element/index.ts +29 -21
  244. package/src/infra/renderer.ts +1 -1
  245. package/src/render.ts +34 -14
  246. package/src/sitemap/renderer.ts +1 -1
  247. package/src/timeline/renderer.ts +1 -1
  248. package/src/utils/hover-styles.ts +6 -1
  249. package/src/utils/legend-d3.ts +1 -4
  250. package/src/utils/legend-svg.ts +1 -1
@@ -0,0 +1,422 @@
1
+ import {
2
+ acyclicOrient
3
+ } from "./chunk-YGJTDXVR.js";
4
+
5
+ // src/swimlane/layout.ts
6
+ var MARGIN = 30;
7
+ var COL_GAP = 64;
8
+ var NODE_W = 124;
9
+ var NODE_H = 44;
10
+ var DIAMOND = 56;
11
+ var TERM_D = 40;
12
+ var INTRA_GAP = 16;
13
+ var LANE_PAD = 22;
14
+ var MIN_LANE = NODE_H + 2 * LANE_PAD;
15
+ var LANE_HEADER = 116;
16
+ var PHASE_HEADER = 30;
17
+ var BACK_CHANNEL = 28;
18
+ var BACK_STEP = 18;
19
+ function nodeSize(shape) {
20
+ if (shape === "exclusive" || shape === "parallel")
21
+ return { w: DIAMOND, h: DIAMOND };
22
+ if (shape === "terminal") return { w: TERM_D, h: TERM_D };
23
+ return { w: NODE_W, h: NODE_H };
24
+ }
25
+ function compactRanks(ids, edges, laneOf, floors) {
26
+ const adj = /* @__PURE__ */ new Map();
27
+ const indeg = /* @__PURE__ */ new Map();
28
+ for (const id of ids) {
29
+ adj.set(id, []);
30
+ indeg.set(id, 0);
31
+ }
32
+ for (const e of edges) {
33
+ adj.get(e.from)?.push(e.to);
34
+ indeg.set(e.to, (indeg.get(e.to) ?? 0) + 1);
35
+ }
36
+ const rank = new Map(ids.map((id) => [id, 0]));
37
+ const laneMaxIn = /* @__PURE__ */ new Map();
38
+ for (const id of ids) laneMaxIn.set(id, /* @__PURE__ */ new Map());
39
+ const queue = ids.filter((id) => (indeg.get(id) ?? 0) === 0);
40
+ for (let qi = 0; qi < queue.length; qi++) {
41
+ const u = queue[qi];
42
+ const lu = laneOf(u);
43
+ const accIn = laneMaxIn.get(u);
44
+ const fl = floors?.get(u);
45
+ if (fl !== void 0 && (rank.get(u) ?? 0) < fl) rank.set(u, fl);
46
+ const sameLaneAnc = accIn.get(lu);
47
+ if (sameLaneAnc !== void 0 && (rank.get(u) ?? 0) <= sameLaneAnc) {
48
+ rank.set(u, sameLaneAnc + 1);
49
+ }
50
+ const ru = rank.get(u);
51
+ const accOut = new Map(accIn);
52
+ accOut.set(lu, Math.max(accOut.get(lu) ?? -1, ru));
53
+ for (const w of adj.get(u) ?? []) {
54
+ const cand = ru + (laneOf(w) === lu ? 1 : 0);
55
+ if (cand > (rank.get(w) ?? 0)) rank.set(w, cand);
56
+ const wIn = laneMaxIn.get(w);
57
+ for (const [lane, r] of accOut)
58
+ if (r > (wIn.get(lane) ?? -1)) wIn.set(lane, r);
59
+ const d = (indeg.get(w) ?? 0) - 1;
60
+ indeg.set(w, d);
61
+ if (d === 0) queue.push(w);
62
+ }
63
+ }
64
+ return rank;
65
+ }
66
+ function layoutSwimlane(parsed) {
67
+ const dir = parsed.direction;
68
+ const isLR = dir === "LR";
69
+ const nodeById = new Map(parsed.nodes.map((n) => [n.id, n]));
70
+ const ids = parsed.nodes.map((n) => n.id);
71
+ const size = new Map(parsed.nodes.map((n) => [n.id, nodeSize(n.shape)]));
72
+ const flowLenOf = (id) => {
73
+ const s = size.get(id);
74
+ return isLR ? s.w : s.h;
75
+ };
76
+ const crossLenOf = (id) => {
77
+ const s = size.get(id);
78
+ return isLR ? s.h : s.w;
79
+ };
80
+ const realEdges = parsed.edges.map((e, idx) => ({ from: e.source, to: e.target, idx })).filter(
81
+ (e) => e.from !== e.to && nodeById.has(e.from) && nodeById.has(e.to)
82
+ );
83
+ const { dag } = acyclicOrient(ids, realEdges);
84
+ const laneOf = (id) => nodeById.get(id).lane;
85
+ const baseRank = compactRanks(
86
+ ids,
87
+ dag.map((d) => ({ from: d.from, to: d.to })),
88
+ laneOf
89
+ );
90
+ let finalRank = /* @__PURE__ */ new Map();
91
+ for (const id of ids) finalRank.set(id, baseRank.get(id) ?? 0);
92
+ {
93
+ const laneIdx = new Map(parsed.lanes.map((l, i) => [l.id, i]));
94
+ const dagEdges = dag.map((d) => ({ from: d.from, to: d.to }));
95
+ const floors = /* @__PURE__ */ new Map();
96
+ for (let pass = 0; pass < ids.length; pass++) {
97
+ let changed = false;
98
+ for (const e of realEdges) {
99
+ if ((finalRank.get(e.to) ?? 0) >= (finalRank.get(e.from) ?? 0))
100
+ continue;
101
+ for (const leg of [e.from, e.to]) {
102
+ const legRank = finalRank.get(leg);
103
+ const legLane = laneIdx.get(laneOf(leg));
104
+ for (const id of ids) {
105
+ if (id === e.from || id === e.to) continue;
106
+ if (finalRank.get(id) !== legRank) continue;
107
+ if ((laneIdx.get(laneOf(id)) ?? 0) <= legLane) continue;
108
+ if ((floors.get(id) ?? 0) <= legRank) {
109
+ floors.set(id, legRank + 1);
110
+ changed = true;
111
+ }
112
+ }
113
+ }
114
+ }
115
+ if (!changed) break;
116
+ finalRank = compactRanks(ids, dagEdges, laneOf, floors);
117
+ }
118
+ }
119
+ const usedRanks = Array.from(
120
+ new Set(ids.map((id) => finalRank.get(id)))
121
+ ).sort((a, b) => a - b);
122
+ const rankIndex = new Map(usedRanks.map((r, i) => [r, i]));
123
+ const R = usedRanks.length;
124
+ const riOf = (id) => rankIndex.get(finalRank.get(id)) ?? 0;
125
+ const contentFlowStart = LANE_HEADER + MARGIN;
126
+ const colFlowLen = Array.from({ length: R }, () => 0);
127
+ for (const id of ids) {
128
+ const ri = riOf(id);
129
+ colFlowLen[ri] = Math.max(colFlowLen[ri], flowLenOf(id));
130
+ }
131
+ const flowCenter = [];
132
+ const colLen = [];
133
+ {
134
+ let acc = contentFlowStart;
135
+ for (let ri = 0; ri < R; ri++) {
136
+ const len = Math.max(colFlowLen[ri], NODE_W);
137
+ colLen[ri] = len;
138
+ flowCenter[ri] = acc + len / 2;
139
+ acc += len + COL_GAP;
140
+ }
141
+ }
142
+ const gapMid = (gi) => flowCenter[gi] + colLen[gi] / 2 + COL_GAP / 2;
143
+ const totalFlow = (R > 0 ? flowCenter[R - 1] + Math.max(colFlowLen[R - 1], NODE_W) / 2 : contentFlowStart) + MARGIN;
144
+ const contentCrossStart = (parsed.phases.length ? PHASE_HEADER : 0) + MARGIN;
145
+ const cellNodes = /* @__PURE__ */ new Map();
146
+ for (const n of parsed.nodes) {
147
+ const key = `${n.lane}\0${riOf(n.id)}`;
148
+ (cellNodes.get(key) ?? cellNodes.set(key, []).get(key)).push(n.id);
149
+ }
150
+ const cellCross = (laneId, ri) => {
151
+ const arr = cellNodes.get(`${laneId}\0${ri}`) ?? [];
152
+ if (arr.length === 0) return 0;
153
+ return arr.reduce((s, id) => s + crossLenOf(id), 0) + INTRA_GAP * (arr.length - 1);
154
+ };
155
+ const laneCrossStart = /* @__PURE__ */ new Map();
156
+ const laneThick = /* @__PURE__ */ new Map();
157
+ const laneCenter = /* @__PURE__ */ new Map();
158
+ {
159
+ let acc = contentCrossStart;
160
+ for (const lane of parsed.lanes) {
161
+ let maxCell = 0;
162
+ for (let ri = 0; ri < R; ri++)
163
+ maxCell = Math.max(maxCell, cellCross(lane.id, ri));
164
+ const thick = Math.max(MIN_LANE, maxCell + 2 * LANE_PAD);
165
+ laneCrossStart.set(lane.id, acc);
166
+ laneThick.set(lane.id, thick);
167
+ laneCenter.set(lane.id, acc + thick / 2);
168
+ acc += thick;
169
+ }
170
+ }
171
+ const laneCrossEnd = (() => {
172
+ let acc = contentCrossStart;
173
+ for (const lane of parsed.lanes) acc += laneThick.get(lane.id);
174
+ return acc;
175
+ })();
176
+ const nodeFlow = /* @__PURE__ */ new Map();
177
+ const nodeCross = /* @__PURE__ */ new Map();
178
+ for (const [key, arr] of cellNodes) {
179
+ const sep = key.indexOf("\0");
180
+ const laneId = key.slice(0, sep);
181
+ const center = laneCenter.get(laneId) ?? contentCrossStart;
182
+ const stackH = arr.reduce((s, id) => s + crossLenOf(id), 0) + INTRA_GAP * (arr.length - 1);
183
+ let c = center - stackH / 2;
184
+ for (const id of arr) {
185
+ const cl = crossLenOf(id);
186
+ nodeCross.set(id, c + cl / 2);
187
+ c += cl + INTRA_GAP;
188
+ nodeFlow.set(id, flowCenter[riOf(id)]);
189
+ }
190
+ }
191
+ let backCount = 0;
192
+ for (const e of realEdges)
193
+ if ((finalRank.get(e.to) ?? 0) < (finalRank.get(e.from) ?? 0)) backCount++;
194
+ const needsBack = backCount > 0;
195
+ const backReserve = needsBack ? BACK_CHANNEL + BACK_STEP * (backCount - 1) : 0;
196
+ const totalCross = laneCrossEnd + backReserve + MARGIN;
197
+ const project = (flow, cross) => isLR ? { x: flow, y: cross } : { x: cross, y: flow };
198
+ const layoutNodes = parsed.nodes.map((n) => {
199
+ const s = size.get(n.id);
200
+ const p = project(nodeFlow.get(n.id), nodeCross.get(n.id));
201
+ return {
202
+ id: n.id,
203
+ label: n.label,
204
+ shape: n.shape,
205
+ event: n.event,
206
+ lane: n.lane,
207
+ ...n.phase !== void 0 && { phase: n.phase },
208
+ ...n.color !== void 0 && { color: n.color },
209
+ tags: n.tags,
210
+ x: p.x,
211
+ y: p.y,
212
+ width: s.w,
213
+ height: s.h,
214
+ lineNumber: n.lineNumber
215
+ };
216
+ });
217
+ const CHANNEL_GAP = 16;
218
+ const bendOffset = new Array(parsed.edges.length).fill(0);
219
+ {
220
+ const groups = /* @__PURE__ */ new Map();
221
+ parsed.edges.forEach((e, i) => {
222
+ const s = nodeById.get(e.source);
223
+ const t = nodeById.get(e.target);
224
+ if (!s || !t || s.id === t.id) return;
225
+ const sR = finalRank.get(s.id) ?? 0;
226
+ const tR = finalRank.get(t.id) ?? 0;
227
+ if (tR <= sR) return;
228
+ if (Math.abs((nodeCross.get(s.id) ?? 0) - (nodeCross.get(t.id) ?? 0)) < 0.5)
229
+ return;
230
+ const key = `${e.target}\0${sR}`;
231
+ (groups.get(key) ?? groups.set(key, []).get(key)).push(i);
232
+ });
233
+ for (const idxs of groups.values()) {
234
+ if (idxs.length < 2) continue;
235
+ idxs.sort(
236
+ (a, b) => (nodeCross.get(parsed.edges[a].source) ?? 0) - (nodeCross.get(parsed.edges[b].source) ?? 0)
237
+ );
238
+ idxs.forEach((idx, k) => {
239
+ bendOffset[idx] = (k - (idxs.length - 1) / 2) * CHANNEL_GAP;
240
+ });
241
+ }
242
+ }
243
+ const BLOCK_CLEAR = 4;
244
+ const routeBackLeg = (selfId, flow, fromCross, toCross, ri, towardFlow) => {
245
+ let firstBlockTop = Infinity;
246
+ for (const id of ids) {
247
+ if (id === selfId) continue;
248
+ const fh = flowLenOf(id) / 2 + BLOCK_CLEAR;
249
+ if (Math.abs(nodeFlow.get(id) - flow) >= fh) continue;
250
+ const ch = crossLenOf(id) / 2;
251
+ const c = nodeCross.get(id);
252
+ if (c + ch <= fromCross || c - ch >= toCross) continue;
253
+ firstBlockTop = Math.min(firstBlockTop, c - ch);
254
+ }
255
+ if (firstBlockTop === Infinity) return { flow };
256
+ const leftGap = ri - 1;
257
+ const rightGap = ri < R - 1 ? ri : -1;
258
+ let gi = towardFlow < flow ? leftGap : rightGap;
259
+ if (gi < 0) gi = towardFlow < flow ? rightGap : leftGap;
260
+ if (gi < 0) return { flow };
261
+ return { flow: gapMid(gi), jogCross: (fromCross + firstBlockTop) / 2 };
262
+ };
263
+ let backIdx = 0;
264
+ const layoutEdges = [];
265
+ parsed.edges.forEach((e, ei) => {
266
+ const s = nodeById.get(e.source);
267
+ const t = nodeById.get(e.target);
268
+ if (!s || !t || s.id === t.id) return;
269
+ const sFlow = nodeFlow.get(s.id);
270
+ const sCross = nodeCross.get(s.id);
271
+ const tFlow = nodeFlow.get(t.id);
272
+ const tCross = nodeCross.get(t.id);
273
+ const sFlowHalf = flowLenOf(s.id) / 2;
274
+ const tFlowHalf = flowLenOf(t.id) / 2;
275
+ const sCrossHalf = crossLenOf(s.id) / 2;
276
+ const tCrossHalf = crossLenOf(t.id) / 2;
277
+ const sRank = finalRank.get(s.id) ?? 0;
278
+ const tRank = finalRank.get(t.id) ?? 0;
279
+ let pts;
280
+ let back = false;
281
+ if (tRank > sRank) {
282
+ const a = sFlow + sFlowHalf;
283
+ const b = tFlow - tFlowHalf;
284
+ if (Math.abs(sCross - tCross) < 0.5) {
285
+ pts = [project(a, sCross), project(b, tCross)];
286
+ } else {
287
+ const mid = (a + b) / 2 + bendOffset[ei];
288
+ pts = [
289
+ project(a, sCross),
290
+ project(mid, sCross),
291
+ project(mid, tCross),
292
+ project(b, tCross)
293
+ ];
294
+ }
295
+ } else if (tRank === sRank) {
296
+ const downward = tCross >= sCross;
297
+ const a = sCross + (downward ? sCrossHalf : -sCrossHalf);
298
+ const b = tCross + (downward ? -tCrossHalf : tCrossHalf);
299
+ if (Math.abs(sFlow - tFlow) < 0.5) {
300
+ pts = [project(sFlow, a), project(tFlow, b)];
301
+ } else {
302
+ const midC = (a + b) / 2;
303
+ pts = [
304
+ project(sFlow, a),
305
+ project(sFlow, midC),
306
+ project(tFlow, midC),
307
+ project(tFlow, b)
308
+ ];
309
+ }
310
+ } else {
311
+ back = true;
312
+ const channelC = laneCrossEnd + BACK_CHANNEL + BACK_STEP * backIdx;
313
+ backIdx++;
314
+ const sBottom = sCross + sCrossHalf;
315
+ const tBottom = tCross + tCrossHalf;
316
+ const sLeg = routeBackLeg(
317
+ s.id,
318
+ sFlow,
319
+ sBottom,
320
+ channelC,
321
+ riOf(s.id),
322
+ tFlow
323
+ );
324
+ const tLeg = routeBackLeg(
325
+ t.id,
326
+ tFlow,
327
+ tBottom,
328
+ channelC,
329
+ riOf(t.id),
330
+ sFlow
331
+ );
332
+ pts = [
333
+ project(sFlow, sBottom),
334
+ ...sLeg.jogCross !== void 0 ? [project(sFlow, sLeg.jogCross), project(sLeg.flow, sLeg.jogCross)] : [],
335
+ project(sLeg.flow, channelC),
336
+ project(tLeg.flow, channelC),
337
+ ...tLeg.jogCross !== void 0 ? [project(tLeg.flow, tLeg.jogCross), project(tFlow, tLeg.jogCross)] : [],
338
+ project(tFlow, tBottom)
339
+ ];
340
+ }
341
+ layoutEdges.push({
342
+ source: e.source,
343
+ target: e.target,
344
+ ...e.label !== void 0 && { label: e.label },
345
+ points: pts,
346
+ back,
347
+ lineNumber: e.lineNumber
348
+ });
349
+ });
350
+ const projectBand = (flowStart, flowExtent, crossStart, crossExtent) => isLR ? { x: flowStart, y: crossStart, width: flowExtent, height: crossExtent } : { x: crossStart, y: flowStart, width: crossExtent, height: flowExtent };
351
+ const lanes = parsed.lanes.map((lane) => {
352
+ const box = projectBand(
353
+ 0,
354
+ totalFlow,
355
+ laneCrossStart.get(lane.id),
356
+ laneThick.get(lane.id)
357
+ );
358
+ return {
359
+ id: lane.id,
360
+ label: lane.label,
361
+ ...lane.color !== void 0 && { color: lane.color },
362
+ ...box,
363
+ headerSize: LANE_HEADER,
364
+ lineNumber: lane.lineNumber
365
+ };
366
+ });
367
+ const phaseOrder = new Map(parsed.phases.map((ph, i) => [ph.id, i]));
368
+ const colMinPhase = Array.from(
369
+ { length: R },
370
+ () => void 0
371
+ );
372
+ for (const n of parsed.nodes) {
373
+ if (n.phase === void 0) continue;
374
+ const po = phaseOrder.get(n.phase);
375
+ if (po === void 0) continue;
376
+ const ri = riOf(n.id);
377
+ const cur = colMinPhase[ri];
378
+ if (cur === void 0 || po < cur) colMinPhase[ri] = po;
379
+ }
380
+ const colPhase = Array.from({ length: R }, () => 0);
381
+ let carry = 0;
382
+ for (let ri = 0; ri < R; ri++) {
383
+ const v = colMinPhase[ri];
384
+ if (v !== void 0 && v > carry) carry = v;
385
+ colPhase[ri] = carry;
386
+ }
387
+ const colMid = (i, j) => (flowCenter[i] + flowCenter[j]) / 2;
388
+ const phaseBands = [];
389
+ if (parsed.phases.length > 0 && R > 0) {
390
+ let start = 0;
391
+ for (let ri = 1; ri <= R; ri++) {
392
+ if (ri === R || colPhase[ri] !== colPhase[start]) {
393
+ const a = start;
394
+ const b = ri - 1;
395
+ const phase = parsed.phases[colPhase[start]];
396
+ const leftEdge = a === 0 ? 0 : colMid(a - 1, a);
397
+ const rightEdge = b === R - 1 ? totalFlow : colMid(b, b + 1);
398
+ phaseBands.push({
399
+ id: phase.id,
400
+ label: phase.label,
401
+ ...projectBand(leftEdge, rightEdge - leftEdge, 0, totalCross),
402
+ headerSize: PHASE_HEADER,
403
+ lineNumber: phase.lineNumber
404
+ });
405
+ start = ri;
406
+ }
407
+ }
408
+ }
409
+ return {
410
+ nodes: layoutNodes,
411
+ edges: layoutEdges,
412
+ lanes,
413
+ phases: phaseBands,
414
+ width: isLR ? totalFlow : totalCross,
415
+ height: isLR ? totalCross : totalFlow
416
+ };
417
+ }
418
+
419
+ export {
420
+ layoutSwimlane
421
+ };
422
+ //# sourceMappingURL=chunk-725LDASD.js.map
@@ -0,0 +1,130 @@
1
+ import {
2
+ PYRAMID_REGISTRY,
3
+ measureIndent,
4
+ parseFirstLine,
5
+ splitNameAndMeta,
6
+ tryParseSharedOption,
7
+ warnUnknownMetaKeys
8
+ } from "./chunk-Y3J7VR52.js";
9
+ import {
10
+ makeDgmoError,
11
+ makeFail
12
+ } from "./chunk-CXK4DZH3.js";
13
+
14
+ // src/pyramid/parser.ts
15
+ var MAX_LAYERS = 15;
16
+ function parsePyramid(content) {
17
+ const options = {};
18
+ const result = {
19
+ type: "pyramid",
20
+ title: "",
21
+ titleLineNumber: 0,
22
+ layers: [],
23
+ inverted: false,
24
+ options,
25
+ diagnostics: [],
26
+ error: null
27
+ };
28
+ const lines = content.split("\n");
29
+ let headerParsed = false;
30
+ let currentLayer = null;
31
+ const fail = makeFail(result);
32
+ const warn = (line, message, severity = "warning") => {
33
+ result.diagnostics.push(makeDgmoError(line, message, severity));
34
+ };
35
+ const flushLayer = () => {
36
+ if (currentLayer) {
37
+ result.layers.push(currentLayer);
38
+ currentLayer = null;
39
+ }
40
+ };
41
+ for (let i = 0; i < lines.length; i++) {
42
+ const lineNum = i + 1;
43
+ const raw = lines[i];
44
+ const trimmed = raw.trim();
45
+ if (!trimmed || trimmed.startsWith("//")) continue;
46
+ const indent = measureIndent(raw);
47
+ if (!headerParsed) {
48
+ const firstLineResult = parseFirstLine(trimmed);
49
+ if (firstLineResult?.chartType === "pyramid") {
50
+ result.title = firstLineResult.title ?? "";
51
+ result.titleLineNumber = lineNum;
52
+ headerParsed = true;
53
+ continue;
54
+ }
55
+ return fail(lineNum, 'Expected "pyramid [Title]" as the first line.');
56
+ }
57
+ if (indent === 0 && trimmed.toLowerCase() === "inverted") {
58
+ result.inverted = true;
59
+ continue;
60
+ }
61
+ if (indent === 0 && tryParseSharedOption(trimmed, options)) {
62
+ continue;
63
+ }
64
+ if (indent === 0) {
65
+ flushLayer();
66
+ const split = splitNameAndMeta(
67
+ trimmed,
68
+ PYRAMID_REGISTRY,
69
+ /* @__PURE__ */ new Map(),
70
+ void 0,
71
+ result.diagnostics,
72
+ lineNum
73
+ );
74
+ warnUnknownMetaKeys(
75
+ split.meta,
76
+ PYRAMID_REGISTRY,
77
+ (msg) => warn(lineNum, msg),
78
+ split.name
79
+ );
80
+ const label = split.name;
81
+ const restMeta = { ...split.meta };
82
+ const color = split.color ?? restMeta["color"];
83
+ delete restMeta["color"];
84
+ const description = [];
85
+ const descFromMeta = restMeta["description"];
86
+ if (descFromMeta) description.push(descFromMeta);
87
+ delete restMeta["description"];
88
+ if (!label) {
89
+ warn(lineNum, "Empty layer label.");
90
+ continue;
91
+ }
92
+ currentLayer = {
93
+ label,
94
+ lineNumber: lineNum,
95
+ ...color !== void 0 && { color },
96
+ description,
97
+ metadata: restMeta
98
+ };
99
+ continue;
100
+ }
101
+ if (!currentLayer) {
102
+ warn(
103
+ lineNum,
104
+ `Indented description "${trimmed}" has no layer above it \u2014 add a layer name on a non-indented line first. (\xA723)`
105
+ );
106
+ continue;
107
+ }
108
+ const descLine = trimmed.startsWith("- ") ? `\u2022 ${trimmed.substring(2)}` : trimmed;
109
+ currentLayer.description.push(descLine);
110
+ }
111
+ flushLayer();
112
+ if (result.layers.length < 2) {
113
+ return fail(
114
+ result.titleLineNumber || 1,
115
+ "pyramid requires at least 2 layers."
116
+ );
117
+ }
118
+ if (result.layers.length > MAX_LAYERS) {
119
+ return fail(
120
+ result.titleLineNumber || 1,
121
+ `pyramid supports at most ${MAX_LAYERS} layers; got ${result.layers.length}.`
122
+ );
123
+ }
124
+ return result;
125
+ }
126
+
127
+ export {
128
+ parsePyramid
129
+ };
130
+ //# sourceMappingURL=chunk-76OWZ3BA.js.map