@diagrammo/dgmo 0.32.1 → 0.34.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.
- package/.cursorrules +7 -2
- package/.github/copilot-instructions.md +7 -2
- package/.windsurfrules +7 -2
- package/SKILL.md +7 -2
- package/dist/advanced.cjs +1434 -443
- package/dist/advanced.d.cts +41 -1
- package/dist/advanced.d.ts +41 -1
- package/dist/advanced.js +1433 -443
- package/dist/auto.cjs +1242 -318
- package/dist/auto.js +91 -91
- package/dist/auto.mjs +1242 -318
- package/dist/cli.cjs +138 -136
- package/dist/index.cjs +1308 -317
- package/dist/index.d.cts +35 -1
- package/dist/index.d.ts +35 -1
- package/dist/index.js +1307 -317
- package/docs/ai-integration.md +7 -2
- package/docs/language-reference.md +39 -8
- package/package.json +2 -2
- package/src/advanced.ts +6 -1
- package/src/boxes-and-lines/label-placement.ts +339 -0
- package/src/boxes-and-lines/layout-grouped.ts +909 -0
- package/src/boxes-and-lines/layout-search.ts +34 -3
- package/src/boxes-and-lines/layout.ts +32 -7
- package/src/boxes-and-lines/parser.ts +3 -2
- package/src/boxes-and-lines/renderer.ts +67 -139
- package/src/c4/layout.ts +2 -1
- package/src/c4/parser.ts +3 -2
- package/src/c4/renderer.ts +3 -2
- package/src/cli.ts +68 -0
- package/src/er/parser.ts +2 -1
- package/src/er/renderer.ts +2 -1
- package/src/gantt/parser.ts +3 -5
- package/src/gantt/renderer.ts +7 -6
- package/src/index.ts +6 -1
- package/src/infra/parser.ts +2 -1
- package/src/infra/renderer.ts +4 -3
- package/src/journey-map/parser.ts +27 -8
- package/src/journey-map/renderer.ts +26 -9
- package/src/kanban/parser.ts +4 -3
- package/src/kanban/renderer.ts +6 -5
- package/src/map/completion.ts +116 -0
- package/src/map/layout.ts +4 -3
- package/src/map/parser.ts +3 -2
- package/src/mindmap/parser.ts +4 -3
- package/src/mindmap/renderer.ts +2 -1
- package/src/org/layout.ts +3 -2
- package/src/org/parser.ts +3 -2
- package/src/org/renderer.ts +5 -4
- package/src/pert/parser.ts +3 -2
- package/src/sequence/renderer.ts +10 -12
- package/src/sequence/tag-resolution.ts +2 -1
- package/src/sitemap/layout.ts +3 -2
- package/src/sitemap/parser.ts +36 -2
- package/src/sitemap/renderer.ts +12 -6
- package/src/timeline/renderer.ts +4 -3
- package/src/utils/legend-d3.ts +4 -3
- package/src/utils/legend-svg.ts +3 -2
- package/src/utils/tag-groups.ts +28 -7
- package/src/visualizations/parse.ts +2 -1
package/dist/auto.mjs
CHANGED
|
@@ -1156,6 +1156,9 @@ var init_parsing = __esm({
|
|
|
1156
1156
|
});
|
|
1157
1157
|
|
|
1158
1158
|
// src/utils/tag-groups.ts
|
|
1159
|
+
function tagAttrKey(name) {
|
|
1160
|
+
return name.trim().toLowerCase().replace(/[^a-z0-9_-]+/g, "-").replace(/^-+|-+$/g, "");
|
|
1161
|
+
}
|
|
1159
1162
|
function stripDefaultModifier(text) {
|
|
1160
1163
|
if (/\bdefault\s*$/.test(text)) {
|
|
1161
1164
|
return { text: text.replace(/\s+default\s*$/, "").trim(), isDefault: true };
|
|
@@ -1301,17 +1304,17 @@ function parseTagDeclaration(line11) {
|
|
|
1301
1304
|
function resolveTagColor(metadata, tagGroups, activeGroupName, isContainer) {
|
|
1302
1305
|
if (!activeGroupName) return void 0;
|
|
1303
1306
|
const group = tagGroups.find(
|
|
1304
|
-
(g) => g.name
|
|
1307
|
+
(g) => tagAttrKey(g.name) === tagAttrKey(activeGroupName)
|
|
1305
1308
|
);
|
|
1306
1309
|
if (!group) return void 0;
|
|
1307
|
-
const metaValue = metadata[group.name
|
|
1310
|
+
const metaValue = metadata[tagAttrKey(group.name)] ?? (isContainer ? void 0 : group.defaultValue);
|
|
1308
1311
|
if (!metaValue) return "#999999";
|
|
1309
1312
|
return group.entries.find((e) => e.value.toLowerCase() === metaValue.toLowerCase())?.color ?? "#999999";
|
|
1310
1313
|
}
|
|
1311
1314
|
function validateTagValues(entities, tagGroups, pushWarning, suggestFn) {
|
|
1312
1315
|
if (tagGroups.length === 0) return;
|
|
1313
1316
|
const groupMap = /* @__PURE__ */ new Map();
|
|
1314
|
-
for (const g of tagGroups) groupMap.set(g.name
|
|
1317
|
+
for (const g of tagGroups) groupMap.set(tagAttrKey(g.name), g);
|
|
1315
1318
|
for (const entity of entities) {
|
|
1316
1319
|
for (const [key, value] of Object.entries(entity.metadata)) {
|
|
1317
1320
|
const group = groupMap.get(key);
|
|
@@ -1348,10 +1351,10 @@ function validateTagGroupNames(tagGroups, pushWarning, pushError) {
|
|
|
1348
1351
|
`'none' is a reserved keyword and cannot be used as a tag group name`
|
|
1349
1352
|
);
|
|
1350
1353
|
}
|
|
1351
|
-
if (!VALID_TAG_IDENT_RE.test(group.name)) {
|
|
1354
|
+
if (!VALID_TAG_IDENT_RE.test(tagAttrKey(group.name))) {
|
|
1352
1355
|
report(
|
|
1353
1356
|
group.lineNumber,
|
|
1354
|
-
`Tag group name "${group.name}"
|
|
1357
|
+
`Tag group name "${group.name}" can't form a valid key \u2014 use letters, digits, underscore, or hyphen, and quote a multi-word name (e.g. tag "Trust Zone" as tz)`
|
|
1355
1358
|
);
|
|
1356
1359
|
}
|
|
1357
1360
|
if (group.alias != null && !VALID_TAG_IDENT_RE.test(group.alias)) {
|
|
@@ -1363,7 +1366,7 @@ function validateTagGroupNames(tagGroups, pushWarning, pushError) {
|
|
|
1363
1366
|
}
|
|
1364
1367
|
}
|
|
1365
1368
|
function cascadeTagMetadata(roots, tagGroups) {
|
|
1366
|
-
const keys = tagGroups.map((g) => g.name
|
|
1369
|
+
const keys = tagGroups.map((g) => tagAttrKey(g.name));
|
|
1367
1370
|
if (keys.length === 0) return;
|
|
1368
1371
|
const walk = (node, inherited) => {
|
|
1369
1372
|
const childInherited = { ...inherited };
|
|
@@ -1384,7 +1387,7 @@ function injectDefaultTagMetadata(entities, tagGroups, skip) {
|
|
|
1384
1387
|
for (const group of tagGroups) {
|
|
1385
1388
|
if (group.defaultValue) {
|
|
1386
1389
|
defaults.push({
|
|
1387
|
-
key: group.name
|
|
1390
|
+
key: tagAttrKey(group.name),
|
|
1388
1391
|
value: group.defaultValue
|
|
1389
1392
|
});
|
|
1390
1393
|
}
|
|
@@ -2775,7 +2778,7 @@ function parseVisualizationFull(content, palette) {
|
|
|
2775
2778
|
);
|
|
2776
2779
|
for (const group of result.timelineTagGroups) {
|
|
2777
2780
|
if (!group.defaultValue) continue;
|
|
2778
|
-
const key = group.name
|
|
2781
|
+
const key = tagAttrKey(group.name);
|
|
2779
2782
|
for (const event of result.timelineEvents) {
|
|
2780
2783
|
if (!event.metadata[key]) {
|
|
2781
2784
|
event.metadata[key] = group.defaultValue;
|
|
@@ -5167,7 +5170,7 @@ function renderLegendD3(container, config, state, palette, isDark, callbacks, co
|
|
|
5167
5170
|
};
|
|
5168
5171
|
}
|
|
5169
5172
|
function renderCapsule(parent, capsule, palette, groupBg, pillBorder, isDark, callbacks) {
|
|
5170
|
-
const g = parent.append("g").attr("transform", `translate(${capsule.x},${capsule.y})`).attr("data-legend-group", capsule.groupName
|
|
5173
|
+
const g = parent.append("g").attr("transform", `translate(${capsule.x},${capsule.y})`).attr("data-legend-group", tagAttrKey(capsule.groupName)).style("cursor", "pointer");
|
|
5171
5174
|
g.append("rect").attr("width", capsule.width).attr("height", capsule.height).attr("rx", LEGEND_HEIGHT / 2).attr("fill", groupBg);
|
|
5172
5175
|
const pill = capsule.pill;
|
|
5173
5176
|
g.append("rect").attr("x", pill.x).attr("y", pill.y).attr("width", pill.width).attr("height", pill.height).attr("rx", pill.height / 2).attr("fill", palette.bg);
|
|
@@ -5175,7 +5178,7 @@ function renderCapsule(parent, capsule, palette, groupBg, pillBorder, isDark, ca
|
|
|
5175
5178
|
g.append("text").attr("x", pill.x + pill.width / 2).attr("y", LEGEND_HEIGHT / 2).attr("text-anchor", "middle").call(centerText).attr("font-size", LEGEND_PILL_FONT_SIZE).attr("font-weight", 500).attr("fill", palette.text).attr("pointer-events", "none").attr("font-family", FONT_FAMILY).text(capsule.groupName);
|
|
5176
5179
|
if (capsule.gradient) {
|
|
5177
5180
|
const gr = capsule.gradient;
|
|
5178
|
-
const gradId = `dgmo-legend-ramp-${capsule.groupName
|
|
5181
|
+
const gradId = `dgmo-legend-ramp-${tagAttrKey(capsule.groupName).replace(/[^a-z0-9]+/g, "-")}`;
|
|
5179
5182
|
const def = g.append("defs").append("linearGradient").attr("id", gradId);
|
|
5180
5183
|
for (const stop of valueRampStops(gr.low, gr.high, { isDark })) {
|
|
5181
5184
|
def.append("stop").attr("offset", `${stop.offset * 100}%`).attr("stop-color", stop.color);
|
|
@@ -5205,7 +5208,7 @@ function renderCapsule(parent, capsule, palette, groupBg, pillBorder, isDark, ca
|
|
|
5205
5208
|
}
|
|
5206
5209
|
}
|
|
5207
5210
|
function renderPill(parent, pill, palette, groupBg, callbacks) {
|
|
5208
|
-
const g = parent.append("g").attr("transform", `translate(${pill.x},${pill.y})`).attr("data-legend-group", pill.groupName
|
|
5211
|
+
const g = parent.append("g").attr("transform", `translate(${pill.x},${pill.y})`).attr("data-legend-group", tagAttrKey(pill.groupName)).style("cursor", "pointer");
|
|
5209
5212
|
g.append("rect").attr("width", pill.width).attr("height", pill.height).attr("rx", pill.height / 2).attr("fill", groupBg);
|
|
5210
5213
|
g.append("text").attr("x", pill.width / 2).attr("y", pill.height / 2).attr("text-anchor", "middle").call(centerText).attr("font-size", LEGEND_PILL_FONT_SIZE).attr("font-weight", 500).attr("fill", palette.textMuted).attr("pointer-events", "none").attr("font-family", FONT_FAMILY).text(pill.groupName);
|
|
5211
5214
|
if (callbacks?.onGroupToggle) {
|
|
@@ -5311,6 +5314,7 @@ var LEGEND_TEXT_DY;
|
|
|
5311
5314
|
var init_legend_d3 = __esm({
|
|
5312
5315
|
"src/utils/legend-d3.ts"() {
|
|
5313
5316
|
"use strict";
|
|
5317
|
+
init_tag_groups();
|
|
5314
5318
|
init_legend_constants();
|
|
5315
5319
|
init_legend_layout();
|
|
5316
5320
|
init_color_utils();
|
|
@@ -9297,7 +9301,7 @@ function parseERDiagram(content, palette) {
|
|
|
9297
9301
|
);
|
|
9298
9302
|
for (const group of result.tagGroups) {
|
|
9299
9303
|
if (!group.defaultValue) continue;
|
|
9300
|
-
const key = group.name
|
|
9304
|
+
const key = tagAttrKey(group.name);
|
|
9301
9305
|
for (const table of result.tables) {
|
|
9302
9306
|
if (!table.metadata[key]) {
|
|
9303
9307
|
const mutableMeta = tableMetadataMap.get(table.id);
|
|
@@ -9527,12 +9531,12 @@ function parseOrg(content, palette) {
|
|
|
9527
9531
|
if (tagBlockMatch.alias) {
|
|
9528
9532
|
metaAliasMap.set(
|
|
9529
9533
|
normalizeName(tagBlockMatch.alias),
|
|
9530
|
-
tagBlockMatch.name
|
|
9534
|
+
tagAttrKey(tagBlockMatch.name)
|
|
9531
9535
|
);
|
|
9532
9536
|
}
|
|
9533
9537
|
metaAliasMap.set(
|
|
9534
9538
|
normalizeName(tagBlockMatch.name),
|
|
9535
|
-
tagBlockMatch.name
|
|
9539
|
+
tagAttrKey(tagBlockMatch.name)
|
|
9536
9540
|
);
|
|
9537
9541
|
result.tagGroups.push(currentTagGroup);
|
|
9538
9542
|
continue;
|
|
@@ -9918,12 +9922,12 @@ function parseSitemap(content, palette) {
|
|
|
9918
9922
|
if (tagBlockMatch.alias) {
|
|
9919
9923
|
metaAliasMap.set(
|
|
9920
9924
|
normalizeName(tagBlockMatch.alias),
|
|
9921
|
-
tagBlockMatch.name
|
|
9925
|
+
tagAttrKey(tagBlockMatch.name)
|
|
9922
9926
|
);
|
|
9923
9927
|
}
|
|
9924
9928
|
metaAliasMap.set(
|
|
9925
9929
|
normalizeName(tagBlockMatch.name),
|
|
9926
|
-
tagBlockMatch.name
|
|
9930
|
+
tagAttrKey(tagBlockMatch.name)
|
|
9927
9931
|
);
|
|
9928
9932
|
result.tagGroups.push(newTagGroup);
|
|
9929
9933
|
continue;
|
|
@@ -10093,6 +10097,14 @@ function parseSitemap(content, palette) {
|
|
|
10093
10097
|
continue;
|
|
10094
10098
|
}
|
|
10095
10099
|
}
|
|
10100
|
+
const enclosingContainer = nestedPageInsideContainer(indent, indentStack);
|
|
10101
|
+
if (enclosingContainer) {
|
|
10102
|
+
pushError(
|
|
10103
|
+
lineNumber,
|
|
10104
|
+
`Pages inside container '[${enclosingContainer}]' cannot have indented sub-pages. Containers hold a flat list of pages.`
|
|
10105
|
+
);
|
|
10106
|
+
continue;
|
|
10107
|
+
}
|
|
10096
10108
|
const node = parseNodeLabel2(
|
|
10097
10109
|
trimmed,
|
|
10098
10110
|
lineNumber,
|
|
@@ -10240,6 +10252,16 @@ function attachNode2(node, indent, indentStack, result) {
|
|
|
10240
10252
|
}
|
|
10241
10253
|
indentStack.push({ node, indent });
|
|
10242
10254
|
}
|
|
10255
|
+
function nestedPageInsideContainer(indent, indentStack) {
|
|
10256
|
+
let idx = indentStack.length - 1;
|
|
10257
|
+
while (idx >= 0 && indentStack[idx].indent >= indent) idx--;
|
|
10258
|
+
if (idx < 0) return null;
|
|
10259
|
+
if (indentStack[idx].node.isContainer) return null;
|
|
10260
|
+
for (let k = idx - 1; k >= 0; k--) {
|
|
10261
|
+
if (indentStack[k].node.isContainer) return indentStack[k].node.label;
|
|
10262
|
+
}
|
|
10263
|
+
return null;
|
|
10264
|
+
}
|
|
10243
10265
|
function findParentNode(indent, indentStack) {
|
|
10244
10266
|
for (let i = indentStack.length - 1; i >= 0; i--) {
|
|
10245
10267
|
if (indentStack[i].indent < indent) {
|
|
@@ -10823,12 +10845,12 @@ function parsePert(content, parseOpts = {}) {
|
|
|
10823
10845
|
if (tagBlockMatch.alias) {
|
|
10824
10846
|
metaAliasMap.set(
|
|
10825
10847
|
tagBlockMatch.alias.toLowerCase(),
|
|
10826
|
-
tagBlockMatch.name
|
|
10848
|
+
tagAttrKey(tagBlockMatch.name)
|
|
10827
10849
|
);
|
|
10828
10850
|
}
|
|
10829
10851
|
metaAliasMap.set(
|
|
10830
10852
|
normalizeName(tagBlockMatch.name),
|
|
10831
|
-
tagBlockMatch.name
|
|
10853
|
+
tagAttrKey(tagBlockMatch.name)
|
|
10832
10854
|
);
|
|
10833
10855
|
tagGroups.push(currentTagGroup);
|
|
10834
10856
|
if (tagBlockMatch.inlineValues) {
|
|
@@ -12293,10 +12315,10 @@ function emitCapsule(capsule, palette, groupBg, pillBorder) {
|
|
|
12293
12315
|
`<g data-legend-entry="${esc(entry.value.toLowerCase())}" data-series-name="${esc(entry.value)}" style="cursor:pointer"><circle cx="${entry.dotCx}" cy="${entry.dotCy}" r="${LEGEND_DOT_R}" fill="${esc(entry.color)}"/><text x="${entry.textX}" y="${entry.dotCy + LEGEND_ENTRY_FONT_SIZE / 2 - 1}" font-size="${LEGEND_ENTRY_FONT_SIZE}" fill="${esc(palette.textMuted)}" font-family="${esc(FONT_FAMILY)}">${esc(label)}</text></g>`
|
|
12294
12316
|
);
|
|
12295
12317
|
}
|
|
12296
|
-
return `<g transform="translate(${capsule.x},${capsule.y})" data-legend-group="${esc(capsule.groupName
|
|
12318
|
+
return `<g transform="translate(${capsule.x},${capsule.y})" data-legend-group="${esc(tagAttrKey(capsule.groupName))}" style="cursor:pointer">${inner.join("")}</g>`;
|
|
12297
12319
|
}
|
|
12298
12320
|
function emitPill(pill, palette, groupBg) {
|
|
12299
|
-
return `<g transform="translate(${pill.x},${pill.y})" data-legend-group="${esc(pill.groupName
|
|
12321
|
+
return `<g transform="translate(${pill.x},${pill.y})" data-legend-group="${esc(tagAttrKey(pill.groupName))}" style="cursor:pointer"><rect width="${pill.width}" height="${pill.height}" rx="${pill.height / 2}" fill="${esc(groupBg)}"/><text x="${pill.width / 2}" y="${pill.height / 2 + LEGEND_PILL_FONT_SIZE / 2 - 2}" font-size="${LEGEND_PILL_FONT_SIZE}" font-weight="500" fill="${esc(palette.textMuted)}" text-anchor="middle" font-family="${esc(FONT_FAMILY)}">${esc(pill.groupName)}</text></g>`;
|
|
12300
12322
|
}
|
|
12301
12323
|
function renderLegendSvg(groups, options) {
|
|
12302
12324
|
if (groups.length === 0) return { svg: "", height: 0, width: 0 };
|
|
@@ -12344,6 +12366,7 @@ function renderLegendSvg(groups, options) {
|
|
|
12344
12366
|
var init_legend_svg = __esm({
|
|
12345
12367
|
"src/utils/legend-svg.ts"() {
|
|
12346
12368
|
"use strict";
|
|
12369
|
+
init_tag_groups();
|
|
12347
12370
|
init_legend_constants();
|
|
12348
12371
|
init_legend_layout();
|
|
12349
12372
|
init_color_utils();
|
|
@@ -15052,12 +15075,12 @@ function parseKanban(content, palette) {
|
|
|
15052
15075
|
if (tagBlockMatch.alias) {
|
|
15053
15076
|
metaAliasMap.set(
|
|
15054
15077
|
normalizeName(tagBlockMatch.alias),
|
|
15055
|
-
tagBlockMatch.name
|
|
15078
|
+
tagAttrKey(tagBlockMatch.name)
|
|
15056
15079
|
);
|
|
15057
15080
|
}
|
|
15058
15081
|
metaAliasMap.set(
|
|
15059
15082
|
normalizeName(tagBlockMatch.name),
|
|
15060
|
-
tagBlockMatch.name
|
|
15083
|
+
tagAttrKey(tagBlockMatch.name)
|
|
15061
15084
|
);
|
|
15062
15085
|
result.tagGroups.push(currentTagGroup);
|
|
15063
15086
|
continue;
|
|
@@ -15246,7 +15269,7 @@ function parseKanban(content, palette) {
|
|
|
15246
15269
|
}
|
|
15247
15270
|
for (const group of result.tagGroups) {
|
|
15248
15271
|
const values = new Set(group.entries.map((e) => e.value.toLowerCase()));
|
|
15249
|
-
tagValueSets.set(group.name
|
|
15272
|
+
tagValueSets.set(tagAttrKey(group.name), values);
|
|
15250
15273
|
}
|
|
15251
15274
|
for (const col of result.columns) {
|
|
15252
15275
|
if (col.wipLimit != null && col.cards.length > col.wipLimit) {
|
|
@@ -15508,12 +15531,12 @@ function parseC4(content, palette) {
|
|
|
15508
15531
|
if (tagBlockMatch.alias) {
|
|
15509
15532
|
metaAliasMap.set(
|
|
15510
15533
|
normalizeName(tagBlockMatch.alias),
|
|
15511
|
-
tagBlockMatch.name
|
|
15534
|
+
tagAttrKey(tagBlockMatch.name)
|
|
15512
15535
|
);
|
|
15513
15536
|
}
|
|
15514
15537
|
metaAliasMap.set(
|
|
15515
15538
|
normalizeName(tagBlockMatch.name),
|
|
15516
|
-
tagBlockMatch.name
|
|
15539
|
+
tagAttrKey(tagBlockMatch.name)
|
|
15517
15540
|
);
|
|
15518
15541
|
result.tagGroups.push(currentTagGroup);
|
|
15519
15542
|
continue;
|
|
@@ -17196,7 +17219,7 @@ function parseInfra(content) {
|
|
|
17196
17219
|
}
|
|
17197
17220
|
for (const tg of result.tagGroups) {
|
|
17198
17221
|
if (!tg.defaultValue) continue;
|
|
17199
|
-
const key = (tg.alias ?? tg.name)
|
|
17222
|
+
const key = tagAttrKey(tg.alias ?? tg.name);
|
|
17200
17223
|
for (const node of result.nodes) {
|
|
17201
17224
|
if (node.isEdge) continue;
|
|
17202
17225
|
if (!(key in node.tags)) {
|
|
@@ -17333,6 +17356,7 @@ var CONNECTION_RE, SIMPLE_CONNECTION_RE, ASYNC_CONNECTION_RE, ASYNC_SIMPLE_CONNE
|
|
|
17333
17356
|
var init_parser15 = __esm({
|
|
17334
17357
|
"src/infra/parser.ts"() {
|
|
17335
17358
|
"use strict";
|
|
17359
|
+
init_tag_groups();
|
|
17336
17360
|
init_diagnostics();
|
|
17337
17361
|
init_description_helpers();
|
|
17338
17362
|
init_arrows();
|
|
@@ -17878,13 +17902,10 @@ function parseGantt(content, palette) {
|
|
|
17878
17902
|
if (tagMatch.alias) {
|
|
17879
17903
|
metaAliasMap.set(
|
|
17880
17904
|
normalizeName(tagMatch.alias),
|
|
17881
|
-
tagMatch.name
|
|
17905
|
+
tagAttrKey(tagMatch.name)
|
|
17882
17906
|
);
|
|
17883
17907
|
}
|
|
17884
|
-
metaAliasMap.set(
|
|
17885
|
-
normalizeName(tagMatch.name),
|
|
17886
|
-
tagMatch.name.toLowerCase()
|
|
17887
|
-
);
|
|
17908
|
+
metaAliasMap.set(normalizeName(tagMatch.name), tagAttrKey(tagMatch.name));
|
|
17888
17909
|
continue;
|
|
17889
17910
|
}
|
|
17890
17911
|
const topWorkweekMatch = line11.match(WORKWEEK_RE);
|
|
@@ -18810,7 +18831,7 @@ function parseMap(content, palette) {
|
|
|
18810
18831
|
const aliasMap = /* @__PURE__ */ new Map();
|
|
18811
18832
|
const open = { tag: null, route: null, poi: null };
|
|
18812
18833
|
const registry = () => withTagAliases(MAP_REGISTRY, new Set(aliasMap.keys()));
|
|
18813
|
-
const tagGroupNames = () => new Set(tagGroups.map((g) => g.name
|
|
18834
|
+
const tagGroupNames = () => new Set(tagGroups.map((g) => tagAttrKey(g.name)));
|
|
18814
18835
|
const closeBlocks = () => {
|
|
18815
18836
|
open.tag = null;
|
|
18816
18837
|
open.route = null;
|
|
@@ -18994,7 +19015,7 @@ function parseMap(content, palette) {
|
|
|
18994
19015
|
entries: [],
|
|
18995
19016
|
lineNumber: line11
|
|
18996
19017
|
};
|
|
18997
|
-
if (m.alias) aliasMap.set(m.alias.toLowerCase(), m.name
|
|
19018
|
+
if (m.alias) aliasMap.set(m.alias.toLowerCase(), tagAttrKey(m.name));
|
|
18998
19019
|
tagGroups.push(group);
|
|
18999
19020
|
open.tag = group;
|
|
19000
19021
|
if (m.inlineValues?.length) {
|
|
@@ -19527,12 +19548,12 @@ function parseBoxesAndLines(content, palette) {
|
|
|
19527
19548
|
if (tagBlockMatch.alias) {
|
|
19528
19549
|
metaAliasMap.set(
|
|
19529
19550
|
normalizeName(tagBlockMatch.alias),
|
|
19530
|
-
tagBlockMatch.name
|
|
19551
|
+
tagAttrKey(tagBlockMatch.name)
|
|
19531
19552
|
);
|
|
19532
19553
|
}
|
|
19533
19554
|
metaAliasMap.set(
|
|
19534
19555
|
normalizeName(tagBlockMatch.name),
|
|
19535
|
-
tagBlockMatch.name
|
|
19556
|
+
tagAttrKey(tagBlockMatch.name)
|
|
19536
19557
|
);
|
|
19537
19558
|
if (tagBlockMatch.inlineValues) {
|
|
19538
19559
|
for (const rawVal of tagBlockMatch.inlineValues) {
|
|
@@ -20273,12 +20294,12 @@ function parseMindmap(content, palette) {
|
|
|
20273
20294
|
if (tagBlockMatch.alias) {
|
|
20274
20295
|
aliasMap.set(
|
|
20275
20296
|
tagBlockMatch.alias.toLowerCase(),
|
|
20276
|
-
tagBlockMatch.name
|
|
20297
|
+
tagAttrKey(tagBlockMatch.name)
|
|
20277
20298
|
);
|
|
20278
20299
|
}
|
|
20279
20300
|
aliasMap.set(
|
|
20280
|
-
tagBlockMatch.name
|
|
20281
|
-
tagBlockMatch.name
|
|
20301
|
+
tagAttrKey(tagBlockMatch.name),
|
|
20302
|
+
tagAttrKey(tagBlockMatch.name)
|
|
20282
20303
|
);
|
|
20283
20304
|
result.tagGroups.push(currentTagGroup);
|
|
20284
20305
|
continue;
|
|
@@ -21987,7 +22008,18 @@ function parseJourneyMap(content, palette) {
|
|
|
21987
22008
|
palette
|
|
21988
22009
|
) ?? void 0;
|
|
21989
22010
|
} else {
|
|
21990
|
-
|
|
22011
|
+
const { label, colorName } = peelTrailingColorName(afterKeyword);
|
|
22012
|
+
if (colorName) {
|
|
22013
|
+
personaName = label;
|
|
22014
|
+
personaColor = resolveColorWithDiagnostic(
|
|
22015
|
+
colorName,
|
|
22016
|
+
lineNumber,
|
|
22017
|
+
result.diagnostics,
|
|
22018
|
+
palette
|
|
22019
|
+
) ?? void 0;
|
|
22020
|
+
} else {
|
|
22021
|
+
personaName = afterKeyword;
|
|
22022
|
+
}
|
|
21991
22023
|
}
|
|
21992
22024
|
}
|
|
21993
22025
|
if (!personaName) {
|
|
@@ -22030,12 +22062,12 @@ function parseJourneyMap(content, palette) {
|
|
|
22030
22062
|
if (tagBlockMatch.alias) {
|
|
22031
22063
|
aliasMap.set(
|
|
22032
22064
|
tagBlockMatch.alias.toLowerCase(),
|
|
22033
|
-
tagBlockMatch.name
|
|
22065
|
+
tagAttrKey(tagBlockMatch.name)
|
|
22034
22066
|
);
|
|
22035
22067
|
}
|
|
22036
22068
|
aliasMap.set(
|
|
22037
|
-
tagBlockMatch.name
|
|
22038
|
-
tagBlockMatch.name
|
|
22069
|
+
tagAttrKey(tagBlockMatch.name),
|
|
22070
|
+
tagAttrKey(tagBlockMatch.name)
|
|
22039
22071
|
);
|
|
22040
22072
|
result.tagGroups.push(currentTagGroup);
|
|
22041
22073
|
continue;
|
|
@@ -22179,7 +22211,7 @@ function parseJourneyMap(content, palette) {
|
|
|
22179
22211
|
}
|
|
22180
22212
|
for (const group of result.tagGroups) {
|
|
22181
22213
|
const values = new Set(group.entries.map((e) => e.value.toLowerCase()));
|
|
22182
|
-
tagValueSets.set(group.name
|
|
22214
|
+
tagValueSets.set(tagAttrKey(group.name), values);
|
|
22183
22215
|
}
|
|
22184
22216
|
const allSteps = hasPhases ? result.phases.flatMap((p) => p.steps) : result.steps;
|
|
22185
22217
|
for (const step of allSteps) {
|
|
@@ -24166,7 +24198,7 @@ function computeLegendGroups(tagGroups, showEyeIcons, usedValuesByGroup) {
|
|
|
24166
24198
|
const groups = [];
|
|
24167
24199
|
for (const group of tagGroups) {
|
|
24168
24200
|
if (group.entries.length === 0) continue;
|
|
24169
|
-
const usedValues = usedValuesByGroup?.get(group.name
|
|
24201
|
+
const usedValues = usedValuesByGroup?.get(tagAttrKey(group.name));
|
|
24170
24202
|
const visibleEntries = usedValues ? group.entries.filter((e) => usedValues.has(e.value.toLowerCase())) : group.entries;
|
|
24171
24203
|
if (visibleEntries.length === 0) continue;
|
|
24172
24204
|
const pillWidth2 = measureLegendText(group.name, LEGEND_PILL_FONT_SIZE) + LEGEND_PILL_PAD;
|
|
@@ -24779,7 +24811,7 @@ function layoutOrg(parsed, hiddenCounts, activeTagGroup, hiddenAttributes, expan
|
|
|
24779
24811
|
const totalHeight = finalMaxY - minY + MARGIN * 2;
|
|
24780
24812
|
const usedValuesByGroup = /* @__PURE__ */ new Map();
|
|
24781
24813
|
for (const group of parsed.tagGroups) {
|
|
24782
|
-
const key = group.name
|
|
24814
|
+
const key = tagAttrKey(group.name);
|
|
24783
24815
|
const used = /* @__PURE__ */ new Set();
|
|
24784
24816
|
const walk = (node) => {
|
|
24785
24817
|
if (!node.isContainer && node.metadata[key]) {
|
|
@@ -24838,6 +24870,7 @@ var init_layout = __esm({
|
|
|
24838
24870
|
"src/org/layout.ts"() {
|
|
24839
24871
|
"use strict";
|
|
24840
24872
|
init_tag_groups();
|
|
24873
|
+
init_tag_groups();
|
|
24841
24874
|
init_legend_constants();
|
|
24842
24875
|
init_text_measure();
|
|
24843
24876
|
LABEL_FONT_SIZE = 13;
|
|
@@ -25198,14 +25231,14 @@ function renderOrg(container, parsed, layout, palette, isDark, onClickItem, expo
|
|
|
25198
25231
|
const contentG = mainG.append("g").attr("transform", `translate(0, ${contentYShift})`);
|
|
25199
25232
|
const displayNames = /* @__PURE__ */ new Map();
|
|
25200
25233
|
for (const group of parsed.tagGroups) {
|
|
25201
|
-
displayNames.set(group.name
|
|
25234
|
+
displayNames.set(tagAttrKey(group.name), group.name);
|
|
25202
25235
|
}
|
|
25203
25236
|
const rootNodeIds = new Set(parsed.roots.map((r) => r.id));
|
|
25204
25237
|
const colorOff = parsed.options?.["color"] === "off";
|
|
25205
25238
|
for (const c of layout.containers) {
|
|
25206
25239
|
const cG = contentG.append("g").attr("transform", `translate(${c.x}, ${c.y})`).attr("class", "org-container").attr("data-line-number", String(c.lineNumber));
|
|
25207
25240
|
if (activeTagGroup) {
|
|
25208
|
-
const tagKey = activeTagGroup
|
|
25241
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
25209
25242
|
const metaValue = c.tagMetadata[tagKey];
|
|
25210
25243
|
if (metaValue) {
|
|
25211
25244
|
cG.attr(`data-tag-${tagKey}`, metaValue.toLowerCase());
|
|
@@ -25287,7 +25320,7 @@ function renderOrg(container, parsed, layout, palette, isDark, onClickItem, expo
|
|
|
25287
25320
|
if (containerNodeIds.has(node.id)) continue;
|
|
25288
25321
|
const nodeG = contentG.append("g").attr("transform", `translate(${node.x - node.width / 2}, ${node.y})`).attr("class", "org-node").attr("data-line-number", String(node.lineNumber));
|
|
25289
25322
|
if (activeTagGroup) {
|
|
25290
|
-
const tagKey = activeTagGroup
|
|
25323
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
25291
25324
|
const metaValue = node.tagMetadata[tagKey];
|
|
25292
25325
|
if (metaValue) {
|
|
25293
25326
|
nodeG.attr(`data-tag-${tagKey}`, metaValue.toLowerCase());
|
|
@@ -25460,7 +25493,7 @@ function renderOrg(container, parsed, layout, palette, isDark, onClickItem, expo
|
|
|
25460
25493
|
const computedLayout = legendHandle.getLayout();
|
|
25461
25494
|
if (computedLayout.activeCapsule?.addonX != null) {
|
|
25462
25495
|
const capsule = computedLayout.activeCapsule;
|
|
25463
|
-
const groupKey = capsule.groupName
|
|
25496
|
+
const groupKey = tagAttrKey(capsule.groupName);
|
|
25464
25497
|
const isHidden = hiddenAttributes?.has(groupKey) ?? false;
|
|
25465
25498
|
const activeGroupEl = legendParentBase.select(
|
|
25466
25499
|
`[data-legend-group="${groupKey}"]`
|
|
@@ -25499,6 +25532,7 @@ var DIAGRAM_PADDING, MAX_SCALE, TITLE_HEIGHT, ANCESTOR_DOT_R, ANCESTOR_LABEL_FON
|
|
|
25499
25532
|
var init_renderer = __esm({
|
|
25500
25533
|
"src/org/renderer.ts"() {
|
|
25501
25534
|
"use strict";
|
|
25535
|
+
init_tag_groups();
|
|
25502
25536
|
init_fonts();
|
|
25503
25537
|
init_export_container();
|
|
25504
25538
|
init_scaling();
|
|
@@ -25584,7 +25618,7 @@ function computeLegendGroups2(tagGroups, usedValuesByGroup) {
|
|
|
25584
25618
|
const groups = [];
|
|
25585
25619
|
for (const group of tagGroups) {
|
|
25586
25620
|
if (group.entries.length === 0) continue;
|
|
25587
|
-
const usedValues = usedValuesByGroup?.get(group.name
|
|
25621
|
+
const usedValues = usedValuesByGroup?.get(tagAttrKey(group.name));
|
|
25588
25622
|
const visibleEntries = usedValues ? group.entries.filter((e) => usedValues.has(e.value.toLowerCase())) : group.entries;
|
|
25589
25623
|
if (visibleEntries.length === 0) continue;
|
|
25590
25624
|
const pillWidth2 = measureLegendText(group.name, LEGEND_PILL_FONT_SIZE) + LEGEND_PILL_PAD;
|
|
@@ -26064,7 +26098,7 @@ function layoutSitemap(parsed, hiddenCounts, activeTagGroup, hiddenAttributes, e
|
|
|
26064
26098
|
totalHeight += MARGIN2;
|
|
26065
26099
|
const usedValuesByGroup = /* @__PURE__ */ new Map();
|
|
26066
26100
|
for (const group of parsed.tagGroups) {
|
|
26067
|
-
const key = group.name
|
|
26101
|
+
const key = tagAttrKey(group.name);
|
|
26068
26102
|
const used = /* @__PURE__ */ new Set();
|
|
26069
26103
|
const walk = (node) => {
|
|
26070
26104
|
if (!node.isContainer && node.metadata[key]) {
|
|
@@ -26109,6 +26143,7 @@ var init_layout2 = __esm({
|
|
|
26109
26143
|
"src/sitemap/layout.ts"() {
|
|
26110
26144
|
"use strict";
|
|
26111
26145
|
init_tag_groups();
|
|
26146
|
+
init_tag_groups();
|
|
26112
26147
|
init_legend_constants();
|
|
26113
26148
|
init_text_measure();
|
|
26114
26149
|
LABEL_FONT_SIZE3 = 13;
|
|
@@ -26378,10 +26413,10 @@ function renderSitemap(container, parsed, layout, palette, isDark, onClickItem,
|
|
|
26378
26413
|
const displayNames = /* @__PURE__ */ new Map();
|
|
26379
26414
|
const tagColors = /* @__PURE__ */ new Map();
|
|
26380
26415
|
for (const group of parsed.tagGroups) {
|
|
26381
|
-
displayNames.set(group.name
|
|
26416
|
+
displayNames.set(tagAttrKey(group.name), group.name);
|
|
26382
26417
|
for (const entry of group.entries) {
|
|
26383
26418
|
tagColors.set(
|
|
26384
|
-
`${group.name
|
|
26419
|
+
`${tagAttrKey(group.name)}:${entry.value.toLowerCase()}`,
|
|
26385
26420
|
entry.color
|
|
26386
26421
|
);
|
|
26387
26422
|
}
|
|
@@ -26398,7 +26433,7 @@ function renderSitemap(container, parsed, layout, palette, isDark, onClickItem,
|
|
|
26398
26433
|
);
|
|
26399
26434
|
}
|
|
26400
26435
|
if (activeTagGroup) {
|
|
26401
|
-
const tagKey = activeTagGroup
|
|
26436
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
26402
26437
|
const tagVal = c.tagMetadata[tagKey];
|
|
26403
26438
|
if (tagVal) cG.attr(`data-tag-${tagKey}`, tagVal.toLowerCase());
|
|
26404
26439
|
}
|
|
@@ -26461,7 +26496,7 @@ function renderSitemap(container, parsed, layout, palette, isDark, onClickItem,
|
|
|
26461
26496
|
nodeG.style("cursor", "pointer").on("click", () => onClickItem(node.lineNumber));
|
|
26462
26497
|
}
|
|
26463
26498
|
if (activeTagGroup) {
|
|
26464
|
-
const tagKey = activeTagGroup
|
|
26499
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
26465
26500
|
const tagVal = node.tagMetadata[tagKey];
|
|
26466
26501
|
if (tagVal) nodeG.attr(`data-tag-${tagKey}`, tagVal.toLowerCase());
|
|
26467
26502
|
}
|
|
@@ -26588,7 +26623,7 @@ function renderLegend(parent, legendGroups, palette, isDark, activeTagGroup, fix
|
|
|
26588
26623
|
const computedLayout = legendHandle.getLayout();
|
|
26589
26624
|
if (computedLayout.activeCapsule?.addonX != null) {
|
|
26590
26625
|
const capsule = computedLayout.activeCapsule;
|
|
26591
|
-
const groupKey = capsule.groupName
|
|
26626
|
+
const groupKey = tagAttrKey(capsule.groupName);
|
|
26592
26627
|
const isHidden = hiddenAttributes?.has(groupKey) ?? false;
|
|
26593
26628
|
const activeGroupEl = parent.select(`[data-legend-group="${groupKey}"]`);
|
|
26594
26629
|
if (!activeGroupEl.empty()) {
|
|
@@ -26653,6 +26688,7 @@ var DIAGRAM_PADDING2, MAX_SCALE2, TITLE_HEIGHT2, ARROWHEAD_W, ARROWHEAD_H, EDGE_
|
|
|
26653
26688
|
var init_renderer2 = __esm({
|
|
26654
26689
|
"src/sitemap/renderer.ts"() {
|
|
26655
26690
|
"use strict";
|
|
26691
|
+
init_tag_groups();
|
|
26656
26692
|
init_fonts();
|
|
26657
26693
|
init_color_utils();
|
|
26658
26694
|
init_inline_markdown();
|
|
@@ -26700,7 +26736,7 @@ function resolveCardTagMeta(card, tagGroups, hiddenMetaGroups) {
|
|
|
26700
26736
|
const meta = [];
|
|
26701
26737
|
for (const group of tagGroups) {
|
|
26702
26738
|
if (hiddenMetaGroups?.includes(group.name.toLowerCase())) continue;
|
|
26703
|
-
const tagValue = card.tags[group.name
|
|
26739
|
+
const tagValue = card.tags[tagAttrKey(group.name)];
|
|
26704
26740
|
const value = tagValue ?? group.defaultValue;
|
|
26705
26741
|
if (!value) continue;
|
|
26706
26742
|
const entry = group.entries.find(
|
|
@@ -26720,7 +26756,7 @@ function resolveCardTagColor(card, tagGroups, activeTagGroup) {
|
|
|
26720
26756
|
(g) => g.name.toLowerCase() === activeTagGroup.toLowerCase()
|
|
26721
26757
|
);
|
|
26722
26758
|
if (!group) return card.color;
|
|
26723
|
-
const tagValue = card.tags[group.name
|
|
26759
|
+
const tagValue = card.tags[tagAttrKey(group.name)];
|
|
26724
26760
|
const value = tagValue ?? group.defaultValue;
|
|
26725
26761
|
if (!value) return void 0;
|
|
26726
26762
|
const entry = group.entries.find(
|
|
@@ -27030,7 +27066,7 @@ function renderKanban(container, parsed, palette, isDark, options) {
|
|
|
27030
27066
|
);
|
|
27031
27067
|
const cg = g.append("g").attr("class", "kanban-card").attr("data-card-id", card.id).attr("data-line-number", card.lineNumber);
|
|
27032
27068
|
if (activeTagGroup) {
|
|
27033
|
-
const tagKey = activeTagGroup
|
|
27069
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
27034
27070
|
const tagValue = card.tags[tagKey];
|
|
27035
27071
|
const group = parsed.tagGroups.find(
|
|
27036
27072
|
(tg) => tg.name.toLowerCase() === tagKey
|
|
@@ -27091,7 +27127,7 @@ function drawSwimlaneIcon(parent, x, y, isActive, palette) {
|
|
|
27091
27127
|
return iconG;
|
|
27092
27128
|
}
|
|
27093
27129
|
function bucketCardsBySwimlane(columns, swimlaneGroup) {
|
|
27094
|
-
const tagKey = swimlaneGroup.name
|
|
27130
|
+
const tagKey = tagAttrKey(swimlaneGroup.name);
|
|
27095
27131
|
const buckets = /* @__PURE__ */ new Map();
|
|
27096
27132
|
for (const entry of swimlaneGroup.entries) {
|
|
27097
27133
|
buckets.set(entry.value.toLowerCase(), {
|
|
@@ -27379,7 +27415,7 @@ function renderSwimlaneCard(parent, cardLayout, tagGroups, activeTagGroup, palet
|
|
|
27379
27415
|
);
|
|
27380
27416
|
const cg = parent.append("g").attr("class", "kanban-card").attr("data-card-id", card.id).attr("data-line-number", card.lineNumber);
|
|
27381
27417
|
if (activeTagGroup) {
|
|
27382
|
-
const tagKey = activeTagGroup
|
|
27418
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
27383
27419
|
const group = tagGroups.find((tg) => tg.name.toLowerCase() === tagKey);
|
|
27384
27420
|
const value = card.tags[tagKey] ?? group?.defaultValue;
|
|
27385
27421
|
if (value) {
|
|
@@ -27412,6 +27448,7 @@ var DIAGRAM_PADDING3, COLUMN_GAP, COLUMN_HEADER_HEIGHT, COLUMN_PADDING, COLUMN_M
|
|
|
27412
27448
|
var init_renderer3 = __esm({
|
|
27413
27449
|
"src/kanban/renderer.ts"() {
|
|
27414
27450
|
"use strict";
|
|
27451
|
+
init_tag_groups();
|
|
27415
27452
|
init_fonts();
|
|
27416
27453
|
init_color_utils();
|
|
27417
27454
|
init_inline_markdown();
|
|
@@ -28393,7 +28430,7 @@ function classifyEREntities(tables, relationships) {
|
|
|
28393
28430
|
const variance = indegreeValues.reduce((a, b) => a + (b - mean) ** 2, 0) / indegreeValues.length;
|
|
28394
28431
|
const stddev = Math.sqrt(variance);
|
|
28395
28432
|
const sorted = [...indegreeValues].sort((a, b) => a - b);
|
|
28396
|
-
const
|
|
28433
|
+
const median2 = sorted.length % 2 === 0 ? (sorted[sorted.length / 2 - 1] + sorted[sorted.length / 2]) / 2 : sorted[Math.floor(sorted.length / 2)];
|
|
28397
28434
|
for (const table of tables) {
|
|
28398
28435
|
const id = table.id;
|
|
28399
28436
|
const cols = table.columns;
|
|
@@ -28434,7 +28471,7 @@ function classifyEREntities(tables, relationships) {
|
|
|
28434
28471
|
const nameMatchesLookup = LOOKUP_NAME_SUFFIXES.some(
|
|
28435
28472
|
(s) => nameLower.endsWith(s)
|
|
28436
28473
|
);
|
|
28437
|
-
if (nameMatchesLookup && cols.length <= 6 && fkCount <= 1 && indegree >
|
|
28474
|
+
if (nameMatchesLookup && cols.length <= 6 && fkCount <= 1 && indegree > median2) {
|
|
28438
28475
|
result.set(id, "lookup");
|
|
28439
28476
|
continue;
|
|
28440
28477
|
}
|
|
@@ -28675,7 +28712,7 @@ function renderERDiagram(container, parsed, layout, palette, isDark, onClickItem
|
|
|
28675
28712
|
seriesColors2[ni % seriesColors2.length];
|
|
28676
28713
|
const nodeG = contentG.append("g").attr("transform", `translate(${node.x}, ${node.y})`).attr("class", "er-table").attr("data-line-number", String(node.lineNumber)).attr("data-node-id", node.id);
|
|
28677
28714
|
if (activeTagGroup) {
|
|
28678
|
-
const tagKey = activeTagGroup
|
|
28715
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
28679
28716
|
const tagValue = node.metadata[tagKey];
|
|
28680
28717
|
if (tagValue) {
|
|
28681
28718
|
nodeG.attr(`data-tag-${tagKey}`, tagValue.toLowerCase());
|
|
@@ -28854,6 +28891,7 @@ var DIAGRAM_PADDING5, MAX_SCALE4, TABLE_FONT_SIZE2, COLUMN_FONT_SIZE2, EDGE_LABE
|
|
|
28854
28891
|
var init_renderer5 = __esm({
|
|
28855
28892
|
"src/er/renderer.ts"() {
|
|
28856
28893
|
"use strict";
|
|
28894
|
+
init_tag_groups();
|
|
28857
28895
|
init_fonts();
|
|
28858
28896
|
init_color_utils();
|
|
28859
28897
|
init_palettes();
|
|
@@ -29024,63 +29062,6 @@ function ensureArrowMarkers(defs, colors) {
|
|
|
29024
29062
|
).attr("fill", color);
|
|
29025
29063
|
}
|
|
29026
29064
|
}
|
|
29027
|
-
function edgePolylineMidpoint(points) {
|
|
29028
|
-
if (points.length === 0) return { x: 0, y: 0 };
|
|
29029
|
-
if (points.length === 1) return { x: points[0].x, y: points[0].y };
|
|
29030
|
-
let total = 0;
|
|
29031
|
-
const segLen = [];
|
|
29032
|
-
for (let k = 1; k < points.length; k++) {
|
|
29033
|
-
const len = Math.hypot(
|
|
29034
|
-
points[k].x - points[k - 1].x,
|
|
29035
|
-
points[k].y - points[k - 1].y
|
|
29036
|
-
);
|
|
29037
|
-
segLen.push(len);
|
|
29038
|
-
total += len;
|
|
29039
|
-
}
|
|
29040
|
-
let half = total / 2;
|
|
29041
|
-
for (let k = 1; k < points.length; k++) {
|
|
29042
|
-
const len = segLen[k - 1];
|
|
29043
|
-
if (half <= len || k === points.length - 1) {
|
|
29044
|
-
const t = len === 0 ? 0 : Math.min(1, half / len);
|
|
29045
|
-
return {
|
|
29046
|
-
x: points[k - 1].x + (points[k].x - points[k - 1].x) * t,
|
|
29047
|
-
y: points[k - 1].y + (points[k].y - points[k - 1].y) * t
|
|
29048
|
-
};
|
|
29049
|
-
}
|
|
29050
|
-
half -= len;
|
|
29051
|
-
}
|
|
29052
|
-
const last = points[points.length - 1];
|
|
29053
|
-
return { x: last.x, y: last.y };
|
|
29054
|
-
}
|
|
29055
|
-
function resolveEdgeLabelOverlaps(labels) {
|
|
29056
|
-
const MAX_PASSES = 8;
|
|
29057
|
-
const PAD = 4;
|
|
29058
|
-
for (let pass = 0; pass < MAX_PASSES; pass++) {
|
|
29059
|
-
let moved = false;
|
|
29060
|
-
for (let i = 0; i < labels.length; i++) {
|
|
29061
|
-
for (let j = i + 1; j < labels.length; j++) {
|
|
29062
|
-
const a = labels[i];
|
|
29063
|
-
const b = labels[j];
|
|
29064
|
-
const dx = Math.abs(a.x - b.x);
|
|
29065
|
-
const dy = Math.abs(a.y - b.y);
|
|
29066
|
-
const overlapX = (a.width + b.width) / 2 + PAD - dx;
|
|
29067
|
-
const overlapY = (a.height + b.height) / 2 + PAD - dy;
|
|
29068
|
-
if (overlapX > 0 && overlapY > 0) {
|
|
29069
|
-
const shift = overlapY / 2 + 1;
|
|
29070
|
-
if (a.y < b.y) {
|
|
29071
|
-
a.y -= shift;
|
|
29072
|
-
b.y += shift;
|
|
29073
|
-
} else {
|
|
29074
|
-
a.y += shift;
|
|
29075
|
-
b.y -= shift;
|
|
29076
|
-
}
|
|
29077
|
-
moved = true;
|
|
29078
|
-
}
|
|
29079
|
-
}
|
|
29080
|
-
}
|
|
29081
|
-
if (!moved) break;
|
|
29082
|
-
}
|
|
29083
|
-
}
|
|
29084
29065
|
function renderBoxesAndLines(container, parsed, layout, palette, isDark, options) {
|
|
29085
29066
|
const {
|
|
29086
29067
|
onClickItem,
|
|
@@ -29287,8 +29268,6 @@ function renderBoxesAndLines(container, parsed, layout, palette, isDark, options
|
|
|
29287
29268
|
groupG.append("text").attr("class", "bl-group-label").attr("x", gx + group.width / 2).attr("y", gy + 18).attr("text-anchor", "middle").attr("font-family", FONT_FAMILY).attr("font-size", sGroupLabelFontSize).attr("font-weight", "600").attr("fill", palette.text).text(group.label);
|
|
29288
29269
|
}
|
|
29289
29270
|
}
|
|
29290
|
-
const labelPositions = [];
|
|
29291
|
-
const edgeGroups = /* @__PURE__ */ new Map();
|
|
29292
29271
|
for (let i = 0; i < layout.edges.length; i++) {
|
|
29293
29272
|
const le = layout.edges[i];
|
|
29294
29273
|
const color = edgeColorMap.get(i) ?? palette.textMuted;
|
|
@@ -29307,7 +29286,6 @@ function renderBoxesAndLines(container, parsed, layout, palette, isDark, options
|
|
|
29307
29286
|
const nodeLayout = layoutNodeMap.get(le.source);
|
|
29308
29287
|
if (nodeLayout) {
|
|
29309
29288
|
const edgeG2 = diagramG.append("g").attr("class", "bl-edge-group").attr("data-line-number", String(le.lineNumber));
|
|
29310
|
-
edgeGroups.set(i, edgeG2);
|
|
29311
29289
|
const markerId2 = `bl-arrow-${color.replace("#", "")}`;
|
|
29312
29290
|
const cx = nodeLayout.x;
|
|
29313
29291
|
const cy = nodeLayout.y;
|
|
@@ -29356,7 +29334,6 @@ function renderBoxesAndLines(container, parsed, layout, palette, isDark, options
|
|
|
29356
29334
|
}
|
|
29357
29335
|
if (points.length < 2) continue;
|
|
29358
29336
|
const edgeG = diagramG.append("g").attr("class", "bl-edge-group").attr("data-line-number", String(le.lineNumber));
|
|
29359
|
-
edgeGroups.set(i, edgeG);
|
|
29360
29337
|
const markerId = `bl-arrow-${color.replace("#", "")}`;
|
|
29361
29338
|
const gen = le.straight ? lineGeneratorStraight : parsed.direction === "TB" ? lineGeneratorTB : lineGeneratorLR;
|
|
29362
29339
|
const path = edgeG.append("path").attr("class", "bl-edge").attr("d", gen(points) ?? "").attr("fill", "none").attr("stroke", color).attr("stroke-width", sEdgeStrokeWidth).attr("marker-end", `url(#${markerId})`);
|
|
@@ -29364,31 +29341,6 @@ function renderBoxesAndLines(container, parsed, layout, palette, isDark, options
|
|
|
29364
29341
|
const revId = `bl-arrow-rev-${color.replace("#", "")}`;
|
|
29365
29342
|
path.attr("marker-start", `url(#${revId})`);
|
|
29366
29343
|
}
|
|
29367
|
-
if (le.label && le.points.length > 0) {
|
|
29368
|
-
const lw = measureText(le.label, sEdgeLabelFontSize);
|
|
29369
|
-
const labelH = sEdgeLabelFontSize + 6;
|
|
29370
|
-
const mid = edgePolylineMidpoint(le.points);
|
|
29371
|
-
let ly = mid.y;
|
|
29372
|
-
if (le.parallelCount > 1 && le.yOffset !== 0) {
|
|
29373
|
-
ly += (le.yOffset < 0 ? -labelH : labelH) * 0.5;
|
|
29374
|
-
}
|
|
29375
|
-
labelPositions.push({
|
|
29376
|
-
x: mid.x,
|
|
29377
|
-
y: ly,
|
|
29378
|
-
width: lw + 8,
|
|
29379
|
-
height: labelH,
|
|
29380
|
-
idx: i
|
|
29381
|
-
});
|
|
29382
|
-
}
|
|
29383
|
-
}
|
|
29384
|
-
resolveEdgeLabelOverlaps(labelPositions);
|
|
29385
|
-
for (const lp of labelPositions) {
|
|
29386
|
-
const le = layout.edges[lp.idx];
|
|
29387
|
-
if (!le.label) continue;
|
|
29388
|
-
const edgeG = edgeGroups.get(lp.idx);
|
|
29389
|
-
const target = edgeG ?? diagramG;
|
|
29390
|
-
target.append("rect").attr("x", lp.x - lp.width / 2).attr("y", lp.y - lp.height / 2).attr("width", lp.width).attr("height", lp.height).attr("rx", 3).attr("fill", palette.bg).attr("opacity", 0.85);
|
|
29391
|
-
target.append("text").attr("x", lp.x).attr("y", lp.y + sEdgeLabelFontSize / 3).attr("text-anchor", "middle").attr("font-size", sEdgeLabelFontSize).attr("fill", palette.textMuted).text(le.label);
|
|
29392
29344
|
}
|
|
29393
29345
|
for (const ln of layout.nodes) {
|
|
29394
29346
|
const node = nodeMap.get(ln.label);
|
|
@@ -29439,8 +29391,8 @@ function renderBoxesAndLines(container, parsed, layout, palette, isDark, options
|
|
|
29439
29391
|
nodeG.append("rect").attr("x", x).attr("y", y).attr("width", ln.width).attr("height", ln.height).attr("rx", NODE_RX).attr("ry", NODE_RX).attr("fill", colors.fill).attr("stroke", colors.stroke).attr("stroke-width", sNodeStrokeWidth);
|
|
29440
29392
|
const desc = node.description;
|
|
29441
29393
|
if (desc && desc.length > 0 && !hideDescriptions) {
|
|
29442
|
-
const
|
|
29443
|
-
const fitted = fitLabelToHeader(node.label, ln.width,
|
|
29394
|
+
const MAX_LABEL_LINES4 = 3;
|
|
29395
|
+
const fitted = fitLabelToHeader(node.label, ln.width, MAX_LABEL_LINES4);
|
|
29444
29396
|
const labelLines = fitted.lines;
|
|
29445
29397
|
const labelLineH = fitted.fontSize * 1.3;
|
|
29446
29398
|
const labelTotalH = labelLines.length * labelLineH;
|
|
@@ -29574,6 +29526,35 @@ function renderBoxesAndLines(container, parsed, layout, palette, isDark, options
|
|
|
29574
29526
|
}
|
|
29575
29527
|
}
|
|
29576
29528
|
}
|
|
29529
|
+
const labelLayer = diagramG.append("g").attr("class", "bl-edge-labels");
|
|
29530
|
+
const labelLineHeight = sEdgeLabelFontSize * 1.3;
|
|
29531
|
+
for (const le of layout.edges) {
|
|
29532
|
+
if (!le.labelLines || le.labelLines.length === 0) continue;
|
|
29533
|
+
if (le.labelX === void 0 || le.labelY === void 0) continue;
|
|
29534
|
+
const lx = le.labelX;
|
|
29535
|
+
const ly = le.labelY;
|
|
29536
|
+
if (hidden.size > 0) {
|
|
29537
|
+
let isHidden = false;
|
|
29538
|
+
for (const [groupKey, hiddenVals] of hidden) {
|
|
29539
|
+
const val = le.metadata[groupKey];
|
|
29540
|
+
if (val && hiddenVals.has(val.toLowerCase())) {
|
|
29541
|
+
isHidden = true;
|
|
29542
|
+
break;
|
|
29543
|
+
}
|
|
29544
|
+
}
|
|
29545
|
+
if (isHidden) continue;
|
|
29546
|
+
}
|
|
29547
|
+
const lw = le.labelWidth ?? 0;
|
|
29548
|
+
const lh = le.labelHeight ?? sEdgeLabelFontSize + 6;
|
|
29549
|
+
const lines = le.labelLines;
|
|
29550
|
+
const labelG = labelLayer.append("g").attr("class", "bl-edge-label").attr("data-line-number", String(le.lineNumber));
|
|
29551
|
+
labelG.append("rect").attr("x", lx - lw / 2).attr("y", ly - lh / 2).attr("width", lw).attr("height", lh).attr("rx", 3).attr("fill", palette.bg).attr("opacity", 0.72);
|
|
29552
|
+
const text = labelG.append("text").attr("x", lx).attr("text-anchor", "middle").attr("font-family", FONT_FAMILY).attr("font-size", sEdgeLabelFontSize).attr("fill", palette.textMuted);
|
|
29553
|
+
const firstY = ly - (lines.length - 1) / 2 * labelLineHeight + sEdgeLabelFontSize / 3;
|
|
29554
|
+
lines.forEach((line11, k) => {
|
|
29555
|
+
text.append("tspan").attr("x", lx).attr("y", firstY + k * labelLineHeight).text(line11);
|
|
29556
|
+
});
|
|
29557
|
+
}
|
|
29577
29558
|
const hasDescriptions = parsed.nodes.some(
|
|
29578
29559
|
(n) => n.description && n.description.length > 0
|
|
29579
29560
|
);
|
|
@@ -29688,6 +29669,222 @@ var init_renderer6 = __esm({
|
|
|
29688
29669
|
}
|
|
29689
29670
|
});
|
|
29690
29671
|
|
|
29672
|
+
// src/boxes-and-lines/label-placement.ts
|
|
29673
|
+
function measureEdgeLabel(label, fontSize = EDGE_LABEL_FONT_SIZE6, maxWidth = LABEL_MAX_WIDTH) {
|
|
29674
|
+
let lines = wrapTextToWidth(label, fontSize, maxWidth, { hardBreak: true });
|
|
29675
|
+
if (lines.length > MAX_LABEL_LINES) {
|
|
29676
|
+
const kept = lines.slice(0, MAX_LABEL_LINES - 1);
|
|
29677
|
+
const rest = lines.slice(MAX_LABEL_LINES - 1).join(" ");
|
|
29678
|
+
kept.push(truncateText(rest, fontSize, maxWidth));
|
|
29679
|
+
lines = kept;
|
|
29680
|
+
}
|
|
29681
|
+
let textW = 0;
|
|
29682
|
+
for (const ln of lines) {
|
|
29683
|
+
const w = measureText(ln, fontSize);
|
|
29684
|
+
if (w > textW) textW = w;
|
|
29685
|
+
}
|
|
29686
|
+
return {
|
|
29687
|
+
lines,
|
|
29688
|
+
width: textW + 2 * H_PAD,
|
|
29689
|
+
height: lines.length * fontSize * LABEL_LINE_HEIGHT + 2 * V_PAD
|
|
29690
|
+
};
|
|
29691
|
+
}
|
|
29692
|
+
function edgePolylineMidpoint(points) {
|
|
29693
|
+
return pointAtArcFraction(points, 0.5).p;
|
|
29694
|
+
}
|
|
29695
|
+
function pointAtArcFraction(points, t) {
|
|
29696
|
+
if (points.length === 0) return { p: { x: 0, y: 0 }, nx: 0, ny: 1 };
|
|
29697
|
+
if (points.length === 1)
|
|
29698
|
+
return { p: { x: points[0].x, y: points[0].y }, nx: 0, ny: 1 };
|
|
29699
|
+
const segLen = [];
|
|
29700
|
+
let total = 0;
|
|
29701
|
+
for (let k = 1; k < points.length; k++) {
|
|
29702
|
+
const len = Math.hypot(
|
|
29703
|
+
points[k].x - points[k - 1].x,
|
|
29704
|
+
points[k].y - points[k - 1].y
|
|
29705
|
+
);
|
|
29706
|
+
segLen.push(len);
|
|
29707
|
+
total += len;
|
|
29708
|
+
}
|
|
29709
|
+
let want = total * Math.max(0, Math.min(1, t));
|
|
29710
|
+
for (let k = 1; k < points.length; k++) {
|
|
29711
|
+
const len = segLen[k - 1];
|
|
29712
|
+
if (want <= len || k === points.length - 1) {
|
|
29713
|
+
const f = len === 0 ? 0 : Math.min(1, want / len);
|
|
29714
|
+
const ax = points[k - 1].x;
|
|
29715
|
+
const ay = points[k - 1].y;
|
|
29716
|
+
const bx = points[k].x;
|
|
29717
|
+
const by = points[k].y;
|
|
29718
|
+
const dx = bx - ax;
|
|
29719
|
+
const dy = by - ay;
|
|
29720
|
+
const dlen = Math.hypot(dx, dy) || 1;
|
|
29721
|
+
return {
|
|
29722
|
+
p: { x: ax + dx * f, y: ay + dy * f },
|
|
29723
|
+
nx: -dy / dlen,
|
|
29724
|
+
ny: dx / dlen
|
|
29725
|
+
};
|
|
29726
|
+
}
|
|
29727
|
+
want -= len;
|
|
29728
|
+
}
|
|
29729
|
+
const last = points[points.length - 1];
|
|
29730
|
+
return { p: { x: last.x, y: last.y }, nx: 0, ny: 1 };
|
|
29731
|
+
}
|
|
29732
|
+
function rectFromCenter(cx, cy, w, h) {
|
|
29733
|
+
return {
|
|
29734
|
+
minX: cx - w / 2,
|
|
29735
|
+
minY: cy - h / 2,
|
|
29736
|
+
maxX: cx + w / 2,
|
|
29737
|
+
maxY: cy + h / 2
|
|
29738
|
+
};
|
|
29739
|
+
}
|
|
29740
|
+
function overlapsAny(cx, cy, w, h, obstacles, pad2) {
|
|
29741
|
+
const minX = cx - w / 2 - pad2;
|
|
29742
|
+
const minY = cy - h / 2 - pad2;
|
|
29743
|
+
const maxX = cx + w / 2 + pad2;
|
|
29744
|
+
const maxY = cy + h / 2 + pad2;
|
|
29745
|
+
for (const o of obstacles) {
|
|
29746
|
+
if (minX < o.maxX && maxX > o.minX && minY < o.maxY && maxY > o.minY)
|
|
29747
|
+
return true;
|
|
29748
|
+
}
|
|
29749
|
+
return false;
|
|
29750
|
+
}
|
|
29751
|
+
function slideFractions() {
|
|
29752
|
+
const out = [0.5];
|
|
29753
|
+
for (let k = 1; k <= SLIDE_SAMPLES; k++) {
|
|
29754
|
+
const off = k * 0.08;
|
|
29755
|
+
if (0.5 - off >= 0.12) out.push(0.5 - off);
|
|
29756
|
+
if (0.5 + off <= 0.88) out.push(0.5 + off);
|
|
29757
|
+
}
|
|
29758
|
+
return out;
|
|
29759
|
+
}
|
|
29760
|
+
function findClearPosition(w, h, points, obstacles) {
|
|
29761
|
+
const ts = slideFractions();
|
|
29762
|
+
for (const t of ts) {
|
|
29763
|
+
const { p } = pointAtArcFraction(points, t);
|
|
29764
|
+
if (!overlapsAny(p.x, p.y, w, h, obstacles, BOX_CLEAR_PAD)) return p;
|
|
29765
|
+
}
|
|
29766
|
+
for (let mag = PERP_STEP; mag <= PERP_MAX; mag += PERP_STEP) {
|
|
29767
|
+
for (const t of ts) {
|
|
29768
|
+
const { p, nx, ny } = pointAtArcFraction(points, t);
|
|
29769
|
+
for (const sign of [-1, 1]) {
|
|
29770
|
+
const x = p.x + nx * mag * sign;
|
|
29771
|
+
const y = p.y + ny * mag * sign;
|
|
29772
|
+
if (!overlapsAny(x, y, w, h, obstacles, BOX_CLEAR_PAD)) return { x, y };
|
|
29773
|
+
}
|
|
29774
|
+
}
|
|
29775
|
+
}
|
|
29776
|
+
return null;
|
|
29777
|
+
}
|
|
29778
|
+
function resolveLabelOverlaps(boxes) {
|
|
29779
|
+
const MAX_PASSES = 8;
|
|
29780
|
+
const PAD = 4;
|
|
29781
|
+
for (let pass = 0; pass < MAX_PASSES; pass++) {
|
|
29782
|
+
let moved = false;
|
|
29783
|
+
for (let i = 0; i < boxes.length; i++) {
|
|
29784
|
+
for (let j = i + 1; j < boxes.length; j++) {
|
|
29785
|
+
const a = boxes[i];
|
|
29786
|
+
const b = boxes[j];
|
|
29787
|
+
const dx = Math.abs(a.cx - b.cx);
|
|
29788
|
+
const dy = Math.abs(a.cy - b.cy);
|
|
29789
|
+
const overlapX = (a.w + b.w) / 2 + PAD - dx;
|
|
29790
|
+
const overlapY = (a.h + b.h) / 2 + PAD - dy;
|
|
29791
|
+
if (overlapX > 0 && overlapY > 0) {
|
|
29792
|
+
const shift = overlapY / 2 + 1;
|
|
29793
|
+
if (a.cy < b.cy) {
|
|
29794
|
+
a.cy -= shift;
|
|
29795
|
+
b.cy += shift;
|
|
29796
|
+
} else {
|
|
29797
|
+
a.cy += shift;
|
|
29798
|
+
b.cy -= shift;
|
|
29799
|
+
}
|
|
29800
|
+
moved = true;
|
|
29801
|
+
}
|
|
29802
|
+
}
|
|
29803
|
+
}
|
|
29804
|
+
if (!moved) break;
|
|
29805
|
+
}
|
|
29806
|
+
}
|
|
29807
|
+
function placeEdgeLabels(layout, opts) {
|
|
29808
|
+
const fontSize = opts?.fontSize ?? EDGE_LABEL_FONT_SIZE6;
|
|
29809
|
+
const maxWidth = opts?.maxWidth ?? LABEL_MAX_WIDTH;
|
|
29810
|
+
const obstacles = [];
|
|
29811
|
+
for (const n of layout.nodes)
|
|
29812
|
+
obstacles.push(rectFromCenter(n.x, n.y, n.width, n.height));
|
|
29813
|
+
for (const g of layout.groups)
|
|
29814
|
+
if (g.collapsed)
|
|
29815
|
+
obstacles.push(rectFromCenter(g.x, g.y, g.width, g.height));
|
|
29816
|
+
const boxes = [];
|
|
29817
|
+
layout.edges.forEach((e, idx) => {
|
|
29818
|
+
if (!e.label || e.points.length < 2) return;
|
|
29819
|
+
const m = measureEdgeLabel(e.label, fontSize, maxWidth);
|
|
29820
|
+
const mid = edgePolylineMidpoint(e.points);
|
|
29821
|
+
let cy = mid.y;
|
|
29822
|
+
if (e.parallelCount > 1 && e.yOffset !== 0)
|
|
29823
|
+
cy += (e.yOffset < 0 ? -1 : 1) * (m.height / 2);
|
|
29824
|
+
boxes.push({
|
|
29825
|
+
edgeIdx: idx,
|
|
29826
|
+
cx: mid.x,
|
|
29827
|
+
cy,
|
|
29828
|
+
w: m.width,
|
|
29829
|
+
h: m.height,
|
|
29830
|
+
lines: m.lines,
|
|
29831
|
+
resolved: true
|
|
29832
|
+
});
|
|
29833
|
+
});
|
|
29834
|
+
for (const box of boxes) {
|
|
29835
|
+
if (!overlapsAny(box.cx, box.cy, box.w, box.h, obstacles, BOX_CLEAR_PAD))
|
|
29836
|
+
continue;
|
|
29837
|
+
const e = layout.edges[box.edgeIdx];
|
|
29838
|
+
const clear = findClearPosition(box.w, box.h, e.points, obstacles);
|
|
29839
|
+
if (clear) {
|
|
29840
|
+
box.cx = clear.x;
|
|
29841
|
+
box.cy = clear.y;
|
|
29842
|
+
} else {
|
|
29843
|
+
box.resolved = false;
|
|
29844
|
+
}
|
|
29845
|
+
}
|
|
29846
|
+
resolveLabelOverlaps(boxes);
|
|
29847
|
+
for (const box of boxes) {
|
|
29848
|
+
if (overlapsAny(box.cx, box.cy, box.w, box.h, obstacles, BOX_CLEAR_PAD))
|
|
29849
|
+
box.resolved = false;
|
|
29850
|
+
}
|
|
29851
|
+
const boxByIdx = /* @__PURE__ */ new Map();
|
|
29852
|
+
for (const b of boxes) boxByIdx.set(b.edgeIdx, b);
|
|
29853
|
+
const edges = layout.edges.map((e, idx) => {
|
|
29854
|
+
const b = boxByIdx.get(idx);
|
|
29855
|
+
if (!b) return e;
|
|
29856
|
+
return {
|
|
29857
|
+
...e,
|
|
29858
|
+
labelX: b.cx,
|
|
29859
|
+
labelY: b.cy,
|
|
29860
|
+
labelWidth: b.w,
|
|
29861
|
+
labelHeight: b.h,
|
|
29862
|
+
labelLines: b.lines
|
|
29863
|
+
};
|
|
29864
|
+
});
|
|
29865
|
+
return {
|
|
29866
|
+
layout: { ...layout, edges },
|
|
29867
|
+
unresolved: boxes.filter((b) => !b.resolved).map((b) => b.edgeIdx)
|
|
29868
|
+
};
|
|
29869
|
+
}
|
|
29870
|
+
var EDGE_LABEL_FONT_SIZE6, LABEL_MAX_WIDTH, MAX_LABEL_LINES, LABEL_LINE_HEIGHT, H_PAD, V_PAD, BOX_CLEAR_PAD, PERP_STEP, PERP_MAX, SLIDE_SAMPLES;
|
|
29871
|
+
var init_label_placement = __esm({
|
|
29872
|
+
"src/boxes-and-lines/label-placement.ts"() {
|
|
29873
|
+
"use strict";
|
|
29874
|
+
init_text_measure();
|
|
29875
|
+
EDGE_LABEL_FONT_SIZE6 = 11;
|
|
29876
|
+
LABEL_MAX_WIDTH = 160;
|
|
29877
|
+
MAX_LABEL_LINES = 3;
|
|
29878
|
+
LABEL_LINE_HEIGHT = 1.3;
|
|
29879
|
+
H_PAD = 6;
|
|
29880
|
+
V_PAD = 3;
|
|
29881
|
+
BOX_CLEAR_PAD = 4;
|
|
29882
|
+
PERP_STEP = 8;
|
|
29883
|
+
PERP_MAX = 40;
|
|
29884
|
+
SLIDE_SAMPLES = 9;
|
|
29885
|
+
}
|
|
29886
|
+
});
|
|
29887
|
+
|
|
29691
29888
|
// src/boxes-and-lines/layout-layered.ts
|
|
29692
29889
|
function rng(s) {
|
|
29693
29890
|
return () => {
|
|
@@ -29847,7 +30044,7 @@ function layeredCandidates(parsed, sizes, opts) {
|
|
|
29847
30044
|
for (let r = 0; r < maxRank; r++) c += gapCrossings(r);
|
|
29848
30045
|
return c;
|
|
29849
30046
|
};
|
|
29850
|
-
const
|
|
30047
|
+
const median2 = (vals) => {
|
|
29851
30048
|
if (vals.length === 0) return -1;
|
|
29852
30049
|
vals.sort((x, y) => x - y);
|
|
29853
30050
|
const m = Math.floor(vals.length / 2);
|
|
@@ -29862,7 +30059,7 @@ function layeredCandidates(parsed, sizes, opts) {
|
|
|
29862
30059
|
const neigh = useUp ? up : down;
|
|
29863
30060
|
const med = /* @__PURE__ */ new Map();
|
|
29864
30061
|
for (const id of ids)
|
|
29865
|
-
med.set(id,
|
|
30062
|
+
med.set(id, median2(neigh.get(id).map((x) => orderOf.get(x))));
|
|
29866
30063
|
const movable = ids.filter((id) => med.get(id) >= 0).sort((a, b) => med.get(a) - med.get(b));
|
|
29867
30064
|
const out = new Array(ids.length).fill(null);
|
|
29868
30065
|
for (const id of ids) if (med.get(id) < 0) out[orderOf.get(id)] = id;
|
|
@@ -30192,6 +30389,695 @@ var init_layout_layered = __esm({
|
|
|
30192
30389
|
}
|
|
30193
30390
|
});
|
|
30194
30391
|
|
|
30392
|
+
// src/boxes-and-lines/layout-grouped.ts
|
|
30393
|
+
function rng2(s) {
|
|
30394
|
+
return () => {
|
|
30395
|
+
s |= 0;
|
|
30396
|
+
s = s + 1831565813 | 0;
|
|
30397
|
+
let t = Math.imul(s ^ s >>> 15, 1 | s);
|
|
30398
|
+
t = t + Math.imul(t ^ t >>> 7, 61 | t) ^ t;
|
|
30399
|
+
return ((t ^ t >>> 14) >>> 0) / 4294967296;
|
|
30400
|
+
};
|
|
30401
|
+
}
|
|
30402
|
+
function median(vals) {
|
|
30403
|
+
if (vals.length === 0) return -1;
|
|
30404
|
+
vals.sort((x, y) => x - y);
|
|
30405
|
+
const m = Math.floor(vals.length / 2);
|
|
30406
|
+
if (vals.length % 2 === 1) return vals[m];
|
|
30407
|
+
if (vals.length === 2) return (vals[0] + vals[1]) / 2;
|
|
30408
|
+
const left = vals[m - 1] - vals[0];
|
|
30409
|
+
const right = vals[vals.length - 1] - vals[m];
|
|
30410
|
+
return left + right === 0 ? (vals[m - 1] + vals[m]) / 2 : (vals[m - 1] * right + vals[m] * left) / (left + right);
|
|
30411
|
+
}
|
|
30412
|
+
function acyclicOrient(ids, edges) {
|
|
30413
|
+
const adj = /* @__PURE__ */ new Map();
|
|
30414
|
+
for (const l of ids) adj.set(l, []);
|
|
30415
|
+
for (const e of edges) adj.get(e.from)?.push({ to: e.to, idx: e.idx });
|
|
30416
|
+
const reversed = /* @__PURE__ */ new Set();
|
|
30417
|
+
const state = /* @__PURE__ */ new Map();
|
|
30418
|
+
for (const l of ids) state.set(l, 0);
|
|
30419
|
+
const stack = [];
|
|
30420
|
+
const visit = (root) => {
|
|
30421
|
+
stack.push(root);
|
|
30422
|
+
const it = /* @__PURE__ */ new Map();
|
|
30423
|
+
while (stack.length) {
|
|
30424
|
+
const u = stack[stack.length - 1];
|
|
30425
|
+
if (state.get(u) === 0) state.set(u, 1);
|
|
30426
|
+
const list = adj.get(u);
|
|
30427
|
+
let i = it.get(u) ?? 0;
|
|
30428
|
+
let descended = false;
|
|
30429
|
+
for (; i < list.length; i++) {
|
|
30430
|
+
const { to, idx } = list[i];
|
|
30431
|
+
const st = state.get(to);
|
|
30432
|
+
if (st === 1) reversed.add(idx);
|
|
30433
|
+
else if (st === 0) {
|
|
30434
|
+
it.set(u, i + 1);
|
|
30435
|
+
stack.push(to);
|
|
30436
|
+
descended = true;
|
|
30437
|
+
break;
|
|
30438
|
+
}
|
|
30439
|
+
}
|
|
30440
|
+
if (!descended) {
|
|
30441
|
+
it.set(u, list.length);
|
|
30442
|
+
state.set(u, 2);
|
|
30443
|
+
stack.pop();
|
|
30444
|
+
}
|
|
30445
|
+
}
|
|
30446
|
+
};
|
|
30447
|
+
for (const l of ids) if (state.get(l) === 0) visit(l);
|
|
30448
|
+
const dag = edges.map(
|
|
30449
|
+
(e) => reversed.has(e.idx) ? { from: e.to, to: e.from, idx: e.idx, rev: true } : { from: e.from, to: e.to, idx: e.idx, rev: false }
|
|
30450
|
+
);
|
|
30451
|
+
return { dag };
|
|
30452
|
+
}
|
|
30453
|
+
function longestPath(ids, dag) {
|
|
30454
|
+
const out = /* @__PURE__ */ new Map();
|
|
30455
|
+
const inDeg = /* @__PURE__ */ new Map();
|
|
30456
|
+
for (const l of ids) {
|
|
30457
|
+
out.set(l, []);
|
|
30458
|
+
inDeg.set(l, 0);
|
|
30459
|
+
}
|
|
30460
|
+
for (const d of dag) {
|
|
30461
|
+
out.get(d.from).push(d.to);
|
|
30462
|
+
inDeg.set(d.to, (inDeg.get(d.to) ?? 0) + 1);
|
|
30463
|
+
}
|
|
30464
|
+
const rank = /* @__PURE__ */ new Map();
|
|
30465
|
+
for (const l of ids) rank.set(l, 0);
|
|
30466
|
+
const queue = ids.filter((l) => (inDeg.get(l) ?? 0) === 0);
|
|
30467
|
+
const indeg2 = new Map(inDeg);
|
|
30468
|
+
let seen = 0;
|
|
30469
|
+
while (queue.length) {
|
|
30470
|
+
const u = queue.shift();
|
|
30471
|
+
seen++;
|
|
30472
|
+
for (const v of out.get(u)) {
|
|
30473
|
+
rank.set(v, Math.max(rank.get(v), rank.get(u) + 1));
|
|
30474
|
+
indeg2.set(v, indeg2.get(v) - 1);
|
|
30475
|
+
if (indeg2.get(v) === 0) queue.push(v);
|
|
30476
|
+
}
|
|
30477
|
+
}
|
|
30478
|
+
return seen === ids.length ? rank : null;
|
|
30479
|
+
}
|
|
30480
|
+
function groupedTierCandidates(parsed, sizes, opts) {
|
|
30481
|
+
if (parsed.groups.length === 0) return [];
|
|
30482
|
+
const nCount = parsed.nodes.length;
|
|
30483
|
+
if (nCount < 3 || nCount > 60) return [];
|
|
30484
|
+
const isTB = parsed.direction === "TB";
|
|
30485
|
+
const labels = parsed.nodes.map((n) => n.label);
|
|
30486
|
+
const labelSet = new Set(labels);
|
|
30487
|
+
for (const e of parsed.edges)
|
|
30488
|
+
if (e.source.startsWith("__group_") || e.target.startsWith("__group_"))
|
|
30489
|
+
return [];
|
|
30490
|
+
const groupByLabel = new Map(parsed.groups.map((g) => [g.label, g]));
|
|
30491
|
+
const directGroupOf = /* @__PURE__ */ new Map();
|
|
30492
|
+
for (const grp of parsed.groups)
|
|
30493
|
+
for (const c of grp.children)
|
|
30494
|
+
if (labelSet.has(c)) directGroupOf.set(c, grp.label);
|
|
30495
|
+
const topGroupOf = (groupLabel) => {
|
|
30496
|
+
let cur = groupLabel;
|
|
30497
|
+
const guard = /* @__PURE__ */ new Set();
|
|
30498
|
+
while (true) {
|
|
30499
|
+
const g = groupByLabel.get(cur);
|
|
30500
|
+
if (!g?.parentGroup || guard.has(cur)) return cur;
|
|
30501
|
+
guard.add(cur);
|
|
30502
|
+
cur = g.parentGroup;
|
|
30503
|
+
}
|
|
30504
|
+
};
|
|
30505
|
+
const pathOf = (label) => {
|
|
30506
|
+
const direct = directGroupOf.get(label);
|
|
30507
|
+
if (!direct) return [];
|
|
30508
|
+
const chain = [direct];
|
|
30509
|
+
let cur = direct;
|
|
30510
|
+
const guard = /* @__PURE__ */ new Set([direct]);
|
|
30511
|
+
while (true) {
|
|
30512
|
+
const g = groupByLabel.get(cur);
|
|
30513
|
+
if (!g?.parentGroup || guard.has(g.parentGroup)) break;
|
|
30514
|
+
chain.push(g.parentGroup);
|
|
30515
|
+
guard.add(g.parentGroup);
|
|
30516
|
+
cur = g.parentGroup;
|
|
30517
|
+
}
|
|
30518
|
+
return chain.reverse();
|
|
30519
|
+
};
|
|
30520
|
+
const SINGLE = "\0node\0";
|
|
30521
|
+
const unitOf = (label) => {
|
|
30522
|
+
const direct = directGroupOf.get(label);
|
|
30523
|
+
return direct ? topGroupOf(direct) : SINGLE + label;
|
|
30524
|
+
};
|
|
30525
|
+
const edges = parsed.edges.map((e, i) => ({ e, i })).filter(
|
|
30526
|
+
({ e }) => labelSet.has(e.source) && labelSet.has(e.target) && e.source !== e.target
|
|
30527
|
+
);
|
|
30528
|
+
if (edges.length === 0) return [];
|
|
30529
|
+
const unitOfNode = /* @__PURE__ */ new Map();
|
|
30530
|
+
for (const l of labels) unitOfNode.set(l, unitOf(l));
|
|
30531
|
+
const units = Array.from(new Set(labels.map((l) => unitOfNode.get(l))));
|
|
30532
|
+
const interUnit = edges.filter(({ e }) => unitOfNode.get(e.source) !== unitOfNode.get(e.target)).map(({ e, i }) => ({
|
|
30533
|
+
from: unitOfNode.get(e.source),
|
|
30534
|
+
to: unitOfNode.get(e.target),
|
|
30535
|
+
idx: i
|
|
30536
|
+
}));
|
|
30537
|
+
const { dag: unitDag } = acyclicOrient(units, interUnit);
|
|
30538
|
+
const tier = longestPath(
|
|
30539
|
+
units,
|
|
30540
|
+
unitDag.map((d) => ({ from: d.from, to: d.to }))
|
|
30541
|
+
);
|
|
30542
|
+
if (!tier) return [];
|
|
30543
|
+
const localRank = /* @__PURE__ */ new Map();
|
|
30544
|
+
const unitMembers = /* @__PURE__ */ new Map();
|
|
30545
|
+
for (const l of labels) {
|
|
30546
|
+
const u = unitOfNode.get(l);
|
|
30547
|
+
(unitMembers.get(u) ?? unitMembers.set(u, []).get(u)).push(l);
|
|
30548
|
+
}
|
|
30549
|
+
for (const [u, members] of unitMembers) {
|
|
30550
|
+
const memberSet = new Set(members);
|
|
30551
|
+
const intra = edges.filter(
|
|
30552
|
+
({ e }) => unitOfNode.get(e.source) === u && unitOfNode.get(e.target) === u && memberSet.has(e.source) && memberSet.has(e.target)
|
|
30553
|
+
).map(({ e, i }) => ({ from: e.source, to: e.target, idx: i }));
|
|
30554
|
+
const { dag } = acyclicOrient(members, intra);
|
|
30555
|
+
const lr = longestPath(
|
|
30556
|
+
members,
|
|
30557
|
+
dag.map((d) => ({ from: d.from, to: d.to }))
|
|
30558
|
+
);
|
|
30559
|
+
if (!lr) return [];
|
|
30560
|
+
for (const m of members) localRank.set(m, lr.get(m));
|
|
30561
|
+
}
|
|
30562
|
+
const maxTier = Math.max(...units.map((u) => tier.get(u)));
|
|
30563
|
+
const bandHeight = Array.from({ length: maxTier + 1 }, () => 1);
|
|
30564
|
+
for (const u of units) {
|
|
30565
|
+
const h = Math.max(
|
|
30566
|
+
...unitMembers.get(u).map((m) => localRank.get(m) + 1)
|
|
30567
|
+
);
|
|
30568
|
+
const t = tier.get(u);
|
|
30569
|
+
bandHeight[t] = Math.max(bandHeight[t], h);
|
|
30570
|
+
}
|
|
30571
|
+
const tierBase = [];
|
|
30572
|
+
let accBase = 0;
|
|
30573
|
+
for (let t = 0; t <= maxTier; t++) {
|
|
30574
|
+
tierBase[t] = accBase;
|
|
30575
|
+
accBase += bandHeight[t];
|
|
30576
|
+
}
|
|
30577
|
+
const tierStartRanks = new Set(tierBase.slice(1));
|
|
30578
|
+
const globalRank = /* @__PURE__ */ new Map();
|
|
30579
|
+
for (const l of labels)
|
|
30580
|
+
globalRank.set(
|
|
30581
|
+
l,
|
|
30582
|
+
tierBase[tier.get(unitOfNode.get(l))] + localRank.get(l)
|
|
30583
|
+
);
|
|
30584
|
+
const maxRank = Math.max(...labels.map((l) => globalRank.get(l)));
|
|
30585
|
+
const node = /* @__PURE__ */ new Map();
|
|
30586
|
+
for (const n of parsed.nodes) {
|
|
30587
|
+
const s = sizes.get(n.label) ?? { width: NODE_WIDTH, height: NODE_HEIGHT };
|
|
30588
|
+
node.set(n.label, {
|
|
30589
|
+
id: n.label,
|
|
30590
|
+
dummy: false,
|
|
30591
|
+
rank: globalRank.get(n.label),
|
|
30592
|
+
cross: 0,
|
|
30593
|
+
thick: isTB ? s.width : s.height,
|
|
30594
|
+
depth: isTB ? s.height : s.width,
|
|
30595
|
+
realW: s.width,
|
|
30596
|
+
realH: s.height,
|
|
30597
|
+
unit: unitOfNode.get(n.label),
|
|
30598
|
+
path: pathOf(n.label)
|
|
30599
|
+
});
|
|
30600
|
+
}
|
|
30601
|
+
const chains = [];
|
|
30602
|
+
const segs = [];
|
|
30603
|
+
const backEdges = [];
|
|
30604
|
+
const flatEdges = [];
|
|
30605
|
+
for (const { e, i } of edges) {
|
|
30606
|
+
const rs = globalRank.get(e.source);
|
|
30607
|
+
const rt = globalRank.get(e.target);
|
|
30608
|
+
if (rs === rt) {
|
|
30609
|
+
flatEdges.push({ edgeIdx: i, a: e.source, b: e.target });
|
|
30610
|
+
continue;
|
|
30611
|
+
}
|
|
30612
|
+
if (rt < rs) {
|
|
30613
|
+
backEdges.push({ edgeIdx: i, src: e.source, tgt: e.target });
|
|
30614
|
+
continue;
|
|
30615
|
+
}
|
|
30616
|
+
const chain = [e.source];
|
|
30617
|
+
let prev = e.source;
|
|
30618
|
+
for (let r = rs + 1; r < rt; r++) {
|
|
30619
|
+
const id = `__d${i}_${r}`;
|
|
30620
|
+
node.set(id, {
|
|
30621
|
+
id,
|
|
30622
|
+
dummy: true,
|
|
30623
|
+
rank: r,
|
|
30624
|
+
cross: 0,
|
|
30625
|
+
thick: DUMMY_THICK2,
|
|
30626
|
+
depth: 0,
|
|
30627
|
+
realW: 0,
|
|
30628
|
+
realH: 0,
|
|
30629
|
+
unit: SINGLE + id,
|
|
30630
|
+
path: []
|
|
30631
|
+
});
|
|
30632
|
+
segs.push({ a: prev, b: id });
|
|
30633
|
+
chain.push(id);
|
|
30634
|
+
prev = id;
|
|
30635
|
+
}
|
|
30636
|
+
segs.push({ a: prev, b: e.target });
|
|
30637
|
+
chain.push(e.target);
|
|
30638
|
+
chains.push({ edgeIdx: i, chain });
|
|
30639
|
+
}
|
|
30640
|
+
const ranks = Array.from({ length: maxRank + 1 }, () => []);
|
|
30641
|
+
for (const n of node.values()) ranks[n.rank].push(n.id);
|
|
30642
|
+
const up = /* @__PURE__ */ new Map();
|
|
30643
|
+
const down = /* @__PURE__ */ new Map();
|
|
30644
|
+
for (const id of node.keys()) {
|
|
30645
|
+
up.set(id, []);
|
|
30646
|
+
down.set(id, []);
|
|
30647
|
+
}
|
|
30648
|
+
for (const s of segs) {
|
|
30649
|
+
down.get(s.a).push(s.b);
|
|
30650
|
+
up.get(s.b).push(s.a);
|
|
30651
|
+
}
|
|
30652
|
+
const orderOf = /* @__PURE__ */ new Map();
|
|
30653
|
+
const gapCrossings = (r) => {
|
|
30654
|
+
const lower = ranks[r + 1];
|
|
30655
|
+
if (!lower) return 0;
|
|
30656
|
+
const es = [];
|
|
30657
|
+
for (const a of ranks[r]) {
|
|
30658
|
+
const pa = orderOf.get(a);
|
|
30659
|
+
for (const b of down.get(a)) es.push({ p: pa, q: orderOf.get(b) });
|
|
30660
|
+
}
|
|
30661
|
+
let c = 0;
|
|
30662
|
+
for (let i = 0; i < es.length; i++)
|
|
30663
|
+
for (let j = i + 1; j < es.length; j++) {
|
|
30664
|
+
const A = es[i], B = es[j];
|
|
30665
|
+
if ((A.p - B.p) * (A.q - B.q) < 0) c++;
|
|
30666
|
+
}
|
|
30667
|
+
return c;
|
|
30668
|
+
};
|
|
30669
|
+
const totalCrossings = () => {
|
|
30670
|
+
let c = 0;
|
|
30671
|
+
for (let r = 0; r < maxRank; r++) c += gapCrossings(r);
|
|
30672
|
+
return c;
|
|
30673
|
+
};
|
|
30674
|
+
const wmedianRank = (r, useUp) => {
|
|
30675
|
+
const ids = ranks[r];
|
|
30676
|
+
const neigh = useUp ? up : down;
|
|
30677
|
+
const med = /* @__PURE__ */ new Map();
|
|
30678
|
+
for (const id of ids)
|
|
30679
|
+
med.set(id, median(neigh.get(id).map((x) => orderOf.get(x))));
|
|
30680
|
+
const movable = ids.filter((id) => med.get(id) >= 0).sort((a, b) => med.get(a) - med.get(b));
|
|
30681
|
+
const out = new Array(ids.length).fill(null);
|
|
30682
|
+
for (const id of ids) if (med.get(id) < 0) out[orderOf.get(id)] = id;
|
|
30683
|
+
let mi = 0;
|
|
30684
|
+
for (let slot = 0; slot < out.length; slot++)
|
|
30685
|
+
if (out[slot] === null) out[slot] = movable[mi++];
|
|
30686
|
+
const final = out;
|
|
30687
|
+
final.forEach((id, i) => orderOf.set(id, i));
|
|
30688
|
+
ranks[r] = final;
|
|
30689
|
+
};
|
|
30690
|
+
const transpose = () => {
|
|
30691
|
+
let improved = true;
|
|
30692
|
+
let guard = 0;
|
|
30693
|
+
while (improved && guard++ < 12) {
|
|
30694
|
+
improved = false;
|
|
30695
|
+
for (let r = 0; r <= maxRank; r++) {
|
|
30696
|
+
const ids = ranks[r];
|
|
30697
|
+
for (let i = 0; i < ids.length - 1; i++) {
|
|
30698
|
+
const before = (r > 0 ? gapCrossings(r - 1) : 0) + (r < maxRank ? gapCrossings(r) : 0);
|
|
30699
|
+
const a = ids[i], b = ids[i + 1];
|
|
30700
|
+
ids[i] = b;
|
|
30701
|
+
ids[i + 1] = a;
|
|
30702
|
+
orderOf.set(b, i);
|
|
30703
|
+
orderOf.set(a, i + 1);
|
|
30704
|
+
const after = (r > 0 ? gapCrossings(r - 1) : 0) + (r < maxRank ? gapCrossings(r) : 0);
|
|
30705
|
+
if (after < before) improved = true;
|
|
30706
|
+
else {
|
|
30707
|
+
ids[i] = a;
|
|
30708
|
+
ids[i + 1] = b;
|
|
30709
|
+
orderOf.set(a, i);
|
|
30710
|
+
orderOf.set(b, i + 1);
|
|
30711
|
+
}
|
|
30712
|
+
}
|
|
30713
|
+
}
|
|
30714
|
+
}
|
|
30715
|
+
};
|
|
30716
|
+
const initOrder = (seed) => {
|
|
30717
|
+
const r = seed === 0 ? null : rng2(seed);
|
|
30718
|
+
for (let rr = 0; rr <= maxRank; rr++) {
|
|
30719
|
+
const ids = ranks[rr].slice();
|
|
30720
|
+
if (r)
|
|
30721
|
+
for (let i = ids.length - 1; i > 0; i--) {
|
|
30722
|
+
const j = Math.floor(r() * (i + 1));
|
|
30723
|
+
[ids[i], ids[j]] = [ids[j], ids[i]];
|
|
30724
|
+
}
|
|
30725
|
+
ranks[rr] = ids;
|
|
30726
|
+
ids.forEach((id, i) => orderOf.set(id, i));
|
|
30727
|
+
}
|
|
30728
|
+
};
|
|
30729
|
+
const restarts = opts?.restarts ?? (nCount <= 16 ? 20 : nCount <= 30 ? 12 : 6);
|
|
30730
|
+
const keepK = opts?.keepK ?? 3;
|
|
30731
|
+
const found = [];
|
|
30732
|
+
for (let s = 0; s < restarts; s++) {
|
|
30733
|
+
initOrder(s);
|
|
30734
|
+
let best = totalCrossings();
|
|
30735
|
+
let bestSnap = new Map(orderOf);
|
|
30736
|
+
for (let iter = 0; iter < 8; iter++) {
|
|
30737
|
+
if (iter % 2 === 0)
|
|
30738
|
+
for (let r = 1; r <= maxRank; r++) wmedianRank(r, true);
|
|
30739
|
+
else for (let r = maxRank - 1; r >= 0; r--) wmedianRank(r, false);
|
|
30740
|
+
transpose();
|
|
30741
|
+
const c = totalCrossings();
|
|
30742
|
+
if (c < best) {
|
|
30743
|
+
best = c;
|
|
30744
|
+
bestSnap = new Map(orderOf);
|
|
30745
|
+
}
|
|
30746
|
+
if (c === 0) break;
|
|
30747
|
+
}
|
|
30748
|
+
for (const [k, v] of bestSnap) orderOf.set(k, v);
|
|
30749
|
+
for (let r = 0; r <= maxRank; r++)
|
|
30750
|
+
ranks[r].sort((a, b) => orderOf.get(a) - orderOf.get(b));
|
|
30751
|
+
const sig = ranks.map((r) => r.join(",")).join("|");
|
|
30752
|
+
if (!found.some((f) => f.sig === sig))
|
|
30753
|
+
found.push({ sig, cross: best, order: new Map(bestSnap) });
|
|
30754
|
+
}
|
|
30755
|
+
found.sort((a, b) => a.cross - b.cross);
|
|
30756
|
+
const keep = found.slice(0, keepK);
|
|
30757
|
+
if (keep.length === 0) return [];
|
|
30758
|
+
const results = [];
|
|
30759
|
+
for (const cand of keep) {
|
|
30760
|
+
for (const [k, v] of cand.order) orderOf.set(k, v);
|
|
30761
|
+
const rk = Array.from({ length: maxRank + 1 }, () => []);
|
|
30762
|
+
for (const n of node.values()) rk[n.rank].push(n.id);
|
|
30763
|
+
for (let r = 0; r <= maxRank; r++)
|
|
30764
|
+
rk[r].sort((a, b) => cand.order.get(a) - cand.order.get(b));
|
|
30765
|
+
results.push(realize(rk));
|
|
30766
|
+
}
|
|
30767
|
+
return results;
|
|
30768
|
+
function weight(a, b) {
|
|
30769
|
+
if (a.dummy && b.dummy) return W_DUMMY_DUMMY2;
|
|
30770
|
+
if (a.dummy || b.dummy) return W_REAL_DUMMY2;
|
|
30771
|
+
return W_REAL_REAL2;
|
|
30772
|
+
}
|
|
30773
|
+
function placeWithSeparation(ids, desired, gap) {
|
|
30774
|
+
const n = ids.length;
|
|
30775
|
+
if (n === 0) return;
|
|
30776
|
+
const off = [0];
|
|
30777
|
+
for (let i = 1; i < n; i++) off[i] = off[i - 1] + gap[i];
|
|
30778
|
+
const d = desired.map((v, i) => v - off[i]);
|
|
30779
|
+
const blocks = [];
|
|
30780
|
+
for (let i = 0; i < n; i++) {
|
|
30781
|
+
let b = { pos: d[i], count: 1, sumOffset: d[i], first: i };
|
|
30782
|
+
while (blocks.length && blocks[blocks.length - 1].pos >= b.pos) {
|
|
30783
|
+
const prev = blocks.pop();
|
|
30784
|
+
const count = prev.count + b.count;
|
|
30785
|
+
const sumOffset = prev.sumOffset + b.sumOffset;
|
|
30786
|
+
b = { pos: sumOffset / count, count, sumOffset, first: prev.first };
|
|
30787
|
+
}
|
|
30788
|
+
blocks.push(b);
|
|
30789
|
+
}
|
|
30790
|
+
const xs = new Array(n);
|
|
30791
|
+
for (const b of blocks)
|
|
30792
|
+
for (let k = 0; k < b.count; k++) xs[b.first + k] = b.pos;
|
|
30793
|
+
for (let i = 0; i < n; i++) node.get(ids[i]).cross = xs[i] + off[i];
|
|
30794
|
+
}
|
|
30795
|
+
function gapBetween(a, b) {
|
|
30796
|
+
const base = a.thick / 2 + b.thick / 2 + NODESEP2;
|
|
30797
|
+
if (a.dummy || b.dummy) return base;
|
|
30798
|
+
if (a.unit !== b.unit) return base + 2 * GROUP_PAD + GROUP_GAP;
|
|
30799
|
+
const da = a.path[a.path.length - 1];
|
|
30800
|
+
const db = b.path[b.path.length - 1];
|
|
30801
|
+
if (da !== db && (da || db)) return base + 2 * GROUP_PAD;
|
|
30802
|
+
return base;
|
|
30803
|
+
}
|
|
30804
|
+
function realize(rk) {
|
|
30805
|
+
const bandDepth = rk.map(
|
|
30806
|
+
(ids) => Math.max(0, ...ids.map((id) => node.get(id).depth))
|
|
30807
|
+
);
|
|
30808
|
+
const bandCenter = [];
|
|
30809
|
+
let acc = MARGIN4;
|
|
30810
|
+
for (let r = 0; r <= maxRank; r++) {
|
|
30811
|
+
if (r > 0) acc += RANKSEP2 + (tierStartRanks.has(r) ? TIER_GAP : 0);
|
|
30812
|
+
bandCenter[r] = acc + bandDepth[r] / 2;
|
|
30813
|
+
acc += bandDepth[r];
|
|
30814
|
+
}
|
|
30815
|
+
const gapsFor = (ids) => ids.map(
|
|
30816
|
+
(id, i) => i === 0 ? 0 : gapBetween(node.get(ids[i - 1]), node.get(id))
|
|
30817
|
+
);
|
|
30818
|
+
for (let r = 0; r <= maxRank; r++) {
|
|
30819
|
+
const ids = rk[r];
|
|
30820
|
+
const gap = gapsFor(ids);
|
|
30821
|
+
let x = MARGIN4;
|
|
30822
|
+
for (let i = 0; i < ids.length; i++) {
|
|
30823
|
+
const n = node.get(ids[i]);
|
|
30824
|
+
x += gap[i];
|
|
30825
|
+
n.cross = i === 0 ? MARGIN4 + n.thick / 2 : x;
|
|
30826
|
+
}
|
|
30827
|
+
}
|
|
30828
|
+
const ITER = 18;
|
|
30829
|
+
for (let it = 0; it < ITER; it++) {
|
|
30830
|
+
const downPass = it % 2 === 0;
|
|
30831
|
+
const order = downPass ? Array.from({ length: maxRank + 1 }, (_, i) => i) : Array.from({ length: maxRank + 1 }, (_, i) => maxRank - i);
|
|
30832
|
+
for (const r of order) {
|
|
30833
|
+
const ids = rk[r];
|
|
30834
|
+
const desired = ids.map((id) => {
|
|
30835
|
+
const n = node.get(id);
|
|
30836
|
+
let sw = 0, sx2 = 0;
|
|
30837
|
+
for (const nb of up.get(id)) {
|
|
30838
|
+
const w = weight(n, node.get(nb));
|
|
30839
|
+
sw += w;
|
|
30840
|
+
sx2 += w * node.get(nb).cross;
|
|
30841
|
+
}
|
|
30842
|
+
for (const nb of down.get(id)) {
|
|
30843
|
+
const w = weight(n, node.get(nb));
|
|
30844
|
+
sw += w;
|
|
30845
|
+
sx2 += w * node.get(nb).cross;
|
|
30846
|
+
}
|
|
30847
|
+
return sw > 0 ? sx2 / sw : n.cross;
|
|
30848
|
+
});
|
|
30849
|
+
placeWithSeparation(ids, desired, gapsFor(ids));
|
|
30850
|
+
}
|
|
30851
|
+
}
|
|
30852
|
+
let minC = Infinity;
|
|
30853
|
+
for (const n of node.values()) minC = Math.min(minC, n.cross - n.thick / 2);
|
|
30854
|
+
const shiftC = MARGIN4 - minC;
|
|
30855
|
+
for (const n of node.values()) n.cross += shiftC;
|
|
30856
|
+
const coord = (n) => isTB ? { x: n.cross, y: bandCenter[n.rank] } : { x: bandCenter[n.rank], y: n.cross };
|
|
30857
|
+
const layoutNodes = parsed.nodes.map((pn) => {
|
|
30858
|
+
const n = node.get(pn.label);
|
|
30859
|
+
const c = coord(n);
|
|
30860
|
+
return {
|
|
30861
|
+
label: pn.label,
|
|
30862
|
+
x: c.x,
|
|
30863
|
+
y: c.y,
|
|
30864
|
+
width: n.realW,
|
|
30865
|
+
height: n.realH
|
|
30866
|
+
};
|
|
30867
|
+
});
|
|
30868
|
+
const chainById = /* @__PURE__ */ new Map();
|
|
30869
|
+
for (const ch of chains) chainById.set(ch.edgeIdx, ch.chain);
|
|
30870
|
+
let minCross = Infinity, maxCross = -Infinity;
|
|
30871
|
+
for (const n of node.values()) {
|
|
30872
|
+
if (n.dummy) continue;
|
|
30873
|
+
minCross = Math.min(minCross, n.cross - n.thick / 2);
|
|
30874
|
+
maxCross = Math.max(maxCross, n.cross + n.thick / 2);
|
|
30875
|
+
}
|
|
30876
|
+
const GAP = 34;
|
|
30877
|
+
const LANE = 28;
|
|
30878
|
+
const faceLim = (depth) => Math.max(0, depth / 2 - 6);
|
|
30879
|
+
const sideOf = (b) => {
|
|
30880
|
+
const d = node.get(b.src).cross - node.get(b.tgt).cross;
|
|
30881
|
+
return d >= 0 ? 1 : -1;
|
|
30882
|
+
};
|
|
30883
|
+
const backSorted = backEdges.map((b) => ({
|
|
30884
|
+
...b,
|
|
30885
|
+
side: sideOf(b),
|
|
30886
|
+
span: Math.abs(node.get(b.src).rank - node.get(b.tgt).rank)
|
|
30887
|
+
})).sort((a, b) => a.side - b.side || a.span - b.span);
|
|
30888
|
+
const sideCounts = /* @__PURE__ */ new Map();
|
|
30889
|
+
for (const b of backSorted)
|
|
30890
|
+
sideCounts.set(b.side, (sideCounts.get(b.side) ?? 0) + 1);
|
|
30891
|
+
const laneCounter = /* @__PURE__ */ new Map();
|
|
30892
|
+
const backPoints = /* @__PURE__ */ new Map();
|
|
30893
|
+
for (const b of backSorted) {
|
|
30894
|
+
const s = b.side;
|
|
30895
|
+
const k = laneCounter.get(s) ?? 0;
|
|
30896
|
+
laneCounter.set(s, k + 1);
|
|
30897
|
+
const K = sideCounts.get(s);
|
|
30898
|
+
const src = node.get(b.src);
|
|
30899
|
+
const tgt = node.get(b.tgt);
|
|
30900
|
+
const laneC = s > 0 ? maxCross + GAP + k * LANE : minCross - GAP - k * LANE;
|
|
30901
|
+
const srcCtr = bandCenter[src.rank];
|
|
30902
|
+
const tgtCtr = bandCenter[tgt.rank];
|
|
30903
|
+
const frac = K > 1 ? (k + 1) / (K + 1) : 0;
|
|
30904
|
+
const srcR = srcCtr - frac * faceLim(src.depth);
|
|
30905
|
+
const tgtR = tgtCtr + frac * faceLim(tgt.depth);
|
|
30906
|
+
const m = (c, rr) => isTB ? { x: c, y: rr } : { x: rr, y: c };
|
|
30907
|
+
const off = 10;
|
|
30908
|
+
const srcEdgeC = src.cross + s * (src.thick / 2 + off);
|
|
30909
|
+
const tgtEdgeC = tgt.cross + s * (tgt.thick / 2 + off);
|
|
30910
|
+
backPoints.set(b.edgeIdx, [
|
|
30911
|
+
m(src.cross, srcCtr),
|
|
30912
|
+
m(srcEdgeC, srcR),
|
|
30913
|
+
m(laneC, srcR),
|
|
30914
|
+
m(laneC, tgtR),
|
|
30915
|
+
m(tgtEdgeC, tgtR),
|
|
30916
|
+
m(tgt.cross, tgtCtr)
|
|
30917
|
+
]);
|
|
30918
|
+
}
|
|
30919
|
+
const flatPoints = /* @__PURE__ */ new Map();
|
|
30920
|
+
for (const f of flatEdges) {
|
|
30921
|
+
const a = node.get(f.a);
|
|
30922
|
+
const b = node.get(f.b);
|
|
30923
|
+
const ctr = bandCenter[a.rank];
|
|
30924
|
+
const bow = ctr - (a.depth / 2 + 26);
|
|
30925
|
+
const m = (c, rr) => isTB ? { x: c, y: rr } : { x: rr, y: c };
|
|
30926
|
+
flatPoints.set(f.edgeIdx, [
|
|
30927
|
+
m(a.cross, ctr),
|
|
30928
|
+
m(a.cross, bow),
|
|
30929
|
+
m(b.cross, bow),
|
|
30930
|
+
m(b.cross, ctr)
|
|
30931
|
+
]);
|
|
30932
|
+
}
|
|
30933
|
+
const layoutEdges = [];
|
|
30934
|
+
for (let i = 0; i < parsed.edges.length; i++) {
|
|
30935
|
+
const e = parsed.edges[i];
|
|
30936
|
+
if (!labelSet.has(e.source) || !labelSet.has(e.target)) continue;
|
|
30937
|
+
let points;
|
|
30938
|
+
if (e.source === e.target) {
|
|
30939
|
+
const c = coord(node.get(e.source));
|
|
30940
|
+
points = [c, c];
|
|
30941
|
+
} else if (backPoints.has(i)) points = backPoints.get(i);
|
|
30942
|
+
else if (flatPoints.has(i)) points = flatPoints.get(i);
|
|
30943
|
+
else {
|
|
30944
|
+
const chain = chainById.get(i);
|
|
30945
|
+
if (!chain) continue;
|
|
30946
|
+
points = chain.map((id) => coord(node.get(id)));
|
|
30947
|
+
}
|
|
30948
|
+
layoutEdges.push({
|
|
30949
|
+
source: e.source,
|
|
30950
|
+
target: e.target,
|
|
30951
|
+
...e.label !== void 0 && { label: e.label },
|
|
30952
|
+
bidirectional: e.bidirectional,
|
|
30953
|
+
lineNumber: e.lineNumber,
|
|
30954
|
+
points,
|
|
30955
|
+
yOffset: 0,
|
|
30956
|
+
parallelCount: 1,
|
|
30957
|
+
metadata: e.metadata
|
|
30958
|
+
});
|
|
30959
|
+
}
|
|
30960
|
+
const nodeBox = new Map(
|
|
30961
|
+
layoutNodes.map((n) => [
|
|
30962
|
+
n.label,
|
|
30963
|
+
{
|
|
30964
|
+
l: n.x - n.width / 2,
|
|
30965
|
+
r: n.x + n.width / 2,
|
|
30966
|
+
t: n.y - n.height / 2,
|
|
30967
|
+
b: n.y + n.height / 2
|
|
30968
|
+
}
|
|
30969
|
+
])
|
|
30970
|
+
);
|
|
30971
|
+
const depthOf = (label) => {
|
|
30972
|
+
let d = 0;
|
|
30973
|
+
let cur = label;
|
|
30974
|
+
const guard = /* @__PURE__ */ new Set();
|
|
30975
|
+
while (cur && !guard.has(cur)) {
|
|
30976
|
+
guard.add(cur);
|
|
30977
|
+
cur = groupByLabel.get(cur)?.parentGroup;
|
|
30978
|
+
if (cur) d++;
|
|
30979
|
+
}
|
|
30980
|
+
return d;
|
|
30981
|
+
};
|
|
30982
|
+
const childGroups = /* @__PURE__ */ new Map();
|
|
30983
|
+
for (const g of parsed.groups)
|
|
30984
|
+
if (g.parentGroup)
|
|
30985
|
+
(childGroups.get(g.parentGroup) ?? childGroups.set(g.parentGroup, []).get(g.parentGroup)).push(g.label);
|
|
30986
|
+
const rectByGroup = /* @__PURE__ */ new Map();
|
|
30987
|
+
const ordered = [...parsed.groups].sort(
|
|
30988
|
+
(a, b) => depthOf(b.label) - depthOf(a.label)
|
|
30989
|
+
);
|
|
30990
|
+
const layoutGroups = [];
|
|
30991
|
+
for (const grp of ordered) {
|
|
30992
|
+
let l = Infinity, r = -Infinity, t = Infinity, bm = -Infinity;
|
|
30993
|
+
const acc2 = (box) => {
|
|
30994
|
+
l = Math.min(l, box.l);
|
|
30995
|
+
r = Math.max(r, box.r);
|
|
30996
|
+
t = Math.min(t, box.t);
|
|
30997
|
+
bm = Math.max(bm, box.b);
|
|
30998
|
+
};
|
|
30999
|
+
for (const c of grp.children) {
|
|
31000
|
+
const nb = nodeBox.get(c);
|
|
31001
|
+
if (nb) acc2(nb);
|
|
31002
|
+
}
|
|
31003
|
+
for (const sub of childGroups.get(grp.label) ?? []) {
|
|
31004
|
+
const sr = rectByGroup.get(sub);
|
|
31005
|
+
if (sr) acc2(sr);
|
|
31006
|
+
}
|
|
31007
|
+
if (!Number.isFinite(l)) continue;
|
|
31008
|
+
const x0 = l - GROUP_PAD;
|
|
31009
|
+
const x1 = r + GROUP_PAD;
|
|
31010
|
+
const y0 = t - GROUP_LABEL_ZONE2;
|
|
31011
|
+
const y1 = bm + GROUP_PAD;
|
|
31012
|
+
rectByGroup.set(grp.label, { l: x0, r: x1, t: y0, b: y1 });
|
|
31013
|
+
layoutGroups.push({
|
|
31014
|
+
label: grp.label,
|
|
31015
|
+
lineNumber: grp.lineNumber,
|
|
31016
|
+
x: (x0 + x1) / 2,
|
|
31017
|
+
y: (y0 + y1) / 2,
|
|
31018
|
+
width: x1 - x0,
|
|
31019
|
+
height: y1 - y0,
|
|
31020
|
+
collapsed: false,
|
|
31021
|
+
childCount: grp.children.length
|
|
31022
|
+
});
|
|
31023
|
+
}
|
|
31024
|
+
let minX = Infinity, minY = Infinity, maxX = -Infinity, maxY = -Infinity;
|
|
31025
|
+
const ext = (x0, y0, x1, y1) => {
|
|
31026
|
+
minX = Math.min(minX, x0);
|
|
31027
|
+
minY = Math.min(minY, y0);
|
|
31028
|
+
maxX = Math.max(maxX, x1);
|
|
31029
|
+
maxY = Math.max(maxY, y1);
|
|
31030
|
+
};
|
|
31031
|
+
for (const n of layoutNodes)
|
|
31032
|
+
ext(
|
|
31033
|
+
n.x - n.width / 2,
|
|
31034
|
+
n.y - n.height / 2,
|
|
31035
|
+
n.x + n.width / 2,
|
|
31036
|
+
n.y + n.height / 2
|
|
31037
|
+
);
|
|
31038
|
+
for (const e of layoutEdges)
|
|
31039
|
+
for (const p of e.points) ext(p.x, p.y, p.x, p.y);
|
|
31040
|
+
for (const g of layoutGroups)
|
|
31041
|
+
ext(
|
|
31042
|
+
g.x - g.width / 2,
|
|
31043
|
+
g.y - g.height / 2,
|
|
31044
|
+
g.x + g.width / 2,
|
|
31045
|
+
g.y + g.height / 2
|
|
31046
|
+
);
|
|
31047
|
+
const sx = MARGIN4 - minX;
|
|
31048
|
+
const sy = MARGIN4 - minY;
|
|
31049
|
+
const shift = sx !== 0 || sy !== 0;
|
|
31050
|
+
return {
|
|
31051
|
+
nodes: shift ? layoutNodes.map((n) => ({ ...n, x: n.x + sx, y: n.y + sy })) : layoutNodes,
|
|
31052
|
+
edges: shift ? layoutEdges.map((e) => ({
|
|
31053
|
+
...e,
|
|
31054
|
+
points: e.points.map((p) => ({ x: p.x + sx, y: p.y + sy }))
|
|
31055
|
+
})) : layoutEdges,
|
|
31056
|
+
groups: shift ? layoutGroups.map((g) => ({ ...g, x: g.x + sx, y: g.y + sy })) : layoutGroups,
|
|
31057
|
+
width: maxX + sx + MARGIN4,
|
|
31058
|
+
height: maxY + sy + MARGIN4
|
|
31059
|
+
};
|
|
31060
|
+
}
|
|
31061
|
+
}
|
|
31062
|
+
var NODESEP2, RANKSEP2, DUMMY_THICK2, MARGIN4, GROUP_PAD, GROUP_LABEL_ZONE2, GROUP_GAP, TIER_GAP, W_REAL_REAL2, W_REAL_DUMMY2, W_DUMMY_DUMMY2;
|
|
31063
|
+
var init_layout_grouped = __esm({
|
|
31064
|
+
"src/boxes-and-lines/layout-grouped.ts"() {
|
|
31065
|
+
"use strict";
|
|
31066
|
+
init_layout5();
|
|
31067
|
+
NODESEP2 = 50;
|
|
31068
|
+
RANKSEP2 = 60;
|
|
31069
|
+
DUMMY_THICK2 = 10;
|
|
31070
|
+
MARGIN4 = 40;
|
|
31071
|
+
GROUP_PAD = 16;
|
|
31072
|
+
GROUP_LABEL_ZONE2 = 32;
|
|
31073
|
+
GROUP_GAP = 24;
|
|
31074
|
+
TIER_GAP = GROUP_LABEL_ZONE2 + 2 * GROUP_PAD;
|
|
31075
|
+
W_REAL_REAL2 = 1;
|
|
31076
|
+
W_REAL_DUMMY2 = 2;
|
|
31077
|
+
W_DUMMY_DUMMY2 = 8;
|
|
31078
|
+
}
|
|
31079
|
+
});
|
|
31080
|
+
|
|
30195
31081
|
// src/boxes-and-lines/layout-search.ts
|
|
30196
31082
|
var layout_search_exports = {};
|
|
30197
31083
|
__export(layout_search_exports, {
|
|
@@ -30209,7 +31095,7 @@ __export(layout_search_exports, {
|
|
|
30209
31095
|
});
|
|
30210
31096
|
import dagre4 from "@dagrejs/dagre";
|
|
30211
31097
|
import { line as d3line, curveBasis as curveBasis5 } from "d3-shape";
|
|
30212
|
-
function
|
|
31098
|
+
function rng3(s) {
|
|
30213
31099
|
return () => {
|
|
30214
31100
|
s |= 0;
|
|
30215
31101
|
s = s + 1831565813 | 0;
|
|
@@ -30564,7 +31450,7 @@ function detectGroupOverlaps(layout, opts) {
|
|
|
30564
31450
|
const contains = (outer, inner) => outer.l <= inner.l + margin && outer.r >= inner.r - margin && outer.t <= inner.t + margin && outer.b >= inner.b - margin;
|
|
30565
31451
|
const rend = raw.map((a, i) => {
|
|
30566
31452
|
const parent = raw.some((b, j) => j !== i && contains(a, b));
|
|
30567
|
-
return parent ? { ...a, t: a.t -
|
|
31453
|
+
return parent ? { ...a, t: a.t - GROUP_LABEL_ZONE3 } : a;
|
|
30568
31454
|
});
|
|
30569
31455
|
const hit = /* @__PURE__ */ new Set();
|
|
30570
31456
|
for (let i = 0; i < raw.length; i++)
|
|
@@ -30591,7 +31477,7 @@ function countGroupOverlaps(layout, opts) {
|
|
|
30591
31477
|
const contains = (outer, inner) => outer.l <= inner.l + margin && outer.r >= inner.r - margin && outer.t <= inner.t + margin && outer.b >= inner.b - margin;
|
|
30592
31478
|
const rend = raw.map((a, i) => {
|
|
30593
31479
|
const parent = raw.some((b, j) => j !== i && contains(a, b));
|
|
30594
|
-
return parent ? { ...a, t: a.t -
|
|
31480
|
+
return parent ? { ...a, t: a.t - GROUP_LABEL_ZONE3 } : a;
|
|
30595
31481
|
});
|
|
30596
31482
|
let count = 0;
|
|
30597
31483
|
for (let i = 0; i < raw.length; i++)
|
|
@@ -30634,7 +31520,7 @@ function separateGroupBands(layout, parsed) {
|
|
|
30634
31520
|
let lo = (axis === "y" ? g.y : g.x) - half2;
|
|
30635
31521
|
const hi = (axis === "y" ? g.y : g.x) + half2;
|
|
30636
31522
|
const isParent = parsed.groups.some((c) => c.parentGroup === label);
|
|
30637
|
-
if (axis === "y" && isParent) lo -=
|
|
31523
|
+
if (axis === "y" && isParent) lo -= GROUP_LABEL_ZONE3;
|
|
30638
31524
|
return { label, lo, hi, c: (lo + hi) / 2 };
|
|
30639
31525
|
});
|
|
30640
31526
|
bands.sort((a, b) => a.c - b.c);
|
|
@@ -30705,7 +31591,7 @@ function separateGroupBands(layout, parsed) {
|
|
|
30705
31591
|
acc(n.x + n.width / 2, n.y + n.height / 2);
|
|
30706
31592
|
}
|
|
30707
31593
|
for (const g of groups) {
|
|
30708
|
-
acc(g.x - g.width / 2, g.y - g.height / 2 -
|
|
31594
|
+
acc(g.x - g.width / 2, g.y - g.height / 2 - GROUP_LABEL_ZONE3);
|
|
30709
31595
|
acc(g.x + g.width / 2, g.y + g.height / 2);
|
|
30710
31596
|
}
|
|
30711
31597
|
for (const e of edges) for (const p of e.points) acc(p.x, p.y);
|
|
@@ -30788,6 +31674,7 @@ function edgeLength(layout) {
|
|
|
30788
31674
|
}
|
|
30789
31675
|
async function layoutBoxesAndLinesSearch(parsed, collapseInfo, opts) {
|
|
30790
31676
|
const hideDescriptions = opts?.hideDescriptions ?? false;
|
|
31677
|
+
const reserveEdgeLabels = opts?.reserveEdgeLabels ?? false;
|
|
30791
31678
|
const onProgress = opts?.onProgress;
|
|
30792
31679
|
const tick = onProgress ? () => new Promise((r) => setTimeout(r)) : () => void 0;
|
|
30793
31680
|
const collapsedGroupLabels = /* @__PURE__ */ new Set();
|
|
@@ -30969,7 +31856,7 @@ async function layoutBoxesAndLinesSearch(parsed, collapseInfo, opts) {
|
|
|
30969
31856
|
}
|
|
30970
31857
|
];
|
|
30971
31858
|
});
|
|
30972
|
-
const
|
|
31859
|
+
const GROUP_PAD2 = 16;
|
|
30973
31860
|
const nodeByLabel = new Map(nodes.map((n2) => [n2.label, n2]));
|
|
30974
31861
|
const groups = [];
|
|
30975
31862
|
for (const grp of parsed.groups) {
|
|
@@ -30983,10 +31870,10 @@ async function layoutBoxesAndLinesSearch(parsed, collapseInfo, opts) {
|
|
|
30983
31870
|
gy1 = Math.max(gy1, n2.y + n2.height / 2);
|
|
30984
31871
|
}
|
|
30985
31872
|
if (!Number.isFinite(gx0)) continue;
|
|
30986
|
-
const x0 = gx0 -
|
|
30987
|
-
const x1 = gx1 +
|
|
30988
|
-
const y0 = gy0 -
|
|
30989
|
-
const y1 = gy1 +
|
|
31873
|
+
const x0 = gx0 - GROUP_PAD2;
|
|
31874
|
+
const x1 = gx1 + GROUP_PAD2;
|
|
31875
|
+
const y0 = gy0 - GROUP_LABEL_ZONE3;
|
|
31876
|
+
const y1 = gy1 + GROUP_PAD2;
|
|
30990
31877
|
groups.push({
|
|
30991
31878
|
label: grp.label,
|
|
30992
31879
|
lineNumber: grp.lineNumber,
|
|
@@ -31043,7 +31930,7 @@ async function layoutBoxesAndLinesSearch(parsed, collapseInfo, opts) {
|
|
|
31043
31930
|
};
|
|
31044
31931
|
}
|
|
31045
31932
|
function place(cfg) {
|
|
31046
|
-
const r = cfg.seed === void 0 ? null :
|
|
31933
|
+
const r = cfg.seed === void 0 ? null : rng3(cfg.seed + 1);
|
|
31047
31934
|
const ord = (a) => r ? shuffle(a, r) : a.slice();
|
|
31048
31935
|
const g = new dagre4.graphlib.Graph({ compound: true, multigraph: true });
|
|
31049
31936
|
g.setGraph({
|
|
@@ -31080,8 +31967,14 @@ async function layoutBoxesAndLinesSearch(parsed, collapseInfo, opts) {
|
|
|
31080
31967
|
for (const e of ord(parsed.edges)) {
|
|
31081
31968
|
const s = srcRep(e.source);
|
|
31082
31969
|
const t = tgtRep(e.target);
|
|
31083
|
-
if (s !== t && g.hasNode(s) && g.hasNode(t))
|
|
31084
|
-
|
|
31970
|
+
if (s !== t && g.hasNode(s) && g.hasNode(t)) {
|
|
31971
|
+
let edgeLabel = {};
|
|
31972
|
+
if (reserveEdgeLabels && e.label) {
|
|
31973
|
+
const m = measureEdgeLabel(e.label, EDGE_LABEL_FONT_SIZE6);
|
|
31974
|
+
edgeLabel = { width: m.width, height: m.height, labelpos: "c" };
|
|
31975
|
+
}
|
|
31976
|
+
g.setEdge(s, t, edgeLabel, edgeKey(e));
|
|
31977
|
+
}
|
|
31085
31978
|
}
|
|
31086
31979
|
dagre4.layout(g);
|
|
31087
31980
|
const nodes = parsed.nodes.map((n2) => {
|
|
@@ -31230,8 +32123,15 @@ async function layoutBoxesAndLinesSearch(parsed, collapseInfo, opts) {
|
|
|
31230
32123
|
layered = layeredCandidates(parsed, sizes);
|
|
31231
32124
|
} catch {
|
|
31232
32125
|
}
|
|
32126
|
+
if (parsed.groups.length > 0 && collapsedGroupLabels.size === 0) {
|
|
32127
|
+
try {
|
|
32128
|
+
layered = layered.concat(groupedTierCandidates(parsed, sizes));
|
|
32129
|
+
} catch {
|
|
32130
|
+
}
|
|
32131
|
+
}
|
|
31233
32132
|
const fastKey = /* @__PURE__ */ new Map();
|
|
31234
|
-
for (const lay of pool)
|
|
32133
|
+
for (const lay of pool)
|
|
32134
|
+
fastKey.set(lay, objective(lay, countCrossingsFast(lay)));
|
|
31235
32135
|
pool.sort((a, b) => fastKey.get(a) - fastKey.get(b));
|
|
31236
32136
|
const refineK = Math.min(REFINE_K, pool.length);
|
|
31237
32137
|
let best = pool[0];
|
|
@@ -31296,12 +32196,14 @@ async function layoutBoxesAndLinesSearch(parsed, collapseInfo, opts) {
|
|
|
31296
32196
|
}
|
|
31297
32197
|
return best;
|
|
31298
32198
|
}
|
|
31299
|
-
var DEFAULT_LAMBDA, ESCALATE_THRESHOLD, ESCALATE_MAX_N, ESCALATE_SEEDS, ESCALATE_REFINE, splineGen, PATH_TOKEN_RE, FLAT_CACHE,
|
|
32199
|
+
var DEFAULT_LAMBDA, ESCALATE_THRESHOLD, ESCALATE_MAX_N, ESCALATE_SEEDS, ESCALATE_REFINE, splineGen, PATH_TOKEN_RE, FLAT_CACHE, GROUP_LABEL_ZONE3;
|
|
31300
32200
|
var init_layout_search = __esm({
|
|
31301
32201
|
"src/boxes-and-lines/layout-search.ts"() {
|
|
31302
32202
|
"use strict";
|
|
31303
32203
|
init_layout5();
|
|
31304
32204
|
init_layout_layered();
|
|
32205
|
+
init_layout_grouped();
|
|
32206
|
+
init_label_placement();
|
|
31305
32207
|
DEFAULT_LAMBDA = 4;
|
|
31306
32208
|
ESCALATE_THRESHOLD = 4;
|
|
31307
32209
|
ESCALATE_MAX_N = 45;
|
|
@@ -31310,7 +32212,7 @@ var init_layout_search = __esm({
|
|
|
31310
32212
|
splineGen = d3line().x((d) => d.x).y((d) => d.y).curve(curveBasis5);
|
|
31311
32213
|
PATH_TOKEN_RE = /[MLQC]|-?\d*\.?\d+(?:e-?\d+)?/gi;
|
|
31312
32214
|
FLAT_CACHE = /* @__PURE__ */ new WeakMap();
|
|
31313
|
-
|
|
32215
|
+
GROUP_LABEL_ZONE3 = 32;
|
|
31314
32216
|
}
|
|
31315
32217
|
});
|
|
31316
32218
|
|
|
@@ -31360,9 +32262,9 @@ function estimateLabelLines(label, nodeWidth = NODE_WIDTH) {
|
|
|
31360
32262
|
current = word;
|
|
31361
32263
|
}
|
|
31362
32264
|
}
|
|
31363
|
-
if (lines <=
|
|
32265
|
+
if (lines <= MAX_LABEL_LINES2) return Math.min(lines, MAX_LABEL_LINES2);
|
|
31364
32266
|
}
|
|
31365
|
-
return
|
|
32267
|
+
return MAX_LABEL_LINES2;
|
|
31366
32268
|
}
|
|
31367
32269
|
function computeNodeSize(node, reserveValueRow) {
|
|
31368
32270
|
if (!node.description || node.description.length === 0) {
|
|
@@ -31370,7 +32272,7 @@ function computeNodeSize(node, reserveValueRow) {
|
|
|
31370
32272
|
}
|
|
31371
32273
|
const w = DESC_NODE_WIDTH;
|
|
31372
32274
|
const labelLines = estimateLabelLines(node.label, w);
|
|
31373
|
-
const labelHeight = labelLines * 13 *
|
|
32275
|
+
const labelHeight = labelLines * 13 * LABEL_LINE_HEIGHT2 + LABEL_PAD;
|
|
31374
32276
|
const maxTextWidth = w - 24;
|
|
31375
32277
|
let totalRenderedLines = 0;
|
|
31376
32278
|
for (const line11 of node.description) {
|
|
@@ -31394,7 +32296,7 @@ function computeNodeSize(node, reserveValueRow) {
|
|
|
31394
32296
|
}
|
|
31395
32297
|
async function layoutBoxesAndLines(parsed, collapseInfo, layoutOptions) {
|
|
31396
32298
|
const { layoutBoxesAndLinesSearch: layoutBoxesAndLinesSearch2 } = await Promise.resolve().then(() => (init_layout_search(), layout_search_exports));
|
|
31397
|
-
const
|
|
32299
|
+
const searchOpts = {
|
|
31398
32300
|
...layoutOptions?.hideDescriptions !== void 0 && {
|
|
31399
32301
|
hideDescriptions: layoutOptions.hideDescriptions
|
|
31400
32302
|
},
|
|
@@ -31404,12 +32306,23 @@ async function layoutBoxesAndLines(parsed, collapseInfo, layoutOptions) {
|
|
|
31404
32306
|
...layoutOptions?.onProgress !== void 0 && {
|
|
31405
32307
|
onProgress: layoutOptions.onProgress
|
|
31406
32308
|
}
|
|
31407
|
-
}
|
|
31408
|
-
|
|
31409
|
-
applyParallelEdgeOffsets(searched),
|
|
32309
|
+
};
|
|
32310
|
+
const searched = await layoutBoxesAndLinesSearch2(
|
|
31410
32311
|
parsed,
|
|
31411
|
-
|
|
31412
|
-
|
|
32312
|
+
collapseInfo,
|
|
32313
|
+
searchOpts
|
|
32314
|
+
);
|
|
32315
|
+
let placed = placeEdgeLabels(applyParallelEdgeOffsets(searched));
|
|
32316
|
+
if (placed.unresolved.length > 0) {
|
|
32317
|
+
const relaid = await layoutBoxesAndLinesSearch2(parsed, collapseInfo, {
|
|
32318
|
+
...searchOpts,
|
|
32319
|
+
reserveEdgeLabels: true
|
|
32320
|
+
});
|
|
32321
|
+
const relaidPlaced = placeEdgeLabels(applyParallelEdgeOffsets(relaid));
|
|
32322
|
+
if (relaidPlaced.unresolved.length < placed.unresolved.length)
|
|
32323
|
+
placed = relaidPlaced;
|
|
32324
|
+
}
|
|
32325
|
+
return attachNotes(placed.layout, parsed, layoutOptions?.collapsedNotes);
|
|
31413
32326
|
}
|
|
31414
32327
|
function attachNotes(layout, parsed, collapsedNotes) {
|
|
31415
32328
|
const notesSuppressed = parsed.options?.["no-notes"] === "on";
|
|
@@ -31477,6 +32390,7 @@ function attachNotes(layout, parsed, collapsedNotes) {
|
|
|
31477
32390
|
points: e.points.map((pt) => ({ x: pt.x + shiftX, y: pt.y + shiftY })),
|
|
31478
32391
|
...e.labelX !== void 0 && { labelX: e.labelX + shiftX },
|
|
31479
32392
|
...e.labelY !== void 0 && { labelY: e.labelY + shiftY }
|
|
32393
|
+
// labelWidth/labelHeight/labelLines are shift-invariant — carried via spread.
|
|
31480
32394
|
})) : layout.edges;
|
|
31481
32395
|
const finalGroups = shifted ? layout.groups.map((grp) => ({
|
|
31482
32396
|
...grp,
|
|
@@ -31487,8 +32401,8 @@ function attachNotes(layout, parsed, collapsedNotes) {
|
|
|
31487
32401
|
nodes: finalNodes,
|
|
31488
32402
|
edges: finalEdges,
|
|
31489
32403
|
groups: finalGroups,
|
|
31490
|
-
width: bbMaxX + shiftX +
|
|
31491
|
-
height: bbMaxY + shiftY +
|
|
32404
|
+
width: bbMaxX + shiftX + MARGIN5,
|
|
32405
|
+
height: bbMaxY + shiftY + MARGIN5
|
|
31492
32406
|
};
|
|
31493
32407
|
}
|
|
31494
32408
|
function applyParallelEdgeOffsets(layout) {
|
|
@@ -31521,13 +32435,14 @@ function applyParallelEdgeOffsets(layout) {
|
|
|
31521
32435
|
}))
|
|
31522
32436
|
};
|
|
31523
32437
|
}
|
|
31524
|
-
var
|
|
32438
|
+
var MARGIN5, MAX_PARALLEL_EDGES, PARALLEL_SPACING, PHI, NODE_HEIGHT, NODE_WIDTH, DESC_NODE_WIDTH, DESC_FONT_SIZE2, DESC_LINE_HEIGHT2, DESC_PADDING, SEPARATOR_GAP4, MAX_DESC_LINES2, MAX_LABEL_LINES2, LABEL_LINE_HEIGHT2, LABEL_PAD, VALUE_ROW_FONT, VALUE_ROW_H;
|
|
31525
32439
|
var init_layout5 = __esm({
|
|
31526
32440
|
"src/boxes-and-lines/layout.ts"() {
|
|
31527
32441
|
"use strict";
|
|
31528
32442
|
init_text_measure();
|
|
32443
|
+
init_label_placement();
|
|
31529
32444
|
init_notes();
|
|
31530
|
-
|
|
32445
|
+
MARGIN5 = 40;
|
|
31531
32446
|
MAX_PARALLEL_EDGES = 5;
|
|
31532
32447
|
PARALLEL_SPACING = 22;
|
|
31533
32448
|
PHI = 1.618;
|
|
@@ -31539,8 +32454,8 @@ var init_layout5 = __esm({
|
|
|
31539
32454
|
DESC_PADDING = 8;
|
|
31540
32455
|
SEPARATOR_GAP4 = 4;
|
|
31541
32456
|
MAX_DESC_LINES2 = 6;
|
|
31542
|
-
|
|
31543
|
-
|
|
32457
|
+
MAX_LABEL_LINES2 = 3;
|
|
32458
|
+
LABEL_LINE_HEIGHT2 = 1.3;
|
|
31544
32459
|
LABEL_PAD = 12;
|
|
31545
32460
|
VALUE_ROW_FONT = 11;
|
|
31546
32461
|
VALUE_ROW_H = SEPARATOR_GAP4 + VALUE_ROW_FONT * DESC_LINE_HEIGHT2 + DESC_PADDING;
|
|
@@ -31559,7 +32474,7 @@ function tokenize(text) {
|
|
|
31559
32474
|
return tokens;
|
|
31560
32475
|
}
|
|
31561
32476
|
function tryWrap(tokens, maxWidth, fontSize, maxLines) {
|
|
31562
|
-
const availWidth = maxWidth -
|
|
32477
|
+
const availWidth = maxWidth - H_PAD2;
|
|
31563
32478
|
const lines = [];
|
|
31564
32479
|
let currentLine = "";
|
|
31565
32480
|
for (const token of tokens) {
|
|
@@ -31584,7 +32499,7 @@ function tryWrap(tokens, maxWidth, fontSize, maxLines) {
|
|
|
31584
32499
|
return lines;
|
|
31585
32500
|
}
|
|
31586
32501
|
function truncateLastLine(lines, maxWidth, fontSize) {
|
|
31587
|
-
const availWidth = maxWidth -
|
|
32502
|
+
const availWidth = maxWidth - H_PAD2;
|
|
31588
32503
|
const result = [...lines];
|
|
31589
32504
|
const last = result[result.length - 1];
|
|
31590
32505
|
if (measureText(last, fontSize) > availWidth) {
|
|
@@ -31592,7 +32507,7 @@ function truncateLastLine(lines, maxWidth, fontSize) {
|
|
|
31592
32507
|
}
|
|
31593
32508
|
return result;
|
|
31594
32509
|
}
|
|
31595
|
-
function wrapText(text, maxWidth, baseFontSize, minFontSize, maxLines =
|
|
32510
|
+
function wrapText(text, maxWidth, baseFontSize, minFontSize, maxLines = MAX_LABEL_LINES3) {
|
|
31596
32511
|
if (!text) return { lines: [""], fontSize: baseFontSize };
|
|
31597
32512
|
const tokens = tokenize(text);
|
|
31598
32513
|
for (let fs = baseFontSize; fs >= minFontSize; fs--) {
|
|
@@ -31607,7 +32522,7 @@ function wrapText(text, maxWidth, baseFontSize, minFontSize, maxLines = MAX_LABE
|
|
|
31607
32522
|
if (allLines.length > maxLines) {
|
|
31608
32523
|
const last = truncated[truncated.length - 1];
|
|
31609
32524
|
if (!last.endsWith("\u2026")) {
|
|
31610
|
-
const availWidth = maxWidth -
|
|
32525
|
+
const availWidth = maxWidth - H_PAD2;
|
|
31611
32526
|
if (measureText(last + "\u2026", minFontSize) > availWidth) {
|
|
31612
32527
|
truncated[truncated.length - 1] = truncateText(
|
|
31613
32528
|
last,
|
|
@@ -31634,7 +32549,7 @@ function computeNodeText(label, description, depth, nodeWidth, hideDescriptions)
|
|
|
31634
32549
|
nodeWidth,
|
|
31635
32550
|
baseFontSize,
|
|
31636
32551
|
MIN_FONT_SIZE,
|
|
31637
|
-
|
|
32552
|
+
MAX_LABEL_LINES3
|
|
31638
32553
|
);
|
|
31639
32554
|
const descLines = [];
|
|
31640
32555
|
let descFontSize = DESC_FONT_SIZE3;
|
|
@@ -31662,14 +32577,14 @@ function computeNodeText(label, description, depth, nodeWidth, hideDescriptions)
|
|
|
31662
32577
|
descFontSize
|
|
31663
32578
|
};
|
|
31664
32579
|
}
|
|
31665
|
-
var
|
|
32580
|
+
var H_PAD2, MAX_LABEL_LINES3, MAX_DESC_LINES3, ROOT_FONT_SIZE, MIN_FONT_SIZE, FONT_STEP, DESC_FONT_SIZE3;
|
|
31666
32581
|
var init_text_wrap = __esm({
|
|
31667
32582
|
"src/mindmap/text-wrap.ts"() {
|
|
31668
32583
|
"use strict";
|
|
31669
32584
|
init_description_helpers();
|
|
31670
32585
|
init_text_measure();
|
|
31671
|
-
|
|
31672
|
-
|
|
32586
|
+
H_PAD2 = 16;
|
|
32587
|
+
MAX_LABEL_LINES3 = 3;
|
|
31673
32588
|
MAX_DESC_LINES3 = 2;
|
|
31674
32589
|
ROOT_FONT_SIZE = 17;
|
|
31675
32590
|
MIN_FONT_SIZE = 9;
|
|
@@ -31698,7 +32613,7 @@ function layoutMindmap(parsed, _palette, options) {
|
|
|
31698
32613
|
leafWidth: ctx.structural(LEAF_WIDTH),
|
|
31699
32614
|
hGap: ctx.aesthetic(H_GAP2),
|
|
31700
32615
|
vGap: ctx.aesthetic(V_GAP2),
|
|
31701
|
-
margin: ctx.aesthetic(
|
|
32616
|
+
margin: ctx.aesthetic(MARGIN6),
|
|
31702
32617
|
multiRootGap: ctx.aesthetic(MULTI_ROOT_GAP)
|
|
31703
32618
|
};
|
|
31704
32619
|
populateDepthCache(roots);
|
|
@@ -32056,7 +32971,7 @@ function nodeHeightS(node, hideDescriptions, sc) {
|
|
|
32056
32971
|
hideDescriptions
|
|
32057
32972
|
);
|
|
32058
32973
|
const labelLineCount = text.labelLines.length;
|
|
32059
|
-
const labelH = labelLineCount <= 1 ? SINGLE_LABEL_HEIGHT :
|
|
32974
|
+
const labelH = labelLineCount <= 1 ? SINGLE_LABEL_HEIGHT : LABEL_LINE_HEIGHT3 * labelLineCount;
|
|
32060
32975
|
let h = labelH + NODE_V_PAD;
|
|
32061
32976
|
if (text.descLines.length > 0) {
|
|
32062
32977
|
h += DESC_LINE_HEIGHT3 * text.descLines.length + 4;
|
|
@@ -32076,7 +32991,7 @@ function populateDepthCache(roots) {
|
|
|
32076
32991
|
};
|
|
32077
32992
|
walk(roots, 0);
|
|
32078
32993
|
}
|
|
32079
|
-
var ROOT_WIDTH, DEPTH1_WIDTH, LEAF_WIDTH, SINGLE_LABEL_HEIGHT,
|
|
32994
|
+
var ROOT_WIDTH, DEPTH1_WIDTH, LEAF_WIDTH, SINGLE_LABEL_HEIGHT, LABEL_LINE_HEIGHT3, DESC_LINE_HEIGHT3, NODE_V_PAD, H_GAP2, V_GAP2, MARGIN6, MULTI_ROOT_GAP, nodeDepthCache;
|
|
32080
32995
|
var init_layout6 = __esm({
|
|
32081
32996
|
"src/mindmap/layout.ts"() {
|
|
32082
32997
|
"use strict";
|
|
@@ -32087,12 +33002,12 @@ var init_layout6 = __esm({
|
|
|
32087
33002
|
DEPTH1_WIDTH = 150;
|
|
32088
33003
|
LEAF_WIDTH = 120;
|
|
32089
33004
|
SINGLE_LABEL_HEIGHT = 28;
|
|
32090
|
-
|
|
33005
|
+
LABEL_LINE_HEIGHT3 = 18;
|
|
32091
33006
|
DESC_LINE_HEIGHT3 = 14;
|
|
32092
33007
|
NODE_V_PAD = 10;
|
|
32093
33008
|
H_GAP2 = 40;
|
|
32094
33009
|
V_GAP2 = 12;
|
|
32095
|
-
|
|
33010
|
+
MARGIN6 = 40;
|
|
32096
33011
|
MULTI_ROOT_GAP = 60;
|
|
32097
33012
|
nodeDepthCache = /* @__PURE__ */ new Map();
|
|
32098
33013
|
}
|
|
@@ -32350,7 +33265,7 @@ function renderMindmap(container, parsed, layout, palette, isDark, onClickItem,
|
|
|
32350
33265
|
);
|
|
32351
33266
|
const nodeG = mainG.append("g").attr("class", "mindmap-node").attr("data-line-number", node.lineNumber);
|
|
32352
33267
|
if (activeTagGroup) {
|
|
32353
|
-
const tagKey = activeTagGroup
|
|
33268
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
32354
33269
|
const metaValue = node.metadata[tagKey];
|
|
32355
33270
|
if (metaValue) {
|
|
32356
33271
|
nodeG.attr(`data-tag-${tagKey}`, metaValue.toLowerCase());
|
|
@@ -32379,18 +33294,18 @@ function renderMindmap(container, parsed, layout, palette, isDark, onClickItem,
|
|
|
32379
33294
|
descFontSize
|
|
32380
33295
|
} = textLayout;
|
|
32381
33296
|
const labelLineCount = labelLines.length;
|
|
32382
|
-
const labelZoneH = labelLineCount <= 1 ? SINGLE_LABEL_HEIGHT2 :
|
|
33297
|
+
const labelZoneH = labelLineCount <= 1 ? SINGLE_LABEL_HEIGHT2 : LABEL_LINE_HEIGHT4 * labelLineCount;
|
|
32383
33298
|
const labelZoneHeight = showDesc ? labelZoneH : node.height;
|
|
32384
33299
|
const centerX = node.x + node.width / 2;
|
|
32385
33300
|
if (labelLineCount <= 1) {
|
|
32386
33301
|
const labelY = node.y + labelZoneHeight / 2 + fontSize * 0.35;
|
|
32387
33302
|
nodeG.append("text").attr("x", centerX).attr("y", labelY).attr("text-anchor", "middle").attr("font-size", fontSize).attr("font-weight", isRoot ? "bold" : "normal").attr("fill", onFillText).text(labelLines[0]);
|
|
32388
33303
|
} else {
|
|
32389
|
-
const blockH =
|
|
33304
|
+
const blockH = LABEL_LINE_HEIGHT4 * (labelLineCount - 1);
|
|
32390
33305
|
const firstBaselineY = node.y + labelZoneHeight / 2 - blockH / 2 + fontSize * 0.35;
|
|
32391
33306
|
const textEl = nodeG.append("text").attr("x", centerX).attr("text-anchor", "middle").attr("font-size", fontSize).attr("font-weight", isRoot ? "bold" : "normal").attr("fill", onFillText);
|
|
32392
33307
|
for (let i = 0; i < labelLines.length; i++) {
|
|
32393
|
-
textEl.append("tspan").attr("x", centerX).attr("y", firstBaselineY + i *
|
|
33308
|
+
textEl.append("tspan").attr("x", centerX).attr("y", firstBaselineY + i * LABEL_LINE_HEIGHT4).text(labelLines[i]);
|
|
32394
33309
|
}
|
|
32395
33310
|
}
|
|
32396
33311
|
if (labelLines.length > 1 || labelLines[0] !== node.label) {
|
|
@@ -32465,10 +33380,11 @@ function renderMindmapForExport(content, theme, palette) {
|
|
|
32465
33380
|
return extractExportSvg(container, theme);
|
|
32466
33381
|
});
|
|
32467
33382
|
}
|
|
32468
|
-
var DIAGRAM_PADDING7, TITLE_HEIGHT4, SINGLE_LABEL_HEIGHT2,
|
|
33383
|
+
var DIAGRAM_PADDING7, TITLE_HEIGHT4, SINGLE_LABEL_HEIGHT2, LABEL_LINE_HEIGHT4, DESC_LINE_HEIGHT4, NODE_RADIUS, ROOT_STROKE_WIDTH, DEPTH_COLOR_KEYS;
|
|
32469
33384
|
var init_renderer7 = __esm({
|
|
32470
33385
|
"src/mindmap/renderer.ts"() {
|
|
32471
33386
|
"use strict";
|
|
33387
|
+
init_tag_groups();
|
|
32472
33388
|
init_fonts();
|
|
32473
33389
|
init_export_container();
|
|
32474
33390
|
init_color_utils();
|
|
@@ -32486,7 +33402,7 @@ var init_renderer7 = __esm({
|
|
|
32486
33402
|
DIAGRAM_PADDING7 = 20;
|
|
32487
33403
|
TITLE_HEIGHT4 = 30;
|
|
32488
33404
|
SINGLE_LABEL_HEIGHT2 = 28;
|
|
32489
|
-
|
|
33405
|
+
LABEL_LINE_HEIGHT4 = 18;
|
|
32490
33406
|
DESC_LINE_HEIGHT4 = 14;
|
|
32491
33407
|
NODE_RADIUS = 6;
|
|
32492
33408
|
ROOT_STROKE_WIDTH = 2.5;
|
|
@@ -33679,7 +34595,7 @@ function resolveNodeColor4(el, tagGroups, activeGroupName, ancestors) {
|
|
|
33679
34595
|
(g) => g.name.toLowerCase() === activeGroupName.toLowerCase()
|
|
33680
34596
|
);
|
|
33681
34597
|
if (!group) return void 0;
|
|
33682
|
-
const key = group.name
|
|
34598
|
+
const key = tagAttrKey(group.name);
|
|
33683
34599
|
let metaValue = el.metadata[key];
|
|
33684
34600
|
if (!metaValue && ancestors) {
|
|
33685
34601
|
for (const ancestor of ancestors) {
|
|
@@ -33881,8 +34797,8 @@ function layoutC4Context(parsed, activeTagGroup) {
|
|
|
33881
34797
|
}
|
|
33882
34798
|
}
|
|
33883
34799
|
if (nodes.length > 0) {
|
|
33884
|
-
const shiftX =
|
|
33885
|
-
const shiftY =
|
|
34800
|
+
const shiftX = MARGIN7 - minX;
|
|
34801
|
+
const shiftY = MARGIN7 - minY;
|
|
33886
34802
|
for (const node of nodes) {
|
|
33887
34803
|
node.x += shiftX;
|
|
33888
34804
|
node.y += shiftY;
|
|
@@ -33894,12 +34810,12 @@ function layoutC4Context(parsed, activeTagGroup) {
|
|
|
33894
34810
|
}
|
|
33895
34811
|
}
|
|
33896
34812
|
}
|
|
33897
|
-
let totalWidth = nodes.length > 0 ? maxX - minX +
|
|
33898
|
-
let totalHeight = nodes.length > 0 ? maxY - minY +
|
|
34813
|
+
let totalWidth = nodes.length > 0 ? maxX - minX + MARGIN7 * 2 : 0;
|
|
34814
|
+
let totalHeight = nodes.length > 0 ? maxY - minY + MARGIN7 * 2 : 0;
|
|
33899
34815
|
const legendGroups = computeLegendGroups3(parsed.tagGroups);
|
|
33900
34816
|
if (legendGroups.length > 0) {
|
|
33901
|
-
const legendY = totalHeight +
|
|
33902
|
-
let legendX =
|
|
34817
|
+
const legendY = totalHeight + MARGIN7;
|
|
34818
|
+
let legendX = MARGIN7;
|
|
33903
34819
|
for (const lg of legendGroups) {
|
|
33904
34820
|
lg.x = legendX;
|
|
33905
34821
|
lg.y = legendY;
|
|
@@ -34231,8 +35147,8 @@ function layoutC4Containers(parsed, systemName, activeTagGroup) {
|
|
|
34231
35147
|
if (pt.y > maxY) maxY = pt.y;
|
|
34232
35148
|
}
|
|
34233
35149
|
}
|
|
34234
|
-
const shiftX =
|
|
34235
|
-
const shiftY =
|
|
35150
|
+
const shiftX = MARGIN7 - minX;
|
|
35151
|
+
const shiftY = MARGIN7 - minY;
|
|
34236
35152
|
for (const node of nodes) {
|
|
34237
35153
|
node.x += shiftX;
|
|
34238
35154
|
node.y += shiftY;
|
|
@@ -34249,12 +35165,12 @@ function layoutC4Containers(parsed, systemName, activeTagGroup) {
|
|
|
34249
35165
|
pt.y += shiftY;
|
|
34250
35166
|
}
|
|
34251
35167
|
}
|
|
34252
|
-
let totalWidth = maxX - minX +
|
|
34253
|
-
let totalHeight = maxY - minY +
|
|
35168
|
+
let totalWidth = maxX - minX + MARGIN7 * 2;
|
|
35169
|
+
let totalHeight = maxY - minY + MARGIN7 * 2;
|
|
34254
35170
|
const legendGroups = computeLegendGroups3(parsed.tagGroups);
|
|
34255
35171
|
if (legendGroups.length > 0) {
|
|
34256
|
-
const legendY = totalHeight +
|
|
34257
|
-
let legendX =
|
|
35172
|
+
const legendY = totalHeight + MARGIN7;
|
|
35173
|
+
let legendX = MARGIN7;
|
|
34258
35174
|
for (const lg of legendGroups) {
|
|
34259
35175
|
lg.x = legendX;
|
|
34260
35176
|
lg.y = legendY;
|
|
@@ -34646,8 +35562,8 @@ function layoutC4Components(parsed, systemName, containerName, activeTagGroup) {
|
|
|
34646
35562
|
if (pt.y > maxY) maxY = pt.y;
|
|
34647
35563
|
}
|
|
34648
35564
|
}
|
|
34649
|
-
const shiftX =
|
|
34650
|
-
const shiftY =
|
|
35565
|
+
const shiftX = MARGIN7 - minX;
|
|
35566
|
+
const shiftY = MARGIN7 - minY;
|
|
34651
35567
|
for (const node of nodes) {
|
|
34652
35568
|
node.x += shiftX;
|
|
34653
35569
|
node.y += shiftY;
|
|
@@ -34664,12 +35580,12 @@ function layoutC4Components(parsed, systemName, containerName, activeTagGroup) {
|
|
|
34664
35580
|
pt.y += shiftY;
|
|
34665
35581
|
}
|
|
34666
35582
|
}
|
|
34667
|
-
let totalWidth = maxX - minX +
|
|
34668
|
-
let totalHeight = maxY - minY +
|
|
35583
|
+
let totalWidth = maxX - minX + MARGIN7 * 2;
|
|
35584
|
+
let totalHeight = maxY - minY + MARGIN7 * 2;
|
|
34669
35585
|
const legendGroups = computeLegendGroups3(parsed.tagGroups);
|
|
34670
35586
|
if (legendGroups.length > 0) {
|
|
34671
|
-
const legendY = totalHeight +
|
|
34672
|
-
let legendX =
|
|
35587
|
+
const legendY = totalHeight + MARGIN7;
|
|
35588
|
+
let legendX = MARGIN7;
|
|
34673
35589
|
for (const lg of legendGroups) {
|
|
34674
35590
|
lg.x = legendX;
|
|
34675
35591
|
lg.y = legendY;
|
|
@@ -34957,8 +35873,8 @@ function layoutC4Deployment(parsed, activeTagGroup) {
|
|
|
34957
35873
|
if (pt.y > maxY) maxY = pt.y;
|
|
34958
35874
|
}
|
|
34959
35875
|
}
|
|
34960
|
-
const shiftX =
|
|
34961
|
-
const shiftY =
|
|
35876
|
+
const shiftX = MARGIN7 - minX;
|
|
35877
|
+
const shiftY = MARGIN7 - minY;
|
|
34962
35878
|
for (const node of nodes) {
|
|
34963
35879
|
node.x += shiftX;
|
|
34964
35880
|
node.y += shiftY;
|
|
@@ -34973,12 +35889,12 @@ function layoutC4Deployment(parsed, activeTagGroup) {
|
|
|
34973
35889
|
pt.y += shiftY;
|
|
34974
35890
|
}
|
|
34975
35891
|
}
|
|
34976
|
-
let totalWidth = maxX - minX +
|
|
34977
|
-
let totalHeight = maxY - minY +
|
|
35892
|
+
let totalWidth = maxX - minX + MARGIN7 * 2;
|
|
35893
|
+
let totalHeight = maxY - minY + MARGIN7 * 2;
|
|
34978
35894
|
const legendGroups = computeLegendGroups3(parsed.tagGroups);
|
|
34979
35895
|
if (legendGroups.length > 0) {
|
|
34980
|
-
const legendY = totalHeight +
|
|
34981
|
-
let legendX =
|
|
35896
|
+
const legendY = totalHeight + MARGIN7;
|
|
35897
|
+
let legendX = MARGIN7;
|
|
34982
35898
|
for (const lg of legendGroups) {
|
|
34983
35899
|
lg.x = legendX;
|
|
34984
35900
|
lg.y = legendY;
|
|
@@ -34998,10 +35914,11 @@ function layoutC4Deployment(parsed, activeTagGroup) {
|
|
|
34998
35914
|
height: totalHeight
|
|
34999
35915
|
};
|
|
35000
35916
|
}
|
|
35001
|
-
var gNode, gEdge, MIN_NODE_WIDTH, MAX_NODE_WIDTH, TYPE_LABEL_HEIGHT, DIVIDER_GAP, NAME_HEIGHT, NAME_FONT_SIZE, DESC_LINE_HEIGHT5, DESC_FONT_SIZE4, CARD_V_PAD3, CARD_H_PAD3, META_LINE_HEIGHT4, META_FONT_SIZE4,
|
|
35917
|
+
var gNode, gEdge, MIN_NODE_WIDTH, MAX_NODE_WIDTH, TYPE_LABEL_HEIGHT, DIVIDER_GAP, NAME_HEIGHT, NAME_FONT_SIZE, DESC_LINE_HEIGHT5, DESC_FONT_SIZE4, CARD_V_PAD3, CARD_H_PAD3, META_LINE_HEIGHT4, META_FONT_SIZE4, MARGIN7, BOUNDARY_PAD, GROUP_BOUNDARY_PAD, EDGE_NODE_COLLISION_WEIGHT, META_EXCLUDE_KEYS;
|
|
35002
35918
|
var init_layout8 = __esm({
|
|
35003
35919
|
"src/c4/layout.ts"() {
|
|
35004
35920
|
"use strict";
|
|
35921
|
+
init_tag_groups();
|
|
35005
35922
|
init_legend_constants();
|
|
35006
35923
|
init_text_measure();
|
|
35007
35924
|
gNode = (g, name) => g.node(name);
|
|
@@ -35018,7 +35935,7 @@ var init_layout8 = __esm({
|
|
|
35018
35935
|
CARD_H_PAD3 = 20;
|
|
35019
35936
|
META_LINE_HEIGHT4 = 16;
|
|
35020
35937
|
META_FONT_SIZE4 = 11;
|
|
35021
|
-
|
|
35938
|
+
MARGIN7 = 40;
|
|
35022
35939
|
BOUNDARY_PAD = 40;
|
|
35023
35940
|
GROUP_BOUNDARY_PAD = 24;
|
|
35024
35941
|
EDGE_NODE_COLLISION_WEIGHT = 5e3;
|
|
@@ -35154,7 +36071,7 @@ function renderC4Context(container, parsed, layout, palette, isDark, onClickItem
|
|
|
35154
36071
|
const labelText = edge.label ?? "";
|
|
35155
36072
|
const techText = edge.technology ? `[${edge.technology}]` : "";
|
|
35156
36073
|
const textW = Math.max(
|
|
35157
|
-
measureText(labelText,
|
|
36074
|
+
measureText(labelText, EDGE_LABEL_FONT_SIZE7),
|
|
35158
36075
|
measureText(techText, TECH_FONT_SIZE)
|
|
35159
36076
|
);
|
|
35160
36077
|
const bgW = textW + 12;
|
|
@@ -35165,7 +36082,7 @@ function renderC4Context(container, parsed, layout, palette, isDark, onClickItem
|
|
|
35165
36082
|
textY = midPt.y - 4;
|
|
35166
36083
|
}
|
|
35167
36084
|
if (labelText) {
|
|
35168
|
-
edgeG.append("text").attr("x", midPt.x).attr("y", textY + 4).attr("text-anchor", "middle").attr("fill", edgeColor3).attr("font-size",
|
|
36085
|
+
edgeG.append("text").attr("x", midPt.x).attr("y", textY + 4).attr("text-anchor", "middle").attr("fill", edgeColor3).attr("font-size", EDGE_LABEL_FONT_SIZE7).attr("class", "c4-edge-label").text(labelText);
|
|
35169
36086
|
}
|
|
35170
36087
|
if (techText) {
|
|
35171
36088
|
edgeG.append("text").attr("x", midPt.x).attr("y", labelText ? textY + 18 : textY + 4).attr("text-anchor", "middle").attr("fill", edgeColor3).attr("font-size", TECH_FONT_SIZE).attr("font-style", "italic").attr("class", "c4-edge-tech").text(techText);
|
|
@@ -35175,7 +36092,7 @@ function renderC4Context(container, parsed, layout, palette, isDark, onClickItem
|
|
|
35175
36092
|
for (const node of layout.nodes) {
|
|
35176
36093
|
const nodeG = contentG.append("g").attr("transform", `translate(${node.x}, ${node.y})`).attr("class", "c4-card").attr("data-line-number", String(node.lineNumber)).attr("data-node-id", node.id);
|
|
35177
36094
|
if (activeTagGroup) {
|
|
35178
|
-
const tagKey = activeTagGroup
|
|
36095
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
35179
36096
|
const tagValue = node.metadata[tagKey];
|
|
35180
36097
|
if (tagValue) {
|
|
35181
36098
|
nodeG.attr(`data-tag-${tagKey}`, tagValue.toLowerCase());
|
|
@@ -35349,7 +36266,7 @@ function renderEdges(contentG, edges, palette, onClickItem, obstacleRects) {
|
|
|
35349
36266
|
const labelText = edge.label ?? "";
|
|
35350
36267
|
const techText = edge.technology ? `[${edge.technology}]` : "";
|
|
35351
36268
|
const textW = Math.max(
|
|
35352
|
-
measureText(labelText,
|
|
36269
|
+
measureText(labelText, EDGE_LABEL_FONT_SIZE7),
|
|
35353
36270
|
measureText(techText, TECH_FONT_SIZE)
|
|
35354
36271
|
);
|
|
35355
36272
|
const bgW = textW + 12;
|
|
@@ -35367,7 +36284,7 @@ function renderEdges(contentG, edges, palette, onClickItem, obstacleRects) {
|
|
|
35367
36284
|
});
|
|
35368
36285
|
}
|
|
35369
36286
|
}
|
|
35370
|
-
|
|
36287
|
+
placeEdgeLabels2(pendingLabels, edges, obstacleRects);
|
|
35371
36288
|
for (const lbl of pendingLabels) {
|
|
35372
36289
|
lbl.edgeG.append("rect").attr("x", lbl.x - lbl.bgW / 2).attr("y", lbl.y - lbl.bgH / 2).attr("width", lbl.bgW).attr("height", lbl.bgH).attr("rx", 3).attr("fill", palette.bg).attr("opacity", 0.9).attr("class", "c4-edge-label-bg");
|
|
35373
36290
|
let textY = lbl.y;
|
|
@@ -35375,7 +36292,7 @@ function renderEdges(contentG, edges, palette, onClickItem, obstacleRects) {
|
|
|
35375
36292
|
textY = lbl.y - 4;
|
|
35376
36293
|
}
|
|
35377
36294
|
if (lbl.labelText) {
|
|
35378
|
-
lbl.edgeG.append("text").attr("x", lbl.x).attr("y", textY + 4).attr("text-anchor", "middle").attr("fill", lbl.edgeColor).attr("font-size",
|
|
36295
|
+
lbl.edgeG.append("text").attr("x", lbl.x).attr("y", textY + 4).attr("text-anchor", "middle").attr("fill", lbl.edgeColor).attr("font-size", EDGE_LABEL_FONT_SIZE7).attr("class", "c4-edge-label").text(lbl.labelText);
|
|
35379
36296
|
}
|
|
35380
36297
|
if (lbl.techText) {
|
|
35381
36298
|
lbl.edgeG.append("text").attr("x", lbl.x).attr("y", lbl.labelText ? textY + 18 : textY + 4).attr("text-anchor", "middle").attr("fill", lbl.edgeColor).attr("font-size", TECH_FONT_SIZE).attr("font-style", "italic").attr("class", "c4-edge-tech").text(lbl.techText);
|
|
@@ -35456,7 +36373,7 @@ function tangentAt(points, t) {
|
|
|
35456
36373
|
}
|
|
35457
36374
|
return { x: 0, y: 1 };
|
|
35458
36375
|
}
|
|
35459
|
-
function
|
|
36376
|
+
function placeEdgeLabels2(labels, edges, obstacleRects) {
|
|
35460
36377
|
if (labels.length === 0) return;
|
|
35461
36378
|
const allPaths = edges.map((e) => e.points);
|
|
35462
36379
|
const placedRects = [];
|
|
@@ -35734,7 +36651,7 @@ function renderC4Containers(container, parsed, layout, palette, isDark, onClickI
|
|
|
35734
36651
|
for (const node of layout.nodes) {
|
|
35735
36652
|
const nodeG = contentG.append("g").attr("transform", `translate(${node.x}, ${node.y})`).attr("class", "c4-card").attr("data-line-number", String(node.lineNumber)).attr("data-node-id", node.id);
|
|
35736
36653
|
if (activeTagGroup) {
|
|
35737
|
-
const tagKey = activeTagGroup
|
|
36654
|
+
const tagKey = tagAttrKey(activeTagGroup);
|
|
35738
36655
|
const tagValue = node.metadata[tagKey];
|
|
35739
36656
|
if (tagValue) {
|
|
35740
36657
|
nodeG.attr(`data-tag-${tagKey}`, tagValue.toLowerCase());
|
|
@@ -35994,10 +36911,11 @@ function renderC4DeploymentForExport(content, theme, palette) {
|
|
|
35994
36911
|
document.body.removeChild(el);
|
|
35995
36912
|
}
|
|
35996
36913
|
}
|
|
35997
|
-
var DIAGRAM_PADDING8, MAX_SCALE5, TITLE_HEIGHT6, TYPE_FONT_SIZE, NAME_FONT_SIZE2, DESC_FONT_SIZE5, DESC_LINE_HEIGHT6,
|
|
36914
|
+
var DIAGRAM_PADDING8, MAX_SCALE5, TITLE_HEIGHT6, TYPE_FONT_SIZE, NAME_FONT_SIZE2, DESC_FONT_SIZE5, DESC_LINE_HEIGHT6, EDGE_LABEL_FONT_SIZE7, TECH_FONT_SIZE, CARD_H_PAD4, CARD_V_PAD4, TYPE_LABEL_HEIGHT2, DIVIDER_GAP2, NAME_HEIGHT2, BOUNDARY_LABEL_FONT_SIZE, BOUNDARY_STROKE_WIDTH, BOUNDARY_RADIUS, DRILL_BAR_HEIGHT, CYLINDER_RY, PERSON_HEAD_R, PERSON_ARM_SPAN, PERSON_LEG_SPAN, PERSON_ICON_W, PERSON_SW, lineGenerator4;
|
|
35998
36915
|
var init_renderer9 = __esm({
|
|
35999
36916
|
"src/c4/renderer.ts"() {
|
|
36000
36917
|
"use strict";
|
|
36918
|
+
init_tag_groups();
|
|
36001
36919
|
init_fonts();
|
|
36002
36920
|
init_color_utils();
|
|
36003
36921
|
init_inline_markdown();
|
|
@@ -36016,7 +36934,7 @@ var init_renderer9 = __esm({
|
|
|
36016
36934
|
NAME_FONT_SIZE2 = 14;
|
|
36017
36935
|
DESC_FONT_SIZE5 = 11;
|
|
36018
36936
|
DESC_LINE_HEIGHT6 = 16;
|
|
36019
|
-
|
|
36937
|
+
EDGE_LABEL_FONT_SIZE7 = 11;
|
|
36020
36938
|
TECH_FONT_SIZE = 10;
|
|
36021
36939
|
CARD_H_PAD4 = 20;
|
|
36022
36940
|
CARD_V_PAD4 = 14;
|
|
@@ -36641,7 +37559,7 @@ function renderFlowchart(container, graph, layout, palette, isDark, onClickItem,
|
|
|
36641
37559
|
const sTitleFontSize = ctx.text(TITLE_FONT_SIZE);
|
|
36642
37560
|
const sTitleY = ctx.structural(TITLE_Y);
|
|
36643
37561
|
const sNodeFontSize = ctx.text(NODE_FONT_SIZE2);
|
|
36644
|
-
const sEdgeLabelFontSize = ctx.text(
|
|
37562
|
+
const sEdgeLabelFontSize = ctx.text(EDGE_LABEL_FONT_SIZE8);
|
|
36645
37563
|
const sEdgeStrokeWidth = ctx.structural(EDGE_STROKE_WIDTH);
|
|
36646
37564
|
const sNodeStrokeWidth = ctx.structural(NODE_STROKE_WIDTH);
|
|
36647
37565
|
const sArrowheadW = ctx.structural(ARROWHEAD_W3);
|
|
@@ -36867,7 +37785,7 @@ function renderFlowchartForExport(content, theme, palette) {
|
|
|
36867
37785
|
document.body.removeChild(container);
|
|
36868
37786
|
}
|
|
36869
37787
|
}
|
|
36870
|
-
var DIAGRAM_PADDING9, MAX_SCALE6, NODE_FONT_SIZE2,
|
|
37788
|
+
var DIAGRAM_PADDING9, MAX_SCALE6, NODE_FONT_SIZE2, EDGE_LABEL_FONT_SIZE8, ARROWHEAD_W3, ARROWHEAD_H3, IO_SKEW, SUBROUTINE_INSET, DOC_WAVE_HEIGHT;
|
|
36871
37789
|
var init_flowchart_renderer = __esm({
|
|
36872
37790
|
"src/graph/flowchart-renderer.ts"() {
|
|
36873
37791
|
"use strict";
|
|
@@ -36886,7 +37804,7 @@ var init_flowchart_renderer = __esm({
|
|
|
36886
37804
|
DIAGRAM_PADDING9 = 20;
|
|
36887
37805
|
MAX_SCALE6 = 3;
|
|
36888
37806
|
NODE_FONT_SIZE2 = 13;
|
|
36889
|
-
|
|
37807
|
+
EDGE_LABEL_FONT_SIZE8 = 11;
|
|
36890
37808
|
ARROWHEAD_W3 = 10;
|
|
36891
37809
|
ARROWHEAD_H3 = 7;
|
|
36892
37810
|
IO_SKEW = 15;
|
|
@@ -38061,7 +38979,7 @@ function separateGroups(groups, nodes, isLR, maxIterations = 20) {
|
|
|
38061
38979
|
const crossOverlap = isLR ? Math.min(ga.x + ga.width, gb.x + gb.width) - Math.max(ga.x, gb.x) : Math.min(ga.y + ga.height, gb.y + gb.height) - Math.max(ga.y, gb.y);
|
|
38062
38980
|
if (crossOverlap <= 0) continue;
|
|
38063
38981
|
anyOverlap = true;
|
|
38064
|
-
const shift = primaryOverlap +
|
|
38982
|
+
const shift = primaryOverlap + GROUP_GAP2;
|
|
38065
38983
|
const aCenter = isLR ? ga.y + ga.height / 2 : ga.x + ga.width / 2;
|
|
38066
38984
|
const bCenter = isLR ? gb.y + gb.height / 2 : gb.x + gb.width / 2;
|
|
38067
38985
|
const groupToShift = aCenter <= bCenter ? gb : ga;
|
|
@@ -38321,7 +39239,7 @@ function layoutInfra(computed, expandedNodeIds, collapsedNodes) {
|
|
|
38321
39239
|
const midIdx = Math.floor(edge.points.length / 2);
|
|
38322
39240
|
const midPt = edge.points[midIdx];
|
|
38323
39241
|
if (midPt) {
|
|
38324
|
-
const halfWidth = (measureText(edge.label,
|
|
39242
|
+
const halfWidth = (measureText(edge.label, EDGE_LABEL_FONT_SIZE9) + 8) / 2;
|
|
38325
39243
|
if (midPt.x - halfWidth < minX) minX = midPt.x - halfWidth;
|
|
38326
39244
|
if (midPt.x + halfWidth > maxX) maxX = midPt.x + halfWidth;
|
|
38327
39245
|
}
|
|
@@ -38355,7 +39273,7 @@ function layoutInfra(computed, expandedNodeIds, collapsedNodes) {
|
|
|
38355
39273
|
height: totalHeight
|
|
38356
39274
|
};
|
|
38357
39275
|
}
|
|
38358
|
-
var MIN_NODE_WIDTH2, NODE_HEADER_HEIGHT, META_LINE_HEIGHT5, NODE_SEPARATOR_GAP, NODE_PAD_BOTTOM, ROLE_DOT_ROW, COLLAPSE_BAR_HEIGHT3, NODE_FONT_SIZE3, META_FONT_SIZE5,
|
|
39276
|
+
var MIN_NODE_WIDTH2, NODE_HEADER_HEIGHT, META_LINE_HEIGHT5, NODE_SEPARATOR_GAP, NODE_PAD_BOTTOM, ROLE_DOT_ROW, COLLAPSE_BAR_HEIGHT3, NODE_FONT_SIZE3, META_FONT_SIZE5, EDGE_LABEL_FONT_SIZE9, PADDING_X3, GROUP_PADDING2, GROUP_HEADER_HEIGHT, EDGE_MARGIN, DISPLAY_KEYS, DISPLAY_NAMES, GROUP_GAP2;
|
|
38359
39277
|
var init_layout10 = __esm({
|
|
38360
39278
|
"src/infra/layout.ts"() {
|
|
38361
39279
|
"use strict";
|
|
@@ -38369,7 +39287,7 @@ var init_layout10 = __esm({
|
|
|
38369
39287
|
COLLAPSE_BAR_HEIGHT3 = 6;
|
|
38370
39288
|
NODE_FONT_SIZE3 = 13;
|
|
38371
39289
|
META_FONT_SIZE5 = 10;
|
|
38372
|
-
|
|
39290
|
+
EDGE_LABEL_FONT_SIZE9 = 11;
|
|
38373
39291
|
PADDING_X3 = 24;
|
|
38374
39292
|
GROUP_PADDING2 = 20;
|
|
38375
39293
|
GROUP_HEADER_HEIGHT = 24;
|
|
@@ -38410,7 +39328,7 @@ var init_layout10 = __esm({
|
|
|
38410
39328
|
"retention-hours": "retention",
|
|
38411
39329
|
partitions: "partitions"
|
|
38412
39330
|
};
|
|
38413
|
-
|
|
39331
|
+
GROUP_GAP2 = GROUP_PADDING2 * 2 + GROUP_HEADER_HEIGHT;
|
|
38414
39332
|
}
|
|
38415
39333
|
});
|
|
38416
39334
|
|
|
@@ -38476,7 +39394,7 @@ function buildScaledConstants(ctx) {
|
|
|
38476
39394
|
sNodeFontSize: ctx.text(NODE_FONT_SIZE4),
|
|
38477
39395
|
sMetaFontSize: ctx.text(META_FONT_SIZE6),
|
|
38478
39396
|
sMetaLineHeight: ctx.structural(META_LINE_HEIGHT6),
|
|
38479
|
-
sEdgeLabelFontSize: ctx.text(
|
|
39397
|
+
sEdgeLabelFontSize: ctx.text(EDGE_LABEL_FONT_SIZE10),
|
|
38480
39398
|
sGroupLabelFontSize: ctx.text(GROUP_LABEL_FONT_SIZE2),
|
|
38481
39399
|
sNodeBorderRadius: ctx.structural(NODE_BORDER_RADIUS),
|
|
38482
39400
|
sEdgeStrokeWidth: ctx.structural(EDGE_STROKE_WIDTH),
|
|
@@ -39205,7 +40123,7 @@ function renderEdgeLabels(svg, edges, nodes, groups, palette, _isDark, animate,
|
|
|
39205
40123
|
if (!midPt) continue;
|
|
39206
40124
|
const labelText = edge.label;
|
|
39207
40125
|
const g = svg.append("g").attr("class", animate ? "infra-edge-label" : "");
|
|
39208
|
-
const textWidth = measureText(labelText,
|
|
40126
|
+
const textWidth = measureText(labelText, EDGE_LABEL_FONT_SIZE10) + 8;
|
|
39209
40127
|
g.append("rect").attr("x", midPt.x - textWidth / 2).attr("y", midPt.y - 8).attr("width", textWidth).attr("height", 16).attr("rx", 3).attr("fill", palette.bg).attr("opacity", 0.9);
|
|
39210
40128
|
g.append("text").attr("x", midPt.x).attr("y", midPt.y + 4).attr("text-anchor", "middle").attr("font-family", FONT_FAMILY).attr("font-size", sc.sEdgeLabelFontSize).attr("fill", palette.textMuted).text(labelText);
|
|
39211
40129
|
if (animate) {
|
|
@@ -39219,7 +40137,7 @@ function resolveActiveTagStroke(node, activeGroup, tagGroups, palette) {
|
|
|
39219
40137
|
(t) => t.name.toLowerCase() === activeGroup.toLowerCase()
|
|
39220
40138
|
);
|
|
39221
40139
|
if (!tg) return null;
|
|
39222
|
-
const tagKey = (tg.alias ?? tg.name)
|
|
40140
|
+
const tagKey = tagAttrKey(tg.alias ?? tg.name);
|
|
39223
40141
|
const tagVal = node.tags[tagKey];
|
|
39224
40142
|
if (!tagVal) return null;
|
|
39225
40143
|
const tv = tg.values.find(
|
|
@@ -39548,7 +40466,7 @@ function computeInfraLegendGroups(nodes, tagGroups, palette, edges) {
|
|
|
39548
40466
|
groups.push({
|
|
39549
40467
|
name: tg.name,
|
|
39550
40468
|
type: "tag",
|
|
39551
|
-
tagKey: (tg.alias ?? tg.name)
|
|
40469
|
+
tagKey: tagAttrKey(tg.alias ?? tg.name),
|
|
39552
40470
|
entries,
|
|
39553
40471
|
width: LEGEND_CAPSULE_PAD * 2 + pillWidth2 + 4 + entriesWidth2,
|
|
39554
40472
|
minifiedWidth: pillWidth2
|
|
@@ -39596,7 +40514,7 @@ function renderLegend3(rootSvg, legendGroups, totalWidth, legendY, palette, isDa
|
|
|
39596
40514
|
});
|
|
39597
40515
|
legendG.selectAll("[data-legend-group]").classed("infra-legend-group", true);
|
|
39598
40516
|
for (const group of legendGroups) {
|
|
39599
|
-
const groupKey = group.name
|
|
40517
|
+
const groupKey = tagAttrKey(group.name);
|
|
39600
40518
|
for (const entry of group.entries) {
|
|
39601
40519
|
const entryEl = legendG.select(
|
|
39602
40520
|
`[data-legend-group="${groupKey}"] [data-legend-entry="${entry.value.toLowerCase()}"]`
|
|
@@ -39815,10 +40733,11 @@ function parseAndLayoutInfra(content) {
|
|
|
39815
40733
|
const layout = layoutInfra(computed);
|
|
39816
40734
|
return { parsed, computed, layout };
|
|
39817
40735
|
}
|
|
39818
|
-
var NODE_FONT_SIZE4, META_FONT_SIZE6, META_LINE_HEIGHT6,
|
|
40736
|
+
var NODE_FONT_SIZE4, META_FONT_SIZE6, META_LINE_HEIGHT6, EDGE_LABEL_FONT_SIZE10, GROUP_LABEL_FONT_SIZE2, NODE_BORDER_RADIUS, OVERLOAD_STROKE_WIDTH, ROLE_DOT_RADIUS, NODE_HEADER_HEIGHT2, NODE_SEPARATOR_GAP2, NODE_PAD_BOTTOM2, LEGEND_FIXED_GAP3, SPEED_BADGE_H_PAD, SPEED_BADGE_V_PAD, SPEED_BADGE_GAP, COLOR_HEALTHY, COLOR_WARNING, COLOR_OVERLOADED, FLOW_SPEED_MIN, FLOW_SPEED_MAX, PARTICLE_R, PARTICLE_COUNT_MIN, PARTICLE_COUNT_MAX, NODE_PULSE_SPEED, NODE_PULSE_OVERLOAD, REJECT_DROP_DISTANCE, REJECT_DURATION_MIN, REJECT_DURATION_MAX, REJECT_COUNT_MIN, REJECT_COUNT_MAX, PROP_DISPLAY, DESC_MAX_CHARS, DESC_MAX_WIDTH, RPS_FORMAT_KEYS, MS_FORMAT_KEYS, PCT_FORMAT_KEYS;
|
|
39819
40737
|
var init_renderer10 = __esm({
|
|
39820
40738
|
"src/infra/renderer.ts"() {
|
|
39821
40739
|
"use strict";
|
|
40740
|
+
init_tag_groups();
|
|
39822
40741
|
init_fonts();
|
|
39823
40742
|
init_color_utils();
|
|
39824
40743
|
init_colors();
|
|
@@ -39838,7 +40757,7 @@ var init_renderer10 = __esm({
|
|
|
39838
40757
|
NODE_FONT_SIZE4 = 13;
|
|
39839
40758
|
META_FONT_SIZE6 = 10;
|
|
39840
40759
|
META_LINE_HEIGHT6 = 14;
|
|
39841
|
-
|
|
40760
|
+
EDGE_LABEL_FONT_SIZE10 = 11;
|
|
39842
40761
|
GROUP_LABEL_FONT_SIZE2 = 14;
|
|
39843
40762
|
NODE_BORDER_RADIUS = 8;
|
|
39844
40763
|
OVERLOAD_STROKE_WIDTH = 3;
|
|
@@ -39915,17 +40834,17 @@ function mulberry32(seed) {
|
|
|
39915
40834
|
return ((t ^ t >>> 14) >>> 0) / 4294967296;
|
|
39916
40835
|
};
|
|
39917
40836
|
}
|
|
39918
|
-
function standardNormal(
|
|
40837
|
+
function standardNormal(rng4) {
|
|
39919
40838
|
let u = 0;
|
|
39920
40839
|
let v = 0;
|
|
39921
|
-
while (u === 0) u =
|
|
39922
|
-
while (v === 0) v =
|
|
40840
|
+
while (u === 0) u = rng4();
|
|
40841
|
+
while (v === 0) v = rng4();
|
|
39923
40842
|
return Math.sqrt(-2 * Math.log(u)) * Math.cos(2 * Math.PI * v);
|
|
39924
40843
|
}
|
|
39925
|
-
function gamma(shape,
|
|
40844
|
+
function gamma(shape, rng4) {
|
|
39926
40845
|
if (shape < 1) {
|
|
39927
|
-
const u =
|
|
39928
|
-
return gamma(shape + 1,
|
|
40846
|
+
const u = rng4();
|
|
40847
|
+
return gamma(shape + 1, rng4) * Math.pow(u, 1 / shape);
|
|
39929
40848
|
}
|
|
39930
40849
|
const d = shape - 1 / 3;
|
|
39931
40850
|
const c = 1 / Math.sqrt(9 * d);
|
|
@@ -39933,29 +40852,29 @@ function gamma(shape, rng3) {
|
|
|
39933
40852
|
let x;
|
|
39934
40853
|
let v;
|
|
39935
40854
|
do {
|
|
39936
|
-
x = standardNormal(
|
|
40855
|
+
x = standardNormal(rng4);
|
|
39937
40856
|
v = 1 + c * x;
|
|
39938
40857
|
} while (v <= 0);
|
|
39939
40858
|
v = v * v * v;
|
|
39940
|
-
const u =
|
|
40859
|
+
const u = rng4();
|
|
39941
40860
|
if (u < 1 - 0.0331 * x * x * x * x) return d * v;
|
|
39942
40861
|
if (Math.log(u) < x * x / 2 + d * (1 - v + Math.log(v))) return d * v;
|
|
39943
40862
|
}
|
|
39944
40863
|
}
|
|
39945
|
-
function sampleBeta(alpha, beta,
|
|
39946
|
-
const x = gamma(alpha,
|
|
39947
|
-
const y = gamma(beta,
|
|
40864
|
+
function sampleBeta(alpha, beta, rng4) {
|
|
40865
|
+
const x = gamma(alpha, rng4);
|
|
40866
|
+
const y = gamma(beta, rng4);
|
|
39948
40867
|
return x / (x + y);
|
|
39949
40868
|
}
|
|
39950
|
-
function sampleBetaPert(o, m, p,
|
|
40869
|
+
function sampleBetaPert(o, m, p, rng4) {
|
|
39951
40870
|
if (o === p) return m;
|
|
39952
40871
|
const range = p - o;
|
|
39953
40872
|
const alpha = 1 + 4 * (m - o) / range;
|
|
39954
40873
|
const beta = 1 + 4 * (p - m) / range;
|
|
39955
|
-
return o + sampleBeta(alpha, beta,
|
|
40874
|
+
return o + sampleBeta(alpha, beta, rng4) * range;
|
|
39956
40875
|
}
|
|
39957
40876
|
function simulate(resolved, expanded, _predecessors, _successors, topo, terminals, poisoned, opts) {
|
|
39958
|
-
const
|
|
40877
|
+
const rng4 = mulberry32(opts.seed);
|
|
39959
40878
|
const expById = /* @__PURE__ */ new Map();
|
|
39960
40879
|
for (const e of expanded) expById.set(e.id, e);
|
|
39961
40880
|
const completionTimes = new Array(opts.trials);
|
|
@@ -39978,7 +40897,7 @@ function simulate(resolved, expanded, _predecessors, _successors, topo, terminal
|
|
|
39978
40897
|
} else if (exp.o === exp.p) {
|
|
39979
40898
|
duration = exp.m;
|
|
39980
40899
|
} else {
|
|
39981
|
-
duration = sampleBetaPert(exp.o, exp.m, exp.p,
|
|
40900
|
+
duration = sampleBetaPert(exp.o, exp.m, exp.p, rng4);
|
|
39982
40901
|
}
|
|
39983
40902
|
let esLower = 0;
|
|
39984
40903
|
let efLower = -Infinity;
|
|
@@ -44265,7 +45184,7 @@ function renderGantt(container, resolved, palette, isDark, options, exportDims)
|
|
|
44265
45184
|
const ctx = exportDims ? ScaleContext.identity() : ScaleContext.from(containerWidth, idealWidth);
|
|
44266
45185
|
const sBarH = ctx.structural(BAR_H);
|
|
44267
45186
|
const sRowGap = ctx.structural(ROW_GAP);
|
|
44268
|
-
const sGroupGap = ctx.structural(
|
|
45187
|
+
const sGroupGap = ctx.structural(GROUP_GAP3);
|
|
44269
45188
|
const sMilestoneSize = ctx.structural(MILESTONE_SIZE);
|
|
44270
45189
|
const sBottomMargin = ctx.aesthetic(BOTTOM_MARGIN);
|
|
44271
45190
|
const sRightMargin = ctx.aesthetic(RIGHT_MARGIN);
|
|
@@ -44437,7 +45356,7 @@ function renderGantt(container, resolved, palette, isDark, options, exportDims)
|
|
|
44437
45356
|
(tg) => tg.name.toLowerCase() === currentSwimlaneGroup.toLowerCase()
|
|
44438
45357
|
);
|
|
44439
45358
|
if (tagGroup) {
|
|
44440
|
-
const tagKey = tagGroup.name
|
|
45359
|
+
const tagKey = tagAttrKey(tagGroup.name);
|
|
44441
45360
|
for (const rt of resolved.tasks) {
|
|
44442
45361
|
let value = rt.effectiveMetadata[tagKey];
|
|
44443
45362
|
if (!value && tagGroup.defaultValue) value = tagGroup.defaultValue;
|
|
@@ -45178,7 +46097,7 @@ function renderTagLegend(svg, chartG, tagGroups, activeGroupName, chartLeftMargi
|
|
|
45178
46097
|
const usedValues = /* @__PURE__ */ new Map();
|
|
45179
46098
|
if (resolvedTasks) {
|
|
45180
46099
|
for (const group of visibleGroups) {
|
|
45181
|
-
const key = group.name
|
|
46100
|
+
const key = tagAttrKey(group.name);
|
|
45182
46101
|
const used = /* @__PURE__ */ new Set();
|
|
45183
46102
|
for (const rt of resolvedTasks) {
|
|
45184
46103
|
const val = rt.effectiveMetadata[key];
|
|
@@ -45189,7 +46108,7 @@ function renderTagLegend(svg, chartG, tagGroups, activeGroupName, chartLeftMargi
|
|
|
45189
46108
|
}
|
|
45190
46109
|
const filteredEntries = /* @__PURE__ */ new Map();
|
|
45191
46110
|
for (const group of visibleGroups) {
|
|
45192
|
-
const key = group.name
|
|
46111
|
+
const key = tagAttrKey(group.name);
|
|
45193
46112
|
const used = usedValues.get(key);
|
|
45194
46113
|
if (used && used.size > 0) {
|
|
45195
46114
|
filteredEntries.set(
|
|
@@ -45210,7 +46129,7 @@ function renderTagLegend(svg, chartG, tagGroups, activeGroupName, chartLeftMargi
|
|
|
45210
46129
|
const pillW = measureLegendText(group.name, LEGEND_PILL_FONT_SIZE) + LEGEND_PILL_PAD + iconReserve;
|
|
45211
46130
|
let groupW = pillW;
|
|
45212
46131
|
if (isActive) {
|
|
45213
|
-
const entries = filteredEntries.get(group.name
|
|
46132
|
+
const entries = filteredEntries.get(tagAttrKey(group.name)) ?? group.entries;
|
|
45214
46133
|
let entriesW = 0;
|
|
45215
46134
|
for (const entry of entries) {
|
|
45216
46135
|
entriesW += LEGEND_DOT_R * 2 + LEGEND_ENTRY_DOT_GAP + measureLegendText(entry.value, LEGEND_ENTRY_FONT_SIZE) + LEGEND_ENTRY_TRAIL;
|
|
@@ -45267,7 +46186,7 @@ function renderTagLegend(svg, chartG, tagGroups, activeGroupName, chartLeftMargi
|
|
|
45267
46186
|
},
|
|
45268
46187
|
...onControlsToggle !== void 0 && { onControlsToggle },
|
|
45269
46188
|
onEntryHover: (groupName, entryValue) => {
|
|
45270
|
-
const tagKey = groupName
|
|
46189
|
+
const tagKey = tagAttrKey(groupName);
|
|
45271
46190
|
if (entryValue) {
|
|
45272
46191
|
const ev = entryValue.toLowerCase();
|
|
45273
46192
|
chartG.selectAll(".gantt-task").each(function() {
|
|
@@ -45957,7 +46876,7 @@ function buildTagLaneRowList(resolved, swimlaneGroup, collapsedLanes) {
|
|
|
45957
46876
|
(g) => g.name.toLowerCase() === swimlaneGroup.toLowerCase()
|
|
45958
46877
|
);
|
|
45959
46878
|
if (!tagGroup) return null;
|
|
45960
|
-
const tagKey = tagGroup.name
|
|
46879
|
+
const tagKey = tagAttrKey(tagGroup.name);
|
|
45961
46880
|
const rows = [];
|
|
45962
46881
|
const buckets = /* @__PURE__ */ new Map();
|
|
45963
46882
|
const unbucketed = [];
|
|
@@ -46141,10 +47060,11 @@ function renderTimeScaleHorizontal(g, scale, _innerWidth, innerHeight, textColor
|
|
|
46141
47060
|
g.append("text").attr("class", "gantt-scale-tick").attr("x", tick.pos).attr("y", innerHeight + tickLen + 12).attr("text-anchor", "middle").attr("font-size", "10px").attr("fill", textColor).attr("opacity", opacity).text(tick.label);
|
|
46142
47061
|
}
|
|
46143
47062
|
}
|
|
46144
|
-
var BAR_H, ROW_GAP,
|
|
47063
|
+
var BAR_H, ROW_GAP, GROUP_GAP3, MILESTONE_SIZE, MIN_LEFT_MARGIN, BOTTOM_MARGIN, RIGHT_MARGIN, LABEL_PAD2, LABEL_GAP, BAND_ACCENT_W, BAND_RADIUS, bandClipCounter, JS_DAY_TO_WEEKDAY2, ERA_COLORS, SPRINT_BAND_OPACITY, SPRINT_HOVER_OPACITY, SPRINT_BOUNDARY_OPACITY, FADE_OPACITY;
|
|
46145
47064
|
var init_renderer12 = __esm({
|
|
46146
47065
|
"src/gantt/renderer.ts"() {
|
|
46147
47066
|
"use strict";
|
|
47067
|
+
init_tag_groups();
|
|
46148
47068
|
init_fonts();
|
|
46149
47069
|
init_palettes();
|
|
46150
47070
|
init_color_utils();
|
|
@@ -46159,7 +47079,7 @@ var init_renderer12 = __esm({
|
|
|
46159
47079
|
init_title_constants();
|
|
46160
47080
|
BAR_H = 22;
|
|
46161
47081
|
ROW_GAP = 6;
|
|
46162
|
-
|
|
47082
|
+
GROUP_GAP3 = 14;
|
|
46163
47083
|
MILESTONE_SIZE = 10;
|
|
46164
47084
|
MIN_LEFT_MARGIN = 120;
|
|
46165
47085
|
BOTTOM_MARGIN = 40;
|
|
@@ -46226,7 +47146,7 @@ function renderState(container, graph, layout, palette, isDark, onClickItem, exp
|
|
|
46226
47146
|
const sTitleFontSize = ctx.text(TITLE_FONT_SIZE);
|
|
46227
47147
|
const sTitleY = ctx.structural(TITLE_Y);
|
|
46228
47148
|
const sNodeFontSize = ctx.text(NODE_FONT_SIZE6);
|
|
46229
|
-
const sEdgeLabelFontSize = ctx.text(
|
|
47149
|
+
const sEdgeLabelFontSize = ctx.text(EDGE_LABEL_FONT_SIZE11);
|
|
46230
47150
|
const sGroupLabelFontSize = ctx.text(GROUP_LABEL_FONT_SIZE3);
|
|
46231
47151
|
const sEdgeStrokeWidth = ctx.structural(EDGE_STROKE_WIDTH);
|
|
46232
47152
|
const sNodeStrokeWidth = ctx.structural(NODE_STROKE_WIDTH);
|
|
@@ -46506,7 +47426,7 @@ function renderStateForExport(content, theme, palette) {
|
|
|
46506
47426
|
document.body.removeChild(container);
|
|
46507
47427
|
}
|
|
46508
47428
|
}
|
|
46509
|
-
var DIAGRAM_PADDING12, MAX_SCALE7, NODE_FONT_SIZE6,
|
|
47429
|
+
var DIAGRAM_PADDING12, MAX_SCALE7, NODE_FONT_SIZE6, EDGE_LABEL_FONT_SIZE11, GROUP_LABEL_FONT_SIZE3, ARROWHEAD_W5, ARROWHEAD_H5, PSEUDOSTATE_RADIUS, STATE_CORNER_RADIUS, GROUP_EXTRA_PADDING;
|
|
46510
47430
|
var init_state_renderer = __esm({
|
|
46511
47431
|
"src/graph/state-renderer.ts"() {
|
|
46512
47432
|
"use strict";
|
|
@@ -46525,7 +47445,7 @@ var init_state_renderer = __esm({
|
|
|
46525
47445
|
DIAGRAM_PADDING12 = 20;
|
|
46526
47446
|
MAX_SCALE7 = 3;
|
|
46527
47447
|
NODE_FONT_SIZE6 = 13;
|
|
46528
|
-
|
|
47448
|
+
EDGE_LABEL_FONT_SIZE11 = 11;
|
|
46529
47449
|
GROUP_LABEL_FONT_SIZE3 = 11;
|
|
46530
47450
|
ARROWHEAD_W5 = 10;
|
|
46531
47451
|
ARROWHEAD_H5 = 7;
|
|
@@ -48234,7 +49154,7 @@ function renderJourneyMap(container, parsed, palette, isDark, options) {
|
|
|
48234
49154
|
const panelWidth = 280;
|
|
48235
49155
|
const textAreaWidth = panelWidth - silhouetteZone - CARD_PADDING_X3;
|
|
48236
49156
|
const descLineH = 14;
|
|
48237
|
-
const descLines = parsed.persona.description ?
|
|
49157
|
+
const descLines = parsed.persona.description ? wrapNoteBody(parsed.persona.description, textAreaWidth, FONT_SIZE_META) : [];
|
|
48238
49158
|
const descRowH = descLines.length > 0 ? descLines.length * descLineH + 8 : 0;
|
|
48239
49159
|
const panelHeight = titleRowH + descRowH;
|
|
48240
49160
|
const panelX = layout.totalWidth - PADDING2 - panelWidth;
|
|
@@ -48259,8 +49179,14 @@ function renderJourneyMap(container, parsed, palette, isDark, options) {
|
|
|
48259
49179
|
personaG.append("rect").attr("x", panelX).attr("y", panelY).attr("width", panelWidth).attr("height", panelHeight).attr("rx", CARD_RADIUS).attr("fill", "none").attr("stroke", personaColor).attr("stroke-width", CARD_STROKE_WIDTH2);
|
|
48260
49180
|
personaG.append("text").attr("x", textX).attr("y", panelY + CARD_PADDING_Y3 + FONT_SIZE_STEP).attr("font-size", FONT_SIZE_STEP).attr("font-weight", "500").attr("fill", onPersonaText).text(parsed.persona.name);
|
|
48261
49181
|
for (let li = 0; li < descLines.length; li++) {
|
|
48262
|
-
const
|
|
48263
|
-
|
|
49182
|
+
const line11 = descLines[li];
|
|
49183
|
+
const indent = line11.kind === "plain" ? 0 : NOTE_BULLET_INDENT;
|
|
49184
|
+
const lineY = panelY + titleRowH + descLineH * (li + 1);
|
|
49185
|
+
if (line11.kind === "bullet-first") {
|
|
49186
|
+
personaG.append("text").attr("x", textX).attr("y", lineY).attr("font-size", FONT_SIZE_META).attr("fill", onPersonaText).text("\u2022");
|
|
49187
|
+
}
|
|
49188
|
+
const lineEl = personaG.append("text").attr("x", textX + indent).attr("y", lineY).attr("font-size", FONT_SIZE_META).attr("fill", onPersonaText);
|
|
49189
|
+
renderInlineText(lineEl, line11.text, palette, FONT_SIZE_META);
|
|
48264
49190
|
}
|
|
48265
49191
|
if (onNavigateToLine) {
|
|
48266
49192
|
personaG.style("cursor", "pointer").on("click", () => {
|
|
@@ -48299,7 +49225,7 @@ function renderJourneyMap(container, parsed, palette, isDark, options) {
|
|
|
48299
49225
|
return;
|
|
48300
49226
|
}
|
|
48301
49227
|
const isScore = groupName === "Score";
|
|
48302
|
-
const attrName = isScore ? "data-score" : `data-tag-${groupName
|
|
49228
|
+
const attrName = isScore ? "data-score" : `data-tag-${tagAttrKey(groupName)}`;
|
|
48303
49229
|
const matches = (el) => el.getAttribute(attrName) === entryValue;
|
|
48304
49230
|
svg.selectAll(".journey-step").each(function() {
|
|
48305
49231
|
const hit = matches(this);
|
|
@@ -48780,7 +49706,7 @@ function resolveStepColor(step, scoreColor, activeGroup, tagGroups, _palette) {
|
|
|
48780
49706
|
(g) => g.name.toLowerCase() === activeGroup.toLowerCase()
|
|
48781
49707
|
);
|
|
48782
49708
|
if (!group) return void 0;
|
|
48783
|
-
const tagValue = step.tags[group.name
|
|
49709
|
+
const tagValue = step.tags[tagAttrKey(group.name)];
|
|
48784
49710
|
if (!tagValue) return void 0;
|
|
48785
49711
|
const entry = group.entries.find(
|
|
48786
49712
|
(e) => e.value.toLowerCase() === tagValue.toLowerCase()
|
|
@@ -48995,11 +49921,13 @@ var DIAGRAM_PADDING13, PADDING2, CARD_PADDING_X3, CARD_PADDING_Y3, CARD_HEADER_H
|
|
|
48995
49921
|
var init_renderer14 = __esm({
|
|
48996
49922
|
"src/journey-map/renderer.ts"() {
|
|
48997
49923
|
"use strict";
|
|
49924
|
+
init_tag_groups();
|
|
48998
49925
|
init_color_utils();
|
|
48999
49926
|
init_fonts();
|
|
49000
49927
|
init_parser23();
|
|
49001
49928
|
init_layout13();
|
|
49002
49929
|
init_inline_markdown();
|
|
49930
|
+
init_note_box();
|
|
49003
49931
|
init_legend_integration();
|
|
49004
49932
|
init_tag_groups();
|
|
49005
49933
|
init_scaling();
|
|
@@ -49339,10 +50267,10 @@ function renderedDescNodeHeight(numLines, scale) {
|
|
|
49339
50267
|
return headerH + textBlockH + bottomPad;
|
|
49340
50268
|
}
|
|
49341
50269
|
function wrapEdgeLabelText(label, description, maxWidth = EDGE_LABEL_MAX_WIDTH) {
|
|
49342
|
-
const labelLines = label ? wrapTextToWidth(label,
|
|
50270
|
+
const labelLines = label ? wrapTextToWidth(label, EDGE_LABEL_FONT_SIZE12, maxWidth) : [];
|
|
49343
50271
|
const descLines = [];
|
|
49344
50272
|
for (const d of description) {
|
|
49345
|
-
descLines.push(...wrapTextToWidth(d,
|
|
50273
|
+
descLines.push(...wrapTextToWidth(d, EDGE_LABEL_FONT_SIZE12, maxWidth));
|
|
49346
50274
|
}
|
|
49347
50275
|
return { labelLines, descLines };
|
|
49348
50276
|
}
|
|
@@ -49480,9 +50408,9 @@ function computeEdgePaths(layoutNodes, parsed, cx, cy, radius, isClockwise) {
|
|
|
49480
50408
|
const lineCount = labelLines.length + descLines.length;
|
|
49481
50409
|
let labelPxW = 0;
|
|
49482
50410
|
for (const l of labelLines)
|
|
49483
|
-
labelPxW = Math.max(labelPxW, measureText(l,
|
|
50411
|
+
labelPxW = Math.max(labelPxW, measureText(l, EDGE_LABEL_FONT_SIZE12));
|
|
49484
50412
|
for (const l of descLines)
|
|
49485
|
-
labelPxW = Math.max(labelPxW, measureText(l,
|
|
50413
|
+
labelPxW = Math.max(labelPxW, measureText(l, EDGE_LABEL_FONT_SIZE12));
|
|
49486
50414
|
const { labelX, labelY, labelAngle } = computeEdgeLabelPosition(
|
|
49487
50415
|
midAngle,
|
|
49488
50416
|
radius,
|
|
@@ -49584,9 +50512,9 @@ function fitToCanvas(nodes, edges, parsed, _cx, _cy, radius, width, height, _isC
|
|
|
49584
50512
|
);
|
|
49585
50513
|
let textWidth = 0;
|
|
49586
50514
|
for (const l of labelLines)
|
|
49587
|
-
textWidth = Math.max(textWidth, measureText(l,
|
|
50515
|
+
textWidth = Math.max(textWidth, measureText(l, EDGE_LABEL_FONT_SIZE12));
|
|
49588
50516
|
for (const l of descLines)
|
|
49589
|
-
textWidth = Math.max(textWidth, measureText(l,
|
|
50517
|
+
textWidth = Math.max(textWidth, measureText(l, EDGE_LABEL_FONT_SIZE12));
|
|
49590
50518
|
if (textWidth === 0) continue;
|
|
49591
50519
|
const normAngle = (le.labelAngle % (2 * Math.PI) + 2 * Math.PI) % (2 * Math.PI);
|
|
49592
50520
|
const isRight = normAngle < Math.PI * 0.4 || normAngle > Math.PI * 1.6;
|
|
@@ -49660,7 +50588,7 @@ function buildEdgeArc(src, tgt, cx, cy, radius, isClockwise, arrowLength = 0) {
|
|
|
49660
50588
|
const midAngle = srcExitAngle + dir * visibleSweep / 2;
|
|
49661
50589
|
return { path, midAngle };
|
|
49662
50590
|
}
|
|
49663
|
-
var MIN_ARC_ANGLE, LABEL_FONT_SIZE4, CIRCLE_LABEL_FONT_SIZE, DESC_FONT_SIZE6,
|
|
50591
|
+
var MIN_ARC_ANGLE, LABEL_FONT_SIZE4, CIRCLE_LABEL_FONT_SIZE, DESC_FONT_SIZE6, EDGE_LABEL_FONT_SIZE12, MIN_NODE_WIDTH4, MAX_NODE_WIDTH3, DESC_MIN_WIDTH, DESC_WIDTH_STEP, DESC_TARGET_RATIO, PLAIN_NODE_HEIGHT, HEADER_HEIGHT4, DESC_LINE_HEIGHT7, DESC_PAD_Y, NODE_PAD_X, MIN_CIRCLE_RADIUS, CIRCLE_PAD, RENDERER_DESC_FONT, RENDERER_DESC_FONT_MIN, RENDERER_DESC_LINE_H, RENDERER_DESC_LINE_H_MIN, EDGE_LABEL_MAX_WIDTH;
|
|
49664
50592
|
var init_layout14 = __esm({
|
|
49665
50593
|
"src/cycle/layout.ts"() {
|
|
49666
50594
|
"use strict";
|
|
@@ -49671,7 +50599,7 @@ var init_layout14 = __esm({
|
|
|
49671
50599
|
LABEL_FONT_SIZE4 = 13;
|
|
49672
50600
|
CIRCLE_LABEL_FONT_SIZE = 16;
|
|
49673
50601
|
DESC_FONT_SIZE6 = 11;
|
|
49674
|
-
|
|
50602
|
+
EDGE_LABEL_FONT_SIZE12 = 11;
|
|
49675
50603
|
MIN_NODE_WIDTH4 = 70;
|
|
49676
50604
|
MAX_NODE_WIDTH3 = 260;
|
|
49677
50605
|
DESC_MIN_WIDTH = 140;
|
|
@@ -49817,7 +50745,7 @@ function renderCycle(container, parsed, palette, isDark, onClickItem, exportDims
|
|
|
49817
50745
|
const scaledNodeFont = Math.max(6, Math.round(NODE_FONT_SIZE7 * layout.scale));
|
|
49818
50746
|
const scaledEdgeLabelFont = Math.max(
|
|
49819
50747
|
6,
|
|
49820
|
-
Math.round(
|
|
50748
|
+
Math.round(EDGE_LABEL_FONT_SIZE13 * layout.scale)
|
|
49821
50749
|
);
|
|
49822
50750
|
const CIRCLE_LABEL_FONT_SIZE2 = 16;
|
|
49823
50751
|
const scaledCircleLabelFont = Math.max(
|
|
@@ -49980,7 +50908,7 @@ function ensureArrowMarker(defs, color, strokeWidth) {
|
|
|
49980
50908
|
const mh = Math.max(1.5, mw * 0.5);
|
|
49981
50909
|
defs.append("marker").attr("id", id).attr("viewBox", `0 0 ${mw} ${mh}`).attr("refX", mw * 0.1).attr("refY", mh / 2).attr("markerWidth", mw).attr("markerHeight", mh).attr("orient", "auto").append("polygon").attr("points", `0,0 ${mw},${mh / 2} 0,${mh}`).attr("fill", color);
|
|
49982
50910
|
}
|
|
49983
|
-
var NODE_FONT_SIZE7, DESC_FONT_SIZE7,
|
|
50911
|
+
var NODE_FONT_SIZE7, DESC_FONT_SIZE7, EDGE_LABEL_FONT_SIZE13, DESC_LINE_HEIGHT8, TITLE_AREA_HEIGHT;
|
|
49984
50912
|
var init_renderer15 = __esm({
|
|
49985
50913
|
"src/cycle/renderer.ts"() {
|
|
49986
50914
|
"use strict";
|
|
@@ -49997,7 +50925,7 @@ var init_renderer15 = __esm({
|
|
|
49997
50925
|
init_text_measure();
|
|
49998
50926
|
NODE_FONT_SIZE7 = 13;
|
|
49999
50927
|
DESC_FONT_SIZE7 = 11;
|
|
50000
|
-
|
|
50928
|
+
EDGE_LABEL_FONT_SIZE13 = 11;
|
|
50001
50929
|
DESC_LINE_HEIGHT8 = 15;
|
|
50002
50930
|
TITLE_AREA_HEIGHT = 50;
|
|
50003
50931
|
}
|
|
@@ -51834,7 +52762,7 @@ function layoutMap(resolvedIn, data, size, opts) {
|
|
|
51834
52762
|
(g) => g.name.toLowerCase() === groupName.toLowerCase()
|
|
51835
52763
|
);
|
|
51836
52764
|
if (!group) return null;
|
|
51837
|
-
const val = tags[group.name
|
|
52765
|
+
const val = tags[tagAttrKey(group.name)] ?? group.defaultValue;
|
|
51838
52766
|
if (!val) return null;
|
|
51839
52767
|
const entry = group.entries.find(
|
|
51840
52768
|
(e) => e.value.toLowerCase() === val.toLowerCase()
|
|
@@ -52448,7 +53376,7 @@ function layoutMap(resolvedIn, data, size, opts) {
|
|
|
52448
53376
|
if (directHex)
|
|
52449
53377
|
return { fill: directHex, stroke: mix(directHex, palette.text, 18) };
|
|
52450
53378
|
for (const group of resolved.tagGroups) {
|
|
52451
|
-
const val = p.tags[group.name
|
|
53379
|
+
const val = p.tags[tagAttrKey(group.name)];
|
|
52452
53380
|
if (!val) continue;
|
|
52453
53381
|
const entry = group.entries.find(
|
|
52454
53382
|
(e) => e.value.toLowerCase() === val.toLowerCase()
|
|
@@ -52463,7 +53391,7 @@ function layoutMap(resolvedIn, data, size, opts) {
|
|
|
52463
53391
|
};
|
|
52464
53392
|
const lineColor = (tags) => {
|
|
52465
53393
|
for (const group of resolved.tagGroups) {
|
|
52466
|
-
const val = tags[group.name
|
|
53394
|
+
const val = tags[tagAttrKey(group.name)];
|
|
52467
53395
|
if (!val) continue;
|
|
52468
53396
|
const entry = group.entries.find(
|
|
52469
53397
|
(e) => e.value.toLowerCase() === val.toLowerCase()
|
|
@@ -53729,6 +54657,7 @@ var FIT_PAD, PATH_DIGITS, THIN_TOL, ALBERS_SKEW_MAX, RAMP_FLOOR2, R_DEFAULT, R_M
|
|
|
53729
54657
|
var init_layout15 = __esm({
|
|
53730
54658
|
"src/map/layout.ts"() {
|
|
53731
54659
|
"use strict";
|
|
54660
|
+
init_tag_groups();
|
|
53732
54661
|
init_color_utils();
|
|
53733
54662
|
init_geo();
|
|
53734
54663
|
init_colorize();
|
|
@@ -56142,7 +57071,7 @@ function resolveSequenceTags(parsed, activeTagGroup) {
|
|
|
56142
57071
|
}
|
|
56143
57072
|
return result;
|
|
56144
57073
|
}
|
|
56145
|
-
const groupKey = group.name
|
|
57074
|
+
const groupKey = tagAttrKey(group.name);
|
|
56146
57075
|
const participantMeta = /* @__PURE__ */ new Map();
|
|
56147
57076
|
for (const p of parsed.participants) {
|
|
56148
57077
|
participantMeta.set(p.id, { ...p.metadata || {} });
|
|
@@ -56178,6 +57107,7 @@ function resolveSequenceTags(parsed, activeTagGroup) {
|
|
|
56178
57107
|
var init_tag_resolution = __esm({
|
|
56179
57108
|
"src/sequence/tag-resolution.ts"() {
|
|
56180
57109
|
"use strict";
|
|
57110
|
+
init_tag_groups();
|
|
56181
57111
|
}
|
|
56182
57112
|
});
|
|
56183
57113
|
|
|
@@ -56653,7 +57583,7 @@ function renderSequenceDiagram(container, parsed, palette, isDark, _onNavigateTo
|
|
|
56653
57583
|
}
|
|
56654
57584
|
}
|
|
56655
57585
|
const getTagColor = (value) => value ? tagValueToColor.get(value.toLowerCase()) : void 0;
|
|
56656
|
-
const tagKey = activeTagGroup
|
|
57586
|
+
const tagKey = activeTagGroup ? tagAttrKey(activeTagGroup) : void 0;
|
|
56657
57587
|
const hiddenMsgIndices = /* @__PURE__ */ new Set();
|
|
56658
57588
|
if (collapsedSections && collapsedSections.size > 0) {
|
|
56659
57589
|
const sectionGroups = groupMessagesBySection(elements, messages);
|
|
@@ -57245,11 +58175,7 @@ function renderSequenceDiagram(container, parsed, palette, isDark, _onNavigateTo
|
|
|
57245
58175
|
const boxH = sBoxH + GROUP_PADDING_TOP2 + GROUP_PADDING_BOTTOM2;
|
|
57246
58176
|
const groupTagValue = tagKey && group.metadata?.[tagKey];
|
|
57247
58177
|
const groupTagColor = getTagColor(groupTagValue || void 0);
|
|
57248
|
-
const fillColor = groupTagColor ? mix(
|
|
57249
|
-
groupTagColor,
|
|
57250
|
-
themeBaseBg(palette, isDark),
|
|
57251
|
-
isDark ? 15 : 20
|
|
57252
|
-
) : isDark ? palette.surface : palette.bg;
|
|
58178
|
+
const fillColor = groupTagColor ? mix(groupTagColor, themeBaseBg(palette, isDark), isDark ? 15 : 20) : isDark ? palette.surface : palette.bg;
|
|
57253
58179
|
const strokeColor = groupTagColor || palette.textMuted;
|
|
57254
58180
|
const groupG = svg.append("g").attr("class", "group-box-wrapper").attr("data-group-toggle", "").attr("data-group-line", String(group.lineNumber)).attr("tabindex", "0").attr("role", "button").attr("aria-expanded", "true").attr("cursor", "pointer");
|
|
57255
58181
|
groupG.append("title").text("Click to collapse");
|
|
@@ -57299,11 +58225,7 @@ function renderSequenceDiagram(container, parsed, palette, isDark, _onNavigateTo
|
|
|
57299
58225
|
);
|
|
57300
58226
|
participantG.attr("data-group-toggle", "").attr("data-group-line", String(meta.lineNumber)).attr("tabindex", "0").attr("role", "button").attr("aria-expanded", "false").attr("cursor", "pointer");
|
|
57301
58227
|
participantG.append("title").text("Click to expand");
|
|
57302
|
-
const pFill = effectiveTagColor ? mix(
|
|
57303
|
-
effectiveTagColor,
|
|
57304
|
-
themeBaseBg(palette, isDark),
|
|
57305
|
-
isDark ? 30 : 40
|
|
57306
|
-
) : isDark ? mix(palette.overlay, palette.surface, 50) : mix(palette.bg, palette.surface, 50);
|
|
58228
|
+
const pFill = effectiveTagColor ? mix(effectiveTagColor, themeBaseBg(palette, isDark), isDark ? 30 : 40) : isDark ? mix(palette.overlay, palette.surface, 50) : mix(palette.bg, palette.surface, 50);
|
|
57307
58229
|
const pStroke = effectiveTagColor || palette.border;
|
|
57308
58230
|
participantG.append("rect").attr("x", -boxW / 2).attr("y", -GROUP_PADDING_TOP2).attr("width", boxW).attr("height", fullH).attr("rx", 6).attr("fill", pFill).attr("stroke", pStroke).attr("stroke-width", 1.5);
|
|
57309
58231
|
participantG.append("text").attr("x", 0).attr("y", -GROUP_PADDING_TOP2 + fullH / 2).attr("text-anchor", "middle").attr("dominant-baseline", "central").attr("fill", palette.text).attr("font-size", ctx.text(13)).attr("font-weight", 500).text(participant.label);
|
|
@@ -57799,6 +58721,7 @@ var PARTICIPANT_GAP, PARTICIPANT_BOX_WIDTH, PARTICIPANT_BOX_HEIGHT, LABEL_FONT_S
|
|
|
57799
58721
|
var init_renderer20 = __esm({
|
|
57800
58722
|
"src/sequence/renderer.ts"() {
|
|
57801
58723
|
"use strict";
|
|
58724
|
+
init_tag_groups();
|
|
57802
58725
|
init_color_utils();
|
|
57803
58726
|
init_inline_markdown();
|
|
57804
58727
|
init_fonts();
|
|
@@ -58953,6 +59876,7 @@ function renderArcDiagram(container, parsed, palette, _isDark, onClickItem, expo
|
|
|
58953
59876
|
init_parser3();
|
|
58954
59877
|
|
|
58955
59878
|
// src/timeline/renderer.ts
|
|
59879
|
+
init_tag_groups();
|
|
58956
59880
|
init_fonts();
|
|
58957
59881
|
init_time_ticks();
|
|
58958
59882
|
init_scaling();
|
|
@@ -59217,7 +60141,7 @@ function setupTimeline(container, parsed, palette, isDark, exportDims, activeTag
|
|
|
59217
60141
|
});
|
|
59218
60142
|
let tagLanes = null;
|
|
59219
60143
|
if (resolvedSwimlaneTG) {
|
|
59220
|
-
const tagKey = resolvedSwimlaneTG
|
|
60144
|
+
const tagKey = tagAttrKey(resolvedSwimlaneTG);
|
|
59221
60145
|
const tagGroup = parsed.timelineTagGroups.find(
|
|
59222
60146
|
(g) => g.name.toLowerCase() === tagKey
|
|
59223
60147
|
);
|
|
@@ -59523,7 +60447,7 @@ function renderTimelineTagLegendOverlay(container, parsed, palette, isDark, setu
|
|
|
59523
60447
|
onTagStateChange?.(currentActiveGroup, currentSwimlaneGroup);
|
|
59524
60448
|
},
|
|
59525
60449
|
onEntryHover: (groupName, entryValue) => {
|
|
59526
|
-
const tagKey = groupName
|
|
60450
|
+
const tagKey = tagAttrKey(groupName);
|
|
59527
60451
|
if (entryValue) {
|
|
59528
60452
|
const tagVal = entryValue.toLowerCase();
|
|
59529
60453
|
fadeToTagValue(mainG, tagKey, tagVal);
|
|
@@ -59542,7 +60466,7 @@ function renderTimelineTagLegendOverlay(container, parsed, palette, isDark, setu
|
|
|
59542
60466
|
}
|
|
59543
60467
|
},
|
|
59544
60468
|
onGroupRendered: (groupName, groupEl, isActive) => {
|
|
59545
|
-
const groupKey = groupName
|
|
60469
|
+
const groupKey = tagAttrKey(groupName);
|
|
59546
60470
|
groupEl.attr("data-tag-group", groupKey);
|
|
59547
60471
|
if (isActive && !viewMode) {
|
|
59548
60472
|
const isSwimActive = currentSwimlaneGroup?.toLowerCase() === groupKey;
|
|
@@ -63264,7 +64188,7 @@ pre.dgmo, code.language-dgmo, pre > code.language-dgmo,
|
|
|
63264
64188
|
|
|
63265
64189
|
// src/auto/index.ts
|
|
63266
64190
|
init_safe_href();
|
|
63267
|
-
var VERSION = "0.
|
|
64191
|
+
var VERSION = "0.34.0";
|
|
63268
64192
|
var DEFAULTS = {
|
|
63269
64193
|
theme: "auto",
|
|
63270
64194
|
palette: "slate",
|