@onjmin/dtm 0.1.11 → 0.1.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1209,6 +1209,9 @@ var ICONS = {
1209
1209
  settings: {
1210
1210
  d: "M10.325 4.317c.426-1.756 2.924-1.756 3.35 0a1.724 1.724 0 002.573 1.066c1.543-.94 3.31.826 2.37 2.37a1.724 1.724 0 001.065 2.572c1.756.426 1.756 2.924 0 3.35a1.724 1.724 0 00-1.066 2.573c.94 1.543-.826 3.31-2.37 2.37a1.724 1.724 0 00-2.572 1.065c-.426 1.756-2.924 1.756-3.35 0a1.724 1.724 0 00-2.573-1.066c-1.543.94-3.31-.826-2.37-2.37a1.724 1.724 0 00-1.065-2.572c-1.756-.426-1.756-2.924 0-3.35a1.724 1.724 0 001.066-2.573c-.94-1.543.826-3.31 2.37-2.37.996.608 2.296.07 2.572-1.065zM15 12a3 3 0 11-6 0 3 3 0 016 0z",
1211
1211
  stroke: true
1212
+ },
1213
+ info: {
1214
+ d: "M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm1 15h-2v-6h2v6zm0-8h-2V7h2v2z"
1212
1215
  }
1213
1216
  };
