schematex 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (194) hide show
  1. package/README.md +229 -40
  2. package/dist/api-bQZ98gkJ.d.cts +22 -0
  3. package/dist/api-bQZ98gkJ.d.ts +22 -0
  4. package/dist/browser.cjs +46 -0
  5. package/dist/browser.cjs.map +1 -0
  6. package/dist/browser.d.cts +27 -0
  7. package/dist/browser.d.ts +27 -0
  8. package/dist/browser.js +40 -0
  9. package/dist/browser.js.map +1 -0
  10. package/dist/{chunk-XXU36667.js → chunk-2OIW3MAE.js} +4 -3
  11. package/dist/chunk-2OIW3MAE.js.map +1 -0
  12. package/dist/{chunk-3FTUWAXK.cjs → chunk-3M7QWADF.cjs} +5 -4
  13. package/dist/chunk-3M7QWADF.cjs.map +1 -0
  14. package/dist/{chunk-BE5HNDA5.cjs → chunk-4HPT4BOI.cjs} +5 -4
  15. package/dist/{chunk-BE5HNDA5.cjs.map → chunk-4HPT4BOI.cjs.map} +1 -1
  16. package/dist/{chunk-CZRM7LT7.js → chunk-4TS5NB7L.js} +4 -3
  17. package/dist/chunk-4TS5NB7L.js.map +1 -0
  18. package/dist/{chunk-4G7ZIBHN.js → chunk-5SH5NUDW.js} +3 -2
  19. package/dist/{chunk-4G7ZIBHN.js.map → chunk-5SH5NUDW.js.map} +1 -1
  20. package/dist/{chunk-47ZC6EMJ.js → chunk-7WXAAVR3.js} +4 -3
  21. package/dist/{chunk-47ZC6EMJ.js.map → chunk-7WXAAVR3.js.map} +1 -1
  22. package/dist/{chunk-5C7DPDHQ.js → chunk-A74ZCP5I.js} +4 -3
  23. package/dist/{chunk-5C7DPDHQ.js.map → chunk-A74ZCP5I.js.map} +1 -1
  24. package/dist/{chunk-DS47NTWZ.cjs → chunk-AMP2FFES.cjs} +11 -10
  25. package/dist/chunk-AMP2FFES.cjs.map +1 -0
  26. package/dist/{chunk-2UKC6ZCY.cjs → chunk-CEV3GZA3.cjs} +12 -11
  27. package/dist/chunk-CEV3GZA3.cjs.map +1 -0
  28. package/dist/{chunk-NYCIK4SU.cjs → chunk-DTMCQXXC.cjs} +13 -12
  29. package/dist/chunk-DTMCQXXC.cjs.map +1 -0
  30. package/dist/{chunk-FDLZEKEB.js → chunk-GEPBET4L.js} +3 -2
  31. package/dist/chunk-GEPBET4L.js.map +1 -0
  32. package/dist/chunk-HAIBAF6J.cjs +1880 -0
  33. package/dist/chunk-HAIBAF6J.cjs.map +1 -0
  34. package/dist/{chunk-FGPTCDUT.cjs → chunk-HKRYKEOV.cjs} +5 -4
  35. package/dist/chunk-HKRYKEOV.cjs.map +1 -0
  36. package/dist/{chunk-D4JTSPOL.js → chunk-HLYA4QBB.js} +4 -3
  37. package/dist/chunk-HLYA4QBB.js.map +1 -0
  38. package/dist/{chunk-URSKIHSY.cjs → chunk-IMHR3S5H.cjs} +6 -5
  39. package/dist/chunk-IMHR3S5H.cjs.map +1 -0
  40. package/dist/{chunk-U4I37IBN.js → chunk-IQIJ6WW6.js} +4 -3
  41. package/dist/chunk-IQIJ6WW6.js.map +1 -0
  42. package/dist/{chunk-UHLYS3W5.cjs → chunk-IY52OWPG.cjs} +5 -4
  43. package/dist/{chunk-UHLYS3W5.cjs.map → chunk-IY52OWPG.cjs.map} +1 -1
  44. package/dist/chunk-JZGFSRVT.js +1873 -0
  45. package/dist/chunk-JZGFSRVT.js.map +1 -0
  46. package/dist/{chunk-3J7TFUOC.js → chunk-L6IHSTPP.js} +4 -3
  47. package/dist/{chunk-3J7TFUOC.js.map → chunk-L6IHSTPP.js.map} +1 -1
  48. package/dist/{chunk-4DBRNOPA.cjs → chunk-LKHWBDWZ.cjs} +5 -4
  49. package/dist/{chunk-4DBRNOPA.cjs.map → chunk-LKHWBDWZ.cjs.map} +1 -1
  50. package/dist/{chunk-34X3ZJ6E.cjs → chunk-LXNFVHDT.cjs} +3 -2
  51. package/dist/{chunk-34X3ZJ6E.cjs.map → chunk-LXNFVHDT.cjs.map} +1 -1
  52. package/dist/chunk-M6AMNXQ7.js +4539 -0
  53. package/dist/chunk-M6AMNXQ7.js.map +1 -0
  54. package/dist/{chunk-XX4BKS7Y.js → chunk-MRGS54WN.js} +4 -3
  55. package/dist/chunk-MRGS54WN.js.map +1 -0
  56. package/dist/{chunk-ROFLJ74T.js → chunk-MXJ6FHSY.js} +4 -3
  57. package/dist/chunk-MXJ6FHSY.js.map +1 -0
  58. package/dist/{chunk-V6WO7RK7.cjs → chunk-PIQG2Z5N.cjs} +5 -4
  59. package/dist/chunk-PIQG2Z5N.cjs.map +1 -0
  60. package/dist/{chunk-U5GGE6PJ.js → chunk-RQX53J6M.js} +4 -3
  61. package/dist/chunk-RQX53J6M.js.map +1 -0
  62. package/dist/{chunk-N7KOXOMX.cjs → chunk-S6VPECM3.cjs} +72 -2
  63. package/dist/chunk-S6VPECM3.cjs.map +1 -0
  64. package/dist/{chunk-VFQCTXOX.js → chunk-SPIW4VWP.js} +4 -3
  65. package/dist/chunk-SPIW4VWP.js.map +1 -0
  66. package/dist/{chunk-IX554O5K.js → chunk-TIGP2OEJ.js} +72 -3
  67. package/dist/chunk-TIGP2OEJ.js.map +1 -0
  68. package/dist/{chunk-LMFSHK45.js → chunk-TPA36ULU.js} +4 -3
  69. package/dist/{chunk-LMFSHK45.js.map → chunk-TPA36ULU.js.map} +1 -1
  70. package/dist/{chunk-ZX7QKZK2.cjs → chunk-ULERCTGS.cjs} +5 -4
  71. package/dist/{chunk-ZX7QKZK2.cjs.map → chunk-ULERCTGS.cjs.map} +1 -1
  72. package/dist/chunk-VP54YPOX.cjs +4544 -0
  73. package/dist/chunk-VP54YPOX.cjs.map +1 -0
  74. package/dist/{chunk-XQ52ICHU.cjs → chunk-YKO7DY2F.cjs} +14 -13
  75. package/dist/chunk-YKO7DY2F.cjs.map +1 -0
  76. package/dist/{chunk-PDPHRZZT.js → chunk-YO4GU6JX.js} +4 -3
  77. package/dist/chunk-YO4GU6JX.js.map +1 -0
  78. package/dist/{chunk-S6BK5DB6.cjs → chunk-ZGKEFVJQ.cjs} +13 -12
  79. package/dist/chunk-ZGKEFVJQ.cjs.map +1 -0
  80. package/dist/{chunk-2MQWZ2XY.cjs → chunk-ZO77FHBF.cjs} +3 -2
  81. package/dist/chunk-ZO77FHBF.cjs.map +1 -0
  82. package/dist/diagrams/blockdiagram/index.cjs +5 -5
  83. package/dist/diagrams/blockdiagram/index.d.cts +1 -1
  84. package/dist/diagrams/blockdiagram/index.d.ts +1 -1
  85. package/dist/diagrams/blockdiagram/index.js +1 -1
  86. package/dist/diagrams/circuit/index.cjs +8 -8
  87. package/dist/diagrams/circuit/index.d.cts +1 -1
  88. package/dist/diagrams/circuit/index.d.ts +1 -1
  89. package/dist/diagrams/circuit/index.js +2 -2
  90. package/dist/diagrams/ecomap/index.cjs +7 -7
  91. package/dist/diagrams/ecomap/index.d.cts +1 -1
  92. package/dist/diagrams/ecomap/index.d.ts +1 -1
  93. package/dist/diagrams/ecomap/index.js +2 -2
  94. package/dist/diagrams/entity/index.cjs +6 -6
  95. package/dist/diagrams/entity/index.d.cts +1 -1
  96. package/dist/diagrams/entity/index.d.ts +1 -1
  97. package/dist/diagrams/entity/index.js +2 -2
  98. package/dist/diagrams/fishbone/index.cjs +8 -8
  99. package/dist/diagrams/fishbone/index.d.cts +9 -9
  100. package/dist/diagrams/fishbone/index.d.ts +9 -9
  101. package/dist/diagrams/fishbone/index.js +2 -2
  102. package/dist/diagrams/flowchart/index.cjs +8 -8
  103. package/dist/diagrams/flowchart/index.d.cts +2 -2
  104. package/dist/diagrams/flowchart/index.d.ts +2 -2
  105. package/dist/diagrams/flowchart/index.js +2 -2
  106. package/dist/diagrams/genogram/index.cjs +9 -9
  107. package/dist/diagrams/genogram/index.d.cts +1 -1
  108. package/dist/diagrams/genogram/index.d.ts +1 -1
  109. package/dist/diagrams/genogram/index.js +2 -2
  110. package/dist/diagrams/ladder/index.cjs +6 -6
  111. package/dist/diagrams/ladder/index.d.cts +1 -1
  112. package/dist/diagrams/ladder/index.d.ts +1 -1
  113. package/dist/diagrams/ladder/index.js +2 -2
  114. package/dist/diagrams/logic/index.cjs +6 -6
  115. package/dist/diagrams/logic/index.d.cts +1 -1
  116. package/dist/diagrams/logic/index.d.ts +1 -1
  117. package/dist/diagrams/logic/index.js +2 -2
  118. package/dist/diagrams/orgchart/index.cjs +7 -7
  119. package/dist/diagrams/orgchart/index.d.cts +1 -1
  120. package/dist/diagrams/orgchart/index.d.ts +1 -1
  121. package/dist/diagrams/orgchart/index.js +2 -2
  122. package/dist/diagrams/pedigree/index.cjs +7 -7
  123. package/dist/diagrams/pedigree/index.d.cts +1 -1
  124. package/dist/diagrams/pedigree/index.d.ts +1 -1
  125. package/dist/diagrams/pedigree/index.js +2 -2
  126. package/dist/diagrams/phylo/index.cjs +7 -7
  127. package/dist/diagrams/phylo/index.d.cts +1 -1
  128. package/dist/diagrams/phylo/index.d.ts +1 -1
  129. package/dist/diagrams/phylo/index.js +2 -2
  130. package/dist/diagrams/sld/index.cjs +6 -6
  131. package/dist/diagrams/sld/index.d.cts +1 -1
  132. package/dist/diagrams/sld/index.d.ts +1 -1
  133. package/dist/diagrams/sld/index.js +2 -2
  134. package/dist/diagrams/sociogram/index.cjs +6 -6
  135. package/dist/diagrams/sociogram/index.d.cts +1 -1
  136. package/dist/diagrams/sociogram/index.d.ts +1 -1
  137. package/dist/diagrams/sociogram/index.js +2 -2
  138. package/dist/diagrams/timing/index.cjs +4 -4
  139. package/dist/diagrams/timing/index.d.cts +1 -1
  140. package/dist/diagrams/timing/index.d.ts +1 -1
  141. package/dist/diagrams/timing/index.js +1 -1
  142. package/dist/diagrams/venn/index.cjs +9 -9
  143. package/dist/diagrams/venn/index.d.cts +1 -1
  144. package/dist/diagrams/venn/index.d.ts +1 -1
  145. package/dist/diagrams/venn/index.js +2 -2
  146. package/dist/export.cjs +87 -0
  147. package/dist/export.cjs.map +1 -0
  148. package/dist/export.d.cts +38 -0
  149. package/dist/export.d.ts +38 -0
  150. package/dist/export.js +83 -0
  151. package/dist/export.js.map +1 -0
  152. package/dist/{index-BXefHVce.d.cts → index-SSGpCggE.d.cts} +52 -3
  153. package/dist/{index-BSlza1YY.d.ts → index-ga04CTBI.d.ts} +52 -3
  154. package/dist/index.cjs +65 -1948
  155. package/dist/index.cjs.map +1 -1
  156. package/dist/index.d.cts +7 -12
  157. package/dist/index.d.ts +7 -12
  158. package/dist/index.js +19 -1942
  159. package/dist/index.js.map +1 -1
  160. package/dist/react.cjs +56 -0
  161. package/dist/react.cjs.map +1 -0
  162. package/dist/react.d.cts +24 -0
  163. package/dist/react.d.ts +24 -0
  164. package/dist/react.js +54 -0
  165. package/dist/react.js.map +1 -0
  166. package/dist/{types-DqfcYkcY.d.ts → types-BcPhMdHd.d.cts} +6 -2
  167. package/dist/{types-DqfcYkcY.d.cts → types-BcPhMdHd.d.ts} +6 -2
  168. package/package.json +31 -2
  169. package/dist/chunk-2MQWZ2XY.cjs.map +0 -1
  170. package/dist/chunk-2UKC6ZCY.cjs.map +0 -1
  171. package/dist/chunk-3FTUWAXK.cjs.map +0 -1
  172. package/dist/chunk-ADOXGKAK.js +0 -1251
  173. package/dist/chunk-ADOXGKAK.js.map +0 -1
  174. package/dist/chunk-CZRM7LT7.js.map +0 -1
  175. package/dist/chunk-D4JTSPOL.js.map +0 -1
  176. package/dist/chunk-DS47NTWZ.cjs.map +0 -1
  177. package/dist/chunk-FDLZEKEB.js.map +0 -1
  178. package/dist/chunk-FGPTCDUT.cjs.map +0 -1
  179. package/dist/chunk-IX554O5K.js.map +0 -1
  180. package/dist/chunk-MDICUK6F.cjs +0 -1258
  181. package/dist/chunk-MDICUK6F.cjs.map +0 -1
  182. package/dist/chunk-N7KOXOMX.cjs.map +0 -1
  183. package/dist/chunk-NYCIK4SU.cjs.map +0 -1
  184. package/dist/chunk-PDPHRZZT.js.map +0 -1
  185. package/dist/chunk-ROFLJ74T.js.map +0 -1
  186. package/dist/chunk-S6BK5DB6.cjs.map +0 -1
  187. package/dist/chunk-U4I37IBN.js.map +0 -1
  188. package/dist/chunk-U5GGE6PJ.js.map +0 -1
  189. package/dist/chunk-URSKIHSY.cjs.map +0 -1
  190. package/dist/chunk-V6WO7RK7.cjs.map +0 -1
  191. package/dist/chunk-VFQCTXOX.js.map +0 -1
  192. package/dist/chunk-XQ52ICHU.cjs.map +0 -1
  193. package/dist/chunk-XX4BKS7Y.js.map +0 -1
  194. package/dist/chunk-XXU36667.js.map +0 -1
