@diagrammo/dgmo 0.8.21 → 0.8.23

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (114) hide show
  1. package/AGENTS.md +2 -1
  2. package/README.md +1 -0
  3. package/dist/cli.cjs +145 -93
  4. package/dist/editor.cjs +20 -3
  5. package/dist/editor.cjs.map +1 -1
  6. package/dist/editor.js +20 -3
  7. package/dist/editor.js.map +1 -1
  8. package/dist/highlight.cjs +15 -2
  9. package/dist/highlight.cjs.map +1 -1
  10. package/dist/highlight.js +15 -2
  11. package/dist/highlight.js.map +1 -1
  12. package/dist/index.cjs +20843 -14937
  13. package/dist/index.cjs.map +1 -1
  14. package/dist/index.d.cts +426 -17
  15. package/dist/index.d.ts +426 -17
  16. package/dist/index.js +20795 -14912
  17. package/dist/index.js.map +1 -1
  18. package/dist/internal.cjs +380 -0
  19. package/dist/internal.cjs.map +1 -0
  20. package/dist/internal.d.cts +179 -0
  21. package/dist/internal.d.ts +179 -0
  22. package/dist/internal.js +337 -0
  23. package/dist/internal.js.map +1 -0
  24. package/docs/guide/chart-cycle.md +156 -0
  25. package/docs/guide/chart-journey-map.md +179 -0
  26. package/docs/guide/chart-pyramid.md +111 -0
  27. package/docs/guide/chart-sitemap.md +18 -1
  28. package/docs/guide/chart-tech-radar.md +219 -0
  29. package/docs/guide/registry.json +6 -0
  30. package/docs/language-reference.md +177 -6
  31. package/gallery/fixtures/boxes-and-lines.dgmo +10 -3
  32. package/gallery/fixtures/c4-full.dgmo +2 -2
  33. package/gallery/fixtures/cycle/ooda-loop.dgmo +25 -0
  34. package/gallery/fixtures/cycle/pdca-circle-nodes.dgmo +12 -0
  35. package/gallery/fixtures/cycle/pdca-minimal.dgmo +6 -0
  36. package/gallery/fixtures/cycle/sprint-cycle-span.dgmo +17 -0
  37. package/gallery/fixtures/gantt-full.dgmo +2 -2
  38. package/gallery/fixtures/gantt.dgmo +2 -2
  39. package/gallery/fixtures/infra-full.dgmo +2 -2
  40. package/gallery/fixtures/infra.dgmo +1 -1
  41. package/gallery/fixtures/pyramid/dikw.dgmo +17 -0
  42. package/gallery/fixtures/pyramid/inverted-funnel.dgmo +16 -0
  43. package/gallery/fixtures/pyramid/minimal.dgmo +5 -0
  44. package/gallery/fixtures/sequence-tags-protocols.dgmo +2 -2
  45. package/gallery/fixtures/sequence-tags.dgmo +2 -2
  46. package/gallery/fixtures/tech-radar-dense.dgmo +77 -0
  47. package/gallery/fixtures/tech-radar.dgmo +36 -0
  48. package/gallery/fixtures/timeline.dgmo +1 -1
  49. package/package.json +11 -1
  50. package/src/boxes-and-lines/layout.ts +309 -33
  51. package/src/boxes-and-lines/parser.ts +86 -10
  52. package/src/boxes-and-lines/renderer.ts +250 -91
  53. package/src/boxes-and-lines/types.ts +1 -1
  54. package/src/c4/layout.ts +8 -8
  55. package/src/c4/parser.ts +35 -2
  56. package/src/c4/renderer.ts +19 -3
  57. package/src/c4/types.ts +1 -0
  58. package/src/chart.ts +14 -7
  59. package/src/cli.ts +5 -35
  60. package/src/completion.ts +233 -41
  61. package/src/cycle/layout.ts +723 -0
  62. package/src/cycle/parser.ts +352 -0
  63. package/src/cycle/renderer.ts +566 -0
  64. package/src/cycle/types.ts +98 -0
  65. package/src/d3.ts +107 -8
  66. package/src/dgmo-router.ts +82 -3
  67. package/src/echarts.ts +8 -5
  68. package/src/editor/dgmo.grammar +5 -1
  69. package/src/editor/dgmo.grammar.js +1 -1
  70. package/src/editor/keywords.ts +17 -0
  71. package/src/gantt/parser.ts +2 -8
  72. package/src/graph/flowchart-parser.ts +15 -21
  73. package/src/graph/state-parser.ts +5 -10
  74. package/src/index.ts +63 -2
  75. package/src/infra/layout.ts +218 -74
  76. package/src/infra/parser.ts +32 -8
  77. package/src/infra/renderer.ts +14 -8
  78. package/src/infra/types.ts +10 -3
  79. package/src/internal.ts +16 -0
  80. package/src/journey-map/layout.ts +386 -0
  81. package/src/journey-map/parser.ts +540 -0
  82. package/src/journey-map/renderer.ts +1521 -0
  83. package/src/journey-map/types.ts +47 -0
  84. package/src/kanban/parser.ts +3 -10
  85. package/src/kanban/renderer.ts +31 -15
  86. package/src/mindmap/parser.ts +12 -18
  87. package/src/mindmap/renderer.ts +14 -13
  88. package/src/mindmap/text-wrap.ts +22 -12
  89. package/src/mindmap/types.ts +2 -2
  90. package/src/org/collapse.ts +81 -0
  91. package/src/org/parser.ts +2 -6
  92. package/src/org/renderer.ts +212 -4
  93. package/src/pyramid/parser.ts +172 -0
  94. package/src/pyramid/renderer.ts +684 -0
  95. package/src/pyramid/types.ts +28 -0
  96. package/src/render.ts +2 -8
  97. package/src/sequence/parser.ts +62 -20
  98. package/src/sequence/renderer.ts +146 -40
  99. package/src/sharing.ts +1 -0
  100. package/src/sitemap/layout.ts +21 -6
  101. package/src/sitemap/parser.ts +26 -17
  102. package/src/sitemap/renderer.ts +34 -0
  103. package/src/sitemap/types.ts +1 -0
  104. package/src/tech-radar/index.ts +14 -0
  105. package/src/tech-radar/interactive.ts +1112 -0
  106. package/src/tech-radar/layout.ts +190 -0
  107. package/src/tech-radar/parser.ts +385 -0
  108. package/src/tech-radar/renderer.ts +1159 -0
  109. package/src/tech-radar/shared.ts +187 -0
  110. package/src/tech-radar/types.ts +81 -0
  111. package/src/utils/description-helpers.ts +33 -0
  112. package/src/utils/legend-layout.ts +3 -1
  113. package/src/utils/parsing.ts +47 -7
  114. package/src/utils/tag-groups.ts +46 -60
