@cardenelabs/cdl 0.122.0 → 0.124.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 (64) hide show
  1. package/CHANGELOG.md +28 -1
  2. package/README.md +70 -1
  3. package/dist/index.cjs +1125 -618
  4. package/dist/index.cjs.map +1 -1
  5. package/dist/index.d.cts +38 -26
  6. package/dist/index.d.ts +38 -26
  7. package/dist/index.js +1125 -619
  8. package/dist/index.js.map +1 -1
  9. package/dist/react.cjs +894 -404
  10. package/dist/react.cjs.map +1 -1
  11. package/dist/react.d.cts +1 -1
  12. package/dist/react.d.ts +1 -1
  13. package/dist/react.js +894 -404
  14. package/dist/react.js.map +1 -1
  15. package/dist/{render-U_pC-Ksh.d.cts → render-U6omSNH2.d.cts} +23 -4
  16. package/dist/{render-U_pC-Ksh.d.ts → render-U6omSNH2.d.ts} +23 -4
  17. package/package.json +9 -12
  18. package/src/builder.ts +5 -0
  19. package/src/index.ts +2 -0
  20. package/src/kinds/box-lines.ts +17 -4
  21. package/src/kinds/chart-bar.tsx +4 -0
  22. package/src/kinds/chart-gauge.tsx +20 -9
  23. package/src/kinds/chart-pie.tsx +67 -17
  24. package/src/kinds/chart-radial.tsx +7 -2
  25. package/src/kinds/chart-slope.tsx +26 -7
  26. package/src/kinds/chart-stacked-bar.tsx +8 -4
  27. package/src/kinds/chart-stat.tsx +19 -4
  28. package/src/kinds/chart-waffle.tsx +7 -2
  29. package/src/kinds/funnel.tsx +9 -2
  30. package/src/kinds/generic.tsx +5 -2
  31. package/src/kinds/mind-map.tsx +26 -10
  32. package/src/kinds/quadrant.tsx +14 -4
  33. package/src/kinds/row-align.ts +19 -7
  34. package/src/kinds/sequence-board-metrics.ts +13 -3
  35. package/src/kinds/sequence-board.tsx +4 -2
  36. package/src/kinds/shape-basement.tsx +57 -32
  37. package/src/kinds/shape-blockchain.tsx +83 -34
  38. package/src/kinds/shape-commerce.tsx +65 -24
  39. package/src/kinds/shape-finance.tsx +90 -26
  40. package/src/kinds/shape-hardware.tsx +48 -17
  41. package/src/kinds/shape-region.tsx +16 -6
  42. package/src/kinds/shape-software.tsx +30 -8
  43. package/src/kinds/text-width.ts +17 -3
  44. package/src/kinds/tree.tsx +25 -7
  45. package/src/layout/collisions.ts +21 -8
  46. package/src/layout/curve-path.ts +3 -2
  47. package/src/layout/edges.ts +173 -29
  48. package/src/layout/head-label.ts +3 -1
  49. package/src/layout/lanes.ts +3 -2
  50. package/src/layout/metro-path.ts +3 -2
  51. package/src/layout/nodes.ts +14 -6
  52. package/src/layout/predict-bbox.ts +6 -3
  53. package/src/layout/self-loop.ts +10 -4
  54. package/src/layout/spec.ts +20 -6
  55. package/src/layout/text-width.ts +25 -8
  56. package/src/layout.ts +39 -15
  57. package/src/presets.ts +69 -43
  58. package/src/render/edges.tsx +18 -3
  59. package/src/render/interactive-panel.tsx +34 -7
  60. package/src/render/nodes.tsx +97 -48
  61. package/src/render/stage.tsx +3 -0
  62. package/src/text-metrics.ts +9 -0
  63. package/src/types.ts +22 -2
  64. package/src/visual-validate.ts +67 -17
package/dist/index.cjs CHANGED
@@ -712,6 +712,11 @@ function \u5B57\u3092\u5DEE\u3057\u8FBC\u3080(template, values) {
712
712
  return template.replace(/\{(\w+)\}/g, (whole, name) => name in values ? String(values[name]) : whole);
713
713
  }
714
714
 
715
+ // src/text-metrics.ts
716
+ function resolveTextMetrics(value) {
717
+ return value === "monospace" ? "monospace" : "proportional";
718
+ }
719
+
715
720
  // src/formula/ast.ts
716
721
  var ALLOWED_MATH_FNS = /* @__PURE__ */ new Set([
717
722
  "min",
@@ -1650,13 +1655,215 @@ function \u5024\u3092\u540D\u524D\u3067\u8AAD\u3080(\u5165\u529B\u6B04, \u5024)
1650
1655
  return \u5024.split(",").map((v) => \u5165\u529B\u6B04.\u540D\u524D.get(v) ?? v).join(",");
1651
1656
  }
1652
1657
 
1658
+ // src/layout/text-width.ts
1659
+ var INTER_BOLD_ADVANCE_EM = {
1660
+ // uppercase (実測係数化、 Inter Bold 仕様 × 1.20)
1661
+ A: 0.86,
1662
+ B: 0.86,
1663
+ C: 0.88,
1664
+ D: 0.93,
1665
+ E: 0.82,
1666
+ F: 0.79,
1667
+ G: 0.94,
1668
+ H: 0.92,
1669
+ I: 0.44,
1670
+ J: 0.66,
1671
+ K: 0.86,
1672
+ L: 0.74,
1673
+ M: 1.12,
1674
+ N: 0.94,
1675
+ O: 0.94,
1676
+ P: 0.85,
1677
+ Q: 0.94,
1678
+ R: 0.87,
1679
+ S: 0.79,
1680
+ T: 0.82,
1681
+ U: 0.91,
1682
+ V: 0.85,
1683
+ W: 1.22,
1684
+ X: 0.85,
1685
+ Y: 0.82,
1686
+ Z: 0.82,
1687
+ // lowercase (実測係数化、 Inter Bold 仕様 × 1.22)
1688
+ a: 0.73,
1689
+ b: 0.77,
1690
+ c: 0.68,
1691
+ d: 0.77,
1692
+ e: 0.73,
1693
+ f: 0.51,
1694
+ g: 0.76,
1695
+ h: 0.77,
1696
+ i: 0.39,
1697
+ j: 0.41,
1698
+ k: 0.73,
1699
+ l: 0.39,
1700
+ m: 1.15,
1701
+ n: 0.77,
1702
+ o: 0.76,
1703
+ p: 0.77,
1704
+ q: 0.77,
1705
+ r: 0.54,
1706
+ s: 0.65,
1707
+ t: 0.54,
1708
+ u: 0.77,
1709
+ v: 0.71,
1710
+ w: 1.05,
1711
+ x: 0.71,
1712
+ y: 0.71,
1713
+ z: 0.66,
1714
+ // digits (Inter Bold tabular-nums、 実測係数化 × 1.20)
1715
+ "0": 0.72,
1716
+ "1": 0.72,
1717
+ "2": 0.72,
1718
+ "3": 0.72,
1719
+ "4": 0.72,
1720
+ "5": 0.72,
1721
+ "6": 0.72,
1722
+ "7": 0.72,
1723
+ "8": 0.72,
1724
+ "9": 0.72,
1725
+ // ascii symbols (実測係数化 × 1.15、 punct 系は kerning が広く効くため 1.20)
1726
+ " ": 0.35,
1727
+ "!": 0.44,
1728
+ '"': 0.59,
1729
+ "#": 0.78,
1730
+ "$": 0.72,
1731
+ "%": 1,
1732
+ "&": 0.86,
1733
+ "'": 0.32,
1734
+ "(": 0.46,
1735
+ ")": 0.46,
1736
+ "*": 0.63,
1737
+ "+": 0.78,
1738
+ ",": 0.36,
1739
+ "-": 0.5,
1740
+ ".": 0.36,
1741
+ "/": 0.51,
1742
+ ":": 0.36,
1743
+ ";": 0.36,
1744
+ "<": 0.78,
1745
+ "=": 0.78,
1746
+ ">": 0.78,
1747
+ "?": 0.63,
1748
+ "@": 1.17,
1749
+ "[": 0.48,
1750
+ "\\": 0.51,
1751
+ "]": 0.48,
1752
+ "^": 0.63,
1753
+ "_": 0.63,
1754
+ "`": 0.48,
1755
+ "{": 0.52,
1756
+ "|": 0.37,
1757
+ "}": 0.52,
1758
+ "~": 0.78
1759
+ };
1760
+ var JETBRAINS_MONO_ADVANCE_EM = 0.63;
1761
+ function isCJK(code) {
1762
+ return code >= 12288 && code <= 12543 || // CJK symbols / hiragana / katakana
1763
+ code >= 13312 && code <= 40959 || // CJK ideographs
1764
+ code >= 63744 && code <= 64255 || // CJK compat ideographs
1765
+ code >= 65281 && code <= 65376 || // fullwidth ASCII
1766
+ code >= 65504 && code <= 65510;
1767
+ }
1768
+ function isHalfwidthKana(code) {
1769
+ return code >= 65377 && code <= 65500;
1770
+ }
1771
+ var EMOJI_ADVANCE_EM = 1.05;
1772
+ var MONO_EMOJI_ADVANCE_EM = 1.16;
1773
+ var DRAWN_CJK_RATIO = 1.08;
1774
+ var DRAWN_ASCII_RATIO = 1.16;
1775
+ function isAscii(code) {
1776
+ return code < 128;
1777
+ }
1778
+ var WIDE_SYMBOL_ADVANCE_EM = 0.95;
1779
+ function isEmoji(code) {
1780
+ return code >= 126976 && code <= 129791 || // 絵文字の主要面
1781
+ code >= 9728 && code <= 10175 || // 記号と絵文字 (♻ ✅ ❤ 等)
1782
+ code >= 127462 && code <= 127487;
1783
+ }
1784
+ function isEmojiGrapheme(grapheme, firstCode) {
1785
+ return isEmoji(firstCode) || grapheme.includes("\uFE0F");
1786
+ }
1787
+ function isWideSymbol(code) {
1788
+ return code >= 8592 && code <= 8703 || // 矢印
1789
+ code >= 9472 && code <= 9599 || // 罫線
1790
+ code >= 9632 && code <= 9727 || // 幾何図形
1791
+ code >= 11008 && code <= 11263;
1792
+ }
1793
+ var CLUSTER_JOINER_RE = /\u200d|\ufe0f|[\u{1f000}-\u{1faff}]|[\u{2600}-\u{27bf}]/u;
1794
+ var \u66F8\u8A18\u7D20\u3067\u5206\u3051\u308B;
1795
+ function segmentGraphemes(text) {
1796
+ if (typeof Intl === "undefined" || typeof Intl.Segmenter !== "function") {
1797
+ return [...text];
1798
+ }
1799
+ \u66F8\u8A18\u7D20\u3067\u5206\u3051\u308B ??= new Intl.Segmenter(void 0, { granularity: "grapheme" });
1800
+ return [...\u66F8\u8A18\u7D20\u3067\u5206\u3051\u308B.segment(text)].map((s) => s.segment);
1801
+ }
1802
+ function defaultAdvanceEm(ch, code) {
1803
+ if (isEmoji(code)) return EMOJI_ADVANCE_EM;
1804
+ if (isWideSymbol(code)) return WIDE_SYMBOL_ADVANCE_EM;
1805
+ if (isCJK(code)) return 1.08;
1806
+ if (isHalfwidthKana(code)) return 0.72;
1807
+ if (ch >= "a" && ch <= "z") return 0.73;
1808
+ if (ch >= "A" && ch <= "Z") return 0.86;
1809
+ if (ch >= "0" && ch <= "9") return 0.72;
1810
+ return 0.65;
1811
+ }
1812
+ function measureAdvanceWidth(text, opts = {}) {
1813
+ const fontSize = opts.fontSize ?? 22;
1814
+ const letterSpacing = opts.letterSpacing ?? 0;
1815
+ const fontFamily = opts.textMetrics === "monospace" ? "mono" : opts.fontFamily ?? "sans";
1816
+ const bound = opts.bound ?? "layout";
1817
+ let advanceEmSum = 0;
1818
+ let charCount = 0;
1819
+ const \u6587\u5B57\u5217 = CLUSTER_JOINER_RE.test(text) ? segmentGraphemes(text) : [...text];
1820
+ for (const ch of \u6587\u5B57\u5217) {
1821
+ charCount++;
1822
+ const code = ch.codePointAt(0) ?? 0;
1823
+ const \u5272\u308A\u623B\u3057 = bound === "drawn" && !isEmojiGrapheme(ch, code) ? isAscii(code) && fontFamily !== "mono" ? DRAWN_ASCII_RATIO : isCJK(code) ? DRAWN_CJK_RATIO : 1 : 1;
1824
+ if (isEmojiGrapheme(ch, code)) {
1825
+ advanceEmSum += fontFamily === "mono" ? MONO_EMOJI_ADVANCE_EM : EMOJI_ADVANCE_EM;
1826
+ continue;
1827
+ }
1828
+ if (fontFamily === "mono") {
1829
+ advanceEmSum += (isCJK(code) ? 1.08 : JETBRAINS_MONO_ADVANCE_EM) / \u5272\u308A\u623B\u3057;
1830
+ continue;
1831
+ }
1832
+ if (isCJK(code)) {
1833
+ advanceEmSum += 1.08 / \u5272\u308A\u623B\u3057;
1834
+ continue;
1835
+ }
1836
+ const table = ch.length === 1 ? INTER_BOLD_ADVANCE_EM[ch] : void 0;
1837
+ advanceEmSum += (table !== void 0 ? table : defaultAdvanceEm(ch, code)) / \u5272\u308A\u623B\u3057;
1838
+ }
1839
+ return advanceEmSum * fontSize + letterSpacing * charCount;
1840
+ }
1841
+ function measureTextWidth(text, opts = {}) {
1842
+ const fontSize = opts.fontSize ?? 22;
1843
+ const bound = opts.bound ?? "layout";
1844
+ const w = measureAdvanceWidth(text, opts);
1845
+ return bound === "drawn" ? w : Math.max(w, fontSize * 1.2);
1846
+ }
1847
+ function \u53CE\u3081\u308B\u500D\u7387(text, opts, \u5E45) {
1848
+ if (!(\u5E45 > 0) || !(opts.fontSize > 0)) return 1;
1849
+ const \u5B9F\u5E45 = measureTextWidth(text, { ...opts, letterSpacing: 0 });
1850
+ return \u5B9F\u5E45 > \u5E45 ? \u5E45 / \u5B9F\u5E45 : 1;
1851
+ }
1852
+
1653
1853
  // src/kinds/text-width.ts
1654
1854
  var WIDE_RATIO = 1.04;
1655
1855
  var NARROW_RATIO = 0.37;
1656
1856
  var ASCII_RATIO = 0.86;
1657
1857
  var WIDE_CHARS = "W@%Mm";
1658
1858
  var NARROW_CHARS = "ijlI.,:;'! ";
1659
- function textWidth(s, size, \u5B57\u9001\u308A = 0) {
1859
+ function textWidth(s, size, \u5B57\u9001\u308A = 0, textMetrics = "proportional") {
1860
+ if (textMetrics === "monospace") {
1861
+ return measureAdvanceWidth(s, {
1862
+ fontSize: size,
1863
+ letterSpacing: \u5B57\u9001\u308A,
1864
+ fontFamily: "mono"
1865
+ });
1866
+ }
1660
1867
  let \u5E45 = 0;
1661
1868
  let \u5B57\u6570 = 0;
1662
1869
  for (const c of s) {
@@ -1693,8 +1900,8 @@ function splitRow(row) {
1693
1900
  }
1694
1901
  return { left: row.trim(), right: "", split: false };
1695
1902
  }
1696
- function rowColumnWidth(text, size, mono) {
1697
- return mono ? displayWidth(text) * size * MONO_ADVANCE_RATIO : textWidth(text, size);
1903
+ function rowColumnWidth(text, size, mono, textMetrics = "proportional") {
1904
+ return mono ? displayWidth(text) * size * MONO_ADVANCE_RATIO : textWidth(text, size, 0, textMetrics);
1698
1905
  }
1699
1906
  function displayWidth(text) {
1700
1907
  let w = 0;
@@ -1720,12 +1927,12 @@ function \u6841\u3067\u7701\u304F(text, \u4E0A\u9650) {
1720
1927
  if (displayWidth(text) <= \u4E0A\u9650) return text;
1721
1928
  return `${\u6841\u3067\u5272\u308B(text, \u4E0A\u9650 - 1)[0]}\u2026`;
1722
1929
  }
1723
- function requiredRowsWidth(rows, kind) {
1930
+ function requiredRowsWidth(rows, kind, textMetrics = "proportional") {
1724
1931
  if (!rows || rows.length === 0) return 0;
1725
1932
  const splits = rows.map(splitRow);
1726
1933
  const \u4E00\u756A\u5E83\u3044 = (\u53D6\u308B) => splits.reduce((m, s) => Math.max(m, \u53D6\u308B(s)), 0);
1727
- const storage = ROW_PAD_X_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.left, 26, true)) + STORAGE_COL_GAP_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.right, 26, true)) + ROW_RIGHT_PAD_PX;
1728
- const generic = ROW_PAD_X_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.left, GENERIC_ROW_LEFT_SIZE_PX, false)) + ROW_COL_GAP_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.right, GENERIC_ROW_RIGHT_SIZE_PX, true)) + ROW_RIGHT_PAD_PX;
1934
+ const storage = ROW_PAD_X_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.left, 26, true, textMetrics)) + STORAGE_COL_GAP_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.right, 26, true, textMetrics)) + ROW_RIGHT_PAD_PX;
1935
+ const generic = ROW_PAD_X_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.left, GENERIC_ROW_LEFT_SIZE_PX, false, textMetrics)) + ROW_COL_GAP_PX + \u4E00\u756A\u5E83\u3044((s) => rowColumnWidth(s.right, GENERIC_ROW_RIGHT_SIZE_PX, true, textMetrics)) + ROW_RIGHT_PAD_PX;
1729
1936
  if (kind === void 0) return Math.ceil(Math.max(storage, generic));
1730
1937
  return Math.ceil(kind === "storage" ? storage : generic);
1731
1938
  }
@@ -1790,7 +1997,10 @@ var \u5DE6\u53F3\u306E\u4F59\u767D = 8;
1790
1997
  function \u4F7F\u3048\u308B\u5E45(\u7BB1\u306E\u5E45) {
1791
1998
  return \u7BB1\u306E\u5E45 - \u5DE6\u53F3\u306E\u4F59\u767D * 2;
1792
1999
  }
1793
- function \u5E45\u3067\u5207\u308B(text, fontSize, \u4F7F\u3048\u308B\u5E452, \u6E2C\u308B = textWidth) {
2000
+ function \u7BB1\u306E\u5B57\u3092\u6E2C\u308B(textMetrics = "proportional") {
2001
+ return (text, fontSize) => textWidth(text, fontSize, 0, textMetrics);
2002
+ }
2003
+ function \u5E45\u3067\u5207\u308B(text, fontSize, \u4F7F\u3048\u308B\u5E452, \u6E2C\u308B) {
1794
2004
  if (\u4F7F\u3048\u308B\u5E452 <= 0) return "";
1795
2005
  if (\u6E2C\u308B(text, fontSize) <= \u4F7F\u3048\u308B\u5E452) return text;
1796
2006
  const \u7701\u7565 = "\u2026";
@@ -1807,7 +2017,7 @@ function \u5E45\u3067\u5207\u308B(text, fontSize, \u4F7F\u3048\u308B\u5E452, \u6
1807
2017
  return `${\u51FA}${\u7701\u7565}`;
1808
2018
  }
1809
2019
  var \u7E2E\u3081\u306E\u4E0B\u9650 = MIN_TEXT_SIZE;
1810
- function \u5E45\u306B\u53CE\u3081\u308B(text, fontSize, \u4F7F\u3048\u308B\u5E452, \u6E2C\u308B = textWidth) {
2020
+ function \u5E45\u306B\u53CE\u3081\u308B(text, fontSize, \u4F7F\u3048\u308B\u5E452, \u6E2C\u308B) {
1811
2021
  let size = fontSize;
1812
2022
  while (size > \u7E2E\u3081\u306E\u4E0B\u9650 && \u6E2C\u308B(text, size) > \u4F7F\u3048\u308B\u5E452) size -= 1;
1813
2023
  return { text: \u5E45\u3067\u5207\u308B(text, size, \u4F7F\u3048\u308B\u5E452, \u6E2C\u308B), fontSize: size };
@@ -1817,7 +2027,7 @@ function \u66F8\u8A18\u7D20\u306B\u5206\u3051\u308B(text) {
1817
2027
  if (typeof \u533A\u5207\u308A !== "function") return [...text];
1818
2028
  return [...new \u533A\u5207\u308A(void 0, { granularity: "grapheme" }).segment(text)].map((g) => g.segment);
1819
2029
  }
1820
- function \u7BB1\u306B\u7A4D\u3080(\u884C, \u7BB1\u306E\u5E45, \u7BB1\u306E\u9AD8\u30553) {
2030
+ function \u7BB1\u306B\u7A4D\u3080(\u884C, \u7BB1\u306E\u5E45, \u7BB1\u306E\u9AD8\u30553, \u6E2C\u308B) {
1821
2031
  const \u5019\u88DC = \u884C.filter((r, i) => i === 0 || r.text.trim() !== "");
1822
2032
  if (\u5019\u88DC.length === 0) return [];
1823
2033
  const \u4F7F\u3048\u308B\u9AD8\u3055 = \u7BB1\u306E\u9AD8\u30553 - \u4E0A\u4E0B\u306E\u4F59\u767D * 2;
@@ -1825,7 +2035,7 @@ function \u7BB1\u306B\u7A4D\u3080(\u884C, \u7BB1\u306E\u5E45, \u7BB1\u306E\u9AD8
1825
2035
  const \u6B8B\u3059 = [...\u5019\u88DC];
1826
2036
  while (\u6B8B\u3059.length > 1 && \u9AD8\u3055(\u6B8B\u3059) > \u4F7F\u3048\u308B\u9AD8\u3055) \u6B8B\u3059.pop();
1827
2037
  const \u5E45 = \u4F7F\u3048\u308B\u5E45(\u7BB1\u306E\u5E45);
1828
- const \u53CE\u3081\u305F = \u6B8B\u3059.map((r) => ({ ...r, ...\u5E45\u306B\u53CE\u3081\u308B(r.text, r.fontSize, \u5E45) }));
2038
+ const \u53CE\u3081\u305F = \u6B8B\u3059.map((r) => ({ ...r, ...\u5E45\u306B\u53CE\u3081\u308B(r.text, r.fontSize, \u5E45, \u6E2C\u308B) }));
1829
2039
  const \u7DCF\u9AD8 = \u9AD8\u3055(\u53CE\u3081\u305F);
1830
2040
  let \u7A4D\u307F = -\u7DCF\u9AD8 / 2;
1831
2041
  return \u53CE\u3081\u305F.map((r) => {
@@ -2182,7 +2392,15 @@ function useInteractiveIntegration(diagram2, options = {}) {
2182
2392
  f.id
2183
2393
  )) }),
2184
2394
  scrolls.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "cdl-ip-group", children: scrolls.map((s) => /* @__PURE__ */ jsxRuntime.jsx(ScrollReadout, { id: s.id, name: s.label || s.id, progress: stateOverrides[s.id] }, s.id)) }),
2185
- readouts.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "cdl-ip-group", children: readouts.map((r) => /* @__PURE__ */ jsxRuntime.jsx(ReadoutWidget, { readout: r, stateOverrides: mergedStateValues }, r.id)) })
2395
+ readouts.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "cdl-ip-group", children: readouts.map((r) => /* @__PURE__ */ jsxRuntime.jsx(
2396
+ ReadoutWidget,
2397
+ {
2398
+ readout: r,
2399
+ stateOverrides: mergedStateValues,
2400
+ textMetrics: resolveTextMetrics(diagram2.textMetrics)
2401
+ },
2402
+ r.id
2403
+ )) })
2186
2404
  ] }) })
2187
2405
  );
2188
2406
  }, [diagram2, signals, stateOverrides, mergedStateValues]);
@@ -2603,7 +2821,8 @@ function StepperWidget({
2603
2821
  }
2604
2822
  function ReadoutWidget({
2605
2823
  readout,
2606
- stateOverrides
2824
+ stateOverrides,
2825
+ textMetrics = "proportional"
2607
2826
  }) {
2608
2827
  const rawValue = "source" in readout ? stateOverrides[readout.source] : void 0;
2609
2828
  const numericValue = typeof rawValue === "number" ? rawValue : typeof rawValue === "string" ? Number(rawValue) : Number.NaN;
@@ -2851,7 +3070,8 @@ function ReadoutWidget({
2851
3070
  max: readout.max,
2852
3071
  viewW: readout.viewW ?? 280,
2853
3072
  viewH: readout.viewH ?? 60,
2854
- color: readout.color ?? "#2563eb"
3073
+ color: readout.color ?? "#2563eb",
3074
+ textMetrics
2855
3075
  }
2856
3076
  );
2857
3077
  case "radar": {
@@ -3667,7 +3887,8 @@ function ReadoutWidget({
3667
3887
  { status: "idle", color: "#94a3b8" },
3668
3888
  { status: "error", color: "#ef4444" }
3669
3889
  ],
3670
- max: readout.max ?? 10
3890
+ max: readout.max ?? 10,
3891
+ textMetrics
3671
3892
  }
3672
3893
  );
3673
3894
  case "calendar-week":
@@ -4811,8 +5032,8 @@ function ProgressGroupReadout({
4811
5032
  }) })
4812
5033
  ] });
4813
5034
  }
4814
- function sequenceLabelAnchor(x, name, fontSize, viewW) {
4815
- const half = textWidth(name, fontSize) / 2;
5035
+ function sequenceLabelAnchor(x, name, fontSize, viewW, textMetrics = "proportional") {
5036
+ const half = textWidth(name, fontSize, 0, textMetrics) / 2;
4816
5037
  if (x - half < 0) return "start";
4817
5038
  if (x + half > viewW) return "end";
4818
5039
  return "middle";
@@ -4825,7 +5046,8 @@ function SequenceTimelineReadout({
4825
5046
  max,
4826
5047
  viewW,
4827
5048
  viewH,
4828
- color
5049
+ color,
5050
+ textMetrics = "proportional"
4829
5051
  }) {
4830
5052
  const events = [];
4831
5053
  const trimmed = value.trim();
@@ -4868,7 +5090,17 @@ function SequenceTimelineReadout({
4868
5090
  const x = xFor(e.t);
4869
5091
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { "data-cdl-event-marker": e.name, children: [
4870
5092
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: x, cy: trackY, r: 5, fill: color, stroke: "#fff", strokeWidth: 1.5, children: /* @__PURE__ */ jsxRuntime.jsx(\u5B57\u306E\u898B\u51FA\u3057, { k: "readout.sequenceTimeline.title", v: { name: e.name, t: e.t } }) }),
4871
- /* @__PURE__ */ jsxRuntime.jsx("text", { x, y: trackY - 12, textAnchor: sequenceLabelAnchor(x, e.name, 10, viewW), fontSize: 10, fill: "var(--v4-ink, #1a1f2a)", children: e.name }),
5093
+ /* @__PURE__ */ jsxRuntime.jsx(
5094
+ "text",
5095
+ {
5096
+ x,
5097
+ y: trackY - 12,
5098
+ textAnchor: sequenceLabelAnchor(x, e.name, 10, viewW, textMetrics),
5099
+ fontSize: 10,
5100
+ fill: "var(--v4-ink, #1a1f2a)",
5101
+ children: e.name
5102
+ }
5103
+ ),
4872
5104
  /* @__PURE__ */ jsxRuntime.jsx("text", { x, y: trackY + 18, textAnchor: "middle", fontSize: 9, fill: "var(--v4-mute, #64748b)", children: e.t })
4873
5105
  ] }, i);
4874
5106
  })
