@meltemi/diagrams-layout 0.0.0-stage → 1.9.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 (99) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +52 -2
  3. package/dist/audit.d.ts +58 -0
  4. package/dist/audit.d.ts.map +1 -0
  5. package/dist/audit.js +239 -0
  6. package/dist/audit.js.map +1 -0
  7. package/dist/checks.d.ts +38 -0
  8. package/dist/checks.d.ts.map +1 -0
  9. package/dist/checks.js +331 -0
  10. package/dist/checks.js.map +1 -0
  11. package/dist/constraints.d.ts +20 -0
  12. package/dist/constraints.d.ts.map +1 -0
  13. package/dist/constraints.js +149 -0
  14. package/dist/constraints.js.map +1 -0
  15. package/dist/engine.d.ts +96 -0
  16. package/dist/engine.d.ts.map +1 -0
  17. package/dist/engine.js +3 -0
  18. package/dist/engine.js.map +1 -0
  19. package/dist/frame.d.ts +17 -0
  20. package/dist/frame.d.ts.map +1 -0
  21. package/dist/frame.js +51 -0
  22. package/dist/frame.js.map +1 -0
  23. package/dist/free.d.ts +75 -0
  24. package/dist/free.d.ts.map +1 -0
  25. package/dist/free.js +122 -0
  26. package/dist/free.js.map +1 -0
  27. package/dist/geometry.d.ts +58 -0
  28. package/dist/geometry.d.ts.map +1 -0
  29. package/dist/geometry.js +223 -0
  30. package/dist/geometry.js.map +1 -0
  31. package/dist/icons.d.ts +16 -0
  32. package/dist/icons.d.ts.map +1 -0
  33. package/dist/icons.js +94 -0
  34. package/dist/icons.js.map +1 -0
  35. package/dist/index.d.ts +20 -0
  36. package/dist/index.d.ts.map +1 -0
  37. package/dist/index.js +19 -0
  38. package/dist/index.js.map +1 -0
  39. package/dist/layout.d.ts +206 -0
  40. package/dist/layout.d.ts.map +1 -0
  41. package/dist/layout.js +3527 -0
  42. package/dist/layout.js.map +1 -0
  43. package/dist/mark.d.ts +24 -0
  44. package/dist/mark.d.ts.map +1 -0
  45. package/dist/mark.js +60 -0
  46. package/dist/mark.js.map +1 -0
  47. package/dist/markers.d.ts +62 -0
  48. package/dist/markers.d.ts.map +1 -0
  49. package/dist/markers.js +255 -0
  50. package/dist/markers.js.map +1 -0
  51. package/dist/measure.d.ts +38 -0
  52. package/dist/measure.d.ts.map +1 -0
  53. package/dist/measure.js +44 -0
  54. package/dist/measure.js.map +1 -0
  55. package/dist/messages/en.d.ts +160 -0
  56. package/dist/messages/en.d.ts.map +1 -0
  57. package/dist/messages/en.js +163 -0
  58. package/dist/messages/en.js.map +1 -0
  59. package/dist/messages/es.d.ts +4 -0
  60. package/dist/messages/es.d.ts.map +1 -0
  61. package/dist/messages/es.js +104 -0
  62. package/dist/messages/es.js.map +1 -0
  63. package/dist/messages/index.d.ts +86 -0
  64. package/dist/messages/index.d.ts.map +1 -0
  65. package/dist/messages/index.js +17 -0
  66. package/dist/messages/index.js.map +1 -0
  67. package/dist/routing.d.ts +94 -0
  68. package/dist/routing.d.ts.map +1 -0
  69. package/dist/routing.js +549 -0
  70. package/dist/routing.js.map +1 -0
  71. package/dist/scene.d.ts +220 -0
  72. package/dist/scene.d.ts.map +1 -0
  73. package/dist/scene.js +5 -0
  74. package/dist/scene.js.map +1 -0
  75. package/dist/sequence.d.ts +17 -0
  76. package/dist/sequence.d.ts.map +1 -0
  77. package/dist/sequence.js +875 -0
  78. package/dist/sequence.js.map +1 -0
  79. package/dist/shapes.d.ts +140 -0
  80. package/dist/shapes.d.ts.map +1 -0
  81. package/dist/shapes.js +1030 -0
  82. package/dist/shapes.js.map +1 -0
  83. package/dist/styles.d.ts +58 -0
  84. package/dist/styles.d.ts.map +1 -0
  85. package/dist/styles.js +106 -0
  86. package/dist/styles.js.map +1 -0
  87. package/dist/text.d.ts +8 -0
  88. package/dist/text.d.ts.map +1 -0
  89. package/dist/text.js +28 -0
  90. package/dist/text.js.map +1 -0
  91. package/dist/theme.d.ts +100 -0
  92. package/dist/theme.d.ts.map +1 -0
  93. package/dist/theme.js +246 -0
  94. package/dist/theme.js.map +1 -0
  95. package/dist/viewport.d.ts +98 -0
  96. package/dist/viewport.d.ts.map +1 -0
  97. package/dist/viewport.js +177 -0
  98. package/dist/viewport.js.map +1 -0
  99. package/package.json +49 -3
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Architecture Studio contributors
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -1,3 +1,53 @@
1
- # Temporary Holding Version
1
+ # @meltemi/diagrams-layout
2
2
 