@@ -0,0 +1,380 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
+ // If the importer is in node compatibility mode or this is not an ESM
22
+ // file that has been converted to a CommonJS file using a Babel-
23
+ // compatible transform (i.e. "__esModule" has not been set), then set
24
+ // "default" to the CommonJS "module.exports" for node compatibility.
25
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
+ mod
27
+ ));
28
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
+
30
+ // src/internal.ts
31
+ var internal_exports = {};
32
+ __export(internal_exports, {
33
+ buildNoteMessageMap: () => buildNoteMessageMap,
34
+ collectNoteLineNumbers: () => collectNoteLineNumbers,
35
+ computeCardArchive: () => computeCardArchive,
36
+ computeCardMove: () => computeCardMove,
37
+ groupMessagesBySection: () => groupMessagesBySection,
38
+ isArchiveColumn: () => isArchiveColumn,
39
+ parseDataRowValues: () => parseDataRowValues
40
+ });
41
+ module.exports = __toCommonJS(internal_exports);
42
+
43
+ // src/utils/parsing.ts
44
+ function normalizeNumericToken(token) {
45
+ if (!token.includes(",") && !token.includes("_")) return null;
46
+ if (token.includes(",") && token.includes("_")) return null;
47
+ let sign = "";
48
+ let unsigned = token;
49
+ if (unsigned.startsWith("-")) {
50
+ sign = "-";
51
+ unsigned = unsigned.substring(1);
52
+ }
53
+ if (!unsigned) return null;
54
+ if (unsigned.includes(",")) {
55
+ if (/^\d{1,3}(,\d{3})+$/.test(unsigned))
56
+ return sign + unsigned.replace(/,/g, "");
57
+ if (/^\d{1,3}(,\d{3})+\.\d+$/.test(unsigned))
58
+ return sign + unsigned.replace(/,/g, "");
59
+ return null;
60
+ }
61
+ if (/^\d+(_\d+)+$/.test(unsigned)) return sign + unsigned.replace(/_/g, "");
62
+ if (/^\d+(_\d+)*\.\d+$/.test(unsigned) && unsigned.includes("_"))
63
+ return sign + unsigned.replace(/_/g, "");
64
+ return null;
65
+ }
66
+
67
+ // src/chart.ts
68
+ function parseDataRowValues(line, options) {
69
+ const segments = line.split(",");
70
+ const normalized = [];
71
+ for (let i = 0; i < segments.length; i++) {
72
+ const seg = segments[i].trim();
73
+ if (i > 0 && /^\d{3}(\.\d+)?$/.test(seg) && !/^\s/.test(segments[i])) {
74
+ const prevSeg = normalized[normalized.length - 1].trimEnd();
75
+ if (/\d{1,3}$/.test(prevSeg)) {
76
+ const prevMatch = prevSeg.match(/(\d{1,3})$/);
77
+ if (prevMatch) {
78
+ normalized[normalized.length - 1] = prevSeg + seg;
79
+ continue;
80
+ }
81
+ }
82
+ }
83
+ normalized.push(segments[i]);
84
+ }
85
+ const rebuilt = normalized.join(",");
86
+ const commaParts = rebuilt.split(",");
87
+ if (commaParts.length > 1) {
88
+ let numericCount = 0;
89
+ for (let j = commaParts.length - 1; j >= 0; j--) {
90
+ const part = normalizeNumericToken(commaParts[j].trim()) ?? commaParts[j].trim();
91
+ if (part && !isNaN(parseFloat(part)) && isFinite(Number(part))) {
92
+ numericCount++;
93
+ } else {
94
+ break;
95
+ }
96
+ }
97
+ if (numericCount > 0) {
98
+ const splitAt = commaParts.length - numericCount;
99
+ const extraValueParts = commaParts.slice(splitAt);
100
+ const firstPart = commaParts.slice(0, splitAt).join(",").trim();
101
+ const lastSpaceIdx = firstPart.lastIndexOf(" ");
102
+ if (lastSpaceIdx >= 0) {
103
+ const rawFirstVal = firstPart.substring(lastSpaceIdx + 1).trim();
104
+ const possibleFirstVal = normalizeNumericToken(rawFirstVal) ?? rawFirstVal;
105
+ if (possibleFirstVal && !isNaN(parseFloat(possibleFirstVal)) && isFinite(Number(possibleFirstVal))) {
106
+ const label2 = firstPart.substring(0, lastSpaceIdx).trim();
107
+ if (label2) {
108
+ const values = [parseFloat(possibleFirstVal)];
109
+ for (const p of extraValueParts) {
110
+ const normP = normalizeNumericToken(p.trim()) ?? p.trim();
111
+ values.push(parseFloat(normP));
112
+ }
113
+ return { label: label2, values };
114
+ }
115
+ }
116
+ }
117
+ }
118
+ }
119
+ const tokens = rebuilt.split(/\s+/);
120
+ if (tokens.length < 2) return null;
121
+ if (options?.multiValue) {
122
+ const limit = options.expectedValues ?? Infinity;
123
+ const values = [];
124
+ let idx = tokens.length - 1;
125
+ while (idx >= 1 && values.length < limit) {
126
+ const tok = tokens[idx];
127
+ const normTok = normalizeNumericToken(tok) ?? tok;
128
+ const num2 = parseFloat(normTok);
129
+ if (isNaN(num2) || !isFinite(Number(normTok))) break;
130
+ values.unshift(num2);
131
+ idx--;
132
+ }
133
+ if (values.length === 0) return null;
134
+ const label2 = tokens.slice(0, idx + 1).join(" ");
135
+ if (!label2) return null;
136
+ return { label: label2, values };
137
+ }
138
+ const lastToken = tokens[tokens.length - 1];
139
+ const normalizedLast = normalizeNumericToken(lastToken) ?? lastToken;
140
+ const num = parseFloat(normalizedLast);
141
+ if (isNaN(num) || !isFinite(Number(normalizedLast))) return null;
142
+ const label = tokens.slice(0, -1).join(" ");
143
+ if (!label) return null;
144
+ return { label, values: [num] };
145
+ }
146
+
147
+ // src/kanban/mutations.ts
148
+ var ARCHIVE_COLUMN_NAME = "archive";
149
+ function computeCardMove(content, parsed, cardId, targetColumnId, targetIndex) {
150
+ let sourceCard = null;
151
+ let sourceColumn = null;
152
+ for (const col of parsed.columns) {
153
+ for (const card of col.cards) {
154
+ if (card.id === cardId) {
155
+ sourceCard = card;
156
+ sourceColumn = col;
157
+ break;
158
+ }
159
+ }
160
+ if (sourceCard) break;
161
+ }
162
+ if (!sourceCard || !sourceColumn) return null;
163
+ const targetColumn = parsed.columns.find((c) => c.id === targetColumnId);
164
+ if (!targetColumn) return null;
165
+ const lines = content.split("\n");
166
+ const startIdx = sourceCard.lineNumber - 1;
167
+ const endIdx = sourceCard.endLineNumber - 1;
168
+ const cardLines = lines.slice(startIdx, endIdx + 1);
169
+ const withoutCard = [
170
+ ...lines.slice(0, startIdx),
171
+ ...lines.slice(endIdx + 1)
172
+ ];
173
+ let insertIdx;
174
+ const removedCount = endIdx - startIdx + 1;
175
+ const adjustLine = (ln) => {
176
+ if (ln > endIdx + 1) return ln - removedCount;
177
+ return ln;
178
+ };
179
+ if (targetIndex === 0) {
180
+ const adjColLine = adjustLine(targetColumn.lineNumber);
181
+ insertIdx = adjColLine;
182
+ } else {
183
+ const targetCards = targetColumn.cards.filter((c) => c.id !== cardId);
184
+ const clampedIdx = Math.min(targetIndex, targetCards.length);
185
+ const precedingCard = targetCards[clampedIdx - 1];
186
+ if (!precedingCard) {
187
+ const adjColLine = adjustLine(targetColumn.lineNumber);
188
+ insertIdx = adjColLine;
189
+ } else {
190
+ const adjEndLine = adjustLine(precedingCard.endLineNumber);
191
+ insertIdx = adjEndLine;
192
+ }
193
+ }
194
+ const result = [
195
+ ...withoutCard.slice(0, insertIdx),
196
+ ...cardLines,
197
+ ...withoutCard.slice(insertIdx)
198
+ ];
199
+ return result.join("\n");
200
+ }
201
+ function computeCardArchive(content, parsed, cardId) {
202
+ let sourceCard = null;
203
+ for (const col of parsed.columns) {
204
+ for (const card of col.cards) {
205
+ if (card.id === cardId) {
206
+ sourceCard = card;
207
+ break;
208
+ }
209
+ }
210
+ if (sourceCard) break;
211
+ }
212
+ if (!sourceCard) return null;
213
+ const lines = content.split("\n");
214
+ const startIdx = sourceCard.lineNumber - 1;
215
+ const endIdx = sourceCard.endLineNumber - 1;
216
+ const cardLines = lines.slice(startIdx, endIdx + 1);
217
+ const withoutCard = [
218
+ ...lines.slice(0, startIdx),
219
+ ...lines.slice(endIdx + 1)
220
+ ];
221
+ const archiveCol = parsed.columns.find(
222
+ (c) => c.name.toLowerCase() === ARCHIVE_COLUMN_NAME
223
+ );
224
+ if (archiveCol) {
225
+ const removedCount = endIdx - startIdx + 1;
226
+ let archiveEndLine = archiveCol.lineNumber;
227
+ if (archiveCol.cards.length > 0) {
228
+ const lastCard = archiveCol.cards[archiveCol.cards.length - 1];
229
+ archiveEndLine = lastCard.endLineNumber;
230
+ }
231
+ if (archiveEndLine > endIdx + 1) {
232
+ archiveEndLine -= removedCount;
233
+ }
234
+ const insertIdx = archiveEndLine;
235
+ return [
236
+ ...withoutCard.slice(0, insertIdx),
237
+ ...cardLines,
238
+ ...withoutCard.slice(insertIdx)
239
+ ].join("\n");
240
+ } else {
241
+ const trimmedEnd = withoutCard.length > 0 && withoutCard[withoutCard.length - 1].trim() === "" ? withoutCard : [...withoutCard, ""];
242
+ return [
243
+ ...trimmedEnd,
244
+ "[Archive]",
245
+ ...cardLines
246
+ ].join("\n");
247
+ }
248
+ }
249
+ function isArchiveColumn(name) {
250
+ return name.toLowerCase() === ARCHIVE_COLUMN_NAME;
251
+ }
252
+
253
+ // src/sequence/renderer.ts
254
+ var d3Selection = __toESM(require("d3-selection"), 1);
255
+
256
+ // src/sequence/parser.ts
257
+ function isSequenceBlock(el) {
258
+ return "kind" in el && el.kind === "block";
259
+ }
260
+ function isSequenceSection(el) {
261
+ return "kind" in el && el.kind === "section";
262
+ }
263
+ function isSequenceNote(el) {
264
+ return "kind" in el && el.kind === "note";
265
+ }
266
+
267
+ // src/sequence/renderer.ts
268
+ var PARTICIPANT_GAP = 160;
269
+ var PARTICIPANT_BOX_WIDTH = 120;
270
+ var NOTE_MAX_W = 200;
271
+ var NOTE_FOLD = 10;
272
+ var NOTE_PAD_H = 8;
273
+ var NOTE_GAP = 15;
274
+ var NOTE_CHAR_W = 6;
275
+ var NOTE_CHARS_PER_LINE = Math.floor(
276
+ (NOTE_MAX_W - NOTE_PAD_H * 2 - NOTE_FOLD) / NOTE_CHAR_W
277
+ );
278
+ var ACTIVATION_WIDTH = 10;
279
+ var NOTE_LANE_MAX = PARTICIPANT_GAP - ACTIVATION_WIDTH - NOTE_GAP;
280
+ var LABEL_CHAR_WIDTH = 7.5;
281
+ var LABEL_MAX_CHARS = Math.floor(
282
+ (PARTICIPANT_BOX_WIDTH - 10) / LABEL_CHAR_WIDTH
283
+ );
284
+ function groupMessagesBySection(elements, messages) {
285
+ const groups = [];
286
+ let currentGroup = null;
287
+ const collectIndices = (els) => {
288
+ const indices = [];
289
+ for (const el of els) {
290
+ if (isSequenceBlock(el)) {
291
+ indices.push(
292
+ ...collectIndices(el.children),
293
+ ...collectIndices(el.elseChildren)
294
+ );
295
+ if (el.elseIfBranches) {
296
+ for (const branch of el.elseIfBranches) {
297
+ indices.push(...collectIndices(branch.children));
298
+ }
299
+ }
300
+ } else if (isSequenceSection(el) || isSequenceNote(el)) {
301
+ continue;
302
+ } else {
303
+ const idx = messages.indexOf(el);
304
+ if (idx >= 0) indices.push(idx);
305
+ }
306
+ }
307
+ return indices;
308
+ };
309
+ for (const el of elements) {
310
+ if (isSequenceSection(el)) {
311
+ currentGroup = { section: el, messageIndices: [] };
312
+ groups.push(currentGroup);
313
+ } else if (currentGroup) {
314
+ if (isSequenceBlock(el)) {
315
+ currentGroup.messageIndices.push(...collectIndices([el]));
316
+ } else if (!isSequenceNote(el)) {
317
+ const idx = messages.indexOf(el);
318
+ if (idx >= 0) currentGroup.messageIndices.push(idx);
319
+ }
320
+ }
321
+ }
322
+ return groups;
323
+ }
324
+ function buildNoteMessageMap(elements) {
325
+ const map = /* @__PURE__ */ new Map();
326
+ let lastMessageLine = -1;
327
+ const walk = (els) => {
328
+ for (const el of els) {
329
+ if (isSequenceNote(el)) {
330
+ if (lastMessageLine >= 0) {
331
+ map.set(el.lineNumber, lastMessageLine);
332
+ }
333
+ } else if (isSequenceBlock(el)) {
334
+ walk(el.children);
335
+ if (el.elseIfBranches) {
336
+ for (const branch of el.elseIfBranches) {
337
+ walk(branch.children);
338
+ }
339
+ }
340
+ walk(el.elseChildren);
341
+ } else if (!isSequenceSection(el)) {
342
+ const msg = el;
343
+ lastMessageLine = msg.lineNumber;
344
+ }
345
+ }
346
+ };
347
+ walk(elements);
348
+ return map;
349
+ }
350
+ function collectNoteLineNumbers(elements) {
351
+ const result = [];
352
+ const walk = (els) => {
353
+ for (const el of els) {
354
+ if (isSequenceNote(el)) {
355
+ result.push(el.lineNumber);
356
+ } else if (isSequenceBlock(el)) {
357
+ walk(el.children);
358
+ if (el.elseIfBranches) {
359
+ for (const branch of el.elseIfBranches) {
360
+ walk(branch.children);
361
+ }
362
+ }
363
+ walk(el.elseChildren);
364
+ }
365
+ }
366
+ };
367
+ walk(elements);
368
+ return result;
369
+ }
370
+ // Annotate the CommonJS export names for ESM import in node:
371
+ 0 && (module.exports = {
372
+ buildNoteMessageMap,
373
+ collectNoteLineNumbers,
374
+ computeCardArchive,
375
+ computeCardMove,
376
+ groupMessagesBySection,
377
+ isArchiveColumn,
378
+ parseDataRowValues
379
+ });
380
+ //# sourceMappingURL=internal.cjs.map