@@ -7945,7 +8177,8 @@ function StatusTimelineReadout({
7945
8177
  label,
7946
8178
  value,
7947
8179
  colorMap,
7948
- max
8180
+ max,
8181
+ textMetrics = "proportional"
7949
8182
  }) {
7950
8183
  const events = [];
7951
8184
  const trimmed = value.trim();
@@ -7970,6 +8203,7 @@ function StatusTimelineReadout({
7970
8203
  const cellW = shown.length > 0 ? (width - 20) / shown.length : 0;
7971
8204
  const height = stripHeight + 40;
7972
8205
  const \u533A\u9593\u306E\u5B57 = (status) => status === "active" || status === "idle" || status === "error" ? \u5F15\u304F(`readout.statusTimeline.${status}`) : status.toUpperCase();
8206
+ const \u6E2C\u308B = \u7BB1\u306E\u5B57\u3092\u6E2C\u308B(textMetrics);
7973
8207
  return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "cdl-ip-item cdl-ip-readout-status-timeline", "data-cdl-readout": id, children: [
7974
8208
  /* @__PURE__ */ jsxRuntime.jsx("span", { className: "cdl-ip-label", children: label }),
7975
8209
  /* @__PURE__ */ jsxRuntime.jsx(
@@ -7983,7 +8217,7 @@ function StatusTimelineReadout({
7983
8217
  const x = 10 + i * cellW;
7984
8218
  const c = colorLookup.get(ev.status) ?? "#cbd5e1";
7985
8219
  const \u5B572 = \u533A\u9593\u306E\u5B57(ev.status);
7986
- const \u63CF\u304F\u5B57 = \u5E45\u3067\u5207\u308B(\u5B572, 10, cellW - 8);
8220
+ const \u63CF\u304F\u5B57 = \u5E45\u3067\u5207\u308B(\u5B572, 10, cellW - 8, \u6E2C\u308B);
7987
8221
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { "data-cdl-status-event": i, "data-cdl-status": ev.status, children: [
7988
8222
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x, y: 10, width: cellW - 2, height: stripHeight, fill: c, rx: 2 }),
7989
8223
  /* @__PURE__ */ jsxRuntime.jsxs(
@@ -12094,6 +12328,8 @@ function diagram(id, options) {
12094
12328
  ...options.palette !== void 0 ? { palette: options.palette } : {},
12095
12329
  // 言語も素通しする。 型の外の値を既定に落とすのは `layout` の 1 箇所に置く
12096
12330
  ...options.lang !== void 0 ? { lang: options.lang } : {},
12331
+ // 字幅の測り方も素通しする。型の外の値を既定に落とすのは `layout` の 1 箇所に置く
12332
+ ...options.textMetrics !== void 0 ? { textMetrics: options.textMetrics } : {},
12097
12333
  // 種類の名前も同じ経路で渡し、空文字の扱いを `layout` の 1 箇所に揃える
12098
12334
  ...options.type !== void 0 ? { type: options.type } : {},
12099
12335
  // inputs / formulas / scrollTriggers / eventBindings は空なら省略 (static diagram の JSON 形状維持)
@@ -12126,196 +12362,6 @@ var ARROW_ANGLE_MAX_DEG = 100;
12126
12362
  var FAN_GAP = 120;
12127
12363
  var DETOUR_GAP = 94;
12128
12364
 
12129
- // src/layout/text-width.ts
12130
- var INTER_BOLD_ADVANCE_EM = {
12131
- // uppercase (実測係数化、 Inter Bold 仕様 × 1.20)
12132
- A: 0.86,
12133
- B: 0.86,
12134
- C: 0.88,
12135
- D: 0.93,
12136
- E: 0.82,
12137
- F: 0.79,
12138
- G: 0.94,
12139
- H: 0.92,
12140
- I: 0.44,
12141
- J: 0.66,
12142
- K: 0.86,
12143
- L: 0.74,
12144
- M: 1.12,
12145
- N: 0.94,
12146
- O: 0.94,
12147
- P: 0.85,
12148
- Q: 0.94,
12149
- R: 0.87,
12150
- S: 0.79,
12151
- T: 0.82,
12152
- U: 0.91,
12153
- V: 0.85,
12154
- W: 1.22,
12155
- X: 0.85,
12156
- Y: 0.82,
12157
- Z: 0.82,
12158
- // lowercase (実測係数化、 Inter Bold 仕様 × 1.22)
12159
- a: 0.73,
12160
- b: 0.77,
12161
- c: 0.68,
12162
- d: 0.77,
12163
- e: 0.73,
12164
- f: 0.51,
12165
- g: 0.76,
12166
- h: 0.77,
12167
- i: 0.39,
12168
- j: 0.41,
12169
- k: 0.73,
12170
- l: 0.39,
12171
- m: 1.15,
12172
- n: 0.77,
12173
- o: 0.76,
12174
- p: 0.77,
12175
- q: 0.77,
12176
- r: 0.54,
12177
- s: 0.65,
12178
- t: 0.54,
12179
- u: 0.77,
12180
- v: 0.71,
12181
- w: 1.05,
12182
- x: 0.71,
12183
- y: 0.71,
12184
- z: 0.66,
12185
- // digits (Inter Bold tabular-nums、 実測係数化 × 1.20)
12186
- "0": 0.72,
12187
- "1": 0.72,
12188
- "2": 0.72,
12189
- "3": 0.72,
12190
- "4": 0.72,
12191
- "5": 0.72,
12192
- "6": 0.72,
12193
- "7": 0.72,
12194
- "8": 0.72,
12195
- "9": 0.72,
12196
- // ascii symbols (実測係数化 × 1.15、 punct 系は kerning が広く効くため 1.20)
12197
- " ": 0.35,
12198
- "!": 0.44,
12199
- '"': 0.59,
12200
- "#": 0.78,
12201
- "$": 0.72,
12202
- "%": 1,
12203
- "&": 0.86,
12204
- "'": 0.32,
12205
- "(": 0.46,
12206
- ")": 0.46,
12207
- "*": 0.63,
12208
- "+": 0.78,
12209
- ",": 0.36,
12210
- "-": 0.5,
12211
- ".": 0.36,
12212
- "/": 0.51,
12213
- ":": 0.36,
12214
- ";": 0.36,
12215
- "<": 0.78,
12216
- "=": 0.78,
12217
- ">": 0.78,
12218
- "?": 0.63,
12219
- "@": 1.17,
12220
- "[": 0.48,
12221
- "\\": 0.51,
12222
- "]": 0.48,
12223
- "^": 0.63,
12224
- "_": 0.63,
12225
- "`": 0.48,
12226
- "{": 0.52,
12227
- "|": 0.37,
12228
- "}": 0.52,
12229
- "~": 0.78
12230
- };
12231
- var JETBRAINS_MONO_ADVANCE_EM = 0.63;
12232
- function isCJK(code) {
12233
- return code >= 12288 && code <= 12543 || // CJK symbols / hiragana / katakana
12234
- code >= 13312 && code <= 40959 || // CJK ideographs
12235
- code >= 63744 && code <= 64255 || // CJK compat ideographs
12236
- code >= 65281 && code <= 65376 || // fullwidth ASCII
12237
- code >= 65504 && code <= 65510;
12238
- }
12239
- function isHalfwidthKana(code) {
12240
- return code >= 65377 && code <= 65500;
12241
- }
12242
- var EMOJI_ADVANCE_EM = 1.05;
12243
- var MONO_EMOJI_ADVANCE_EM = 1.16;
12244
- var DRAWN_CJK_RATIO = 1.08;
12245
- var DRAWN_ASCII_RATIO = 1.16;
12246
- function isAscii(code) {
12247
- return code < 128;
12248
- }
12249
- var WIDE_SYMBOL_ADVANCE_EM = 0.95;
12250
- function isEmoji(code) {
12251
- return code >= 126976 && code <= 129791 || // 絵文字の主要面
12252
- code >= 9728 && code <= 10175 || // 記号と絵文字 (♻ ✅ ❤ 等)
12253
- code >= 127462 && code <= 127487;
12254
- }
12255
- function isEmojiGrapheme(grapheme, firstCode) {
12256
- return isEmoji(firstCode) || grapheme.includes("\uFE0F");
12257
- }
12258
- function isWideSymbol(code) {
12259
- return code >= 8592 && code <= 8703 || // 矢印
12260
- code >= 9472 && code <= 9599 || // 罫線
12261
- code >= 9632 && code <= 9727 || // 幾何図形
12262
- code >= 11008 && code <= 11263;
12263
- }
12264
- var CLUSTER_JOINER_RE = /\u200d|\ufe0f|[\u{1f000}-\u{1faff}]|[\u{2600}-\u{27bf}]/u;
12265
- var \u66F8\u8A18\u7D20\u3067\u5206\u3051\u308B;
12266
- function segmentGraphemes(text) {
12267
- if (typeof Intl === "undefined" || typeof Intl.Segmenter !== "function") {
12268
- return [...text];
12269
- }
12270
- \u66F8\u8A18\u7D20\u3067\u5206\u3051\u308B ??= new Intl.Segmenter(void 0, { granularity: "grapheme" });
12271
- return [...\u66F8\u8A18\u7D20\u3067\u5206\u3051\u308B.segment(text)].map((s) => s.segment);
12272
- }
12273
- function defaultAdvanceEm(ch, code) {
12274
- if (isEmoji(code)) return EMOJI_ADVANCE_EM;
12275
- if (isWideSymbol(code)) return WIDE_SYMBOL_ADVANCE_EM;
12276
- if (isCJK(code)) return 1.08;
12277
- if (isHalfwidthKana(code)) return 0.72;
12278
- if (ch >= "a" && ch <= "z") return 0.73;
12279
- if (ch >= "A" && ch <= "Z") return 0.86;
12280
- if (ch >= "0" && ch <= "9") return 0.72;
12281
- return 0.65;
12282
- }
12283
- function measureTextWidth(text, opts = {}) {
12284
- const fontSize = opts.fontSize ?? 22;
12285
- const letterSpacing = opts.letterSpacing ?? 0;
12286
- const fontFamily = opts.fontFamily ?? "sans";
12287
- const bound = opts.bound ?? "layout";
12288
- let advanceEmSum = 0;
12289
- let charCount = 0;
12290
- const \u6587\u5B57\u5217 = CLUSTER_JOINER_RE.test(text) ? segmentGraphemes(text) : [...text];
12291
- for (const ch of \u6587\u5B57\u5217) {
12292
- charCount++;
12293
- const code = ch.codePointAt(0) ?? 0;
12294
- const \u5272\u308A\u623B\u3057 = bound === "drawn" && !isEmojiGrapheme(ch, code) ? isAscii(code) ? DRAWN_ASCII_RATIO : isCJK(code) ? DRAWN_CJK_RATIO : 1 : 1;
12295
- if (isEmojiGrapheme(ch, code)) {
12296
- advanceEmSum += fontFamily === "mono" ? MONO_EMOJI_ADVANCE_EM : EMOJI_ADVANCE_EM;
12297
- continue;
12298
- }
12299
- if (fontFamily === "mono") {
12300
- advanceEmSum += (isCJK(code) ? 1.08 : JETBRAINS_MONO_ADVANCE_EM) / \u5272\u308A\u623B\u3057;
12301
- continue;
12302
- }
12303
- if (isCJK(code)) {
12304
- advanceEmSum += 1.08 / \u5272\u308A\u623B\u3057;
12305
- continue;
12306
- }
12307
- const table = ch.length === 1 ? INTER_BOLD_ADVANCE_EM[ch] : void 0;
12308
- advanceEmSum += (table !== void 0 ? table : defaultAdvanceEm(ch, code)) / \u5272\u308A\u623B\u3057;
12309
- }
12310
- const w = advanceEmSum * fontSize + letterSpacing * charCount;
12311
- return bound === "drawn" ? w : Math.max(w, fontSize * 1.2);
12312
- }
12313
- function \u53CE\u3081\u308B\u500D\u7387(text, opts, \u5E45) {
12314
- if (!(\u5E45 > 0) || !(opts.fontSize > 0)) return 1;
12315
- const \u5B9F\u5E45 = measureTextWidth(text, { ...opts, letterSpacing: 0 });
12316
- return \u5B9F\u5E45 > \u5E45 ? \u5E45 / \u5B9F\u5E45 : 1;
12317
- }
12318
-
12319
12365
  // src/label-text.ts
12320
12366
  var EDGE_LABEL_TEXT = {
12321
12367
  // main 行は family を指定せず、 host 側の指定を継承する。
@@ -12675,15 +12721,22 @@ function requiredVerticalLabelGap(pillHs) {
12675
12721
  const step = parallelLabelStepY(pillHs);
12676
12722
  return (pillHs.length - 1) * step + Math.max(first, last) + CLEARANCE_NODE_LABEL * 2;
12677
12723
  }
12678
- function computeLabelBoxW(label, sub) {
12679
- const mainW = measureTextWidth(label ?? "", { fontSize: EDGE_LABEL_TEXT.main.fontSize });
12680
- const subW = sub ? measureTextWidth(sub, { fontSize: EDGE_LABEL_TEXT.sub.fontSize, fontFamily: "mono" }) : 0;
12724
+ function computeLabelBoxW(label, sub, textMetrics = "proportional") {
12725
+ const mainW = measureTextWidth(label ?? "", {
12726
+ fontSize: EDGE_LABEL_TEXT.main.fontSize,
12727
+ textMetrics
12728
+ });
12729
+ const subW = sub ? measureTextWidth(sub, {
12730
+ fontSize: EDGE_LABEL_TEXT.sub.fontSize,
12731
+ fontFamily: "mono",
12732
+ textMetrics
12733
+ }) : 0;
12681
12734
  const raw = Math.max(mainW, subW) + LABEL_PILL_PAD_X * 2;
12682
12735
  const EPSILON = 1e-6;
12683
12736
  return Math.ceil((raw - EPSILON) / 2) * 2;
12684
12737
  }
12685
- function computeLabelBBoxWorld(edge) {
12686
- const boxW = computeLabelBoxW(edge.label, edge.sub);
12738
+ function computeLabelBBoxWorld(edge, textMetrics = "proportional") {
12739
+ const boxW = computeLabelBoxW(edge.label, edge.sub, textMetrics);
12687
12740
  const boxH = edge.sub ? LABEL_PILL_H_WITH_SUB : LABEL_PILL_H_MAIN_ONLY;
12688
12741
  const anchor = edge.labelAnchor;
12689
12742
  const boxLeftX = anchor === "start" ? 0 : anchor === "end" ? -boxW : -boxW / 2;
@@ -12922,7 +12975,7 @@ function footerShapeDrawTop(node) {
12922
12975
  // src/layout/collisions.ts
12923
12976
  var LANE_LABEL_CLEARANCE_MARGIN = 2;
12924
12977
  var NEAR_MISS_MARGIN = LANE_LABEL_CLEARANCE_MARGIN;
12925
- function collectBBoxes(lanes, nodes, edges) {
12978
+ function collectBBoxes(lanes, nodes, edges, textMetrics = "proportional") {
12926
12979
  const out = [];
12927
12980
  for (const lane of lanes) {
12928
12981
  if (!lane.label) continue;
@@ -12931,7 +12984,7 @@ function collectBBoxes(lanes, nodes, edges) {
12931
12984
  id: lane.id,
12932
12985
  x: lane.x + 16,
12933
12986
  y: lane.y + 8,
12934
- w: measureTextWidth(lane.label, { fontSize: 20, letterSpacing: 2 }) + 24,
12987
+ w: measureTextWidth(lane.label, { fontSize: 20, letterSpacing: 2, textMetrics }) + 24,
12935
12988
  h: 28
12936
12989
  });
12937
12990
  }
@@ -12949,7 +13002,7 @@ function collectBBoxes(lanes, nodes, edges) {
12949
13002
  }
12950
13003
  for (const e of edges) {
12951
13004
  if (!hasRenderedLabel(e)) continue;
12952
- const bbox = computeLabelBBoxWorld(e);
13005
+ const bbox = computeLabelBBoxWorld(e, textMetrics);
12953
13006
  out.push({
12954
13007
  kind: "edge-label",
12955
13008
  id: e.id,
@@ -13647,10 +13700,10 @@ function forEachCandidatePair(bboxes, margin, visit) {
13647
13700
  }
13648
13701
  }
13649
13702
  }
13650
- function resolveEdgeLabelOverlapsWithChain(edges, fixedObstacles, minClearance = 16, maxIter = 20) {
13703
+ function resolveEdgeLabelOverlapsWithChain(edges, fixedObstacles, minClearance = 16, maxIter = 20, textMetrics = "proportional") {
13651
13704
  if (edges.length === 0) return edges;
13652
13705
  const labelBBox = (e, offsetX, offsetY) => {
13653
- const base = computeLabelBBoxWorld(e);
13706
+ const base = computeLabelBBoxWorld(e, textMetrics);
13654
13707
  return {
13655
13708
  kind: "edge-label",
13656
13709
  id: e.id,
@@ -13751,7 +13804,7 @@ function clampShiftMagnitude(shift, maxMagnitude) {
13751
13804
  };
13752
13805
  return { dx: clampAxis(shift.dx), dy: clampAxis(shift.dy) };
13753
13806
  }
13754
- function resolveEdgeLabelOverlapsWithChainAndPropagate(edges, obstacles, minClearance = 16, maxIter = 20, pathLabelClearance = LABEL_TO_PATH_CLEARANCE) {
13807
+ function resolveEdgeLabelOverlapsWithChainAndPropagate(edges, obstacles, minClearance = 16, maxIter = 20, pathLabelClearance = LABEL_TO_PATH_CLEARANCE, textMetrics = "proportional") {
13755
13808
  if (edges.length === 0) {
13756
13809
  return {
13757
13810
  edges,
@@ -13762,7 +13815,7 @@ function resolveEdgeLabelOverlapsWithChainAndPropagate(edges, obstacles, minClea
13762
13815
  }
13763
13816
  const MAX_ACCUMULATED_SHIFT = CHAIN_SHIFT_MAX_ACCUMULATED;
13764
13817
  const labelBBox = (e, offsetX, offsetY) => {
13765
- const base = computeLabelBBoxWorld(e);
13818
+ const base = computeLabelBBoxWorld(e, textMetrics);
13766
13819
  return {
13767
13820
  kind: "edge-label",
13768
13821
  id: e.id,
@@ -14363,11 +14416,15 @@ var \u5411\u304D\u306E\u9806 = [
14363
14416
  { axis: "x", sign: -1, \u540D\u524D: "\u5DE6" },
14364
14417
  { axis: "x", sign: 1, \u540D\u524D: "\u53F3" }
14365
14418
  ];
14366
- function \u672D\u304C\u52D5\u3051\u306A\u3044\u7406\u7531(labelId, \u76F8\u624B, edges, obstacles) {
14419
+ function \u672D\u304C\u52D5\u3051\u306A\u3044\u7406\u7531(labelId, \u76F8\u624B, edges, obstacles, textMetrics = "proportional") {
14367
14420
  const edgeById = new Map(edges.map((e) => [e.id, e]));
14368
14421
  const \u81EA\u5206 = edgeById.get(labelId);
14369
14422
  if (!\u81EA\u5206) return null;
14370
- const labels = edges.filter((e) => e.label?.trim() || e.sub?.trim()).map((e) => ({ kind: "edge-label", id: e.id, ...computeLabelBBoxWorld(e) }));
14423
+ const labels = edges.filter((e) => e.label?.trim() || e.sub?.trim()).map((e) => ({
14424
+ kind: "edge-label",
14425
+ id: e.id,
14426
+ ...computeLabelBBoxWorld(e, textMetrics)
14427
+ }));
14371
14428
  const label = labels.find((l) => l.id === labelId);
14372
14429
  if (!label) return null;
14373
14430
  const \u6E2C\u308A\u65B9 = \u7DDA\u306E\u6E2C\u308A\u65B9\u3092\u4F5C\u308B();
@@ -14409,7 +14466,7 @@ function \u672D\u304C\u52D5\u3051\u306A\u3044\u7406\u7531(labelId, \u76F8\u624B,
14409
14466
  }
14410
14467
  return `\u9003\u3052\u5834\u306A\u3057: ${\u7406\u7531.sort((a, b) => a.\u9806 - b.\u9806).map((r) => r.\u6587).join(" / ")}`;
14411
14468
  }
14412
- function resolveLabelClearanceAfterPathPasses(edges, obstacles, maxIter = 8) {
14469
+ function resolveLabelClearanceAfterPathPasses(edges, obstacles, maxIter = 8, textMetrics = "proportional") {
14413
14470
  if (edges.length === 0) return edges;
14414
14471
  const labeledIds = new Set(
14415
14472
  edges.filter((e) => e.label?.trim() || e.sub?.trim()).map((e) => e.id)
@@ -14427,7 +14484,7 @@ function resolveLabelClearanceAfterPathPasses(edges, obstacles, maxIter = 8) {
14427
14484
  const out = [];
14428
14485
  for (const e of edges) {
14429
14486
  if (!labeledIds.has(e.id)) continue;
14430
- const base = computeLabelBBoxWorld(e);
14487
+ const base = computeLabelBBoxWorld(e, textMetrics);
14431
14488
  const s = getShift(e.id);
14432
14489
  out.push({ kind: "edge-label", id: e.id, x: base.x + s.dx, y: base.y + s.dy, w: base.w, h: base.h });
14433
14490
  }
@@ -14560,7 +14617,7 @@ function applyEdgeLabelAndPathShifts(edges, labelShiftMap, edgePathShiftMap) {
14560
14617
 
14561
14618
  // src/layout/curve-path.ts
14562
14619
  var SAME_HEIGHT_THRESHOLD = 1;
14563
- function curvePath(from, to, edge, labelMarginExtra = 0) {
14620
+ function curvePath(from, to, edge, labelMarginExtra = 0, textMetrics = "proportional") {
14564
14621
  const fromLeft = from.cx - from.w / 2;
14565
14622
  const fromRight = from.cx + from.w / 2;
14566
14623
  const toLeft = to.cx - to.w / 2;
@@ -14628,7 +14685,7 @@ function curvePath(from, to, edge, labelMarginExtra = 0) {
14628
14685
  normalX *= -1;
14629
14686
  normalY *= -1;
14630
14687
  }
14631
- const labelW = computeLabelBoxW(edge?.label, edge?.sub);
14688
+ const labelW = computeLabelBoxW(edge?.label, edge?.sub, textMetrics);
14632
14689
  const labelH = labelPillH(edge?.sub);
14633
14690
  const distance = labelPathClearanceHorizontal(edge) + (Math.abs(normalX) * labelW + Math.abs(normalY) * labelH) / 2 + labelMarginExtra;
14634
14691
  return {
@@ -14660,7 +14717,7 @@ function polyline(points) {
14660
14717
  });
14661
14718
  return distinct.map((p, i) => `${i === 0 ? "M" : "L"} ${point(p)}`).join(" ");
14662
14719
  }
14663
- function metroPath(from, to, edge, labelMarginExtra = 0) {
14720
+ function metroPath(from, to, edge, labelMarginExtra = 0, textMetrics = "proportional") {
14664
14721
  const fromLeft = from.cx - from.w / 2;
14665
14722
  const fromRight = from.cx + from.w / 2;
14666
14723
  const toLeft = to.cx - to.w / 2;
@@ -14771,7 +14828,7 @@ function metroPath(from, to, edge, labelMarginExtra = 0) {
14771
14828
  normalX *= -1;
14772
14829
  normalY *= -1;
14773
14830
  }
14774
- const labelW = computeLabelBoxW(edge?.label, edge?.sub);
14831
+ const labelW = computeLabelBoxW(edge?.label, edge?.sub, textMetrics);
14775
14832
  const labelH = labelPillH(edge?.sub);
14776
14833
  const distance = labelPathClearanceHorizontal(edge) + (Math.abs(normalX) * labelW + Math.abs(normalY) * labelH) / 2 + labelMarginExtra;
14777
14834
  return {
@@ -14940,9 +14997,9 @@ function \u66F8\u3044\u305F\u5024\u304B\u63A7\u3048(\u66F8\u3044\u305F, \u63A7\u
14940
14997
  const v = (\u66F8\u3044\u305F ?? "").trim();
14941
14998
  return v === "" ? \u63A7\u3048 : v;
14942
14999
  }
14943
- function \u5E45\u306E\u500D\u7387(text, size, letterSpacing, \u5E45) {
15000
+ function \u5E45\u306E\u500D\u7387(text, size, letterSpacing, \u5E45, textMetrics = "proportional") {
14944
15001
  if (!(\u5E45 > 0) || !(size > 0)) return 1;
14945
- const \u5B9F\u5E45 = textWidth(text, size, letterSpacing);
15002
+ const \u5B9F\u5E45 = textWidth(text, size, letterSpacing, textMetrics);
14946
15003
  return \u5B9F\u5E45 > \u5E45 ? \u5E45 / \u5B9F\u5E45 : 1;
14947
15004
  }
14948
15005
  function \u8AAD\u3081\u308B\u4E0B\u9650\u306E\u500D\u7387(\u5927\u304D\u3055) {
@@ -15157,13 +15214,13 @@ function fitArt(region, extent, art) {
15157
15214
  );
15158
15215
  }
15159
15216
  var \u5E2F\u306E\u9AD8\u3055\u306B\u5BFE\u3059\u308B\u4E0A\u9650 = 0.8;
15160
- function \u7D75\u306E\u4E2D\u306E\u5B57\u306E\u5E45(text, size, letterSpacing = 0) {
15217
+ function \u7D75\u306E\u4E2D\u306E\u5B57\u306E\u5E45(text, size, letterSpacing = 0, textMetrics = "proportional") {
15161
15218
  return Math.max(
15162
15219
  displayWidth(text) * size * MONO_ADVANCE_RATIO,
15163
- textWidth(text, size, letterSpacing)
15220
+ textWidth(text, size, letterSpacing, textMetrics)
15164
15221
  );
15165
15222
  }
15166
- function \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u5B57\u3089) {
15223
+ function \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u5B57\u3089, textMetrics = "proportional") {
15167
15224
  const \u623B\u3057 = Number.isFinite(\u500D\u7387) && \u500D\u7387 > 0 ? 1 / \u500D\u7387 : 1;
15168
15225
  let \u4E0A\u9650 = Number.POSITIVE_INFINITY;
15169
15226
  for (const \u5B572 of \u5B57\u3089) {
@@ -15172,7 +15229,7 @@ function \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u5B57\u3089)
15172
15229
  if (Number.isFinite(\u9AD8\u3055) && \u9AD8\u3055 > 0) {
15173
15230
  \u4E0A\u9650 = Math.min(\u4E0A\u9650, \u9AD8\u3055 * \u5E2F\u306E\u9AD8\u3055\u306B\u5BFE\u3059\u308B\u4E0A\u9650 / \u5B572.size);
15174
15231
  }
15175
- const \u5B9F\u5E45 = \u7D75\u306E\u4E2D\u306E\u5B57\u306E\u5E45(\u5B572.text, \u5B572.size, \u5B572.letterSpacing ?? 0);
15232
+ const \u5B9F\u5E45 = \u7D75\u306E\u4E2D\u306E\u5B57\u306E\u5E45(\u5B572.text, \u5B572.size, \u5B572.letterSpacing ?? 0, textMetrics);
15176
15233
  if (Number.isFinite(\u5E45) && \u5E45 > 0 && \u5B9F\u5E45 > 0) {
15177
15234
  \u4E0A\u9650 = Math.min(\u4E0A\u9650, \u5E45 / \u5B9F\u5E45);
15178
15235
  }
@@ -16028,9 +16085,14 @@ function \u6728\u306E\u5F62(treeNodes) {
16028
16085
  return { \u8449\u306E\u6570, \u6BB5\u6570 };
16029
16086
  }
16030
16087
  var \u6728\u306E\u679D\u306E\u592A\u3055 = (\u6BB5) => Math.max(1.1, 2.6 - \u6BB5 * 0.45);
16031
- function \u6728\u306E\u4E2D\u8EAB(node, stateValues = {}) {
16088
+ function \u6728\u306E\u4E2D\u8EAB(node, stateValues = {}, textMetrics = "proportional") {
16032
16089
  const treeNodes = resolveTreeData(node.treeData ?? [], stateValues);
16033
- return computeTreeLayout(treeNodes, node.w - PAD_LEFT - PAD_RIGHT, node.h - PAD_TOP - PAD_BOTTOM);
16090
+ return computeTreeLayout(
16091
+ treeNodes,
16092
+ node.w - PAD_LEFT - PAD_RIGHT,
16093
+ node.h - PAD_TOP - PAD_BOTTOM,
16094
+ textMetrics
16095
+ );
16034
16096
  }
16035
16097
  function \u6728\u306E\u884C(n) {
16036
16098
  return [
@@ -16043,12 +16105,14 @@ function TreeNode({
16043
16105
  active,
16044
16106
  stateValues = {},
16045
16107
  drawing = false,
16046
- progress = 1
16108
+ progress = 1,
16109
+ textMetrics = "proportional"
16047
16110
  }) {
16048
16111
  const x0 = node.cx - node.w / 2;
16049
16112
  const y0 = node.cy - node.h / 2;
16050
16113
  const gradientId = `tree-root-grad-${node.id}`;
16051
- const layout2 = \u6728\u306E\u4E2D\u8EAB(node, stateValues);
16114
+ const layout2 = \u6728\u306E\u4E2D\u8EAB(node, stateValues, textMetrics);
16115
+ const \u6E2C\u308B = \u7BB1\u306E\u5B57\u3092\u6E2C\u308B(textMetrics);
16052
16116
  const \u4F38\u3073 = \u9032\u307F\u3092\u7573\u3080(drawing, progress);
16053
16117
  const \u6700\u5927\u6DF1\u3055 = layout2.nodes.reduce((m, n) => Math.max(m, n.depth), 0);
16054
16118
  const \u7BB1\u304C\u51FA\u308B = (\u6DF1\u3055) => !drawing || \u6BB5\u306E\u4F38\u3073(\u4F38\u3073, \u6DF1\u3055, \u6700\u5927\u6DF1\u3055) >= 1;
@@ -16102,10 +16166,10 @@ function TreeNode({
16102
16166
  const accent = depthColors[Math.min(n.depth, depthColors.length - 1)] ?? depthColors[0];
16103
16167
  const isRoot = n.depth === 0;
16104
16168
  const \u6750\u6599 = \u6728\u306E\u884C(n);
16105
- const \u884C = \u7BB1\u306B\u7A4D\u3080(\u6750\u6599, n.w, n.h);
16169
+ const \u884C = \u7BB1\u306B\u7A4D\u3080(\u6750\u6599, n.w, n.h, \u6E2C\u308B);
16106
16170
  const \u88DC\u8DB3\u3042\u308A = (n.subtitle ?? "").trim() !== "";
16107
16171
  const \u540D\u524D = \u6750\u6599[0];
16108
- const \u53CE\u3081\u305F\u540D\u524D = \u88DC\u8DB3\u3042\u308A ? void 0 : \u5E45\u306B\u53CE\u3081\u308B(\u540D\u524D.text, \u540D\u524D.fontSize, \u4F7F\u3048\u308B\u5E45(n.w));
16172
+ const \u53CE\u3081\u305F\u540D\u524D = \u88DC\u8DB3\u3042\u308A ? void 0 : \u5E45\u306B\u53CE\u3081\u308B(\u540D\u524D.text, \u540D\u524D.fontSize, \u4F7F\u3048\u308B\u5E45(n.w), \u6E2C\u308B);
16109
16173
  return /* @__PURE__ */ jsxRuntime.jsx(
16110
16174
  "g",
16111
16175
  {
@@ -16187,7 +16251,7 @@ function TreeNode({
16187
16251
  })
16188
16252
  ] });
16189
16253
  }
16190
- function computeTreeLayout(treeNodes, canvasW, canvasH) {
16254
+ function computeTreeLayout(treeNodes, canvasW, canvasH, textMetrics = "proportional") {
16191
16255
  const ids = new Set(treeNodes.map((n) => n.id));
16192
16256
  const childrenOf = /* @__PURE__ */ new Map();
16193
16257
  for (const n of treeNodes) {
@@ -16235,7 +16299,7 @@ function computeTreeLayout(treeNodes, canvasW, canvasH) {
16235
16299
  const \u7BB1\u306E\u5E45 = (n, depth) => {
16236
16300
  const \u6750\u6599 = \u6728\u306E\u884C({ ...n, depth });
16237
16301
  const \u540D\u524D = \u6750\u6599[0];
16238
- const \u8981\u308B = measureTextWidth(\u540D\u524D.text, { fontSize: \u540D\u524D.fontSize}) + (nodeW - \u4F7F\u3048\u308B\u5E45(nodeW));
16302
+ const \u8981\u308B = measureTextWidth(\u540D\u524D.text, { fontSize: \u540D\u524D.fontSize, textMetrics }) + (nodeW - \u4F7F\u3048\u308B\u5E45(nodeW));
16239
16303
  return Math.min(Math.max(\u8981\u308B, nodeW), slotW * 0.92);
16240
16304
  };
16241
16305
  const \u8449\u306E\u4E26\u3073 = [];
@@ -16339,7 +16403,7 @@ var BRANCH_BOX_H_MAX = 48;
16339
16403
  var SUB_BOX_H_MAX = 40;
16340
16404
  var \u7E26\u306E\u9593\u9694\u306E\u4E0A\u9650 = (\u679D\u306E\u6A2A\u306E\u4F38\u3073) => \u679D\u306E\u6A2A\u306E\u4F38\u3073;
16341
16405
  var MIND_PAD = 40;
16342
- function \u653E\u5C04\u306E\u4E2D\u8EAB(node, stateValues = {}) {
16406
+ function \u653E\u5C04\u306E\u4E2D\u8EAB(node, stateValues = {}, textMetrics = "proportional") {
16343
16407
  const mindData = node.mindData ? resolveMindData(node.mindData, stateValues) : void 0;
16344
16408
  if (!mindData) return void 0;
16345
16409
  return computeMindMapLayout(
@@ -16347,7 +16411,8 @@ function \u653E\u5C04\u306E\u4E2D\u8EAB(node, stateValues = {}) {
16347
16411
  node.w / 2,
16348
16412
  node.h / 2,
16349
16413
  node.w - MIND_PAD * 2,
16350
- node.h - MIND_PAD * 2
16414
+ node.h - MIND_PAD * 2,
16415
+ textMetrics
16351
16416
  );
16352
16417
  }
16353
16418
  function \u653E\u5C04\u306E\u884C(n) {
@@ -16361,12 +16426,14 @@ function MindMapNode({
16361
16426
  active,
16362
16427
  stateValues = {},
16363
16428
  drawing = false,
16364
- progress = 1
16429
+ progress = 1,
16430
+ textMetrics = "proportional"
16365
16431
  }) {
16366
16432
  const x0 = node.cx - node.w / 2;
16367
16433
  const y0 = node.cy - node.h / 2;
16368
- const layout2 = \u653E\u5C04\u306E\u4E2D\u8EAB(node, stateValues);
16434
+ const layout2 = \u653E\u5C04\u306E\u4E2D\u8EAB(node, stateValues, textMetrics);
16369
16435
  if (!layout2) return /* @__PURE__ */ jsxRuntime.jsx("g", { transform: `translate(${x0} ${y0})` });
16436
+ const \u6E2C\u308B = \u7BB1\u306E\u5B57\u3092\u6E2C\u308B(textMetrics);
16370
16437
  const \u4F38\u3073 = \u9032\u307F\u3092\u7573\u3080(drawing, progress);
16371
16438
  const \u6700\u5927\u6DF1\u3055 = layout2.nodes.reduce((m, n) => Math.max(m, n.depth), 0);
16372
16439
  const \u7BB1\u304C\u51FA\u308B = (\u6DF1\u3055) => !drawing || \u6BB5\u306E\u4F38\u3073(\u4F38\u3073, \u6DF1\u3055, \u6700\u5927\u6DF1\u3055) >= 1;
@@ -16413,8 +16480,13 @@ function MindMapNode({
16413
16480
  const \u6587\u5B57\u306E\u5BC4\u305B = \u67A0\u306A\u3057 ? \u5916\u3078 ? "start" : "end" : "middle";
16414
16481
  const \u63CF\u753B\u57DF\u306E\u7AEF = \u5916\u3078 ? node.w - MIND_PAD : MIND_PAD;
16415
16482
  const \u4F7F\u3048\u308B = \u67A0\u306A\u3057 ? Math.abs(\u63CF\u753B\u57DF\u306E\u7AEF - \u6587\u5B57\u306Ex) : \u4F7F\u3048\u308B\u5E45(n.w);
16416
- const \u53CE\u3081\u305F\u540D\u524D = \u88DC\u8DB3\u3042\u308A ? void 0 : \u5E45\u306B\u53CE\u3081\u308B(\u540D\u524D.text, \u540D\u524D.fontSize, \u4F7F\u3048\u308B);
16417
- const \u884C = \u7BB1\u306B\u7A4D\u3080(\u6750\u6599, \u67A0\u306A\u3057 ? \u4F7F\u3048\u308B + (n.w - \u4F7F\u3048\u308B\u5E45(n.w)) : n.w, n.h);
16483
+ const \u53CE\u3081\u305F\u540D\u524D = \u88DC\u8DB3\u3042\u308A ? void 0 : \u5E45\u306B\u53CE\u3081\u308B(\u540D\u524D.text, \u540D\u524D.fontSize, \u4F7F\u3048\u308B, \u6E2C\u308B);
16484
+ const \u884C = \u7BB1\u306B\u7A4D\u3080(
16485
+ \u6750\u6599,
16486
+ \u67A0\u306A\u3057 ? \u4F7F\u3048\u308B + (n.w - \u4F7F\u3048\u308B\u5E45(n.w)) : n.w,
16487
+ n.h,
16488
+ \u6E2C\u308B
16489
+ );
16418
16490
  const \u6587\u5B57\u306E\u8272 = n.isRoot ? "var(--cdl-text-on-tone, #ffffff)" : "var(--cdl-chip-text, #1a1f2a)";
16419
16491
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { "data-cdl-unresolved": n.unresolved ? "true" : void 0, children: [
16420
16492
  \u67A0\u306A\u3057 ? null : /* @__PURE__ */ jsxRuntime.jsx(
@@ -16466,14 +16538,14 @@ function MindMapNode({
16466
16538
  })
16467
16539
  ] });
16468
16540
  }
16469
- function \u63CF\u304F\u6A2A\u306E\u7AEF(n) {
16541
+ function \u63CF\u304F\u6A2A\u306E\u7AEF(n, textMetrics = "proportional") {
16470
16542
  if (n.isRoot || !n.isLeaf) return [n.x - n.w / 2, n.x + n.w / 2];
16471
16543
  const \u8D77\u70B9 = n.x + (n.side === "right" ? -n.w / 2 : n.w / 2);
16472
16544
  const \u540D\u524D = \u653E\u5C04\u306E\u884C(n)[0];
16473
- const \u5E45 = textWidth(\u540D\u524D.text, \u540D\u524D.fontSize);
16545
+ const \u5E45 = textWidth(\u540D\u524D.text, \u540D\u524D.fontSize, 0, textMetrics);
16474
16546
  return n.side === "right" ? [\u8D77\u70B9, \u8D77\u70B9 + \u5E45] : [\u8D77\u70B9 - \u5E45, \u8D77\u70B9];
16475
16547
  }
16476
- function computeMindMapLayout(mindData, cx, cy, canvasW, canvasH) {
16548
+ function computeMindMapLayout(mindData, cx, cy, canvasW, canvasH, textMetrics = "proportional") {
16477
16549
  const nodes = [];
16478
16550
  const edges = [];
16479
16551
  const rootW = 120;
@@ -16551,7 +16623,7 @@ function computeMindMapLayout(mindData, cx, cy, canvasW, canvasH) {
16551
16623
  const PREFERRED_GAP = MIND_BOX_GAP;
16552
16624
  const \u679D\u306E\u540D\u524D\u306E\u5E45 = (title) => {
16553
16625
  const \u540D\u524D = \u653E\u5C04\u306E\u884C({ title, isRoot: false })[0];
16554
- return textWidth(\u540D\u524D.text, \u540D\u524D.fontSize);
16626
+ return textWidth(\u540D\u524D.text, \u540D\u524D.fontSize, 0, textMetrics);
16555
16627
  };
16556
16628
  const \u679D\u306E\u6A2A\u3092\u6C7A\u3081\u308B = (br) => {
16557
16629
  const maxSubDepth = subDepthOf(br.id, /* @__PURE__ */ new Set());
@@ -16669,7 +16741,7 @@ function computeMindMapLayout(mindData, cx, cy, canvasW, canvasH) {
16669
16741
  let maxExtentX = rootW / 2;
16670
16742
  let maxExtentY = rootH / 2;
16671
16743
  for (const n of nodes) {
16672
- const [\u5DE6, \u53F3] = \u63CF\u304F\u6A2A\u306E\u7AEF(n);
16744
+ const [\u5DE6, \u53F3] = \u63CF\u304F\u6A2A\u306E\u7AEF(n, textMetrics);
16673
16745
  maxExtentX = Math.max(maxExtentX, Math.abs(\u5DE6 - cx), Math.abs(\u53F3 - cx));
16674
16746
  maxExtentY = Math.max(maxExtentY, Math.abs(n.y - cy) + n.h / 2);
16675
16747
  }
@@ -16689,7 +16761,7 @@ function computeMindMapLayout(mindData, cx, cy, canvasW, canvasH) {
16689
16761
  let \u5DE6\u7AEF = Number.POSITIVE_INFINITY;
16690
16762
  let \u53F3\u7AEF = Number.NEGATIVE_INFINITY;
16691
16763
  for (const n of nodes) {
16692
- const [l, r] = \u63CF\u304F\u6A2A\u306E\u7AEF(n);
16764
+ const [l, r] = \u63CF\u304F\u6A2A\u306E\u7AEF(n, textMetrics);
16693
16765
  \u5DE6\u7AEF = Math.min(\u5DE6\u7AEF, l);
16694
16766
  \u53F3\u7AEF = Math.max(\u53F3\u7AEF, r);
16695
16767
  }
@@ -16932,10 +17004,16 @@ function emptyCounts() {
16932
17004
  "validation-interrupted": 0
16933
17005
  };
16934
17006
  }
16935
- function \u7A4D\u3080\u7BB1\u3092\u96C6\u3081\u308B(n) {
16936
- const \u7BB1 = (b, \u884C) => ({ \u884C, w: b.w, h: b.h });
16937
- if (n.kind === "tree-hierarchy") return \u6728\u306E\u4E2D\u8EAB(n).nodes.map((b) => \u7BB1(b, \u6728\u306E\u884C(b)));
16938
- if (n.kind === "mind-map") return (\u653E\u5C04\u306E\u4E2D\u8EAB(n)?.nodes ?? []).map((b) => \u7BB1(b, \u653E\u5C04\u306E\u884C(b)));
17007
+ function \u7A4D\u3080\u7BB1\u3092\u96C6\u3081\u308B(n, textMetrics = "proportional") {
17008
+ const \u7BB1 = (b, \u884C, \u6E2C\u308B) => ({ \u884C, w: b.w, h: b.h, \u6E2C\u308B });
17009
+ if (n.kind === "tree-hierarchy") {
17010
+ const \u6E2C\u308B = \u7BB1\u306E\u5B57\u3092\u6E2C\u308B(textMetrics);
17011
+ return \u6728\u306E\u4E2D\u8EAB(n, {}, textMetrics).nodes.map((b) => \u7BB1(b, \u6728\u306E\u884C(b), \u6E2C\u308B));
17012
+ }
17013
+ if (n.kind === "mind-map") {
17014
+ const \u6E2C\u308B = \u7BB1\u306E\u5B57\u3092\u6E2C\u308B(textMetrics);
17015
+ return (\u653E\u5C04\u306E\u4E2D\u8EAB(n, {}, textMetrics)?.nodes ?? []).map((b) => \u7BB1(b, \u653E\u5C04\u306E\u884C(b), \u6E2C\u308B));
17016
+ }
16939
17017
  return [];
16940
17018
  }
16941
17019
  function measureStubOut(segs) {
@@ -17621,6 +17699,7 @@ function \u4F4D\u7F6E\u3092\u624B\u3067\u66F8\u3044\u305F(n) {
17621
17699
  return n.posX !== void 0 && n.posY !== void 0;
17622
17700
  }
17623
17701
  function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5668) {
17702
+ const textMetrics = laid.textMetrics ?? "proportional";
17624
17703
  const LIFELINE_W_THRESHOLD = 8;
17625
17704
  for (const n of laid.nodes) {
17626
17705
  if (n.w < LIFELINE_W_THRESHOLD) continue;
@@ -17632,7 +17711,7 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17632
17711
  );
17633
17712
  }
17634
17713
  }
17635
- const bboxes = collectBBoxes(laid.lanes, laid.nodes, laid.edges);
17714
+ const bboxes = collectBBoxes(laid.lanes, laid.nodes, laid.edges, textMetrics);
17636
17715
  const collisions = detectCollisions(bboxes, laid.edges);
17637
17716
  for (const c of collisions) {
17638
17717
  const involvesEdgeLabel = c.a.kind === "edge-label" || c.b.kind === "edge-label";
@@ -17652,7 +17731,11 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17652
17731
  if (!titleTrimmed) continue;
17653
17732
  const \u4F59\u767D = drawsTitleOutsideBox(n.kind) ? 0 : TITLE_BOX_PADDING;
17654
17733
  const \u4F7F\u3048\u308B\u5E452 = n.w - \u4F59\u767D;
17655
- const \u5B9F\u5E45 = measureTextWidth(titleTrimmed, { fontSize: titleFontSize(n.kind), bound: "drawn" });
17734
+ const \u5B9F\u5E45 = measureTextWidth(titleTrimmed, {
17735
+ fontSize: titleFontSize(n.kind),
17736
+ bound: "drawn",
17737
+ textMetrics
17738
+ });
17656
17739
  if (titleScalesToFit(n.kind, n.h)) {
17657
17740
  const \u7E2E\u3081\u305F\u5927\u304D\u3055 = \u5B9F\u5E45 > 0 ? titleFontSize(n.kind) * Math.min(1, \u4F7F\u3048\u308B\u5E452 / \u5B9F\u5E45) : titleFontSize(n.kind);
17658
17741
  if (\u7E2E\u3081\u305F\u5927\u304D\u3055 < MIN_TITLE_FONT_SIZE) {
@@ -17720,7 +17803,13 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17720
17803
  const b\u306F\u672D = n.b.kind === "edge-label";
17721
17804
  const \u52D5\u304B\u3059 = a\u306F\u672D && b\u306F\u672D ? (\u8FBA\u306E\u9806.get(n.a.id) ?? 0) > (\u8FBA\u306E\u9806.get(n.b.id) ?? 0) ? n.a : n.b : a\u306F\u672D ? n.a : b\u306F\u672D ? n.b : null;
17722
17805
  const \u76F8\u624B = \u52D5\u304B\u3059 === n.a ? n.b : n.a;
17723
- const reason = \u52D5\u304B\u3059 !== null ? \u672D\u304C\u52D5\u3051\u306A\u3044\u7406\u7531(\u52D5\u304B\u3059.id, \u76F8\u624B, laid.edges, \u672D\u306E\u969C\u5BB3\u7269) ?? void 0 : void 0;
17806
+ const reason = \u52D5\u304B\u3059 !== null ? \u672D\u304C\u52D5\u3051\u306A\u3044\u7406\u7531(
17807
+ \u52D5\u304B\u3059.id,
17808
+ \u76F8\u624B,
17809
+ laid.edges,
17810
+ \u672D\u306E\u969C\u5BB3\u7269,
17811
+ textMetrics
17812
+ ) ?? void 0 : void 0;
17724
17813
  push(
17725
17814
  "clearance",
17726
17815
  `${n.a.kind}:${n.a.id} \u2194 ${n.b.kind}:${n.b.id} gap=${n.gap.toFixed(1)}px (need ${n.required}px)`,
@@ -17734,7 +17823,10 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17734
17823
  if (!hasRenderedLabel(e)) continue;
17735
17824
  const segs = extractPathSegments(e.d);
17736
17825
  if (segs.length === 0) continue;
17737
- const minDist = measurePathLabelGapSegs(flattenPathSegments(segs), computeLabelBBoxWorld(e));
17826
+ const minDist = measurePathLabelGapSegs(
17827
+ flattenPathSegments(segs),
17828
+ computeLabelBBoxWorld(e, textMetrics)
17829
+ );
17738
17830
  if (!Number.isFinite(minDist)) continue;
17739
17831
  if (minDist > PROXIMITY_ERROR_THRESHOLD) {
17740
17832
  push(
@@ -17784,8 +17876,15 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17784
17876
  }
17785
17877
  for (const e of laid.edges) {
17786
17878
  if (!hasRenderedLabel(e)) continue;
17787
- const mainW = measureTextWidth(e.label ?? "", { fontSize: EDGE_LABEL_TEXT.main.fontSize });
17788
- const subW = e.sub ? measureTextWidth(e.sub, { fontSize: EDGE_LABEL_TEXT.sub.fontSize, fontFamily: "mono" }) : 0;
17879
+ const mainW = measureTextWidth(e.label ?? "", {
17880
+ fontSize: EDGE_LABEL_TEXT.main.fontSize,
17881
+ textMetrics
17882
+ });
17883
+ const subW = e.sub ? measureTextWidth(e.sub, {
17884
+ fontSize: EDGE_LABEL_TEXT.sub.fontSize,
17885
+ fontFamily: "mono",
17886
+ textMetrics
17887
+ }) : 0;
17789
17888
  const expectedBoxW = Math.max(mainW, subW) + LABEL_PILL_PAD_X * 2;
17790
17889
  const bbox = bboxes.find((b) => b.kind === "edge-label" && b.id === e.id);
17791
17890
  if (!bbox) continue;
@@ -17927,7 +18026,9 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17927
18026
  }
17928
18027
  }
17929
18028
  for (const n of laid.nodes) {
17930
- const \u843D\u3068\u3057\u305F = labelPlan(n).\u843D\u3068\u3057\u305F.filter((line) => droppedLineIsHidden(n.kind, line));
18029
+ const \u843D\u3068\u3057\u305F = labelPlan(n).\u843D\u3068\u3057\u305F.filter(
18030
+ (line) => droppedLineIsHidden(n.kind, line)
18031
+ );
17931
18032
  if (\u843D\u3068\u3057\u305F.length === 0) continue;
17932
18033
  push(
17933
18034
  "shape-label-dropped",
@@ -17936,7 +18037,7 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17936
18037
  );
17937
18038
  }
17938
18039
  for (const n of laid.nodes) {
17939
- const \u7BB1 = \u7A4D\u3080\u7BB1\u3092\u96C6\u3081\u308B(n);
18040
+ const \u7BB1 = \u7A4D\u3080\u7BB1\u3092\u96C6\u3081\u308B(n, textMetrics);
17940
18041
  if (\u7BB1.length === 0) continue;
17941
18042
  let \u5BFE\u8C61 = 0;
17942
18043
  const \u843D\u3061\u305F = [];
@@ -17944,7 +18045,7 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
17944
18045
  const \u5BA3\u8A00 = b.\u884C.slice(1).filter((r) => r.text.trim() !== "");
17945
18046
  if (\u5BA3\u8A00.length === 0) continue;
17946
18047
  \u5BFE\u8C61 += 1;
17947
- const \u6B8B\u3063\u305F = new Set(\u7BB1\u306B\u7A4D\u3080(b.\u884C, b.w, b.h).map((r) => r.\u5F79\u5272));
18048
+ const \u6B8B\u3063\u305F = new Set(\u7BB1\u306B\u7A4D\u3080(b.\u884C, b.w, b.h, b.\u6E2C\u308B).map((r) => r.\u5F79\u5272));
17948
18049
  if (\u5BA3\u8A00.every((r) => \u6B8B\u3063\u305F.has(r.\u5F79\u5272))) continue;
17949
18050
  \u843D\u3061\u305F.push({ title: b.\u884C[0]?.text ?? "", h: b.h });
17950
18051
  }
@@ -19007,7 +19108,7 @@ function runAxes(laid, diag, violations, counts, push, profile, skippedAxes, \u5
19007
19108
  const allowedLanes = /* @__PURE__ */ new Set();
19008
19109
  if (fromNode) allowedLanes.add(fromNode.lane);
19009
19110
  if (toNode) allowedLanes.add(toNode.lane);
19010
- const box = computeLabelBBoxWorld(e);
19111
+ const box = computeLabelBBoxWorld(e, textMetrics);
19011
19112
  for (const lane of laid.lanes) {
19012
19113
  if (allowedLanes.has(lane.id)) continue;
19013
19114
  const side = rectCrossesLaneBorder(box, lane, rangeByLane.get(lane.id));
@@ -19385,7 +19486,7 @@ function pickFreeSides(occupied, count) {
19385
19486
  const \u4F7F\u3046 = \u7A7A\u304D.length > 0 ? \u7A7A\u304D : [SELF_LOOP_SIDE_FALLBACK];
19386
19487
  return Array.from({ length: count }, (_, i) => \u4F7F\u3046[i % \u4F7F\u3046.length]);
19387
19488
  }
19388
- function routeSelfLoopGroup(edges, node, side) {
19489
+ function routeSelfLoopGroup(edges, node, side, textMetrics = "proportional") {
19389
19490
  const horizontal = side === "left" || side === "right";
19390
19491
  const g = sideGeometry(node, side);
19391
19492
  const span = fitSpan(horizontal ? node.h : node.w, SELF_LOOP_SPAN);
@@ -19394,7 +19495,7 @@ function routeSelfLoopGroup(edges, node, side) {
19394
19495
  const \u6700\u5916 = controlOffset(SELF_LOOP_OUT + (edges.length - 1) * SELF_LOOP_STAGGER);
19395
19496
  const \u8A9E\u307E\u3067 = \u6700\u5916 + LABEL_TO_PATH_CLEARANCE;
19396
19497
  const \u8A9E\u5E45 = edges.map(
19397
- (e) => horizontal ? labelPillH(e.sub) : computeLabelBoxW(e.label, e.sub)
19498
+ (e) => horizontal ? labelPillH(e.sub) : computeLabelBoxW(e.label, e.sub, textMetrics)
19398
19499
  );
19399
19500
  const \u4F4D\u7F6E = [];
19400
19501
  let \u7A4D = 0;
@@ -19424,7 +19525,7 @@ function routeSelfLoopGroup(edges, node, side) {
19424
19525
  function isSelfLoop(e) {
19425
19526
  return e.from === e.to;
19426
19527
  }
19427
- function layoutSelfLoops(edges, nodes, occupiedBySide) {
19528
+ function layoutSelfLoops(edges, nodes, occupiedBySide, textMetrics = "proportional") {
19428
19529
  const \u5272\u5F53 = /* @__PURE__ */ new Map();
19429
19530
  for (const edge of edges) {
19430
19531
  if (edge.side) continue;
@@ -19451,7 +19552,7 @@ function layoutSelfLoops(edges, nodes, occupiedBySide) {
19451
19552
  if (\u65E2) \u65E2.edges.push(edge);
19452
19553
  else \u675F.set(key, { node, side, edges: [edge] });
19453
19554
  }
19454
- return [...\u675F.values()].flatMap((b) => routeSelfLoopGroup(b.edges, b.node, b.side));
19555
+ return [...\u675F.values()].flatMap((b) => routeSelfLoopGroup(b.edges, b.node, b.side, textMetrics));
19455
19556
  }
19456
19557
 
19457
19558
  // src/layout/tokens.ts
@@ -19669,7 +19770,7 @@ function verticalDetourBlockers(A, B, obstacles) {
19669
19770
  function detourColumnFor(blockers, side) {
19670
19771
  return side === "left" ? Math.min(...blockers.map((n) => n.cx - n.w / 2)) - VERTICAL_DETOUR_GAP : Math.max(...blockers.map((n) => n.cx + n.w / 2)) + VERTICAL_DETOUR_GAP;
19671
19772
  }
19672
- function layoutEdges(diag, nodes, lanes = []) {
19773
+ function layoutEdges(diag, nodes, lanes = [], textMetrics = "proportional") {
19673
19774
  const labelMarginExtra = (diag.viewport?.labelMargin ?? diag.viewport?.gap ?? DEFAULT_LABEL_MARGIN) - DEFAULT_LABEL_MARGIN;
19674
19775
  const nmap = new Map(nodes.map((n) => [n.id, n]));
19675
19776
  const lmap = new Map(lanes.map((l) => [l.id, l]));
@@ -19702,7 +19803,7 @@ function layoutEdges(diag, nodes, lanes = []) {
19702
19803
  const to = nmap.get(e.to);
19703
19804
  if (!from) throw new Error(`cdl layout: edge "${e.id}" \u306E from "${e.from}" \u304C node \u306B\u7121\u3044`);
19704
19805
  if (!to) throw new Error(`cdl layout: edge "${e.id}" \u306E to "${e.to}" \u304C node \u306B\u7121\u3044`);
19705
- const c = curvePath(from, to, e, labelMarginExtra);
19806
+ const c = curvePath(from, to, e, labelMarginExtra, textMetrics);
19706
19807
  positionedEdges.push({
19707
19808
  ...e,
19708
19809
  d: c.d,
@@ -19717,7 +19818,7 @@ function layoutEdges(diag, nodes, lanes = []) {
19717
19818
  const to = nmap.get(e.to);
19718
19819
  if (!from) throw new Error(`cdl layout: edge "${e.id}" \u306E from "${e.from}" \u304C node \u306B\u7121\u3044`);
19719
19820
  if (!to) throw new Error(`cdl layout: edge "${e.id}" \u306E to "${e.to}" \u304C node \u306B\u7121\u3044`);
19720
- const m = metroPath(from, to, e, labelMarginExtra);
19821
+ const m = metroPath(from, to, e, labelMarginExtra, textMetrics);
19721
19822
  positionedEdges.push({
19722
19823
  ...e,
19723
19824
  d: m.d,
@@ -19765,7 +19866,7 @@ function layoutEdges(diag, nodes, lanes = []) {
19765
19866
  \u4F7F\u3046(le.from, le.fromSide);
19766
19867
  \u4F7F\u3046(le.to, le.toSide);
19767
19868
  }
19768
- const loopEdges = layoutSelfLoops(selfLoopEdges, nmap, occupiedBySide);
19869
+ const loopEdges = layoutSelfLoops(selfLoopEdges, nmap, occupiedBySide, textMetrics);
19769
19870
  const labelOffsetsByEdgeId = /* @__PURE__ */ new Map();
19770
19871
  const parallelKey = (p) => p.e.from < p.e.to ? `${p.e.from}::${p.e.to}` : `${p.e.to}::${p.e.from}`;
19771
19872
  const byParallel = /* @__PURE__ */ new Map();
@@ -19919,7 +20020,7 @@ function layoutEdges(diag, nodes, lanes = []) {
19919
20020
  const others = nodes.filter((n) => n.id !== c.from && n.id !== c.to);
19920
20021
  if (others.some((n) => segmentsCrossRect(segs, nodeRect(n)))) return true;
19921
20022
  if (!hasRenderedLabel(c.e)) return false;
19922
- const boxW = computeLabelBoxW(c.e.label, c.e.sub);
20023
+ const boxW = computeLabelBoxW(c.e.label, c.e.sub, textMetrics);
19923
20024
  const boxH = labelPillH(c.e.sub);
19924
20025
  const centerX = columnX - (labelPathClearanceHorizontal(c.e) + boxW / 2);
19925
20026
  const pill = { x: centerX - boxW / 2, y: (exitY + returnY) / 2 - boxH / 2, w: boxW, h: boxH };
@@ -20034,7 +20135,8 @@ function layoutEdges(diag, nodes, lanes = []) {
20034
20135
  allOtherNodes,
20035
20136
  { x: endpointOffset.fromDx, y: endpointOffset.fromDy },
20036
20137
  { x: endpointOffset.toDx, y: endpointOffset.toDy },
20037
- avoidRects
20138
+ avoidRects,
20139
+ textMetrics
20038
20140
  );
20039
20141
  const routed1 = route([]);
20040
20142
  const { d, labelX, labelY, labelAnchor, labelAltX } = routed1;
@@ -20090,13 +20192,13 @@ function layoutEdges(diag, nodes, lanes = []) {
20090
20192
  const pillById = /* @__PURE__ */ new Map();
20091
20193
  for (const r of list) {
20092
20194
  if (!hasRenderedLabel(r.e)) continue;
20093
- const w = computeLabelBoxW(r.e.label, r.e.sub);
20195
+ const w = computeLabelBoxW(r.e.label, r.e.sub, textMetrics);
20094
20196
  const h = labelPillH(r.e.sub);
20095
20197
  pillById.set(r.e.id, { x: r.baseLabelX - w / 2, y: r.baseLabelY - h / 2, w, h });
20096
20198
  }
20097
20199
  for (const le of positionedEdges) {
20098
20200
  if (!hasRenderedLabel(le)) continue;
20099
- const w = computeLabelBoxW(le.label, le.sub);
20201
+ const w = computeLabelBoxW(le.label, le.sub, textMetrics);
20100
20202
  const h = labelPillH(le.sub);
20101
20203
  pillById.set(le.id, { x: le.labelX - w / 2, y: le.labelY - h / 2, w, h });
20102
20204
  }
@@ -20126,7 +20228,7 @@ function layoutEdges(diag, nodes, lanes = []) {
20126
20228
  const laneOfNode = new Map(nodes.map((n) => [n.id, n.lane]));
20127
20229
  for (const r of flippable) {
20128
20230
  const ownSegs = segsByEdgeId.get(r.e.id);
20129
- const boxW = computeLabelBoxW(r.e.label, r.e.sub);
20231
+ const boxW = computeLabelBoxW(r.e.label, r.e.sub, textMetrics);
20130
20232
  const boxH = labelPillH(r.e.sub);
20131
20233
  const pillAt = (centerX) => ({
20132
20234
  x: centerX - boxW / 2,
@@ -20171,7 +20273,7 @@ function layoutEdges(diag, nodes, lanes = []) {
20171
20273
  if (list.length < 2) continue;
20172
20274
  const boxes = list.map((r) => ({
20173
20275
  cx: r.baseLabelX,
20174
- halfW: computeLabelBoxW(r.e.label, r.e.sub) / 2
20276
+ halfW: computeLabelBoxW(r.e.label, r.e.sub, textMetrics) / 2
20175
20277
  }));
20176
20278
  const overlapsX = (i, j) => Math.abs(boxes[i].cx - boxes[j].cx) < boxes[i].halfW + boxes[j].halfW + CLEARANCE_LABEL_LABEL;
20177
20279
  const componentOf = list.map((_, i) => i);
@@ -20221,7 +20323,7 @@ function layoutEdges(diag, nodes, lanes = []) {
20221
20323
  r,
20222
20324
  baseX: r.baseLabelX,
20223
20325
  baseY: r.baseLabelY,
20224
- w: computeLabelBoxW(r.e.label, r.e.sub),
20326
+ w: computeLabelBoxW(r.e.label, r.e.sub, textMetrics),
20225
20327
  h: labelPillH(r.e.sub)
20226
20328
  }));
20227
20329
  items.sort((a, b) => a.baseX - b.baseX);
@@ -20333,7 +20435,7 @@ function singleStraightSegment(d) {
20333
20435
  if (x1 === x2 && y1 === y2) return null;
20334
20436
  return { x1, y1, x2, y2 };
20335
20437
  }
20336
- function bowSharedStraightPaths(edges, nodes, skipIds) {
20438
+ function bowSharedStraightPaths(edges, nodes, skipIds, textMetrics = "proportional") {
20337
20439
  const groups = /* @__PURE__ */ new Map();
20338
20440
  for (const e of edges) {
20339
20441
  if (skipIds.has(e.id)) continue;
@@ -20369,7 +20471,7 @@ function bowSharedStraightPaths(edges, nodes, skipIds) {
20369
20471
  )
20370
20472
  );
20371
20473
  const groupIds = new Set(group.map((g) => g.e.id));
20372
- const labelRects = edges.filter((x) => hasRenderedLabel(x) && !groupIds.has(x.id)).map((x) => computeLabelBBoxWorld(x));
20474
+ const labelRects = edges.filter((x) => hasRenderedLabel(x) && !groupIds.has(x.id)).map((x) => computeLabelBBoxWorld(x, textMetrics));
20373
20475
  const nodeRects = nodes.map((n) => ({ x: n.cx - n.w / 2, y: n.cy - n.h / 2, w: n.w, h: n.h }));
20374
20476
  const build = (seg, offset) => {
20375
20477
  const cx = midX + nx * offset * 2;
@@ -20412,6 +20514,55 @@ function bowSharedStraightPaths(edges, nodes, skipIds) {
20412
20514
  function nodeRect(n) {
20413
20515
  return { x: n.cx - n.w / 2, y: n.cy - n.h / 2, w: n.w, h: n.h };
20414
20516
  }
20517
+ function countPathObstacleCrossings(d, obstacles) {
20518
+ const segments = flattenPathSegments(extractPathSegments(d));
20519
+ return obstacles.filter((obstacle) => segmentsCrossRect(segments, nodeRect(obstacle))).length;
20520
+ }
20521
+ function makeBackDetourCandidate(A, B, from, to, obstacles, detourY, side) {
20522
+ const lowIsA = A.y >= B.y;
20523
+ const low = lowIsA ? A : B;
20524
+ const lowBendY = low.y - VERTICAL_DETOUR_EXIT;
20525
+ const bandTop = Math.min(detourY, lowBendY);
20526
+ const bandBottom = Math.max(detourY, lowBendY);
20527
+ const bandObstacles = obstacles.map(nodeRect).filter((rect) => rect.y + rect.h >= bandTop && rect.y <= bandBottom);
20528
+ let columnX = detourColumnFor([from, to], side);
20529
+ while (true) {
20530
+ const blockers = bandObstacles.filter(
20531
+ (rect) => rect.x - VERTICAL_DETOUR_GAP < columnX && columnX < rect.x + rect.w + VERTICAL_DETOUR_GAP
20532
+ );
20533
+ if (blockers.length === 0) break;
20534
+ columnX = side === "left" ? Math.min(...blockers.map((rect) => rect.x - VERTICAL_DETOUR_GAP)) : Math.max(...blockers.map((rect) => rect.x + rect.w + VERTICAL_DETOUR_GAP));
20535
+ }
20536
+ const bendAY = lowIsA ? lowBendY : detourY;
20537
+ const bendBY = lowIsA ? detourY : lowBendY;
20538
+ const vertices = [
20539
+ A,
20540
+ { x: A.x, y: bendAY },
20541
+ { x: columnX, y: bendAY },
20542
+ { x: columnX, y: bendBY },
20543
+ { x: B.x, y: bendBY },
20544
+ B
20545
+ ];
20546
+ const d = verticesToPath(vertices);
20547
+ const high = lowIsA ? B : A;
20548
+ return {
20549
+ d,
20550
+ labelX: (high.x + columnX) / 2,
20551
+ crossings: countPathObstacleCrossings(d, obstacles),
20552
+ length: vertices.slice(1).reduce((sum, vertex, index) => {
20553
+ const previous = vertices[index];
20554
+ return sum + Math.hypot(vertex.x - previous.x, vertex.y - previous.y);
20555
+ }, 0)
20556
+ };
20557
+ }
20558
+ function chooseBackDetourCandidate(A, B, from, to, obstacles, detourY) {
20559
+ const left = makeBackDetourCandidate(A, B, from, to, obstacles, detourY, "left");
20560
+ const right = makeBackDetourCandidate(A, B, from, to, obstacles, detourY, "right");
20561
+ if (left.crossings !== right.crossings) return left.crossings < right.crossings ? left : right;
20562
+ if (Math.abs(left.length - right.length) >= 0.5) return left.length < right.length ? left : right;
20563
+ const preferred = Math.abs(A.x - B.x) < 0.5 ? "right" : A.x < B.x ? "left" : "right";
20564
+ return preferred === "left" ? left : right;
20565
+ }
20415
20566
  function rectGap(a, b) {
20416
20567
  const dx = Math.max(0, a.x - (b.x + b.w), b.x - (a.x + a.w));
20417
20568
  const dy = Math.max(0, a.y - (b.y + b.h), b.y - (a.y + a.h));
@@ -20489,8 +20640,8 @@ function sidePoint(n, side) {
20489
20640
  return { x: n.cx + n.w / 2, y: n.cy };
20490
20641
  }
20491
20642
  }
20492
- function routePath(from, to, fromSide, toSide, obstacles = [], detourSide, _fromLane, _toLane, edge, labelObstacles = obstacles, fromOffset = { x: 0, y: 0 }, toOffset = { x: 0, y: 0 }, avoidRects = []) {
20493
- const labelBoxW = edge ? computeLabelBoxW(edge.label, edge.sub) : 0;
20643
+ function routePath(from, to, fromSide, toSide, obstacles = [], detourSide, _fromLane, _toLane, edge, labelObstacles = obstacles, fromOffset = { x: 0, y: 0 }, toOffset = { x: 0, y: 0 }, avoidRects = [], textMetrics = "proportional") {
20644
+ const labelBoxW = edge ? computeLabelBoxW(edge.label, edge.sub, textMetrics) : 0;
20494
20645
  const labelHalfW = labelBoxW / 2;
20495
20646
  const labelInit = labelInitClearance(edge);
20496
20647
  const verticalPair = fromSide === "bottom" && toSide === "top" || fromSide === "top" && toSide === "bottom";
@@ -20862,7 +21013,7 @@ function routePath(from, to, fromSide, toSide, obstacles = [], detourSide, _from
20862
21013
  const detourY = Math.min(A.y, B.y) - 100;
20863
21014
  const corner = 14;
20864
21015
  const xDir = B.x > A.x ? 1 : -1;
20865
- return {
21016
+ const existing = {
20866
21017
  d: `M ${A.x} ${A.y}
20867
21018
  L ${A.x} ${detourY + corner}
20868
21019
  Q ${A.x} ${detourY}, ${A.x + xDir * corner} ${detourY}
@@ -20876,6 +21027,16 @@ function routePath(from, to, fromSide, toSide, obstacles = [], detourSide, _from
20876
21027
  labelY: detourY - labelInit,
20877
21028
  labelAnchor: "middle"
20878
21029
  };
21030
+ const existingCrossings = countPathObstacleCrossings(existing.d, obstacles);
21031
+ if (existingCrossings === 0) return existing;
21032
+ const candidate = chooseBackDetourCandidate(A, B, from, to, obstacles, detourY);
21033
+ if (candidate.crossings >= existingCrossings) return existing;
21034
+ return {
21035
+ d: candidate.d,
21036
+ labelX: candidate.labelX,
21037
+ labelY: detourY - labelInit,
21038
+ labelAnchor: "middle"
21039
+ };
20879
21040
  }
20880
21041
  const midX = fromSide === "left" || fromSide === "right" ? B.x : A.x;
20881
21042
  const midY = fromSide === "top" || fromSide === "bottom" ? B.y : A.y;
@@ -20889,7 +21050,7 @@ function routePath(from, to, fromSide, toSide, obstacles = [], detourSide, _from
20889
21050
  labelAnchor: "middle"
20890
21051
  };
20891
21052
  }
20892
- function repositionParallelLabels(edges, nodes) {
21053
+ function repositionParallelLabels(edges, nodes, textMetrics = "proportional") {
20893
21054
  const allSegs = new Map(
20894
21055
  edges.map((e) => [e.id, flattenPathSegments(extractPathSegments(e.d))])
20895
21056
  );
@@ -20914,7 +21075,7 @@ function repositionParallelLabels(edges, nodes) {
20914
21075
  for (const pair of byPair.values()) {
20915
21076
  if (pair.length < 2) continue;
20916
21077
  const pairOrder = [...pair].sort(compareSharedPairOrder);
20917
- const boxes = pair.map((e) => computeLabelBBoxWorld(e));
21078
+ const boxes = pair.map((e) => computeLabelBBoxWorld(e, textMetrics));
20918
21079
  const componentOf = pair.map((_, i) => i);
20919
21080
  for (let i = 0; i < pair.length; i++) {
20920
21081
  for (let j = i + 1; j < pair.length; j++) {
@@ -20939,17 +21100,27 @@ function repositionParallelLabels(edges, nodes) {
20939
21100
  nodes,
20940
21101
  allEdges: edges,
20941
21102
  allSegs,
20942
- xRange
21103
+ xRange,
21104
+ textMetrics
20943
21105
  });
20944
21106
  for (let i = 0; i < members.length; i++) members[i].labelY = placed[i];
20945
21107
  }
20946
21108
  }
20947
21109
  }
20948
21110
  function placeAvoidingSiblingPaths(args) {
20949
- const { members, pair, pairOrder, nodes, allEdges, allSegs, xRange } = args;
21111
+ const {
21112
+ members,
21113
+ pair,
21114
+ pairOrder,
21115
+ nodes,
21116
+ allEdges,
21117
+ allSegs,
21118
+ xRange,
21119
+ textMetrics = "proportional"
21120
+ } = args;
20950
21121
  const sizes = members.map((e) => labelPillH(e.sub));
20951
21122
  const wants = members.map((e) => e.labelY);
20952
- const boxes = members.map((e) => computeLabelBBoxWorld(e));
21123
+ const boxes = members.map((e) => computeLabelBBoxWorld(e, textMetrics));
20953
21124
  const all = members.map((_, i) => i);
20954
21125
  const spread = (idx) => spreadWithMinimalShift(
20955
21126
  idx.map((i) => ({ want: wants[i], size: sizes[i] })),
@@ -21140,14 +21311,14 @@ function labelRectAt(cx, cy, w, h) {
21140
21311
  function inflate(r, pad) {
21141
21312
  return { x: r.x - pad, y: r.y - pad, w: r.w + pad * 2, h: r.h + pad * 2 };
21142
21313
  }
21143
- function slideLabelsAlongOwnPath(edges, nodes) {
21314
+ function slideLabelsAlongOwnPath(edges, nodes, textMetrics = "proportional") {
21144
21315
  const withLabel = edges.filter((e) => hasRenderedLabel(e));
21145
21316
  if (withLabel.length === 0) return;
21146
21317
  const segsById = /* @__PURE__ */ new Map();
21147
21318
  for (const e of edges) segsById.set(e.id, flattenPathSegments(extractPathSegments(e.d)));
21148
21319
  const nodeRects = nodes.map(nodeRect);
21149
21320
  for (const e of withLabel) {
21150
- const w = computeLabelBoxW(e.label, e.sub);
21321
+ const w = computeLabelBoxW(e.label, e.sub, textMetrics);
21151
21322
  const h = labelPillH(e.sub);
21152
21323
  if (w === 0 || h === 0) continue;
21153
21324
  const own = segsById.get(e.id) ?? [];
@@ -21449,7 +21620,7 @@ function separateSharedStraightRuns(edges, nodes) {
21449
21620
  e.d = verticesToPath(verts.get(e.id));
21450
21621
  }
21451
21622
  }
21452
- function pullOutgoingFirstCorner(edges, nodes) {
21623
+ function pullOutgoingFirstCorner(edges, nodes, textMetrics = "proportional") {
21453
21624
  if (edges.length < 2) return;
21454
21625
  const \u675F = /* @__PURE__ */ new Map();
21455
21626
  const \u540C\u3058\u7D44\u306E\u6570 = /* @__PURE__ */ new Map();
@@ -21503,10 +21674,10 @@ function pullOutgoingFirstCorner(edges, nodes) {
21503
21674
  }
21504
21675
  e.d = \u524D;
21505
21676
  if (!\u672D\u3092\u65E7\u7D4C\u8DEF\u3078\u8FFD\u5F93\u6E08\u307F) {
21506
- slideLabelsAlongOwnPath(edges, nodes);
21677
+ slideLabelsAlongOwnPath(edges, nodes, textMetrics);
21507
21678
  \u672D\u3092\u65E7\u7D4C\u8DEF\u3078\u8FFD\u5F93\u6E08\u307F = true;
21508
21679
  }
21509
- const labelBox = computeLabelBBoxWorld(e);
21680
+ const labelBox = computeLabelBBoxWorld(e, textMetrics);
21510
21681
  const label = { x: labelBox.x + labelBox.w / 2, y: labelBox.y + labelBox.h / 2 };
21511
21682
  const \u7DDA\u5206\u307E\u3067\u306E\u8DDD\u96E22 = (a, b) => {
21512
21683
  const dx = b.x - a.x;
@@ -21618,13 +21789,13 @@ function fanIncomingEndpoints(edges, nodes) {
21618
21789
  }
21619
21790
  return \u7D42\u70B9\u306E\u79FB\u52D5;
21620
21791
  }
21621
- function followLabelsToFannedTails(edges, obstacles, shifts) {
21792
+ function followLabelsToFannedTails(edges, obstacles, shifts, textMetrics = "proportional") {
21622
21793
  if (shifts.size === 0) return;
21623
21794
  const \u6E2C\u308A\u65B9 = \u7DDA\u306E\u6E2C\u308A\u65B9\u3092\u4F5C\u308B();
21624
21795
  const labels = edges.filter(hasRenderedLabel).map((e) => ({
21625
21796
  kind: "edge-label",
21626
21797
  id: e.id,
21627
- ...computeLabelBBoxWorld(e)
21798
+ ...computeLabelBBoxWorld(e, textMetrics)
21628
21799
  }));
21629
21800
  const labelIndexByEdgeId = new Map(labels.map((label, index) => [label.id, index]));
21630
21801
  const edgeById = new Map(edges.map((e) => [e.id, e]));
@@ -21656,7 +21827,7 @@ function followLabelsToFannedTails(edges, obstacles, shifts) {
21656
21827
  labelY: e.labelY + \u79FB\u52D5.dy,
21657
21828
  labelAnchor: e.labelAnchor
21658
21829
  };
21659
- const \u5019\u88DCa\u306E\u7BB1 = computeLabelBBoxWorld({ ...e, ...\u5019\u88DCa });
21830
+ const \u5019\u88DCa\u306E\u7BB1 = computeLabelBBoxWorld({ ...e, ...\u5019\u88DCa }, textMetrics);
21660
21831
  const \u6700\u5F8C\u306F\u7E26 = Math.abs(\u6700\u5F8C.x2 - \u6700\u5F8C.x1) <= Math.abs(\u6700\u5F8C.y2 - \u6700\u5F8C.y1);
21661
21832
  const \u5019\u88DC = [
21662
21833
  \u5019\u88DCa,
@@ -21667,7 +21838,11 @@ function followLabelsToFannedTails(edges, obstacles, shifts) {
21667
21838
  }
21668
21839
  ];
21669
21840
  for (const c of \u5019\u88DC) {
21670
- const \u672D = { kind: "edge-label", id: e.id, ...computeLabelBBoxWorld({ ...e, ...c }) };
21841
+ const \u672D = {
21842
+ kind: "edge-label",
21843
+ id: e.id,
21844
+ ...computeLabelBBoxWorld({ ...e, ...c }, textMetrics)
21845
+ };
21671
21846
  if (segmentsCrossRect([\u6700\u5F8C], \u672D)) continue;
21672
21847
  if (\u672D\u306E\u79FB\u52D5\u3092\u585E\u3050\u76F8\u624B\u3092\u63A2\u3059(\u5468\u308A, \u5143\u306E\u672D, \u672D) !== null) continue;
21673
21848
  e.labelX = c.labelX;
@@ -21861,7 +22036,7 @@ function expandLanesForNodes(lanes, nodes) {
21861
22036
  };
21862
22037
  });
21863
22038
  }
21864
- function expandLaneGapsForEdgeLabels(lanes, nodes, edges) {
22039
+ function expandLaneGapsForEdgeLabels(lanes, nodes, edges, textMetrics = "proportional") {
21865
22040
  if (lanes.length < 2) return lanes;
21866
22041
  const layoutedLanes = lanes.filter((l) => !(l.posX !== void 0 && l.posY !== void 0));
21867
22042
  if (layoutedLanes.length < 2) return lanes;
@@ -21877,7 +22052,7 @@ function expandLaneGapsForEdgeLabels(lanes, nodes, edges) {
21877
22052
  const fi = laneIndexById.get(fromLane);
21878
22053
  const ti = laneIndexById.get(toLane);
21879
22054
  if (fi === void 0 || ti === void 0 || fi === ti) continue;
21880
- const labelBoxW = computeLabelBoxW(edge.label, edge.sub);
22055
+ const labelBoxW = computeLabelBoxW(edge.label, edge.sub, textMetrics);
21881
22056
  if (labelBoxW === 0) continue;
21882
22057
  const lo = Math.min(fi, ti);
21883
22058
  const hi = Math.max(fi, ti);
@@ -21999,7 +22174,7 @@ function \u7DDA\u306E\u7AEF\u306E\u5411\u304D(d, \u7AEF) {
21999
22174
  const \u5019\u88DC = segs.flatMap((s) => [...s.ctrl ?? [], { x: s.x2, y: s.y2 }]);
22000
22175
  return \u5411\u304D\u3092\u53D6\u308B(end, \u5019\u88DC);
22001
22176
  }
22002
- function \u7AEF\u306E\u5B57\u3092\u7F6E\u304F(edge, \u7AEF = "head") {
22177
+ function \u7AEF\u306E\u5B57\u3092\u7F6E\u304F(edge, \u7AEF = "head", textMetrics = "proportional") {
22003
22178
  const text = (\u7AEF === "head" ? edge.headLabel : edge.tailLabel)?.trim();
22004
22179
  if (!text) return null;
22005
22180
  const \u5411\u304D = \u7DDA\u306E\u7AEF\u306E\u5411\u304D(edge.d, \u7AEF);
@@ -22010,7 +22185,8 @@ function \u7AEF\u306E\u5B57\u3092\u7F6E\u304F(edge, \u7AEF = "head") {
22010
22185
  const w = measureTextWidth(text, {
22011
22186
  fontSize: \u7AEF\u306E\u5B57\u306E\u5927\u304D\u3055,
22012
22187
  fontWeight: EDGE_LABEL_TEXT.sub.fontWeight,
22013
- fontFamily: "mono"
22188
+ fontFamily: "mono",
22189
+ textMetrics
22014
22190
  });
22015
22191
  const h = \u7BB1\u306E\u9AD8\u3055;
22016
22192
  const \u672D = hasRenderedLabel(edge) && edge.labelX !== void 0 && edge.labelY !== void 0 ? { x: edge.labelX, y: edge.labelY } : null;
@@ -22059,10 +22235,10 @@ function autoStorageHeight(n, defaultH) {
22059
22235
  }
22060
22236
  return Math.max(defaultH, \u5FC5\u8981);
22061
22237
  }
22062
- function autoRowsWidth(n, defaultW) {
22238
+ function autoRowsWidth(n, defaultW, textMetrics = "proportional") {
22063
22239
  if (n.w != null) return n.w;
22064
22240
  if (!n.rows || n.rows.length === 0) return defaultW;
22065
- const required = requiredRowsWidth(n.rows, n.kind);
22241
+ const required = requiredRowsWidth(n.rows, n.kind, textMetrics);
22066
22242
  return Math.max(defaultW, required);
22067
22243
  }
22068
22244
  function \u7BB1\u306E\u9AD8\u30552(n, \u65E2\u5B9Ah) {
@@ -22100,7 +22276,7 @@ function requiredStackGapForEdgeLabels(diag, allStacks) {
22100
22276
  }
22101
22277
  return required;
22102
22278
  }
22103
- function layoutNodes(diag, lanes) {
22279
+ function layoutNodes(diag, lanes, textMetrics) {
22104
22280
  const laneMap = new Map(lanes.map((l) => [l.id, l]));
22105
22281
  const allStacks = Array.from(new Set(diag.nodes.map((n) => n.stack))).sort((a, b) => a - b);
22106
22282
  const rowH = /* @__PURE__ */ new Map();
@@ -22144,7 +22320,7 @@ function layoutNodes(diag, lanes) {
22144
22320
  }
22145
22321
  const size = NODE_SIZE[n.kind];
22146
22322
  if (n.posX !== void 0 && n.posY !== void 0) {
22147
- const w2 = n.posW ?? n.w ?? autoRowsWidth(n, size.w);
22323
+ const w2 = n.posW ?? n.w ?? autoRowsWidth(n, size.w, textMetrics);
22148
22324
  const h2 = n.posH ?? n.h ?? rowH.get(n.stack) ?? size.h;
22149
22325
  out.push({
22150
22326
  ...n,
@@ -22162,7 +22338,7 @@ function layoutNodes(diag, lanes) {
22162
22338
  const \u81EA\u524D\u306E\u9AD8\u3055 = n.rowMarks !== void 0;
22163
22339
  const h = n.h ?? (\u81EA\u524D\u306E\u9AD8\u3055 ? \u7BB1\u306E\u9AD8\u30552(n, size.h) : \u6BB5\u306E\u9AD8\u3055);
22164
22340
  const cy = \u6BB5\u306E\u82AF;
22165
- const w = autoRowsWidth(n, size.w);
22341
+ const w = autoRowsWidth(n, size.w, textMetrics);
22166
22342
  out.push({
22167
22343
  ...n,
22168
22344
  cx,
@@ -22282,10 +22458,16 @@ function applyRowLevelNodeShifts(nodes, lanes, nodeShifts) {
22282
22458
  return moved ? { nodes: outNodes, lanes: outLanes } : null;
22283
22459
  }
22284
22460
  function layout(diag) {
22461
+ const textMetrics = resolveTextMetrics(diag.textMetrics);
22285
22462
  const lanes = layoutLanes(diag);
22286
- const rawNodes = applyFooterShapeDrops(lanes, layoutNodes(diag, lanes));
22463
+ const rawNodes = applyFooterShapeDrops(lanes, layoutNodes(diag, lanes, textMetrics));
22287
22464
  const expandedLanes = expandLanesForNodes(lanes, rawNodes);
22288
- const gapExpandedLanes = expandLaneGapsForEdgeLabels(expandedLanes, rawNodes, diag.edges);
22465
+ const gapExpandedLanes = expandLaneGapsForEdgeLabels(
22466
+ expandedLanes,
22467
+ rawNodes,
22468
+ diag.edges,
22469
+ textMetrics
22470
+ );
22289
22471
  const nodes = rawNodes.map((n) => {
22290
22472
  if (n.posX !== void 0 && n.posY !== void 0) return n;
22291
22473
  const oldLane = lanes.find((l) => l.id === n.lane);
@@ -22294,13 +22476,13 @@ function layout(diag) {
22294
22476
  return { ...n, cx: newLane.x + newLane.width / 2 };
22295
22477
  });
22296
22478
  const containedLanesPre = recomputeContainedLanes(gapExpandedLanes, nodes);
22297
- const edgesPre = layoutEdges(diag, nodes, containedLanesPre);
22298
- const bboxesPre = collectBBoxes(containedLanesPre, nodes, edgesPre);
22479
+ const edgesPre = layoutEdges(diag, nodes, containedLanesPre, textMetrics);
22480
+ const bboxesPre = collectBBoxes(containedLanesPre, nodes, edgesPre, textMetrics);
22299
22481
  const collisionsPre = detectCollisions(bboxesPre, edgesPre);
22300
22482
  const nodesResolved = resolveOverlaps(nodes, collisionsPre);
22301
22483
  const moved = nodesResolved !== nodes;
22302
22484
  const containedLanes = moved ? recomputeContainedLanes(gapExpandedLanes, nodesResolved) : containedLanesPre;
22303
- const edgesAfterMove = moved ? layoutEdges(diag, nodesResolved, containedLanes) : edgesPre;
22485
+ const edgesAfterMove = moved ? layoutEdges(diag, nodesResolved, containedLanes, textMetrics) : edgesPre;
22304
22486
  const chainShiftClearance = Math.max(CLEARANCE_LABEL_LABEL, CLEARANCE_NODE_LABEL);
22305
22487
  let edges;
22306
22488
  let nodesFinal = nodesResolved;
@@ -22311,10 +22493,13 @@ function layout(diag) {
22311
22493
  } else {
22312
22494
  const propagateResult = resolveEdgeLabelOverlapsWithChainAndPropagate(
22313
22495
  edgesAfterMove,
22314
- collectBBoxes(containedLanes, nodesResolved, []).filter(
22496
+ collectBBoxes(containedLanes, nodesResolved, [], textMetrics).filter(
22315
22497
  (b) => b.kind === "node" || b.kind === "lane-label"
22316
22498
  ),
22317
- chainShiftClearance
22499
+ chainShiftClearance,
22500
+ void 0,
22501
+ void 0,
22502
+ textMetrics
22318
22503
  );
22319
22504
  edges = propagateResult.edges;
22320
22505
  if (propagateResult.nodeShifts.size > 0) {
@@ -22326,7 +22511,7 @@ function layout(diag) {
22326
22511
  }
22327
22512
  if (nodesFinal !== nodesResolved) {
22328
22513
  containedLanesFinal = recomputeContainedLanes(laneShiftedBase, nodesFinal);
22329
- edges = layoutEdges(diag, nodesFinal, containedLanesFinal);
22514
+ edges = layoutEdges(diag, nodesFinal, containedLanesFinal, textMetrics);
22330
22515
  }
22331
22516
  }
22332
22517
  const positionedEdgeIds = new Set(
@@ -22334,21 +22519,31 @@ function layout(diag) {
22334
22519
  (e) => e.routing === "curve" || e.routing === "metro" || e.posX1 !== void 0 && e.posY1 !== void 0 && e.posX2 !== void 0 && e.posY2 !== void 0
22335
22520
  ).map((e) => e.id)
22336
22521
  );
22337
- bowSharedStraightPaths(edges, nodesFinal, positionedEdgeIds);
22338
- pullOutgoingFirstCorner(edges, nodesFinal);
22522
+ bowSharedStraightPaths(edges, nodesFinal, positionedEdgeIds, textMetrics);
22523
+ pullOutgoingFirstCorner(edges, nodesFinal, textMetrics);
22339
22524
  const fannedTailShifts = fanIncomingEndpoints(edges, nodesFinal);
22340
22525
  separateSharedStraightRuns(edges, nodesFinal);
22341
22526
  hopEdgeCrossings(edges);
22342
- const labelClearanceObstacles = collectBBoxes(containedLanesFinal, nodesFinal, []).filter(
22527
+ const labelClearanceObstacles = collectBBoxes(
22528
+ containedLanesFinal,
22529
+ nodesFinal,
22530
+ [],
22531
+ textMetrics
22532
+ ).filter(
22343
22533
  (b) => b.kind === "node" || b.kind === "lane-label"
22344
22534
  );
22345
- followLabelsToFannedTails(edges, labelClearanceObstacles, fannedTailShifts);
22346
- repositionParallelLabels(edges, nodesFinal);
22347
- slideLabelsAlongOwnPath(edges, nodesFinal);
22535
+ followLabelsToFannedTails(edges, labelClearanceObstacles, fannedTailShifts, textMetrics);
22536
+ repositionParallelLabels(edges, nodesFinal, textMetrics);
22537
+ slideLabelsAlongOwnPath(edges, nodesFinal, textMetrics);
22348
22538
  if (!isChainEdgeLabelDisabled()) {
22349
- edges = resolveLabelClearanceAfterPathPasses(edges, labelClearanceObstacles);
22539
+ edges = resolveLabelClearanceAfterPathPasses(
22540
+ edges,
22541
+ labelClearanceObstacles,
22542
+ void 0,
22543
+ textMetrics
22544
+ );
22350
22545
  }
22351
- const bboxes = collectBBoxes(containedLanesFinal, nodesFinal, edges);
22546
+ const bboxes = collectBBoxes(containedLanesFinal, nodesFinal, edges, textMetrics);
22352
22547
  const collisions = detectCollisions(bboxes, edges);
22353
22548
  const nearCollisions = detectNearCollisions(bboxes, edges);
22354
22549
  if (collisions.length > 0) {
@@ -22388,6 +22583,8 @@ function layout(diag) {
22388
22583
  // 描画側の固定の字の言語 (#847)。 既定 (`en`) と型の外の値は持たせない = 配置の結果の形を
22389
22584
  // 変更前と揃え、記法の書き損じで一部の字だけ日本語になる形を作らない
22390
22585
  ...resolveLang(diag.lang) === "ja" ? { lang: "ja" } : {},
22586
+ // 既定は持ち越さない。既存の LaidDiagram の形を変えず、等幅の図だけ描画へ伝える
22587
+ ...textMetrics === "monospace" ? { textMetrics: "monospace" } : {},
22391
22588
  // 種類も配色と同じく空の目印を出さない。 遮断をここに揃えると手書きの図にも効く
22392
22589
  ...diag.type ? { type: diag.type } : {},
22393
22590
  bboxes,
@@ -24513,6 +24710,7 @@ function CdlEdgeView({
24513
24710
  "data-cdl-edge-label": edge.label,
24514
24711
  "data-cdl-edge-sub": edge.sub ?? "",
24515
24712
  "data-cdl-tone": edge.tone,
24713
+ "data-cdl-edge-role": edge.role,
24516
24714
  children: [
24517
24715
  isDotted ? /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
24518
24716
  /* @__PURE__ */ jsxRuntime.jsx("path", { id: glowPathId, d: glowPathD, fill: "none", stroke: "none" }),
@@ -24664,11 +24862,12 @@ function CdlEdgeGlowView({
24664
24862
  }
24665
24863
  function CdlEdgeLabelView({
24666
24864
  edge,
24667
- active
24865
+ active,
24866
+ textMetrics = "proportional"
24668
24867
  }) {
24669
24868
  if (!hasRenderedLabel(edge)) return null;
24670
24869
  const color = edgeColor(edge);
24671
- const bbox = computeLabelBBoxWorld(edge);
24870
+ const bbox = computeLabelBBoxWorld(edge, textMetrics);
24672
24871
  const boxW = bbox.w;
24673
24872
  const boxH = bbox.h;
24674
24873
  const boxLeftX = bbox.x - edge.labelX;
@@ -24684,6 +24883,8 @@ function CdlEdgeLabelView({
24684
24883
  "data-cdl-edge-label-for": edge.id,
24685
24884
  "data-cdl-edge-label-text": edge.label,
24686
24885
  "data-cdl-edge-sub-text": edge.sub ?? "",
24886
+ "data-cdl-tone": edge.tone,
24887
+ "data-cdl-edge-role": edge.role,
24687
24888
  children: [
24688
24889
  edge.labelPlate !== false && /* @__PURE__ */ jsxRuntime.jsx(
24689
24890
  "rect",
@@ -24737,9 +24938,10 @@ function CdlEdgeLabelView({
24737
24938
  function CdlEdgeEndLabelView({
24738
24939
  edge,
24739
24940
  active,
24740
- \u7AEF
24941
+ \u7AEF,
24942
+ textMetrics = "proportional"
24741
24943
  }) {
24742
- const \u7F6E\u304D\u5834\u6240 = \u7AEF\u306E\u5B57\u3092\u7F6E\u304F(edge, \u7AEF);
24944
+ const \u7F6E\u304D\u5834\u6240 = \u7AEF\u306E\u5B57\u3092\u7F6E\u304F(edge, \u7AEF, textMetrics);
24743
24945
  if (!\u7F6E\u304D\u5834\u6240) return null;
24744
24946
  const color = edgeColor(edge);
24745
24947
  return /* @__PURE__ */ jsxRuntime.jsx(
@@ -24748,6 +24950,8 @@ function CdlEdgeEndLabelView({
24748
24950
  "data-cdl-role": "edge-end-label",
24749
24951
  "data-cdl-edge-end-label-for": edge.id,
24750
24952
  "data-cdl-edge-end": \u7AEF,
24953
+ "data-cdl-tone": edge.tone,
24954
+ "data-cdl-edge-role": edge.role,
24751
24955
  x: \u7F6E\u304D\u5834\u6240.x,
24752
24956
  y: \u7F6E\u304D\u5834\u6240.y,
24753
24957
  fontSize: \u7AEF\u306E\u5B57\u306E\u5927\u304D\u3055,
@@ -24995,12 +25199,18 @@ var g4 = (v) => Math.round(v / 4) * 4;
24995
25199
  function sequenceStepId() {
24996
25200
  return "seq_step";
24997
25201
  }
24998
- function sequenceBoardMetrics(data) {
25202
+ function sequenceBoardMetrics(data, textMetrics = "proportional") {
24999
25203
  const \u540D\u5E45 = data.actors.map(
25000
- (a) => Math.max(textWidth(a.name, SEQ_NAME), a.subtitle ? textWidth(a.subtitle, SEQ_SUB) : 0)
25204
+ (a) => Math.max(
25205
+ textWidth(a.name, SEQ_NAME, 0, textMetrics),
25206
+ a.subtitle ? textWidth(a.subtitle, SEQ_SUB, 0, textMetrics) : 0
25207
+ )
25001
25208
  );
25002
25209
  const colW = g4(Math.max(SEQ_COL_MIN, Math.max(0, ...\u540D\u5E45) + SEQ_COL_PAD));
25003
- const \u8A9E\u5E45 = Math.max(0, ...data.messages.map((m) => textWidth(m.label, SEQ_LABEL)));
25210
+ const \u8A9E\u5E45 = Math.max(
25211
+ 0,
25212
+ ...data.messages.map((m) => textWidth(m.label, SEQ_LABEL, 0, textMetrics))
25213
+ );
25004
25214
  const gutter = g4(SEQ_EDGE + SEQ_GUTTER_PAD + \u8A9E\u5E45 + SEQ_GUTTER_GAP);
25005
25215
  const headY = SEQ_EDGE + SEQ_HEAD;
25006
25216
  const rowY = (i) => headY + SEQ_ROW_PAD + i * SEQ_ROW;
@@ -25013,11 +25223,12 @@ function sequenceBoardMetrics(data) {
25013
25223
  }
25014
25224
  function SequenceBoardNode({
25015
25225
  node,
25016
- stateValues
25226
+ stateValues,
25227
+ textMetrics = "proportional"
25017
25228
  }) {
25018
25229
  const data = node.sequenceData;
25019
25230
  if (!data) return /* @__PURE__ */ jsxRuntime.jsx("g", { "data-cdl-role": "sequence-board" });
25020
- const m = sequenceBoardMetrics(data);
25231
+ const m = sequenceBoardMetrics(data, textMetrics);
25021
25232
  const x = node.cx - node.w / 2;
25022
25233
  const y = node.cy - node.h / 2;
25023
25234
  const \u73FE\u5728 = (() => {
@@ -25668,7 +25879,8 @@ function GenericNode({
25668
25879
  active,
25669
25880
  value,
25670
25881
  stateValues,
25671
- \u5024\u306E\u540D\u524D
25882
+ \u5024\u306E\u540D\u524D,
25883
+ textMetrics = "proportional"
25672
25884
  }) {
25673
25885
  const base = STYLES[node.kind] ?? FALLBACK;
25674
25886
  const toned = toneColor3(node.tone);
@@ -25807,7 +26019,7 @@ function GenericNode({
25807
26019
  const resolved = node.rows.map((row) => interpolate(row, stateValues, \u5024\u306E\u540D\u524D));
25808
26020
  const splits = resolved.map(splitRow);
25809
26021
  const leftMaxWidth = splits.reduce(
25810
- (m, s) => Math.max(m, rowColumnWidth(s.left, GENERIC_ROW_LEFT_SIZE_PX, false)),
26022
+ (m, s) => Math.max(m, rowColumnWidth(s.left, GENERIC_ROW_LEFT_SIZE_PX, false, textMetrics)),
25811
26023
  0
25812
26024
  );
25813
26025
  const rightColX = ROW_PAD_X_PX + leftMaxWidth + ROW_COL_GAP_PX;
@@ -26291,8 +26503,8 @@ function \u5024\u3068\u5272\u5408\u306E\u6587\u5B57(\u5024, \u5272\u5408, \u5408
26291
26503
  return \u7D44.\u5024 === null ? \u7D44.\u5272\u5408 : `${\u7D44.\u5024} ${\u7D44.\u5272\u5408}`;
26292
26504
  }
26293
26505
  var \u7A74\u306B\u5BFE\u3059\u308B\u4E0A\u9650 = 0.8;
26294
- function \u4E2D\u592E\u306E\u5B57(\u6BD4\u4F8B\u3057\u305F\u5927\u304D\u3055, \u7A74\u306E\u534A\u5F84, \u6587) {
26295
- const \u5165\u308B\u5927\u304D\u3055 = \u7A74\u306E\u534A\u5F84 * 2 * \u7A74\u306B\u5BFE\u3059\u308B\u4E0A\u9650 / Math.max(textWidth(\u6587, 1), 1e-6);
26506
+ function \u4E2D\u592E\u306E\u5B57(\u6BD4\u4F8B\u3057\u305F\u5927\u304D\u3055, \u7A74\u306E\u534A\u5F84, \u6587, textMetrics = "proportional") {
26507
+ const \u5165\u308B\u5927\u304D\u3055 = \u7A74\u306E\u534A\u5F84 * 2 * \u7A74\u306B\u5BFE\u3059\u308B\u4E0A\u9650 / Math.max(textWidth(\u6587, 1, 0, textMetrics), 1e-6);
26296
26508
  return Math.min(Math.max(\u6BD4\u4F8B\u3057\u305F\u5927\u304D\u3055, \u7E2E\u3093\u3060\u7D75\u306E\u5B57\u306E\u4E0B\u9650), \u5165\u308B\u5927\u304D\u3055);
26297
26509
  }
26298
26510
  function ChartPieNode({
@@ -26300,7 +26512,8 @@ function ChartPieNode({
26300
26512
  active,
26301
26513
  stateValues = {},
26302
26514
  drawing = false,
26303
- progress = 1
26515
+ progress = 1,
26516
+ textMetrics = "proportional"
26304
26517
  }) {
26305
26518
  const instanceId = react.useId().replace(/[^A-Za-z0-9_-]/g, "");
26306
26519
  const x0 = node.cx - node.w / 2;
@@ -26331,15 +26544,26 @@ function ChartPieNode({
26331
26544
  return `${\u5B9F\u5024\u8868\u8A18(d.value)}%` === \u5272\u5408\u306E\u6587\u5B57[i] ? \u540D : `${\u540D} ${\u5B9F\u5024\u8868\u8A18(d.value)}`;
26332
26545
  });
26333
26546
  if (\u5F62 !== "ring") {
26334
- const \u5171\u901A = { node, active, data, \u5272\u5408: \u4ECA\u306E\u5272\u5408, x0, y0, drawing, progress, instanceId };
26547
+ const \u5171\u901A = {
26548
+ node,
26549
+ active,
26550
+ data,
26551
+ \u5272\u5408: \u4ECA\u306E\u5272\u5408,
26552
+ x0,
26553
+ y0,
26554
+ drawing,
26555
+ progress,
26556
+ instanceId,
26557
+ textMetrics
26558
+ };
26335
26559
  return \u5F62 === "arcs" ? \u5F27\u306E\u5F62(\u5171\u901A) : \u8868\u306E\u5F62(\u5171\u901A);
26336
26560
  }
26337
26561
  const \u540D\u672D\u5E45 = Math.max(
26338
26562
  0,
26339
26563
  ...data.map(
26340
26564
  (_d, i) => Math.max(
26341
- textWidth(\u5272\u5408\u306E\u6587\u5B57[i] ?? "", \u5272\u5408\u306E\u7D1A),
26342
- textWidth(\u540D\u524D\u306E\u6587\u5B57[i] ?? "", \u540D\u524D\u306E\u7D1A)
26565
+ textWidth(\u5272\u5408\u306E\u6587\u5B57[i] ?? "", \u5272\u5408\u306E\u7D1A, 0, textMetrics),
26566
+ textWidth(\u540D\u524D\u306E\u6587\u5B57[i] ?? "", \u540D\u524D\u306E\u7D1A, 0, textMetrics)
26343
26567
  )
26344
26568
  )
26345
26569
  );
@@ -26354,8 +26578,8 @@ function ChartPieNode({
26354
26578
  const \u524D\u306Eslices = \u524D\u3042\u308A ? \u8F2A\u3092\u7D44\u3080(data, cx, cy, \u524D\u306E\u5916\u534A\u5F84, \u524D\u306E\u5185\u534A\u5F84, \u524D\u306E\u5272\u5408) : [];
26355
26579
  const \u7A74 = \u524D\u3042\u308A ? \u524D\u306E\u5185\u534A\u5F84 : \u5916\u306E\u5185\u534A\u5F84;
26356
26580
  const \u5408\u8A08\u306E\u6587 = \u5B9F\u5024\u8868\u8A18(Math.round(\u524D\u3042\u308A ? \u4ECA\u306E\u5408\u8A08 : total));
26357
- const \u5408\u8A08\u306E\u5B57 = \u4E2D\u592E\u306E\u5B57(Math.round(radius * 0.26), \u7A74, \u5408\u8A08\u306E\u6587);
26358
- const \u898B\u51FA\u3057\u306E\u5B572 = \u4E2D\u592E\u306E\u5B57(Math.round(radius * 0.12), \u7A74, "\u5408\u8A08");
26581
+ const \u5408\u8A08\u306E\u5B57 = \u4E2D\u592E\u306E\u5B57(Math.round(radius * 0.26), \u7A74, \u5408\u8A08\u306E\u6587, textMetrics);
26582
+ const \u898B\u51FA\u3057\u306E\u5B572 = \u4E2D\u592E\u306E\u5B57(Math.round(radius * 0.12), \u7A74, "\u5408\u8A08", textMetrics);
26359
26583
  const \u5408\u8A08\u306E\u4E0B = Math.max(Math.round(radius * 0.2), \u5408\u8A08\u306E\u5B57 * 0.25 + \u898B\u51FA\u3057\u306E\u5B572 * 0.8);
26360
26584
  const slices = \u8F2A\u3092\u7D44\u3080(data, cx, cy, radius, \u5916\u306E\u5185\u534A\u5F84, \u4ECA\u306E\u5272\u5408);
26361
26585
  const \u958B\u304D = \u9032\u307F\u3092\u7573\u3080(drawing, progress);
@@ -26538,14 +26762,24 @@ function \u67A0(node, active) {
26538
26762
  }
26539
26763
  );
26540
26764
  }
26541
- function \u5F27\u306E\u5F62({ node, active, data, \u5272\u5408, x0, y0, drawing, progress }) {
26765
+ function \u5F27\u306E\u5F62({
26766
+ node,
26767
+ active,
26768
+ data,
26769
+ \u5272\u5408,
26770
+ x0,
26771
+ y0,
26772
+ drawing,
26773
+ progress,
26774
+ textMetrics
26775
+ }) {
26542
26776
  const PAD = 20;
26543
26777
  const \u540D\u524D\u306E\u7D1A = 14;
26544
26778
  const \u5272\u5408\u306E\u7D1A = 24;
26545
26779
  const \u5370\u304B\u3089\u540D\u524D\u307E\u30672 = 18;
26546
26780
  const \u540D\u524D\u304B\u3089\u5272\u5408\u307E\u3067 = 24;
26547
26781
  const \u5272\u5408\u306E\u6587\u5B57 = \u5272\u5408.map(\u5272\u5408\u8868\u8A18);
26548
- const \u4E00\u89A7\u5E45 = 10 + \u5370\u304B\u3089\u540D\u524D\u307E\u30672 + Math.max(0, ...data.map((d) => textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A))) + \u540D\u524D\u304B\u3089\u5272\u5408\u307E\u3067 + Math.max(0, ...\u5272\u5408\u306E\u6587\u5B57.map((t) => textWidth(t, \u5272\u5408\u306E\u7D1A)));
26782
+ const \u4E00\u89A7\u5E45 = 10 + \u5370\u304B\u3089\u540D\u524D\u307E\u30672 + Math.max(0, ...data.map((d) => textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A, 0, textMetrics))) + \u540D\u524D\u304B\u3089\u5272\u5408\u307E\u3067 + Math.max(0, ...\u5272\u5408\u306E\u6587\u5B57.map((t) => textWidth(t, \u5272\u5408\u306E\u7D1A, 0, textMetrics)));
26549
26783
  const \u7E26\u304B\u3089 = (node.h - PAD * 2) / 2;
26550
26784
  const \u6A2A\u304B\u3089 = (node.w - PAD * 2 - \u4E00\u89A7\u5E45 - 28) / 2;
26551
26785
  const R = Math.max(24, Math.min(\u7E26\u304B\u3089, \u6A2A\u304B\u3089));
@@ -26631,7 +26865,18 @@ function \u5F27\u306E\u5F62({ node, active, data, \u5272\u5408, x0, y0, drawing,
26631
26865
  })
26632
26866
  ] });
26633
26867
  }
26634
- function \u8868\u306E\u5F62({ node, active, data, \u5272\u5408, x0, y0, drawing, progress, instanceId }) {
26868
+ function \u8868\u306E\u5F62({
26869
+ node,
26870
+ active,
26871
+ data,
26872
+ \u5272\u5408,
26873
+ x0,
26874
+ y0,
26875
+ drawing,
26876
+ progress,
26877
+ instanceId,
26878
+ textMetrics
26879
+ }) {
26635
26880
  const PAD = 20;
26636
26881
  const \u898B\u51FA\u3057\u306E\u7D1A = 11;
26637
26882
  const \u540D\u524D\u306E\u7D1A = 15;
@@ -26640,9 +26885,18 @@ function \u8868\u306E\u5F62({ node, active, data, \u5272\u5408, x0, y0, drawing,
26640
26885
  const \u5370\u304B\u3089\u540D\u524D\u307E\u30672 = 18;
26641
26886
  const \u5272\u5408\u306E\u6587\u5B57 = \u5272\u5408.map(\u5272\u5408\u8868\u8A18);
26642
26887
  const \u5B9F\u6570\u306E\u6587\u5B57 = data.map((d) => \u5B9F\u5024\u8868\u8A18(d.value));
26643
- const \u540D\u524D\u5E45 = Math.max(0, ...data.map((d) => textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A)));
26644
- const \u5272\u5408\u5E45 = Math.max(textWidth("\u5272\u5408", \u898B\u51FA\u3057\u306E\u7D1A), ...\u5272\u5408\u306E\u6587\u5B57.map((t) => textWidth(t, \u5272\u5408\u306E\u7D1A)));
26645
- const \u5B9F\u6570\u5E45 = Math.max(textWidth("\u5024", \u898B\u51FA\u3057\u306E\u7D1A), ...\u5B9F\u6570\u306E\u6587\u5B57.map((t) => textWidth(t, \u5B9F\u6570\u306E\u7D1A)));
26888
+ const \u540D\u524D\u5E45 = Math.max(
26889
+ 0,
26890
+ ...data.map((d) => textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A, 0, textMetrics))
26891
+ );
26892
+ const \u5272\u5408\u5E45 = Math.max(
26893
+ textWidth("\u5272\u5408", \u898B\u51FA\u3057\u306E\u7D1A, 0, textMetrics),
26894
+ ...\u5272\u5408\u306E\u6587\u5B57.map((t) => textWidth(t, \u5272\u5408\u306E\u7D1A, 0, textMetrics))
26895
+ );
26896
+ const \u5B9F\u6570\u5E45 = Math.max(
26897
+ textWidth("\u5024", \u898B\u51FA\u3057\u306E\u7D1A, 0, textMetrics),
26898
+ ...\u5B9F\u6570\u306E\u6587\u5B57.map((t) => textWidth(t, \u5B9F\u6570\u306E\u7D1A, 0, textMetrics))
26899
+ );
26646
26900
  const \u8868\u5E45 = 10 + \u5370\u304B\u3089\u540D\u524D\u307E\u30672 + \u540D\u524D\u5E45 + 28 + \u5272\u5408\u5E45 + 24 + \u5B9F\u6570\u5E45;
26647
26901
  const \u7E26\u304B\u3089 = (node.h - PAD * 2) / 2;
26648
26902
  const \u6A2A\u304B\u3089 = (node.w - PAD * 2 - \u8868\u5E45 - 28) / 2;
@@ -26651,8 +26905,8 @@ function \u8868\u306E\u5F62({ node, active, data, \u5272\u5408, x0, y0, drawing,
26651
26905
  const cx = PAD + R;
26652
26906
  const cy = node.h / 2;
26653
26907
  const \u5408\u8A08\u306E\u6587 = \u5B9F\u5024\u8868\u8A18(Math.round(data.reduce((acc, d) => acc + d.value, 0)));
26654
- const \u5408\u8A08\u306E\u5B57 = \u4E2D\u592E\u306E\u5B57(Math.round(R * 0.26), \u5185\u534A\u5F84, \u5408\u8A08\u306E\u6587);
26655
- const \u898B\u51FA\u3057\u306E\u5B572 = \u4E2D\u592E\u306E\u5B57(Math.round(R * 0.12), \u5185\u534A\u5F84, "\u5408\u8A08");
26908
+ const \u5408\u8A08\u306E\u5B57 = \u4E2D\u592E\u306E\u5B57(Math.round(R * 0.26), \u5185\u534A\u5F84, \u5408\u8A08\u306E\u6587, textMetrics);
26909
+ const \u898B\u51FA\u3057\u306E\u5B572 = \u4E2D\u592E\u306E\u5B57(Math.round(R * 0.12), \u5185\u534A\u5F84, "\u5408\u8A08", textMetrics);
26656
26910
  const \u5408\u8A08\u306E\u4E0B = Math.max(Math.round(R * 0.2), \u5408\u8A08\u306E\u5B57 * 0.25 + \u898B\u51FA\u3057\u306E\u5B572 * 0.8);
26657
26911
  const \u8868\u5DE6 = node.w - PAD - \u8868\u5E45;
26658
26912
  const \u53F3\u7AEF = node.w - PAD;
@@ -26783,7 +27037,8 @@ function ChartGaugeNode({
26783
27037
  active,
26784
27038
  stateValues = {},
26785
27039
  drawing = false,
26786
- progress = 1
27040
+ progress = 1,
27041
+ textMetrics = "proportional"
26787
27042
  }) {
26788
27043
  const x0 = node.cx - node.w / 2;
26789
27044
  const y0 = node.cy - node.h / 2;
@@ -26802,7 +27057,10 @@ function ChartGaugeNode({
26802
27057
  const \u533A\u753B\u306E\u9593 = 12;
26803
27058
  const \u6570\u5024\u306E\u884C = (d) => \u5024\u3068\u5272\u5408\u306E\u6587\u5B57(\u5B9F\u5024\u8868\u8A18(d.value), \u5272\u5408\u8868\u8A18(d.value / total), total);
26804
27059
  const \u5272\u308A\u4ED8\u3051\u308B = (\u4EF6\u305F\u3061) => {
26805
- const \u5E45 = Math.max(\u5370\u306E\u5E452, ...\u4EF6\u305F\u3061.map((d) => textWidth(\u6570\u5024\u306E\u884C(d), \u6570\u5024\u306E\u7D1A))) + \u533A\u753B\u306E\u9593;
27060
+ const \u5E45 = Math.max(
27061
+ \u5370\u306E\u5E452,
27062
+ ...\u4EF6\u305F\u3061.map((d) => textWidth(\u6570\u5024\u306E\u884C(d), \u6570\u5024\u306E\u7D1A, 0, textMetrics))
27063
+ ) + \u533A\u753B\u306E\u9593;
26806
27064
  const \u884C\u306E\u4EF6\u65702 = Math.min(
26807
27065
  Math.max(1, Math.floor(\u4F7F\u3048\u308B\u5E452 / Math.max(\u5E45, 1))),
26808
27066
  Math.max(\u4EF6\u305F\u3061.length, 1)
@@ -26877,7 +27135,7 @@ function ChartGaugeNode({
26877
27135
  return { d, frac, path: \u6247\u306E\u9053(a0, a1, \u524D\u306E\u5185\u534A\u5F84, \u524D\u306E\u5916\u534A\u5F84) };
26878
27136
  });
26879
27137
  const \u5408\u8A08\u306E\u6587\u5B57 = \u5B9F\u5024\u8868\u8A18(Math.round(total));
26880
- const \u5358\u4F4D\u5E45 = Math.max(textWidth(\u5408\u8A08\u306E\u6587\u5B57, 100), 1) / 100;
27138
+ const \u5358\u4F4D\u5E45 = Math.max(textWidth(\u5408\u8A08\u306E\u6587\u5B57, 100, 0, textMetrics), 1) / 100;
26881
27139
  const \u7D1A\u306E\u5019\u88DC = Math.min(
26882
27140
  // 横 = 字の上の角が内側の円に入る大きさ
26883
27141
  \u5185\u534A\u5F84 / Math.sqrt((\u5358\u4F4D\u5E45 / 2) ** 2 + 1.25 ** 2),
@@ -26970,7 +27228,7 @@ function ChartGaugeNode({
26970
27228
  const y = \u5185\u8A33\u306Ey + \u6BB5\u306E\u9AD8\u3055 * \u6BB5;
26971
27229
  const \u53CE\u307E\u308B\u5E45 = \u5185\u8A33\u306E\u5E45 - \u533A\u753B\u306E\u9593;
26972
27230
  const \u6570\u306E\u884C = \u5185\u8A33\u306E\u6570\u5024[idx] ?? "";
26973
- const \u5207\u3063\u305F\u6570\u306E\u884C = \u5207\u308A\u8A70\u3081\u308B(\u6570\u306E\u884C, \u53CE\u307E\u308B\u5E45, \u6570\u5024\u306E\u7D1A);
27231
+ const \u5207\u3063\u305F\u6570\u306E\u884C = \u5207\u308A\u8A70\u3081\u308B(\u6570\u306E\u884C, \u53CE\u307E\u308B\u5E45, \u6570\u5024\u306E\u7D1A, textMetrics);
26974
27232
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { "data-cdl-role": "chart-gauge-item", children: [
26975
27233
  /* @__PURE__ */ jsxRuntime.jsx(
26976
27234
  "rect",
@@ -26991,7 +27249,7 @@ function ChartGaugeNode({
26991
27249
  fontSize: \u540D\u524D\u306E\u7D1A,
26992
27250
  fontWeight: 700,
26993
27251
  fill: "var(--cdl-text, #1a1f2a)",
26994
- children: \u5207\u308A\u8A70\u3081\u308B(d.label ?? "", \u53CE\u307E\u308B\u5E45, \u540D\u524D\u306E\u7D1A)
27252
+ children: \u5207\u308A\u8A70\u3081\u308B(d.label ?? "", \u53CE\u307E\u308B\u5E45, \u540D\u524D\u306E\u7D1A, textMetrics)
26995
27253
  }
26996
27254
  ),
26997
27255
  /* @__PURE__ */ jsxRuntime.jsx("text", { x, y: y + 46, fontSize: \u6570\u5024\u306E\u7D1A, fill: "var(--cdl-text-dim, #5a6270)", children: \u5207\u3063\u305F\u6570\u306E\u884C === \u6570\u306E\u884C ? /* @__PURE__ */ jsxRuntime.jsx(
@@ -27009,12 +27267,12 @@ function ChartGaugeNode({
27009
27267
  function \u6975(cx, cy, r, a) {
27010
27268
  return { x: cx + r * Math.cos(a), y: cy + r * Math.sin(a) };
27011
27269
  }
27012
- function \u5207\u308A\u8A70\u3081\u308B(s, \u4E0A\u9650, \u7D1A) {
27013
- if (\u4E0A\u9650 <= 0 || textWidth(s, \u7D1A) <= \u4E0A\u9650) return s;
27014
- const \u8A18\u53F7\u5E45 = textWidth("\u2026", \u7D1A);
27270
+ function \u5207\u308A\u8A70\u3081\u308B(s, \u4E0A\u9650, \u7D1A, textMetrics = "proportional") {
27271
+ if (\u4E0A\u9650 <= 0 || textWidth(s, \u7D1A, 0, textMetrics) <= \u4E0A\u9650) return s;
27272
+ const \u8A18\u53F7\u5E45 = textWidth("\u2026", \u7D1A, 0, textMetrics);
27015
27273
  let out = "";
27016
27274
  for (const c of s) {
27017
- if (textWidth(out + c, \u7D1A) + \u8A18\u53F7\u5E45 > \u4E0A\u9650) break;
27275
+ if (textWidth(out + c, \u7D1A, 0, textMetrics) + \u8A18\u53F7\u5E45 > \u4E0A\u9650) break;
27018
27276
  out += c;
27019
27277
  }
27020
27278
  return `${out}\u2026`;
@@ -27028,7 +27286,8 @@ function ChartRadialNode({
27028
27286
  active,
27029
27287
  stateValues = {},
27030
27288
  drawing = false,
27031
- progress = 1
27289
+ progress = 1,
27290
+ textMetrics = "proportional"
27032
27291
  }) {
27033
27292
  const x0 = node.cx - node.w / 2;
27034
27293
  const y0 = node.cy - node.h / 2;
@@ -27046,7 +27305,10 @@ function ChartRadialNode({
27046
27305
  const \u4E00\u89A7\u306E\u5E45 = \u5370\u306E\u5E45 + Math.max(
27047
27306
  0,
27048
27307
  ...data.map(
27049
- (d, i) => Math.max(textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A), textWidth(\u6570\u5024\u306E\u6587\u5B57[i] ?? "", \u6570\u5024\u306E\u7D1A))
27308
+ (d, i) => Math.max(
27309
+ textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A, 0, textMetrics),
27310
+ textWidth(\u6570\u5024\u306E\u6587\u5B57[i] ?? "", \u6570\u5024\u306E\u7D1A, 0, textMetrics)
27311
+ )
27050
27312
  )
27051
27313
  );
27052
27314
  const \u5F27\u306B\u4F7F\u3048\u308B\u5E45 = node.w - PAD * 2 - \u4E00\u89A7\u306E\u5E45 - \u4E00\u89A7\u3068\u5F27\u306E\u9593;
@@ -27193,7 +27455,8 @@ function arcColor2(tone, idx) {
27193
27455
  function ChartStatNode({
27194
27456
  node,
27195
27457
  active,
27196
- stateValues = {}
27458
+ stateValues = {},
27459
+ textMetrics = "proportional"
27197
27460
  }) {
27198
27461
  const x0 = node.cx - node.w / 2;
27199
27462
  const y0 = node.cy - node.h / 2;
@@ -27222,7 +27485,13 @@ function ChartStatNode({
27222
27485
  const frac = total > 0 ? d.value / total : 0;
27223
27486
  const \u8272 = \u5370\u306E\u8272(d.tone, idx);
27224
27487
  const \u6570\u5024 = \u5B9F\u5024\u8868\u8A18(d.value);
27225
- const \u6570\u5024\u306E\u7D1A = \u53CE\u3081\u308B\u7D1A(\u6570\u5024, \u67A02.w - \u533A\u753B.\u4F59\u767D * 2, \u533A\u753B.\u6570\u5024\u306E\u7D1A, \u533A\u753B.\u540D\u524D\u306E\u7D1A + 1);
27488
+ const \u6570\u5024\u306E\u7D1A = \u53CE\u3081\u308B\u7D1A(
27489
+ \u6570\u5024,
27490
+ \u67A02.w - \u533A\u753B.\u4F59\u767D * 2,
27491
+ \u533A\u753B.\u6570\u5024\u306E\u7D1A,
27492
+ \u533A\u753B.\u540D\u524D\u306E\u7D1A + 1,
27493
+ textMetrics
27494
+ );
27226
27495
  return /* @__PURE__ */ jsxRuntime.jsxs(
27227
27496
  "g",
27228
27497
  {
@@ -27279,7 +27548,8 @@ function ChartStatNode({
27279
27548
  `\u524D ${\u5B9F\u5024\u8868\u8A18(d.previous)}`,
27280
27549
  \u67A02.w - \u533A\u753B.\u4F59\u767D * 2,
27281
27550
  \u533A\u753B.\u524D\u306E\u7D1A,
27282
- 8
27551
+ 8,
27552
+ textMetrics
27283
27553
  ),
27284
27554
  textAnchor: "middle",
27285
27555
  fill: "var(--cdl-text-dim, #5a6270)",
@@ -27368,9 +27638,9 @@ function \u533A\u753B\u306E\u5272\u4ED8(w, h, \u4EF6\u6570, \u524D\u3092\u51FA\u
27368
27638
  \u67A0: (idx) => ({ x: \u5E45 * idx, y: 0, w: \u5E45, h })
27369
27639
  };
27370
27640
  }
27371
- function \u53CE\u3081\u308B\u7D1A(\u5B572, \u4F7F\u3048\u308B\u5E452, \u521D\u671F, \u4E0B\u9650) {
27641
+ function \u53CE\u3081\u308B\u7D1A(\u5B572, \u4F7F\u3048\u308B\u5E452, \u521D\u671F, \u4E0B\u9650, textMetrics = "proportional") {
27372
27642
  let \u7D1A = \u521D\u671F;
27373
- while (\u7D1A > \u4E0B\u9650 && textWidth(\u5B572, \u7D1A) > \u4F7F\u3048\u308B\u5E452) \u7D1A -= 1;
27643
+ while (\u7D1A > \u4E0B\u9650 && textWidth(\u5B572, \u7D1A, 0, textMetrics) > \u4F7F\u3048\u308B\u5E452) \u7D1A -= 1;
27374
27644
  return \u7D1A;
27375
27645
  }
27376
27646
  function \u5F27\u306E\u90533(cx, cy, r, \u5272\u5408) {
@@ -27405,7 +27675,8 @@ function ChartWaffleNode({
27405
27675
  active,
27406
27676
  stateValues = {},
27407
27677
  drawing = false,
27408
- progress = 1
27678
+ progress = 1,
27679
+ textMetrics = "proportional"
27409
27680
  }) {
27410
27681
  const x0 = node.cx - node.w / 2;
27411
27682
  const y0 = node.cy - node.h / 2;
@@ -27424,7 +27695,10 @@ function ChartWaffleNode({
27424
27695
  const \u4E00\u89A7\u306E\u5E45 = \u5370\u306E\u5E452 + Math.max(
27425
27696
  0,
27426
27697
  ...data.map(
27427
- (d, i) => Math.max(textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A), textWidth(\u6570\u5024\u306E\u6587\u5B57[i] ?? "", \u6570\u5024\u306E\u7D1A))
27698
+ (d, i) => Math.max(
27699
+ textWidth(d.label ?? "", \u540D\u524D\u306E\u7D1A, 0, textMetrics),
27700
+ textWidth(\u6570\u5024\u306E\u6587\u5B57[i] ?? "", \u6570\u5024\u306E\u7D1A, 0, textMetrics)
27701
+ )
27428
27702
  )
27429
27703
  );
27430
27704
  const \u4F7F\u3048\u308B\u9AD8\u3055 = node.h - PAD * 2;
@@ -27526,7 +27800,8 @@ function ChartStackedBarNode({
27526
27800
  active,
27527
27801
  stateValues = {},
27528
27802
  drawing = false,
27529
- progress = 1
27803
+ progress = 1,
27804
+ textMetrics = "proportional"
27530
27805
  }) {
27531
27806
  const x0 = node.cx - node.w / 2;
27532
27807
  const y0 = node.cy - node.h / 2;
@@ -27536,7 +27811,7 @@ function ChartStackedBarNode({
27536
27811
  const \u540D\u524D\u306E\u7D1A = 13;
27537
27812
  const \u533A\u753B\u306E\u7D1A = 12;
27538
27813
  const \u6642\u70B9\u306E\u7D1A = 13;
27539
- const \u6642\u70B9\u306E\u5E45 = Math.max(0, ...\u5E2F\u305F\u3061.map((b) => textWidth(b.\u540D\u524D, \u6642\u70B9\u306E\u7D1A))) + (\u5E2F\u305F\u3061.length > 1 ? 16 : 0);
27814
+ const \u6642\u70B9\u306E\u5E45 = Math.max(0, ...\u5E2F\u305F\u3061.map((b) => textWidth(b.\u540D\u524D, \u6642\u70B9\u306E\u7D1A, 0, textMetrics))) + (\u5E2F\u305F\u3061.length > 1 ? 16 : 0);
27540
27815
  const \u5E2F\u306E\u5DE6 = PAD + \u6642\u70B9\u306E\u5E45;
27541
27816
  const \u5E2F\u306E\u5E45 = Math.max(40, node.w - \u5E2F\u306E\u5DE6 - PAD);
27542
27817
  const \u5E2F\u306E\u9AD8\u3055 = 44;
@@ -27629,7 +27904,7 @@ function ChartStackedBarNode({
27629
27904
  })()
27630
27905
  ] }, `bar-${\u6BB5}`);
27631
27906
  }),
27632
- \u4E00\u89A7\u306E\u4E26\u3073(data, \u5E2F\u306E\u5DE6, node.w - PAD, \u540D\u524D\u306E\u7D1A).map(({ d, idx, x, \u884C }) => {
27907
+ \u4E00\u89A7\u306E\u4E26\u3073(data, \u5E2F\u306E\u5DE6, node.w - PAD, \u540D\u524D\u306E\u7D1A, textMetrics).map(({ d, idx, x, \u884C }) => {
27633
27908
  const y = \u4E0A\u7AEF + \u5E2F\u305F\u3061.length * (\u5E2F\u306E\u9AD8\u3055 + \u5E2F\u306E\u9593) - \u5E2F\u306E\u9593 + 16 + \u4E00\u89A7\u306E\u9AD8\u3055 / 2 + \u884C * \u4E00\u89A7\u306E\u9AD8\u3055;
27634
27909
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { "data-cdl-role": "chart-stacked-bar-legend", children: [
27635
27910
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x, y: y - 5, width: 10, height: 10, rx: 2, fill: \u5370\u306E\u82723(d.tone, idx) }),
@@ -27664,12 +27939,12 @@ function \u5370\u306E\u82723(tone, idx) {
27664
27939
  }
27665
27940
  var \u5370\u304B\u3089\u540D\u524D\u307E\u3067 = 16;
27666
27941
  var \u4EF6\u306E\u9593 = 10;
27667
- function \u4E00\u89A7\u306E\u4E26\u3073(data, \u5DE6, \u53F3\u7AEF, \u7D1A) {
27942
+ function \u4E00\u89A7\u306E\u4E26\u3073(data, \u5DE6, \u53F3\u7AEF, \u7D1A, textMetrics = "proportional") {
27668
27943
  const out = [];
27669
27944
  let x = \u5DE6;
27670
27945
  let \u884C = 0;
27671
27946
  data.forEach((d, idx) => {
27672
- const \u5E45 = \u5370\u304B\u3089\u540D\u524D\u307E\u3067 + textWidth(d.label ?? "", \u7D1A);
27947
+ const \u5E45 = \u5370\u304B\u3089\u540D\u524D\u307E\u3067 + textWidth(d.label ?? "", \u7D1A, 0, textMetrics);
27673
27948
  if (x > \u5DE6 && x + \u5E45 > \u53F3\u7AEF) {
27674
27949
  \u884C += 1;
27675
27950
  x = \u5DE6;
@@ -27685,7 +27960,8 @@ function ChartSlopeNode({
27685
27960
  active,
27686
27961
  stateValues = {},
27687
27962
  drawing = false,
27688
- progress = 1
27963
+ progress = 1,
27964
+ textMetrics = "proportional"
27689
27965
  }) {
27690
27966
  const x0 = node.cx - node.w / 2;
27691
27967
  const y0 = node.cy - node.h / 2;
@@ -27728,16 +28004,22 @@ function ChartSlopeNode({
27728
28004
  const \u53F3\u306E\u5B57 = \u7CFB\u5217\u305F\u3061.map(
27729
28005
  (s) => \u5F62 === "delta" ? \u5897\u6E1B\u8868\u8A18(s.\u524D, s.\u4ECA) : \u5B9F\u5024\u8868\u8A18(s.\u4ECA)
27730
28006
  );
27731
- const \u5DE6\u5024\u5E45 = Math.max(0, ...\u5DE6\u306E\u5B57.map((t) => textWidth(t, \u5024\u306E\u7D1A)));
27732
- const \u53F3\u5024\u5E45 = Math.max(0, ...\u53F3\u306E\u5B57.map((t) => textWidth(t, \u5024\u306E\u7D1A)));
28007
+ const \u5DE6\u5024\u5E45 = Math.max(0, ...\u5DE6\u306E\u5B57.map((t) => textWidth(t, \u5024\u306E\u7D1A, 0, textMetrics)));
28008
+ const \u53F3\u5024\u5E45 = Math.max(0, ...\u53F3\u306E\u5B57.map((t) => textWidth(t, \u5024\u306E\u7D1A, 0, textMetrics)));
27733
28009
  const \u540D\u524D\u306B\u4F7F\u3048\u308B = Math.max(
27734
28010
  0,
27735
28011
  (node.w - PAD * 2 - \u7DDA\u306E\u6700\u5C0F\u5E45 - (\u5DE6\u5024\u5E45 + \u8EF8\u304B\u3089\u5024\u307E\u3067 + \u5024\u304B\u3089\u540D\u524D\u307E\u3067) - (\u53F3\u5024\u5E45 + \u8EF8\u304B\u3089\u5024\u307E\u3067 + \u5024\u304B\u3089\u540D\u524D\u307E\u3067)) / 2
27736
28012
  );
27737
- const \u540D\u524D\u306E\u7D1A = \u53CE\u3081\u308B\u7D1A2(\u7CFB\u5217\u305F\u3061.map((s) => s.\u540D\u524D), \u540D\u524D\u306B\u4F7F\u3048\u308B, \u540D\u524D\u306E\u4E0A\u9650\u7D1A, \u540D\u524D\u306E\u4E0B\u9650\u7D1A);
28013
+ const \u540D\u524D\u306E\u7D1A = \u53CE\u3081\u308B\u7D1A2(
28014
+ \u7CFB\u5217\u305F\u3061.map((s) => s.\u540D\u524D),
28015
+ \u540D\u524D\u306B\u4F7F\u3048\u308B,
28016
+ \u540D\u524D\u306E\u4E0A\u9650\u7D1A,
28017
+ \u540D\u524D\u306E\u4E0B\u9650\u7D1A,
28018
+ textMetrics
28019
+ );
27738
28020
  const \u540D\u524D\u5E45 = Math.min(
27739
28021
  \u540D\u524D\u306B\u4F7F\u3048\u308B,
27740
- Math.max(0, ...\u7CFB\u5217\u305F\u3061.map((s) => textWidth(s.\u540D\u524D, \u540D\u524D\u306E\u7D1A)))
28022
+ Math.max(0, ...\u7CFB\u5217\u305F\u3061.map((s) => textWidth(s.\u540D\u524D, \u540D\u524D\u306E\u7D1A, 0, textMetrics)))
27741
28023
  );
27742
28024
  const \u5DE6\u306E\u4F59\u767D = \u540D\u524D\u5E45 + \u5024\u304B\u3089\u540D\u524D\u307E\u3067 + \u5DE6\u5024\u5E45 + \u8EF8\u304B\u3089\u5024\u307E\u3067;
27743
28025
  const \u53F3\u306E\u4F59\u767D = \u8EF8\u304B\u3089\u5024\u307E\u3067 + \u53F3\u5024\u5E45 + \u5024\u304B\u3089\u540D\u524D\u307E\u3067 + \u540D\u524D\u5E45;
@@ -27923,10 +28205,12 @@ function \u5370\u306E\u82724(tone, idx) {
27923
28205
  if (tone) return TONE[tone];
27924
28206
  return chartSeriesColor(idx);
27925
28207
  }
27926
- function \u53CE\u3081\u308B\u7D1A2(\u540D\u524D\u305F\u3061, \u5E45, \u4E0A\u9650, \u4E0B\u9650) {
28208
+ function \u53CE\u3081\u308B\u7D1A2(\u540D\u524D\u305F\u3061, \u5E45, \u4E0A\u9650, \u4E0B\u9650, textMetrics = "proportional") {
27927
28209
  if (\u540D\u524D\u305F\u3061.length === 0) return \u4E0A\u9650;
27928
28210
  let \u7D1A = \u4E0A\u9650;
27929
- while (\u7D1A > \u4E0B\u9650 && Math.max(...\u540D\u524D\u305F\u3061.map((n) => textWidth(n, \u7D1A))) > \u5E45) \u7D1A -= 1;
28211
+ while (\u7D1A > \u4E0B\u9650 && Math.max(...\u540D\u524D\u305F\u3061.map((n) => textWidth(n, \u7D1A, 0, textMetrics))) > \u5E45) {
28212
+ \u7D1A -= 1;
28213
+ }
27930
28214
  return \u7D1A;
27931
28215
  }
27932
28216
  function \u5C0F\u6570\u306E\u6841(n) {
@@ -27974,6 +28258,7 @@ function ChartBarNode({
27974
28258
  return { y: yAt(v), value: v };
27975
28259
  });
27976
28260
  const \u6FC3\u3055 = (v) => vMax > 0 ? v >= vMax ? 1 : 0.45 : 0.9;
28261
+ const \u4E3B\u5F79\u306E\u68D2\u304B = (v) => vMax > 0 && v >= vMax;
27977
28262
  const \u89D2\u4E38 = Math.min(barW * 0.06, 8);
27978
28263
  const \u4F38\u3073 = \u9032\u307F\u3092\u7573\u3080(drawing, progress);
27979
28264
  const \u6A2A\u8EF8\u306Ey = PAD_TOP2 + canvasH;
@@ -28040,6 +28325,7 @@ function ChartBarNode({
28040
28325
  {
28041
28326
  "data-cdl-role": "chart-bar",
28042
28327
  "data-cdl-unresolved": d.unresolved ? "true" : void 0,
28328
+ "data-cdl-emphasis": \u4E3B\u5F79\u306E\u68D2\u304B(d.value) ? "primary" : void 0,
28043
28329
  x: bx,
28044
28330
  y: by,
28045
28331
  width: barW,
@@ -28386,7 +28672,8 @@ function FunnelNode({
28386
28672
  active,
28387
28673
  stateValues = {},
28388
28674
  drawing = false,
28389
- progress = 1
28675
+ progress = 1,
28676
+ textMetrics = "proportional"
28390
28677
  }) {
28391
28678
  const x0 = node.cx - node.w / 2;
28392
28679
  const y0 = node.cy - node.h / 2;
@@ -28435,7 +28722,11 @@ function FunnelNode({
28435
28722
  const \u540D\u524D\u306E\u5B9F\u5B57 = \u540D\u524D\u306E\u5B57 * \u7E26\u500D;
28436
28723
  const \u88DC\u8DB3\u306E\u67A0\u5B57 = \u88DC\u8DB3\u306E\u5B57 * \u7E26\u500D;
28437
28724
  const \u53CE\u307E\u308B\u5E45 = Math.max(0, bottomW - 16);
28438
- const \u88DC\u8DB3\u306E\u5B9F\u5B57 = \u88DC\u8DB3\u306E\u67A0\u5B57 * \u53CE\u3081\u308B\u500D\u7387(\u88DC\u8DB3, { fontSize: \u88DC\u8DB3\u306E\u67A0\u5B57, fontWeight: 500 }, \u53CE\u307E\u308B\u5E45);
28725
+ const \u88DC\u8DB3\u306E\u5B9F\u5B57 = \u88DC\u8DB3\u306E\u67A0\u5B57 * \u53CE\u3081\u308B\u500D\u7387(
28726
+ \u88DC\u8DB3,
28727
+ { fontSize: \u88DC\u8DB3\u306E\u67A0\u5B57, fontWeight: 500, textMetrics },
28728
+ \u53CE\u307E\u308B\u5E45
28729
+ );
28439
28730
  const \u584A\u306E\u4E0A = y + stageH / 2 - (\u540D\u524D\u306E\u5B9F\u5B57 * 1.2 + \u88DC\u8DB3\u306E\u67A0\u5B57 * 1.25) / 2;
28440
28731
  const \u540D\u524D\u306Ey = \u88DC\u8DB3\u3042\u308A ? \u584A\u306E\u4E0A + \u540D\u524D\u306E\u5B9F\u5B57 * 0.95 : y + stageH / 2 + 5;
28441
28732
  const \u88DC\u8DB3\u306Ey = \u584A\u306E\u4E0A + \u540D\u524D\u306E\u5B9F\u5B57 * 1.2 + \u88DC\u8DB3\u306E\u67A0\u5B57 * 0.95;
@@ -28538,7 +28829,8 @@ function \u7573\u3093\u3060\u6587(\u4EF6\u6570) {
28538
28829
  function QuadrantNode({
28539
28830
  node,
28540
28831
  active,
28541
- stateValues = {}
28832
+ stateValues = {},
28833
+ textMetrics = "proportional"
28542
28834
  }) {
28543
28835
  const x0 = node.cx - node.w / 2;
28544
28836
  const y0 = node.cy - node.h / 2;
@@ -28557,7 +28849,10 @@ function QuadrantNode({
28557
28849
  const SUB_FONT = 10;
28558
28850
  const axisLabelPad = (text) => Math.max(
28559
28851
  PAD_MIN,
28560
- measureTextWidth(`\u2190 ${text}`, { fontSize: AXIS_LABEL_FONT}) + 12
28852
+ measureTextWidth(`\u2190 ${text}`, {
28853
+ fontSize: AXIS_LABEL_FONT,
28854
+ textMetrics
28855
+ }) + 12
28561
28856
  );
28562
28857
  const padBudget = Math.max(0, node.w * 0.5 - PAD_MIN * 2);
28563
28858
  const wantLeft = axisLabelPad(data.xAxis.left) - PAD_MIN;
@@ -28811,7 +29106,11 @@ function QuadrantNode({
28811
29106
  ITEM_MIN_W,
28812
29107
  Math.max(
28813
29108
  ...\u884C\u30892.map(
28814
- (r) => measureTextWidth(r.text, { fontSize: r.size, fontWeight: r.weight })
29109
+ (r) => measureTextWidth(r.text, {
29110
+ fontSize: r.size,
29111
+ fontWeight: r.weight,
29112
+ textMetrics
29113
+ })
28815
29114
  )
28816
29115
  ) + ITEM_PAD_X * 2
28817
29116
  )
@@ -28837,7 +29136,7 @@ function QuadrantNode({
28837
29136
  const \u88DC\u8DB3 = (it.subtitle ?? "").trim();
28838
29137
  const \u88DC\u8DB3\u306E\u5B57 = SUB_FONT * \u53CE\u3081\u308B\u500D\u7387(
28839
29138
  \u88DC\u8DB3,
28840
- { fontSize: SUB_FONT, fontWeight: 500 },
29139
+ { fontSize: SUB_FONT, fontWeight: 500, textMetrics },
28841
29140
  Math.max(0, \u5E45 - ITEM_PAD_X * 2)
28842
29141
  );
28843
29142
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
@@ -29241,24 +29540,30 @@ var EYEBROW_GAP2 = 8;
29241
29540
  var EYEBROW_TRACKING = 2;
29242
29541
  var SUB_SIZE = 11;
29243
29542
  var SUB_GAP = 4;
29244
- function labelBlock(node, pos, size, band) {
29543
+ function labelBlock(node, pos, size, band, textMetrics = "proportional") {
29245
29544
  const \u4E0A = node.eyebrow ? size + EYEBROW_GAP2 + EYEBROW_SIZE2 * ASCENT2 : size * ASCENT2;
29246
29545
  const \u4E0B = node.subtitle ? size + SUB_GAP + SUB_SIZE * DESCENT2 : size * DESCENT2;
29247
29546
  const \u5E45 = Math.max(
29248
- textWidth(node.title ?? "", size),
29249
- node.eyebrow ? textWidth(node.eyebrow, EYEBROW_SIZE2, EYEBROW_TRACKING) : 0,
29250
- node.subtitle ? textWidth(node.subtitle, SUB_SIZE) : 0
29547
+ textWidth(node.title ?? "", size, 0, textMetrics),
29548
+ node.eyebrow ? textWidth(node.eyebrow, EYEBROW_SIZE2, EYEBROW_TRACKING, textMetrics) : 0,
29549
+ node.subtitle ? textWidth(node.subtitle, SUB_SIZE, 0, textMetrics) : 0
29251
29550
  );
29252
- const \u984C\u5E45 = textWidth(node.title ?? "", size);
29253
- const \u4E0B\u9650 = \u984C\u5E45 >= \u5E45 ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(node.title ?? "", size, 0, band.w, textWidth) : 0;
29551
+ const \u984C\u5E45 = textWidth(node.title ?? "", size, 0, textMetrics);
29552
+ const \u6E2C\u308B = (t, s, ls) => textWidth(t, s, ls, textMetrics);
29553
+ const \u4E0B\u9650 = \u984C\u5E45 >= \u5E45 ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(node.title ?? "", size, 0, band.w, \u6E2C\u308B) : 0;
29254
29554
  const { k, x, y: baseline } = fitLabel(band, { \u4E0A, \u4E0B, \u5E45 }, pos, \u4E0B\u9650);
29255
29555
  return { k, x, baseline, \u4E0A\u7AEF: baseline - \u4E0A * k, \u4E0B\u7AEF: baseline + \u4E0B * k };
29256
29556
  }
29257
- function commonLabel(node, pos, size, band) {
29258
- const \u584A = labelBlock(node, pos, size, band);
29557
+ function commonLabel(node, pos, size, band, textMetrics = "proportional") {
29558
+ const \u584A = labelBlock(node, pos, size, band, textMetrics);
29259
29559
  const k = \u584A.k;
29260
29560
  const x = \u584A.x;
29261
- const \u5207\u308B = (t, \u5927\u304D\u3055, \u5B57\u9593 = 0) => \u5E2F\u3067\u5207\u308B(t, \u5927\u304D\u3055 * k, band.w, (u, f) => textWidth(u, f, \u5B57\u9593 * k));
29561
+ const \u5207\u308B = (t, \u5927\u304D\u3055, \u5B57\u9593 = 0) => \u5E2F\u3067\u5207\u308B(
29562
+ t,
29563
+ \u5927\u304D\u3055 * k,
29564
+ band.w,
29565
+ (u, f) => textWidth(u, f, \u5B57\u9593 * k, textMetrics)
29566
+ );
29262
29567
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
29263
29568
  node.eyebrow && /* @__PURE__ */ jsxRuntime.jsx(
29264
29569
  "text",
@@ -29309,7 +29614,7 @@ var RULE_GAP_RATIO = 0.1;
29309
29614
  var RULE_PAD_MAX = 20;
29310
29615
  var RULE_PAD_RATIO = 0.14;
29311
29616
  var RULE_SHRINK_RATIO = 0.055;
29312
- function ShapeFileNode({ node, active }) {
29617
+ function ShapeFileNode({ node, active, textMetrics = "proportional" }) {
29313
29618
  const \u5E2F = bodyBand(node, { \u5F71ry: SHADOW_RY });
29314
29619
  const \u7D19h = \u5E2F.h;
29315
29620
  const \u7D19w = Math.min(\u5E2F.w, \u7D19h * 0.72);
@@ -29329,7 +29634,7 @@ function ShapeFileNode({ node, active }) {
29329
29634
  const foldTriangle = `M ${x + \u7D19w - fold} ${y} L ${x + \u7D19w} ${y + fold} L ${x + \u7D19w - fold} ${y + fold} Z`;
29330
29635
  const \u540D\u524D\u5E2F = { x, y, w: \u7D19w, h: \u7D19h };
29331
29636
  const \u540D\u524D\u4F4D\u7F6E = { x: \u5E2F.cx, y: node.cy + node.h * 0.12 };
29332
- const \u540D\u524D = labelBlock(node, \u540D\u524D\u4F4D\u7F6E, 16, \u540D\u524D\u5E2F);
29637
+ const \u540D\u524D = labelBlock(node, \u540D\u524D\u4F4D\u7F6E, 16, \u540D\u524D\u5E2F, textMetrics);
29333
29638
  const \u9593\u9694 = Math.min(RULE_GAP_MAX, \u7D19h * RULE_GAP_RATIO);
29334
29639
  const \u7DDA\u4F59\u767D = Math.min(RULE_PAD_MAX, \u7D19w * RULE_PAD_RATIO);
29335
29640
  const textLines = [0, 1, 2].map((i) => ({ i, ly: y + fold + \u9593\u9694 * (i + 1) })).filter(({ ly }) => ly < \u540D\u524D.\u4E0A\u7AEF);
@@ -29361,12 +29666,12 @@ function ShapeFileNode({ node, active }) {
29361
29666
  i
29362
29667
  );
29363
29668
  }),
29364
- commonLabel(node, \u540D\u524D\u4F4D\u7F6E, 16, \u540D\u524D\u5E2F)
29669
+ commonLabel(node, \u540D\u524D\u4F4D\u7F6E, 16, \u540D\u524D\u5E2F, textMetrics)
29365
29670
  ] });
29366
29671
  }
29367
29672
  var TAB_H_MAX = 22;
29368
29673
  var TAB_H_RATIO = 0.3;
29369
- function ShapeFolderNode({ node, active }) {
29674
+ function ShapeFolderNode({ node, active, textMetrics = "proportional" }) {
29370
29675
  const \u5E2F = bodyBand(node, { \u5F71ry: SHADOW_RY });
29371
29676
  const x = \u5E2F.x;
29372
29677
  const y = \u5E2F.y;
@@ -29387,7 +29692,7 @@ function ShapeFolderNode({ node, active }) {
29387
29692
  const \u5883\u754Cy = y + tabH + Math.min(8, (\u5E2F.h - tabH) * 0.2);
29388
29693
  const \u7AEF = Math.min(6, \u5E2F.w * 0.1);
29389
29694
  const \u540D\u524D\u4F4D\u7F6E = { x: \u5E2F.cx, y: node.cy + 18 };
29390
- const \u540D\u524D = labelBlock(node, \u540D\u524D\u4F4D\u7F6E, 16, \u5E2F);
29695
+ const \u540D\u524D = labelBlock(node, \u540D\u524D\u4F4D\u7F6E, 16, \u5E2F, textMetrics);
29391
29696
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
29392
29697
  dropShadow(\u5E2F.cx, \u5E2F.\u5E95, \u5E2F.w * 0.44),
29393
29698
  /* @__PURE__ */ jsxRuntime.jsx("path", { "data-cdl-role": "node-body", d: bodyPath, ...frame, strokeLinejoin: "round" }),
@@ -29403,13 +29708,13 @@ function ShapeFolderNode({ node, active }) {
29403
29708
  opacity: 0.35
29404
29709
  }
29405
29710
  ),
29406
- commonLabel(node, \u540D\u524D\u4F4D\u7F6E, 16, \u5E2F)
29711
+ commonLabel(node, \u540D\u524D\u4F4D\u7F6E, 16, \u5E2F, textMetrics)
29407
29712
  ] });
29408
29713
  }
29409
29714
  var CLOUD_VB_W = 640;
29410
29715
  var CLOUD_VB_H = 512;
29411
29716
  var CLOUD_W_RATIO = 0.9;
29412
- function ShapeCloudNode({ node, active }) {
29717
+ function ShapeCloudNode({ node, active, textMetrics = "proportional" }) {
29413
29718
  const \u5E2F = bodyBand(node, { \u5F71ry: SHADOW_RY });
29414
29719
  const frame = commonFrame(active);
29415
29720
  const \u7D20\u306E\u500D\u7387 = Math.min(\u5E2F.h / CLOUD_VB_H, \u5E2F.w * CLOUD_W_RATIO / CLOUD_VB_W);
@@ -29432,13 +29737,13 @@ function ShapeCloudNode({ node, active }) {
29432
29737
  strokeLinejoin: "round"
29433
29738
  }
29434
29739
  ) }),
29435
- commonLabel(node, { x: \u5E2F.cx, y: node.cy + node.h * 0.05 }, 16, \u5E2F)
29740
+ commonLabel(node, { x: \u5E2F.cx, y: node.cy + node.h * 0.05 }, 16, \u5E2F, textMetrics)
29436
29741
  ] });
29437
29742
  }
29438
29743
  var CYLINDER_RY_MAX = 18;
29439
29744
  var CYLINDER_RY_RATIO = 0.1;
29440
29745
  var CYLINDER_DISKS = [0.3, 0.55, 0.8];
29441
- function ShapeCylinderNode({ node, active }) {
29746
+ function ShapeCylinderNode({ node, active, textMetrics = "proportional" }) {
29442
29747
  const \u5E2F = bodyBand(node, { \u5F71ry: CYLINDER_SHADOW_RY });
29443
29748
  const x = \u5E2F.x;
29444
29749
  const y = \u5E2F.y;
@@ -29455,7 +29760,7 @@ function ShapeCylinderNode({ node, active }) {
29455
29760
  const \u84CB\u5E95 = y + ry * 2;
29456
29761
  const \u540D\u524D\u4F4D\u7F6E = { x: \u5E2F.cx, y: node.cy + 6 };
29457
29762
  const \u540D\u524D\u5E2F = { x: \u5E2F.x, y: \u84CB\u5E95, w: \u5E2F.w, h: Math.max(0, \u5E2F.\u5E95 - \u84CB\u5E95) };
29458
- const \u540D\u524D = labelBlock(node, \u540D\u524D\u4F4D\u7F6E, 15, \u540D\u524D\u5E2F);
29763
+ const \u540D\u524D = labelBlock(node, \u540D\u524D\u4F4D\u7F6E, 15, \u540D\u524D\u5E2F, textMetrics);
29459
29764
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
29460
29765
  dropShadow(\u5E2F.cx, \u5E2F.\u5E95, rx * 0.85, CYLINDER_SHADOW_RY),
29461
29766
  /* @__PURE__ */ jsxRuntime.jsx("path", { "data-cdl-role": "node-body", d: bodyPath, ...frame, strokeLinejoin: "round" }),
@@ -29479,11 +29784,11 @@ function ShapeCylinderNode({ node, active }) {
29479
29784
  },
29480
29785
  i
29481
29786
  )),
29482
- commonLabel(node, \u540D\u524D\u4F4D\u7F6E, 15, \u540D\u524D\u5E2F)
29787
+ commonLabel(node, \u540D\u524D\u4F4D\u7F6E, 15, \u540D\u524D\u5E2F, textMetrics)
29483
29788
  ] });
29484
29789
  }
29485
29790
  var HEX_DOT_R = 2.5;
29486
- function ShapeHexagonNode({ node, active }) {
29791
+ function ShapeHexagonNode({ node, active, textMetrics = "proportional" }) {
29487
29792
  const \u5E2F = bodyBand(node, { \u5F71ry: SHADOW_RY, \u5916: Math.max(HEX_DOT_R, FRAME_HALF) });
29488
29793
  const cx = \u5E2F.cx;
29489
29794
  const cy = \u5E2F.cy;
@@ -29506,11 +29811,12 @@ function ShapeHexagonNode({ node, active }) {
29506
29811
  node,
29507
29812
  { x: cx, y: node.cy + 6 },
29508
29813
  16,
29509
- { x: \u5E2F.x + cut, y: \u5E2F.y, w: Math.max(0, \u5E2F.w - cut * 2), h: \u5E2F.h }
29814
+ { x: \u5E2F.x + cut, y: \u5E2F.y, w: Math.max(0, \u5E2F.w - cut * 2), h: \u5E2F.h },
29815
+ textMetrics
29510
29816
  )
29511
29817
  ] });
29512
29818
  }
29513
- function ShapeDiamondNode({ node, active }) {
29819
+ function ShapeDiamondNode({ node, active, textMetrics = "proportional" }) {
29514
29820
  const \u5E2F = bodyBand(node, { \u5F71ry: SHADOW_RY });
29515
29821
  const cx = \u5E2F.cx;
29516
29822
  const cy = \u5E2F.cy;
@@ -29551,13 +29857,14 @@ function ShapeDiamondNode({ node, active }) {
29551
29857
  y: cy - \u5E2F.h * innerScale / 4,
29552
29858
  w: \u5E2F.w * innerScale / 2,
29553
29859
  h: \u5E2F.h * innerScale / 2
29554
- }
29860
+ },
29861
+ textMetrics
29555
29862
  )
29556
29863
  ] });
29557
29864
  }
29558
29865
  var STACK_OFFSET_MAX = 12;
29559
29866
  var STACK_OFFSET_RATIO = 0.15;
29560
- function ShapeStackNode({ node, active }) {
29867
+ function ShapeStackNode({ node, active, textMetrics = "proportional" }) {
29561
29868
  const \u5E2F = bodyBand(node, { \u5F71ry: SHADOW_RY });
29562
29869
  const x = \u5E2F.x;
29563
29870
  const y = \u5E2F.y;
@@ -29611,7 +29918,8 @@ function ShapeStackNode({ node, active }) {
29611
29918
  node,
29612
29919
  { x: \u624B\u524Dcx, y: node.cy + \u305A\u308C + 6 },
29613
29920
  15,
29614
- { x, y: y + \u305A\u308C * 2, w: cardW, h: cardH }
29921
+ { x, y: y + \u305A\u308C * 2, w: cardW, h: cardH },
29922
+ textMetrics
29615
29923
  )
29616
29924
  ] });
29617
29925
  }
@@ -29623,16 +29931,22 @@ var PERSON_BODY_LEN = 90;
29623
29931
  var PERSON_SHADOW_DY = 20;
29624
29932
  var PERSON_SHADOW_RY = 4;
29625
29933
  var PERSON_SHADOW_RX = 55;
29626
- function planLabel(node, cx, \u5E45\u4E0A\u9650, plan) {
29934
+ function planLabel(node, cx, \u5E45\u4E0A\u9650, plan, textMetrics = "proportional") {
29627
29935
  const \u5E45 = Math.max(
29628
- textWidth(node.title ?? "", plan.\u540D\u524D.size),
29629
- node.eyebrow && plan.\u80A9\u66F8 ? textWidth(node.eyebrow, plan.\u80A9\u66F8.size, EYEBROW_TRACKING) : 0,
29630
- node.subtitle && plan.\u8AAC\u660E ? textWidth(node.subtitle, plan.\u8AAC\u660E.size) : 0
29936
+ textWidth(node.title ?? "", plan.\u540D\u524D.size, 0, textMetrics),
29937
+ node.eyebrow && plan.\u80A9\u66F8 ? textWidth(node.eyebrow, plan.\u80A9\u66F8.size, EYEBROW_TRACKING, textMetrics) : 0,
29938
+ node.subtitle && plan.\u8AAC\u660E ? textWidth(node.subtitle, plan.\u8AAC\u660E.size, 0, textMetrics) : 0
29631
29939
  );
29632
- const \u984C\u5E45 = textWidth(node.title ?? "", plan.\u540D\u524D.size);
29633
- const \u4E0B\u9650 = \u984C\u5E45 >= \u5E45 ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(node.title ?? "", plan.\u540D\u524D.size, 0, \u5E45\u4E0A\u9650, textWidth) : 0;
29940
+ const \u984C\u5E45 = textWidth(node.title ?? "", plan.\u540D\u524D.size, 0, textMetrics);
29941
+ const \u6E2C\u308B = (t, s, ls) => textWidth(t, s, ls, textMetrics);
29942
+ const \u4E0B\u9650 = \u984C\u5E45 >= \u5E45 ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(node.title ?? "", plan.\u540D\u524D.size, 0, \u5E45\u4E0A\u9650, \u6E2C\u308B) : 0;
29634
29943
  const k = \u5E45 > 0 && \u5E45\u4E0A\u9650 > 0 ? Math.min(1, Math.max(\u5E45\u4E0A\u9650 / \u5E45, \u4E0B\u9650)) : 1;
29635
- const \u5207\u308B = (t, \u5927\u304D\u3055, \u5B57\u9593 = 0) => \u5E2F\u3067\u5207\u308B(t, \u5927\u304D\u3055 * k, \u5E45\u4E0A\u9650, (u, f) => textWidth(u, f, \u5B57\u9593 * k));
29944
+ const \u5207\u308B = (t, \u5927\u304D\u3055, \u5B57\u9593 = 0) => \u5E2F\u3067\u5207\u308B(
29945
+ t,
29946
+ \u5927\u304D\u3055 * k,
29947
+ \u5E45\u4E0A\u9650,
29948
+ (u, f) => textWidth(u, f, \u5B57\u9593 * k, textMetrics)
29949
+ );
29636
29950
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
29637
29951
  node.eyebrow && plan.\u80A9\u66F8 && /* @__PURE__ */ jsxRuntime.jsx(
29638
29952
  "text",
@@ -29673,7 +29987,7 @@ function planLabel(node, cx, \u5E45\u4E0A\u9650, plan) {
29673
29987
  )
29674
29988
  ] });
29675
29989
  }
29676
- function ShapePersonNode({ node, active }) {
29990
+ function ShapePersonNode({ node, active, textMetrics = "proportional" }) {
29677
29991
  const r = shapeRegion(node);
29678
29992
  const cx = r.cx;
29679
29993
  const strokeColor = active ? "var(--cdl-tone-accent, #2d6a8f)" : "var(--cdl-divider, #d4d4d8)";
@@ -29735,7 +30049,7 @@ function ShapePersonNode({ node, active }) {
29735
30049
  )
29736
30050
  ] })
29737
30051
  ),
29738
- planLabel(node, r.cx, Math.max(0, node.w), r.label)
30052
+ planLabel(node, r.cx, Math.max(0, node.w), r.label, textMetrics)
29739
30053
  ] });
29740
30054
  }
29741
30055
  var commonFrame2 = (active) => ({
@@ -29985,7 +30299,12 @@ function ShapeTerminalNode({ node, active, lang }) {
29985
30299
  )
29986
30300
  ] });
29987
30301
  }
29988
- function ShapeCodeBlockNode({ node, active, lang }) {
30302
+ function ShapeCodeBlockNode({
30303
+ node,
30304
+ active,
30305
+ lang,
30306
+ textMetrics = "proportional"
30307
+ }) {
29989
30308
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
29990
30309
  const frame = commonFrame2(active);
29991
30310
  const \u7DDA = frame.strokeWidth / 2;
@@ -29996,7 +30315,10 @@ function ShapeCodeBlockNode({ node, active, lang }) {
29996
30315
  const lineFont = "ui-monospace, SFMono-Regular, Menlo, monospace";
29997
30316
  const \u672D = \u66F8\u3044\u305F\u5024\u304B\u63A7\u3048(node.subtitle, \u5B57\u5F15("codeBlock.fileName"));
29998
30317
  const \u672D\u306E\u5B57 = 11;
29999
- const \u30BF\u30D6\u5E45 = Math.min(Math.max(100, textWidth(\u672D, \u672D\u306E\u5B57, 0) + 24), Math.max(0, w));
30318
+ const \u30BF\u30D6\u5E45 = Math.min(
30319
+ Math.max(100, textWidth(\u672D, \u672D\u306E\u5B57, 0, textMetrics) + 24),
30320
+ Math.max(0, w)
30321
+ );
30000
30322
  const \u30BF\u30D6\u9AD8 = 24;
30001
30323
  const \u89D2 = 10;
30002
30324
  const \u6E9D = 32;
@@ -30036,7 +30358,7 @@ function ShapeCodeBlockNode({ node, active, lang }) {
30036
30358
  { text: \u672D, size: \u672D\u306E\u5B57, \u5E2F: { \u5E45: \u30BF\u30D6\u5E45, \u9AD8\u3055: \u30BF\u30D6\u9AD8 } },
30037
30359
  { text: "1", size: \u884C\u756A\u53F7\u306E\u5B57, \u5E2F: { \u5E45: \u6E9D - \u6301\u3061\u4E0A\u3052, \u9AD8\u3055: \u884C\u9593 } }
30038
30360
  ];
30039
- const \u500D\u8FD4\u3057 = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D, \u6253\u3061\u6D88\u3059\u5B57\u3089);
30361
+ const \u500D\u8FD4\u3057 = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
30040
30362
  const tabW = \u30BF\u30D6\u5E45 * \u500D;
30041
30363
  const tabH = \u30BF\u30D6\u9AD8 * \u500D;
30042
30364
  const \u4E38 = \u89D2 * \u500D;
@@ -30075,7 +30397,7 @@ function ShapeCodeBlockNode({ node, active, lang }) {
30075
30397
  "data-cdl-counter-scaled": "1",
30076
30398
  x: x + tabW / 2,
30077
30399
  y: y + tabH / 2 + 4 * \u500D,
30078
- fontSize: \u672D\u306E\u5B57 * \u500D * \u500D\u8FD4\u3057 * \u5E45\u306E\u500D\u7387(\u672D, \u672D\u306E\u5B57 * \u500D * \u500D\u8FD4\u3057, 0, tabW),
30400
+ fontSize: \u672D\u306E\u5B57 * \u500D * \u500D\u8FD4\u3057 * \u5E45\u306E\u500D\u7387(\u672D, \u672D\u306E\u5B57 * \u500D * \u500D\u8FD4\u3057, 0, tabW, textMetrics),
30079
30401
  fontFamily: lineFont,
30080
30402
  textAnchor: "middle",
30081
30403
  fill: "#e6edf3",
@@ -30157,7 +30479,12 @@ function ShapeCodeBlockNode({ node, active, lang }) {
30157
30479
  )
30158
30480
  ] });
30159
30481
  }
30160
- function ShapeKanbanCardNode({ node, active, lang }) {
30482
+ function ShapeKanbanCardNode({
30483
+ node,
30484
+ active,
30485
+ lang,
30486
+ textMetrics = "proportional"
30487
+ }) {
30161
30488
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
30162
30489
  const frame = commonFrame2(active);
30163
30490
  const \u7DDA = frame.strokeWidth / 2;
@@ -30211,7 +30538,7 @@ function ShapeKanbanCardNode({ node, active, lang }) {
30211
30538
  );
30212
30539
  const \u8AAC\u660E = \u66F8\u3044\u305F\u5024\u304B\u63A7\u3048(node.subtitle, \u5B57\u5F15("kanbanCard.task"));
30213
30540
  const \u72B6\u614B = \u66F8\u3044\u305F\u5024\u304B\u63A7\u3048(node.eyebrow, \u5B57\u5F15("kanbanCard.status"));
30214
- const \u72B6\u614B\u306E\u500D\u7387 = \u5E45\u306E\u500D\u7387(\u72B6\u614B, PILL\u5B57, PILL\u5B57\u9593, PILL\u5B57\u5E45);
30541
+ const \u72B6\u614B\u306E\u500D\u7387 = \u5E45\u306E\u500D\u7387(\u72B6\u614B, PILL\u5B57, PILL\u5B57\u9593, PILL\u5B57\u5E45, textMetrics);
30215
30542
  const \u8AAC\u660E\u306E\u5B57 = \u540D\u524D.size * \u8AAC\u660E\u5B57\u6BD4;
30216
30543
  const \u4F7F\u3048\u308B\u5E452 = Math.max(0, w - \u5DE6\u53F3\u4F59\u767D * \u500D * 2);
30217
30544
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
@@ -30298,7 +30625,7 @@ function ShapeKanbanCardNode({ node, active, lang }) {
30298
30625
  {
30299
30626
  x: x + w / 2,
30300
30627
  y: \u540D\u524D.y + \u540D\u524D.size * \u8AAC\u660E\u57FA\u6E96\u6BD4,
30301
- fontSize: \u8AAC\u660E\u306E\u5B57 * \u5E45\u306E\u500D\u7387(\u8AAC\u660E, \u8AAC\u660E\u306E\u5B57, 0, \u4F7F\u3048\u308B\u5E452),
30628
+ fontSize: \u8AAC\u660E\u306E\u5B57 * \u5E45\u306E\u500D\u7387(\u8AAC\u660E, \u8AAC\u660E\u306E\u5B57, 0, \u4F7F\u3048\u308B\u5E452, textMetrics),
30302
30629
  textAnchor: "middle",
30303
30630
  fill: "var(--cdl-text-dim, #5a6270)",
30304
30631
  children: \u8AAC\u660E
@@ -30589,18 +30916,33 @@ var externalLabel = (node, cx, bottomY) => /* @__PURE__ */ jsxRuntime.jsxs(jsxRu
30589
30916
  )
30590
30917
  ] });
30591
30918
  var LABEL_EYEBROW_SPACING = 2;
30592
- function \u5E45\u306B\u53CE\u3081\u308B2(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u984C\u304B = false) {
30593
- const \u5E45 = textWidth(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593);
30594
- const \u4E0B\u9650 = \u984C\u304B ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, textWidth) : 0;
30919
+ function \u5E45\u306B\u53CE\u3081\u308B2(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u984C\u304B = false, textMetrics = "proportional") {
30920
+ const \u6E2C\u308B = (t, s, ls) => textWidth(t, s, ls, textMetrics);
30921
+ const \u5E45 = \u6E2C\u308B(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593);
30922
+ const \u4E0B\u9650 = \u984C\u304B ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u6E2C\u308B) : 0;
30595
30923
  const \u500D\u7387 = \u5E45 > 0 && \u7BB1\u5E45 > 0 ? Math.min(1, Math.max(\u7BB1\u5E45 / \u5E45, \u4E0B\u9650)) : 1;
30596
30924
  const size = \u5927\u304D\u3055 * \u500D\u7387;
30597
30925
  const spacing = \u5B57\u9593 * \u500D\u7387;
30598
- return { size, spacing, text: \u5E2F\u3067\u5207\u308B(\u6587\u5B57\u5217, size, \u7BB1\u5E45, (u, f) => textWidth(u, f, spacing)) };
30599
- }
30600
- function bottomLabel(node, cx, plan) {
30601
- const \u80A9 = \u5E45\u306B\u53CE\u3081\u308B2(node.eyebrow ?? "", plan.\u80A9\u66F8?.size ?? 0, LABEL_EYEBROW_SPACING, node.w);
30602
- const \u540D = \u5E45\u306B\u53CE\u3081\u308B2(node.title ?? "", plan.\u540D\u524D.size, 0, node.w, true);
30603
- const \u8AAC = \u5E45\u306B\u53CE\u3081\u308B2(node.subtitle ?? "", plan.\u8AAC\u660E?.size ?? 0, 0, node.w);
30926
+ return { size, spacing, text: \u5E2F\u3067\u5207\u308B(\u6587\u5B57\u5217, size, \u7BB1\u5E45, (u, f) => \u6E2C\u308B(u, f, spacing)) };
30927
+ }
30928
+ function bottomLabel(node, cx, plan, textMetrics = "proportional") {
30929
+ const \u80A9 = \u5E45\u306B\u53CE\u3081\u308B2(
30930
+ node.eyebrow ?? "",
30931
+ plan.\u80A9\u66F8?.size ?? 0,
30932
+ LABEL_EYEBROW_SPACING,
30933
+ node.w,
30934
+ false,
30935
+ textMetrics
30936
+ );
30937
+ const \u540D = \u5E45\u306B\u53CE\u3081\u308B2(node.title ?? "", plan.\u540D\u524D.size, 0, node.w, true, textMetrics);
30938
+ const \u8AAC = \u5E45\u306B\u53CE\u3081\u308B2(
30939
+ node.subtitle ?? "",
30940
+ plan.\u8AAC\u660E?.size ?? 0,
30941
+ 0,
30942
+ node.w,
30943
+ false,
30944
+ textMetrics
30945
+ );
30604
30946
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
30605
30947
  node.eyebrow && plan.\u80A9\u66F8 && /* @__PURE__ */ jsxRuntime.jsx("text", { x: cx, y: plan.\u80A9\u66F8.y, fontSize: \u80A9.size, fontWeight: 700, letterSpacing: \u80A9.spacing, textAnchor: "middle", fill: "var(--cdl-tone-accent, #2d6a8f)", children: \u80A9.text }),
30606
30948
  /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-role": "node-label", x: cx, y: plan.\u540D\u524D.y, fontSize: \u540D.size, fontWeight: 700, textAnchor: "middle", fill: "var(--cdl-text, #1a1f2a)", children: \u540D.text }),
@@ -30614,7 +30956,7 @@ var RACK_SLOT_N = 4;
30614
30956
  var RACK_BOTTOM = 8;
30615
30957
  var RACK_H = RACK_SLOT_TOP + RACK_SLOT_N * RACK_SLOT_H + (RACK_SLOT_N - 1) * RACK_SLOT_GAP + RACK_BOTTOM;
30616
30958
  var RACK_W_MIN = 120;
30617
- function ShapeServerRackNode({ node, active }) {
30959
+ function ShapeServerRackNode({ node, active, textMetrics = "proportional" }) {
30618
30960
  const r = shapeRegion(node);
30619
30961
  const frame = commonFrame3(active);
30620
30962
  const \u7DDA = frame.strokeWidth / 2;
@@ -30696,7 +31038,7 @@ function ShapeServerRackNode({ node, active }) {
30696
31038
  ] }, i);
30697
31039
  })
30698
31040
  ] })),
30699
- bottomLabel(node, r.cx, r.label)
31041
+ bottomLabel(node, r.cx, r.label, textMetrics)
30700
31042
  ] });
30701
31043
  }
30702
31044
  var HUB_R = 30;
@@ -30704,7 +31046,7 @@ var ARM_LEN = 68;
30704
31046
  var END_R = 7;
30705
31047
  var WIFI_ARC_R = [10, 16, 22];
30706
31048
  var WIFI_BASE_Y = 5;
30707
- function ShapeNetworkNodeNode({ node, active }) {
31049
+ function ShapeNetworkNodeNode({ node, active, textMetrics = "proportional" }) {
30708
31050
  const r = shapeRegion(node);
30709
31051
  const cx = r.cx;
30710
31052
  const cy = r.cy;
@@ -30780,12 +31122,12 @@ function ShapeNetworkNodeNode({ node, active }) {
30780
31122
  )),
30781
31123
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx, cy: cy + WIFI_BASE_Y + 3, r: 2.5, fill: "var(--cdl-tone-accent, #2d6a8f)", stroke: "none" })
30782
31124
  ] })),
30783
- bottomLabel(node, r.cx, r.label)
31125
+ bottomLabel(node, r.cx, r.label, textMetrics)
30784
31126
  ] });
30785
31127
  }
30786
31128
  var PHONE_H = 240;
30787
31129
  var PHONE_W = 110;
30788
- function ShapeMobileDeviceNode({ node, active }) {
31130
+ function ShapeMobileDeviceNode({ node, active, textMetrics = "proportional" }) {
30789
31131
  const r = shapeRegion(node);
30790
31132
  const frame = commonFrame3(active);
30791
31133
  const \u7DDA = frame.strokeWidth / 2;
@@ -30852,7 +31194,7 @@ function ShapeMobileDeviceNode({ node, active }) {
30852
31194
  }
30853
31195
  )
30854
31196
  ] })),
30855
- bottomLabel(node, r.cx, r.label)
31197
+ bottomLabel(node, r.cx, r.label, textMetrics)
30856
31198
  ] });
30857
31199
  }
30858
31200
  function ShapeIotSensorNode({ node, active }) {
@@ -31123,7 +31465,7 @@ var SAT_DISH_R = 12;
31123
31465
  var SAT_DISH_STEM = 12;
31124
31466
  var SAT_MAST_LEN = 22;
31125
31467
  var SAT_MAST_TIP_R = 4;
31126
- function ShapeSatelliteNode({ node, active }) {
31468
+ function ShapeSatelliteNode({ node, active, textMetrics = "proportional" }) {
31127
31469
  const r = shapeRegion(node);
31128
31470
  const cx = r.cx;
31129
31471
  const cy = r.cy;
@@ -31312,7 +31654,7 @@ function ShapeSatelliteNode({ node, active }) {
31312
31654
  ),
31313
31655
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx, cy: cy - bodyH / 2 - SAT_MAST_LEN, r: 2, fill: "#ff5f56", stroke: "none", children: /* @__PURE__ */ jsxRuntime.jsx("animate", { attributeName: "opacity", values: "0.4;1;0.4", dur: "1.4s", repeatCount: "indefinite" }) })
31314
31656
  ] })),
31315
- bottomLabel(node, r.cx, r.label)
31657
+ bottomLabel(node, r.cx, r.label, textMetrics)
31316
31658
  ] });
31317
31659
  }
31318
31660
  var FRAME_SW_ACTIVE = 3;
@@ -31398,9 +31740,9 @@ function blockchainNodeExtent(strokeWidth) {
31398
31740
  const \u6A2A = (NODE_PEER_DIST + NODE_PEER_R) * Math.cos(Math.PI / 6) + \u7DDA;
31399
31741
  return { \u4E0A: \u7E26, \u4E0B: \u7E26, \u5DE6: \u6A2A, \u53F3: \u6A2A };
31400
31742
  }
31401
- function bottomLabel2(node, cx, plan) {
31743
+ function bottomLabel2(node, cx, plan, textMetrics = "proportional") {
31402
31744
  const \u53CE\u3081\u308B = (t, \u5927\u304D\u3055, \u5B57\u9593, \u984C\u304B = false) => {
31403
- const \u6E2C\u308B = (u, f, ls) => \u5B57\u306E\u5E45(u, f) + ls * [...u].length;
31745
+ const \u6E2C\u308B = (u, f, ls) => \u5B57\u306E\u5E45(u, f, textMetrics) + ls * [...u].length;
31404
31746
  const \u7D20\u306E\u5E45 = \u6E2C\u308B(t, \u5927\u304D\u3055, \u5B57\u9593);
31405
31747
  const \u53CE\u307E\u308B = \u7D20\u306E\u5E45 > node.w && node.w > 0 ? node.w / \u7D20\u306E\u5E45 : 1;
31406
31748
  const \u4E0B\u9650 = \u984C\u304B ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(t, \u5927\u304D\u3055, \u5B57\u9593, node.w, \u6E2C\u308B) : 0;
@@ -31433,7 +31775,12 @@ function EthereumDiamond({ cx, cy, h, colors }) {
31433
31775
  /* @__PURE__ */ jsxRuntime.jsx("path", { d: `M ${cx} ${midY} L ${cx + w} ${cy + h * 0.05} L ${cx} ${lowerBotY} Z`, fill: c.dark, stroke: c.stroke, strokeWidth: 0.6, strokeLinejoin: "round" })
31434
31776
  ] });
31435
31777
  }
31436
- function ShapeSmartContractNode({ node, active, lang }) {
31778
+ function ShapeSmartContractNode({
31779
+ node,
31780
+ active,
31781
+ lang,
31782
+ textMetrics = "proportional"
31783
+ }) {
31437
31784
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
31438
31785
  const frame = commonFrame4(active);
31439
31786
  const r = shapeRegion(node);
@@ -31474,7 +31821,7 @@ function ShapeSmartContractNode({ node, active, lang }) {
31474
31821
  }
31475
31822
  ];
31476
31823
  const art = (\u500D\u7387) => {
31477
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
31824
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
31478
31825
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31479
31826
  /* @__PURE__ */ jsxRuntime.jsx("path", { "data-cdl-role": "node-body", d: path, ...frame, strokeLinejoin: "round" }),
31480
31827
  /* @__PURE__ */ jsxRuntime.jsx("path", { d: foldPath, fill: "none", stroke: frame.stroke, strokeWidth: frame.strokeWidth, strokeLinejoin: "round" }),
@@ -31496,10 +31843,10 @@ function ShapeSmartContractNode({ node, active, lang }) {
31496
31843
  };
31497
31844
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31498
31845
  fitArt(r, smartContractExtent(frame.strokeWidth), art),
31499
- bottomLabel2(node, r.cx, r.label)
31846
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31500
31847
  ] });
31501
31848
  }
31502
- var \u5B57\u306E\u5E45 = (text, size) => \u7D75\u306E\u4E2D\u306E\u5B57\u306E\u5E45(text, size);
31849
+ var \u5B57\u306E\u5E45 = (text, size, textMetrics = "proportional") => \u7D75\u306E\u4E2D\u306E\u5B57\u306E\u5E45(text, size, 0, textMetrics);
31503
31850
  var BLOCK_DEFAULT_FIELDS = [
31504
31851
  { key: "hash", label: "blockchainBlock.hash", value: { text: "0xaf31..." } },
31505
31852
  { key: "prev", label: "blockchainBlock.prev", value: { text: "0x7b3f..." } },
@@ -31507,10 +31854,16 @@ var BLOCK_DEFAULT_FIELDS = [
31507
31854
  { key: "nonce", label: "blockchainBlock.nonce", value: { text: "82,914" } },
31508
31855
  { key: "tx", label: "blockchainBlock.tx", value: { \u8F9E\u66F8: "blockchainBlock.txCount" } }
31509
31856
  ];
31510
- function ShapeBlockchainBlockNode({ node, active, lang }) {
31857
+ function ShapeBlockchainBlockNode({
31858
+ node,
31859
+ active,
31860
+ lang,
31861
+ textMetrics = "proportional"
31862
+ }) {
31511
31863
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
31512
31864
  const frame = commonFrame4(active);
31513
31865
  const r = shapeRegion(node);
31866
+ const \u6E2C\u308B\u5B57 = (text, size) => \u5B57\u306E\u5E45(text, size, textMetrics);
31514
31867
  const bw = BLOCK_W;
31515
31868
  const bh = BLOCK_H;
31516
31869
  const cx = r.cx;
@@ -31531,9 +31884,9 @@ function ShapeBlockchainBlockNode({ node, active, lang }) {
31531
31884
  const \u5E2F\u306E\u6B8B\u308A = bw - 14 - 30;
31532
31885
  const \u80A9\u66F8\u306E\u9699\u9593 = 8;
31533
31886
  const \u80A9\u66F8\u306E\u4E0A\u9650 = (\u5E2F\u306E\u6B8B\u308A - \u80A9\u66F8\u306E\u9699\u9593) / 2;
31534
- const \u80A9\u66F8\u306E\u500D\u7387 = \u80A9\u66F8 === "" ? 1 : \u5E45\u306E\u500D\u7387(\u80A9\u66F8, \u80A9\u66F8\u306E\u5B57, 0, \u80A9\u66F8\u306E\u4E0A\u9650);
31887
+ const \u80A9\u66F8\u306E\u500D\u7387 = \u80A9\u66F8 === "" ? 1 : \u5E45\u306E\u500D\u7387(\u80A9\u66F8, \u80A9\u66F8\u306E\u5B57, 0, \u80A9\u66F8\u306E\u4E0A\u9650, textMetrics);
31535
31888
  const \u80A9\u66F8\u306E\u6307\u5B9A = \u80A9\u66F8\u306E\u5B57 * \u80A9\u66F8\u306E\u500D\u7387;
31536
- const \u80A9\u66F8\u306E\u5E45 = \u80A9\u66F8 === "" ? 0 : \u5B57\u306E\u5E45(\u80A9\u66F8, \u80A9\u66F8\u306E\u6307\u5B9A);
31889
+ const \u80A9\u66F8\u306E\u5E45 = \u80A9\u66F8 === "" ? 0 : \u6E2C\u308B\u5B57(\u80A9\u66F8, \u80A9\u66F8\u306E\u6307\u5B9A);
31537
31890
  const \u898B\u51FA\u3057\u306E\u5E45 = \u5E2F\u306E\u6B8B\u308A - (\u80A9\u66F8 === "" ? 0 : \u80A9\u66F8\u306E\u5E45 + \u80A9\u66F8\u306E\u9699\u9593);
31538
31891
  const \u6253\u3061\u6D88\u3059\u5B57\u3089 = [
31539
31892
  { text: \u898B\u51FA\u3057, size: \u898B\u51FA\u3057\u306E\u5B57, \u5E2F: { \u5E45: \u898B\u51FA\u3057\u306E\u5E45, \u9AD8\u3055: \u898B\u51FA\u3057\u306E\u5E2F } },
@@ -31544,12 +31897,12 @@ function ShapeBlockchainBlockNode({ node, active, lang }) {
31544
31897
  {
31545
31898
  text: f.value,
31546
31899
  size: \u5024\u306E\u5B57,
31547
- \u5E2F: { \u5E45: bw - 28 - \u5B57\u306E\u5E45(f.label, \u540D\u306E\u5B57) - 8, \u9AD8\u3055: \u884C\u306E\u9593\u9694 }
31900
+ \u5E2F: { \u5E45: bw - 28 - \u6E2C\u308B\u5B57(f.label, \u540D\u306E\u5B57) - 8, \u9AD8\u3055: \u884C\u306E\u9593\u9694 }
31548
31901
  }
31549
31902
  ])
31550
31903
  ];
31551
31904
  const art = (\u500D\u7387) => {
31552
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
31905
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
31553
31906
  const \u984C\u306E\u5927\u304D\u3055 = \u898B\u51FA\u3057\u306E\u5B57 * \u500D;
31554
31907
  const \u80A9\u66F8\u306E\u5927\u304D\u3055 = \u80A9\u66F8\u306E\u6307\u5B9A * \u500D;
31555
31908
  const \u540D\u306E\u5927\u304D\u3055 = \u540D\u306E\u5B57 * \u500D;
@@ -31558,7 +31911,7 @@ function ShapeBlockchainBlockNode({ node, active, lang }) {
31558
31911
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x: x + 6, y: y + 6, width: bw, height: bh, rx: 8, fill: frame.stroke, opacity: 0.2, stroke: "none" }),
31559
31912
  /* @__PURE__ */ jsxRuntime.jsx("rect", { "data-cdl-role": "node-body", x, y, width: bw, height: bh, rx: 8, ...frame }),
31560
31913
  /* @__PURE__ */ jsxRuntime.jsx("path", { d: `M ${x} ${y + 32} L ${x} ${y + 8} Q ${x} ${y}, ${x + 8} ${y} L ${x + bw - 8} ${y} Q ${x + bw} ${y}, ${x + bw} ${y + 8} L ${x + bw} ${y + 32} Z`, fill: "var(--cdl-tone-accent, #2d6a8f)", fillOpacity: 0.9, stroke: "none" }),
31561
- /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-role": "blockchain-block-title", "data-cdl-counter-scaled": "1", x: x + 14, y: y + 22, fontSize: \u984C\u306E\u5927\u304D\u3055, fontWeight: 700, fontFamily: "ui-monospace, SFMono-Regular, Menlo, monospace", fill: "#ffffff", children: \u5E45\u3067\u5207\u308B(\u898B\u51FA\u3057, \u984C\u306E\u5927\u304D\u3055, \u898B\u51FA\u3057\u306E\u5E45, \u5B57\u306E\u5E45) }),
31914
+ /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-role": "blockchain-block-title", "data-cdl-counter-scaled": "1", x: x + 14, y: y + 22, fontSize: \u984C\u306E\u5927\u304D\u3055, fontWeight: 700, fontFamily: "ui-monospace, SFMono-Regular, Menlo, monospace", fill: "#ffffff", children: \u5E45\u3067\u5207\u308B(\u898B\u51FA\u3057, \u984C\u306E\u5927\u304D\u3055, \u898B\u51FA\u3057\u306E\u5E45, \u6E2C\u308B\u5B57) }),
31562
31915
  \u80A9\u66F8 !== "" && /* @__PURE__ */ jsxRuntime.jsx(
31563
31916
  "text",
31564
31917
  {
@@ -31578,7 +31931,12 @@ function ShapeBlockchainBlockNode({ node, active, lang }) {
31578
31931
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: x + bw - 16, cy: y + 16, r: 5.5, fill: "#7cd88f", stroke: "#ffffff", strokeWidth: 1.5 }),
31579
31932
  fields.map((f, i) => /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31580
31933
  /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-counter-scaled": "1", x: x + 14, y: y + 54 + i * \u884C\u306E\u9593\u9694, fontSize: \u540D\u306E\u5927\u304D\u3055, fontFamily: "ui-monospace, SFMono-Regular, Menlo, monospace", fill: "var(--cdl-text-dim, #5a6270)", children: f.label }),
31581
- /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-role": `blockchain-block-${f.key}`, "data-cdl-counter-scaled": "1", x: x + bw - 14, y: y + 54 + i * \u884C\u306E\u9593\u9694, fontSize: \u5024\u306E\u5927\u304D\u3055, fontFamily: "ui-monospace, SFMono-Regular, Menlo, monospace", fontWeight: 600, textAnchor: "end", fill: "var(--cdl-text, #1a1f2a)", children: \u5E45\u3067\u5207\u308B(f.value, \u5024\u306E\u5927\u304D\u3055, bw - 28 - \u5B57\u306E\u5E45(f.label, \u540D\u306E\u5927\u304D\u3055) - 8, \u5B57\u306E\u5E45) }),
31934
+ /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-role": `blockchain-block-${f.key}`, "data-cdl-counter-scaled": "1", x: x + bw - 14, y: y + 54 + i * \u884C\u306E\u9593\u9694, fontSize: \u5024\u306E\u5927\u304D\u3055, fontFamily: "ui-monospace, SFMono-Regular, Menlo, monospace", fontWeight: 600, textAnchor: "end", fill: "var(--cdl-text, #1a1f2a)", children: \u5E45\u3067\u5207\u308B(
31935
+ f.value,
31936
+ \u5024\u306E\u5927\u304D\u3055,
31937
+ bw - 28 - \u6E2C\u308B\u5B57(f.label, \u540D\u306E\u5927\u304D\u3055) - 8,
31938
+ \u6E2C\u308B\u5B57
31939
+ ) }),
31582
31940
  /* @__PURE__ */ jsxRuntime.jsx("line", { x1: x + 14, y1: y + 60 + i * \u884C\u306E\u9593\u9694, x2: x + bw - 14, y2: y + 60 + i * \u884C\u306E\u9593\u9694, stroke: "var(--cdl-divider, #d4d4d8)", strokeWidth: 0.5, opacity: 0.5 })
31583
31941
  ] }, i)),
31584
31942
  /* @__PURE__ */ jsxRuntime.jsxs("g", { transform: `translate(${cx - 32}, ${y + bh - 26})`, children: [
@@ -31590,7 +31948,11 @@ function ShapeBlockchainBlockNode({ node, active, lang }) {
31590
31948
  };
31591
31949
  return /* @__PURE__ */ jsxRuntime.jsx("g", { children: fitArt(r, blockchainBlockExtent(frame.strokeWidth), art) });
31592
31950
  }
31593
- function ShapeBlockchainNode({ node, active }) {
31951
+ function ShapeBlockchainNode({
31952
+ node,
31953
+ active,
31954
+ textMetrics = "proportional"
31955
+ }) {
31594
31956
  const frame = commonFrame4(active);
31595
31957
  const r = shapeRegion(node);
31596
31958
  const cx = r.cx;
@@ -31606,7 +31968,7 @@ function ShapeBlockchainNode({ node, active }) {
31606
31968
  { text: "0x\u2026", size: CHAIN_HASH_SIZE, \u5E2F: { \u5E45: CHAIN_TEXT_W, \u9AD8\u3055: CHAIN_ROW_GAP } }
31607
31969
  ];
31608
31970
  const art = (\u500D\u7387) => {
31609
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
31971
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
31610
31972
  return /* @__PURE__ */ jsxRuntime.jsx("g", { children: Array.from({ length: blockCount }, (_, i) => i).map((i) => {
31611
31973
  const bx = startX + i * (blockW + linkW);
31612
31974
  const isCurrent = i === blockCount - 1;
@@ -31642,10 +32004,14 @@ function ShapeBlockchainNode({ node, active }) {
31642
32004
  };
31643
32005
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31644
32006
  fitArt(r, chainExtent(), art),
31645
- bottomLabel2(node, r.cx, r.label)
32007
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31646
32008
  ] });
31647
32009
  }
31648
- function ShapeBitcoinChainNode({ node, active }) {
32010
+ function ShapeBitcoinChainNode({
32011
+ node,
32012
+ active,
32013
+ textMetrics = "proportional"
32014
+ }) {
31649
32015
  const frame = commonFrame4(active);
31650
32016
  const r = shapeRegion(node);
31651
32017
  const cx = r.cx;
@@ -31661,7 +32027,7 @@ function ShapeBitcoinChainNode({ node, active }) {
31661
32027
  { text: "#820", size: BTC_NO_SIZE, \u5E2F: { \u5E45: CHAIN_TEXT_W, \u9AD8\u3055: 20 } }
31662
32028
  ];
31663
32029
  const art = (\u500D\u7387) => {
31664
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
32030
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
31665
32031
  return /* @__PURE__ */ jsxRuntime.jsx("g", { children: Array.from({ length: blockCount }, (_, i) => i).map((i) => {
31666
32032
  const bx = startX + i * (blockW + linkW);
31667
32033
  const isCurrent = i === blockCount - 1;
@@ -31692,10 +32058,14 @@ function ShapeBitcoinChainNode({ node, active }) {
31692
32058
  };
31693
32059
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31694
32060
  fitArt(r, chainExtent(), art),
31695
- bottomLabel2(node, r.cx, r.label)
32061
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31696
32062
  ] });
31697
32063
  }
31698
- function ShapeEthereumChainNode({ node, active }) {
32064
+ function ShapeEthereumChainNode({
32065
+ node,
32066
+ active,
32067
+ textMetrics = "proportional"
32068
+ }) {
31699
32069
  const frame = commonFrame4(active);
31700
32070
  const r = shapeRegion(node);
31701
32071
  const cx = r.cx;
@@ -31711,7 +32081,7 @@ function ShapeEthereumChainNode({ node, active }) {
31711
32081
  { text: "#214", size: ETH_NO_SIZE, \u5E2F: { \u5E45: CHAIN_TEXT_W, \u9AD8\u3055: 20 } }
31712
32082
  ];
31713
32083
  const art = (\u500D\u7387) => {
31714
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
32084
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
31715
32085
  return /* @__PURE__ */ jsxRuntime.jsx("g", { children: Array.from({ length: blockCount }, (_, i) => i).map((i) => {
31716
32086
  const bx = startX + i * (blockW + linkW);
31717
32087
  const isCurrent = i === blockCount - 1;
@@ -31743,10 +32113,14 @@ function ShapeEthereumChainNode({ node, active }) {
31743
32113
  };
31744
32114
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31745
32115
  fitArt(r, chainExtent(), art),
31746
- bottomLabel2(node, r.cx, r.label)
32116
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31747
32117
  ] });
31748
32118
  }
31749
- function ShapeBlockchainNodeNode({ node, active }) {
32119
+ function ShapeBlockchainNodeNode({
32120
+ node,
32121
+ active,
32122
+ textMetrics = "proportional"
32123
+ }) {
31750
32124
  const frame = commonFrame4(active);
31751
32125
  const r = shapeRegion(node);
31752
32126
  const cx = r.cx;
@@ -31800,10 +32174,15 @@ function ShapeBlockchainNodeNode({ node, active }) {
31800
32174
  ] });
31801
32175
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31802
32176
  fitArt(r, blockchainNodeExtent(frame.strokeWidth), art),
31803
- bottomLabel2(node, r.cx, r.label)
32177
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31804
32178
  ] });
31805
32179
  }
31806
- function ShapeRpcNodeNode({ node, active, lang }) {
32180
+ function ShapeRpcNodeNode({
32181
+ node,
32182
+ active,
32183
+ lang,
32184
+ textMetrics = "proportional"
32185
+ }) {
31807
32186
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
31808
32187
  const frame = commonFrame4(active);
31809
32188
  const r = shapeRegion(node);
@@ -31822,10 +32201,10 @@ function ShapeRpcNodeNode({ node, active, lang }) {
31822
32201
  /* @__PURE__ */ jsxRuntime.jsx("text", { x: cx, y: cy + 26, fontSize: 11, textAnchor: "middle", fill: "#7a8290", fontFamily: "ui-monospace, SFMono-Regular, Menlo, monospace", children: "JSON-RPC 2.0" }),
31823
32202
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x: x + 16, y: y + bh - 24, width: bw - 32, height: 8, rx: 4, fill: "#0f1419", stroke: "none" }),
31824
32203
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x: x + 16, y: y + bh - 24, width: (bw - 32) * 0.92, height: 8, rx: 4, fill: "#27c93f", stroke: "none", children: /* @__PURE__ */ jsxRuntime.jsx("animate", { attributeName: "width", values: `${(bw - 32) * 0.86};${(bw - 32) * 0.96};${(bw - 32) * 0.86}`, dur: "3s", repeatCount: "indefinite" }) }),
31825
- bottomLabel2(node, r.cx, r.label)
32204
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31826
32205
  ] });
31827
32206
  }
31828
- function ShapeWalletNode({ node, active }) {
32207
+ function ShapeWalletNode({ node, active, textMetrics = "proportional" }) {
31829
32208
  const frame = commonFrame4(active);
31830
32209
  const r = shapeRegion(node);
31831
32210
  const cx = r.cx;
@@ -31899,10 +32278,10 @@ function ShapeWalletNode({ node, active }) {
31899
32278
  /* @__PURE__ */ jsxRuntime.jsx("text", { x: cx, y: foldY + 3, fontSize: 9, fontWeight: 700, fill: "#5a3a10", textAnchor: "middle", opacity: 0.8, children: "\u039E" }),
31900
32279
  /* @__PURE__ */ jsxRuntime.jsx("path", { d: `M ${x + 2} ${y + 6} L ${x + w - 2} ${y + 6}`, fill: "none", stroke: "#ffffff", strokeWidth: 1, opacity: 0.4 })
31901
32280
  ] }),
31902
- bottomLabel2(node, r.cx, r.label)
32281
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31903
32282
  ] });
31904
32283
  }
31905
- function ShapeNftNode({ node, active }) {
32284
+ function ShapeNftNode({ node, active, textMetrics = "proportional" }) {
31906
32285
  const frame = commonFrame4(active);
31907
32286
  const r = shapeRegion(node);
31908
32287
  const cx = r.cx;
@@ -31918,7 +32297,7 @@ function ShapeNftNode({ node, active }) {
31918
32297
  { text: "#1024", size: NFT_ID_SIZE, \u5E2F: { \u5E45: cardW - 16 - 34, \u9AD8\u3055: cardH - artH } }
31919
32298
  ];
31920
32299
  const art = (\u500D\u7387) => {
31921
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
32300
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
31922
32301
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31923
32302
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x: x + 4, y: y + 4, width: cardW, height: cardH, rx: 14, fill: frame.stroke, opacity: 0.2, stroke: "none" }),
31924
32303
  /* @__PURE__ */ jsxRuntime.jsx("rect", { "data-cdl-role": "node-body", x, y, width: cardW, height: cardH, rx: 14, ...frame }),
@@ -31956,10 +32335,10 @@ function ShapeNftNode({ node, active }) {
31956
32335
  };
31957
32336
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
31958
32337
  fitArt(r, nftExtent(frame.strokeWidth), art),
31959
- bottomLabel2(node, r.cx, r.label)
32338
+ bottomLabel2(node, r.cx, r.label, textMetrics)
31960
32339
  ] });
31961
32340
  }
31962
- function ShapeTokenNode({ node, active }) {
32341
+ function ShapeTokenNode({ node, active, textMetrics = "proportional" }) {
31963
32342
  const frame = commonFrame4(active);
31964
32343
  const r = shapeRegion(node);
31965
32344
  const cx = r.cx;
@@ -31996,7 +32375,7 @@ function ShapeTokenNode({ node, active }) {
31996
32375
  }
31997
32376
  }
31998
32377
  ),
31999
- bottomLabel2(node, r.cx, r.label)
32378
+ bottomLabel2(node, r.cx, r.label, textMetrics)
32000
32379
  ] });
32001
32380
  }
32002
32381
  var commonFrame5 = (active) => ({
@@ -32015,7 +32394,8 @@ function \u5B57\u306E\u6BD4(c) {
32015
32394
  if (\u5E83\u5B57.has(c)) return \u5E83\u5B57\u6BD4;
32016
32395
  return (c.codePointAt(0) ?? 0) < 128 ? \u4E26\u5B57\u6BD4 : \u5E83\u5B57\u6BD4;
32017
32396
  }
32018
- function \u5B57\u5E45(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593) {
32397
+ function \u5B57\u5E45(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, textMetrics = "proportional") {
32398
+ if (textMetrics === "monospace") return textWidth(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, textMetrics);
32019
32399
  let \u5E45 = 0;
32020
32400
  let \u5B57\u6570 = 0;
32021
32401
  for (const c of \u6587\u5B57\u5217) {
@@ -32024,18 +32404,33 @@ function \u5B57\u5E45(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593) {
32024
32404
  }
32025
32405
  return \u5E45 + \u5B57\u9593 * \u5B57\u6570;
32026
32406
  }
32027
- function \u5E45\u306B\u53CE\u3081\u308B3(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u984C\u304B = false) {
32028
- const \u5E45 = \u5B57\u5E45(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593);
32029
- const \u4E0B\u9650 = \u984C\u304B ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u5B57\u5E45) : 0;
32407
+ function \u5E45\u306B\u53CE\u3081\u308B3(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u984C\u304B = false, textMetrics = "proportional") {
32408
+ const \u6E2C\u308B = (t, s, ls) => \u5B57\u5E45(t, s, ls, textMetrics);
32409
+ const \u5E45 = \u6E2C\u308B(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593);
32410
+ const \u4E0B\u9650 = \u984C\u304B ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u6E2C\u308B) : 0;
32030
32411
  const \u500D\u7387 = \u5E45 > 0 && \u7BB1\u5E45 > 0 ? Math.min(1, Math.max(\u7BB1\u5E45 / \u5E45, \u4E0B\u9650)) : 1;
32031
32412
  const size = \u5927\u304D\u3055 * \u500D\u7387;
32032
32413
  const spacing = \u5B57\u9593 * \u500D\u7387;
32033
- return { size, spacing, text: \u5E2F\u3067\u5207\u308B(\u6587\u5B57\u5217, size, \u7BB1\u5E45, (u, f) => \u5B57\u5E45(u, f, spacing)) };
32034
- }
32035
- function bottomLabel3(node, cx, plan) {
32036
- const \u80A9 = \u5E45\u306B\u53CE\u3081\u308B3(node.eyebrow ?? "", plan.\u80A9\u66F8?.size ?? 0, LABEL_EYEBROW_SPACING2, node.w);
32037
- const \u540D = \u5E45\u306B\u53CE\u3081\u308B3(node.title ?? "", plan.\u540D\u524D.size, 0, node.w, true);
32038
- const \u8AAC = \u5E45\u306B\u53CE\u3081\u308B3(node.subtitle ?? "", plan.\u8AAC\u660E?.size ?? 0, 0, node.w);
32414
+ return { size, spacing, text: \u5E2F\u3067\u5207\u308B(\u6587\u5B57\u5217, size, \u7BB1\u5E45, (u, f) => \u6E2C\u308B(u, f, spacing)) };
32415
+ }
32416
+ function bottomLabel3(node, cx, plan, textMetrics = "proportional") {
32417
+ const \u80A9 = \u5E45\u306B\u53CE\u3081\u308B3(
32418
+ node.eyebrow ?? "",
32419
+ plan.\u80A9\u66F8?.size ?? 0,
32420
+ LABEL_EYEBROW_SPACING2,
32421
+ node.w,
32422
+ false,
32423
+ textMetrics
32424
+ );
32425
+ const \u540D = \u5E45\u306B\u53CE\u3081\u308B3(node.title ?? "", plan.\u540D\u524D.size, 0, node.w, true, textMetrics);
32426
+ const \u8AAC = \u5E45\u306B\u53CE\u3081\u308B3(
32427
+ node.subtitle ?? "",
32428
+ plan.\u8AAC\u660E?.size ?? 0,
32429
+ 0,
32430
+ node.w,
32431
+ false,
32432
+ textMetrics
32433
+ );
32039
32434
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
32040
32435
  node.eyebrow && plan.\u80A9\u66F8 && /* @__PURE__ */ jsxRuntime.jsx("text", { x: cx, y: plan.\u80A9\u66F8.y, fontSize: \u80A9.size, fontWeight: 700, letterSpacing: \u80A9.spacing, textAnchor: "middle", fill: "var(--cdl-tone-accent, #2d6a8f)", children: \u80A9.text }),
32041
32436
  /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-role": "node-label", x: cx, y: plan.\u540D\u524D.y, fontSize: \u540D.size, fontWeight: 700, textAnchor: "middle", fill: "var(--cdl-text, #1a1f2a)", children: \u540D.text }),
@@ -32054,7 +32449,7 @@ var BANK_STEP_SW = 1;
32054
32449
  var BANK_COLUMN_MIN = 24;
32055
32450
  var BANK_BLD_W_MIN = 120;
32056
32451
  var BANK_BLD_W_MAX = 280;
32057
- function ShapeBankNode({ node, active }) {
32452
+ function ShapeBankNode({ node, active, textMetrics = "proportional" }) {
32058
32453
  const frame = commonFrame5(active);
32059
32454
  const r = shapeRegion(node);
32060
32455
  const \u7DDA = frame.strokeWidth / 2;
@@ -32101,7 +32496,7 @@ function ShapeBankNode({ node, active }) {
32101
32496
  ] });
32102
32497
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32103
32498
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32104
- bottomLabel3(node, r.cx, r.label)
32499
+ bottomLabel3(node, r.cx, r.label, textMetrics)
32105
32500
  ] });
32106
32501
  }
32107
32502
  var TRUST_CROWN_RISE = 4;
@@ -32113,7 +32508,12 @@ var TRUST_BASE_H = 14;
32113
32508
  var TRUST_BODY_OUT = 8;
32114
32509
  var TRUST_BLD_W_MIN = 140;
32115
32510
  var TRUST_BLD_W_MAX = 280;
32116
- function ShapeTrustBankNode({ node, active, lang }) {
32511
+ function ShapeTrustBankNode({
32512
+ node,
32513
+ active,
32514
+ lang,
32515
+ textMetrics = "proportional"
32516
+ }) {
32117
32517
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32118
32518
  const frame = commonFrame5(active);
32119
32519
  const r = shapeRegion(node);
@@ -32167,10 +32567,15 @@ function ShapeTrustBankNode({ node, active, lang }) {
32167
32567
  ] });
32168
32568
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32169
32569
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32170
- bottomLabel3(node, r.cx, r.label)
32570
+ bottomLabel3(node, r.cx, r.label, textMetrics)
32171
32571
  ] });
32172
32572
  }
32173
- function ShapePaymentProviderNode({ node, active, lang }) {
32573
+ function ShapePaymentProviderNode({
32574
+ node,
32575
+ active,
32576
+ lang,
32577
+ textMetrics = "proportional"
32578
+ }) {
32174
32579
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32175
32580
  const frame = commonFrame5(active);
32176
32581
  const r = shapeRegion(node);
@@ -32195,10 +32600,14 @@ function ShapePaymentProviderNode({ node, active, lang }) {
32195
32600
  /* @__PURE__ */ jsxRuntime.jsx("text", { x: cx, y: cy + 9, fontSize: 13, fontWeight: 700, textAnchor: "middle", fill: accentDarker, fontFamily: "Georgia, serif", children: "$" })
32196
32601
  ] }),
32197
32602
  /* @__PURE__ */ jsxRuntime.jsx("text", { x: cx, y: y + boxH - 16, fontSize: 11, fontWeight: 700, letterSpacing: 2, textAnchor: "middle", fill: "#a4b5f2", children: \u5B57\u5F15("paymentProvider.status") }),
32198
- bottomLabel3(node, r.cx, r.label)
32603
+ bottomLabel3(node, r.cx, r.label, textMetrics)
32199
32604
  ] });
32200
32605
  }
32201
- function ShapeCreditCardNode({ node, active }) {
32606
+ function ShapeCreditCardNode({
32607
+ node,
32608
+ active,
32609
+ textMetrics = "proportional"
32610
+ }) {
32202
32611
  const frame = commonFrame5(active);
32203
32612
  const r = shapeRegion(node);
32204
32613
  const cardW = Math.min(r.availW - 30, 260);
@@ -32220,7 +32629,7 @@ function ShapeCreditCardNode({ node, active }) {
32220
32629
  [0, 1, 2, 3].map((block) => /* @__PURE__ */ jsxRuntime.jsx("g", { children: [0, 1, 2, 3].map((dot) => /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: x + 32 + block * (cardW - 64) / 4 + dot * 8, cy: y + cardH - 40, r: 2.8, fill: "#ffffff", stroke: "none" }, dot)) }, block)),
32221
32630
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: x + cardW - 48, cy: y + cardH - 24, r: 15, fill: "#c9302c", opacity: 0.9, stroke: "none" }),
32222
32631
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: x + cardW - 30, cy: y + cardH - 24, r: 15, fill: "#e5c07b", opacity: 0.9, stroke: "none" }),
32223
- bottomLabel3(node, r.cx, r.label)
32632
+ bottomLabel3(node, r.cx, r.label, textMetrics)
32224
32633
  ] });
32225
32634
  }
32226
32635
  var BROKERAGE_TICK_H = 18;
@@ -32245,7 +32654,12 @@ var BROKERAGE_SHADE_OUT = 2;
32245
32654
  var BROKERAGE_W_MIN = BROKERAGE_COLS * BROKERAGE_CELL_W + (BROKERAGE_COLS - 1) * BROKERAGE_GAP_X + 6;
32246
32655
  var BROKERAGE_W_MAX = 140;
32247
32656
  var BROKERAGE_H_MIN = BROKERAGE_TICK_H + BROKERAGE_LOGO_H + BROKERAGE_BASE_H;
32248
- function ShapeBrokerageNode({ node, active, lang }) {
32657
+ function ShapeBrokerageNode({
32658
+ node,
32659
+ active,
32660
+ lang,
32661
+ textMetrics = "proportional"
32662
+ }) {
32249
32663
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32250
32664
  const frame = commonFrame5(active);
32251
32665
  const r = shapeRegion(node);
@@ -32284,7 +32698,7 @@ function ShapeBrokerageNode({ node, active, lang }) {
32284
32698
  }
32285
32699
  ];
32286
32700
  const \u7D75 = (\u500D\u7387) => {
32287
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
32701
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
32288
32702
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32289
32703
  /* @__PURE__ */ jsxRuntime.jsx("ellipse", { cx, cy: y + h + BROKERAGE_SHADOW_DY, rx: w * BROKERAGE_SHADOW_RX_RATIO, ry: BROKERAGE_SHADOW_RY, fill: frame.stroke, opacity: 0.2, stroke: "none" }),
32290
32704
  /* @__PURE__ */ jsxRuntime.jsx("rect", { "data-cdl-role": "node-body", x, y, width: w, height: h, fill: "#255a7a", stroke: accentDarker, strokeWidth: frame.strokeWidth }),
@@ -32312,12 +32726,17 @@ function ShapeBrokerageNode({ node, active, lang }) {
32312
32726
  };
32313
32727
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32314
32728
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32315
- bottomLabel3(node, r.cx, r.label)
32729
+ bottomLabel3(node, r.cx, r.label, textMetrics)
32316
32730
  ] });
32317
32731
  }
32318
32732
  var EXCHANGE_SUB_SIZE = 11;
32319
32733
  var EXCHANGE_HEX_R = 52;
32320
- function ShapeExchangeNode({ node, active, lang }) {
32734
+ function ShapeExchangeNode({
32735
+ node,
32736
+ active,
32737
+ lang,
32738
+ textMetrics = "proportional"
32739
+ }) {
32321
32740
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32322
32741
  const frame = commonFrame5(active);
32323
32742
  const r = shapeRegion(node);
@@ -32362,7 +32781,7 @@ function ShapeExchangeNode({ node, active, lang }) {
32362
32781
  }
32363
32782
  ];
32364
32783
  const \u7D75 = (\u500D\u7387) => {
32365
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
32784
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
32366
32785
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32367
32786
  nodes.map((n, i) => /* @__PURE__ */ jsxRuntime.jsx("line", { x1: cx, y1: cy, x2: n.cx, y2: n.cy, stroke: accentDarker, strokeWidth: 1.5, strokeDasharray: "3 2" }, `l${i}`)),
32368
32787
  nodes.map((n, i) => {
@@ -32381,7 +32800,7 @@ function ShapeExchangeNode({ node, active, lang }) {
32381
32800
  };
32382
32801
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32383
32802
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32384
- bottomLabel3(node, r.cx, r.label)
32803
+ bottomLabel3(node, r.cx, r.label, textMetrics)
32385
32804
  ] });
32386
32805
  }
32387
32806
  var ATM_SIGN_H = 26;
@@ -32398,7 +32817,12 @@ var ATM_PANEL_H = 146;
32398
32817
  var ATM_W_MIN = 100;
32399
32818
  var ATM_W_MAX = ATM_PANEL_W;
32400
32819
  var ATM_H_MIN = ATM_SIGN_H + ATM_SIGN_GAP + 30 + ATM_FLOOR_RESERVE;
32401
- function ShapeAtmNode({ node, active, lang }) {
32820
+ function ShapeAtmNode({
32821
+ node,
32822
+ active,
32823
+ lang,
32824
+ textMetrics = "proportional"
32825
+ }) {
32402
32826
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32403
32827
  const frame = commonFrame5(active);
32404
32828
  const r = shapeRegion(node);
@@ -32482,7 +32906,7 @@ function ShapeAtmNode({ node, active, lang }) {
32482
32906
  ] });
32483
32907
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32484
32908
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32485
- bottomLabel3(node, r.cx, r.label)
32909
+ bottomLabel3(node, r.cx, r.label, textMetrics)
32486
32910
  ] });
32487
32911
  }
32488
32912
  var commonFrame6 = (active) => ({
@@ -32501,7 +32925,8 @@ function \u5B57\u306E\u6BD42(c) {
32501
32925
  if (\u5E83\u5B572.has(c)) return \u5E83\u5B57\u6BD42;
32502
32926
  return (c.codePointAt(0) ?? 0) < 128 ? \u4E26\u5B57\u6BD42 : \u5E83\u5B57\u6BD42;
32503
32927
  }
32504
- function \u5B57\u5E452(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593) {
32928
+ function \u5B57\u5E452(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, textMetrics = "proportional") {
32929
+ if (textMetrics === "monospace") return textWidth(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, textMetrics);
32505
32930
  let \u5E45 = 0;
32506
32931
  let \u5B57\u6570 = 0;
32507
32932
  for (const c of \u6587\u5B57\u5217) {
@@ -32510,18 +32935,33 @@ function \u5B57\u5E452(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593) {
32510
32935
  }
32511
32936
  return \u5E45 + \u5B57\u9593 * \u5B57\u6570;
32512
32937
  }
32513
- function \u5E45\u306B\u53CE\u3081\u308B4(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u984C\u304B = false) {
32514
- const \u5E45 = \u5B57\u5E452(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593);
32515
- const \u4E0B\u9650 = \u984C\u304B ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u5B57\u5E452) : 0;
32938
+ function \u5E45\u306B\u53CE\u3081\u308B4(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u984C\u304B = false, textMetrics = "proportional") {
32939
+ const \u6E2C\u308B = (t, s, ls) => \u5B57\u5E452(t, s, ls, textMetrics);
32940
+ const \u5E45 = \u6E2C\u308B(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593);
32941
+ const \u4E0B\u9650 = \u984C\u304B ? \u5207\u3063\u3066\u53CE\u307E\u308B\u4E0B\u9650(\u6587\u5B57\u5217, \u5927\u304D\u3055, \u5B57\u9593, \u7BB1\u5E45, \u6E2C\u308B) : 0;
32516
32942
  const \u500D\u7387 = \u5E45 > 0 && \u7BB1\u5E45 > 0 ? Math.min(1, Math.max(\u7BB1\u5E45 / \u5E45, \u4E0B\u9650)) : 1;
32517
32943
  const size = \u5927\u304D\u3055 * \u500D\u7387;
32518
32944
  const spacing = \u5B57\u9593 * \u500D\u7387;
32519
- return { size, spacing, text: \u5E2F\u3067\u5207\u308B(\u6587\u5B57\u5217, size, \u7BB1\u5E45, (u, f) => \u5B57\u5E452(u, f, spacing)) };
32520
- }
32521
- function bottomLabel4(node, cx, plan) {
32522
- const \u80A9 = \u5E45\u306B\u53CE\u3081\u308B4(node.eyebrow ?? "", plan.\u80A9\u66F8?.size ?? 0, LABEL_EYEBROW_SPACING3, node.w);
32523
- const \u540D = \u5E45\u306B\u53CE\u3081\u308B4(node.title ?? "", plan.\u540D\u524D.size, 0, node.w, true);
32524
- const \u8AAC = \u5E45\u306B\u53CE\u3081\u308B4(node.subtitle ?? "", plan.\u8AAC\u660E?.size ?? 0, 0, node.w);
32945
+ return { size, spacing, text: \u5E2F\u3067\u5207\u308B(\u6587\u5B57\u5217, size, \u7BB1\u5E45, (u, f) => \u6E2C\u308B(u, f, spacing)) };
32946
+ }
32947
+ function bottomLabel4(node, cx, plan, textMetrics = "proportional") {
32948
+ const \u80A9 = \u5E45\u306B\u53CE\u3081\u308B4(
32949
+ node.eyebrow ?? "",
32950
+ plan.\u80A9\u66F8?.size ?? 0,
32951
+ LABEL_EYEBROW_SPACING3,
32952
+ node.w,
32953
+ false,
32954
+ textMetrics
32955
+ );
32956
+ const \u540D = \u5E45\u306B\u53CE\u3081\u308B4(node.title ?? "", plan.\u540D\u524D.size, 0, node.w, true, textMetrics);
32957
+ const \u8AAC = \u5E45\u306B\u53CE\u3081\u308B4(
32958
+ node.subtitle ?? "",
32959
+ plan.\u8AAC\u660E?.size ?? 0,
32960
+ 0,
32961
+ node.w,
32962
+ false,
32963
+ textMetrics
32964
+ );
32525
32965
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
32526
32966
  node.eyebrow && plan.\u80A9\u66F8 && /* @__PURE__ */ jsxRuntime.jsx("text", { x: cx, y: plan.\u80A9\u66F8.y, fontSize: \u80A9.size, fontWeight: 700, letterSpacing: \u80A9.spacing, textAnchor: "middle", fill: "var(--cdl-tone-accent, #2d6a8f)", children: \u80A9.text }),
32527
32967
  /* @__PURE__ */ jsxRuntime.jsx("text", { "data-cdl-role": "node-label", x: cx, y: plan.\u540D\u524D.y, fontSize: \u540D.size, fontWeight: 700, textAnchor: "middle", fill: "var(--cdl-text, #1a1f2a)", children: \u540D.text }),
@@ -32533,7 +32973,7 @@ var WEBSITE_BAR_H = 32;
32533
32973
  var WEBSITE_H_MIN = WEBSITE_BAR_H + 98;
32534
32974
  var WEBSITE_W_MIN = 160;
32535
32975
  var WEBSITE_W_MAX = 280;
32536
- function ShapeWebsiteNode({ node, active }) {
32976
+ function ShapeWebsiteNode({ node, active, textMetrics = "proportional" }) {
32537
32977
  const frame = commonFrame6(active);
32538
32978
  const r = shapeRegion(node);
32539
32979
  const cx = r.cx;
@@ -32559,10 +32999,10 @@ function ShapeWebsiteNode({ node, active }) {
32559
32999
  ] });
32560
33000
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32561
33001
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32562
- bottomLabel4(node, r.cx, r.label)
33002
+ bottomLabel4(node, r.cx, r.label, textMetrics)
32563
33003
  ] });
32564
33004
  }
32565
- function ShapeStorefrontNode({ node, active, lang }) {
33005
+ function ShapeStorefrontNode({ node, active, lang, textMetrics = "proportional" }) {
32566
33006
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32567
33007
  const frame = commonFrame6(active);
32568
33008
  const r = shapeRegion(node);
@@ -32607,7 +33047,7 @@ function ShapeStorefrontNode({ node, active, lang }) {
32607
33047
  /* @__PURE__ */ jsxRuntime.jsx("text", { x: doorX + doorW / 2, y: doorY + doorH * 0.85 + 11, fontSize: 11, fontWeight: 700, letterSpacing: 1, textAnchor: "middle", fill: "#5a3a10", children: \u5B57\u5F15("storefront.open") }),
32608
33048
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: doorX + 6, cy: doorY + doorH * 0.55, r: 1.5, fill: "#c15a4a" }),
32609
33049
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x: x - 6, y: y + bh - 6, width: bw + 12, height: 8, fill: "#5a6270", stroke: "none" }),
32610
- bottomLabel4(node, r.cx, r.label)
33050
+ bottomLabel4(node, r.cx, r.label, textMetrics)
32611
33051
  ] });
32612
33052
  }
32613
33053
  var WAREHOUSE_ROOF_H = 18;
@@ -32621,7 +33061,7 @@ var WAREHOUSE_SHADOW_RX_RATIO = 0.5;
32621
33061
  var WAREHOUSE_H_MIN = WAREHOUSE_ROOF_H + WAREHOUSE_SIGN_H + 68;
32622
33062
  var WAREHOUSE_W_MIN = 160;
32623
33063
  var WAREHOUSE_W_MAX = 240;
32624
- function ShapeWarehouseNode({ node, active, lang }) {
33064
+ function ShapeWarehouseNode({ node, active, lang, textMetrics = "proportional" }) {
32625
33065
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32626
33066
  const frame = commonFrame6(active);
32627
33067
  const r = shapeRegion(node);
@@ -32674,13 +33114,13 @@ function ShapeWarehouseNode({ node, active, lang }) {
32674
33114
  ] });
32675
33115
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32676
33116
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32677
- bottomLabel4(node, r.cx, r.label)
33117
+ bottomLabel4(node, r.cx, r.label, textMetrics)
32678
33118
  ] });
32679
33119
  }
32680
33120
  var HANDLE_GRIP_X = 118;
32681
33121
  var HANDLE_GRIP_R = 4;
32682
33122
  var CART_SHADOW_RX = 80;
32683
- function ShapeOnlineShopNode({ node, active }) {
33123
+ function ShapeOnlineShopNode({ node, active, textMetrics = "proportional" }) {
32684
33124
  const frame = commonFrame6(active);
32685
33125
  const r = shapeRegion(node);
32686
33126
  const cy = r.cy + 10;
@@ -32736,10 +33176,10 @@ function ShapeOnlineShopNode({ node, active }) {
32736
33176
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: wheelR, cy: wheelY, r: 16 * s, fill: "#0f1830", stroke: "#000", strokeWidth: 2 * s }),
32737
33177
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: wheelR, cy: wheelY, r: 8 * s, fill: "#5a6270", stroke: "#0f1830", strokeWidth: 1.5 * s }),
32738
33178
  /* @__PURE__ */ jsxRuntime.jsx("circle", { cx: wheelR, cy: wheelY, r: 2 * s, fill: "#0f1830" }),
32739
- bottomLabel4(node, r.cx, r.label)
33179
+ bottomLabel4(node, r.cx, r.label, textMetrics)
32740
33180
  ] });
32741
33181
  }
32742
- function ShapeCdnEdgeNode({ node, active }) {
33182
+ function ShapeCdnEdgeNode({ node, active, textMetrics = "proportional" }) {
32743
33183
  const frame = commonFrame6(active);
32744
33184
  const r = shapeRegion(node);
32745
33185
  const cx = r.cx;
@@ -32802,7 +33242,7 @@ function ShapeCdnEdgeNode({ node, active }) {
32802
33242
  ] });
32803
33243
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32804
33244
  fitArt(r, { \u4E0A: \u5E83\u304C\u308A, \u4E0B: \u5E83\u304C\u308A, \u5DE6: \u5E83\u304C\u308A, \u53F3: \u5E83\u304C\u308A }, \u7D75),
32805
- bottomLabel4(node, r.cx, r.label)
33245
+ bottomLabel4(node, r.cx, r.label, textMetrics)
32806
33246
  ] });
32807
33247
  }
32808
33248
  var API_ROW_TOP = 52;
@@ -32817,7 +33257,7 @@ var API_METHOD_BOX_W = 54;
32817
33257
  var API_METHOD_TEXT_W = 48;
32818
33258
  var API_W_MIN = 200;
32819
33259
  var API_W_MAX = 300;
32820
- function ShapeApiGatewayNode({ node, active, lang }) {
33260
+ function ShapeApiGatewayNode({ node, active, lang, textMetrics = "proportional" }) {
32821
33261
  const \u5B57\u5F15 = \u5B57\u5F15\u304D\u3092\u4F5C\u308B(lang);
32822
33262
  const frame = commonFrame6(active);
32823
33263
  const r = shapeRegion(node);
@@ -32829,7 +33269,13 @@ function ShapeApiGatewayNode({ node, active, lang }) {
32829
33269
  const x = cx - bw / 2;
32830
33270
  const y = r.cy - \u7E26 / 2 + \u4F59\u767D;
32831
33271
  const \u5E83\u304C\u308A = { \u4E0A: \u7E26 / 2, \u4E0B: \u7E26 / 2, \u5DE6: bw / 2 + \u4F59\u767D, \u53F3: bw / 2 + \u4F59\u767D };
32832
- const \u7A2E\u985E\u306E\u5B57 = (s) => Math.min(11, 11 * API_METHOD_TEXT_W / Math.max(displayWidth(s) * 11 * MONO_ADVANCE_RATIO, textWidth(s, 11)));
33272
+ const \u7A2E\u985E\u306E\u5B57 = (s) => Math.min(
33273
+ 11,
33274
+ 11 * API_METHOD_TEXT_W / Math.max(
33275
+ displayWidth(s) * 11 * MONO_ADVANCE_RATIO,
33276
+ textWidth(s, 11, 0, textMetrics)
33277
+ )
33278
+ );
32833
33279
  const rowPitch = Math.max(
32834
33280
  API_ROW_PITCH_MIN,
32835
33281
  (bh - API_ROW_TOP - API_ROW_H - API_ROW_BOTTOM_PAD) / (API_ROWS - 1)
@@ -32845,7 +33291,7 @@ function ShapeApiGatewayNode({ node, active, lang }) {
32845
33291
  \u5E2F: { \u5E45: bw - 32 - 64 - 16, \u9AD8\u3055: API_ROW_H }
32846
33292
  }));
32847
33293
  const \u7D75 = (\u500D\u7387) => {
32848
- const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089);
33294
+ const \u500D = \u6253\u3061\u6D88\u3057\u306E\u500D\u7387(\u500D\u7387, \u6253\u3061\u6D88\u3059\u5B57\u3089, textMetrics);
32849
33295
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32850
33296
  /* @__PURE__ */ jsxRuntime.jsx("rect", { x: x + DROP_SHADOW_D, y: y + DROP_SHADOW_D, width: bw, height: bh, rx: 10, fill: frame.stroke, opacity: 0.2, stroke: "none" }),
32851
33297
  /* @__PURE__ */ jsxRuntime.jsx("rect", { "data-cdl-role": "node-body", x, y, width: bw, height: bh, rx: 10, fill: "#1a2332", stroke: frame.stroke, strokeWidth: frame.strokeWidth }),
@@ -32862,7 +33308,7 @@ function ShapeApiGatewayNode({ node, active, lang }) {
32862
33308
  };
32863
33309
  return /* @__PURE__ */ jsxRuntime.jsxs("g", { children: [
32864
33310
  fitArt(r, \u5E83\u304C\u308A, \u7D75),
32865
- bottomLabel4(node, r.cx, r.label)
33311
+ bottomLabel4(node, r.cx, r.label, textMetrics)
32866
33312
  ] });
32867
33313
  }
32868
33314
  function bottomLabel5(node, cx, plan) {
@@ -33162,6 +33608,7 @@ function CdlNodeView({
33162
33608
  chartLineScale,
33163
33609
  \u95A2\u4FC2\u306E\u53D7\u3051\u53E3,
33164
33610
  lang,
33611
+ textMetrics,
33165
33612
  \u5024\u306E\u540D\u524D
33166
33613
  }) {
33167
33614
  const value = node.value ? interpolate(node.value, stateValues, \u5024\u306E\u540D\u524D) : void 0;
@@ -33206,7 +33653,14 @@ function CdlNodeView({
33206
33653
  return /* @__PURE__ */ jsxRuntime.jsx(CardNode, { node: resolvedNode, active });
33207
33654
  // 時系列のやり取り (#578)。 1 つの箱が図を丸ごと描く = 縦が時間で、参加者は箱を持たない
33208
33655
  case "sequence-board":
33209
- return /* @__PURE__ */ jsxRuntime.jsx(SequenceBoardNode, { node: resolvedNode, stateValues });
33656
+ return /* @__PURE__ */ jsxRuntime.jsx(
33657
+ SequenceBoardNode,
33658
+ {
33659
+ node: resolvedNode,
33660
+ stateValues,
33661
+ textMetrics
33662
+ }
33663
+ );
33210
33664
  // 図表 9 種は payload が `{signal}` を取れるので stateValues を渡す
33211
33665
  // (`render/payload-binding.ts` が描画直前に解決する)。 取れる欄は種別で違い、
33212
33666
  // 数と語を取る 7 種に対し、mind-map / tree-hierarchy は **名前だけ** を取る (#467)。
@@ -33231,7 +33685,8 @@ function CdlNodeView({
33231
33685
  active,
33232
33686
  stateValues,
33233
33687
  drawing,
33234
- progress
33688
+ progress,
33689
+ textMetrics
33235
33690
  }
33236
33691
  );
33237
33692
  case "chart-gauge":
@@ -33242,7 +33697,8 @@ function CdlNodeView({
33242
33697
  active,
33243
33698
  stateValues,
33244
33699
  drawing,
33245
- progress
33700
+ progress,
33701
+ textMetrics
33246
33702
  }
33247
33703
  );
33248
33704
  case "chart-stacked-bar":
@@ -33253,7 +33709,8 @@ function CdlNodeView({
33253
33709
  active,
33254
33710
  stateValues,
33255
33711
  drawing,
33256
- progress
33712
+ progress,
33713
+ textMetrics
33257
33714
  }
33258
33715
  );
33259
33716
  case "chart-slope":
@@ -33264,7 +33721,8 @@ function CdlNodeView({
33264
33721
  active,
33265
33722
  stateValues,
33266
33723
  drawing,
33267
- progress
33724
+ progress,
33725
+ textMetrics
33268
33726
  }
33269
33727
  );
33270
33728
  case "chart-waffle":
@@ -33275,11 +33733,20 @@ function CdlNodeView({
33275
33733
  active,
33276
33734
  stateValues,
33277
33735
  drawing,
33278
- progress
33736
+ progress,
33737
+ textMetrics
33279
33738
  }
33280
33739
  );
33281
33740
  case "chart-stat":
33282
- return /* @__PURE__ */ jsxRuntime.jsx(ChartStatNode, { node: resolvedNode, active, stateValues });
33741
+ return /* @__PURE__ */ jsxRuntime.jsx(
33742
+ ChartStatNode,
33743
+ {
33744
+ node: resolvedNode,
33745
+ active,
33746
+ stateValues,
33747
+ textMetrics
33748
+ }
33749
+ );
33283
33750
  case "chart-radial":
33284
33751
  return /* @__PURE__ */ jsxRuntime.jsx(
33285
33752
  ChartRadialNode,
@@ -33288,7 +33755,8 @@ function CdlNodeView({
33288
33755
  active,
33289
33756
  stateValues,
33290
33757
  drawing,
33291
- progress
33758
+ progress,
33759
+ textMetrics
33292
33760
  }
33293
33761
  );
33294
33762
  case "chart-bar":
@@ -33321,7 +33789,8 @@ function CdlNodeView({
33321
33789
  active,
33322
33790
  stateValues,
33323
33791
  drawing,
33324
- progress
33792
+ progress,
33793
+ textMetrics
33325
33794
  }
33326
33795
  );
33327
33796
  case "funnel-stages":
@@ -33332,11 +33801,20 @@ function CdlNodeView({
33332
33801
  active,
33333
33802
  stateValues,
33334
33803
  drawing,
33335
- progress
33804
+ progress,
33805
+ textMetrics
33336
33806
  }
33337
33807
  );
33338
33808
  case "quadrant-matrix":
33339
- return /* @__PURE__ */ jsxRuntime.jsx(QuadrantNode, { node: resolvedNode, active, stateValues });
33809
+ return /* @__PURE__ */ jsxRuntime.jsx(
33810
+ QuadrantNode,
33811
+ {
33812
+ node: resolvedNode,
33813
+ active,
33814
+ stateValues,
33815
+ textMetrics
33816
+ }
33817
+ );
33340
33818
  case "tree-hierarchy":
33341
33819
  return /* @__PURE__ */ jsxRuntime.jsx(
33342
33820
  TreeNode,
@@ -33345,7 +33823,8 @@ function CdlNodeView({
33345
33823
  active,
33346
33824
  stateValues,
33347
33825
  drawing,
33348
- progress
33826
+ progress,
33827
+ textMetrics
33349
33828
  }
33350
33829
  );
33351
33830
  case "journey-map":
@@ -33360,91 +33839,91 @@ function CdlNodeView({
33360
33839
  }
33361
33840
  );
33362
33841
  case "shape-file":
33363
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeFileNode, { node: resolvedNode, active });
33842
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeFileNode, { node: resolvedNode, active, textMetrics });
33364
33843
  case "shape-folder":
33365
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeFolderNode, { node: resolvedNode, active });
33844
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeFolderNode, { node: resolvedNode, active, textMetrics });
33366
33845
  case "shape-cloud":
33367
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeCloudNode, { node: resolvedNode, active });
33846
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeCloudNode, { node: resolvedNode, active, textMetrics });
33368
33847
  case "shape-cylinder":
33369
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeCylinderNode, { node: resolvedNode, active });
33848
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeCylinderNode, { node: resolvedNode, active, textMetrics });
33370
33849
  case "shape-hexagon":
33371
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeHexagonNode, { node: resolvedNode, active });
33850
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeHexagonNode, { node: resolvedNode, active, textMetrics });
33372
33851
  case "shape-diamond":
33373
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeDiamondNode, { node: resolvedNode, active });
33852
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeDiamondNode, { node: resolvedNode, active, textMetrics });
33374
33853
  case "shape-stack":
33375
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeStackNode, { node: resolvedNode, active });
33854
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeStackNode, { node: resolvedNode, active, textMetrics });
33376
33855
  case "shape-person":
33377
- return /* @__PURE__ */ jsxRuntime.jsx(ShapePersonNode, { node: resolvedNode, active });
33856
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapePersonNode, { node: resolvedNode, active, textMetrics });
33378
33857
  case "shape-window":
33379
33858
  return /* @__PURE__ */ jsxRuntime.jsx(ShapeWindowNode, { node: resolvedNode, active });
33380
33859
  case "shape-terminal":
33381
33860
  return /* @__PURE__ */ jsxRuntime.jsx(ShapeTerminalNode, { node: resolvedNode, active, lang });
33382
33861
  case "shape-code-block":
33383
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeCodeBlockNode, { node: resolvedNode, active, lang });
33862
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeCodeBlockNode, { node: resolvedNode, active, lang, textMetrics });
33384
33863
  case "shape-kanban-card":
33385
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeKanbanCardNode, { node: resolvedNode, active, lang });
33864
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeKanbanCardNode, { node: resolvedNode, active, lang, textMetrics });
33386
33865
  case "shape-message-bubble":
33387
33866
  return /* @__PURE__ */ jsxRuntime.jsx(ShapeMessageBubbleNode, { node: resolvedNode, active });
33388
33867
  case "shape-gear":
33389
33868
  return /* @__PURE__ */ jsxRuntime.jsx(ShapeGearNode, { node: resolvedNode, active });
33390
33869
  case "shape-server-rack":
33391
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeServerRackNode, { node: resolvedNode, active });
33870
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeServerRackNode, { node: resolvedNode, active, textMetrics });
33392
33871
  case "shape-network-node":
33393
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeNetworkNodeNode, { node: resolvedNode, active });
33872
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeNetworkNodeNode, { node: resolvedNode, active, textMetrics });
33394
33873
  case "shape-mobile-device":
33395
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeMobileDeviceNode, { node: resolvedNode, active });
33874
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeMobileDeviceNode, { node: resolvedNode, active, textMetrics });
33396
33875
  case "shape-iot-sensor":
33397
33876
  return /* @__PURE__ */ jsxRuntime.jsx(ShapeIotSensorNode, { node: resolvedNode, active });
33398
33877
  case "shape-robot-arm":
33399
33878
  return /* @__PURE__ */ jsxRuntime.jsx(ShapeRobotArmNode, { node: resolvedNode, active });
33400
33879
  case "shape-satellite":
33401
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeSatelliteNode, { node: resolvedNode, active });
33880
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeSatelliteNode, { node: resolvedNode, active, textMetrics });
33402
33881
  case "shape-smart-contract":
33403
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeSmartContractNode, { node: resolvedNode, active, lang });
33882
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeSmartContractNode, { node: resolvedNode, active, lang, textMetrics });
33404
33883
  case "shape-blockchain-block":
33405
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeBlockchainBlockNode, { node: resolvedNode, active, lang });
33884
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeBlockchainBlockNode, { node: resolvedNode, active, lang, textMetrics });
33406
33885
  case "shape-rpc-node":
33407
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeRpcNodeNode, { node: resolvedNode, active, lang });
33886
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeRpcNodeNode, { node: resolvedNode, active, lang, textMetrics });
33408
33887
  case "shape-wallet":
33409
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeWalletNode, { node: resolvedNode, active });
33888
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeWalletNode, { node: resolvedNode, active, textMetrics });
33410
33889
  case "shape-nft":
33411
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeNftNode, { node: resolvedNode, active });
33890
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeNftNode, { node: resolvedNode, active, textMetrics });
33412
33891
  case "shape-token":
33413
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeTokenNode, { node: resolvedNode, active });
33892
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeTokenNode, { node: resolvedNode, active, textMetrics });
33414
33893
  case "shape-blockchain":
33415
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeBlockchainNode, { node: resolvedNode, active });
33894
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeBlockchainNode, { node: resolvedNode, active, textMetrics });
33416
33895
  case "shape-bitcoin-chain":
33417
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeBitcoinChainNode, { node: resolvedNode, active });
33896
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeBitcoinChainNode, { node: resolvedNode, active, textMetrics });
33418
33897
  case "shape-ethereum-chain":
33419
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeEthereumChainNode, { node: resolvedNode, active });
33898
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeEthereumChainNode, { node: resolvedNode, active, textMetrics });
33420
33899
  case "shape-blockchain-node":
33421
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeBlockchainNodeNode, { node: resolvedNode, active });
33900
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeBlockchainNodeNode, { node: resolvedNode, active, textMetrics });
33422
33901
  case "shape-bank":
33423
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeBankNode, { node: resolvedNode, active });
33902
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeBankNode, { node: resolvedNode, active, textMetrics });
33424
33903
  case "shape-trust-bank":
33425
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeTrustBankNode, { node: resolvedNode, active, lang });
33904
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeTrustBankNode, { node: resolvedNode, active, lang, textMetrics });
33426
33905
  case "shape-payment-provider":
33427
- return /* @__PURE__ */ jsxRuntime.jsx(ShapePaymentProviderNode, { node: resolvedNode, active, lang });
33906
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapePaymentProviderNode, { node: resolvedNode, active, lang, textMetrics });
33428
33907
  case "shape-credit-card":
33429
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeCreditCardNode, { node: resolvedNode, active });
33908
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeCreditCardNode, { node: resolvedNode, active, textMetrics });
33430
33909
  case "shape-brokerage":
33431
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeBrokerageNode, { node: resolvedNode, active, lang });
33910
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeBrokerageNode, { node: resolvedNode, active, lang, textMetrics });
33432
33911
  case "shape-exchange":
33433
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeExchangeNode, { node: resolvedNode, active, lang });
33912
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeExchangeNode, { node: resolvedNode, active, lang, textMetrics });
33434
33913
  case "shape-atm":
33435
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeAtmNode, { node: resolvedNode, active, lang });
33914
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeAtmNode, { node: resolvedNode, active, lang, textMetrics });
33436
33915
  case "shape-website":
33437
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeWebsiteNode, { node: resolvedNode, active });
33916
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeWebsiteNode, { node: resolvedNode, active, textMetrics });
33438
33917
  case "shape-storefront":
33439
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeStorefrontNode, { node: resolvedNode, active, lang });
33918
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeStorefrontNode, { node: resolvedNode, active, lang, textMetrics });
33440
33919
  case "shape-warehouse":
33441
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeWarehouseNode, { node: resolvedNode, active, lang });
33920
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeWarehouseNode, { node: resolvedNode, active, lang, textMetrics });
33442
33921
  case "shape-online-shop":
33443
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeOnlineShopNode, { node: resolvedNode, active });
33922
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeOnlineShopNode, { node: resolvedNode, active, textMetrics });
33444
33923
  case "shape-cdn-edge":
33445
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeCdnEdgeNode, { node: resolvedNode, active });
33924
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeCdnEdgeNode, { node: resolvedNode, active, textMetrics });
33446
33925
  case "shape-api-gateway":
33447
- return /* @__PURE__ */ jsxRuntime.jsx(ShapeApiGatewayNode, { node: resolvedNode, active, lang });
33926
+ return /* @__PURE__ */ jsxRuntime.jsx(ShapeApiGatewayNode, { node: resolvedNode, active, lang, textMetrics });
33448
33927
  case "shape-auditor":
33449
33928
  return /* @__PURE__ */ jsxRuntime.jsx(ShapeAuditorNode, { node: resolvedNode, active });
33450
33929
  case "shape-regulator":
@@ -33464,7 +33943,17 @@ function CdlNodeView({
33464
33943
  case "station":
33465
33944
  return /* @__PURE__ */ jsxRuntime.jsx(StationNode, { node: resolvedNode, active });
33466
33945
  default:
33467
- return /* @__PURE__ */ jsxRuntime.jsx(GenericNode, { node: resolvedNode, active, value: node.value, stateValues, \u5024\u306E\u540D\u524D });
33946
+ return /* @__PURE__ */ jsxRuntime.jsx(
33947
+ GenericNode,
33948
+ {
33949
+ node: resolvedNode,
33950
+ active,
33951
+ value: node.value,
33952
+ stateValues,
33953
+ \u5024\u306E\u540D\u524D,
33954
+ textMetrics
33955
+ }
33956
+ );
33468
33957
  }
33469
33958
  })();
33470
33959
  const offsetX = node.renderOffsetX !== void 0 ? resolveNumericAttr(node.renderOffsetX, stateValues, 0) : 0;
@@ -33525,7 +34014,7 @@ function CdlNodeView({
33525
34014
  }
33526
34015
  ),
33527
34016
  inner,
33528
- \u7BB1\u306E\u4E0A\u306E\u8A9E(resolvedNode)
34017
+ \u7BB1\u306E\u4E0A\u306E\u8A9E(resolvedNode, textMetrics ?? "proportional")
33529
34018
  ]
33530
34019
  }
33531
34020
  );
@@ -33534,17 +34023,17 @@ var FIGURE_TITLE_GAP = 10;
33534
34023
  var FIGURE_TITLE_SIZE = 15;
33535
34024
  var FIGURE_EYEBROW_SIZE = 11;
33536
34025
  var FIGURE_EYEBROW_LIFT = 1.1;
33537
- function \u5E45\u306B\u53CE\u3081\u305F\u5927\u304D\u3055(\u8A9E, \u7D20\u306E\u5927\u304D\u3055, \u5E45) {
33538
- const \u5B9F\u5E45 = textWidth(\u8A9E, \u7D20\u306E\u5927\u304D\u3055, 0);
34026
+ function \u5E45\u306B\u53CE\u3081\u305F\u5927\u304D\u3055(\u8A9E, \u7D20\u306E\u5927\u304D\u3055, \u5E45, textMetrics = "proportional") {
34027
+ const \u5B9F\u5E45 = textWidth(\u8A9E, \u7D20\u306E\u5927\u304D\u3055, 0, textMetrics);
33539
34028
  return \u5B9F\u5E45 > \u5E45 ? \u7D20\u306E\u5927\u304D\u3055 * \u5E45 / \u5B9F\u5E45 : \u7D20\u306E\u5927\u304D\u3055;
33540
34029
  }
33541
- function \u7BB1\u306E\u4E0A\u306E\u8A9E(node) {
34030
+ function \u7BB1\u306E\u4E0A\u306E\u8A9E(node, textMetrics = "proportional") {
33542
34031
  if (!drawsFigureTitle(node.kind)) return null;
33543
34032
  const \u540D\u524D = (node.title ?? "").trim();
33544
34033
  const \u5C0F\u898B\u51FA\u3057 = (node.eyebrow ?? "").trim();
33545
34034
  if (\u540D\u524D === "" && \u5C0F\u898B\u51FA\u3057 === "") return null;
33546
34035
  const \u984C\u306Ey = node.cy - node.h / 2 - FIGURE_TITLE_GAP;
33547
- const \u984C\u306E\u5927\u304D\u3055 = \u5E45\u306B\u53CE\u3081\u305F\u5927\u304D\u3055(\u540D\u524D, FIGURE_TITLE_SIZE, node.w);
34036
+ const \u984C\u306E\u5927\u304D\u3055 = \u5E45\u306B\u53CE\u3081\u305F\u5927\u304D\u3055(\u540D\u524D, FIGURE_TITLE_SIZE, node.w, textMetrics);
33548
34037
  const \u5C0F\u898B\u51FA\u3057\u306Ey = \u540D\u524D === "" ? \u984C\u306Ey : \u984C\u306Ey - \u984C\u306E\u5927\u304D\u3055 * FIGURE_EYEBROW_LIFT;
33549
34038
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
33550
34039
  \u5C0F\u898B\u51FA\u3057 !== "" && /* @__PURE__ */ jsxRuntime.jsx(
@@ -33554,7 +34043,7 @@ function \u7BB1\u306E\u4E0A\u306E\u8A9E(node) {
33554
34043
  x: node.cx,
33555
34044
  y: \u5C0F\u898B\u51FA\u3057\u306Ey,
33556
34045
  textAnchor: "middle",
33557
- fontSize: \u5E45\u306B\u53CE\u3081\u305F\u5927\u304D\u3055(\u5C0F\u898B\u51FA\u3057, FIGURE_EYEBROW_SIZE, node.w),
34046
+ fontSize: \u5E45\u306B\u53CE\u3081\u305F\u5927\u304D\u3055(\u5C0F\u898B\u51FA\u3057, FIGURE_EYEBROW_SIZE, node.w, textMetrics),
33558
34047
  fontWeight: 600,
33559
34048
  letterSpacing: 0.6,
33560
34049
  fill: "var(--cdl-text-dim, #5a6270)",
@@ -33879,6 +34368,7 @@ function CdlStage({
33879
34368
  node,
33880
34369
  active: activeSet.has(node.id),
33881
34370
  lang: laid.lang,
34371
+ textMetrics: laid.textMetrics,
33882
34372
  \u95A2\u4FC2\u306E\u53D7\u3051\u53E3: \u7BB1\u306E\u53D7\u3051\u53E3,
33883
34373
  drawing: \u63CF\u304F,
33884
34374
  progress: \u63CF\u304F ? \u63CF\u304F\u9032\u307F : progress,
@@ -33895,7 +34385,8 @@ function CdlStage({
33895
34385
  CdlEdgeLabelView,
33896
34386
  {
33897
34387
  edge,
33898
- active: activeSet.has(edge.id)
34388
+ active: activeSet.has(edge.id),
34389
+ textMetrics: laid.textMetrics
33899
34390
  },
33900
34391
  `label-${edge.id}`
33901
34392
  )),
@@ -33905,7 +34396,8 @@ function CdlStage({
33905
34396
  {
33906
34397
  edge,
33907
34398
  active: activeSet.has(edge.id),
33908
- \u7AEF
34399
+ \u7AEF,
34400
+ textMetrics: laid.textMetrics
33909
34401
  },
33910
34402
  `${\u7AEF}-label-${edge.id}`
33911
34403
  ))
@@ -34350,8 +34842,8 @@ function pointToSegmentDistance2(px, py, seg) {
34350
34842
  }
34351
34843
 
34352
34844
  // src/layout/predict-bbox.ts
34353
- function predictLabelBBoxWorld(edge) {
34354
- return computeLabelBBoxWorld(edge);
34845
+ function predictLabelBBoxWorld(edge, textMetrics = "proportional") {
34846
+ return computeLabelBBoxWorld(edge, textMetrics);
34355
34847
  }
34356
34848
  function predictNodeBBoxWorld(n) {
34357
34849
  return {
@@ -34411,12 +34903,12 @@ function resolveStorageBoxW(width, presetName, optionName) {
34411
34903
  }
34412
34904
  return width;
34413
34905
  }
34414
- function fitRowsWidth(boxW, rows) {
34415
- return Math.max(boxW, requiredRowsWidth(rows ? [...rows] : void 0, "storage"));
34906
+ function fitRowsWidth(boxW, rows, textMetrics = "proportional") {
34907
+ return Math.max(boxW, requiredRowsWidth(rows ? [...rows] : void 0, "storage", textMetrics));
34416
34908
  }
34417
34909
  function swimlane(preset) {
34418
34910
  const w = preset.laneWidth ?? 400;
34419
- const b = diagram(preset.id, { topic: preset.topic, type: "swimlane" });
34911
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "swimlane" });
34420
34912
  const labelToId = /* @__PURE__ */ new Map();
34421
34913
  const idsInOrder = [];
34422
34914
  for (const label of preset.lanes) {
@@ -34436,7 +34928,7 @@ function swimlane(preset) {
34436
34928
  }
34437
34929
  function flow(preset) {
34438
34930
  const w = preset.laneWidth ?? 400;
34439
- const b = diagram(preset.id, { topic: preset.topic, type: "flow" });
34931
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "flow" });
34440
34932
  b.lane("flow", { width: w, ...preset.laneLabel ? { label: preset.laneLabel } : {} });
34441
34933
  const tone = preset.defaultTone ?? "accent";
34442
34934
  const style = preset.defaultStyle ?? "dotted-flow";
@@ -34497,7 +34989,7 @@ var SEQUENCE_MESSAGE_LOOK = {
34497
34989
  };
34498
34990
  function sequence(preset) {
34499
34991
  const tone = preset.defaultTone ?? "accent";
34500
- const b = diagram(preset.id, { topic: preset.topic, type: "sequence" });
34992
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "sequence" });
34501
34993
  const \u9762\u3005 = preset.actors.map(
34502
34994
  (a) => typeof a === "string" ? { name: a } : { name: a.name, ...a.subtitle ? { subtitle: a.subtitle } : {} }
34503
34995
  );
@@ -34523,7 +35015,7 @@ function sequence(preset) {
34523
35015
  return \u51FA\u756A.length > 0 ? { actor: i, from: \u51FA\u756A[0], to: \u51FA\u756A[\u51FA\u756A.length - 1] } : null;
34524
35016
  }).filter((x) => x !== null);
34525
35017
  const data = { actors: \u9762\u3005, messages: \u8A00\u3065\u3066, bands: \u5E2F };
34526
- const m = sequenceBoardMetrics(data);
35018
+ const m = sequenceBoardMetrics(data, resolveTextMetrics(preset.textMetrics));
34527
35019
  const laneId = "seq";
34528
35020
  b.lane(laneId, { width: m.w + LANE_PAD_MIN * 2 });
34529
35021
  b.node(preset.id, {
@@ -34552,7 +35044,7 @@ function topology(preset) {
34552
35044
  const groupW = preset.groupWidth ?? 460;
34553
35045
  const tone = preset.defaultTone ?? "accent";
34554
35046
  const style = preset.defaultStyle ?? "solid";
34555
- const b = diagram(preset.id, { topic: preset.topic, type: "topology" });
35047
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "topology" });
34556
35048
  const groupOrder = [];
34557
35049
  const groupStackCount = /* @__PURE__ */ new Map();
34558
35050
  const phaseActivate = [];
@@ -34621,7 +35113,12 @@ function er(preset) {
34621
35113
  const entityW = resolveStorageBoxW(preset.entityWidth, "er", "entityWidth");
34622
35114
  const tone = preset.defaultTone ?? "info";
34623
35115
  const \u7E1E\u3092\u6577\u304F = preset.rowStripe ?? true;
34624
- const b = diagram(preset.id, { topic: preset.topic, palette: preset.palette, type: "er" });
35116
+ const b = diagram(preset.id, {
35117
+ topic: preset.topic,
35118
+ palette: preset.palette,
35119
+ textMetrics: preset.textMetrics,
35120
+ type: "er"
35121
+ });
34625
35122
  const entities = [];
34626
35123
  const phaseActivate = [];
34627
35124
  let relIdx = 0;
@@ -34644,7 +35141,7 @@ function er(preset) {
34644
35141
  \u5024.forEach(\u8DB3\u3059);
34645
35142
  const \u8A2D\u8A08\u306E\u5F62 = \u884C.length > 0;
34646
35143
  const rows = \u8A2D\u8A08\u306E\u5F62 ? \u884C : e.rows ?? [];
34647
- const boxW = fitRowsWidth(entityW, rows);
35144
+ const boxW = fitRowsWidth(entityW, rows, resolveTextMetrics(preset.textMetrics));
34648
35145
  b.lane(laneId, { width: boxLaneW(boxW) });
34649
35146
  b.node(e.id, {
34650
35147
  lane: laneId,
@@ -34708,7 +35205,7 @@ function stateMachine(preset) {
34708
35205
  const stateW = resolveStateW(preset.stateWidth, "stateMachine");
34709
35206
  const tone = preset.defaultTone ?? "accent";
34710
35207
  const diagramType = "state";
34711
- const b = diagram(preset.id, { topic: preset.topic, type: diagramType });
35208
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: diagramType });
34712
35209
  const phaseActivate = [];
34713
35210
  const stateOrder = /* @__PURE__ */ new Map();
34714
35211
  const \u72B6\u614B = [];
@@ -34739,7 +35236,7 @@ function stateMachine(preset) {
34739
35236
  const \u884C = (s.actions ?? []).map((a) => a.note ? `${a.label}: ${a.note}` : a.label);
34740
35237
  const \u5370 = (s.actions ?? []).map((a) => FSM_ACTION_MARK[a.when]);
34741
35238
  const laneId = \u683C\u5B50 && s.col !== void 0 ? `col-${s.col}` : `lane-${s.id}`;
34742
- const boxW = \u8A2D\u8A08\u306E\u5F62 ? fitRowsWidth(stateW, \u884C) : stateW;
35239
+ const boxW = \u8A2D\u8A08\u306E\u5F62 ? fitRowsWidth(stateW, \u884C, resolveTextMetrics(preset.textMetrics)) : stateW;
34743
35240
  return { s, \u884C, \u5370, laneId, boxW, stack: \u683C\u5B50 ? s.row ?? 0 : 0 };
34744
35241
  });
34745
35242
  const \u7BC0\u70B9\u306E\u4E2D\u8EAB = \u7BC0\u70B9.map((m) => ({
@@ -34820,7 +35317,11 @@ function infrastructure(preset) {
34820
35317
  const laneW = preset.laneWidth ?? 380;
34821
35318
  const tone = preset.defaultTone ?? "accent";
34822
35319
  const style = preset.defaultStyle ?? "solid";
34823
- const b = diagram(preset.id, { topic: preset.topic, type: "infrastructure" });
35320
+ const b = diagram(preset.id, {
35321
+ topic: preset.topic,
35322
+ textMetrics: preset.textMetrics,
35323
+ type: "infrastructure"
35324
+ });
34824
35325
  const colLaneIds = /* @__PURE__ */ new Map();
34825
35326
  const phaseActivate = [];
34826
35327
  let connIdx = 0;
@@ -34901,7 +35402,12 @@ function classDiagram(preset) {
34901
35402
  const classW = resolveStorageBoxW(preset.classWidth, "classDiagram", "classWidth");
34902
35403
  const \u56F3\u306E\u65E2\u5B9A = preset.defaultTone;
34903
35404
  const \u7E1E\u3092\u6577\u304F = preset.rowStripe ?? true;
34904
- const b = diagram(preset.id, { topic: preset.topic, palette: preset.palette, type: "class" });
35405
+ const b = diagram(preset.id, {
35406
+ topic: preset.topic,
35407
+ palette: preset.palette,
35408
+ textMetrics: preset.textMetrics,
35409
+ type: "class"
35410
+ });
34905
35411
  const classes = [];
34906
35412
  const phaseActivate = [];
34907
35413
  const \u7BB1 = [];
@@ -34927,7 +35433,7 @@ function classDiagram(preset) {
34927
35433
  rows.push(stripAccess(m));
34928
35434
  rowMarks.push({ shape: "chevron", filled: isPublic(m) });
34929
35435
  }
34930
- const boxW = fitRowsWidth(classW, rows);
35436
+ const boxW = fitRowsWidth(classW, rows, resolveTextMetrics(preset.textMetrics));
34931
35437
  const laneId = c.col !== void 0 ? `col-${c.col}` : `lane-${c.id}`;
34932
35438
  return { c, rows, rowMarks, boxW, laneId, stack: c.col !== void 0 ? c.row ?? 0 : 0 };
34933
35439
  });
@@ -34990,7 +35496,7 @@ function classDiagram(preset) {
34990
35496
  }
34991
35497
  function tree(preset) {
34992
35498
  const canvasH = 480;
34993
- const b = diagram(preset.id, { topic: preset.topic, type: "tree" });
35499
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "tree" });
34994
35500
  const treeNodes = [];
34995
35501
  const api = {
34996
35502
  node(n) {
@@ -35029,7 +35535,7 @@ function tree(preset) {
35029
35535
  function userJourney(preset) {
35030
35536
  const canvasW = preset.stepWidth ? preset.stepWidth * 2 : 720;
35031
35537
  const canvasH = 480;
35032
- const b = diagram(preset.id, { topic: preset.topic, type: "journey" });
35538
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "journey" });
35033
35539
  const steps = [];
35034
35540
  const api = {
35035
35541
  step(s) {
@@ -35069,7 +35575,7 @@ function mindMap(preset) {
35069
35575
  const canvasW = preset.branchWidth ? preset.branchWidth * 2 : 720;
35070
35576
  const canvasH = 480;
35071
35577
  const diagramType = "mind";
35072
- const b = diagram(preset.id, { topic: preset.topic, type: diagramType });
35578
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: diagramType });
35073
35579
  const branches = [];
35074
35580
  const api = {
35075
35581
  branch(br) {
@@ -35113,7 +35619,7 @@ function mindMap(preset) {
35113
35619
  function funnel(preset) {
35114
35620
  const canvasW = toGridSize(preset.stageWidth ?? 560);
35115
35621
  const canvasH = 480;
35116
- const b = diagram(preset.id, { topic: preset.topic, type: "funnel" });
35622
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "funnel" });
35117
35623
  const stages = [];
35118
35624
  const api = {
35119
35625
  stage(s) {
@@ -35151,7 +35657,7 @@ function funnel(preset) {
35151
35657
  function quadrant(preset) {
35152
35658
  const canvasW = 640;
35153
35659
  const canvasH = 480;
35154
- const b = diagram(preset.id, { topic: preset.topic, type: "quadrant" });
35660
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "quadrant" });
35155
35661
  const items = [];
35156
35662
  const api = {
35157
35663
  item(it) {
@@ -35202,7 +35708,7 @@ function chart(preset) {
35202
35708
  const canvasH = toGridSize(
35203
35709
  preset.type === "pie" || preset.type === "gauge" || preset.type === "radial" || preset.type === "stat" || preset.type === "waffle" || preset.type === "stacked-bar" ? 320 : 360
35204
35710
  );
35205
- const b = diagram(preset.id, { topic: preset.topic, type: "chart" });
35711
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "chart" });
35206
35712
  const data = [];
35207
35713
  const kindMap = {
35208
35714
  line: "chart-line",
@@ -35252,7 +35758,7 @@ function gantt(preset) {
35252
35758
  const canvasW = preset.laneWidth ? preset.laneWidth * 2 : 720;
35253
35759
  const canvasH = 360;
35254
35760
  const tone = preset.defaultTone ?? "teal";
35255
- const b = diagram(preset.id, { topic: preset.topic, type: "gantt" });
35761
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "gantt" });
35256
35762
  const tasks = [];
35257
35763
  const api = {
35258
35764
  task(t) {
@@ -35320,7 +35826,7 @@ function flowchart(preset) {
35320
35826
  const laneW = preset.laneWidth ?? 380;
35321
35827
  const tone = preset.defaultTone ?? "accent";
35322
35828
  const \u7E26\u306B\u7A4D\u3080 = (preset.direction ?? "horizontal") === "vertical";
35323
- const b = diagram(preset.id, { topic: preset.topic, type: "flowchart" });
35829
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "flowchart" });
35324
35830
  const laneToId = /* @__PURE__ */ new Map();
35325
35831
  const laneStackCount = /* @__PURE__ */ new Map();
35326
35832
  if (\u7E26\u306B\u7A4D\u3080) {
@@ -35395,7 +35901,7 @@ var NET_KIND_LABEL = {
35395
35901
  function network(preset) {
35396
35902
  const laneW = preset.laneWidth ?? 320;
35397
35903
  const tone = preset.defaultTone ?? "info";
35398
- const b = diagram(preset.id, { topic: preset.topic, type: "network" });
35904
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: "network" });
35399
35905
  const colLaneIds = /* @__PURE__ */ new Map();
35400
35906
  const phaseActivate = [];
35401
35907
  let edgeIdx = 0;
@@ -35446,7 +35952,7 @@ function stateMachine2(preset) {
35446
35952
  const laneW = boxLaneW(stateW);
35447
35953
  const tone = preset.defaultTone ?? "accent";
35448
35954
  const diagramType = "state";
35449
- const b = diagram(preset.id, { topic: preset.topic, type: diagramType });
35955
+ const b = diagram(preset.id, { topic: preset.topic, textMetrics: preset.textMetrics, type: diagramType });
35450
35956
  const stateOrder = /* @__PURE__ */ new Map();
35451
35957
  const phaseActivate = [];
35452
35958
  let transIdx = 0;
@@ -35651,6 +36157,7 @@ exports.resolveLang = resolveLang;
35651
36157
  exports.resolveOverlapsWithChain = resolveOverlapsWithChain;
35652
36158
  exports.resolveTarget = resolveTarget;
35653
36159
  exports.resolveTargetAll = resolveTargetAll;
36160
+ exports.resolveTextMetrics = resolveTextMetrics;
35654
36161
  exports.segmentsIntersect = segmentsIntersect2;
35655
36162
  exports.sequence = sequence;
35656
36163
  exports.sequenceBoardMetrics = sequenceBoardMetrics;