3
- This version is a temporary placeholder for this package. An operational version to replace this has been submitted for review and is awaiting a staged release.
3
+ Layout of every profile into a vector scene: measured boxes, ports, constraints, connector
4
+ routing, label placement, composition checks and the label audit. Automatic arrangement comes from
5
+ an engine such as `@meltemi/diagrams-layout-elk`.
6
+
7
+ It is part of [Meltemi Diagrams](https://github.com/askenaz-dev/meltemi-diagrams#readme), diagrams as code with a canvas, motion and
8
+ exports. Every package of the product has the same version.
9
+
10
+ ## Install
11
+
12
+ ```bash
13
+ npm install @meltemi/diagrams-layout
14
+ ```
15
+
16
+ Node 22.12.0 or later. The package is an ES module with type declarations.
17
+
18
+ ## Use
19
+
20
+ ```ts
21
+ import { layoutDiagram } from "@meltemi/diagrams-layout";
22
+ import { createElkEngine } from "@meltemi/diagrams-layout-elk";
23
+ import { compile } from "@meltemi/diagrams-model";
24
+ import { renderSvg } from "@meltemi/diagrams-render";
25
+
26
+ const text = `language "0.2"
27
+
28
+ diagram shop: flow {
29
+ web["Web shop"]
30
+ api["Orders API"]
31
+ db[("Orders")]
32
+ web -> api: "HTTPS" as call
33
+ api -> db: "SQL" as store
34
+ }
35
+ `;
36
+
37
+ const compilation = compile(text);
38
+ const result = layoutDiagram(compilation, compilation.document.diagrams[0]!, {
39
+ engine: createElkEngine(),
40
+ });
41
+ console.log(result.diagnostics.map((d) => d.code)); // composition and label findings
42
+ console.log(renderSvg(result.scene!).slice(0, 4)); // <svg
43
+ ```
44
+
45
+ ## Documentation
46
+
47
+ - [Layout](https://github.com/askenaz-dev/meltemi-diagrams/blob/main/docs/language/layout.md)
48
+ - [Styles and themes](https://github.com/askenaz-dev/meltemi-diagrams/blob/main/docs/language/styles.md)
49
+ - [All documentation](https://github.com/askenaz-dev/meltemi-diagrams/blob/main/docs/README.md)
50
+
51
+ ## Licence
52
+
53
+ MIT. Third-party components and their licences are listed in [THIRD_PARTY_LICENSES.md](https://github.com/askenaz-dev/meltemi-diagrams/blob/main/THIRD_PARTY_LICENSES.md).
@@ -0,0 +1,58 @@
1
+ import type { TextMeasurer } from "./measure.js";
2
+ import type { GroupItem, Scene } from "./scene.js";
3
+ /** A rectangle in scene pixels. */
4
+ interface Box {
5
+ readonly x: number;
6
+ readonly y: number;
7
+ readonly width: number;
8
+ readonly height: number;
9
+ }
10
+ /** A text of the scene with the box its glyphs cover and the drawing it belongs to. */
11
+ export interface PlacedText {
12
+ readonly text: string;
13
+ readonly box: Box;
14
+ /** The id of the element, relation, event or label that draws it; `frame` for the frame. */
15
+ readonly owner: string;
16
+ readonly role: GroupItem["role"];
17
+ }
18
+ /** A label that is cut, or that overlaps another label, a box or a connector. */
19
+ export type LabelProblem = {
20
+ readonly kind: "cut";
21
+ readonly text: PlacedText;
22
+ /** What cuts it: its own shape, the background behind it, or the edge of the picture. */
23
+ readonly by: "shape" | "background" | "picture";
24
+ /** How far the text goes beyond it, in pixels. */
25
+ readonly overflow: number;
26
+ } | {
27
+ readonly kind: "overlap";
28
+ readonly text: PlacedText;
29
+ /** Another label, the box of an element, or a connector. */
30
+ readonly other: {
31
+ readonly kind: "text" | "box" | "connector";
32
+ readonly owner: string;
33
+ readonly text?: string;
34
+ };
35
+ };
36
+ export interface AuditOptions {
37
+ /**
38
+ * Elements drawn on the sheet by hand as annotations (tags, notes, free texts and icons): their
39
+ * labels may lie on boxes, as a badge on a corner does, but not on other labels.
40
+ */
41
+ readonly annotations?: ReadonlySet<string>;
42
+ /** Free diagrams: the layer of each element; labels may lie on boxes of other layers. */
43
+ readonly layers?: ReadonlyMap<string, string>;
44
+ }
45
+ /**
46
+ * Checks the labels of a laid-out scene. Every text must lie inside the picture, inside the
47
+ * element that draws it (the inscribed rectangle of a shape other than a box, `SceneBounds.inner`,
48
+ * or the label an icon shape draws outside its box, `SceneBounds.label`),
49
+ * and inside the background drawn just before it (the pill of a relation's label, the band of a
50
+ * guard). No text may overlap another element's text, the box of an element
51
+ * it does not belong to (containers hold labels; annotations may sit on boxes), or a connector
52
+ * other than its own. A container's own texts may lie over the boxes it holds; two texts that
53
+ * coincide are still reported. Text boxes are measured with the scene's fonts, from the cap
54
+ * height above the baseline to the descenders below it.
55
+ */
56
+ export declare function auditLabels(scene: Scene, measurer: TextMeasurer, options?: AuditOptions): LabelProblem[];
57
+ export {};
58
+ //# sourceMappingURL=audit.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit.d.ts","sourceRoot":"","sources":["../src/audit.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,cAAc,CAAC;AACjD,OAAO,KAAK,EAAE,SAAS,EAAE,KAAK,EAAuB,MAAM,YAAY,CAAC;AAExE,mCAAmC;AACnC,UAAU,GAAG;IACX,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB;AAED,uFAAuF;AACvF,MAAM,WAAW,UAAU;IACzB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,GAAG,EAAE,GAAG,CAAC;IAClB,4FAA4F;IAC5F,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,IAAI,EAAE,SAAS,CAAC,MAAM,CAAC,CAAC;CAClC;AAED,iFAAiF;AACjF,MAAM,MAAM,YAAY,GACpB;IACE,QAAQ,CAAC,IAAI,EAAE,KAAK,CAAC;IACrB,QAAQ,CAAC,IAAI,EAAE,UAAU,CAAC;IAC1B,yFAAyF;IACzF,QAAQ,CAAC,EAAE,EAAE,OAAO,GAAG,YAAY,GAAG,SAAS,CAAC;IAChD,kDAAkD;IAClD,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;CAC3B,GACD;IACE,QAAQ,CAAC,IAAI,EAAE,SAAS,CAAC;IACzB,QAAQ,CAAC,IAAI,EAAE,UAAU,CAAC;IAC1B,4DAA4D;IAC5D,QAAQ,CAAC,KAAK,EAAE;QACd,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,KAAK,GAAG,WAAW,CAAC;QAC5C,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;QACvB,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,CAAC;KACxB,CAAC;CACH,CAAC;AAEN,MAAM,WAAW,YAAY;IAC3B;;;OAGG;IACH,QAAQ,CAAC,WAAW,CAAC,EAAE,WAAW,CAAC,MAAM,CAAC,CAAC;IAC3C,yFAAyF;IACzF,QAAQ,CAAC,MAAM,CAAC,EAAE,WAAW,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAC/C;AA0FD;;;;;;;;;;GAUG;AACH,wBAAgB,WAAW,CACzB,KAAK,EAAE,KAAK,EACZ,QAAQ,EAAE,YAAY,EACtB,OAAO,GAAE,YAAiB,GACzB,YAAY,EAAE,CA0JhB"}
package/dist/audit.js ADDED
@@ -0,0 +1,239 @@
1
+ /** Overlaps smaller than this, in pixels, are rounding, not collisions. */
2
+ const TOLERANCE = 0.75;
3
+ const intersects = (a, b) => Math.min(a.x + a.width, b.x + b.width) - Math.max(a.x, b.x) > TOLERANCE &&
4
+ Math.min(a.y + a.height, b.y + b.height) - Math.max(a.y, b.y) > TOLERANCE;
5
+ const contains = (outer, inner) => inner.x >= outer.x - TOLERANCE &&
6
+ inner.y >= outer.y - TOLERANCE &&
7
+ inner.x + inner.width <= outer.x + outer.width + TOLERANCE &&
8
+ inner.y + inner.height <= outer.y + outer.height + TOLERANCE;
9
+ /** The box around every point of some lines. */
10
+ function extentOf(lines) {
11
+ let x0 = Infinity;
12
+ let y0 = Infinity;
13
+ let x1 = -Infinity;
14
+ let y1 = -Infinity;
15
+ for (const line of lines) {
16
+ for (const p of line) {
17
+ x0 = Math.min(x0, p.x);
18
+ y0 = Math.min(y0, p.y);
19
+ x1 = Math.max(x1, p.x);
20
+ y1 = Math.max(y1, p.y);
21
+ }
22
+ }
23
+ return { x: x0, y: y0, width: x1 - x0, height: y1 - y0 };
24
+ }
25
+ /** Whether two boxes touch, borders included. */
26
+ const intersectsLoose = (a, b) => a.x <= b.x + b.width && b.x <= a.x + a.width && a.y <= b.y + b.height && b.y <= a.y + a.height;
27
+ /** How far `inner` goes beyond `outer` on its worst side. */
28
+ function overflow(outer, inner) {
29
+ return Math.max(outer.x - inner.x, outer.y - inner.y, inner.x + inner.width - (outer.x + outer.width), inner.y + inner.height - (outer.y + outer.height));
30
+ }
31
+ /** Whether a segment crosses the inside of a box (shrunk by the tolerance). */
32
+ function segmentCrosses(a, b, box) {
33
+ const x0 = box.x + TOLERANCE;
34
+ const y0 = box.y + TOLERANCE;
35
+ const x1 = box.x + box.width - TOLERANCE;
36
+ const y1 = box.y + box.height - TOLERANCE;
37
+ if (x1 <= x0 || y1 <= y0)
38
+ return false;
39
+ // Liang–Barsky clipping: the segment crosses when some part of it lies inside.
40
+ let t0 = 0;
41
+ let t1 = 1;
42
+ const dx = b.x - a.x;
43
+ const dy = b.y - a.y;
44
+ for (const [p, q] of [
45
+ [-dx, a.x - x0],
46
+ [dx, x1 - a.x],
47
+ [-dy, a.y - y0],
48
+ [dy, y1 - a.y],
49
+ ]) {
50
+ if (p === 0) {
51
+ if (q < 0)
52
+ return false;
53
+ continue;
54
+ }
55
+ const r = q / p;
56
+ if (p < 0)
57
+ t0 = Math.max(t0, r);
58
+ else
59
+ t1 = Math.min(t1, r);
60
+ if (t0 > t1)
61
+ return false;
62
+ }
63
+ return t1 - t0 > 1e-6;
64
+ }
65
+ /**
66
+ * Checks the labels of a laid-out scene. Every text must lie inside the picture, inside the
67
+ * element that draws it (the inscribed rectangle of a shape other than a box, `SceneBounds.inner`,
68
+ * or the label an icon shape draws outside its box, `SceneBounds.label`),
69
+ * and inside the background drawn just before it (the pill of a relation's label, the band of a
70
+ * guard). No text may overlap another element's text, the box of an element
71
+ * it does not belong to (containers hold labels; annotations may sit on boxes), or a connector
72
+ * other than its own. A container's own texts may lie over the boxes it holds; two texts that
73
+ * coincide are still reported. Text boxes are measured with the scene's fonts, from the cap
74
+ * height above the baseline to the descenders below it.
75
+ */
76
+ export function auditLabels(scene, measurer, options = {}) {
77
+ const annotations = options.annotations ?? new Set();
78
+ const layers = options.layers ?? new Map();
79
+ const sameLayer = (a, b) => (layers.get(a) ?? "main") === (layers.get(b) ?? "main");
80
+ const owners = [];
81
+ const problems = [];
82
+ const view = scene.viewBox ?? { x: 0, y: 0, width: scene.width, height: scene.height };
83
+ const place = (item, owner, background) => {
84
+ const stack = item.font === "mono" ? scene.fonts.mono : scene.fonts.body;
85
+ const width = measurer.width(item.text, stack, item.weight, item.size);
86
+ const cap = measurer.capHeight(stack, item.weight);
87
+ const top = item.baseline - (cap + 0.06) * item.size;
88
+ const bottom = item.baseline + 0.22 * item.size;
89
+ const x = item.anchor === "start"
90
+ ? item.x
91
+ : item.anchor === "end"
92
+ ? item.x - width
93
+ : item.x - width / 2;
94
+ const text = {
95
+ text: item.text,
96
+ box: { x, y: top, width, height: bottom - top },
97
+ owner: owner.id,
98
+ role: owner.role,
99
+ };
100
+ owner.texts.push(text);
101
+ if (!contains(view, text.box)) {
102
+ problems.push({ kind: "cut", text, by: "picture", overflow: overflow(view, text.box) });
103
+ }
104
+ else if (background && !contains(background, text.box)) {
105
+ problems.push({
106
+ kind: "cut",
107
+ text,
108
+ by: "background",
109
+ overflow: overflow(background, text.box),
110
+ });
111
+ }
112
+ else if (owner.box && owner.role === "element") {
113
+ // A shape other than a box holds its text in its inscribed rectangle; an icon shape's label
114
+ // is its own text outside it.
115
+ const area = owner.inner ?? owner.box;
116
+ if (!contains(area, text.box) && !(owner.label && contains(owner.label, text.box))) {
117
+ problems.push({ kind: "cut", text, by: "shape", overflow: overflow(area, text.box) });
118
+ }
119
+ }
120
+ };
121
+ const walk = (items, owner) => {
122
+ let background;
123
+ for (const item of items) {
124
+ if (item.kind === "group") {
125
+ // The brand mark is drawn in its own units; its text sits beside it.
126
+ if (item.transform)
127
+ continue;
128
+ const next = {
129
+ id: item.id,
130
+ role: item.role,
131
+ ...(item.bounds
132
+ ? {
133
+ box: {
134
+ x: item.bounds.x,
135
+ y: item.bounds.y,
136
+ width: item.bounds.width,
137
+ height: item.bounds.height,
138
+ },
139
+ ...(item.bounds.inner ? { inner: item.bounds.inner } : {}),
140
+ ...(item.bounds.label ? { label: item.bounds.label } : {}),
141
+ }
142
+ : {}),
143
+ texts: [],
144
+ lines: [],
145
+ };
146
+ owners.push(next);
147
+ walk(item.items, next);
148
+ background = undefined;
149
+ }
150
+ else if (item.kind === "polyline" && owner?.role === "relation") {
151
+ owner.lines.push(item.points);
152
+ background = undefined;
153
+ }
154
+ else if (item.kind === "rect") {
155
+ // A rectangle drawn right before a text in a label is the background it sits on.
156
+ background = owner?.role === "label" ? item : undefined;
157
+ }
158
+ else if (item.kind === "text") {
159
+ if (item.text.trim() !== "") {
160
+ const target = owner ?? { id: "scene", role: "frame", texts: [], lines: [] };
161
+ if (!owner)
162
+ owners.push(target);
163
+ place(item, target, background);
164
+ }
165
+ background = undefined;
166
+ }
167
+ else {
168
+ background = undefined;
169
+ }
170
+ }
171
+ };
172
+ walk(scene.items, undefined);
173
+ const boxes = owners.filter((o) => o.box && o.role === "element");
174
+ // A container holds other boxes; labels may lie inside it.
175
+ const containers = new Set(boxes.filter((o) => boxes.some((p) => p !== o && contains(o.box, p.box))).map((o) => o.id));
176
+ // Labels against labels.
177
+ const texts = owners.flatMap((o) => o.texts).sort((a, b) => a.box.x - b.box.x);
178
+ for (let i = 0; i < texts.length; i++) {
179
+ const a = texts[i];
180
+ for (let j = i + 1; j < texts.length; j++) {
181
+ const b = texts[j];
182
+ if (b.box.x > a.box.x + a.box.width)
183
+ break;
184
+ if (a.owner === b.owner)
185
+ continue;
186
+ if (intersects(a.box, b.box)) {
187
+ problems.push({
188
+ kind: "overlap",
189
+ text: b,
190
+ other: { kind: "text", owner: a.owner, text: a.text },
191
+ });
192
+ }
193
+ }
194
+ }
195
+ // Labels against boxes they do not belong to, sorted by their left edge to stop early.
196
+ const sortedBoxes = [...boxes].sort((a, b) => a.box.x - b.box.x);
197
+ const boxOf = new Map(boxes.map((o) => [o.id, o.box]));
198
+ for (const text of texts) {
199
+ if (annotations.has(text.owner))
200
+ continue;
201
+ // A container's own text may lie over the boxes it holds.
202
+ const holder = containers.has(text.owner) ? boxOf.get(text.owner) : undefined;
203
+ for (const owner of sortedBoxes) {
204
+ if (owner.box.x > text.box.x + text.box.width)
205
+ break;
206
+ if (owner.id === text.owner || containers.has(owner.id) || annotations.has(owner.id))
207
+ continue;
208
+ if (!sameLayer(owner.id, text.owner))
209
+ continue;
210
+ if (holder && contains(holder, owner.box))
211
+ continue;
212
+ if (intersects(owner.box, text.box)) {
213
+ problems.push({ kind: "overlap", text, other: { kind: "box", owner: owner.id } });
214
+ }
215
+ }
216
+ }
217
+ // Labels against connectors other than their own (a relation's label group has its id).
218
+ const relations = owners
219
+ .filter((o) => o.role === "relation" && o.lines.length > 0)
220
+ .map((o) => ({ owner: o, extent: extentOf(o.lines) }));
221
+ for (const text of texts) {
222
+ for (const { owner: relation, extent } of relations) {
223
+ if (text.owner === relation.id || !intersectsLoose(extent, text.box))
224
+ continue;
225
+ const crossed = relation.lines.some((points) => {
226
+ for (let k = 1; k < points.length; k++) {
227
+ if (segmentCrosses(points[k - 1], points[k], text.box))
228
+ return true;
229
+ }
230
+ return false;
231
+ });
232
+ if (crossed) {
233
+ problems.push({ kind: "overlap", text, other: { kind: "connector", owner: relation.id } });
234
+ }
235
+ }
236
+ }
237
+ return problems;
238
+ }
239
+ //# sourceMappingURL=audit.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit.js","sourceRoot":"","sources":["../src/audit.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,38 @@
1
+ import type { Diagnostic } from "@meltemi/diagrams-language";
2
+ import type { Element, FlowDiagram, Point, Relation } from "@meltemi/diagrams-model";
3
+ import type { Box } from "./geometry.js";
4
+ /** A drawn connector for the checks: its polyline, whether it is curved, and its label pill. */
5
+ export interface CheckedConnector {
6
+ readonly relation: Relation;
7
+ readonly points: readonly Point[];
8
+ readonly curved: boolean;
9
+ readonly label: Box | undefined;
10
+ }
11
+ /** Shortest shared stretch of two collinear connectors that is reported. */
12
+ export declare const CONNECTOR_OVERLAP = 24;
13
+ /**
14
+ * Whether `inner` is stacked on `outer`: inside it, and at least `STACK_INSET` in from one of its
15
+ * sides. Two boxes that coincide hold each other, but one hides the other: they are no stack.
16
+ * Hosts use the same rule to find the boxes a box holds (a stack is the later box of a layer).
17
+ */
18
+ export declare function stacked(outer: Box, inner: Box): boolean;
19
+ /**
20
+ * Composition checks (decision D7 of the layout-engine change): overlapping boxes, boxes crossing
21
+ * group edges, labels lying on other connectors, boxes too close to the edge or title band of a
22
+ * placed group, and connectors running along each other. Tags and notes are not checked, nor are
23
+ * the text, icons and images of free diagrams; boxes and groups on different layers overlap on
24
+ * purpose, and a box declared after a box that holds it whole (`stacked`) is a stack, not an
25
+ * overlap; written the other way round, the overlap's hint says to declare the outer box first.
26
+ * `untitled` tells the groups without a title band (see `isUntitledGroup`). `outlines` holds the
27
+ * outline polygon of the boxes drawn with a shape other than a box (see `shapeOutline`): a
28
+ * connector crosses such a box only through its outline, not through its box's empty corners.
29
+ * `labels` holds the labels boxes draw outside them (an icon shape's): a box and its label are two
30
+ * rectangles that overlap other boxes and groups, with nothing between them; a box over another's
31
+ * label is an overlap, never a stack; boxes keep their groups' margins with their labels;
32
+ * connectors cross the boxes.
33
+ */
34
+ export declare function checkComposition(diagram: FlowDiagram, boxes: ReadonlyMap<string, Box>, connectors: readonly CheckedConnector[], explicitGroups: ReadonlySet<string>, theme: {
35
+ readonly groupPadding: number;
36
+ readonly groupHeader: number;
37
+ }, untitled: (group: Element) => boolean, outlines?: ReadonlyMap<string, readonly Point[]>, labels?: ReadonlyMap<string, Box>): Diagnostic[];
38
+ //# sourceMappingURL=checks.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"checks.d.ts","sourceRoot":"","sources":["../src/checks.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAS,MAAM,4BAA4B,CAAC;AACpE,OAAO,KAAK,EAAE,OAAO,EAAE,WAAW,EAAE,KAAK,EAAE,QAAQ,EAAE,MAAM,yBAAyB,CAAC;AACrF,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,eAAe,CAAC;AAKzC,gGAAgG;AAChG,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,QAAQ,EAAE,QAAQ,CAAC;IAC5B,QAAQ,CAAC,MAAM,EAAE,SAAS,KAAK,EAAE,CAAC;IAClC,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAC;IACzB,QAAQ,CAAC,KAAK,EAAE,GAAG,GAAG,SAAS,CAAC;CACjC;AAeD,4EAA4E;AAC5E,eAAO,MAAM,iBAAiB,KAAK,CAAC;AAkCpC;;;;GAIG;AACH,wBAAgB,OAAO,CAAC,KAAK,EAAE,GAAG,EAAE,KAAK,EAAE,GAAG,GAAG,OAAO,CAWvD;AAmGD;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,gBAAgB,CAC9B,OAAO,EAAE,WAAW,EACpB,KAAK,EAAE,WAAW,CAAC,MAAM,EAAE,GAAG,CAAC,EAC/B,UAAU,EAAE,SAAS,gBAAgB,EAAE,EACvC,cAAc,EAAE,WAAW,CAAC,MAAM,CAAC,EACnC,KAAK,EAAE;IAAE,QAAQ,CAAC,YAAY,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAA;CAAE,EACtE,QAAQ,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,EACrC,QAAQ,GAAE,WAAW,CAAC,MAAM,EAAE,SAAS,KAAK,EAAE,CAAa,EAC3D,MAAM,GAAE,WAAW,CAAC,MAAM,EAAE,GAAG,CAAa,GAC3C,UAAU,EAAE,CAwMd"}