package/dist/index.js CHANGED
@@ -1,1944 +1,21 @@
1
- import { orgchart } from './chunk-47ZC6EMJ.js';
2
- export { orgchart } from './chunk-47ZC6EMJ.js';
3
- import { circuit } from './chunk-XXU36667.js';
4
- export { circuit } from './chunk-XXU36667.js';
5
- import { blockdiagram } from './chunk-4G7ZIBHN.js';
6
- export { blockdiagram } from './chunk-4G7ZIBHN.js';
7
- import { ladder } from './chunk-3J7TFUOC.js';
8
- export { ladder } from './chunk-3J7TFUOC.js';
9
- import { sld } from './chunk-5C7DPDHQ.js';
10
- export { sld } from './chunk-5C7DPDHQ.js';
11
- import { entity } from './chunk-XX4BKS7Y.js';
12
- export { entity } from './chunk-XX4BKS7Y.js';
13
- import { fishbone } from './chunk-U4I37IBN.js';
14
- export { fishbone } from './chunk-U4I37IBN.js';
15
- import { venn } from './chunk-ROFLJ74T.js';
16
- export { venn } from './chunk-ROFLJ74T.js';
17
- import { flowchart } from './chunk-ADOXGKAK.js';
18
- export { flowchart } from './chunk-ADOXGKAK.js';
19
- import { genogram } from './chunk-D4JTSPOL.js';
20
- export { genogram } from './chunk-D4JTSPOL.js';
21
- import { ecomap } from './chunk-U5GGE6PJ.js';
22
- export { ecomap } from './chunk-U5GGE6PJ.js';
23
- import { pedigree } from './chunk-LMFSHK45.js';
24
- export { pedigree } from './chunk-LMFSHK45.js';
25
- import { phylo } from './chunk-CZRM7LT7.js';
26
- export { phylo } from './chunk-CZRM7LT7.js';
27
- import { sociogram } from './chunk-PDPHRZZT.js';
28
- export { sociogram } from './chunk-PDPHRZZT.js';
29
- import { timing } from './chunk-FDLZEKEB.js';
30
- export { timing } from './chunk-FDLZEKEB.js';
31
- import { logic } from './chunk-VFQCTXOX.js';
32
- export { logic } from './chunk-VFQCTXOX.js';
33
- import { resolveMindmapTheme } from './chunk-IX554O5K.js';
34
- export { BASE_THEMES, BIOLOGY_TOKENS, PERSON_TOKENS, VENN_TOKENS, resolveBaseTheme, resolveBiologyTheme, resolveFishboneTheme, resolveGenogramTheme, resolvePersonTheme, resolveVennTheme } from './chunk-IX554O5K.js';
35
- import { path, svgRoot, escapeXml, title, desc, rect, group, defs, el, text, line, circle, polygon } from './chunk-KLJEK547.js';
36
-
37
- // src/diagrams/mindmap/parser.ts
38
- var VALID_STYLES = ["map", "logic-right"];
39
- function parseDirective(line2, out) {
40
- const body = line2.replace(/^%%\s*/, "").trim();
41
- const idx = body.indexOf(":");
42
- if (idx < 0) return;
43
- const key = body.slice(0, idx).trim().toLowerCase();
44
- const val = body.slice(idx + 1).trim();
45
- if (key === "style" && VALID_STYLES.includes(val)) {
46
- out.style = val;
47
- } else if (key === "theme") {
48
- out.themeOverride = val;
49
- }
50
- }
51
- function parseMindmap(text2) {
52
- const lines = text2.split(/\r?\n/);
53
- if (lines[0]?.trim().toLowerCase() === "mindmap") lines.shift();
54
- const directives = { style: "map" };
55
- let root = null;
56
- let idCounter = 0;
57
- const nextId = () => `n${idCounter++}`;
58
- const stack = [];
59
- let lastHeadingDepth = 0;
60
- const attach = (node, depth) => {
61
- while (stack.length && stack[stack.length - 1].depth >= depth) stack.pop();
62
- const parent = stack[stack.length - 1]?.node;
63
- if (!parent) throw new Error("Mindmap: orphan node \u2014 expected root # heading first");
64
- node.depth = parent.depth + 1;
65
- parent.children.push(node);
66
- stack.push({ node, depth });
67
- };
68
- for (const raw of lines) {
69
- const line2 = raw.replace(/\s+$/, "");
70
- const trimmed = line2.trim();
71
- if (!trimmed) continue;
72
- if (trimmed.startsWith("%%")) {
73
- parseDirective(trimmed, directives);
74
- continue;
75
- }
76
- const heading = line2.match(/^\s*(#{1,6})\s+(.+)$/);
77
- if (heading) {
78
- const depth = heading[1].length - 1;
79
- const label = heading[2].trim();
80
- const node = { id: nextId(), label, depth, children: [] };
81
- if (depth === 0) {
82
- if (root) throw new Error("Mindmap: multiple `#` center nodes not allowed");
83
- root = node;
84
- stack.length = 0;
85
- stack.push({ node, depth: 0 });
86
- } else {
87
- attach(node, depth);
88
- }
89
- lastHeadingDepth = depth;
90
- continue;
91
- }
92
- const bullet = line2.match(/^(\s*)[-*+]\s+(.+)$/);
93
- if (bullet) {
94
- const indent = bullet[1].length;
95
- const depth = lastHeadingDepth + 1 + Math.floor(indent / 2);
96
- const label = bullet[2].trim();
97
- const node = { id: nextId(), label, depth, children: [] };
98
- attach(node, depth);
99
- continue;
100
- }
101
- }
102
- if (!root) throw new Error("Mindmap: missing central topic \u2014 start with `# Title`");
103
- const ast = {
104
- type: "mindmap",
105
- style: directives.style,
106
- root
107
- };
108
- if (directives.themeOverride) ast.themeOverride = directives.themeOverride;
109
- return ast;
110
- }
111
-
112
- // src/diagrams/mindmap/layout.ts
113
- var PADDING = 40;
114
- var SIBLING_GAP = 20;
115
- var MAIN_GAP = 44;
116
- var ROOT_CAPSULE_PAD_X = 10;
117
- var ROOT_CAPSULE_PAD_Y = 10;
118
- function bezierGapFor(childDepth) {
119
- if (childDepth <= 1) return 90;
120
- if (childDepth === 2) return 60;
121
- return 45;
122
- }
123
- var FONT_CENTRAL = 20;
124
- var FONT_MAIN = 15;
125
- var FONT_SUB = 13;
126
- function fontSizeOf(depth) {
127
- if (depth === 0) return FONT_CENTRAL;
128
- if (depth === 1) return FONT_MAIN;
129
- return FONT_SUB;
130
- }
131
- function estimateLabelWidth(label, depth) {
132
- return Math.max(32, label.length * fontSizeOf(depth) * 0.58);
133
- }
134
- function rowHeightOf(depth) {
135
- return fontSizeOf(depth) + 14;
136
- }
137
- function computeColumns(subtreeRoots, firstColStartX) {
138
- const maxLW = [];
139
- const walk = (n) => {
140
- const lw = estimateLabelWidth(n.label, n.depth);
141
- if (maxLW[n.depth] === void 0 || lw > maxLW[n.depth]) maxLW[n.depth] = lw;
142
- for (const c of n.children) walk(c);
143
- };
144
- for (const r of subtreeRoots) walk(r);
145
- const center = [];
146
- if (subtreeRoots.length === 0) return { center };
147
- const rootDepth = subtreeRoots[0].depth;
148
- let slotLeft = firstColStartX;
149
- center[rootDepth] = slotLeft + maxLW[rootDepth] / 2;
150
- for (let d = rootDepth + 1; d < maxLW.length; d++) {
151
- slotLeft = slotLeft + maxLW[d - 1] + bezierGapFor(d);
152
- center[d] = slotLeft + maxLW[d] / 2;
153
- }
154
- return { center };
155
- }
156
- function tidyRight(node, yTop, branchIdx, columns, out) {
157
- const rowH = rowHeightOf(node.depth);
158
- const lw = estimateLabelWidth(node.label, node.depth);
159
- const x = columns.center[node.depth];
160
- if (node.children.length === 0) {
161
- const ln2 = {
162
- node,
163
- x,
164
- y: yTop + rowH / 2,
165
- side: "right",
166
- branchIndex: branchIdx,
167
- labelWidth: lw,
168
- labelHeight: rowH
169
- };
170
- out.push(ln2);
171
- return { layoutNode: ln2, height: rowH };
172
- }
173
- let cursor = yTop;
174
- const childLayouts = [];
175
- for (let i = 0; i < node.children.length; i++) {
176
- if (i > 0) cursor += SIBLING_GAP;
177
- const { layoutNode: cln, height } = tidyRight(
178
- node.children[i],
179
- cursor,
180
- branchIdx,
181
- columns,
182
- out
183
- );
184
- childLayouts.push(cln);
185
- cursor += height;
186
- }
187
- const totalH = Math.max(rowH, cursor - yTop);
188
- const firstY = childLayouts[0].y;
189
- const lastY = childLayouts[childLayouts.length - 1].y;
190
- const parentY = (firstY + lastY) / 2;
191
- const ln = {
192
- node,
193
- x,
194
- y: parentY,
195
- side: "right",
196
- branchIndex: branchIdx,
197
- labelWidth: lw,
198
- labelHeight: rowH
199
- };
200
- out.push(ln);
201
- return { layoutNode: ln, height: totalH };
202
- }
203
- function labelEdgeX(n, outward) {
204
- if (n.side === "center") return n.x;
205
- const dir = n.side === "left" ? -1 : 1;
206
- return n.x + (outward ? dir : -dir) * n.labelWidth / 2;
207
- }
208
- function bezierH(x1, y1, x2, y2) {
209
- const k = (x2 - x1) * 0.55;
210
- return `M ${x1.toFixed(1)} ${y1.toFixed(1)} C ${(x1 + k).toFixed(1)} ${y1.toFixed(1)}, ${(x2 - k).toFixed(1)} ${y2.toFixed(1)}, ${x2.toFixed(1)} ${y2.toFixed(1)}`;
211
- }
212
- function edgeWidthFor(depth) {
213
- return depth <= 1 ? 2.2 : 1.4;
214
- }
215
- function normalize(nodes) {
216
- let minX = Infinity, minY = Infinity, maxX = -Infinity, maxY = -Infinity;
217
- for (const n of nodes) {
218
- const lw = n.labelWidth;
219
- const lh = n.labelHeight;
220
- const leftX = n.x - lw / 2;
221
- const rightX = n.x + lw / 2;
222
- minX = Math.min(minX, leftX);
223
- maxX = Math.max(maxX, rightX);
224
- minY = Math.min(minY, n.y - lh);
225
- maxY = Math.max(maxY, n.y + lh);
226
- }
227
- const dx = PADDING - minX;
228
- const dy = PADDING - minY;
229
- for (const n of nodes) {
230
- n.x += dx;
231
- n.y += dy;
232
- }
233
- return { width: maxX - minX + PADDING * 2, height: maxY - minY + PADDING * 2 };
234
- }
235
- function buildEdges(root, byId) {
236
- const edges = [];
237
- const walk = (parent) => {
238
- const pln = byId.get(parent.id);
239
- for (const c of parent.children) {
240
- const cln = byId.get(c.id);
241
- let fromX;
242
- if (pln.side === "center") {
243
- const halfW = pln.labelWidth / 2;
244
- fromX = cln.side === "left" ? pln.x - halfW : pln.x + halfW;
245
- } else {
246
- fromX = labelEdgeX(pln, true);
247
- }
248
- const toX = labelEdgeX(cln, false);
249
- edges.push({
250
- from: parent.id,
251
- to: c.id,
252
- path: bezierH(fromX, pln.y, toX, cln.y),
253
- color: "",
254
- width: edgeWidthFor(c.depth)
255
- });
256
- walk(c);
257
- }
258
- };
259
- walk(root);
260
- return edges;
261
- }
262
- function layoutMap(ast) {
263
- const root = ast.root;
264
- const mains = root.children;
265
- const rightCount = Math.ceil(mains.length / 2);
266
- const rightMains = mains.slice(0, rightCount);
267
- const leftMains = mains.slice(rightCount);
268
- const nodes = [];
269
- const rootLabelW = estimateLabelWidth(root.label, 0);
270
- const rootCapsuleW = rootLabelW + ROOT_CAPSULE_PAD_X * 2;
271
- const rootCapsuleH = rowHeightOf(0) + ROOT_CAPSULE_PAD_Y;
272
- const firstColLeft = rootCapsuleW / 2 + bezierGapFor(1);
273
- const rightCols = computeColumns(rightMains, firstColLeft);
274
- let rightCursor = 0;
275
- for (let i = 0; i < rightMains.length; i++) {
276
- if (i > 0) rightCursor += MAIN_GAP;
277
- const { height: height2 } = tidyRight(rightMains[i], rightCursor, i, rightCols, nodes);
278
- rightCursor += height2;
279
- }
280
- const rightHeight = rightCursor;
281
- const leftCols = computeColumns(leftMains, firstColLeft);
282
- const leftStart = nodes.length;
283
- let leftCursor = 0;
284
- for (let i = 0; i < leftMains.length; i++) {
285
- if (i > 0) leftCursor += MAIN_GAP;
286
- const { height: height2 } = tidyRight(leftMains[i], leftCursor, rightCount + i, leftCols, nodes);
287
- leftCursor += height2;
288
- }
289
- const leftHeight = leftCursor;
290
- for (let k = leftStart; k < nodes.length; k++) {
291
- nodes[k].x = -nodes[k].x;
292
- nodes[k].side = "left";
293
- }
294
- const rootY = Math.max(rightHeight, leftHeight) / 2;
295
- const rootNode = {
296
- node: root,
297
- x: 0,
298
- y: rootY,
299
- side: "center",
300
- branchIndex: -1,
301
- labelWidth: rootCapsuleW,
302
- labelHeight: rootCapsuleH
303
- };
304
- nodes.push(rootNode);
305
- const { width, height } = normalize(nodes);
306
- const byId = new Map(nodes.map((n) => [n.node.id, n]));
307
- const edges = buildEdges(root, byId);
308
- return { width, height, style: "map", nodes, edges, title: ast.title };
309
- }
310
- function layoutLogicRight(ast) {
311
- const root = ast.root;
312
- const nodes = [];
313
- const rootLabelW = estimateLabelWidth(root.label, 0);
314
- const rootCapsuleW = rootLabelW + ROOT_CAPSULE_PAD_X * 2;
315
- const rootCapsuleH = rowHeightOf(0) + ROOT_CAPSULE_PAD_Y;
316
- const firstColLeft = rootCapsuleW / 2 + bezierGapFor(1);
317
- const cols = computeColumns(root.children, firstColLeft);
318
- let cursor = 0;
319
- for (let i = 0; i < root.children.length; i++) {
320
- if (i > 0) cursor += MAIN_GAP;
321
- const { height: height2 } = tidyRight(root.children[i], cursor, i, cols, nodes);
322
- cursor += height2;
323
- }
324
- const totalHeight = cursor;
325
- const rootNode = {
326
- node: root,
327
- x: 0,
328
- y: totalHeight / 2,
329
- side: "center",
330
- branchIndex: -1,
331
- labelWidth: rootCapsuleW,
332
- labelHeight: rootCapsuleH
333
- };
334
- nodes.push(rootNode);
335
- const { width, height } = normalize(nodes);
336
- const byId = new Map(nodes.map((n) => [n.node.id, n]));
337
- const edges = buildEdges(root, byId);
338
- return { width, height, style: "logic-right", nodes, edges, title: ast.title };
339
- }
340
- function layoutMindmap(ast) {
341
- const style = ast.style;
342
- if (style === "logic-right") return layoutLogicRight(ast);
343
- return layoutMap(ast);
344
- }
345
-
346
- // src/diagrams/mindmap/renderer.ts
347
- var UNDERLINE_MAIN = 2.2;
348
- var UNDERLINE_MAIN_MONO = 1.5;
349
- function paletteColor(theme, branchIndex) {
350
- if (branchIndex < 0) return theme.centralFill;
351
- return theme.branchPalette[branchIndex % theme.branchPalette.length];
352
- }
353
- function underlineMain(theme) {
354
- return theme.branchPalette.length <= 1 ? UNDERLINE_MAIN_MONO : UNDERLINE_MAIN;
355
- }
356
- function renderCentral(n, theme, fontFamily) {
357
- const fs = fontSizeOf(0);
358
- const pillW = n.labelWidth;
359
- const pillH = n.labelHeight;
360
- return group(
361
- { class: "schematex-mindmap-central", "data-node-id": n.node.id },
362
- [
363
- rect({
364
- x: n.x - pillW / 2,
365
- y: n.y - pillH / 2,
366
- width: pillW,
367
- height: pillH,
368
- rx: pillH / 2,
369
- ry: pillH / 2,
370
- fill: "none",
371
- stroke: theme.textMuted,
372
- "stroke-width": underlineMain(theme)
373
- }),
374
- text(
375
- {
376
- x: n.x,
377
- y: n.y + fs * 0.35,
378
- "text-anchor": "middle",
379
- "font-family": fontFamily,
380
- "font-size": fs,
381
- "font-weight": 700,
382
- fill: theme.text
383
- },
384
- n.node.label
385
- )
386
- ]
387
- );
388
- }
389
- function renderBranchNode(n, color, theme, fontFamily) {
390
- const isMain = n.node.depth === 1;
391
- const fs = fontSizeOf(n.node.depth);
392
- const tx = n.x;
393
- const ty = isMain ? n.y - 3 : n.y + fs * 0.35;
394
- const ux1 = n.x - n.labelWidth / 2;
395
- const ux2 = n.x + n.labelWidth / 2;
396
- const uy = n.y;
397
- const children = [
398
- text(
399
- {
400
- x: tx,
401
- y: ty,
402
- "text-anchor": "middle",
403
- "font-family": fontFamily,
404
- "font-size": fs,
405
- "font-weight": isMain ? 600 : 400,
406
- fill: theme.text
407
- },
408
- n.node.label
409
- )
410
- ];
411
- if (isMain) {
412
- children.push(
413
- el("line", {
414
- x1: ux1,
415
- y1: uy,
416
- x2: ux2,
417
- y2: uy,
418
- stroke: color,
419
- "stroke-width": underlineMain(theme),
420
- "stroke-linecap": "round"
421
- })
422
- );
423
- }
424
- return group(
425
- {
426
- class: isMain ? "schematex-mindmap-main" : "schematex-mindmap-leaf",
427
- "data-node-id": n.node.id,
428
- "data-depth": n.node.depth,
429
- "data-branch-idx": n.branchIndex
430
- },
431
- children
432
- );
433
- }
434
- function renderMindmapAST(ast, themeName = "default", fontFamily = "system-ui, -apple-system, sans-serif") {
435
- const theme = resolveMindmapTheme(ast.themeOverride ?? themeName);
436
- const layout = layoutMindmap(ast);
437
- const byId = new Map(layout.nodes.map((n) => [n.node.id, n]));
438
- const edgeSvgs = [];
439
- for (const e of layout.edges) {
440
- const target = byId.get(e.to);
441
- if (!target) continue;
442
- const color = paletteColor(theme, target.branchIndex);
443
- edgeSvgs.push(
444
- path({
445
- d: e.path,
446
- fill: "none",
447
- stroke: color,
448
- "stroke-width": e.width,
449
- "stroke-linecap": "round"
450
- })
451
- );
452
- }
453
- const nodeSvgs = [];
454
- for (const n of layout.nodes) {
455
- if (n.node.depth === 0) {
456
- nodeSvgs.push(renderCentral(n, theme, fontFamily));
457
- } else {
458
- nodeSvgs.push(
459
- renderBranchNode(n, paletteColor(theme, n.branchIndex), theme, fontFamily)
460
- );
461
- }
462
- }
463
- const title2 = ast.title ?? ast.root.label;
464
- return svgRoot(
465
- {
466
- viewBox: `0 0 ${layout.width.toFixed(1)} ${layout.height.toFixed(1)}`,
467
- width: layout.width.toFixed(1),
468
- height: layout.height.toFixed(1),
469
- role: "graphics-document",
470
- "aria-label": `Mindmap: ${escapeXml(title2)}`
471
- },
472
- [
473
- title(title2),
474
- desc(`${layout.style} mindmap with ${layout.nodes.length} nodes`),
475
- rect({ x: 0, y: 0, width: layout.width, height: layout.height, fill: theme.bg }),
476
- group({ class: "schematex-mindmap-edges", "aria-hidden": "true" }, edgeSvgs),
477
- group({ class: "schematex-mindmap-nodes" }, nodeSvgs)
478
- ]
479
- );
480
- }
481
- function renderMindmap(text2, opts) {
482
- const ast = parseMindmap(text2);
483
- return renderMindmapAST(ast, opts?.theme, opts?.fontFamily);
484
- }
485
-
486
- // src/diagrams/mindmap/index.ts
487
- var mindmap = {
488
- type: "mindmap",
489
- detect(text2) {
490
- const lines = text2.trim().split("\n");
491
- const first = lines[0]?.trim().toLowerCase() ?? "";
492
- if (first.startsWith("mindmap")) return true;
493
- for (const ln of lines) {
494
- const t = ln.trim();
495
- if (!t) continue;
496
- if (t.startsWith("%%")) continue;
497
- return /^#\s+\S/.test(t);
498
- }
499
- return false;
500
- },
501
- render(text2, config) {
502
- return renderMindmap(text2, {
503
- theme: config?.theme,
504
- fontFamily: config?.fontFamily
505
- });
506
- }
507
- };
508
-
509
- // src/diagrams/matrix/templates.ts
510
- var TEMPLATES = {
511
- "eisenhower": {
512
- grid: "2x2",
513
- xAxis: { low: "Urgent", high: "Not Urgent" },
514
- yAxis: { low: "Not Important", high: "Important" },
515
- annotations: [
516
- { q: 1, label: "Schedule" },
517
- { q: 2, label: "Do First" },
518
- { q: 3, label: "Delete" },
519
- { q: 4, label: "Delegate" }
520
- ]
521
- },
522
- "impact-effort": {
523
- grid: "2x2",
524
- xAxis: { low: "Low Effort", high: "High Effort" },
525
- yAxis: { low: "Low Impact", high: "High Impact" },
526
- annotations: [
527
- { q: 1, label: "Major Projects" },
528
- { q: 2, label: "Quick Wins" },
529
- { q: 3, label: "Fill-ins" },
530
- { q: 4, label: "Thankless" }
531
- ]
532
- },
533
- "rice": {
534
- grid: "2x2",
535
- xAxis: { low: "Low Effort", high: "High Effort" },
536
- yAxis: { low: "Low Reach \xD7 Impact", high: "High Reach \xD7 Impact" },
537
- annotations: [
538
- { q: 1, label: "Strategic Bets" },
539
- { q: 2, label: "High RICE" },
540
- { q: 3, label: "Backlog" },
541
- { q: 4, label: "Reconsider" }
542
- ]
543
- },
544
- "bcg": {
545
- grid: "2x2",
546
- // BCG convention: high market share on left (x-axis reversed)
547
- xAxis: { low: "High Market Share", high: "Low Market Share" },
548
- yAxis: { low: "Low Growth", high: "High Growth" },
549
- annotations: [
550
- { q: 1, label: "Question Marks" },
551
- { q: 2, label: "Stars" },
552
- { q: 3, label: "Cash Cows" },
553
- { q: 4, label: "Dogs" }
554
- ]
555
- },
556
- "ansoff": {
557
- grid: "2x2",
558
- xAxis: { low: "Existing Products", high: "New Products" },
559
- yAxis: { low: "Existing Markets", high: "New Markets" },
560
- annotations: [
561
- { q: 1, label: "Diversification" },
562
- { q: 2, label: "Market Development" },
563
- { q: 3, label: "Market Penetration" },
564
- { q: 4, label: "Product Development" }
565
- ]
566
- },
567
- "johari": {
568
- grid: "2x2",
569
- xAxis: { low: "Known to Self", high: "Not Known to Self" },
570
- yAxis: { low: "Not Known to Others", high: "Known to Others" },
571
- annotations: [
572
- { q: 1, label: "Blind" },
573
- { q: 2, label: "Open / Arena" },
574
- { q: 3, label: "Hidden / Fa\xE7ade" },
575
- { q: 4, label: "Unknown" }
576
- ]
577
- },
578
- "9-box": {
579
- grid: "3x3",
580
- cols: 3,
581
- rows: 3,
582
- xAxis: { low: "Low Performance", high: "High Performance" },
583
- yAxis: { low: "Low Potential", high: "High Potential" },
584
- cellLabels: [
585
- { col: 0, row: 2, label: "Enigma" },
586
- { col: 1, row: 2, label: "Growth Employee" },
587
- { col: 2, row: 2, label: "Future Leader" },
588
- { col: 0, row: 1, label: "Dilemma" },
589
- { col: 1, row: 1, label: "Core Player" },
590
- { col: 2, row: 1, label: "High Impact" },
591
- { col: 0, row: 0, label: "Under-performer" },
592
- { col: 1, row: 0, label: "Effective" },
593
- { col: 2, row: 0, label: "Trusted Pro" }
594
- ]
595
- },
596
- "risk-matrix": {
597
- grid: "NxM",
598
- mode: "heatmap",
599
- cols: 5,
600
- rows: 5,
601
- xAxis: { low: "Negligible", high: "Severe" },
602
- yAxis: { low: "Rare", high: "Certain" },
603
- rowLabels: ["Rare", "Unlikely", "Possible", "Likely", "Certain"],
604
- colLabels: ["Negligible", "Minor", "Moderate", "Major", "Severe"]
605
- }
606
- };
607
- function resolveTemplate(name) {
608
- if (name in TEMPLATES) return TEMPLATES[name];
609
- return void 0;
610
- }
611
- function applyTemplateDefaults(ast, spec) {
612
- if (spec.grid === "3x3") {
613
- ast.grid = "3x3";
614
- ast.cols = 3;
615
- ast.rows = 3;
616
- } else if (spec.grid === "NxM") {
617
- ast.grid = "NxM";
618
- ast.cols = spec.cols ?? 5;
619
- ast.rows = spec.rows ?? 5;
620
- } else {
621
- ast.grid = "2x2";
622
- ast.cols = 2;
623
- ast.rows = 2;
624
- }
625
- if (spec.mode) ast.mode = spec.mode;
626
- if (!ast.xAxis.low && !ast.xAxis.high) ast.xAxis = { ...spec.xAxis };
627
- if (!ast.yAxis.low && !ast.yAxis.high) ast.yAxis = { ...spec.yAxis };
628
- if (spec.annotations && ast.annotations.length === 0) {
629
- ast.annotations = spec.annotations.map((a) => ({ ...a }));
630
- }
631
- if (spec.cellLabels && ast.cellLabels.length === 0) {
632
- ast.cellLabels = spec.cellLabels.map((c) => ({ ...c }));
633
- }
634
- if (spec.rowLabels && !ast.rowLabels) ast.rowLabels = [...spec.rowLabels];
635
- if (spec.colLabels && !ast.colLabels) ast.colLabels = [...spec.colLabels];
636
- }
637
-
638
- // src/diagrams/matrix/parser.ts
639
- var TEMPLATE_NAMES = /* @__PURE__ */ new Set([
640
- "eisenhower",
641
- "impact-effort",
642
- "rice",
643
- "bcg",
644
- "ansoff",
645
- "johari",
646
- "9-box",
647
- "risk-matrix"
648
- ]);
649
- var DEFAULT_CONFIG = {
650
- quadrantBg: true,
651
- gridLines: true,
652
- axisArrows: true,
653
- labelCollision: "auto",
654
- bubbleScale: "area",
655
- quadrantAnnotations: true,
656
- legendPosition: "bottom-right",
657
- offChartPolicy: "clamp-badge",
658
- showAxis: "auto",
659
- margins: false
660
- };
661
- function emptyAxis() {
662
- return { low: "", high: "" };
663
- }
664
- function newAST() {
665
- return {
666
- type: "matrix",
667
- mode: "quadrant",
668
- grid: "2x2",
669
- cols: 2,
670
- rows: 2,
671
- xAxis: emptyAxis(),
672
- yAxis: emptyAxis(),
673
- points: [],
674
- cells: [],
675
- cellLabels: [],
676
- annotations: [],
677
- config: { ...DEFAULT_CONFIG }
678
- };
679
- }
680
- function stripQuotes(s) {
681
- const t = s.trim();
682
- if (t.startsWith('"') && t.endsWith('"') || t.startsWith("'") && t.endsWith("'")) {
683
- return t.slice(1, -1);
684
- }
685
- return t;
686
- }
687
- function readQuoted(line2, from) {
688
- let i = from;
689
- while (i < line2.length && /\s/.test(line2[i])) i++;
690
- if (line2[i] !== '"' && line2[i] !== "'") return null;
691
- const quote = line2[i];
692
- const start = i + 1;
693
- let end = start;
694
- while (end < line2.length && line2[end] !== quote) end++;
695
- if (end >= line2.length) return null;
696
- return { text: line2.slice(start, end), next: end + 1 };
697
- }
698
- function parseAxis(raw) {
699
- const arrowMatch = raw.match(/\s*(→|↑|->|>|↓|←|<-|<)\s*/);
700
- if (arrowMatch) {
701
- const arrow = arrowMatch[1];
702
- const idx = arrowMatch.index;
703
- const left = raw.slice(0, idx).trim();
704
- const right = raw.slice(idx + arrowMatch[0].length).trim();
705
- const reversed = arrow === "\u2190" || arrow === "<-" || arrow === "<";
706
- if (reversed) {
707
- return { low: right, high: left, reversed: true };
708
- }
709
- return { low: left, high: right };
710
- }
711
- return { low: "", high: raw.trim() };
712
- }
713
- function parseNumberList(raw) {
714
- const t = raw.trim();
715
- const inner = t.startsWith("[") && t.endsWith("]") ? t.slice(1, -1) : t;
716
- return inner.split(",").map((s) => stripQuotes(s.trim())).filter((s) => s.length > 0);
717
- }
718
- function parseProperties(raw, point) {
719
- let i = 0;
720
- while (i < raw.length) {
721
- while (i < raw.length && /\s/.test(raw[i])) i++;
722
- if (i >= raw.length) break;
723
- const keyMatch = raw.slice(i).match(/^([a-zA-Z_-]+)\s*:\s*/);
724
- if (!keyMatch) break;
725
- const key = keyMatch[1].toLowerCase();
726
- i += keyMatch[0].length;
727
- if (raw[i] === '"' || raw[i] === "'") {
728
- const q = readQuoted(raw, i);
729
- if (!q) break;
730
- if (key === "note") point.note = q.text;
731
- else if (key === "label") point.label = q.text;
732
- i = q.next;
733
- } else {
734
- const rest = raw.slice(i);
735
- const endMatch = rest.match(/\s+[a-zA-Z_-]+\s*:/);
736
- const end = endMatch ? endMatch.index : rest.length;
737
- const val = rest.slice(0, end).trim();
738
- i += end;
739
- if (key === "size") {
740
- const n = Number(val);
741
- if (!Number.isNaN(n)) point.size = n;
742
- } else if (key === "category") {
743
- point.category = val;
744
- } else if (key === "color") {
745
- point.color = val;
746
- } else if (key === "shape") {
747
- if (val === "circle" || val === "square" || val === "triangle" || val === "diamond") {
748
- point.shape = val;
749
- }
750
- } else if (key === "highlight") {
751
- point.highlight = val === "true" || val === "1";
752
- }
753
- }
754
- }
755
- }
756
- function parsePointLine(line2, st) {
757
- const q = readQuoted(line2, 0);
758
- if (!q) return false;
759
- const rest = line2.slice(q.next).trim();
760
- const atMatch = rest.match(/^at\s*\(\s*(-?\d+(?:\.\d+)?)\s*,\s*(-?\d+(?:\.\d+)?)\s*\)\s*(.*)$/);
761
- if (!atMatch) return false;
762
- const x = Number(atMatch[1]);
763
- const y = Number(atMatch[2]);
764
- const props = atMatch[3];
765
- const offChart = x < 0 || x > 1 || y < 0 || y > 1;
766
- const clampedX = Math.max(0, Math.min(1, x));
767
- const clampedY = Math.max(0, Math.min(1, y));
768
- const point = {
769
- id: `p${st.pointIdSeq++}`,
770
- label: q.text,
771
- x: clampedX,
772
- y: clampedY,
773
- offChart,
774
- origX: offChart ? x : void 0,
775
- origY: offChart ? y : void 0
776
- };
777
- if (props) parseProperties(props, point);
778
- st.ast.points.push(point);
779
- return true;
780
- }
781
- function parseCellLine(line2, st) {
782
- const m = line2.match(/^cell\s*\(\s*(\d+)\s*,\s*(\d+)\s*\)\s*(.*)$/i);
783
- if (!m) return false;
784
- const col = Number(m[1]);
785
- const row = Number(m[2]);
786
- const rest = m[3];
787
- const cell = { col, row };
788
- const valMatch = rest.match(/value:\s*(-?\d+(?:\.\d+)?)/i);
789
- if (valMatch) cell.value = Number(valMatch[1]);
790
- const labMatch = rest.match(/label:\s*"([^"]*)"/i);
791
- if (labMatch) cell.label = labMatch[1];
792
- const lvlMatch = rest.match(/level:\s*(strong|medium|weak)\b/i);
793
- if (lvlMatch) {
794
- const lv = lvlMatch[1].toLowerCase();
795
- cell.level = lv;
796
- if (cell.value === void 0) cell.value = lv === "strong" ? 3 : lv === "medium" ? 2 : 1;
797
- }
798
- st.ast.cells.push(cell);
799
- if (cell.label) {
800
- st.ast.cellLabels.push({ col, row, label: cell.label });
801
- }
802
- return true;
803
- }
804
- function parseConfigLine(key, value, ast) {
805
- const k = key.trim().toLowerCase();
806
- const v = value.trim();
807
- if (k === "quadrantbg") ast.config.quadrantBg = v === "true";
808
- else if (k === "gridlines") ast.config.gridLines = v === "true";
809
- else if (k === "axisarrows") ast.config.axisArrows = v === "true";
810
- else if (k === "labelcollision") ast.config.labelCollision = v.replace(/"/g, "");
811
- else if (k === "bubblescale") ast.config.bubbleScale = v === "radius" ? "radius" : "area";
812
- else if (k === "quadrantannotations") ast.config.quadrantAnnotations = v === "true";
813
- else if (k === "legendposition") {
814
- const t = v.replace(/"/g, "");
815
- ast.config.legendPosition = t;
816
- } else if (k === "offchartpolicy") {
817
- const t = v.replace(/"/g, "");
818
- ast.config.offChartPolicy = t;
819
- }
820
- }
821
- function parseHeader(line2, ast) {
822
- const t = line2.trim();
823
- const rest = t.slice("matrix".length).trim();
824
- const heatMatch = rest.match(/^heatmap\s+(\d+)\s*x\s*(\d+)\s*(.*)$/i);
825
- if (heatMatch) {
826
- ast.mode = "heatmap";
827
- ast.grid = "NxM";
828
- ast.cols = Number(heatMatch[1]);
829
- ast.rows = Number(heatMatch[2]);
830
- const title2 = heatMatch[3].trim();
831
- if (title2) ast.title = stripQuotes(title2);
832
- return void 0;
833
- }
834
- const corrMatch = rest.match(/^correlation\s*(?:(\d+)\s*x\s*(\d+))?\s*(.*)$/i);
835
- if (corrMatch) {
836
- ast.mode = "correlation";
837
- ast.grid = "NxM";
838
- if (corrMatch[1] && corrMatch[2]) {
839
- ast.cols = Number(corrMatch[1]);
840
- ast.rows = Number(corrMatch[2]);
841
- }
842
- const title2 = corrMatch[3].trim();
843
- if (title2) ast.title = stripQuotes(title2);
844
- return void 0;
845
- }
846
- const tokenMatch = rest.match(/^([a-zA-Z0-9_-]+)\s*(.*)$/);
847
- if (tokenMatch) {
848
- const tok = tokenMatch[1].toLowerCase();
849
- const remainder = tokenMatch[2].trim();
850
- if (TEMPLATE_NAMES.has(tok)) {
851
- if (remainder) ast.title = stripQuotes(remainder);
852
- return tok;
853
- }
854
- if (rest.startsWith('"') || rest.startsWith("'")) {
855
- ast.title = stripQuotes(rest);
856
- } else if (rest.length > 0) {
857
- ast.title = stripQuotes(rest);
858
- }
859
- }
860
- return void 0;
861
- }
862
- function parseMatrix(text2) {
863
- const st = { ast: newAST(), pointIdSeq: 0 };
864
- const lines = text2.split(/\r?\n/);
865
- let templateName;
866
- let inConfig = false;
867
- for (let raw of lines) {
868
- let line2 = raw;
869
- const hashIdx = findCommentStart(line2);
870
- if (hashIdx >= 0) line2 = line2.slice(0, hashIdx);
871
- line2 = line2.trim();
872
- if (!line2) {
873
- inConfig = false;
874
- continue;
875
- }
876
- if (/^matrix\b/i.test(line2)) {
877
- templateName = parseHeader(line2, st.ast);
878
- continue;
879
- }
880
- if (/^config\s*:/i.test(line2)) {
881
- inConfig = true;
882
- continue;
883
- }
884
- if (inConfig) {
885
- const kv = line2.match(/^([a-zA-Z]+)\s*:\s*(.+)$/);
886
- if (kv) {
887
- parseConfigLine(kv[1], kv[2], st.ast);
888
- continue;
889
- }
890
- inConfig = false;
891
- }
892
- if (/^title\s*:/i.test(line2)) {
893
- st.ast.title = stripQuotes(line2.replace(/^title\s*:\s*/i, ""));
894
- continue;
895
- }
896
- if (/^x-axis\s*:/i.test(line2)) {
897
- st.ast.xAxis = parseAxis(line2.replace(/^x-axis\s*:\s*/i, ""));
898
- continue;
899
- }
900
- if (/^y-axis\s*:/i.test(line2)) {
901
- st.ast.yAxis = parseAxis(line2.replace(/^y-axis\s*:\s*/i, ""));
902
- continue;
903
- }
904
- if (/^rows\s*:/i.test(line2)) {
905
- st.ast.rowLabels = parseNumberList(line2.replace(/^rows\s*:\s*/i, ""));
906
- if (st.ast.mode !== "quadrant") st.ast.rows = st.ast.rowLabels.length;
907
- continue;
908
- }
909
- if (/^cols\s*:/i.test(line2)) {
910
- st.ast.colLabels = parseNumberList(line2.replace(/^cols\s*:\s*/i, ""));
911
- if (st.ast.mode !== "quadrant") st.ast.cols = st.ast.colLabels.length;
912
- continue;
913
- }
914
- if (/^grid\s*:/i.test(line2)) {
915
- const v = line2.replace(/^grid\s*:\s*/i, "").trim().toLowerCase();
916
- const gm = v.match(/^(\d+)\s*x\s*(\d+)$/);
917
- if (gm) {
918
- const c = Number(gm[1]);
919
- const r = Number(gm[2]);
920
- st.ast.cols = c;
921
- st.ast.rows = r;
922
- if (c === 2 && r === 2) st.ast.grid = "2x2";
923
- else if (c === 3 && r === 3) st.ast.grid = "3x3";
924
- else st.ast.grid = "NxM";
925
- }
926
- continue;
927
- }
928
- if (/^quadrant\s+/i.test(line2)) {
929
- const m = line2.match(/^quadrant\s+(?:Q)?(\d)\s*"([^"]*)"(.*)$/i);
930
- if (m) {
931
- const q = Number(m[1]);
932
- const rest = m[3].trim();
933
- const descMatch = rest.match(/description:\s*"([^"]*)"/i);
934
- const description = descMatch ? descMatch[1] : void 0;
935
- if (q >= 1 && q <= 4) {
936
- const existing = st.ast.annotations.find((a) => a.q === q);
937
- if (existing) {
938
- existing.label = m[2];
939
- if (description) existing.description = description;
940
- } else {
941
- st.ast.annotations.push({ q, label: m[2], description });
942
- }
943
- }
944
- }
945
- continue;
946
- }
947
- if (/^axis\s*:/i.test(line2)) {
948
- const v = line2.replace(/^axis\s*:\s*/i, "").trim().toLowerCase().replace(/"/g, "");
949
- if (v === "none" || v === "off" || v === "hidden") st.ast.config.showAxis = "off";
950
- else if (v === "on" || v === "show" || v === "visible") st.ast.config.showAxis = "on";
951
- else st.ast.config.showAxis = "auto";
952
- continue;
953
- }
954
- if (/^margins\s*:/i.test(line2)) {
955
- const v = line2.replace(/^margins\s*:\s*/i, "").trim().toLowerCase();
956
- st.ast.config.margins = v === "true" || v === "on" || v === "1";
957
- continue;
958
- }
959
- if (/^cell\s*\(/i.test(line2)) {
960
- parseCellLine(line2, st);
961
- continue;
962
- }
963
- if (line2.startsWith('"') || line2.startsWith("'")) {
964
- if (parsePointLine(line2, st)) continue;
965
- }
966
- }
967
- if (templateName) {
968
- const spec = resolveTemplate(templateName);
969
- if (spec) {
970
- applyTemplateDefaults(st.ast, spec);
971
- st.ast.template = templateName;
972
- }
973
- }
974
- if (st.ast.cols === 3 && st.ast.rows === 3 && st.ast.grid !== "NxM") {
975
- st.ast.grid = "3x3";
976
- }
977
- if (st.ast.mode === "heatmap" || st.ast.mode === "correlation") st.ast.grid = "NxM";
978
- return st.ast;
979
- }
980
- function findCommentStart(line2) {
981
- let inQuote = null;
982
- for (let i = 0; i < line2.length; i++) {
983
- const ch = line2[i];
984
- if (inQuote) {
985
- if (ch === inQuote) inQuote = null;
986
- } else if (ch === '"' || ch === "'") {
987
- inQuote = ch;
988
- } else if (ch === "#") {
989
- return i;
990
- }
991
- }
992
- return -1;
993
- }
994
-
995
- // src/diagrams/matrix/layout.ts
996
- var CANVAS_W = 720;
997
- var CANVAS_H = 560;
998
- var PADDING_X = 110;
999
- var PADDING_Y = 90;
1000
- var CHAR_W = 6.2;
1001
- var LABEL_H = 14;
1002
- function estimateWidth(text2) {
1003
- const cjk = (text2.match(/[\u3000-\u9fff]/g) ?? []).length;
1004
- return (text2.length - cjk) * CHAR_W + cjk * 12 + 8;
1005
- }
1006
- function clamp01(v) {
1007
- return Math.max(0.02, Math.min(0.98, v));
1008
- }
1009
- function placePoint(p, plot) {
1010
- const nx = clamp01(p.x);
1011
- const ny = clamp01(p.y);
1012
- const px = plot.x0 + nx * plot.w;
1013
- const py = plot.y0 + (1 - ny) * plot.h;
1014
- return { px, py };
1015
- }
1016
- function computeRadius(p, maxSize, plot, scale) {
1017
- if (p.size === void 0) return 6;
1018
- const maxRadius = Math.max(14, plot.h * 0.08);
1019
- const minRadius = 4;
1020
- if (maxSize <= 0) return 6;
1021
- const ratio = p.size / maxSize;
1022
- if (scale === "radius") {
1023
- return Math.max(minRadius, ratio * maxRadius);
1024
- }
1025
- const maxArea = Math.PI * maxRadius * maxRadius;
1026
- const area = ratio * maxArea;
1027
- const r = Math.sqrt(area / Math.PI);
1028
- return Math.max(minRadius, r);
1029
- }
1030
- function resolveLabelCollisions(points, plot, mode) {
1031
- if (mode === "off") {
1032
- for (const p of points) {
1033
- p.label.lx = p.px + p.r + 4 + p.label.width / 2;
1034
- p.label.ly = p.py - p.r - 4;
1035
- }
1036
- return;
1037
- }
1038
- for (const p of points) {
1039
- p.label.ax = p.px;
1040
- p.label.ay = p.py;
1041
- p.label.lx = p.px + p.r + 4 + p.label.width / 2;
1042
- p.label.ly = p.py - p.r - 4;
1043
- p.label.external = false;
1044
- p.label.textAnchor = "middle";
1045
- }
1046
- if (mode === "leader-only") {
1047
- for (const p of points) {
1048
- p.label.external = true;
1049
- p.label.lx = p.px + p.r + 12 + p.label.width / 2;
1050
- p.label.ly = p.py;
1051
- p.label.textAnchor = "middle";
1052
- }
1053
- return;
1054
- }
1055
- const PAD = 3;
1056
- for (let iter = 0; iter < 30; iter++) {
1057
- let moved = false;
1058
- for (let i = 0; i < points.length; i++) {
1059
- for (let j = i + 1; j < points.length; j++) {
1060
- const a = points[i].label;
1061
- const b = points[j].label;
1062
- const ax0 = a.lx - a.width / 2 - PAD;
1063
- const ax1 = a.lx + a.width / 2 + PAD;
1064
- const ay0 = a.ly - a.height / 2 - PAD;
1065
- const ay1 = a.ly + a.height / 2 + PAD;
1066
- const bx0 = b.lx - b.width / 2 - PAD;
1067
- const bx1 = b.lx + b.width / 2 + PAD;
1068
- const by0 = b.ly - b.height / 2 - PAD;
1069
- const by1 = b.ly + b.height / 2 + PAD;
1070
- const overlapX = Math.min(ax1, bx1) - Math.max(ax0, bx0);
1071
- const overlapY = Math.min(ay1, by1) - Math.max(ay0, by0);
1072
- if (overlapX > 0 && overlapY > 0) {
1073
- const dx = a.lx - b.lx || 0.1;
1074
- const dy = a.ly - b.ly || 0.1;
1075
- const len = Math.hypot(dx, dy) || 1;
1076
- const ux = dx / len;
1077
- const uy = dy / len;
1078
- const step = Math.min(3, Math.min(overlapX, overlapY) / 2 + 0.5);
1079
- a.lx += ux * step;
1080
- a.ly += uy * step;
1081
- b.lx -= ux * step;
1082
- b.ly -= uy * step;
1083
- moved = true;
1084
- }
1085
- }
1086
- const lb = points[i].label;
1087
- if (lb.lx - lb.width / 2 < plot.x0 + 2) lb.lx = plot.x0 + 2 + lb.width / 2;
1088
- if (lb.lx + lb.width / 2 > plot.x0 + plot.w - 2) lb.lx = plot.x0 + plot.w - 2 - lb.width / 2;
1089
- if (lb.ly - lb.height / 2 < plot.y0 + 2) lb.ly = plot.y0 + 2 + lb.height / 2;
1090
- if (lb.ly + lb.height / 2 > plot.y0 + plot.h - 2) lb.ly = plot.y0 + plot.h - 2 - lb.height / 2;
1091
- }
1092
- if (!moved) break;
1093
- }
1094
- if (mode === "auto") {
1095
- for (const p of points) {
1096
- const dx = p.label.lx - p.px;
1097
- const dy = p.label.ly - p.py;
1098
- if (Math.hypot(dx, dy) > 40) {
1099
- p.label.external = true;
1100
- }
1101
- }
1102
- }
1103
- }
1104
- function layoutMatrix(ast) {
1105
- const canvasWidth = CANVAS_W;
1106
- const canvasHeight = CANVAS_H;
1107
- const plot = {
1108
- x0: PADDING_X,
1109
- y0: PADDING_Y - 30,
1110
- w: canvasWidth - PADDING_X * 2,
1111
- h: canvasHeight - PADDING_Y * 2
1112
- };
1113
- const points = [];
1114
- const categoriesSet = /* @__PURE__ */ new Set();
1115
- if (ast.mode === "quadrant") {
1116
- let maxSize = 0;
1117
- for (const p of ast.points) {
1118
- if (p.size !== void 0 && p.size > maxSize) maxSize = p.size;
1119
- }
1120
- for (const p of ast.points) {
1121
- const { px, py } = placePoint(p, plot);
1122
- const r = computeRadius(p, maxSize, plot, ast.config.bubbleScale);
1123
- const width = estimateWidth(p.label);
1124
- const label = {
1125
- text: p.label,
1126
- ax: px,
1127
- ay: py,
1128
- lx: px + r + 4 + width / 2,
1129
- ly: py - r - 4,
1130
- width,
1131
- height: LABEL_H,
1132
- external: false,
1133
- textAnchor: "middle"
1134
- };
1135
- points.push({ point: p, px, py, r, label });
1136
- if (p.category) categoriesSet.add(p.category);
1137
- }
1138
- resolveLabelCollisions(points, plot, ast.config.labelCollision);
1139
- }
1140
- return {
1141
- canvasWidth,
1142
- canvasHeight,
1143
- plot,
1144
- points,
1145
- categories: [...categoriesSet]
1146
- };
1147
- }
1148
-
1149
- // src/diagrams/matrix/renderer.ts
1150
- var CATEGORY_COLORS = [
1151
- "#2563eb",
1152
- "#16a34a",
1153
- "#dc2626",
1154
- "#9333ea",
1155
- "#ea580c",
1156
- "#0891b2",
1157
- "#ca8a04",
1158
- "#db2777"
1159
- ];
1160
- var QUADRANT_TINTS = [
1161
- // Q1 TR, Q2 TL, Q3 BL, Q4 BR
1162
- "#dbeafe",
1163
- "#dcfce7",
1164
- "#f3f4f6",
1165
- "#fed7aa"
1166
- ];
1167
- var HEAT_RAMP = [
1168
- "#f0fdf4",
1169
- "#bbf7d0",
1170
- "#fde68a",
1171
- "#fdba74",
1172
- "#f87171",
1173
- "#ef4444",
1174
- "#b91c1c"
1175
- ];
1176
- var CSS = `
1177
- .sx-matrix { background: #fff; font-family: system-ui, -apple-system, "Segoe UI", sans-serif; }
1178
- .sx-matrix-title { font: 600 16px sans-serif; fill: #111; }
1179
- .sx-matrix-grid { stroke: #e5e7eb; stroke-width: 1; fill: none; }
1180
- .sx-matrix-mid { stroke: #9ca3af; stroke-width: 1.2; stroke-dasharray: 4 3; fill: none; }
1181
- .sx-matrix-plot-border { stroke: #374151; stroke-width: 1.2; fill: none; }
1182
- .sx-matrix-axis-label { font: 500 12px sans-serif; fill: #374151; }
1183
- .sx-matrix-axis-end { font: 500 11px sans-serif; fill: #6b7280; }
1184
- .sx-matrix-quad-annot { font: 600 13px sans-serif; fill: #475569; opacity: 0.75; }
1185
- .sx-matrix-quad-desc { font: 400 10.5px sans-serif; fill: #64748b; opacity: 0.85; }
1186
- .sx-matrix-corr-header { font: 600 11.5px sans-serif; fill: #1f2937; text-anchor: middle; }
1187
- .sx-matrix-corr-rowlabel { font: 500 11.5px sans-serif; fill: #1f2937; text-anchor: end; dominant-baseline: central; }
1188
- .sx-matrix-corr-margin { font: 500 11px sans-serif; fill: #374151; text-anchor: middle; dominant-baseline: central; }
1189
- .sx-matrix-corr-margin-best { font: 700 11.5px sans-serif; fill: #111; text-anchor: middle; dominant-baseline: central; }
1190
- .sx-matrix-corr-grid { stroke: #d1d5db; stroke-width: 0.8; fill: none; }
1191
- .sx-matrix-corr-rowbg-a { fill: #f0fdf4; }
1192
- .sx-matrix-corr-rowbg-b { fill: #fff; }
1193
- .sx-matrix-cell-label { font: 500 12px sans-serif; fill: #1f2937; text-anchor: middle; }
1194
- .sx-matrix-cell-value { font: 600 18px sans-serif; fill: #111; text-anchor: middle; }
1195
- .sx-matrix-bubble { stroke-width: 1.5; }
1196
- .sx-matrix-label { font: 500 11px sans-serif; fill: #111827; text-anchor: middle; dominant-baseline: central; pointer-events: none; }
1197
- .sx-matrix-leader { stroke: #94a3b8; stroke-width: 0.6; opacity: 0.7; fill: none; }
1198
- .sx-matrix-legend-text { font: 500 11px sans-serif; fill: #374151; }
1199
- .sx-matrix-offchart { fill: #ea580c; }
1200
- `.trim();
1201
- function axisArrow() {
1202
- return el(
1203
- "marker",
1204
- {
1205
- id: "sx-matrix-arrow",
1206
- viewBox: "0 0 10 10",
1207
- refX: 8,
1208
- refY: 5,
1209
- markerWidth: 8,
1210
- markerHeight: 8,
1211
- orient: "auto-start-reverse"
1212
- },
1213
- [el("path", { d: "M0,0 L10,5 L0,10 z", fill: "#374151" })]
1214
- );
1215
- }
1216
- function bubbleFill(p, categories) {
1217
- if (p.color) return p.color;
1218
- if (p.category) {
1219
- const idx = categories.indexOf(p.category);
1220
- if (idx >= 0) return CATEGORY_COLORS[idx % CATEGORY_COLORS.length];
1221
- }
1222
- return "#2563eb";
1223
- }
1224
- function renderQuadrantBackground(ast, lay) {
1225
- if (!ast.config.quadrantBg || ast.grid !== "2x2") return "";
1226
- const { plot } = lay;
1227
- const halfW = plot.w / 2;
1228
- const halfH = plot.h / 2;
1229
- const rects = [
1230
- { x: plot.x0 + halfW, y: plot.y0, w: halfW, h: halfH, fill: QUADRANT_TINTS[0] },
1231
- { x: plot.x0, y: plot.y0, w: halfW, h: halfH, fill: QUADRANT_TINTS[1] },
1232
- { x: plot.x0, y: plot.y0 + halfH, w: halfW, h: halfH, fill: QUADRANT_TINTS[2] },
1233
- { x: plot.x0 + halfW, y: plot.y0 + halfH, w: halfW, h: halfH, fill: QUADRANT_TINTS[3] }
1234
- ];
1235
- return group(
1236
- { id: "sx-matrix-quad-bg" },
1237
- rects.map(
1238
- (r) => rect({ x: r.x, y: r.y, width: r.w, height: r.h, fill: r.fill, "fill-opacity": 0.55 })
1239
- )
1240
- );
1241
- }
1242
- function renderGrid(ast, lay) {
1243
- if (!ast.config.gridLines) return "";
1244
- if (ast.mode === "correlation") return "";
1245
- const { plot } = lay;
1246
- const lines = [];
1247
- const cols = ast.cols;
1248
- const rows = ast.rows;
1249
- for (let i = 1; i < cols; i++) {
1250
- const x = plot.x0 + plot.w * i / cols;
1251
- const cls = cols === 2 && i === 1 ? "sx-matrix-mid" : "sx-matrix-grid";
1252
- lines.push(line({ x1: x, y1: plot.y0, x2: x, y2: plot.y0 + plot.h, class: cls }));
1253
- }
1254
- for (let j = 1; j < rows; j++) {
1255
- const y = plot.y0 + plot.h * j / rows;
1256
- const cls = rows === 2 && j === 1 ? "sx-matrix-mid" : "sx-matrix-grid";
1257
- lines.push(line({ x1: plot.x0, y1: y, x2: plot.x0 + plot.w, y2: y, class: cls }));
1258
- }
1259
- lines.push(
1260
- rect({
1261
- x: plot.x0,
1262
- y: plot.y0,
1263
- width: plot.w,
1264
- height: plot.h,
1265
- class: "sx-matrix-plot-border",
1266
- fill: "none"
1267
- })
1268
- );
1269
- return group({ id: "sx-matrix-grid" }, lines);
1270
- }
1271
- function shouldShowAxis(ast) {
1272
- if (ast.config.showAxis === "on") return true;
1273
- if (ast.config.showAxis === "off") return false;
1274
- return ast.mode === "quadrant";
1275
- }
1276
- function renderAxes(ast, lay) {
1277
- if (!shouldShowAxis(ast)) return "";
1278
- const { plot } = lay;
1279
- const els = [];
1280
- const marker = ast.config.axisArrows ? { "marker-end": "url(#sx-matrix-arrow)" } : {};
1281
- const xy = plot.y0 + plot.h + 14;
1282
- const yx = plot.x0 - 14;
1283
- els.push(
1284
- line({
1285
- x1: plot.x0,
1286
- y1: xy,
1287
- x2: plot.x0 + plot.w,
1288
- y2: xy,
1289
- stroke: "#374151",
1290
- "stroke-width": 1.2,
1291
- ...marker
1292
- })
1293
- );
1294
- els.push(
1295
- line({
1296
- x1: yx,
1297
- y1: plot.y0 + plot.h,
1298
- x2: yx,
1299
- y2: plot.y0,
1300
- stroke: "#374151",
1301
- "stroke-width": 1.2,
1302
- ...marker
1303
- })
1304
- );
1305
- if (ast.xAxis.low) {
1306
- els.push(
1307
- text(
1308
- { x: plot.x0, y: xy + 20, class: "sx-matrix-axis-end", "text-anchor": "start" },
1309
- ast.xAxis.low
1310
- )
1311
- );
1312
- }
1313
- if (ast.xAxis.high) {
1314
- els.push(
1315
- text(
1316
- { x: plot.x0 + plot.w, y: xy + 20, class: "sx-matrix-axis-end", "text-anchor": "end" },
1317
- ast.xAxis.high
1318
- )
1319
- );
1320
- }
1321
- if (ast.yAxis.low) {
1322
- els.push(
1323
- text(
1324
- {
1325
- x: yx - 24,
1326
- y: plot.y0 + plot.h,
1327
- class: "sx-matrix-axis-end",
1328
- "text-anchor": "end",
1329
- transform: `rotate(-90 ${yx - 24} ${plot.y0 + plot.h})`
1330
- },
1331
- ast.yAxis.low
1332
- )
1333
- );
1334
- }
1335
- if (ast.yAxis.high) {
1336
- els.push(
1337
- text(
1338
- {
1339
- x: yx - 24,
1340
- y: plot.y0,
1341
- class: "sx-matrix-axis-end",
1342
- "text-anchor": "start",
1343
- transform: `rotate(-90 ${yx - 24} ${plot.y0})`
1344
- },
1345
- ast.yAxis.high
1346
- )
1347
- );
1348
- }
1349
- return group({ id: "sx-matrix-axes" }, els);
1350
- }
1351
- function renderQuadAnnotations(ast, lay) {
1352
- if (!ast.config.quadrantAnnotations || ast.grid !== "2x2" || ast.annotations.length === 0) return "";
1353
- const { plot } = lay;
1354
- plot.w / 2;
1355
- plot.h / 2;
1356
- const padding = 14;
1357
- const positions = {
1358
- 1: { x: plot.x0 + plot.w - padding, y: plot.y0 + padding + 14, anchor: "end" },
1359
- // TR
1360
- 2: { x: plot.x0 + padding, y: plot.y0 + padding + 14, anchor: "start" },
1361
- // TL
1362
- 3: { x: plot.x0 + padding, y: plot.y0 + plot.h - padding, anchor: "start" },
1363
- // BL
1364
- 4: { x: plot.x0 + plot.w - padding, y: plot.y0 + plot.h - padding, anchor: "end" }
1365
- // BR
1366
- };
1367
- const nodes = [];
1368
- for (const a of ast.annotations) {
1369
- const pos = positions[a.q];
1370
- const growsUp = a.q === 3 || a.q === 4;
1371
- const descLines = a.description ? wrapLabel(a.description, 28) : [];
1372
- const labelY = growsUp && descLines.length > 0 ? pos.y - descLines.length * 12 : pos.y;
1373
- nodes.push(
1374
- text(
1375
- { x: pos.x, y: labelY, class: "sx-matrix-quad-annot", "text-anchor": pos.anchor },
1376
- a.label
1377
- )
1378
- );
1379
- for (let i = 0; i < descLines.length; i++) {
1380
- nodes.push(
1381
- text(
1382
- {
1383
- x: pos.x,
1384
- y: labelY + 14 + i * 12,
1385
- class: "sx-matrix-quad-desc",
1386
- "text-anchor": pos.anchor
1387
- },
1388
- descLines[i]
1389
- )
1390
- );
1391
- }
1392
- }
1393
- return group({ id: "sx-matrix-quad-annot" }, nodes);
1394
- }
1395
- function wrapLabel(text2, maxChars) {
1396
- const words = text2.split(/\s+/);
1397
- const out = [];
1398
- let cur = "";
1399
- for (const w of words) {
1400
- if ((cur + " " + w).trim().length > maxChars) {
1401
- if (cur) out.push(cur);
1402
- cur = w;
1403
- } else {
1404
- cur = (cur ? cur + " " : "") + w;
1405
- }
1406
- }
1407
- if (cur) out.push(cur);
1408
- return out;
1409
- }
1410
- function render3x3CellLabels(ast, lay) {
1411
- if (ast.grid !== "3x3" || ast.cellLabels.length === 0) return "";
1412
- const { plot } = lay;
1413
- const cellW = plot.w / ast.cols;
1414
- const cellH = plot.h / ast.rows;
1415
- const nodes = ast.cellLabels.map((cl) => {
1416
- const cx = plot.x0 + cellW * (cl.col + 0.5);
1417
- const cy = plot.y0 + cellH * (ast.rows - 1 - cl.row + 0.5);
1418
- return text({ x: cx, y: cy, class: "sx-matrix-cell-label" }, cl.label);
1419
- });
1420
- return group({ id: "sx-matrix-cell-labels" }, nodes);
1421
- }
1422
- function renderHeatmap(ast, lay) {
1423
- if (ast.mode !== "heatmap") return "";
1424
- const { plot } = lay;
1425
- const cellW = plot.w / ast.cols;
1426
- const cellH = plot.h / ast.rows;
1427
- const maxVal = Math.max(
1428
- 1,
1429
- ...ast.cells.map((c) => c.value ?? (c.col + 1) * (c.row + 1))
1430
- );
1431
- const cells = [];
1432
- for (let col = 0; col < ast.cols; col++) {
1433
- for (let row = 0; row < ast.rows; row++) {
1434
- const found = ast.cells.find((c) => c.col === col && c.row === row);
1435
- const value = found?.value ?? (col + 1) * (row + 1);
1436
- const ratio = Math.min(1, value / maxVal);
1437
- const idx = Math.min(HEAT_RAMP.length - 1, Math.floor(ratio * HEAT_RAMP.length));
1438
- const color = HEAT_RAMP[idx];
1439
- const x = plot.x0 + col * cellW;
1440
- const y = plot.y0 + (ast.rows - 1 - row) * cellH;
1441
- cells.push(
1442
- rect({
1443
- x,
1444
- y,
1445
- width: cellW,
1446
- height: cellH,
1447
- fill: color,
1448
- stroke: "#fff",
1449
- "stroke-width": 2
1450
- })
1451
- );
1452
- }
1453
- }
1454
- if (ast.rowLabels) {
1455
- for (let row = 0; row < ast.rows; row++) {
1456
- const lbl = ast.rowLabels[row];
1457
- if (!lbl) continue;
1458
- const y = plot.y0 + (ast.rows - 1 - row + 0.5) * cellH;
1459
- cells.push(
1460
- text(
1461
- {
1462
- x: plot.x0 - 8,
1463
- y,
1464
- class: "sx-matrix-axis-end",
1465
- "text-anchor": "end",
1466
- "dominant-baseline": "central"
1467
- },
1468
- lbl
1469
- )
1470
- );
1471
- }
1472
- }
1473
- if (ast.colLabels) {
1474
- for (let col = 0; col < ast.cols; col++) {
1475
- const lbl = ast.colLabels[col];
1476
- if (!lbl) continue;
1477
- const x = plot.x0 + (col + 0.5) * cellW;
1478
- cells.push(
1479
- text(
1480
- {
1481
- x,
1482
- y: plot.y0 + plot.h + 16,
1483
- class: "sx-matrix-axis-end",
1484
- "text-anchor": "middle"
1485
- },
1486
- lbl
1487
- )
1488
- );
1489
- }
1490
- }
1491
- for (const cl of ast.cellLabels) {
1492
- const cx = plot.x0 + cellW * (cl.col + 0.5);
1493
- const cy = plot.y0 + cellH * (ast.rows - 1 - cl.row + 0.5);
1494
- const words = cl.label.split(/\s+/);
1495
- const lines = [];
1496
- let cur = "";
1497
- for (const w of words) {
1498
- if ((cur + " " + w).trim().length > 14) {
1499
- if (cur) lines.push(cur);
1500
- cur = w;
1501
- } else {
1502
- cur = (cur ? cur + " " : "") + w;
1503
- }
1504
- }
1505
- if (cur) lines.push(cur);
1506
- const lineH = 13;
1507
- const startY = cy - (lines.length - 1) * lineH / 2;
1508
- for (let i = 0; i < lines.length; i++) {
1509
- cells.push(
1510
- text(
1511
- {
1512
- x: cx,
1513
- y: startY + i * lineH,
1514
- class: "sx-matrix-cell-label",
1515
- "dominant-baseline": "central"
1516
- },
1517
- lines[i]
1518
- )
1519
- );
1520
- }
1521
- }
1522
- return group({ id: "sx-matrix-heatmap" }, cells);
1523
- }
1524
- var DOT_COLORS = {
1525
- strong: "#16a34a",
1526
- medium: "#86efac",
1527
- weak: "#9ca3af"
1528
- };
1529
- function levelFromValue(v) {
1530
- if (v >= 3) return "strong";
1531
- if (v >= 2) return "medium";
1532
- return "weak";
1533
- }
1534
- function renderCorrelation(ast, lay) {
1535
- if (ast.mode !== "correlation") return "";
1536
- const { plot } = lay;
1537
- const marginCols = ast.config.margins ? 2 : 0;
1538
- const marginRows = ast.config.margins ? 2 : 0;
1539
- const cellW = plot.w / (ast.cols + marginCols);
1540
- const cellH = plot.h / (ast.rows + marginRows);
1541
- const gridW = cellW * ast.cols;
1542
- const gridH = cellH * ast.rows;
1543
- const nodes = [];
1544
- for (let row = 0; row < ast.rows; row++) {
1545
- const y = plot.y0 + (ast.rows - 1 - row) * cellH;
1546
- nodes.push(
1547
- rect({
1548
- x: plot.x0,
1549
- y,
1550
- width: gridW,
1551
- height: cellH,
1552
- class: row % 2 === 0 ? "sx-matrix-corr-rowbg-a" : "sx-matrix-corr-rowbg-b"
1553
- })
1554
- );
1555
- }
1556
- for (let i = 0; i <= ast.cols; i++) {
1557
- const x = plot.x0 + i * cellW;
1558
- nodes.push(line({ x1: x, y1: plot.y0, x2: x, y2: plot.y0 + gridH, class: "sx-matrix-corr-grid" }));
1559
- }
1560
- for (let j = 0; j <= ast.rows; j++) {
1561
- const y = plot.y0 + j * cellH;
1562
- nodes.push(line({ x1: plot.x0, y1: y, x2: plot.x0 + gridW, y2: y, class: "sx-matrix-corr-grid" }));
1563
- }
1564
- const dotR = Math.max(4, Math.min(cellW, cellH) * 0.28);
1565
- const rowSums = new Array(ast.rows).fill(0);
1566
- const colSums = new Array(ast.cols).fill(0);
1567
- for (const c of ast.cells) {
1568
- if (c.col < 0 || c.col >= ast.cols || c.row < 0 || c.row >= ast.rows) continue;
1569
- const v = c.value ?? (c.level ? c.level === "strong" ? 3 : c.level === "medium" ? 2 : 1 : 0);
1570
- if (v <= 0) continue;
1571
- rowSums[c.row] += v;
1572
- colSums[c.col] += v;
1573
- const lvl = c.level ?? levelFromValue(v);
1574
- const cx = plot.x0 + (c.col + 0.5) * cellW;
1575
- const cy = plot.y0 + (ast.rows - 1 - c.row + 0.5) * cellH;
1576
- nodes.push(
1577
- circle({
1578
- cx,
1579
- cy,
1580
- r: dotR,
1581
- fill: DOT_COLORS[lvl],
1582
- stroke: DOT_COLORS[lvl],
1583
- "stroke-width": 1
1584
- })
1585
- );
1586
- }
1587
- if (ast.colLabels) {
1588
- for (let col = 0; col < ast.cols; col++) {
1589
- const label = ast.colLabels[col];
1590
- if (!label) continue;
1591
- const cx = plot.x0 + (col + 0.5) * cellW;
1592
- const lines = wrapLabel(label, 10);
1593
- const startY = plot.y0 - 8 - (lines.length - 1) * 12;
1594
- for (let i = 0; i < lines.length; i++) {
1595
- nodes.push(
1596
- text(
1597
- { x: cx, y: startY + i * 12, class: "sx-matrix-corr-header" },
1598
- lines[i]
1599
- )
1600
- );
1601
- }
1602
- }
1603
- }
1604
- if (ast.rowLabels) {
1605
- for (let row = 0; row < ast.rows; row++) {
1606
- const label = ast.rowLabels[row];
1607
- if (!label) continue;
1608
- const y = plot.y0 + (ast.rows - 1 - row + 0.5) * cellH;
1609
- nodes.push(
1610
- text({ x: plot.x0 - 8, y, class: "sx-matrix-corr-rowlabel" }, label)
1611
- );
1612
- }
1613
- }
1614
- if (ast.config.margins) {
1615
- const rowRanks = rankOf(rowSums);
1616
- const colRanks = rankOf(colSums);
1617
- const bestRow = rowSums.length > 0 ? Math.max(...rowSums) : 0;
1618
- const bestCol = colSums.length > 0 ? Math.max(...colSums) : 0;
1619
- const scoreColX = plot.x0 + gridW + cellW * 0.5;
1620
- const rankColX = plot.x0 + gridW + cellW * 1.5;
1621
- nodes.push(text({ x: scoreColX, y: plot.y0 - 8, class: "sx-matrix-corr-header" }, "Score"));
1622
- nodes.push(text({ x: rankColX, y: plot.y0 - 8, class: "sx-matrix-corr-header" }, "Rank"));
1623
- for (let row = 0; row < ast.rows; row++) {
1624
- const y = plot.y0 + (ast.rows - 1 - row + 0.5) * cellH;
1625
- const sum = rowSums[row];
1626
- const rank = rowRanks[row];
1627
- const cls = sum === bestRow && sum > 0 ? "sx-matrix-corr-margin-best" : "sx-matrix-corr-margin";
1628
- nodes.push(text({ x: scoreColX, y, class: cls }, String(sum)));
1629
- nodes.push(
1630
- text({ x: rankColX, y, class: rank === 1 ? "sx-matrix-corr-margin-best" : "sx-matrix-corr-margin" }, String(rank))
1631
- );
1632
- }
1633
- const scoreRowY = plot.y0 + gridH + cellH * 0.5;
1634
- const rankRowY = plot.y0 + gridH + cellH * 1.5;
1635
- nodes.push(
1636
- text(
1637
- { x: plot.x0 - 8, y: scoreRowY, class: "sx-matrix-corr-rowlabel" },
1638
- "Score"
1639
- )
1640
- );
1641
- nodes.push(
1642
- text(
1643
- { x: plot.x0 - 8, y: rankRowY, class: "sx-matrix-corr-rowlabel" },
1644
- "Rank"
1645
- )
1646
- );
1647
- for (let col = 0; col < ast.cols; col++) {
1648
- const cx = plot.x0 + (col + 0.5) * cellW;
1649
- const sum = colSums[col];
1650
- const rank = colRanks[col];
1651
- nodes.push(
1652
- text(
1653
- {
1654
- x: cx,
1655
- y: scoreRowY,
1656
- class: sum === bestCol && sum > 0 ? "sx-matrix-corr-margin-best" : "sx-matrix-corr-margin"
1657
- },
1658
- String(sum)
1659
- )
1660
- );
1661
- nodes.push(
1662
- text(
1663
- {
1664
- x: cx,
1665
- y: rankRowY,
1666
- class: rank === 1 ? "sx-matrix-corr-margin-best" : "sx-matrix-corr-margin"
1667
- },
1668
- String(rank)
1669
- )
1670
- );
1671
- }
1672
- }
1673
- return group({ id: "sx-matrix-correlation" }, nodes);
1674
- }
1675
- function rankOf(vals) {
1676
- const sorted = [...vals].map((v, i) => ({ v, i })).sort((a, b) => b.v - a.v);
1677
- const ranks = new Array(vals.length).fill(0);
1678
- let prev = -Infinity;
1679
- let rank = 0;
1680
- let seen = 0;
1681
- for (const e of sorted) {
1682
- seen++;
1683
- if (e.v !== prev) {
1684
- rank = seen;
1685
- prev = e.v;
1686
- }
1687
- ranks[e.i] = rank;
1688
- }
1689
- return ranks;
1690
- }
1691
- function renderCorrelationLegend(ast, lay) {
1692
- if (ast.mode !== "correlation") return "";
1693
- const xBase = lay.plot.x0 + lay.plot.w + 20;
1694
- const yBase = lay.plot.y0 + 8;
1695
- const items = [
1696
- ["strong", "Strong (3)"],
1697
- ["medium", "Medium (2)"],
1698
- ["weak", "Weak (1)"]
1699
- ];
1700
- const rows = items.map(
1701
- (it, i) => group({ transform: `translate(${xBase}, ${yBase + i * 18})` }, [
1702
- circle({ cx: 6, cy: 6, r: 5, fill: DOT_COLORS[it[0]], stroke: DOT_COLORS[it[0]] }),
1703
- text({ x: 18, y: 10, class: "sx-matrix-legend-text" }, it[1])
1704
- ])
1705
- );
1706
- return group({ id: "sx-matrix-corr-legend" }, rows);
1707
- }
1708
- function renderPoints(ast, lay) {
1709
- if (ast.mode !== "quadrant") return "";
1710
- const nodes = [];
1711
- for (const p of lay.points) {
1712
- nodes.push(renderOnePoint(p, lay.categories));
1713
- }
1714
- return group({ id: "sx-matrix-points" }, nodes);
1715
- }
1716
- function renderOnePoint(pl, categories) {
1717
- const p = pl.point;
1718
- const color = bubbleFill(p, categories);
1719
- const shape = p.shape ?? "circle";
1720
- let shapeEl;
1721
- const stroke = p.highlight ? "#111" : color;
1722
- const strokeWidth = p.highlight ? 2.2 : 1.5;
1723
- const fillOpacity = p.size !== void 0 ? 0.45 : 0.75;
1724
- if (shape === "circle") {
1725
- shapeEl = circle({
1726
- cx: pl.px,
1727
- cy: pl.py,
1728
- r: pl.r,
1729
- fill: color,
1730
- "fill-opacity": fillOpacity,
1731
- stroke,
1732
- "stroke-width": strokeWidth,
1733
- class: "sx-matrix-bubble"
1734
- });
1735
- } else if (shape === "square") {
1736
- shapeEl = rect({
1737
- x: pl.px - pl.r,
1738
- y: pl.py - pl.r,
1739
- width: pl.r * 2,
1740
- height: pl.r * 2,
1741
- fill: color,
1742
- "fill-opacity": fillOpacity,
1743
- stroke,
1744
- "stroke-width": strokeWidth,
1745
- class: "sx-matrix-bubble"
1746
- });
1747
- } else if (shape === "diamond") {
1748
- const r = pl.r;
1749
- shapeEl = polygon({
1750
- points: `${pl.px},${pl.py - r} ${pl.px + r},${pl.py} ${pl.px},${pl.py + r} ${pl.px - r},${pl.py}`,
1751
- fill: color,
1752
- "fill-opacity": fillOpacity,
1753
- stroke,
1754
- "stroke-width": strokeWidth,
1755
- class: "sx-matrix-bubble"
1756
- });
1757
- } else {
1758
- const r = pl.r;
1759
- shapeEl = polygon({
1760
- points: `${pl.px},${pl.py - r} ${pl.px + r},${pl.py + r * 0.8} ${pl.px - r},${pl.py + r * 0.8}`,
1761
- fill: color,
1762
- "fill-opacity": fillOpacity,
1763
- stroke,
1764
- "stroke-width": strokeWidth,
1765
- class: "sx-matrix-bubble"
1766
- });
1767
- }
1768
- const leader = pl.label.external ? line({
1769
- x1: pl.px,
1770
- y1: pl.py,
1771
- x2: pl.label.lx,
1772
- y2: pl.label.ly,
1773
- class: "sx-matrix-leader"
1774
- }) : "";
1775
- const label = text(
1776
- { x: pl.label.lx, y: pl.label.ly, class: "sx-matrix-label" },
1777
- pl.label.text
1778
- );
1779
- let badge = "";
1780
- if (p.offChart) {
1781
- const bx = pl.px;
1782
- const by = pl.py;
1783
- badge = text(
1784
- { x: bx + pl.r + 4, y: by - pl.r - 2, class: "sx-matrix-offchart", "font-size": 14, "font-weight": 700 },
1785
- "\u2197"
1786
- );
1787
- }
1788
- const titleStr = p.note ? `${p.label} \xB7 (${p.origX ?? p.x}, ${p.origY ?? p.y}) \u2014 ${p.note}` : `${p.label} \xB7 (${(p.origX ?? p.x).toFixed(2)}, ${(p.origY ?? p.y).toFixed(2)})${p.size !== void 0 ? ` \xB7 size ${p.size}` : ""}`;
1789
- return group(
1790
- {
1791
- class: "sx-matrix-point",
1792
- "data-point-id": p.id,
1793
- "data-label": p.label,
1794
- ...p.category ? { "data-category": p.category } : {}
1795
- },
1796
- [title(titleStr), shapeEl, leader, label, badge].filter((s) => s.length > 0)
1797
- );
1798
- }
1799
- function renderLegend(ast, lay) {
1800
- if (ast.config.legendPosition === "none") return "";
1801
- if (ast.mode === "heatmap") {
1802
- const x = lay.plot.x0 + lay.plot.w - 220;
1803
- const y = lay.plot.y0 + lay.plot.h + 40;
1804
- const w = 210;
1805
- const h = 10;
1806
- const stops = HEAT_RAMP.map(
1807
- (c, i) => el("stop", { offset: `${i / (HEAT_RAMP.length - 1) * 100}%`, "stop-color": c })
1808
- );
1809
- const grad = el(
1810
- "linearGradient",
1811
- { id: "sx-matrix-heatgrad", x1: "0%", x2: "100%" },
1812
- stops
1813
- );
1814
- return group({ id: "sx-matrix-legend" }, [
1815
- el("defs", {}, [grad]),
1816
- rect({ x, y, width: w, height: h, fill: "url(#sx-matrix-heatgrad)", stroke: "#d1d5db" }),
1817
- text({ x, y: y - 4, class: "sx-matrix-legend-text", "text-anchor": "start" }, "Low"),
1818
- text(
1819
- { x: x + w, y: y - 4, class: "sx-matrix-legend-text", "text-anchor": "end" },
1820
- "High"
1821
- )
1822
- ]);
1823
- }
1824
- if (lay.categories.length === 0) return "";
1825
- const xBase = lay.plot.x0 + lay.plot.w + 12;
1826
- const yBase = lay.plot.y0 + 8;
1827
- const rows = lay.categories.map((cat, i) => {
1828
- const color = CATEGORY_COLORS[i % CATEGORY_COLORS.length];
1829
- return group({ transform: `translate(${xBase}, ${yBase + i * 18})` }, [
1830
- circle({ cx: 6, cy: 6, r: 5, fill: color, "fill-opacity": 0.7, stroke: color }),
1831
- text({ x: 18, y: 10, class: "sx-matrix-legend-text" }, cat)
1832
- ]);
1833
- });
1834
- return group({ id: "sx-matrix-legend" }, rows);
1835
- }
1836
- function renderTitle(ast, lay) {
1837
- if (!ast.title) return "";
1838
- return text(
1839
- { x: lay.canvasWidth / 2, y: 28, class: "sx-matrix-title", "text-anchor": "middle" },
1840
- ast.title
1841
- );
1842
- }
1843
- function renderMatrixAST(ast) {
1844
- const lay = layoutMatrix(ast);
1845
- const needsLegendSpace = lay.categories.length > 0 || ast.mode === "correlation";
1846
- const extraWidth = needsLegendSpace && lay.plot.x0 + lay.plot.w + 140 > lay.canvasWidth ? 160 : 0;
1847
- const canvasWidth = lay.canvasWidth + extraWidth;
1848
- const body = [
1849
- renderTitle(ast, lay),
1850
- renderQuadrantBackground(ast, lay),
1851
- renderGrid(ast, lay),
1852
- renderQuadAnnotations(ast, lay),
1853
- render3x3CellLabels(ast, lay),
1854
- renderHeatmap(ast, lay),
1855
- renderCorrelation(ast, lay),
1856
- renderAxes(ast, lay),
1857
- renderPoints(ast, lay),
1858
- renderLegend(ast, lay),
1859
- renderCorrelationLegend(ast, lay)
1860
- ].filter((s) => s.length > 0);
1861
- return svgRoot(
1862
- {
1863
- class: "sx-matrix",
1864
- "data-diagram-type": "matrix",
1865
- "data-mode": ast.mode,
1866
- width: canvasWidth,
1867
- height: lay.canvasHeight,
1868
- viewBox: `0 0 ${canvasWidth} ${lay.canvasHeight}`,
1869
- role: "graphics-document"
1870
- },
1871
- [
1872
- title(ast.title ? `Matrix \u2014 ${escapeXml(ast.title)}` : "Matrix diagram"),
1873
- desc(
1874
- `Matrix diagram${ast.template ? ` (${ast.template} template)` : ""}, ${ast.mode} mode, ${ast.points.length} point(s)`
1875
- ),
1876
- defs([el("style", {}, CSS), axisArrow()]),
1877
- ...body
1878
- ]
1879
- );
1880
- }
1881
- function renderMatrix(text2) {
1882
- const ast = parseMatrix(text2);
1883
- return renderMatrixAST(ast);
1884
- }
1885
-
1886
- // src/diagrams/matrix/index.ts
1887
- var matrix = {
1888
- type: "matrix",
1889
- detect(text2) {
1890
- const first = text2.trim().split("\n")[0]?.trim().toLowerCase() ?? "";
1891
- return first.startsWith("matrix");
1892
- },
1893
- render(text2) {
1894
- return renderMatrix(text2);
1895
- }
1896
- };
1897
-
1898
- // src/core/api.ts
1899
- var plugins = [
1900
- genogram,
1901
- ecomap,
1902
- pedigree,
1903
- phylo,
1904
- sociogram,
1905
- timing,
1906
- logic,
1907
- circuit,
1908
- blockdiagram,
1909
- ladder,
1910
- sld,
1911
- entity,
1912
- fishbone,
1913
- venn,
1914
- flowchart,
1915
- mindmap,
1916
- matrix,
1917
- orgchart
1918
- ];
1919
- function detectPlugin(text2, config) {
1920
- if (config?.type) {
1921
- const plugin = plugins.find((p) => p.type === config.type);
1922
- if (plugin) return plugin;
1923
- }
1924
- for (const plugin of plugins) {
1925
- if (plugin.detect(text2)) return plugin;
1926
- }
1927
- throw new Error(
1928
- "Cannot detect diagram type. Start your text with 'genogram', 'ecomap', 'pedigree', 'phylo', 'sociogram', 'timing', 'logic', 'circuit', 'blockdiagram', 'ladder', 'sld', 'entity-structure', 'fishbone', 'venn', 'flowchart', 'mindmap', 'matrix', or 'orgchart'."
1929
- );
1930
- }
1931
- function render(text2, config) {
1932
- const plugin = detectPlugin(text2, config);
1933
- const renderConfig = {
1934
- fontFamily: config?.fontFamily ?? "system-ui, -apple-system, sans-serif",
1935
- fontSize: 12,
1936
- theme: config?.theme ?? "default",
1937
- padding: config?.padding ?? 20
1938
- };
1939
- return plugin.render(text2, renderConfig);
1940
- }
1941
-
1942
- export { render };
1
+ export { decisiontree, parse, render, timeline } from './chunk-M6AMNXQ7.js';
2
+ export { orgchart } from './chunk-7WXAAVR3.js';
3
+ export { circuit } from './chunk-2OIW3MAE.js';
4
+ export { blockdiagram } from './chunk-5SH5NUDW.js';
5
+ export { ladder } from './chunk-L6IHSTPP.js';
6
+ export { sld } from './chunk-A74ZCP5I.js';
7
+ export { entity } from './chunk-MRGS54WN.js';
8
+ export { fishbone } from './chunk-IQIJ6WW6.js';
9
+ export { venn } from './chunk-MXJ6FHSY.js';
10
+ export { flowchart } from './chunk-JZGFSRVT.js';
11
+ export { genogram } from './chunk-HLYA4QBB.js';
12
+ export { ecomap } from './chunk-RQX53J6M.js';
13
+ export { pedigree } from './chunk-TPA36ULU.js';
14
+ export { phylo } from './chunk-4TS5NB7L.js';
15
+ export { sociogram } from './chunk-YO4GU6JX.js';
16
+ export { timing } from './chunk-GEPBET4L.js';
17
+ export { logic } from './chunk-SPIW4VWP.js';
18
+ export { BASE_THEMES, BIOLOGY_TOKENS, PERSON_TOKENS, VENN_TOKENS, resolveBaseTheme, resolveBiologyTheme, resolveFishboneTheme, resolveGenogramTheme, resolvePersonTheme, resolveTimelineTheme, resolveVennTheme } from './chunk-TIGP2OEJ.js';
19
+ import './chunk-KLJEK547.js';
1943
20
  //# sourceMappingURL=index.js.map
1944
21
  //# sourceMappingURL=index.js.map