1214
1217
  var icon = (name, size = 20) => {
@@ -1325,13 +1328,23 @@ var buildUI = (target, options) => {
1325
1328
  </div>
1326
1329
  <div class="dtm-row dtm-hidden" data-dtm="midi-track-selection"></div>
1327
1330
  <div class="dtm-row">
1328
- <span class="dtm-label">MML</span>
1331
+ <div style="display: inline-flex; flex-direction: column; align-items: center; gap: 4px; justify-content: center; min-width: 48px;">
1332
+ <span class="dtm-label" style="line-height: 1;">MML</span>
1333
+ <button class="dtm-infobtn" data-dtm="mml-info" title="MML\u306E\u66F8\u304D\u65B9\u89E3\u8AAC">${icon("info", 12)}</button>
1334
+ </div>
1329
1335
  <textarea class="dtm-textarea dtm-grow" data-dtm="mml-input" placeholder="MML\u3092\u5165\u529B"></textarea>
1330
1336
  <button class="dtm-btn dtm-btn--primary" data-dtm="mml-load">\u8AAD\u8FBC</button>
1331
1337
  </div>
1338
+ </div>
1339
+ </details>
1340
+
1341
+ <details class="dtm-panel">
1342
+ <summary>\u30DE\u30AF\u30ED</summary>
1343
+ <div class="dtm-panel-body">
1332
1344
  <div class="dtm-row">
1333
1345
  <span class="dtm-label">\u5168\u4F53\u30B7\u30D5\u30C8</span>
1334
1346
  <select class="dtm-select" data-dtm="shift-select">
1347
+ <option value="-192">-1\u5C0F\u7BC0</option>
1335
1348
  <option value="-96">-2\u5206</option>
1336
1349
  <option value="-48">-4\u5206</option>
1337
1350
  <option value="-24">-8\u5206</option>
@@ -1340,15 +1353,10 @@ var buildUI = (target, options) => {
1340
1353
  <option value="24">+8\u5206</option>
1341
1354
  <option value="48">+4\u5206</option>
1342
1355
  <option value="96">+2\u5206</option>
1356
+ <option value="192">+1\u5C0F\u7BC0</option>
1343
1357
  </select>
1344
1358
  <button class="dtm-btn dtm-btn--primary" data-dtm="shift-apply">\u9069\u7528</button>
1345
1359
  </div>
1346
- </div>
1347
- </details>
1348
-
1349
- <details class="dtm-panel">
1350
- <summary>\u30DE\u30AF\u30ED</summary>
1351
- <div class="dtm-panel-body">
1352
1360
  <div class="dtm-row">
1353
1361
  <button class="dtm-btn dtm-btn--danger" data-dtm="macro-clear">\u5168\u6D88\u53BB</button>
1354
1362
  <button class="dtm-btn dtm-btn--accent" data-dtm="macro-random">\u30E9\u30F3\u30C0\u30E0\u914D\u7F6E</button>
@@ -1398,6 +1406,17 @@ var buildUI = (target, options) => {
1398
1406
  </div>
1399
1407
  </div>
1400
1408
  </details>
1409
+
1410
+ <!-- \u2550\u2550\u2550\u2550 \u89E3\u8AAC\u30E2\u30FC\u30C0\u30EB \u2550\u2550\u2550\u2550 -->
1411
+ <div class="dtm-modal-overlay" data-dtm="modal-overlay" hidden>
1412
+ <div class="dtm-win dtm-modal">
1413
+ <div class="dtm-modal-header">
1414
+ <span class="dtm-modal-title" data-dtm="modal-title"></span>
1415
+ <button class="dtm-modal-close" data-dtm="modal-close">&times;</button>
1416
+ </div>
1417
+ <div class="dtm-modal-body" data-dtm="modal-body"></div>
1418
+ </div>
1419
+ </div>
1401
1420
  </div>`;
1402
1421
  const root = q(target, '[data-dtm="root"]');
1403
1422
  const sel = (name) => q(root, `[data-dtm="${name}"]`);
@@ -1457,7 +1476,12 @@ var buildUI = (target, options) => {
1457
1476
  outputMini: sel("output-mini"),
1458
1477
  copyFullBtn: sel("copy-full"),
1459
1478
  copyMiniBtn: sel("copy-mini"),
1460
- overlay: sel("overlay")
1479
+ overlay: sel("overlay"),
1480
+ mmlInfoBtn: sel("mml-info"),
1481
+ modalOverlay: sel("modal-overlay"),
1482
+ modalTitle: sel("modal-title"),
1483
+ modalBody: sel("modal-body"),
1484
+ modalClose: sel("modal-close")
1461
1485
  };
1462
1486
  };
1463
1487
 
@@ -2877,7 +2901,7 @@ var analyzeMidiTracks = (midi) => {
2877
2901
  const validNotes = notes.filter((n) => n.end !== void 0);
2878
2902
  result.push({
2879
2903
  index: i,
2880
- name: `Ch${i}`,
2904
+ name: `Ch${i + 1}`,
2881
2905
  noteCount: validNotes.length,
2882
2906
  selected: validNotes.length > 0
2883
2907
  });
@@ -4860,6 +4884,128 @@ var DAW_CSS = `
4860
4884
  @keyframes dtm-blink { 0%,100%{opacity:1} 50%{opacity:0} }
4861
4885
  .dtm-blink { animation: dtm-blink 1s steps(1) infinite; }
4862
4886
 
4887
+ /* \u2500\u2500\u2500 \u30A4\u30F3\u30D5\u30A9\u30DC\u30BF\u30F3 \u2500\u2500\u2500 */
4888
+ .dtm-infobtn {
4889
+ display: inline-flex;
4890
+ align-items: center;
4891
+ justify-content: center;
4892
+ width: 20px;
4893
+ height: 20px;
4894
+ flex: 0 0 auto;
4895
+ border: 2px solid var(--dtm-border2);
4896
+ background: var(--dtm-surface);
4897
+ color: var(--dtm-muted);
4898
+ cursor: pointer;
4899
+ box-shadow: 1px 1px 0 var(--c-black);
4900
+ padding: 0;
4901
+ margin: 0;
4902
+ }
4903
+ .dtm-infobtn:hover {
4904
+ color: var(--dtm-primary);
4905
+ border-color: var(--dtm-primary);
4906
+ }
4907
+ .dtm-infobtn:active {
4908
+ transform: translate(1px, 1px);
4909
+ box-shadow: none;
4910
+ }
4911
+
4912
+ /* \u2500\u2500\u2500 \u89E3\u8AAC\u30E2\u30FC\u30C0\u30EB \u2500\u2500\u2500 */
4913
+ .dtm-modal-overlay {
4914
+ position: fixed;
4915
+ inset: 0;
4916
+ z-index: 10000;
4917
+ background: rgba(0, 0, 0, 0.7);
4918
+ display: flex;
4919
+ align-items: center;
4920
+ justify-content: center;
4921
+ padding: 16px;
4922
+ backdrop-filter: blur(2px);
4923
+ }
4924
+ .dtm-modal-overlay[hidden] {
4925
+ display: none !important;
4926
+ }
4927
+ .dtm-modal {
4928
+ max-width: 500px;
4929
+ width: 100%;
4930
+ max-height: 80vh;
4931
+ display: flex;
4932
+ flex-direction: column;
4933
+ background: var(--dtm-surface);
4934
+ border: 2px solid var(--c-black);
4935
+ box-shadow:
4936
+ inset 0 0 0 2px var(--c-black),
4937
+ 0 0 0 2px var(--dtm-primary),
4938
+ 4px 4px 0 var(--c-black);
4939
+ overflow: hidden;
4940
+ }
4941
+ .dtm-modal-header {
4942
+ display: flex;
4943
+ align-items: center;
4944
+ justify-content: space-between;
4945
+ background: var(--dtm-deep);
4946
+ padding: 8px 12px;
4947
+ border-bottom: 2px solid var(--c-black);
4948
+ }
4949
+ .dtm-modal-title {
4950
+ font-family: var(--dtm-font);
4951
+ font-size: 14px;
4952
+ color: var(--dtm-gold);
4953
+ font-weight: bold;
4954
+ }
4955
+ .dtm-modal-close {
4956
+ background: transparent;
4957
+ border: none;
4958
+ color: var(--dtm-text);
4959
+ font-size: 20px;
4960
+ cursor: pointer;
4961
+ padding: 0;
4962
+ line-height: 1;
4963
+ }
4964
+ .dtm-modal-close:hover {
4965
+ color: var(--dtm-danger);
4966
+ }
4967
+ .dtm-modal-body {
4968
+ padding: 12px;
4969
+ overflow-y: auto;
4970
+ font-size: 13px;
4971
+ line-height: 1.6;
4972
+ }
4973
+ .dtm-modal-body h4 {
4974
+ margin: 12px 0 6px 0;
4975
+ color: var(--dtm-primary);
4976
+ font-size: 13px;
4977
+ }
4978
+ .dtm-modal-body h4:first-child {
4979
+ margin-top: 0;
4980
+ }
4981
+ .dtm-modal-body p {
4982
+ margin: 0 0 8px 0;
4983
+ }
4984
+ .dtm-modal-body ul {
4985
+ margin: 0 0 8px 0;
4986
+ padding-left: 16px;
4987
+ }
4988
+ .dtm-modal-body li {
4989
+ margin-bottom: 4px;
4990
+ }
4991
+ .dtm-modal-body code {
4992
+ background: var(--dtm-deep);
4993
+ color: var(--dtm-accent);
4994
+ padding: 1px 4px;
4995
+ font-family: var(--dtm-font);
4996
+ font-size: 12px;
4997
+ }
4998
+ .dtm-modal-body pre {
4999
+ background: var(--dtm-deep);
5000
+ color: var(--dtm-success);
5001
+ padding: 8px;
5002
+ border: 1px solid var(--dtm-border2);
5003
+ margin: 6px 0;
5004
+ overflow-x: auto;
5005
+ font-family: var(--dtm-font);
5006
+ font-size: 12px;
5007
+ }
5008
+
4863
5009
  .dtm-hidden { display: none !important; }
4864
5010
  .dtm-grow { flex: 1 1 auto; }
4865
5011
  .dtm-lyric-icon {
@@ -5129,6 +5275,85 @@ var VOICE_IMAGES = {
5129
5275
  };
5130
5276
 
5131
5277
  // src/daw.ts
5278
+ var CHORD_INFO_HTML = `
5279
+ <div class="dtm-modal-body-content">
5280
+ <h4>1. \u57FA\u672C\u306E\u66F8\u304D\u65B9</h4>
5281
+ <p>\u30B3\u30FC\u30C9\u540D\uFF08\u548C\u97F3\u8A18\u53F7\uFF09\u3092\u7E26\u7DDA <code>|</code>\u3001\u30B9\u30DA\u30FC\u30B9\u3001\u307E\u305F\u306F\u30AB\u30F3\u30DE\u3067\u533A\u5207\u3063\u3066\u5165\u529B\u3057\u307E\u3059\u3002\u7E26\u7DDA\u3067\u533A\u5207\u308B\u30681\u5C0F\u7BC0\u3054\u3068\u306E\u914D\u7F6E\u306B\u306A\u308A\u307E\u3059\u3002</p>
5282
+ <pre>\u4F8B: C | G | Am | F</pre>
5283
+
5284
+ <h4>2. 1\u5C0F\u7BC0\u306B\u8907\u6570\u30B3\u30FC\u30C9\u3092\u5165\u308C\u308B</h4>
5285
+ <p>\u5C0F\u7BC0\u306E\u533A\u5207\u308A\uFF08\u7E26\u7DDA <code>|</code>\uFF09\u306E\u4E2D\u306B\u3001\u30B9\u30DA\u30FC\u30B9\u533A\u5207\u308A\u3067\u30B3\u30FC\u30C9\u3092\u4E26\u3079\u307E\u3059\u3002\u7B49\u9593\u9694\u306B\u914D\u7F6E\u3055\u308C\u307E\u3059\u3002</p>
5286
+ <pre>\u4F8B: C G | Am F</pre>
5287
+ <p style="margin-top:4px;"><small>\uFF081\u5C0F\u7BC0\u76EE\uFF1A\u524D\u534AC\u30FB\u5F8C\u534AG\u30012\u5C0F\u7BC0\u76EE\uFF1A\u524D\u534AAm\u30FB\u5F8C\u534AF\uFF09</small></p>
5288
+
5289
+ <h4>3. \u5BFE\u5FDC\u30B3\u30FC\u30C9\u540D</h4>
5290
+ <ul>
5291
+ <li>\u30E1\u30B8\u30E3\u30FC / \u30DE\u30A4\u30CA\u30FC: <code>C</code>, <code>Dm</code>, <code>Am</code> \u306A\u3069</li>
5292
+ <li>\u30BB\u30D6\u30F3\u30B9: <code>C7</code>, <code>Am7</code>, <code>FM7</code> \u306A\u3069</li>
5293
+ <li>\u305D\u306E\u4ED6: <code>Csus4</code>, <code>Cdim</code>, <code>Caug</code>, <code>Cadd9</code> \u306A\u3069</li>
5294
+ </ul>
5295
+
5296
+ <h4>4. \u6F14\u594F\u30D1\u30BF\u30FC\u30F3</h4>
5297
+ <ul>
5298
+ <li><strong>\u30D6\u30ED\u30C3\u30AF</strong>: \u548C\u97F3\u306E\u69CB\u6210\u97F3\u3092\u3059\u3079\u3066\u540C\u6642\u306B\u4F38\u3070\u3057\u3066\u6F14\u594F\u3057\u307E\u3059\u3002</li>
5299
+ <li><strong>\u30A2\u30EB\u30DA\u30B8\u30AA</strong>: \u548C\u97F3\u306E\u69CB\u6210\u97F3\u3092\u4F4E\u3044\u9806\u306B\u5206\u6563\u3057\u3066\u6F14\u594F\u3057\u307E\u3059\u3002</li>
5300
+ <li><strong>\u30A2\u30EB\u30DA\u30B8\u30AA\uFF08\u30B8\u30E3\u30E9\u30FC\u30F3\uFF09</strong>: \u7D20\u65E9\u304F\u30A2\u30EB\u30DA\u30B8\u30AA\u3092\u9CF4\u3089\u3057\u307E\u3059\u3002</li>
5301
+ <li><strong>\u88CF\u6253\u3061</strong>: \u5404\u62CD\u306E\u88CF\uFF088\u5206\u88CF\uFF09\u306E\u30BF\u30A4\u30DF\u30F3\u30B0\u3067\u30B3\u30FC\u30C9\u3092\u523B\u307F\u307E\u3059\u3002</li>
5302
+ <li><strong>\u30E4\u30C4\u30E1\u7A74</strong>: \u30EA\u30BA\u30DF\u30AB\u30EB\u306A\u30D4\u30B3\u30D4\u30B3\u30B2\u30FC\u30E0\u98A8\u306E\u4F34\u594F\u30D1\u30BF\u30FC\u30F3\u3067\u3059\u3002</li>
5303
+ <li><strong>\u4EA4\u4E92\u594F</strong>: \u30EB\u30FC\u30C8\u97F3\uFF08\u4F4E\u97F3\uFF09\u3068\u30B3\u30FC\u30C9\u69CB\u6210\u97F3\uFF08\u9AD8\u97F3\uFF09\u3092\u4EA4\u4E92\u306B\u523B\u307F\u307E\u3059\u3002</li>
5304
+ </ul>
5305
+ </div>
5306
+ `;
5307
+ var MML_INFO_HTML = `
5308
+ <div class="dtm-modal-body-content">
5309
+ <h4>1. \u97F3\u7B26\u3068\u4F11\u7B26</h4>
5310
+ <p><code>c</code>(\u30C9) <code>d</code>(\u30EC) <code>e</code>(\u30DF) <code>f</code>(\u30D5\u30A1) <code>g</code>(\u30BD) <code>a</code>(\u30E9) <code>b</code>(\u30B7) \u306E\u30A2\u30EB\u30D5\u30A1\u30D9\u30C3\u30C8\u3067\u8868\u3057\u307E\u3059\u3002</p>
5311
+ <ul>
5312
+ <li>\u534A\u97F3\u4E0A\u3052\u308B: <code>c#</code> \u307E\u305F\u306F <code>c+</code></li>
5313
+ <li>\u534A\u97F3\u4E0B\u3052\u308B: <code>d-</code></li>
5314
+ <li>\u4F11\u7B26: <code>r</code></li>
5315
+ </ul>
5316
+
5317
+ <h4>2. \u97F3\u306E\u9577\u3055</h4>
5318
+ <p>\u97F3\u540D\u3084\u4F11\u7B26\u306E\u5F8C\u306B\u6570\u5024\u3067\u6307\u5B9A\u3057\u307E\u3059\uFF08\u4F8B: <code>4</code> = 4\u5206\u97F3\u7B26, <code>8</code> = 8\u5206\u97F3\u7B26, <code>16</code> = 16\u5206\u97F3\u7B26\uFF09\u3002</p>
5319
+ <ul>
5320
+ <li><code>c4</code> : 4\u5206\u97F3\u7B26\u306E\u30C9</li>
5321
+ <li><code>r8</code> : 8\u5206\u4F11\u7B26</li>
5322
+ <li><code>c4.</code> : \u4ED8\u70B94\u5206\u97F3\u7B26\u306E\u30C9\uFF08\u9577\u3055\u30921.5\u500D\u306B\uFF09</li>
5323
+ <li>\u6570\u5024\u3092\u7701\u7565\u3059\u308B\u3068\u3001<code>l</code> \u30B3\u30DE\u30F3\u30C9\u3067\u8A2D\u5B9A\u3055\u308C\u305F\u30C7\u30D5\u30A9\u30EB\u30C8\u9577\uFF08\u901A\u5E3816\u5206\uFF09\u306B\u306A\u308A\u307E\u3059\u3002</li>
5324
+ </ul>
5325
+
5326
+ <h4>3. \u30AA\u30AF\u30BF\u30FC\u30D6\uFF08\u97F3\u306E\u9AD8\u3055\uFF09</h4>
5327
+ <ul>
5328
+ <li><code>o4</code>, <code>o5</code> : \u9AD8\u3055\u3092\u76F4\u63A5\u6307\u5B9A\uFF08\u3075\u3064\u3046\u306F o4 \u304B o5\uFF09</li>
5329
+ <li><code>&gt;</code> : 1\u30AA\u30AF\u30BF\u30FC\u30D6\u4E0A\u3052\u308B</li>
5330
+ <li><code>&lt;</code> : 1\u30AA\u30AF\u30BF\u30FC\u30D6\u4E0B\u3052\u308B</li>
5331
+ </ul>
5332
+
5333
+ <h4>4. \u30C6\u30F3\u30DD</h4>
5334
+ <ul>
5335
+ <li><code>t120</code> : \u66F2\u306E\u901F\u3055\u3092BPM120\u306B\u6307\u5B9A\u3002\u203B\u30E1\u30ED\u30C7\u30A3\uFF08@0\uFF09\u306E\u30C6\u30F3\u30DD\u6307\u5B9A\u304C\u66F2\u5168\u4F53\u306B\u53CD\u6620\u3055\u308C\u307E\u3059\u3002</li>
5336
+ </ul>
5337
+
5338
+ <h4>5. \u548C\u97F3</h4>
5339
+ <p>\u97F3\u7B26\u3092 <code>[</code> \u3068 <code>]</code> \u3067\u56F2\u3080\u3068\u540C\u6642\u306B\u767A\u97F3\u3057\u307E\u3059\u3002</p>
5340
+ <pre>\u4F8B: [ceg]4 \uFF08\u30C9\u30FB\u30DF\u30FB\u30BD\u30924\u5206\u97F3\u7B26\u3067\u540C\u6642\u306B\u767A\u97F3\uFF09</pre>
5341
+
5342
+ <h4>6. \u30C8\u30E9\u30C3\u30AF\u306E\u533A\u5207\u308A</h4>
5343
+ <p><code>;</code> \u307E\u305F\u306F <code>@0</code>\u301C<code>@3</code> \u3067\u30C8\u30E9\u30C3\u30AF\u3092\u5207\u308A\u66FF\u3048\u307E\u3059\u3002</p>
5344
+ <ul>
5345
+ <li><code>@0</code>: \u30E1\u30ED\u30C7\u30A3</li>
5346
+ <li><code>@1</code>: \u30B5\u30D6\u30E1\u30ED</li>
5347
+ <li><code>@2</code>: \u30D9\u30FC\u30B9</li>
5348
+ <li><code>@3</code>: \u4F34\u594F</li>
5349
+ </ul>
5350
+
5351
+ <h4>7. \u6B4C\u58F0\u30FB\u6B4C\u8A5E\u5165\u529B</h4>
5352
+ <p><code>@@&lt;\u30C8\u30E9\u30C3\u30AF\u756A\u53F7&gt; &lt;\u97F3\u6E90\u540D&gt; &lt;\u6B4C\u8A5E&gt;</code> \u306E\u5F62\u5F0F\u3067\u3001\u97F3\u7B26\u3068\u540C\u671F\u3059\u308B\u6B4C\u8A5E\u3092\u5165\u529B\u3067\u304D\u307E\u3059\u3002</p>
5353
+ <pre>\u4F8B: @@0 klatt \u3061\u3087\u3046\u3061\u3087\u3046\u306A\u306E\u306F\u306B\u3068\u307E\u308C</pre>
5354
+ <p style="margin-top:4px;"><small>\uFF08\u97F3\u6E90\u540D\u306F <code>klatt</code> \u3084 <code>roze</code>, <code>teto</code> \u306A\u3069\u306E\u97F3\u58F0\u30E2\u30C7\u30EB\u3092\u6307\u5B9A\u3067\u304D\u307E\u3059\uFF09</small></p>
5355
+ </div>
5356
+ `;
5132
5357
  var BASE_STEP_WIDTH = 0.5;
5133
5358
  var BASE_KEY_HEIGHT = 15;
5134
5359
  var TRACKS_SIMPLE = [
@@ -5381,6 +5606,7 @@ var mountDAW = (target, options = {}) => {
5381
5606
  return map;
5382
5607
  };
5383
5608
  const getActive = () => trackStates.find((t) => t.config.id === activeTrackId) ?? trackStates[0];
5609
+ let showModal;
5384
5610
  const getMaxNoteStep = () => {
5385
5611
  let maxStep = renderConfig.stepsPerBar * 4;
5386
5612
  for (const t of trackStates) {
@@ -6073,11 +6299,13 @@ var mountDAW = (target, options = {}) => {
6073
6299
  active.core.setVolume(active.volume);
6074
6300
  volLabel.textContent = String(active.volume);
6075
6301
  });
6076
- const lyricDiv = document.createElement("div");
6077
- lyricDiv.className = "dtm-row";
6078
- lyricDiv.style.flexDirection = "column";
6079
- lyricDiv.style.alignItems = "stretch";
6080
- lyricDiv.innerHTML = `
6302
+ const isAdvanced = trackStates.length > TRACKS_SIMPLE.length;
6303
+ if (isAdvanced || active.config.id !== "chord") {
6304
+ const lyricDiv = document.createElement("div");
6305
+ lyricDiv.className = "dtm-row";
6306
+ lyricDiv.style.flexDirection = "column";
6307
+ lyricDiv.style.alignItems = "stretch";
6308
+ lyricDiv.innerHTML = `
6081
6309
  <div class="dtm-row">
6082
6310
  <span class="dtm-label">\u266A \u6B4C\u8A5E</span>
6083
6311
  <select class="dtm-select" data-dtm="lyric-model" aria-label="\u6B4C\u5531\u30E2\u30C7\u30EB"></select>
@@ -6109,144 +6337,134 @@ var mountDAW = (target, options = {}) => {
6109
6337
  </div>
6110
6338
  <textarea class="dtm-textarea" data-dtm="lyric-input" rows="2" placeholder="\u3072\u3089\u304C\u306A\u30FB\u30AB\u30BF\u30AB\u30CA\u3067\u6B4C\u8A5E\uFF08\u4F8B: \u3069\u308C\u307F\u3075\u3041\u305D\u3089\u3057\u3069\uFF09"></textarea>
6111
6339
  </div>`;
6112
- refs.trackBody.appendChild(lyricDiv);
6113
- const lyricModelSel = lyricDiv.querySelector(
6114
- '[data-dtm="lyric-model"]'
6115
- );
6116
- const lyricOctaveSel = lyricDiv.querySelector(
6117
- '[data-dtm="lyric-octave"]'
6118
- );
6119
- const lyricIcon = lyricDiv.querySelector(
6120
- '[data-dtm="lyric-icon"]'
6121
- );
6122
- const lyricBody = lyricDiv.querySelector(
6123
- '[data-dtm="lyric-body"]'
6124
- );
6125
- const lyricInput = lyricDiv.querySelector(
6126
- '[data-dtm="lyric-input"]'
6127
- );
6128
- const lyricCount = lyricDiv.querySelector(
6129
- '[data-dtm="lyric-count"]'
6130
- );
6131
- const lyricVol = lyricDiv.querySelector(
6132
- '[data-dtm="lyric-vol"]'
6133
- );
6134
- const lyricVolLabel = lyricDiv.querySelector(
6135
- '[data-dtm="lyric-vol-label"]'
6136
- );
6137
- const lyricPan = lyricDiv.querySelector(
6138
- '[data-dtm="lyric-pan"]'
6139
- );
6140
- const lyricPanLabel = lyricDiv.querySelector(
6141
- '[data-dtm="lyric-pan-label"]'
6142
- );
6143
- const lyricTerms = lyricDiv.querySelector(
6144
- '[data-dtm="lyric-terms"]'
6145
- );
6146
- const lyricTermsLink = lyricDiv.querySelector(
6147
- '[data-dtm="lyric-terms-link"]'
6148
- );
6149
- const fmtPan = (pan) => pan === 64 ? "C" : pan < 64 ? `L${64 - pan}` : `R${pan - 64}`;
6150
- const addOpt = (value, label) => {
6151
- const o = document.createElement("option");
6152
- o.value = value;
6153
- o.textContent = label;
6154
- lyricModelSel.appendChild(o);
6155
- };
6156
- addOpt("", "\u306A\u3057");
6157
- for (const m of LYRIC_MODELS) addOpt(m, lyricModelLabel(m));
6158
- if (active.lyricModel && !LYRIC_MODELS.includes(active.lyricModel)) {
6159
- addOpt(active.lyricModel, lyricModelLabel(active.lyricModel));
6160
- }
6161
- lyricModelSel.value = active.lyricModel;
6162
- lyricOctaveSel.value = String(active.vocalOctave);
6163
- lyricInput.value = active.lyrics;
6164
- lyricVol.value = String(active.vocalVolume);
6165
- lyricVolLabel.textContent = String(active.vocalVolume);
6166
- lyricPan.value = String(active.vocalPan);
6167
- lyricPanLabel.textContent = fmtPan(active.vocalPan);
6168
- const updateLyricCount = () => {
6169
- const n = normalizeLyrics(lyricInput.value).length;
6170
- lyricCount.textContent = active.lyricModel && n > 0 ? `${n}\u97F3\u7BC0` : "";
6171
- };
6172
- const syncLyricTerms = () => {
6173
- const url = active.lyricModel ? KOE_VOICEBANK_TERMS[active.lyricModel] : void 0;
6174
- if (url) {
6175
- const label = lyricModelLabel(active.lyricModel);
6176
- lyricTermsLink.textContent = `${label}UTAU\u97F3\u6E90`;
6177
- lyricTermsLink.href = url;
6178
- lyricTerms.classList.remove("dtm-hidden");
6179
- } else {
6180
- lyricTerms.classList.add("dtm-hidden");
6181
- }
6182
- };
6183
- const syncLyricIcon = () => {
6184
- const imgKey = active.lyricModel ? VOICE_IMAGE_KEY[active.lyricModel.toLowerCase()] : void 0;
6185
- const src = imgKey ? VOICE_IMAGES[imgKey] : void 0;
6186
- if (src) {
6187
- lyricIcon.src = src;
6188
- lyricIcon.classList.remove("dtm-hidden");
6189
- } else {
6190
- lyricIcon.removeAttribute("src");
6191
- lyricIcon.classList.add("dtm-hidden");
6340
+ refs.trackBody.appendChild(lyricDiv);
6341
+ const lyricModelSel = lyricDiv.querySelector(
6342
+ '[data-dtm="lyric-model"]'
6343
+ );
6344
+ const lyricOctaveSel = lyricDiv.querySelector(
6345
+ '[data-dtm="lyric-octave"]'
6346
+ );
6347
+ const lyricIcon = lyricDiv.querySelector(
6348
+ '[data-dtm="lyric-icon"]'
6349
+ );
6350
+ const lyricBody = lyricDiv.querySelector(
6351
+ '[data-dtm="lyric-body"]'
6352
+ );
6353
+ const lyricInput = lyricDiv.querySelector(
6354
+ '[data-dtm="lyric-input"]'
6355
+ );
6356
+ const lyricCount = lyricDiv.querySelector(
6357
+ '[data-dtm="lyric-count"]'
6358
+ );
6359
+ const lyricVol = lyricDiv.querySelector(
6360
+ '[data-dtm="lyric-vol"]'
6361
+ );
6362
+ const lyricVolLabel = lyricDiv.querySelector(
6363
+ '[data-dtm="lyric-vol-label"]'
6364
+ );
6365
+ const lyricPan = lyricDiv.querySelector(
6366
+ '[data-dtm="lyric-pan"]'
6367
+ );
6368
+ const lyricPanLabel = lyricDiv.querySelector(
6369
+ '[data-dtm="lyric-pan-label"]'
6370
+ );
6371
+ const lyricTerms = lyricDiv.querySelector(
6372
+ '[data-dtm="lyric-terms"]'
6373
+ );
6374
+ const lyricTermsLink = lyricDiv.querySelector(
6375
+ '[data-dtm="lyric-terms-link"]'
6376
+ );
6377
+ const fmtPan = (pan) => pan === 64 ? "C" : pan < 64 ? `L${64 - pan}` : `R${pan - 64}`;
6378
+ const addOpt = (value, label) => {
6379
+ const o = document.createElement("option");
6380
+ o.value = value;
6381
+ o.textContent = label;
6382
+ lyricModelSel.appendChild(o);
6383
+ };
6384
+ addOpt("", "\u306A\u3057");
6385
+ for (const m of LYRIC_MODELS) addOpt(m, lyricModelLabel(m));
6386
+ if (active.lyricModel && !LYRIC_MODELS.includes(active.lyricModel)) {
6387
+ addOpt(active.lyricModel, lyricModelLabel(active.lyricModel));
6192
6388
  }
6193
- };
6194
- const syncLyricVisibility = () => {
6195
- lyricBody.style.display = active.lyricModel ? "" : "none";
6196
- lyricOctaveSel.style.display = active.lyricModel ? "" : "none";
6197
- updateLyricCount();
6198
- syncLyricTerms();
6199
- syncLyricIcon();
6200
- };
6201
- syncLyricVisibility();
6202
- lyricModelSel.addEventListener("change", () => {
6203
- active.lyricModel = lyricModelSel.value;
6204
- syncLyricVisibility();
6205
- });
6206
- lyricOctaveSel.addEventListener("change", () => {
6207
- active.vocalOctave = Number.parseInt(lyricOctaveSel.value, 10);
6208
- });
6209
- lyricInput.addEventListener("input", () => {
6210
- active.lyrics = lyricInput.value;
6211
- updateLyricCount();
6212
- });
6213
- lyricVol.addEventListener("input", () => {
6214
- active.vocalVolume = Number.parseInt(lyricVol.value, 10);
6215
- lyricVolLabel.textContent = lyricVol.value;
6216
- });
6217
- lyricPan.addEventListener("input", () => {
6218
- active.vocalPan = Number.parseInt(lyricPan.value, 10);
6389
+ lyricModelSel.value = active.lyricModel;
6390
+ lyricOctaveSel.value = String(active.vocalOctave);
6391
+ lyricInput.value = active.lyrics;
6392
+ lyricVol.value = String(active.vocalVolume);
6393
+ lyricVolLabel.textContent = String(active.vocalVolume);
6394
+ lyricPan.value = String(active.vocalPan);
6219
6395
  lyricPanLabel.textContent = fmtPan(active.vocalPan);
6220
- });
6221
- lyricPanLabel.style.cursor = "pointer";
6222
- lyricPanLabel.title = "\u30BF\u30C3\u30D7\u3067\u4E2D\u592E(C)\u3078";
6223
- lyricPanLabel.addEventListener("click", () => {
6224
- active.vocalPan = 64;
6225
- lyricPan.value = "64";
6226
- lyricPanLabel.textContent = fmtPan(64);
6227
- });
6396
+ const updateLyricCount = () => {
6397
+ const n = normalizeLyrics(lyricInput.value).length;
6398
+ lyricCount.textContent = active.lyricModel && n > 0 ? `${n}\u97F3\u7BC0` : "";
6399
+ };
6400
+ const syncLyricTerms = () => {
6401
+ const url = active.lyricModel ? KOE_VOICEBANK_TERMS[active.lyricModel] : void 0;
6402
+ if (url) {
6403
+ const label = lyricModelLabel(active.lyricModel);
6404
+ lyricTermsLink.textContent = `${label}UTAU\u97F3\u6E90`;
6405
+ lyricTermsLink.href = url;
6406
+ lyricTerms.classList.remove("dtm-hidden");
6407
+ } else {
6408
+ lyricTerms.classList.add("dtm-hidden");
6409
+ }
6410
+ };
6411
+ const syncLyricIcon = () => {
6412
+ const imgKey = active.lyricModel ? VOICE_IMAGE_KEY[active.lyricModel.toLowerCase()] : void 0;
6413
+ const src = imgKey ? VOICE_IMAGES[imgKey] : void 0;
6414
+ if (src) {
6415
+ lyricIcon.src = src;
6416
+ lyricIcon.classList.remove("dtm-hidden");
6417
+ } else {
6418
+ lyricIcon.removeAttribute("src");
6419
+ lyricIcon.classList.add("dtm-hidden");
6420
+ }
6421
+ };
6422
+ const syncLyricVisibility = () => {
6423
+ lyricBody.style.display = active.lyricModel ? "" : "none";
6424
+ lyricOctaveSel.style.display = active.lyricModel ? "" : "none";
6425
+ updateLyricCount();
6426
+ syncLyricTerms();
6427
+ syncLyricIcon();
6428
+ };
6429
+ syncLyricVisibility();
6430
+ lyricModelSel.addEventListener("change", () => {
6431
+ active.lyricModel = lyricModelSel.value;
6432
+ syncLyricVisibility();
6433
+ });
6434
+ lyricOctaveSel.addEventListener("change", () => {
6435
+ active.vocalOctave = Number.parseInt(lyricOctaveSel.value, 10);
6436
+ });
6437
+ lyricInput.addEventListener("input", () => {
6438
+ active.lyrics = lyricInput.value;
6439
+ updateLyricCount();
6440
+ });
6441
+ lyricVol.addEventListener("input", () => {
6442
+ active.vocalVolume = Number.parseInt(lyricVol.value, 10);
6443
+ lyricVolLabel.textContent = lyricVol.value;
6444
+ });
6445
+ lyricPan.addEventListener("input", () => {
6446
+ active.vocalPan = Number.parseInt(lyricPan.value, 10);
6447
+ lyricPanLabel.textContent = fmtPan(active.vocalPan);
6448
+ });
6449
+ lyricPanLabel.style.cursor = "pointer";
6450
+ lyricPanLabel.title = "\u30BF\u30C3\u30D7\u3067\u4E2D\u592E(C)\u3078";
6451
+ lyricPanLabel.addEventListener("click", () => {
6452
+ active.vocalPan = 64;
6453
+ lyricPan.value = "64";
6454
+ lyricPanLabel.textContent = fmtPan(64);
6455
+ });
6456
+ }
6228
6457
  if (active.config.id === "chord" && showChord) {
6229
6458
  const div = document.createElement("div");
6230
6459
  div.className = "dtm-row";
6231
6460
  div.style.flexDirection = "column";
6232
6461
  div.style.alignItems = "stretch";
6233
- const roots = [
6234
- "C",
6235
- "C#",
6236
- "D",
6237
- "D#",
6238
- "E",
6239
- "F",
6240
- "F#",
6241
- "G",
6242
- "G#",
6243
- "A",
6244
- "A#",
6245
- "B"
6246
- ];
6247
6462
  div.innerHTML = `
6248
- <div class="dtm-row">
6249
- <span class="dtm-label">\u548C\u97F3</span>
6463
+ <div class="dtm-row" style="justify-content: space-between; align-items: center;">
6464
+ <div style="display: inline-flex; align-items: center; gap: 6px;">
6465
+ <span class="dtm-label">\u548C\u97F3</span>
6466
+ <button class="dtm-infobtn" data-dtm="chord-info" title="\u30B3\u30FC\u30C9\u9032\u884C\u306E\u66F8\u304D\u65B9\u89E3\u8AAC">${icon("info", 12)}</button>
6467
+ </div>
6250
6468
  <select class="dtm-select" data-dtm="chord-pattern">
6251
6469
  <option value="block">\u30D6\u30ED\u30C3\u30AF</option>
6252
6470
  <option value="arpeggio">\u30A2\u30EB\u30DA\u30B8\u30AA</option>
@@ -6255,32 +6473,28 @@ var mountDAW = (target, options = {}) => {
6255
6473
  <option value="yatsume">\u30E4\u30C4\u30E1\u7A74</option>
6256
6474
  <option value="alternating">\u4EA4\u4E92\u594F</option>
6257
6475
  </select>
6258
- <select class="dtm-select" data-dtm="chord-root">
6259
- ${roots.map((r, i) => `<option value="${i}">${r}</option>`).join("")}
6260
- </select>
6261
- <button class="dtm-btn dtm-btn--primary" data-dtm="chord-apply">\u9069\u7528</button>
6262
6476
  </div>
6263
- <textarea class="dtm-textarea" data-dtm="chord-input" placeholder="\u4F8B: C|G|Am|Em|F|C|F|G">${active.savedChordInput}</textarea>`;
6477
+ <div class="dtm-row">
6478
+ <textarea class="dtm-textarea dtm-grow" data-dtm="chord-input" placeholder="\u4F8B: C|G|Am|Em|F|C|F|G">${active.savedChordInput}</textarea>
6479
+ <button class="dtm-btn dtm-btn--primary" data-dtm="chord-apply">\u9069\u7528</button>
6480
+ </div>`;
6264
6481
  refs.trackBody.appendChild(div);
6265
6482
  const patternSel = div.querySelector(
6266
6483
  '[data-dtm="chord-pattern"]'
6267
6484
  );
6268
- const rootSel = div.querySelector(
6269
- '[data-dtm="chord-root"]'
6270
- );
6271
6485
  const input = div.querySelector(
6272
6486
  '[data-dtm="chord-input"]'
6273
6487
  );
6274
6488
  patternSel.value = active.savedChordPattern;
6275
- rootSel.value = String(active.savedChordRoot);
6276
6489
  const save = () => {
6277
6490
  active.savedChordInput = input.value;
6278
6491
  active.savedChordPattern = patternSel.value;
6279
- active.savedChordRoot = Number.parseInt(rootSel.value, 10);
6280
6492
  };
6281
6493
  patternSel.addEventListener("change", save);
6282
- rootSel.addEventListener("change", save);
6283
6494
  input.addEventListener("input", save);
6495
+ div.querySelector('[data-dtm="chord-info"]').addEventListener("click", () => {
6496
+ showModal("\u30B3\u30FC\u30C9\u9032\u884C\u306E\u81EA\u52D5\u5165\u529B\u89E3\u8AAC", CHORD_INFO_HTML);
6497
+ });
6284
6498
  div.querySelector('[data-dtm="chord-apply"]').addEventListener("click", () => {
6285
6499
  save();
6286
6500
  applyChord();
@@ -6718,6 +6932,22 @@ var mountDAW = (target, options = {}) => {
6718
6932
  "click",
6719
6933
  () => overlayDuring(() => loadMML(refs.mmlInput.value))
6720
6934
  );
6935
+ showModal = (title, bodyHTML) => {
6936
+ refs.modalTitle.textContent = title;
6937
+ refs.modalBody.innerHTML = bodyHTML;
6938
+ refs.modalOverlay.removeAttribute("hidden");
6939
+ };
6940
+ refs.modalClose.addEventListener("click", () => {
6941
+ refs.modalOverlay.setAttribute("hidden", "");
6942
+ });
6943
+ refs.modalOverlay.addEventListener("click", (e) => {
6944
+ if (e.target === refs.modalOverlay) {
6945
+ refs.modalOverlay.setAttribute("hidden", "");
6946
+ }
6947
+ });
6948
+ refs.mmlInfoBtn.addEventListener("click", () => {
6949
+ showModal("MML\u306E\u66F8\u304D\u65B9\u89E3\u8AAC", MML_INFO_HTML);
6950
+ });
6721
6951
  refs.shiftApplyBtn.addEventListener(
6722
6952
  "click",
6723
6953
  () => overlayDuring(() => {