@libraz/libcantus 1.3.0 → 1.4.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 (130) hide show
  1. package/NOTICE +63 -0
  2. package/README.md +3 -1
  3. package/README_ja.md +13 -11
  4. package/dist/analyze/index.cjs +7 -7
  5. package/dist/analyze/index.cjs.map +1 -1
  6. package/dist/analyze/index.d.cts +14 -12
  7. package/dist/analyze/index.d.ts +14 -12
  8. package/dist/analyze/index.js +6 -6
  9. package/dist/{chunk-NB25P3EH.js → chunk-2G5MCGYU.js} +33 -11
  10. package/dist/chunk-2G5MCGYU.js.map +1 -0
  11. package/dist/{chunk-NM7UAMC3.cjs → chunk-3FDBMIPR.cjs} +64 -64
  12. package/dist/chunk-3FDBMIPR.cjs.map +1 -0
  13. package/dist/{chunk-YFA7X2F6.cjs → chunk-3MDOEFIQ.cjs} +411 -327
  14. package/dist/chunk-3MDOEFIQ.cjs.map +1 -0
  15. package/dist/{chunk-IPEF6NWB.js → chunk-5MWRBYAT.js} +278 -154
  16. package/dist/chunk-5MWRBYAT.js.map +1 -0
  17. package/dist/{chunk-B2PW6EHN.cjs → chunk-6TTBEON3.cjs} +1253 -889
  18. package/dist/chunk-6TTBEON3.cjs.map +1 -0
  19. package/dist/{chunk-UMWZ4ZET.js → chunk-7NQ6AL3H.js} +4 -4
  20. package/dist/chunk-7NQ6AL3H.js.map +1 -0
  21. package/dist/{chunk-PWC4CRWT.cjs → chunk-E3QO3UET.cjs} +31 -23
  22. package/dist/chunk-E3QO3UET.cjs.map +1 -0
  23. package/dist/{chunk-GNVN4PPJ.js → chunk-FJFULJZE.js} +531 -213
  24. package/dist/chunk-FJFULJZE.js.map +1 -0
  25. package/dist/{chunk-CPMB7P75.js → chunk-FK3DGAIZ.js} +608 -244
  26. package/dist/chunk-FK3DGAIZ.js.map +1 -0
  27. package/dist/chunk-GEDTJHAC.cjs.map +1 -1
  28. package/dist/{chunk-RFIBF2RR.js → chunk-H7FVMBUC.js} +138 -65
  29. package/dist/chunk-H7FVMBUC.js.map +1 -0
  30. package/dist/{chunk-4R2LWV7E.cjs → chunk-HYSVSFNI.cjs} +664 -540
  31. package/dist/chunk-HYSVSFNI.cjs.map +1 -0
  32. package/dist/{chunk-35NBV2FT.cjs → chunk-KMYGRFZ6.cjs} +47 -24
  33. package/dist/chunk-KMYGRFZ6.cjs.map +1 -0
  34. package/dist/{chunk-IFZDWIKM.cjs → chunk-LQZQDBCD.cjs} +1048 -730
  35. package/dist/chunk-LQZQDBCD.cjs.map +1 -0
  36. package/dist/{chunk-PM4XJE2Y.cjs → chunk-P3CPXAJ5.cjs} +76 -54
  37. package/dist/chunk-P3CPXAJ5.cjs.map +1 -0
  38. package/dist/{chunk-S5BKZZGM.cjs → chunk-S3QELJUE.cjs} +72 -56
  39. package/dist/chunk-S3QELJUE.cjs.map +1 -0
  40. package/dist/{chunk-PUKJP2Z5.js → chunk-TXFWSU5D.js} +31 -8
  41. package/dist/chunk-TXFWSU5D.js.map +1 -0
  42. package/dist/{chunk-76ZBTRG2.cjs → chunk-U4EQTDGN.cjs} +258 -218
  43. package/dist/chunk-U4EQTDGN.cjs.map +1 -0
  44. package/dist/chunk-UGLFDG7L.cjs.map +1 -1
  45. package/dist/{chunk-MLBPXA4Z.js → chunk-UTE5A36R.js} +198 -114
  46. package/dist/chunk-UTE5A36R.js.map +1 -0
  47. package/dist/{chunk-ZBUROTJQ.js → chunk-UZKQISRF.js} +17 -9
  48. package/dist/chunk-UZKQISRF.js.map +1 -0
  49. package/dist/{chunk-7KG3RTYS.js → chunk-VL5NXVCN.js} +281 -155
  50. package/dist/chunk-VL5NXVCN.js.map +1 -0
  51. package/dist/{chunk-CGBADIO5.cjs → chunk-WOMCXN2W.cjs} +328 -202
  52. package/dist/chunk-WOMCXN2W.cjs.map +1 -0
  53. package/dist/{chunk-3R3QVKY5.cjs → chunk-YDGMWH43.cjs} +397 -324
  54. package/dist/chunk-YDGMWH43.cjs.map +1 -0
  55. package/dist/{chunk-AGOVW7U6.js → chunk-YYVXRV3V.js} +72 -56
  56. package/dist/chunk-YYVXRV3V.js.map +1 -0
  57. package/dist/{chunk-M5RYMAFI.js → chunk-ZLNSH4UL.js} +71 -31
  58. package/dist/chunk-ZLNSH4UL.js.map +1 -0
  59. package/dist/{coerce-DRERzdve.d.cts → coerce-CUhHc3Tu.d.ts} +16 -8
  60. package/dist/{coerce-DP0vYu-x.d.ts → coerce-Ytt2Eiq9.d.cts} +16 -8
  61. package/dist/core/index.cjs +5 -5
  62. package/dist/core/index.cjs.map +1 -1
  63. package/dist/core/index.d.cts +9 -8
  64. package/dist/core/index.d.ts +9 -8
  65. package/dist/core/index.js +4 -4
  66. package/dist/generate/index.cjs +8 -8
  67. package/dist/generate/index.cjs.map +1 -1
  68. package/dist/generate/index.d.cts +28 -18
  69. package/dist/generate/index.d.ts +28 -18
  70. package/dist/generate/index.js +7 -7
  71. package/dist/{index-BMweUlm5.d.cts → index-5VJgKz_Q.d.cts} +6 -2
  72. package/dist/{index-BHIUyjhZ.d.ts → index-BLuDesVG.d.ts} +20 -13
  73. package/dist/{index-B9QLziDe.d.cts → index-BV6APVa6.d.cts} +20 -13
  74. package/dist/{index-CL4b4gUQ.d.ts → index-Bf0Sv8a9.d.ts} +6 -2
  75. package/dist/{index-Dw2DP7vm.d.ts → index-BkT21EMv.d.cts} +3 -2
  76. package/dist/{index-BL5N2Oyz.d.cts → index-C7KCaTRz.d.ts} +3 -2
  77. package/dist/{index-Cy15oTvh.d.ts → index-C9MYbuKS.d.cts} +7 -3
  78. package/dist/{index-Cy15oTvh.d.cts → index-C9MYbuKS.d.ts} +7 -3
  79. package/dist/{index-CY-3NVfy.d.cts → index-DVInzCDS.d.cts} +53 -29
  80. package/dist/{index-9eoQs2C1.d.ts → index-Dg-SAfhz.d.ts} +6 -4
  81. package/dist/{index-zaZdmnU4.d.ts → index-jgeug9EA.d.ts} +53 -29
  82. package/dist/{index-cHvbYgJI.d.cts → index-pQihL4z7.d.cts} +6 -4
  83. package/dist/index.cjs +13 -13
  84. package/dist/index.cjs.map +1 -1
  85. package/dist/index.d.cts +11 -11
  86. package/dist/index.d.ts +11 -11
  87. package/dist/index.js +12 -12
  88. package/dist/{masks-Cc7-MzzY.d.ts → masks-BnzXnBj0.d.cts} +3 -2
  89. package/dist/{masks-pADfTOiD.d.cts → masks-tycmkrgs.d.ts} +3 -2
  90. package/dist/model/index.cjs +12 -12
  91. package/dist/model/index.cjs.map +1 -1
  92. package/dist/model/index.d.cts +63 -48
  93. package/dist/model/index.d.ts +63 -48
  94. package/dist/model/index.js +11 -11
  95. package/dist/{positional-DJgs6ltD.d.ts → positional-CscpxtlE.d.cts} +3 -2
  96. package/dist/{positional-DMZer-FM.d.cts → positional-DLnfUgqG.d.ts} +3 -2
  97. package/dist/{profile-DLdlIpS9.d.ts → profile-B4WqcM4H.d.ts} +25 -17
  98. package/dist/{profile-CQMEqdH9.d.cts → profile-BJd1XkPB.d.cts} +25 -17
  99. package/dist/theory/index.cjs +5 -5
  100. package/dist/theory/index.cjs.map +1 -1
  101. package/dist/theory/index.d.cts +18 -14
  102. package/dist/theory/index.d.ts +18 -14
  103. package/dist/theory/index.js +4 -4
  104. package/dist/{types-D-XgxGvp.d.cts → types-7mGFwvMm.d.ts} +45 -22
  105. package/dist/{types-Dh7C064C.d.ts → types-_ofpb2be.d.cts} +45 -22
  106. package/package.json +13 -13
  107. package/dist/chunk-35NBV2FT.cjs.map +0 -1
  108. package/dist/chunk-3R3QVKY5.cjs.map +0 -1
  109. package/dist/chunk-4R2LWV7E.cjs.map +0 -1
  110. package/dist/chunk-76ZBTRG2.cjs.map +0 -1
  111. package/dist/chunk-7KG3RTYS.js.map +0 -1
  112. package/dist/chunk-AGOVW7U6.js.map +0 -1
  113. package/dist/chunk-B2PW6EHN.cjs.map +0 -1
  114. package/dist/chunk-CGBADIO5.cjs.map +0 -1
  115. package/dist/chunk-CPMB7P75.js.map +0 -1
  116. package/dist/chunk-GNVN4PPJ.js.map +0 -1
  117. package/dist/chunk-IFZDWIKM.cjs.map +0 -1
  118. package/dist/chunk-IPEF6NWB.js.map +0 -1
  119. package/dist/chunk-M5RYMAFI.js.map +0 -1
  120. package/dist/chunk-MLBPXA4Z.js.map +0 -1
  121. package/dist/chunk-NB25P3EH.js.map +0 -1
  122. package/dist/chunk-NM7UAMC3.cjs.map +0 -1
  123. package/dist/chunk-PM4XJE2Y.cjs.map +0 -1
  124. package/dist/chunk-PUKJP2Z5.js.map +0 -1
  125. package/dist/chunk-PWC4CRWT.cjs.map +0 -1
  126. package/dist/chunk-RFIBF2RR.js.map +0 -1
  127. package/dist/chunk-S5BKZZGM.cjs.map +0 -1
  128. package/dist/chunk-UMWZ4ZET.js.map +0 -1
  129. package/dist/chunk-YFA7X2F6.cjs.map +0 -1
  130. package/dist/chunk-ZBUROTJQ.js.map +0 -1
@@ -10,13 +10,13 @@
10
10
 
11
11
 
12
12
 
13
- var _chunkYFA7X2F6cjs = require('./chunk-YFA7X2F6.cjs');
14
13
 
15
14
 
16
15
 
17
16
 
18
17
 
19
18
 
19
+ var _chunk3MDOEFIQcjs = require('./chunk-3MDOEFIQ.cjs');
20
20
 
21
21
 
22
22
 
@@ -34,13 +34,13 @@ var _chunkYFA7X2F6cjs = require('./chunk-YFA7X2F6.cjs');
34
34
 
35
35
 
36
36
 
37
- var _chunkNM7UAMC3cjs = require('./chunk-NM7UAMC3.cjs');
38
37
 
39
38
 
40
39
 
41
40
 
42
41
 
43
42
 
43
+ var _chunk3FDBMIPRcjs = require('./chunk-3FDBMIPR.cjs');
44
44
 
45
45
 
46
46
 
@@ -68,7 +68,6 @@ var _chunkNM7UAMC3cjs = require('./chunk-NM7UAMC3.cjs');
68
68
 
69
69
 
70
70
 
71
- var _chunkB2PW6EHNcjs = require('./chunk-B2PW6EHN.cjs');
72
71
 
73
72
 
74
73
 
@@ -76,6 +75,7 @@ var _chunkB2PW6EHNcjs = require('./chunk-B2PW6EHN.cjs');
76
75
 
77
76
 
78
77
 
78
+ var _chunk6TTBEON3cjs = require('./chunk-6TTBEON3.cjs');
79
79
 
80
80
 
81
81
 
@@ -104,7 +104,6 @@ var _chunkB2PW6EHNcjs = require('./chunk-B2PW6EHN.cjs');
104
104
 
105
105
 
106
106
 
107
- var _chunkIFZDWIKMcjs = require('./chunk-IFZDWIKM.cjs');
108
107
 
109
108
 
110
109
 
@@ -114,13 +113,12 @@ var _chunkIFZDWIKMcjs = require('./chunk-IFZDWIKM.cjs');
114
113
 
115
114
 
116
115
 
116
+ var _chunkLQZQDBCDcjs = require('./chunk-LQZQDBCD.cjs');
117
117
 
118
118
 
119
119
 
120
- var _chunkCGBADIO5cjs = require('./chunk-CGBADIO5.cjs');
121
120
 
122
121
 
123
- var _chunk35NBV2FTcjs = require('./chunk-35NBV2FT.cjs');
124
122
 
125
123
 
126
124
 
@@ -128,30 +126,32 @@ var _chunk35NBV2FTcjs = require('./chunk-35NBV2FT.cjs');
128
126
 
129
127
 
130
128
 
129
+ var _chunkWOMCXN2Wcjs = require('./chunk-WOMCXN2W.cjs');
131
130
 
132
131
 
132
+ var _chunkKMYGRFZ6cjs = require('./chunk-KMYGRFZ6.cjs');
133
133
 
134
134
 
135
135
 
136
136
 
137
137
 
138
- var _chunk76ZBTRG2cjs = require('./chunk-76ZBTRG2.cjs');
139
138
 
140
139
 
141
140
 
142
141
 
143
142
 
144
143
 
145
- var _chunkPM4XJE2Ycjs = require('./chunk-PM4XJE2Y.cjs');
146
144
 
147
145
 
148
146
 
147
+ var _chunkU4EQTDGNcjs = require('./chunk-U4EQTDGN.cjs');
149
148
 
150
149
 
151
150
 
152
151
 
153
152
 
154
153
 
154
+ var _chunkP3CPXAJ5cjs = require('./chunk-P3CPXAJ5.cjs');
155
155
 
156
156
 
157
157
 
@@ -198,7 +198,6 @@ var _chunkPM4XJE2Ycjs = require('./chunk-PM4XJE2Y.cjs');
198
198
 
199
199
 
200
200
 
201
- var _chunk3R3QVKY5cjs = require('./chunk-3R3QVKY5.cjs');
202
201
 
203
202
 
204
203
 
@@ -209,6 +208,7 @@ var _chunk3R3QVKY5cjs = require('./chunk-3R3QVKY5.cjs');
209
208
 
210
209
 
211
210
 
211
+ var _chunkYDGMWH43cjs = require('./chunk-YDGMWH43.cjs');
212
212
 
213
213
 
214
214
 
@@ -242,7 +242,19 @@ var _chunk3R3QVKY5cjs = require('./chunk-3R3QVKY5.cjs');
242
242
 
243
243
 
244
244
 
245
- var _chunkS5BKZZGMcjs = require('./chunk-S5BKZZGM.cjs');
245
+
246
+
247
+
248
+
249
+
250
+
251
+
252
+
253
+
254
+
255
+
256
+
257
+ var _chunkS3QELJUEcjs = require('./chunk-S3QELJUE.cjs');
246
258
 
247
259
  // src/model/interval.ts
248
260
  var INVERSION_SUM = 9;
@@ -251,6 +263,14 @@ function simpleDegree(numberValue) {
251
263
  const reduced = (numberValue - 1) % 7 + 1;
252
264
  return reduced === 1 && numberValue > 1 ? OCTAVE_DEGREES : reduced;
253
265
  }
266
+ function checkedDirection(descending) {
267
+ if (typeof descending !== "boolean") {
268
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
269
+ `interval.descending must be a boolean; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, descending)}`
270
+ );
271
+ }
272
+ return descending;
273
+ }
254
274
  function invertQuality(quality) {
255
275
  if (quality === "P") {
256
276
  return "P";
@@ -282,6 +302,12 @@ var Interval = class _Interval {
282
302
  * @returns The interval from `a` to `b`.
283
303
  */
284
304
  static between(a, b) {
305
+ if (typeof a !== "object" || a === null || typeof a.intervalTo !== "function") {
306
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`interval a must be a Note; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, a)}`);
307
+ }
308
+ if (typeof b !== "object" || b === null || typeof b.data !== "object" || b.data === null) {
309
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`interval b must be a Note; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, b)}`);
310
+ }
285
311
  return a.intervalTo(b);
286
312
  }
287
313
  /**
@@ -311,8 +337,13 @@ var Interval = class _Interval {
311
337
  * @throws If the number, quality, and span do not describe the same interval.
312
338
  */
313
339
  static fromData(data) {
314
- const checked = _chunkS5BKZZGMcjs.toSpelledInterval.call(void 0, data);
315
- return new _Interval(checked.number, checked.quality, checked.semitones, checked.descending);
340
+ const checked = _chunkS3QELJUEcjs.toSpelledInterval.call(void 0, data);
341
+ return new _Interval(
342
+ checked.number,
343
+ checked.quality,
344
+ checked.semitones,
345
+ checkedDirection(checked.descending)
346
+ );
316
347
  }
317
348
  /**
318
349
  * Rebuild an interval from its {@link Interval.toJSON} output.
@@ -335,7 +366,7 @@ var Interval = class _Interval {
335
366
  * interval field read on every keystroke.
336
367
  */
337
368
  static parse(name) {
338
- return _chunkS5BKZZGMcjs.unwrapParse.call(void 0, _Interval.tryParse(name));
369
+ return _chunkS3QELJUEcjs.unwrapParse.call(void 0, _Interval.tryParse(name));
339
370
  }
340
371
  /**
341
372
  * Parse an interval name, reporting failure instead of throwing it.
@@ -354,7 +385,7 @@ var Interval = class _Interval {
354
385
  * ```
355
386
  */
356
387
  static tryParse(name) {
357
- const parsed = _chunkS5BKZZGMcjs.tryParseInterval.call(void 0, name);
388
+ const parsed = _chunkS3QELJUEcjs.tryParseInterval.call(void 0, name);
358
389
  return parsed.ok ? { ok: true, value: _Interval.fromData(parsed.value) } : parsed;
359
390
  }
360
391
  /** Diatonic size: 1 = unison, 2 = second, ... 8 = octave, and beyond. */
@@ -410,7 +441,7 @@ var Interval = class _Interval {
410
441
  invert() {
411
442
  const numberValue = INVERSION_SUM - simpleDegree(this.#number);
412
443
  const quality = invertQuality(this.#quality);
413
- return _Interval.of(numberValue, quality, _chunkS5BKZZGMcjs.intervalSemitones.call(void 0, numberValue, quality));
444
+ return _Interval.of(numberValue, quality, _chunkS3QELJUEcjs.intervalSemitones.call(void 0, numberValue, quality));
414
445
  }
415
446
  /**
416
447
  * The same interval taken in the opposite direction.
@@ -437,12 +468,15 @@ var Interval = class _Interval {
437
468
  /**
438
469
  * Whether the interval is consonant.
439
470
  *
471
+ * The spelling decides, not the span: a diminished fourth is a dissonance
472
+ * though it sounds like a major third.
473
+ *
440
474
  * @param twoVoice When true, the perfect fourth counts as a dissonance,
441
475
  * matching two-voice counterpoint.
442
476
  * @returns True if the interval is consonant in that context.
443
477
  */
444
478
  isConsonant(twoVoice = true) {
445
- return _chunkS5BKZZGMcjs.isConsonantInterval.call(void 0, this.#semitones, twoVoice);
479
+ return _chunkYDGMWH43cjs.classifySpelledInterval.call(void 0, this.toJSON(), twoVoice) !== 2 /* Dissonance */;
446
480
  }
447
481
  /**
448
482
  * Whether another interval is spelled identically.
@@ -489,7 +523,6 @@ var Interval = class _Interval {
489
523
  };
490
524
 
491
525
  // src/model/shared.ts
492
- var STATED_KEY_CONFIDENCE = 1;
493
526
  function describeShape(value) {
494
527
  if (value === null) {
495
528
  return "null";
@@ -498,13 +531,13 @@ function describeShape(value) {
498
531
  }
499
532
  function assertDataObject(value, name) {
500
533
  if (typeof value !== "object" || value === null || Array.isArray(value)) {
501
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(`${name} must be an object; received ${describeShape(value)}`);
534
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`${name} must be an object; received ${describeShape(value)}`);
502
535
  }
503
536
  return value;
504
537
  }
505
538
  function assertDataArray(value, name) {
506
539
  if (!Array.isArray(value)) {
507
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(`${name} must be an array; received ${describeShape(value)}`);
540
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`${name} must be an array; received ${describeShape(value)}`);
508
541
  }
509
542
  return value;
510
543
  }
@@ -516,14 +549,14 @@ function assertDataObjects(value, name) {
516
549
  return items;
517
550
  }
518
551
  function assertNoteEventArray(notes, name, options) {
519
- return _chunkS5BKZZGMcjs.assertNoteEvents.call(void 0, assertDataArray(notes, name), name, options);
552
+ return _chunkS3QELJUEcjs.assertNoteEvents.call(void 0, assertDataArray(notes, name), name, options);
520
553
  }
521
554
  function assertKeyArgument(value, name) {
522
555
  if (value === void 0 || typeof value === "string" || isKeyShaped(value)) {
523
556
  return;
524
557
  }
525
558
  const received = value === null ? "null" : typeof value === "object" ? "an object" : `a ${typeof value}`;
526
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
559
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
527
560
  `${name} must be a Key; received ${received}. A method that also takes options takes them after the key, not in its place`
528
561
  );
529
562
  }
@@ -561,7 +594,7 @@ function copyNoteEvent(note) {
561
594
  }
562
595
  function copyTimeSignature(ts, name) {
563
596
  assertDataObject(ts, _nullishCoalesce(name, () => ( "time signature")));
564
- _chunkS5BKZZGMcjs.assertTimeSignature.call(void 0, ts, name);
597
+ _chunkS3QELJUEcjs.assertTimeSignature.call(void 0, ts, name);
565
598
  const copy = { numerator: ts.numerator, denominator: ts.denominator };
566
599
  if (ts.grouping !== void 0) {
567
600
  copy.grouping = [...ts.grouping];
@@ -574,19 +607,19 @@ function copyPlain(value, name) {
574
607
  }
575
608
  function copyPlainAt(value, name, seen, depth) {
576
609
  if (typeof value === "number") {
577
- return _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, value, name);
610
+ return _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, value, name);
578
611
  }
579
612
  if (typeof value === "function" || typeof value === "symbol" || typeof value === "bigint") {
580
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(`${name} must be plain data; received ${typeof value}`);
613
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`${name} must be plain data; received ${typeof value}`);
581
614
  }
582
615
  if (typeof value !== "object" || value === null) {
583
616
  return value;
584
617
  }
585
618
  if (seen.has(value)) {
586
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(`${name} must be plain data; received a value referring to itself`);
619
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`${name} must be plain data; received a value referring to itself`);
587
620
  }
588
621
  if (depth >= MAX_PLAIN_DEPTH) {
589
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
622
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
590
623
  `${name} must be plain data; received a value nested more than ${MAX_PLAIN_DEPTH} levels deep`
591
624
  );
592
625
  }
@@ -624,7 +657,7 @@ function samePlain(value, other) {
624
657
  function copyNote(data) {
625
658
  assertDataObject(data, "note data");
626
659
  if (!Number.isInteger(data.letter) || data.letter < 0 || data.letter > 6) {
627
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
660
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
628
661
  `note letter must be an integer in [0, 6]; received ${data.letter}`
629
662
  );
630
663
  }
@@ -632,7 +665,7 @@ function copyNote(data) {
632
665
  if (data.octave !== void 0) {
633
666
  copy.octave = data.octave;
634
667
  }
635
- _chunkS5BKZZGMcjs.noteToPitchClass.call(void 0, copy);
668
+ _chunkS3QELJUEcjs.noteToPitchClass.call(void 0, copy);
636
669
  return copy;
637
670
  }
638
671
  var NATURAL_LETTER = /^[A-G]$/;
@@ -641,11 +674,11 @@ function letterNumberOf(letter) {
641
674
  return letter;
642
675
  }
643
676
  if (!NATURAL_LETTER.test(letter)) {
644
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
645
- `Note.of takes a letter number 0..6 or a bare letter name 'C'..'B'; received ${_chunkS5BKZZGMcjs.describeRejected.call(void 0, letter)}. Use Note.parse(${_chunkS5BKZZGMcjs.describeRejected.call(void 0, letter)}) to read a note name with an accidental or an octave.`
677
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
678
+ `Note.of takes a letter number 0..6 or a bare letter name 'C'..'B'; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, letter)}. Use Note.parse(${_chunkS3QELJUEcjs.describeRejected.call(void 0, letter)}) to read a note name with an accidental or an octave.`
646
679
  );
647
680
  }
648
- return _chunkS5BKZZGMcjs.unwrapParse.call(void 0, _chunkS5BKZZGMcjs.tryParseNote.call(void 0, letter)).letter;
681
+ return _chunkS3QELJUEcjs.unwrapParse.call(void 0, _chunkS3QELJUEcjs.tryParseNote.call(void 0, letter)).letter;
649
682
  }
650
683
  var DIMINISHED_SECOND = {
651
684
  number: 2,
@@ -658,7 +691,7 @@ var DESCENDING_DIMINISHED_SECOND = {
658
691
  descending: true
659
692
  };
660
693
  function soundingOrder(note) {
661
- return note.octave === void 0 ? _chunkS5BKZZGMcjs.noteToPitchClass.call(void 0, note) : _chunkS5BKZZGMcjs.noteToMidi.call(void 0, note);
694
+ return note.octave === void 0 ? _chunkS3QELJUEcjs.noteToPitchClass.call(void 0, note) : _chunkS3QELJUEcjs.noteToMidi.call(void 0, note);
662
695
  }
663
696
  var Note = class _Note {
664
697
  #data;
@@ -722,7 +755,7 @@ var Note = class _Note {
722
755
  * ```
723
756
  */
724
757
  static parse(text, opts) {
725
- return _chunkS5BKZZGMcjs.unwrapParse.call(void 0, _Note.tryParse(text, opts));
758
+ return _chunkS3QELJUEcjs.unwrapParse.call(void 0, _Note.tryParse(text, opts));
726
759
  }
727
760
  /**
728
761
  * Parse a note name, reporting failure instead of throwing it.
@@ -743,7 +776,7 @@ var Note = class _Note {
743
776
  * ```
744
777
  */
745
778
  static tryParse(name, opts) {
746
- const parsed = _chunkS5BKZZGMcjs.tryParseNote.call(void 0, name, opts);
779
+ const parsed = _chunkS3QELJUEcjs.tryParseNote.call(void 0, name, opts);
747
780
  return parsed.ok ? { ok: true, value: new _Note(parsed.value) } : parsed;
748
781
  }
749
782
  /**
@@ -754,7 +787,7 @@ var Note = class _Note {
754
787
  * @returns The spelled note, with octave.
755
788
  */
756
789
  static fromMidi(midi, spelling = "sharp") {
757
- return new _Note(_chunkS5BKZZGMcjs.midiToNote.call(void 0, midi, spelling));
790
+ return new _Note(_chunkS3QELJUEcjs.midiToNote.call(void 0, midi, spelling));
758
791
  }
759
792
  /**
760
793
  * Wrap an existing plain note object.
@@ -771,7 +804,7 @@ var Note = class _Note {
771
804
  * `'Bb'`. Use {@link Note.format} to write it in another notation system.
772
805
  */
773
806
  get name() {
774
- return _chunkS5BKZZGMcjs.formatNote.call(void 0, this.#data);
807
+ return _chunkS3QELJUEcjs.formatNote.call(void 0, this.#data);
775
808
  }
776
809
  /**
777
810
  * The note name written in a notation system.
@@ -790,11 +823,11 @@ var Note = class _Note {
790
823
  * ```
791
824
  */
792
825
  format(opts) {
793
- return _chunkS5BKZZGMcjs.formatNote.call(void 0, this.#data, opts);
826
+ return _chunkS3QELJUEcjs.formatNote.call(void 0, this.#data, opts);
794
827
  }
795
828
  /** The pitch class (0..11), ignoring octave. */
796
829
  get pitchClass() {
797
- return _chunkS5BKZZGMcjs.noteToPitchClass.call(void 0, this.#data);
830
+ return _chunkS3QELJUEcjs.noteToPitchClass.call(void 0, this.#data);
798
831
  }
799
832
  /**
800
833
  * The MIDI number (middle C = C4 = 60).
@@ -803,9 +836,9 @@ var Note = class _Note {
803
836
  */
804
837
  get midi() {
805
838
  if (this.#data.octave === void 0) {
806
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(`note ${this.name} has no octave, so it has no MIDI number`);
839
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`note ${this.name} has no octave, so it has no MIDI number`);
807
840
  }
808
- return _chunkS5BKZZGMcjs.noteToMidi.call(void 0, this.#data);
841
+ return _chunkS3QELJUEcjs.noteToMidi.call(void 0, this.#data);
809
842
  }
810
843
  /** The diatonic letter number: 0..6 for C..B. */
811
844
  get letter() {
@@ -847,7 +880,7 @@ var Note = class _Note {
847
880
  * ```
848
881
  */
849
882
  frequency(tuning) {
850
- return _chunkNM7UAMC3cjs.frequencyOf.call(void 0, this.midi, tuning);
883
+ return _chunk3FDBMIPRcjs.frequencyOf.call(void 0, this.midi, tuning);
851
884
  }
852
885
  /**
853
886
  * Transpose by a signed number of semitones, keeping the spelling.
@@ -873,7 +906,7 @@ var Note = class _Note {
873
906
  if (semitones === 0 && _optionalChain([opts, 'optionalAccess', _ => _.spelling]) === void 0) {
874
907
  return new _Note(this.#data);
875
908
  }
876
- return new _Note(_chunkS5BKZZGMcjs.transposeNote.call(void 0, this.#data, semitones, opts));
909
+ return new _Note(_chunkS3QELJUEcjs.transposeNote.call(void 0, this.#data, semitones, opts));
877
910
  }
878
911
  /**
879
912
  * The spelled interval from this note to another.
@@ -882,7 +915,7 @@ var Note = class _Note {
882
915
  * @returns The interval, which {@link Interval.toJSON} unwraps to plain data.
883
916
  */
884
917
  intervalTo(other) {
885
- return Interval.fromData(_chunkS5BKZZGMcjs.spelledInterval.call(void 0, this.#data, other.data));
918
+ return Interval.fromData(_chunkS3QELJUEcjs.spelledInterval.call(void 0, this.#data, other.data));
886
919
  }
887
920
  /**
888
921
  * Transpose by a spelled interval, keeping the spelling the interval names.
@@ -903,7 +936,7 @@ var Note = class _Note {
903
936
  * ```
904
937
  */
905
938
  transposeBy(interval) {
906
- return new _Note(_chunkS5BKZZGMcjs.transposeByInterval.call(void 0, this.#data, _chunkS5BKZZGMcjs.toSpelledInterval.call(void 0, interval)));
939
+ return new _Note(_chunkS3QELJUEcjs.transposeByInterval.call(void 0, this.#data, _chunkS3QELJUEcjs.toSpelledInterval.call(void 0, interval)));
907
940
  }
908
941
  /**
909
942
  * The same spelled note in another octave.
@@ -952,7 +985,7 @@ var Note = class _Note {
952
985
  * ```
953
986
  */
954
987
  forInstrument(instrument) {
955
- return new _Note(_chunk76ZBTRG2cjs.toWrittenPitch.call(void 0, this.#data, instrument));
988
+ return new _Note(_chunkU4EQTDGNcjs.toWrittenPitch.call(void 0, this.#data, instrument));
956
989
  }
957
990
  /**
958
991
  * The other ways this note can be spelled: the same sounding pitch written on
@@ -973,7 +1006,7 @@ var Note = class _Note {
973
1006
  * ```
974
1007
  */
975
1008
  enharmonic() {
976
- return [DIMINISHED_SECOND, DESCENDING_DIMINISHED_SECOND].map((interval) => _chunkS5BKZZGMcjs.transposeByInterval.call(void 0, this.#data, interval)).filter((note) => Math.abs(note.alter) <= _chunkS5BKZZGMcjs.MAX_NAME_ACCIDENTALS).map((note) => new _Note(note));
1009
+ return [DIMINISHED_SECOND, DESCENDING_DIMINISHED_SECOND].map((interval) => _chunkS3QELJUEcjs.transposeByInterval.call(void 0, this.#data, interval)).filter((note) => Math.abs(note.alter) <= _chunkS3QELJUEcjs.MAX_NAME_ACCIDENTALS).map((note) => new _Note(note));
977
1010
  }
978
1011
  /**
979
1012
  * The scale degree this note occupies in a key, counted from 1 at the tonic.
@@ -994,7 +1027,7 @@ var Note = class _Note {
994
1027
  * ```
995
1028
  */
996
1029
  degreeIn(key) {
997
- const degree = _chunk3R3QVKY5cjs.pitchToScaleDegree.call(void 0, this.pitchClass, key);
1030
+ const degree = _chunkYDGMWH43cjs.pitchToScaleDegree.call(void 0, this.pitchClass, key);
998
1031
  return degree === -1 ? null : degree;
999
1032
  }
1000
1033
  /**
@@ -1072,11 +1105,27 @@ var Note = class _Note {
1072
1105
  };
1073
1106
 
1074
1107
  // src/model/timeline.ts
1108
+ var KEY_RELATIONS = [
1109
+ "same",
1110
+ "enharmonic",
1111
+ "relative",
1112
+ "parallel",
1113
+ "dominant",
1114
+ "subdominant",
1115
+ "relativeOfDominant",
1116
+ "relativeOfSubdominant"
1117
+ ];
1118
+ function assertNumeral(numeral, name) {
1119
+ if (typeof numeral !== "string") {
1120
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`${name} must be a string; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, numeral)}`);
1121
+ }
1122
+ return numeral;
1123
+ }
1075
1124
  function copySegment(segment) {
1076
1125
  assertDataObject(segment, "timeline segment");
1077
1126
  return {
1078
- startBeat: _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, segment.startBeat, "timeline segment startBeat"),
1079
- endBeat: _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, segment.endBeat, "timeline segment endBeat"),
1127
+ startBeat: _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, segment.startBeat, "timeline segment startBeat"),
1128
+ endBeat: _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, segment.endBeat, "timeline segment endBeat"),
1080
1129
  // The chord is checked by the same boundary every other chord crosses, so a
1081
1130
  // root of 25 or an interval of NaN is refused or reduced here rather than
1082
1131
  // surfacing wherever the number is finally used.
@@ -1086,22 +1135,22 @@ function copySegment(segment) {
1086
1135
  function copyKeyRegion(region) {
1087
1136
  assertDataObject(region, "key region");
1088
1137
  const copy = {
1089
- startBeat: _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, region.startBeat, "key region startBeat"),
1090
- endBeat: _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, region.endBeat, "key region endBeat"),
1138
+ startBeat: _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, region.startBeat, "key region startBeat"),
1139
+ endBeat: _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, region.endBeat, "key region endBeat"),
1091
1140
  // Read through the key itself, so a tonic that does not spell the region's
1092
1141
  // own root is refused here rather than spelling later notes wrongly.
1093
1142
  key: keyIdentity(toKey(region.key)),
1094
- confidence: _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, region.confidence, "key region confidence")
1143
+ confidence: _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, region.confidence, "key region confidence")
1095
1144
  };
1096
1145
  if (region.modulation !== void 0) {
1097
- copy.modulation = region.modulation;
1146
+ copy.modulation = _chunkS3QELJUEcjs.assertOneOf.call(void 0, region.modulation, KEY_RELATIONS, "key region modulation");
1098
1147
  }
1099
1148
  if (region.pivot !== void 0) {
1100
1149
  assertDataObject(region.pivot, "key region pivot");
1101
1150
  copy.pivot = {
1102
1151
  chord: new Chord(region.pivot.chord).toJSON(),
1103
- romanFrom: region.pivot.romanFrom,
1104
- romanTo: region.pivot.romanTo
1152
+ romanFrom: assertNumeral(region.pivot.romanFrom, "key region pivot romanFrom"),
1153
+ romanTo: assertNumeral(region.pivot.romanTo, "key region pivot romanTo")
1105
1154
  };
1106
1155
  }
1107
1156
  return copy;
@@ -1112,14 +1161,18 @@ function copyConfidence(confidence, segments) {
1112
1161
  }
1113
1162
  assertDataArray(confidence, "timeline segmentConfidence");
1114
1163
  if (confidence.length !== segments) {
1115
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
1164
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1116
1165
  `timeline segmentConfidence must hold one value per segment; received ${confidence.length} for ${segments}`
1117
1166
  );
1118
1167
  }
1119
1168
  return confidence.map(
1120
- (value, index) => _chunkS5BKZZGMcjs.assertRange.call(void 0, value, 0, 1, `timeline segmentConfidence[${index}]`)
1169
+ (value, index) => _chunkS3QELJUEcjs.assertRange.call(void 0, value, 0, 1, `timeline segmentConfidence[${index}]`)
1121
1170
  );
1122
1171
  }
1172
+ function validateTimeline(segments, keys) {
1173
+ _chunkLQZQDBCDcjs.assertSpansInOrder.call(void 0, segments, "timeline segments");
1174
+ _chunkLQZQDBCDcjs.assertSpansInOrder.call(void 0, keys, "timeline keys");
1175
+ }
1123
1176
  function clipSpan(span, fromBeat, toBeat) {
1124
1177
  const startBeat = Math.max(span.startBeat, fromBeat);
1125
1178
  const endBeat = Math.min(span.endBeat, toBeat);
@@ -1135,15 +1188,16 @@ var Timeline = class _Timeline {
1135
1188
  *
1136
1189
  * @param data The segments and the span they cover; copied, never retained.
1137
1190
  * @throws If the span, a segment, or a key region carries a number it cannot
1138
- * hold — a beat that is not finite, a mode mask that names no scale — or if
1139
- * the confidences do not run one per segment.
1191
+ * hold — a beat that is not finite, a mode mask that names no scale — if
1192
+ * the segments or the key regions are not disjoint, in beat order and of
1193
+ * positive length, or if the confidences do not run one per segment.
1140
1194
  */
1141
1195
  constructor(data) {
1142
1196
  assertDataObject(data, "timeline data");
1143
1197
  this.#segments = Object.freeze(
1144
1198
  assertDataArray(data.segments, "timeline segments").map(copySegment)
1145
1199
  );
1146
- this.#totalBeats = _chunkS5BKZZGMcjs.assertRange.call(void 0,
1200
+ this.#totalBeats = _chunkS3QELJUEcjs.assertRange.call(void 0,
1147
1201
  data.totalBeats,
1148
1202
  0,
1149
1203
  Number.MAX_SAFE_INTEGER,
@@ -1155,6 +1209,7 @@ var Timeline = class _Timeline {
1155
1209
  this.#segmentConfidence = Object.freeze(
1156
1210
  copyConfidence(data.segmentConfidence, this.#segments.length)
1157
1211
  );
1212
+ validateTimeline(this.#segments, this.#keys);
1158
1213
  }
1159
1214
  /**
1160
1215
  * Build a timeline from placed chords.
@@ -1162,24 +1217,18 @@ var Timeline = class _Timeline {
1162
1217
  * @param spans The chords with their onsets, in any order.
1163
1218
  * @param totalBeats Where the last chord stops sounding.
1164
1219
  * @param key The key the chords are read in, when it is already known. It
1165
- * becomes the one key region under the whole span; without it the timeline
1220
+ * becomes the one key region from the first chord to the end of the span;
1221
+ * without it, or without a chord for it to be in force over, the timeline
1166
1222
  * carries no key, and the members that need one say so.
1167
1223
  * @returns The timeline.
1168
1224
  */
1169
1225
  static fromChords(spans, totalBeats, key) {
1170
- const timeline = _chunkIFZDWIKMcjs.chordTimelineFromChords.call(void 0, spans, totalBeats);
1226
+ const timeline = _chunkLQZQDBCDcjs.chordTimelineFromChords.call(void 0, spans, totalBeats);
1171
1227
  const data = { segments: timeline.segments, totalBeats };
1172
1228
  if (key !== void 0) {
1173
- data.keys = [
1174
- {
1175
- // The region starts where the music does, as an inferred one does,
1176
- // so a chord placed in a pickup is covered by the key it sounds in.
1177
- startBeat: _nullishCoalesce(_optionalChain([timeline, 'access', _2 => _2.segments, 'access', _3 => _3[0], 'optionalAccess', _4 => _4.startBeat]), () => ( 0)),
1178
- endBeat: totalBeats,
1179
- key: keyIdentity(toKey(key)),
1180
- confidence: STATED_KEY_CONFIDENCE
1181
- }
1182
- ];
1229
+ const stated = keyIdentity(toKey(key));
1230
+ const first = timeline.segments[0];
1231
+ data.keys = first === void 0 ? [] : _chunkLQZQDBCDcjs.statedKeyRegions.call(void 0, stated, first.startBeat, totalBeats);
1183
1232
  }
1184
1233
  return new _Timeline(data);
1185
1234
  }
@@ -1191,8 +1240,8 @@ var Timeline = class _Timeline {
1191
1240
  * @returns The inferred timeline, carrying the key regions the analysis found.
1192
1241
  */
1193
1242
  static fromNotes(notes, opts) {
1194
- const { timeline, keys, segmentConfidence } = _chunkIFZDWIKMcjs.chordTimelineFromNotes.call(void 0, notes, opts);
1195
- const totalBeats = _nullishCoalesce(_optionalChain([opts, 'optionalAccess', _5 => _5.totalBeats]), () => ( spanEnd(timeline.segments, keys)));
1243
+ const { timeline, keys, segmentConfidence } = _chunkLQZQDBCDcjs.chordTimelineFromNotes.call(void 0, notes, opts);
1244
+ const totalBeats = _nullishCoalesce(_optionalChain([opts, 'optionalAccess', _2 => _2.totalBeats]), () => ( spanEnd(timeline.segments, keys)));
1196
1245
  return new _Timeline({ segments: timeline.segments, totalBeats, keys, segmentConfidence });
1197
1246
  }
1198
1247
  /**
@@ -1210,11 +1259,25 @@ var Timeline = class _Timeline {
1210
1259
  * @throws If `beatsEach` is not a positive finite number of beats.
1211
1260
  */
1212
1261
  static fromProgression(progression, beatsEach) {
1213
- _chunkS5BKZZGMcjs.assertRange.call(void 0, beatsEach, Number.MIN_VALUE, Number.MAX_SAFE_INTEGER, "timeline beatsEach");
1214
- const chords = progression.chords;
1215
- const spans = chords.map((chord, index) => _chunk3R3QVKY5cjs.spanFromChord.call(void 0, chord.data, index * beatsEach));
1262
+ const read = progression;
1263
+ if (typeof read !== "object" || read === null || !Array.isArray(read.chords)) {
1264
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1265
+ `timeline progression must be a Progression; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, progression)}`
1266
+ );
1267
+ }
1268
+ _chunkS3QELJUEcjs.assertRange.call(void 0, beatsEach, Number.MIN_VALUE, Number.MAX_SAFE_INTEGER, "timeline beatsEach");
1269
+ const chords = read.chords;
1270
+ const spans = chords.map((chord, index) => {
1271
+ const data = _optionalChain([chord, 'optionalAccess', _3 => _3.data]);
1272
+ if (typeof data !== "object" || data === null) {
1273
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1274
+ `timeline progression chords[${index}] must be a Chord; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, chord)}`
1275
+ );
1276
+ }
1277
+ return _chunkYDGMWH43cjs.spanFromChord.call(void 0, data, index * beatsEach);
1278
+ });
1216
1279
  const totalBeats = chords.length * beatsEach;
1217
- const key = progression.key;
1280
+ const key = read.key;
1218
1281
  return key === void 0 ? _Timeline.fromChords(spans, totalBeats) : _Timeline.fromChords(spans, totalBeats, key);
1219
1282
  }
1220
1283
  /** Rebuild a timeline from the plain data {@link Timeline.data} hands out. */
@@ -1238,7 +1301,7 @@ var Timeline = class _Timeline {
1238
1301
  * @throws If `beat` is not finite.
1239
1302
  */
1240
1303
  at(beat) {
1241
- const chord = _chunkIFZDWIKMcjs.chordAtBeat.call(void 0, this.#segments, beat);
1304
+ const chord = _chunkLQZQDBCDcjs.chordAtBeat.call(void 0, this.#segments, beat);
1242
1305
  if (chord === null) {
1243
1306
  return null;
1244
1307
  }
@@ -1255,7 +1318,7 @@ var Timeline = class _Timeline {
1255
1318
  }
1256
1319
  /** The key held longest across the span, when the analysis found one. */
1257
1320
  get key() {
1258
- const prevailing = _chunkIFZDWIKMcjs.prevailingKeyOf.call(void 0, this.#keys);
1321
+ const prevailing = _chunkLQZQDBCDcjs.prevailingKeyOf.call(void 0, this.#keys);
1259
1322
  return prevailing === null ? void 0 : toKey(prevailing);
1260
1323
  }
1261
1324
  /**
@@ -1327,7 +1390,7 @@ var Timeline = class _Timeline {
1327
1390
  * @throws If the timeline carries no key region to read the chords against.
1328
1391
  */
1329
1392
  reduce(opts) {
1330
- return _chunkIFZDWIKMcjs.reduceProgression.call(void 0, this.chordTimeline, this.#keyContext(), opts);
1393
+ return _chunkLQZQDBCDcjs.reduceProgression.call(void 0, this.chordTimeline, this.#keyContext(), opts);
1331
1394
  }
1332
1395
  /**
1333
1396
  * The cadences the harmony arrives at.
@@ -1340,7 +1403,7 @@ var Timeline = class _Timeline {
1340
1403
  * @throws If the timeline carries no key region to read the chords against.
1341
1404
  */
1342
1405
  cadences() {
1343
- return _chunkIFZDWIKMcjs.detectCadences.call(void 0, this.chordTimeline, this.#keyContext());
1406
+ return _chunkLQZQDBCDcjs.detectCadences.call(void 0, this.chordTimeline, this.#keyContext());
1344
1407
  }
1345
1408
  /**
1346
1409
  * The keys the chords themselves imply, in time order.
@@ -1369,7 +1432,7 @@ var Timeline = class _Timeline {
1369
1432
  * ```
1370
1433
  */
1371
1434
  modulations(opts) {
1372
- return _chunkIFZDWIKMcjs.detectModulations.call(void 0, this.#copySegments(), {
1435
+ return _chunkLQZQDBCDcjs.detectModulations.call(void 0, this.#copySegments(), {
1373
1436
  totalBeats: this.#totalBeats,
1374
1437
  ...opts
1375
1438
  }).map(copyKeyRegion);
@@ -1387,12 +1450,12 @@ var Timeline = class _Timeline {
1387
1450
  */
1388
1451
  roman(key, opts) {
1389
1452
  assertKeyArgument(key, "timeline key");
1390
- const given = key === void 0 ? void 0 : _chunk3R3QVKY5cjs.resolveKey.call(void 0, key);
1453
+ const given = key === void 0 ? void 0 : _chunkYDGMWH43cjs.resolveKey.call(void 0, key);
1391
1454
  const keyAt = given === void 0 ? this.#resolvedKeyAt() : () => given;
1392
1455
  return this.#segments.map((segment) => ({
1393
1456
  startBeat: segment.startBeat,
1394
1457
  endBeat: segment.endBeat,
1395
- roman: _chunkIFZDWIKMcjs.chordToRoman.call(void 0, segment.chord, keyAt(segment.startBeat), opts)
1458
+ roman: _chunkLQZQDBCDcjs.chordToRoman.call(void 0, segment.chord, keyAt(segment.startBeat), opts)
1396
1459
  }));
1397
1460
  }
1398
1461
  /**
@@ -1409,10 +1472,10 @@ var Timeline = class _Timeline {
1409
1472
  * @throws If either beat is not finite, or `toBeat` precedes `fromBeat`.
1410
1473
  */
1411
1474
  slice(fromBeat, toBeat) {
1412
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, fromBeat, "timeline slice fromBeat");
1413
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, toBeat, "timeline slice toBeat");
1475
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, fromBeat, "timeline slice fromBeat");
1476
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, toBeat, "timeline slice toBeat");
1414
1477
  if (toBeat < fromBeat) {
1415
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
1478
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1416
1479
  `timeline slice toBeat must not precede fromBeat; received [${fromBeat}, ${toBeat})`
1417
1480
  );
1418
1481
  }
@@ -1507,7 +1570,7 @@ var Timeline = class _Timeline {
1507
1570
  /** The `{ at, segments }` shape the analysis functions take. */
1508
1571
  get chordTimeline() {
1509
1572
  const segments = this.#copySegments();
1510
- return { at: (beat) => _chunkIFZDWIKMcjs.chordAtBeat.call(void 0, segments, beat), segments };
1573
+ return { at: (beat) => _chunkLQZQDBCDcjs.chordAtBeat.call(void 0, segments, beat), segments };
1511
1574
  }
1512
1575
  /** A fresh copy of the segments, which is what every reader is handed. */
1513
1576
  #copySegments() {
@@ -1515,8 +1578,8 @@ var Timeline = class _Timeline {
1515
1578
  }
1516
1579
  /** The key in force at a beat, or undefined when the timeline knows none. */
1517
1580
  #keyAt(beat) {
1518
- const prevailing = _chunkIFZDWIKMcjs.prevailingKeyOf.call(void 0, this.#keys);
1519
- return prevailing === null ? void 0 : toKey(_chunkIFZDWIKMcjs.keyLookup.call(void 0, this.#keys, prevailing)(beat));
1581
+ const prevailing = _chunkLQZQDBCDcjs.prevailingKeyOf.call(void 0, this.#keys);
1582
+ return prevailing === null ? void 0 : toKey(_chunkLQZQDBCDcjs.keyLookup.call(void 0, this.#keys, prevailing)(beat));
1520
1583
  }
1521
1584
  /**
1522
1585
  * The key every beat of the timeline is read against, spelling and all.
@@ -1529,13 +1592,13 @@ var Timeline = class _Timeline {
1529
1592
  * would number it as the G# minor those read best as.
1530
1593
  */
1531
1594
  #resolvedKeyAt() {
1532
- const prevailing = _chunkIFZDWIKMcjs.prevailingKeyOf.call(void 0, this.#keys);
1595
+ const prevailing = _chunkLQZQDBCDcjs.prevailingKeyOf.call(void 0, this.#keys);
1533
1596
  if (prevailing === null) {
1534
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
1597
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1535
1598
  "timeline carries no key; build it from notes, or pass a key to Timeline.fromChords"
1536
1599
  );
1537
1600
  }
1538
- return _chunkIFZDWIKMcjs.keyLookup.call(void 0, this.#keys, prevailing);
1601
+ return _chunkLQZQDBCDcjs.keyLookup.call(void 0, this.#keys, prevailing);
1539
1602
  }
1540
1603
  /**
1541
1604
  * The pitch classes of that key, for the readings that want them.
@@ -1547,7 +1610,7 @@ var Timeline = class _Timeline {
1547
1610
  */
1548
1611
  #keyContext() {
1549
1612
  const keyAt = this.#resolvedKeyAt();
1550
- return (beat) => _chunk3R3QVKY5cjs.scaleOf.call(void 0, keyAt(beat));
1613
+ return (beat) => _chunkYDGMWH43cjs.scaleOf.call(void 0, keyAt(beat));
1551
1614
  }
1552
1615
  /** Move every chord and every key region by the same step. */
1553
1616
  #moved(moveChord, moveKey) {
@@ -1606,7 +1669,14 @@ var Progression = class _Progression {
1606
1669
  */
1607
1670
  static #attachKey(chords, key) {
1608
1671
  const given = assertDataObjects(chords, "progression chords");
1609
- return key === void 0 ? [...given] : given.map((chord) => chord.withKey(key));
1672
+ return given.map((chord, index) => {
1673
+ if (typeof chord.toJSON !== "function") {
1674
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1675
+ `progression chords[${index}] must be a Chord; received ${_chunkS3QELJUEcjs.describeRejected.call(void 0, chord)}`
1676
+ );
1677
+ }
1678
+ return new Chord(chord.toJSON(), _nullishCoalesce(key, () => ( chord.key)));
1679
+ });
1610
1680
  }
1611
1681
  /**
1612
1682
  * Start from a chord sequence, matching the `of` factory on the other
@@ -1649,24 +1719,39 @@ var Progression = class _Progression {
1649
1719
  */
1650
1720
  static fromSpans(spans, key) {
1651
1721
  const chords = assertDataObjects(spans, "progression spans").map(
1652
- (span) => Chord.fromData(_chunk3R3QVKY5cjs.chordFromSpan.call(void 0, span))
1722
+ (span) => Chord.fromData(_chunkYDGMWH43cjs.chordFromSpan.call(void 0, span))
1653
1723
  );
1654
1724
  return new _Progression(chords, key);
1655
1725
  }
1656
1726
  /**
1657
- * Rebuild a progression from its {@link Progression.toJSON} output.
1727
+ * Rebuild a progression from its {@link Progression.toJSON} output, with the
1728
+ * carried key or, without one, each chord's own key.
1658
1729
  *
1659
- * @param data The serialized chords and key.
1730
+ * @param data The serialized chords and keys.
1660
1731
  * @returns The progression.
1732
+ * @throws If `chordKeys` does not hold one entry per chord.
1661
1733
  */
1662
1734
  static fromJSON(data) {
1663
1735
  assertDataObject(data, "progression data");
1664
1736
  const key = data.key === void 0 ? void 0 : Key.fromJSON(data.key);
1665
- const chords = assertDataArray(data.chords, "progression chords").map(
1666
- (chord) => Chord.fromJSON(chord)
1667
- );
1737
+ const given = assertDataArray(data.chords, "progression chords");
1738
+ const chordKeys = key === void 0 && data.chordKeys !== void 0 ? _Progression.#readChordKeys(data.chordKeys, given.length) : void 0;
1739
+ const chords = given.map((chord, index) => {
1740
+ const own = _optionalChain([chordKeys, 'optionalAccess', _4 => _4[index]]);
1741
+ return own === void 0 ? Chord.fromJSON(chord) : Chord.fromJSON(chord).withKey(own);
1742
+ });
1668
1743
  return key === void 0 ? new _Progression(chords) : new _Progression(chords, key);
1669
1744
  }
1745
+ /** Read the per-chord keys of {@link ProgressionData}, one entry per chord. */
1746
+ static #readChordKeys(value, count) {
1747
+ const entries = assertDataArray(value, "progression chord keys");
1748
+ if (entries.length !== count) {
1749
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1750
+ `progression chord keys must hold one entry per chord (${count}); received ${entries.length}`
1751
+ );
1752
+ }
1753
+ return entries.map((entry) => entry === null ? void 0 : Key.fromJSON(entry));
1754
+ }
1670
1755
  /**
1671
1756
  * Wrap plain progression data, matching the `fromData` factory on the other
1672
1757
  * classes.
@@ -1876,11 +1961,9 @@ var Progression = class _Progression {
1876
1961
  * @throws If any chord admits no voicing within the given ranges.
1877
1962
  */
1878
1963
  voice(opts) {
1879
- const key = _nullishCoalesce(_optionalChain([opts, 'optionalAccess', _6 => _6.key]), () => ( this.#key));
1880
- return _chunk76ZBTRG2cjs.voiceProgression.call(void 0,
1881
- this.#chords.map((chord) => chord.data),
1882
- key === void 0 ? opts : { ...opts, key }
1883
- );
1964
+ const key = _nullishCoalesce(_optionalChain([opts, 'optionalAccess', _5 => _5.key]), () => ( this.#key));
1965
+ const views = _optionalChain([opts, 'optionalAccess', _6 => _6.key]) === void 0 ? this.#chords.map((chord) => chord.data) : this.#viewsIn(toKey(opts.key));
1966
+ return _chunkU4EQTDGNcjs.voiceProgression.call(void 0, views, key === void 0 ? opts : { ...opts, key });
1884
1967
  }
1885
1968
  /**
1886
1969
  * The Roman numeral of each chord in a key.
@@ -1941,12 +2024,13 @@ var Progression = class _Progression {
1941
2024
  const resolved = this.#resolveKey(key);
1942
2025
  const chords = this.#chords.map((chord) => chord.analyze(resolved, opts));
1943
2026
  const { voicing, ...cadenceOpts } = _nullishCoalesce(opts, () => ( {}));
1944
- const from = this.#chords[this.#chords.length - 2];
1945
- const to = this.#chords[this.#chords.length - 1];
1946
- const approach = this.#chords[this.#chords.length - 3];
1947
- const cadence = from !== void 0 && to !== void 0 ? _chunkIFZDWIKMcjs.detectCadence.call(void 0, from.data, to.data, resolved, {
2027
+ const views = this.#viewsIn(resolved);
2028
+ const from = views[views.length - 2];
2029
+ const to = views[views.length - 1];
2030
+ const approach = views[views.length - 3];
2031
+ const cadence = from !== void 0 && to !== void 0 ? _chunkLQZQDBCDcjs.detectCadence.call(void 0, from, to, resolved, {
1948
2032
  ...cadenceOpts,
1949
- ...approach === void 0 ? {} : { approach: approach.data },
2033
+ ...approach === void 0 ? {} : { approach },
1950
2034
  ...voicing === void 0 ? {} : { voicing: this.#closingVoicing(voicing) }
1951
2035
  }) : null;
1952
2036
  return { chords, cadence };
@@ -1964,7 +2048,7 @@ var Progression = class _Progression {
1964
2048
  if (voicing.length === this.#chords.length || voicing.length === 2) {
1965
2049
  return [_nullishCoalesce(voicing[voicing.length - 2], () => ( [])), _nullishCoalesce(voicing[voicing.length - 1], () => ( []))];
1966
2050
  }
1967
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
2051
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
1968
2052
  `voicing must hold one voicing per chord (${this.#chords.length}) or the closing pair; received ${voicing.length}`
1969
2053
  );
1970
2054
  }
@@ -1974,7 +2058,7 @@ var Progression = class _Progression {
1974
2058
  * @returns One scale choice per chord in this progression.
1975
2059
  */
1976
2060
  scales() {
1977
- return _chunkPM4XJE2Ycjs.scalesForChanges.call(void 0, this.#chords.map((chord) => chord.data));
2061
+ return _chunkP3CPXAJ5cjs.scalesForChanges.call(void 0, this.#chords.map((chord) => chord.data));
1978
2062
  }
1979
2063
  /**
1980
2064
  * Classify the motion at every chord change, not only the closing one.
@@ -2011,18 +2095,19 @@ var Progression = class _Progression {
2011
2095
  */
2012
2096
  cadences(key, opts) {
2013
2097
  const resolved = this.#resolveKey(key);
2098
+ const views = this.#viewsIn(resolved);
2014
2099
  const found = [];
2015
- for (let index = 1; index < this.#chords.length; index += 1) {
2016
- const from = this.#chords[index - 1];
2017
- const to = this.#chords[index];
2100
+ for (let index = 1; index < views.length; index += 1) {
2101
+ const from = views[index - 1];
2102
+ const to = views[index];
2018
2103
  if (from === void 0 || to === void 0) {
2019
2104
  continue;
2020
2105
  }
2021
- const approach = index >= 2 ? _optionalChain([this, 'access', _7 => _7.#chords, 'access', _8 => _8[index - 2], 'optionalAccess', _9 => _9.data]) : _optionalChain([opts, 'optionalAccess', _10 => _10.approach]);
2022
- const pair = _optionalChain([opts, 'optionalAccess', _11 => _11.voicing]);
2106
+ const approach = index >= 2 ? views[index - 2] : _optionalChain([opts, 'optionalAccess', _7 => _7.approach]);
2107
+ const pair = _optionalChain([opts, 'optionalAccess', _8 => _8.voicing]);
2023
2108
  found.push(
2024
- _chunkIFZDWIKMcjs.detectCadence.call(void 0, from.data, to.data, resolved, {
2025
- ..._optionalChain([opts, 'optionalAccess', _12 => _12.alternatives]) === void 0 ? {} : { alternatives: opts.alternatives },
2109
+ _chunkLQZQDBCDcjs.detectCadence.call(void 0, from, to, resolved, {
2110
+ ..._optionalChain([opts, 'optionalAccess', _9 => _9.alternatives]) === void 0 ? {} : { alternatives: opts.alternatives },
2026
2111
  ...approach === void 0 ? {} : { approach },
2027
2112
  ...pair === void 0 ? {} : { voicing: [_nullishCoalesce(pair[index - 1], () => ( [])), _nullishCoalesce(pair[index], () => ( []))] }
2028
2113
  })
@@ -2058,16 +2143,16 @@ var Progression = class _Progression {
2058
2143
  const position = index < 0 ? this.#chords.length + index : index;
2059
2144
  const target = this.#chords[position];
2060
2145
  if (target === void 0) {
2061
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
2146
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
2062
2147
  `progression has no chord at index ${index}; it holds ${this.#chords.length}`
2063
2148
  );
2064
2149
  }
2065
2150
  const key = this.#resolveKey();
2066
- const chosen = _chunkB2PW6EHNcjs.substituteChord.call(void 0, target.data, key, opts).find(
2151
+ const chosen = _chunk6TTBEON3cjs.substituteChord.call(void 0, target.data, key, opts).find(
2067
2152
  (candidate) => candidate.type === type
2068
2153
  );
2069
2154
  if (chosen === void 0) {
2070
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
2155
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
2071
2156
  `no ${type} substitution for ${target.symbol()} in ${key.toString()}`
2072
2157
  );
2073
2158
  }
@@ -2109,7 +2194,7 @@ var Progression = class _Progression {
2109
2194
  * ```
2110
2195
  */
2111
2196
  transpose(semitones) {
2112
- const key = _optionalChain([this, 'access', _13 => _13.#key, 'optionalAccess', _14 => _14.transpose, 'call', _15 => _15(semitones)]);
2197
+ const key = _optionalChain([this, 'access', _10 => _10.#key, 'optionalAccess', _11 => _11.transpose, 'call', _12 => _12(semitones)]);
2113
2198
  const chords = this.#chords.map((chord) => chord.transpose(semitones));
2114
2199
  return new _Progression(chords, key);
2115
2200
  }
@@ -2132,7 +2217,7 @@ var Progression = class _Progression {
2132
2217
  * ```
2133
2218
  */
2134
2219
  transposeBy(interval) {
2135
- const key = _optionalChain([this, 'access', _16 => _16.#key, 'optionalAccess', _17 => _17.transposeBy, 'call', _18 => _18(interval)]);
2220
+ const key = _optionalChain([this, 'access', _13 => _13.#key, 'optionalAccess', _14 => _14.transposeBy, 'call', _15 => _15(interval)]);
2136
2221
  const chords = this.#chords.map((chord) => chord.transposeBy(interval));
2137
2222
  return new _Progression(chords, key);
2138
2223
  }
@@ -2160,7 +2245,7 @@ var Progression = class _Progression {
2160
2245
  transposeTo(target) {
2161
2246
  const from = this.#key;
2162
2247
  if (from === void 0) {
2163
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
2248
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
2164
2249
  "progression has no key context; attach one with withKey() before transposing to another key"
2165
2250
  );
2166
2251
  }
@@ -2182,16 +2267,26 @@ var Progression = class _Progression {
2182
2267
  /**
2183
2268
  * The plain progression data, for JSON serialization.
2184
2269
  *
2185
- * Private class fields do not serialize, so this preserves both the chord
2186
- * data and any carried key in `JSON.stringify(progression)`.
2270
+ * Private class fields do not serialize, so this preserves the chord data,
2271
+ * any carried key, and — for a progression with no key of its own — each
2272
+ * chord's own key in `JSON.stringify(progression)`.
2187
2273
  *
2188
- * @returns The chord data sequence and the carried key, if any.
2274
+ * @returns The chord data sequence, the carried key, if any, and the
2275
+ * per-chord keys when they are what spells the chords.
2189
2276
  */
2190
2277
  toJSON() {
2191
- return {
2278
+ const out = {
2192
2279
  chords: this.#chords.map((chord) => chord.toJSON()),
2193
- key: _optionalChain([this, 'access', _19 => _19.#key, 'optionalAccess', _20 => _20.toJSON, 'call', _21 => _21()])
2280
+ key: _optionalChain([this, 'access', _16 => _16.#key, 'optionalAccess', _17 => _17.toJSON, 'call', _18 => _18()])
2194
2281
  };
2282
+ if (this.#key === void 0 && this.#chords.some((chord) => chord.key !== void 0)) {
2283
+ out.chordKeys = this.#chords.map((chord) => _nullishCoalesce(_optionalChain([chord, 'access', _19 => _19.key, 'optionalAccess', _20 => _20.toJSON, 'call', _21 => _21()]), () => ( null)));
2284
+ }
2285
+ return out;
2286
+ }
2287
+ /** The members read in `key`: spellings the caller gave, the rest derived from it. */
2288
+ #viewsIn(key) {
2289
+ return this.#chords.map((chord) => chord.withKey(key).data);
2195
2290
  }
2196
2291
  /**
2197
2292
  * Resolve the key for an analysis method: explicit first, then carried.
@@ -2203,7 +2298,7 @@ var Progression = class _Progression {
2203
2298
  assertKeyArgument(key, "progression key");
2204
2299
  const resolved = key === void 0 ? this.#key : toKey(key);
2205
2300
  if (resolved === void 0) {
2206
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
2301
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
2207
2302
  "progression has no key context; pass a Key or attach one with withKey()"
2208
2303
  );
2209
2304
  }
@@ -2213,25 +2308,25 @@ var Progression = class _Progression {
2213
2308
 
2214
2309
  // src/model/chord.ts
2215
2310
  function hintMatches(hint, pc) {
2216
- return hint !== void 0 && pc !== void 0 && _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, _chunkS5BKZZGMcjs.noteToPitchClass.call(void 0, hint)) === _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, pc);
2311
+ return hint !== void 0 && pc !== void 0 && _chunkS3QELJUEcjs.pitchClassOf.call(void 0, _chunkS3QELJUEcjs.noteToPitchClass.call(void 0, hint)) === _chunkS3QELJUEcjs.pitchClassOf.call(void 0, pc);
2217
2312
  }
2218
2313
  function transposeHintByInterval(hint, interval) {
2219
2314
  if (hint === void 0) {
2220
2315
  return void 0;
2221
2316
  }
2222
- const moved = _chunkS5BKZZGMcjs.transposeByInterval.call(void 0, hint, interval);
2317
+ const moved = _chunkS3QELJUEcjs.transposeByInterval.call(void 0, hint, interval);
2223
2318
  return { letter: moved.letter, alter: moved.alter };
2224
2319
  }
2225
2320
  function transposeToneHintsByInterval(hints, interval) {
2226
2321
  return _optionalChain([hints, 'optionalAccess', _22 => _22.map, 'call', _23 => _23((hint) => {
2227
- const moved = _chunkS5BKZZGMcjs.transposeByInterval.call(void 0, hint, interval);
2322
+ const moved = _chunkS3QELJUEcjs.transposeByInterval.call(void 0, hint, interval);
2228
2323
  return { letter: moved.letter, alter: moved.alter };
2229
2324
  })]);
2230
2325
  }
2231
2326
  function copyChord(data) {
2232
2327
  assertDataObject(data, "chord data");
2233
- _chunk3R3QVKY5cjs.assertChordQuality.call(void 0, data.quality);
2234
- const rootPc = _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, data.rootPc);
2328
+ _chunkYDGMWH43cjs.assertChordQuality.call(void 0, data.quality);
2329
+ const rootPc = _chunkS3QELJUEcjs.pitchClassOf.call(void 0, data.rootPc);
2235
2330
  const copy = {
2236
2331
  rootPc,
2237
2332
  quality: data.quality,
@@ -2239,14 +2334,14 @@ function copyChord(data) {
2239
2334
  // interval voices, spells and formats as a chord that looks real, and the
2240
2335
  // failure surfaces wherever the number is finally used.
2241
2336
  intervals: assertDataArray(data.intervals, "chord intervals").map(
2242
- (interval, index) => _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, interval, `chord intervals[${index}]`)
2337
+ (interval, index) => _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, interval, `chord intervals[${index}]`)
2243
2338
  )
2244
2339
  };
2245
- const bassPc = data.bassPc === void 0 ? void 0 : _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, data.bassPc);
2340
+ const bassPc = data.bassPc === void 0 ? void 0 : _chunkS3QELJUEcjs.pitchClassOf.call(void 0, data.bassPc);
2246
2341
  if (bassPc !== void 0 && bassPc !== rootPc) {
2247
2342
  copy.bassPc = bassPc;
2248
2343
  }
2249
- const tones = _chunk3R3QVKY5cjs.chordToneSpellings.call(void 0, data);
2344
+ const tones = _chunkYDGMWH43cjs.chordToneSpellings.call(void 0, data);
2250
2345
  if (tones !== void 0) {
2251
2346
  copy.toneSpellings = tones;
2252
2347
  }
@@ -2265,8 +2360,8 @@ function deriveBassSpelling(chord, key) {
2265
2360
  }
2266
2361
  const root = chord.rootSpelling;
2267
2362
  if (root !== void 0) {
2268
- const index = chord.intervals.findIndex((i) => _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, chord.rootPc + i) === bassPc);
2269
- const tone = index >= 0 ? _chunk3R3QVKY5cjs.spellChordFromRoot.call(void 0, chord, root)[index] : void 0;
2363
+ const index = chord.intervals.findIndex((i) => _chunkS3QELJUEcjs.pitchClassOf.call(void 0, chord.rootPc + i) === bassPc);
2364
+ const tone = index >= 0 ? _chunkYDGMWH43cjs.spellChordFromRoot.call(void 0, chord, root)[index] : void 0;
2270
2365
  if (tone !== void 0) {
2271
2366
  return { letter: tone.letter, alter: tone.alter };
2272
2367
  }
@@ -2274,7 +2369,7 @@ function deriveBassSpelling(chord, key) {
2274
2369
  if (key === void 0) {
2275
2370
  return void 0;
2276
2371
  }
2277
- const spelled = _chunk3R3QVKY5cjs.spellPitchClass.call(void 0, bassPc, key.tonic.data, key);
2372
+ const spelled = _chunkYDGMWH43cjs.spellPitchClass.call(void 0, bassPc, key.tonic.data, key);
2278
2373
  return { letter: spelled.letter, alter: spelled.alter };
2279
2374
  }
2280
2375
  var Chord = class _Chord {
@@ -2307,7 +2402,7 @@ var Chord = class _Chord {
2307
2402
  #dataWithKey(key) {
2308
2403
  const out = copyChord(this.#given);
2309
2404
  if (out.rootSpelling === void 0 && key !== void 0) {
2310
- out.rootSpelling = _chunk3R3QVKY5cjs.spellPitchClass.call(void 0, out.rootPc, key.tonic.data, key);
2405
+ out.rootSpelling = _chunkYDGMWH43cjs.spellPitchClass.call(void 0, out.rootPc, key.tonic.data, key);
2311
2406
  }
2312
2407
  if (out.bassSpelling === void 0) {
2313
2408
  const bass = deriveBassSpelling(out, key);
@@ -2330,7 +2425,7 @@ var Chord = class _Chord {
2330
2425
  const bassNote = typeof bass === "string" ? Note.parse(bass) : void 0;
2331
2426
  const bassPc = bassNote !== void 0 ? bassNote.pitchClass : bass;
2332
2427
  const rootNote = typeof root === "string" ? Note.parse(root) : void 0;
2333
- const data = _chunk3R3QVKY5cjs.makeChord.call(void 0,
2428
+ const data = _chunkYDGMWH43cjs.makeChord.call(void 0,
2334
2429
  rootNote !== void 0 ? rootNote.pitchClass : root,
2335
2430
  quality,
2336
2431
  bassPc
@@ -2396,7 +2491,7 @@ var Chord = class _Chord {
2396
2491
  * ```
2397
2492
  */
2398
2493
  static fromFiguredBass(bass, figures, key) {
2399
- return new _Chord(_chunk76ZBTRG2cjs.realizeFiguredBass.call(void 0, _chunkS5BKZZGMcjs.toNoteData.call(void 0, bass), figures, key));
2494
+ return new _Chord(_chunkU4EQTDGNcjs.realizeFiguredBass.call(void 0, _chunkS3QELJUEcjs.toNoteData.call(void 0, bass), figures, key));
2400
2495
  }
2401
2496
  /**
2402
2497
  * Parse a lead-sheet chord symbol (e.g. `'Cmaj7'`, `'F#m7b5'`, `'C/G'`).
@@ -2419,7 +2514,7 @@ var Chord = class _Chord {
2419
2514
  * ```
2420
2515
  */
2421
2516
  static parse(symbol, opts) {
2422
- return _chunkS5BKZZGMcjs.unwrapParse.call(void 0, _Chord.tryParse(symbol, opts));
2517
+ return _chunkS3QELJUEcjs.unwrapParse.call(void 0, _Chord.tryParse(symbol, opts));
2423
2518
  }
2424
2519
  /**
2425
2520
  * Parse a lead-sheet chord symbol, reporting failure instead of throwing it.
@@ -2442,7 +2537,7 @@ var Chord = class _Chord {
2442
2537
  * ```
2443
2538
  */
2444
2539
  static tryParse(symbol, opts) {
2445
- const parsed = _chunk3R3QVKY5cjs.tryParseChordSymbol.call(void 0, symbol, opts);
2540
+ const parsed = _chunkYDGMWH43cjs.tryParseChordSymbol.call(void 0, symbol, opts);
2446
2541
  return parsed.ok ? { ok: true, value: new _Chord(parsed.value) } : parsed;
2447
2542
  }
2448
2543
  /**
@@ -2453,8 +2548,8 @@ var Chord = class _Chord {
2453
2548
  * @returns Ranked chord interpretations (may be empty).
2454
2549
  */
2455
2550
  static detect(pitches, opts) {
2456
- return _chunkIFZDWIKMcjs.detectChord.call(void 0, pitches, opts).map(
2457
- (match) => new _Chord(_chunk3R3QVKY5cjs.makeChord.call(void 0, match.rootPc, match.quality, match.bassPc))
2551
+ return _chunkLQZQDBCDcjs.detectChord.call(void 0, pitches, opts).map(
2552
+ (match) => new _Chord(_chunkYDGMWH43cjs.makeChord.call(void 0, match.rootPc, match.quality, match.bassPc))
2458
2553
  );
2459
2554
  }
2460
2555
  /**
@@ -2476,8 +2571,8 @@ var Chord = class _Chord {
2476
2571
  * ```
2477
2572
  */
2478
2573
  static detectMatches(pitches, opts) {
2479
- return _chunkIFZDWIKMcjs.detectChord.call(void 0, pitches, opts).map((match) => ({
2480
- chord: new _Chord(_chunk3R3QVKY5cjs.makeChord.call(void 0, match.rootPc, match.quality, match.bassPc)),
2574
+ return _chunkLQZQDBCDcjs.detectChord.call(void 0, pitches, opts).map((match) => ({
2575
+ chord: new _Chord(_chunkYDGMWH43cjs.makeChord.call(void 0, match.rootPc, match.quality, match.bassPc)),
2481
2576
  match
2482
2577
  }));
2483
2578
  }
@@ -2489,7 +2584,7 @@ var Chord = class _Chord {
2489
2584
  * @returns The top-ranked chord, or null when nothing matches.
2490
2585
  */
2491
2586
  static detectBest(pitches, opts) {
2492
- const best = _chunkIFZDWIKMcjs.detectChordBest.call(void 0, pitches, opts);
2587
+ const best = _chunkLQZQDBCDcjs.detectChordBest.call(void 0, pitches, opts);
2493
2588
  return best === null ? null : new _Chord(best);
2494
2589
  }
2495
2590
  /** The root pitch class (0..11). */
@@ -2533,7 +2628,7 @@ var Chord = class _Chord {
2533
2628
  * ```
2534
2629
  */
2535
2630
  get spec() {
2536
- return _chunk3R3QVKY5cjs.chordSpecOf.call(void 0, this.#data);
2631
+ return _chunkYDGMWH43cjs.chordSpecOf.call(void 0, this.#data);
2537
2632
  }
2538
2633
  /** The carried key context, if any. */
2539
2634
  get key() {
@@ -2571,7 +2666,7 @@ var Chord = class _Chord {
2571
2666
  * ```
2572
2667
  */
2573
2668
  pitchClasses(opts) {
2574
- return _chunk3R3QVKY5cjs.chordPitchClasses.call(void 0, this.#data, opts);
2669
+ return _chunkYDGMWH43cjs.chordPitchClasses.call(void 0, this.#data, opts);
2575
2670
  }
2576
2671
  /**
2577
2672
  * Whether a pitch is one of the chord's tones, ignoring octave.
@@ -2589,7 +2684,7 @@ var Chord = class _Chord {
2589
2684
  * ```
2590
2685
  */
2591
2686
  contains(pitch) {
2592
- return _chunk3R3QVKY5cjs.isChordMember.call(void 0, pitch, this.#data);
2687
+ return _chunkYDGMWH43cjs.isChordMember.call(void 0, pitch, this.#data);
2593
2688
  }
2594
2689
  /**
2595
2690
  * A pitch's harmonic role in the chord: root, third, fifth, sixth, or
@@ -2612,7 +2707,7 @@ var Chord = class _Chord {
2612
2707
  * ```
2613
2708
  */
2614
2709
  roleOf(pitch) {
2615
- return _chunk3R3QVKY5cjs.chordToneRole.call(void 0, pitch, this.#data);
2710
+ return _chunkYDGMWH43cjs.chordToneRole.call(void 0, pitch, this.#data);
2616
2711
  }
2617
2712
  /**
2618
2713
  * The chord's Roman numeral in a key.
@@ -2624,7 +2719,8 @@ var Chord = class _Chord {
2624
2719
  * @throws If no key is given and none is carried.
2625
2720
  */
2626
2721
  roman(key, opts) {
2627
- return _chunkIFZDWIKMcjs.chordToRoman.call(void 0, this.#data, this.#resolveKey(key), opts);
2722
+ const resolved = this.#resolveKey(key);
2723
+ return _chunkLQZQDBCDcjs.chordToRoman.call(void 0, this.#dataWithKey(resolved), resolved, opts);
2628
2724
  }
2629
2725
  /**
2630
2726
  * The chord's Roman numeral together with the reasoning behind it: the degree
@@ -2652,7 +2748,8 @@ var Chord = class _Chord {
2652
2748
  * ```
2653
2749
  */
2654
2750
  explain(key, opts) {
2655
- return _chunkIFZDWIKMcjs.explainRoman.call(void 0, this.#data, this.#resolveKey(key), opts);
2751
+ const resolved = this.#resolveKey(key);
2752
+ return _chunkLQZQDBCDcjs.explainRoman.call(void 0, this.#dataWithKey(resolved), resolved, opts);
2656
2753
  }
2657
2754
  /**
2658
2755
  * The chord's harmonic function (tonic / subdominant / dominant) in a key.
@@ -2663,7 +2760,8 @@ var Chord = class _Chord {
2663
2760
  * @throws If no key is given and none is carried.
2664
2761
  */
2665
2762
  function(key) {
2666
- return _chunkIFZDWIKMcjs.functionOf.call(void 0, this.#data, this.#resolveKey(key));
2763
+ const resolved = this.#resolveKey(key);
2764
+ return _chunkLQZQDBCDcjs.functionOf.call(void 0, this.#dataWithKey(resolved), resolved);
2667
2765
  }
2668
2766
  /**
2669
2767
  * Full functional analysis: function, borrowing, Roman numeral, and the
@@ -2683,7 +2781,8 @@ var Chord = class _Chord {
2683
2781
  * ```
2684
2782
  */
2685
2783
  analyze(key, opts) {
2686
- return _chunkIFZDWIKMcjs.analyzeChord.call(void 0, this.#data, this.#resolveKey(key), opts);
2784
+ const resolved = this.#resolveKey(key);
2785
+ return _chunkLQZQDBCDcjs.analyzeChord.call(void 0, this.#dataWithKey(resolved), resolved, opts);
2687
2786
  }
2688
2787
  /**
2689
2788
  * Whether the chord is borrowed from the parallel mode (modal interchange).
@@ -2694,7 +2793,8 @@ var Chord = class _Chord {
2694
2793
  * @throws If no key is given and none is carried.
2695
2794
  */
2696
2795
  isBorrowed(key) {
2697
- return _chunkIFZDWIKMcjs.isBorrowedChord.call(void 0, this.#data, this.#resolveKey(key));
2796
+ const resolved = this.#resolveKey(key);
2797
+ return _chunkLQZQDBCDcjs.isBorrowedChord.call(void 0, this.#dataWithKey(resolved), resolved);
2698
2798
  }
2699
2799
  /**
2700
2800
  * The origin of a non-diatonic chord (parallel mode or Neapolitan), or null.
@@ -2705,7 +2805,8 @@ var Chord = class _Chord {
2705
2805
  * @throws If no key is given and none is carried.
2706
2806
  */
2707
2807
  borrowedSource(key) {
2708
- return _chunkIFZDWIKMcjs.borrowedSource.call(void 0, this.#data, this.#resolveKey(key));
2808
+ const resolved = this.#resolveKey(key);
2809
+ return _chunkLQZQDBCDcjs.borrowedSource.call(void 0, this.#dataWithKey(resolved), resolved);
2709
2810
  }
2710
2811
  /**
2711
2812
  * The chord written as the figures a bass would carry under it: `6`, `64`,
@@ -2730,7 +2831,8 @@ var Chord = class _Chord {
2730
2831
  * ```
2731
2832
  */
2732
2833
  figuredBass(key) {
2733
- return _chunk76ZBTRG2cjs.figuredBassOf.call(void 0, this.#data, this.#resolveKey(key));
2834
+ const resolved = this.#resolveKey(key);
2835
+ return _chunkU4EQTDGNcjs.figuredBassOf.call(void 0, this.#dataWithKey(resolved), resolved);
2734
2836
  }
2735
2837
  /**
2736
2838
  * The chords that can stand in for this one in a key: its tritone substitute,
@@ -2757,7 +2859,8 @@ var Chord = class _Chord {
2757
2859
  * ```
2758
2860
  */
2759
2861
  substitutions(key, opts) {
2760
- return _chunkB2PW6EHNcjs.substituteChord.call(void 0, this.#data, this.#resolveKey(key), opts);
2862
+ const resolved = this.#resolveKey(key);
2863
+ return _chunk6TTBEON3cjs.substituteChord.call(void 0, this.#dataWithKey(resolved), resolved, opts);
2761
2864
  }
2762
2865
  /**
2763
2866
  * The modal-interchange palette of the chord's key: the parallel mode's
@@ -2782,7 +2885,7 @@ var Chord = class _Chord {
2782
2885
  * ```
2783
2886
  */
2784
2887
  modalInterchange(key) {
2785
- return _chunkB2PW6EHNcjs.modalInterchangePalette.call(void 0, this.#resolveKey(key));
2888
+ return _chunk6TTBEON3cjs.modalInterchangePalette.call(void 0, this.#resolveKey(key));
2786
2889
  }
2787
2890
  /**
2788
2891
  * The chord rendered as a lead-sheet symbol (e.g. `'Cmaj7'`, `'F#m7'`, `'C/G'`).
@@ -2797,7 +2900,7 @@ var Chord = class _Chord {
2797
2900
  * ```
2798
2901
  */
2799
2902
  symbol(opts) {
2800
- return _chunk3R3QVKY5cjs.formatChordSymbol.call(void 0, this.#data, opts);
2903
+ return _chunkYDGMWH43cjs.formatChordSymbol.call(void 0, this.#data, opts);
2801
2904
  }
2802
2905
  /**
2803
2906
  * Realize the chord as one MIDI pitch per voice, ascending.
@@ -2811,7 +2914,8 @@ var Chord = class _Chord {
2811
2914
  */
2812
2915
  voice(opts) {
2813
2916
  const key = _nullishCoalesce(_optionalChain([opts, 'optionalAccess', _24 => _24.key]), () => ( this.#key));
2814
- return _chunk76ZBTRG2cjs.voiceChord.call(void 0, this.#data, key === void 0 ? opts : { ...opts, key });
2917
+ const data = _optionalChain([opts, 'optionalAccess', _25 => _25.key]) === void 0 ? this.#data : this.#dataWithKey(toKey(opts.key));
2918
+ return _chunkU4EQTDGNcjs.voiceChord.call(void 0, data, key === void 0 ? opts : { ...opts, key });
2815
2919
  }
2816
2920
  /**
2817
2921
  * Realize the chord as a single styled voicing (`close`, `drop2`, `drop3`,
@@ -2821,7 +2925,7 @@ var Chord = class _Chord {
2821
2925
  * @returns MIDI pitches, ascending.
2822
2926
  */
2823
2927
  styledVoicing(opts) {
2824
- return _chunk76ZBTRG2cjs.voiceChordStyled.call(void 0, this.#data, opts);
2928
+ return _chunkU4EQTDGNcjs.voiceChordStyled.call(void 0, this.#data, opts);
2825
2929
  }
2826
2930
  /**
2827
2931
  * The negative-harmony mirror of the chord about the key's tonic–dominant
@@ -2834,7 +2938,7 @@ var Chord = class _Chord {
2834
2938
  */
2835
2939
  negativeHarmony(key) {
2836
2940
  const resolved = this.#resolveKey(key);
2837
- return new _Chord(_chunkB2PW6EHNcjs.negativeHarmonyMirror.call(void 0, this.#data, resolved), resolved);
2941
+ return new _Chord(_chunk6TTBEON3cjs.negativeHarmonyMirror.call(void 0, this.#dataWithKey(resolved), resolved), resolved);
2838
2942
  }
2839
2943
  /**
2840
2944
  * The V7 that tonicizes this chord: a dominant seventh a perfect fifth above
@@ -2852,7 +2956,7 @@ var Chord = class _Chord {
2852
2956
  * ```
2853
2957
  */
2854
2958
  secondaryDominant() {
2855
- return new _Chord(_chunkIFZDWIKMcjs.secondaryDominantOf.call(void 0, this.#given), this.#key);
2959
+ return new _Chord(_chunkLQZQDBCDcjs.secondaryDominantOf.call(void 0, this.#given), this.#key);
2856
2960
  }
2857
2961
  /**
2858
2962
  * The n-th inversion: a copy whose bass is the chord tone `n` steps above the
@@ -2871,14 +2975,14 @@ var Chord = class _Chord {
2871
2975
  const intervals = data.intervals;
2872
2976
  const length = intervals.length;
2873
2977
  if (length === 0) {
2874
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)("cannot invert a chord with no intervals");
2978
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)("cannot invert a chord with no intervals");
2875
2979
  }
2876
2980
  const index = (n % length + length) % length;
2877
2981
  delete data.bassSpelling;
2878
2982
  if (index === 0) {
2879
2983
  delete data.bassPc;
2880
2984
  } else {
2881
- data.bassPc = _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, data.rootPc + (_nullishCoalesce(intervals[index], () => ( 0))));
2985
+ data.bassPc = _chunkS3QELJUEcjs.pitchClassOf.call(void 0, data.rootPc + (_nullishCoalesce(intervals[index], () => ( 0))));
2882
2986
  }
2883
2987
  return new _Chord(data, this.#key);
2884
2988
  }
@@ -2899,8 +3003,8 @@ var Chord = class _Chord {
2899
3003
  * ```
2900
3004
  */
2901
3005
  transpose(semitones) {
2902
- const moved = _chunk3R3QVKY5cjs.transposeChord.call(void 0, this.#given, semitones);
2903
- const { rootSpelling, bassSpelling, toneSpellings } = _chunk3R3QVKY5cjs.transposeChordSpellings.call(void 0,
3006
+ const moved = _chunkYDGMWH43cjs.transposeChord.call(void 0, this.#given, semitones);
3007
+ const { rootSpelling, bassSpelling, toneSpellings } = _chunkYDGMWH43cjs.transposeChordSpellings.call(void 0,
2904
3008
  this.#given,
2905
3009
  semitones
2906
3010
  );
@@ -2913,7 +3017,7 @@ var Chord = class _Chord {
2913
3017
  if (toneSpellings !== void 0) {
2914
3018
  moved.toneSpellings = toneSpellings;
2915
3019
  }
2916
- return new _Chord(moved, _optionalChain([this, 'access', _25 => _25.#key, 'optionalAccess', _26 => _26.transpose, 'call', _27 => _27(semitones)]));
3020
+ return new _Chord(moved, _optionalChain([this, 'access', _26 => _26.#key, 'optionalAccess', _27 => _27.transpose, 'call', _28 => _28(semitones)]));
2917
3021
  }
2918
3022
  /**
2919
3023
  * Transpose the chord by a spelled interval.
@@ -2935,8 +3039,8 @@ var Chord = class _Chord {
2935
3039
  * ```
2936
3040
  */
2937
3041
  transposeBy(interval) {
2938
- const spelled = _chunkS5BKZZGMcjs.toSpelledInterval.call(void 0, interval);
2939
- const moved = _chunk3R3QVKY5cjs.transposeChord.call(void 0, this.#given, spelled.semitones);
3042
+ const spelled = _chunkS3QELJUEcjs.toSpelledInterval.call(void 0, interval);
3043
+ const moved = _chunkYDGMWH43cjs.transposeChord.call(void 0, this.#given, spelled.semitones);
2940
3044
  const rootSpelling = transposeHintByInterval(this.#given.rootSpelling, spelled);
2941
3045
  const bassSpelling = transposeHintByInterval(this.#given.bassSpelling, spelled);
2942
3046
  const toneSpellings = transposeToneHintsByInterval(this.#given.toneSpellings, spelled);
@@ -2949,7 +3053,7 @@ var Chord = class _Chord {
2949
3053
  if (toneSpellings !== void 0) {
2950
3054
  moved.toneSpellings = toneSpellings;
2951
3055
  }
2952
- return new _Chord(moved, _optionalChain([this, 'access', _28 => _28.#key, 'optionalAccess', _29 => _29.transposeBy, 'call', _30 => _30(spelled)]));
3056
+ return new _Chord(moved, _optionalChain([this, 'access', _29 => _29.#key, 'optionalAccess', _30 => _30.transposeBy, 'call', _31 => _31(spelled)]));
2953
3057
  }
2954
3058
  /**
2955
3059
  * The named scales that fit over this chord, best fit first, rooted on the
@@ -2962,7 +3066,7 @@ var Chord = class _Chord {
2962
3066
  * @returns The matching scales.
2963
3067
  */
2964
3068
  scales() {
2965
- return _chunkPM4XJE2Ycjs.chordScales.call(void 0, this.#data);
3069
+ return _chunkP3CPXAJ5cjs.chordScales.call(void 0, this.#data);
2966
3070
  }
2967
3071
  /**
2968
3072
  * The scales that fit over this chord, each with the tones it does not state
@@ -2984,7 +3088,7 @@ var Chord = class _Chord {
2984
3088
  * ```
2985
3089
  */
2986
3090
  scaleReport(limit) {
2987
- return _chunkPM4XJE2Ycjs.chordScaleReport.call(void 0, this.#data, limit);
3091
+ return _chunkP3CPXAJ5cjs.chordScaleReport.call(void 0, this.#data, limit);
2988
3092
  }
2989
3093
  /**
2990
3094
  * The available tensions (usable non-chord, non-avoid scale tones) of a
@@ -3009,7 +3113,7 @@ var Chord = class _Chord {
3009
3113
  * ```
3010
3114
  */
3011
3115
  tensions(scaleName, opts) {
3012
- return _chunkPM4XJE2Ycjs.availableTensions.call(void 0, this.#data, scaleName, opts);
3116
+ return _chunkP3CPXAJ5cjs.availableTensions.call(void 0, this.#data, scaleName, opts);
3013
3117
  }
3014
3118
  /**
3015
3119
  * The avoid notes (scale tones a semitone above a chord tone) of a scale
@@ -3033,7 +3137,7 @@ var Chord = class _Chord {
3033
3137
  * ```
3034
3138
  */
3035
3139
  avoidNotes(scaleName, opts) {
3036
- return _chunkPM4XJE2Ycjs.avoidNotes.call(void 0, this.#data, scaleName, opts);
3140
+ return _chunkP3CPXAJ5cjs.avoidNotes.call(void 0, this.#data, scaleName, opts);
3037
3141
  }
3038
3142
  /**
3039
3143
  * Spell the chord tones with letter names, root first, in the key's spelling.
@@ -3064,17 +3168,17 @@ var Chord = class _Chord {
3064
3168
  if (resolved === void 0) {
3065
3169
  const root = data.rootSpelling;
3066
3170
  if (root === void 0) {
3067
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
3171
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
3068
3172
  "chord has no key context and no root spelling; pass a Key, attach one with withKey(), or build the chord from a symbol"
3069
3173
  );
3070
3174
  }
3071
- tones = _chunk3R3QVKY5cjs.spellChordFromRoot.call(void 0, data, root);
3175
+ tones = _chunkYDGMWH43cjs.spellChordFromRoot.call(void 0, data, root);
3072
3176
  } else {
3073
- tones = _chunk3R3QVKY5cjs.spellChord.call(void 0, data, resolved.tonic.data, resolved);
3177
+ tones = _chunkYDGMWH43cjs.spellChord.call(void 0, data, resolved.tonic.data, resolved);
3074
3178
  }
3075
3179
  const bassPc = data.bassPc;
3076
3180
  const bass = data.bassSpelling;
3077
- if (bassPc !== void 0 && bass !== void 0 && !tones.some((tone) => _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, _chunkS5BKZZGMcjs.noteToPitchClass.call(void 0, tone)) === _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, bassPc))) {
3181
+ if (bassPc !== void 0 && bass !== void 0 && !tones.some((tone) => _chunkS3QELJUEcjs.pitchClassOf.call(void 0, _chunkS3QELJUEcjs.noteToPitchClass.call(void 0, tone)) === _chunkS3QELJUEcjs.pitchClassOf.call(void 0, bassPc))) {
3078
3182
  tones = [...tones, { letter: bass.letter, alter: bass.alter }];
3079
3183
  }
3080
3184
  return tones.map((note) => new Note(note));
@@ -3108,7 +3212,7 @@ var Chord = class _Chord {
3108
3212
  * ```
3109
3213
  */
3110
3214
  span(startBeat) {
3111
- return _chunk3R3QVKY5cjs.spanFromChord.call(void 0, this.#data, startBeat);
3215
+ return _chunkYDGMWH43cjs.spanFromChord.call(void 0, this.#data, startBeat);
3112
3216
  }
3113
3217
  /**
3114
3218
  * Whether another chord has the same root, quality, intervals, and bass.
@@ -3148,7 +3252,7 @@ var Chord = class _Chord {
3148
3252
  assertKeyArgument(key, "chord key");
3149
3253
  const resolved = key === void 0 ? this.#key : toKey(key);
3150
3254
  if (resolved === void 0) {
3151
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
3255
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
3152
3256
  "chord has no key context; pass a Key or attach one with withKey()"
3153
3257
  );
3154
3258
  }
@@ -3158,11 +3262,11 @@ var Chord = class _Chord {
3158
3262
 
3159
3263
  // src/model/key.ts
3160
3264
  function detectedKeyMatch(match) {
3161
- const key = { ..._chunk3R3QVKY5cjs.resolveKey.call(void 0, match.key), variant: match.variant };
3265
+ const key = { ..._chunkYDGMWH43cjs.resolveKey.call(void 0, match.key), variant: match.variant };
3162
3266
  return { ...match, key: toKey(key) };
3163
3267
  }
3164
3268
  function scaleWord(mask, isMinor) {
3165
- const name = _chunk3R3QVKY5cjs.scaleNameOfMask.call(void 0, mask);
3269
+ const name = _chunkYDGMWH43cjs.scaleNameOfMask.call(void 0, mask);
3166
3270
  if (name === void 0) {
3167
3271
  return isMinor ? "minor" : "major";
3168
3272
  }
@@ -3177,13 +3281,13 @@ function scaleWord(mask, isMinor) {
3177
3281
  var HEPTATONIC_DEGREES = 7;
3178
3282
  var REFERENCE_TONIC = { letter: 0, alter: 0 };
3179
3283
  function bareInterval(from, to) {
3180
- return _chunkS5BKZZGMcjs.spelledInterval.call(void 0,
3284
+ return _chunkS3QELJUEcjs.spelledInterval.call(void 0,
3181
3285
  { letter: from.letter, alter: from.alter },
3182
3286
  { letter: to.letter, alter: to.alter }
3183
3287
  );
3184
3288
  }
3185
3289
  function spelledTonicFor(scale) {
3186
- return new Note(_chunk3R3QVKY5cjs.resolveKey.call(void 0, scale).tonic);
3290
+ return new Note(_chunkYDGMWH43cjs.resolveKey.call(void 0, scale).tonic);
3187
3291
  }
3188
3292
  function isNoteInstance(value) {
3189
3293
  if (value === null || typeof value !== "object") {
@@ -3214,28 +3318,29 @@ var Key = class _Key {
3214
3318
  */
3215
3319
  constructor(scale, tonic, variant) {
3216
3320
  assertDataObject(scale, "scale");
3217
- _chunkS5BKZZGMcjs.assertInteger.call(void 0, scale.rootPc, "scale.rootPc");
3218
- _chunkS5BKZZGMcjs.assertInteger.call(void 0, scale.modeMask12, "scale.modeMask12", 1, 4095);
3321
+ _chunkS3QELJUEcjs.assertInteger.call(void 0, scale.rootPc, "scale.rootPc");
3322
+ _chunkS3QELJUEcjs.assertInteger.call(void 0, scale.modeMask12, "scale.modeMask12", 1, 4095);
3219
3323
  if ((scale.modeMask12 & 1) === 0) {
3220
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)("scale.modeMask12 must include the tonic (bit 0)");
3324
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)("scale.modeMask12 must include the tonic (bit 0)");
3221
3325
  }
3222
3326
  if (!isNoteInstance(tonic)) {
3223
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
3327
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
3224
3328
  `tonic must be the class API's Note; received ${describeTonic(tonic)}; wrap plain note data with Note.fromData, or omit the tonic to have one chosen`
3225
3329
  );
3226
3330
  }
3227
- const rootPc = _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, scale.rootPc);
3228
- if (tonic.pitchClass !== rootPc) {
3229
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
3230
- `tonic ${tonic.name} does not match the scale root pitch class ${rootPc}; pass a tonic that spells the scale root, or omit it to have one chosen`
3331
+ const note = tonic instanceof Note ? tonic : new Note(tonic.data);
3332
+ const rootPc = _chunkS3QELJUEcjs.pitchClassOf.call(void 0, scale.rootPc);
3333
+ if (note.pitchClass !== rootPc) {
3334
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
3335
+ `tonic ${note.name} does not match the scale root pitch class ${rootPc}; pass a tonic that spells the scale root, or omit it to have one chosen`
3231
3336
  );
3232
3337
  }
3233
3338
  if (variant !== void 0) {
3234
- _chunk3R3QVKY5cjs.assertKeyVariant.call(void 0, variant, scale.modeMask12);
3339
+ _chunkYDGMWH43cjs.assertKeyVariant.call(void 0, variant, scale.modeMask12);
3235
3340
  }
3236
3341
  this.#scale = { rootPc, modeMask12: scale.modeMask12 };
3237
- this.#tonic = tonic;
3238
- this.#variant = _nullishCoalesce(variant, () => ( _chunk3R3QVKY5cjs.variantOfMask.call(void 0, scale.modeMask12)));
3342
+ this.#tonic = note;
3343
+ this.#variant = _nullishCoalesce(variant, () => ( _chunkYDGMWH43cjs.variantOfMask.call(void 0, scale.modeMask12)));
3239
3344
  }
3240
3345
  /** Preserve detection metadata while replacing its plain key with this API's Key. */
3241
3346
  static #fromMatch(match) {
@@ -3262,9 +3367,9 @@ var Key = class _Key {
3262
3367
  static major(root) {
3263
3368
  if (typeof root === "string") {
3264
3369
  const tonic = Note.parse(root);
3265
- return new _Key(_chunk3R3QVKY5cjs.majorKey.call(void 0, tonic.pitchClass), tonic);
3370
+ return new _Key(_chunkYDGMWH43cjs.majorKey.call(void 0, tonic.pitchClass), tonic);
3266
3371
  }
3267
- const scale = _chunk3R3QVKY5cjs.majorKey.call(void 0, root);
3372
+ const scale = _chunkYDGMWH43cjs.majorKey.call(void 0, root);
3268
3373
  return new _Key(scale, spelledTonicFor(scale));
3269
3374
  }
3270
3375
  /**
@@ -3278,9 +3383,9 @@ var Key = class _Key {
3278
3383
  static minor(root) {
3279
3384
  if (typeof root === "string") {
3280
3385
  const tonic = Note.parse(root);
3281
- return new _Key(_chunk3R3QVKY5cjs.minorKey.call(void 0, tonic.pitchClass), tonic);
3386
+ return new _Key(_chunkYDGMWH43cjs.minorKey.call(void 0, tonic.pitchClass), tonic);
3282
3387
  }
3283
- const scale = _chunk3R3QVKY5cjs.minorKey.call(void 0, root);
3388
+ const scale = _chunkYDGMWH43cjs.minorKey.call(void 0, root);
3284
3389
  return new _Key(scale, spelledTonicFor(scale));
3285
3390
  }
3286
3391
  /**
@@ -3296,9 +3401,9 @@ var Key = class _Key {
3296
3401
  static named(name, root) {
3297
3402
  if (typeof root === "string") {
3298
3403
  const tonic = Note.parse(root);
3299
- return new _Key(_chunk3R3QVKY5cjs.scaleByName.call(void 0, name, tonic.pitchClass), tonic);
3404
+ return new _Key(_chunkYDGMWH43cjs.scaleByName.call(void 0, name, tonic.pitchClass), tonic);
3300
3405
  }
3301
- const scale = _chunk3R3QVKY5cjs.scaleByName.call(void 0, name, _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, root));
3406
+ const scale = _chunkYDGMWH43cjs.scaleByName.call(void 0, name, _chunkS3QELJUEcjs.pitchClassOf.call(void 0, root));
3302
3407
  return new _Key(scale, spelledTonicFor(scale));
3303
3408
  }
3304
3409
  /**
@@ -3333,7 +3438,7 @@ var Key = class _Key {
3333
3438
  * ```
3334
3439
  */
3335
3440
  static parse(text, opts) {
3336
- return _chunkS5BKZZGMcjs.unwrapParse.call(void 0, _Key.tryParse(text, opts));
3441
+ return _chunkS3QELJUEcjs.unwrapParse.call(void 0, _Key.tryParse(text, opts));
3337
3442
  }
3338
3443
  /**
3339
3444
  * Parse a key name, reporting failure instead of throwing it.
@@ -3355,7 +3460,7 @@ var Key = class _Key {
3355
3460
  * ```
3356
3461
  */
3357
3462
  static tryParse(text, opts) {
3358
- const parsed = _chunk3R3QVKY5cjs.tryResolveKeyName.call(void 0, text, opts);
3463
+ const parsed = _chunkYDGMWH43cjs.tryResolveKeyName.call(void 0, text, opts);
3359
3464
  return parsed.ok ? {
3360
3465
  ok: true,
3361
3466
  value: new _Key(parsed.value.scale, new Note(parsed.value.tonic), parsed.value.variant)
@@ -3382,7 +3487,7 @@ var Key = class _Key {
3382
3487
  * ```
3383
3488
  */
3384
3489
  static fromFifths(fifths, mode = "major") {
3385
- return _Key.#fromSpelled(_chunk3R3QVKY5cjs.keyFromFifths.call(void 0, fifths, mode));
3490
+ return _Key.#fromSpelled(_chunkYDGMWH43cjs.keyFromFifths.call(void 0, fifths, mode));
3386
3491
  }
3387
3492
  /**
3388
3493
  * Wrap an existing `KeyScale`, synthesizing a spelled tonic when none is
@@ -3405,7 +3510,7 @@ var Key = class _Key {
3405
3510
  * @throws If the given tonic is not the scale's root pitch class.
3406
3511
  */
3407
3512
  static of(key, tonic) {
3408
- const resolved = _chunk3R3QVKY5cjs.resolveKey.call(void 0, key);
3513
+ const resolved = _chunkYDGMWH43cjs.resolveKey.call(void 0, key);
3409
3514
  return new _Key(resolved.scale, _nullishCoalesce(tonic, () => ( new Note(resolved.tonic))), resolved.variant);
3410
3515
  }
3411
3516
  /**
@@ -3447,7 +3552,7 @@ var Key = class _Key {
3447
3552
  * @returns Ranked key matches (may be empty).
3448
3553
  */
3449
3554
  static detectMatches(pitches, opts) {
3450
- return _chunkIFZDWIKMcjs.detectKey.call(void 0, pitches, opts).map((match) => _Key.#fromMatch(match));
3555
+ return _chunkLQZQDBCDcjs.detectKey.call(void 0, pitches, opts).map((match) => _Key.#fromMatch(match));
3451
3556
  }
3452
3557
  /**
3453
3558
  * The single best key interpretation of a pitch set.
@@ -3462,7 +3567,7 @@ var Key = class _Key {
3462
3567
  * ```
3463
3568
  */
3464
3569
  static detectBest(pitches, opts) {
3465
- const best = _chunkIFZDWIKMcjs.detectKeyBest.call(void 0, pitches, opts);
3570
+ const best = _chunkLQZQDBCDcjs.detectKeyBest.call(void 0, pitches, opts);
3466
3571
  return best === null ? null : _Key.#fromMatch(best).key;
3467
3572
  }
3468
3573
  /**
@@ -3492,7 +3597,7 @@ var Key = class _Key {
3492
3597
  }
3493
3598
  /** Whether the scale has a minor third and no major third. */
3494
3599
  get isMinor() {
3495
- return _chunkIFZDWIKMcjs.isMinorKey.call(void 0, this.#scale);
3600
+ return _chunkLQZQDBCDcjs.isMinorKey.call(void 0, this.#scale);
3496
3601
  }
3497
3602
  /**
3498
3603
  * The key signature as a signed count of sharps (positive) or flats
@@ -3510,7 +3615,7 @@ var Key = class _Key {
3510
3615
  * ```
3511
3616
  */
3512
3617
  get fifths() {
3513
- return _chunk3R3QVKY5cjs.keySignatureFifths.call(void 0, this.#tonic.data, this.#scale);
3618
+ return _chunkYDGMWH43cjs.keySignatureFifths.call(void 0, this.#tonic.data, this.#scale);
3514
3619
  }
3515
3620
  /**
3516
3621
  * The built-in scale this key's mode mask is, or undefined when no built-in
@@ -3534,13 +3639,13 @@ var Key = class _Key {
3534
3639
  */
3535
3640
  get scaleName() {
3536
3641
  const mask = this.#scale.modeMask12;
3537
- return Object.keys(_chunk3R3QVKY5cjs.NAMED_SCALES).find((name) => _chunk3R3QVKY5cjs.NAMED_SCALES[name] === mask);
3642
+ return Object.keys(_chunkYDGMWH43cjs.NAMED_SCALES).find((name) => _chunkYDGMWH43cjs.NAMED_SCALES[name] === mask);
3538
3643
  }
3539
3644
  /** A copy of the underlying plain key data. */
3540
3645
  get data() {
3541
3646
  return this.toJSON();
3542
3647
  }
3543
- /** The detected scale form, when this key came from key detection. */
3648
+ /** The scale form this key stands in: natural, harmonic or melodic, read from the mask unless named. */
3544
3649
  get variant() {
3545
3650
  return this.#variant;
3546
3651
  }
@@ -3566,8 +3671,8 @@ var Key = class _Key {
3566
3671
  * ```
3567
3672
  */
3568
3673
  pitchClasses(opts) {
3569
- const order = _optionalChain([opts, 'optionalAccess', _31 => _31.order]) === void 0 ? "degree" : _chunkS5BKZZGMcjs.assertOneOf.call(void 0, opts.order, ["degree", "ascending"], "pitch-class order");
3570
- return order === "ascending" ? _chunk3R3QVKY5cjs.diatonicPitchClasses.call(void 0, this.#scale) : _chunk3R3QVKY5cjs.scaleTonesInDegreeOrder.call(void 0, this.#scale);
3674
+ const order = _optionalChain([opts, 'optionalAccess', _32 => _32.order]) === void 0 ? "degree" : _chunkS3QELJUEcjs.assertOneOf.call(void 0, opts.order, ["degree", "ascending"], "pitch-class order");
3675
+ return order === "ascending" ? _chunkYDGMWH43cjs.diatonicPitchClasses.call(void 0, this.#scale) : _chunkYDGMWH43cjs.scaleTonesInDegreeOrder.call(void 0, this.#scale);
3571
3676
  }
3572
3677
  /**
3573
3678
  * The kind of pitch organisation this key's scale belongs to: the
@@ -3591,7 +3696,7 @@ var Key = class _Key {
3591
3696
  * ```
3592
3697
  */
3593
3698
  system() {
3594
- return _chunk3R3QVKY5cjs.scaleSystemOf.call(void 0, this.#scale);
3699
+ return _chunkYDGMWH43cjs.scaleSystemOf.call(void 0, this.#scale);
3595
3700
  }
3596
3701
  /**
3597
3702
  * Whether functional (Roman-numeral) analysis describes this key.
@@ -3611,7 +3716,7 @@ var Key = class _Key {
3611
3716
  * ```
3612
3717
  */
3613
3718
  supportsFunctionalHarmony() {
3614
- return _chunk3R3QVKY5cjs.supportsFunctionalHarmony.call(void 0, this.#scale);
3719
+ return _chunkYDGMWH43cjs.supportsFunctionalHarmony.call(void 0, this.#scale);
3615
3720
  }
3616
3721
  /**
3617
3722
  * The relative key: for a plain major or minor key, the same key signature
@@ -3635,7 +3740,7 @@ var Key = class _Key {
3635
3740
  * ```
3636
3741
  */
3637
3742
  relative() {
3638
- return _Key.#fromSpelled(_chunk3R3QVKY5cjs.relativeKeyOf.call(void 0, this.#tonic.data, this.#scale));
3743
+ return _Key.#fromSpelled(_chunkYDGMWH43cjs.relativeKeyOf.call(void 0, this.#tonic.data, this.#scale));
3639
3744
  }
3640
3745
  /**
3641
3746
  * The parallel key: the other mode on the same tonic, which keeps this key's
@@ -3649,7 +3754,7 @@ var Key = class _Key {
3649
3754
  * ```
3650
3755
  */
3651
3756
  parallel() {
3652
- return _Key.#fromSpelled(_chunk3R3QVKY5cjs.parallelKeyOf.call(void 0, this.#tonic.data, this.#scale));
3757
+ return _Key.#fromSpelled(_chunkYDGMWH43cjs.parallelKeyOf.call(void 0, this.#tonic.data, this.#scale));
3653
3758
  }
3654
3759
  /**
3655
3760
  * The dominant key: the key a fifth above, in the mode this key's third names.
@@ -3666,7 +3771,7 @@ var Key = class _Key {
3666
3771
  * ```
3667
3772
  */
3668
3773
  dominantKey() {
3669
- return _Key.#fromSpelled(_chunk3R3QVKY5cjs.dominantKeyOf.call(void 0, this.#tonic.data, this.#scale));
3774
+ return _Key.#fromSpelled(_chunkYDGMWH43cjs.dominantKeyOf.call(void 0, this.#tonic.data, this.#scale));
3670
3775
  }
3671
3776
  /**
3672
3777
  * The subdominant key: the key a fifth below, in the mode this key's third
@@ -3682,7 +3787,7 @@ var Key = class _Key {
3682
3787
  * ```
3683
3788
  */
3684
3789
  subdominantKey() {
3685
- return _Key.#fromSpelled(_chunk3R3QVKY5cjs.subdominantKeyOf.call(void 0, this.#tonic.data, this.#scale));
3790
+ return _Key.#fromSpelled(_chunkYDGMWH43cjs.subdominantKeyOf.call(void 0, this.#tonic.data, this.#scale));
3686
3791
  }
3687
3792
  /**
3688
3793
  * The same sounding key written the other way round the circle of fifths.
@@ -3700,7 +3805,7 @@ var Key = class _Key {
3700
3805
  * ```
3701
3806
  */
3702
3807
  enharmonic() {
3703
- const other = _chunk3R3QVKY5cjs.enharmonicKeyOf.call(void 0, this.#tonic.data, this.#scale);
3808
+ const other = _chunkYDGMWH43cjs.enharmonicKeyOf.call(void 0, this.#tonic.data, this.#scale);
3704
3809
  return other === null ? null : _Key.#fromSpelled(other);
3705
3810
  }
3706
3811
  /**
@@ -3731,7 +3836,7 @@ var Key = class _Key {
3731
3836
  * ```
3732
3837
  */
3733
3838
  relatedKeys() {
3734
- return _chunk3R3QVKY5cjs.relatedKeysOf.call(void 0, this.#tonic.data, this.#scale).map(({ relation, ...spelled }) => ({
3839
+ return _chunkYDGMWH43cjs.relatedKeysOf.call(void 0, this.#tonic.data, this.#scale).map(({ relation, ...spelled }) => ({
3735
3840
  relation,
3736
3841
  key: _Key.#fromSpelled(spelled)
3737
3842
  }));
@@ -3758,7 +3863,7 @@ var Key = class _Key {
3758
3863
  * ```
3759
3864
  */
3760
3865
  relationTo(other) {
3761
- return _chunk3R3QVKY5cjs.keyRelationBetween.call(void 0, this.toJSON(), other.toJSON());
3866
+ return _chunkYDGMWH43cjs.keyRelationBetween.call(void 0, this.toJSON(), other.toJSON());
3762
3867
  }
3763
3868
  /**
3764
3869
  * The chords a modulation from this key into another can pivot on.
@@ -3785,7 +3890,7 @@ var Key = class _Key {
3785
3890
  */
3786
3891
  pivotsTo(other) {
3787
3892
  assertKeyArgument(other, "key");
3788
- return _chunkIFZDWIKMcjs.pivotChords.call(void 0, this.#scale, other).map(({ chord, romanFrom, romanTo }) => ({
3893
+ return _chunkLQZQDBCDcjs.pivotChords.call(void 0, this, _chunkYDGMWH43cjs.resolveKey.call(void 0, other)).map(({ chord, romanFrom, romanTo }) => ({
3789
3894
  chord: new Chord(chord, this),
3790
3895
  romanFrom,
3791
3896
  romanTo
@@ -3807,7 +3912,7 @@ var Key = class _Key {
3807
3912
  */
3808
3913
  degree(n) {
3809
3914
  const notes = this.notes();
3810
- _chunkS5BKZZGMcjs.assertInteger.call(void 0, n, "degree", 1, notes.length);
3915
+ _chunkS3QELJUEcjs.assertInteger.call(void 0, n, "degree", 1, notes.length);
3811
3916
  return _nullishCoalesce(notes[n - 1], () => ( this.#tonic));
3812
3917
  }
3813
3918
  /**
@@ -3858,12 +3963,12 @@ var Key = class _Key {
3858
3963
  */
3859
3964
  keyHavingTonicAsDegree(n, mode) {
3860
3965
  const resolved = _nullishCoalesce(mode, () => ( (this.isMinor ? "minor" : "major")));
3861
- const reference = _chunk3R3QVKY5cjs.spellScale.call(void 0, REFERENCE_TONIC, resolved === "minor" ? _chunk3R3QVKY5cjs.minorKey.call(void 0, 0) : _chunk3R3QVKY5cjs.majorKey.call(void 0, 0));
3862
- _chunkS5BKZZGMcjs.assertInteger.call(void 0, n, "degree", 1, reference.length);
3966
+ const reference = _chunkYDGMWH43cjs.spellScale.call(void 0, REFERENCE_TONIC, resolved === "minor" ? _chunkYDGMWH43cjs.minorKey.call(void 0, 0) : _chunkYDGMWH43cjs.majorKey.call(void 0, 0));
3967
+ _chunkS3QELJUEcjs.assertInteger.call(void 0, n, "degree", 1, reference.length);
3863
3968
  const first = reference[0];
3864
- const step = _chunkS5BKZZGMcjs.spelledInterval.call(void 0, first, reference[n - 1]);
3969
+ const step = _chunkS3QELJUEcjs.spelledInterval.call(void 0, first, reference[n - 1]);
3865
3970
  const tonic = new Note(
3866
- _chunkS5BKZZGMcjs.transposeByInterval.call(void 0, this.#tonic.data, {
3971
+ _chunkS3QELJUEcjs.transposeByInterval.call(void 0, this.#tonic.data, {
3867
3972
  number: step.number,
3868
3973
  quality: step.quality,
3869
3974
  // Negating a zero span yields -0, which compares unequal to 0.
@@ -3883,7 +3988,7 @@ var Key = class _Key {
3883
3988
  */
3884
3989
  static #modeOn(mode, tonic) {
3885
3990
  const rootPc = tonic.pitchClass;
3886
- return new _Key(mode === "minor" ? _chunk3R3QVKY5cjs.minorKey.call(void 0, rootPc) : _chunk3R3QVKY5cjs.majorKey.call(void 0, rootPc), tonic).#asWritten();
3991
+ return new _Key(mode === "minor" ? _chunkYDGMWH43cjs.minorKey.call(void 0, rootPc) : _chunkYDGMWH43cjs.majorKey.call(void 0, rootPc), tonic).#asWritten();
3887
3992
  }
3888
3993
  /**
3889
3994
  * The mode a scale degree implies, read off its diatonic triad. Scales that
@@ -3894,7 +3999,7 @@ var Key = class _Key {
3894
3999
  if (this.pitchClasses().length !== HEPTATONIC_DEGREES) {
3895
4000
  return this.isMinor ? "minor" : "major";
3896
4001
  }
3897
- const { quality } = _chunk3R3QVKY5cjs.diatonicTriad.call(void 0, n, this.#scale);
4002
+ const { quality } = _chunkYDGMWH43cjs.diatonicTriad.call(void 0, n, this);
3898
4003
  return quality === "min" || quality === "dim" ? "minor" : "major";
3899
4004
  }
3900
4005
  /**
@@ -3903,7 +4008,7 @@ var Key = class _Key {
3903
4008
  *
3904
4009
  * Unlike {@link Key.transpose}, which picks a letter from the semitone count,
3905
4010
  * the interval's diatonic number decides the tonic's letter: G# minor down an
3906
- * augmented fourth is D minor, while down a diminished fifth it is Dbb minor.
4011
+ * augmented fourth is D minor, while down a diminished fifth it is C## minor.
3907
4012
  * The mode mask is unchanged, so the scale keeps its shape.
3908
4013
  *
3909
4014
  * @param interval The interval to apply, as a name (`'A4'`, `'-A4'`), plain
@@ -3918,10 +4023,10 @@ var Key = class _Key {
3918
4023
  * ```
3919
4024
  */
3920
4025
  transposeBy(interval) {
3921
- const step = _chunkS5BKZZGMcjs.toSpelledInterval.call(void 0, interval);
4026
+ const step = _chunkS3QELJUEcjs.toSpelledInterval.call(void 0, interval);
3922
4027
  return new _Key(
3923
- { rootPc: _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, this.#scale.rootPc + step.semitones), modeMask12: this.#scale.modeMask12 },
3924
- new Note(_chunkS5BKZZGMcjs.transposeByInterval.call(void 0, this.#tonic.data, step)),
4028
+ { rootPc: _chunkS3QELJUEcjs.pitchClassOf.call(void 0, this.#scale.rootPc + step.semitones), modeMask12: this.#scale.modeMask12 },
4029
+ new Note(_chunkS3QELJUEcjs.transposeByInterval.call(void 0, this.#tonic.data, step)),
3925
4030
  this.#variant
3926
4031
  );
3927
4032
  }
@@ -3969,8 +4074,8 @@ var Key = class _Key {
3969
4074
  * ```
3970
4075
  */
3971
4076
  transpose(semitones) {
3972
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, semitones, "semitones");
3973
- const rootPc = _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, this.#scale.rootPc + Math.round(semitones));
4077
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, semitones, "semitones");
4078
+ const rootPc = _chunkS3QELJUEcjs.pitchClassOf.call(void 0, this.#scale.rootPc + Math.round(semitones));
3974
4079
  const scale = { rootPc, modeMask12: this.#scale.modeMask12 };
3975
4080
  return new _Key(scale, this.#tonic.transpose(semitones), this.#variant).#asWritten();
3976
4081
  }
@@ -3994,9 +4099,9 @@ var Key = class _Key {
3994
4099
  if (this.#isWritten()) {
3995
4100
  return this;
3996
4101
  }
3997
- const other = _chunk3R3QVKY5cjs.enharmonicKeyOf.call(void 0, this.#tonic.data, this.#scale);
4102
+ const other = _chunkYDGMWH43cjs.enharmonicKeyOf.call(void 0, this.#tonic.data, this.#scale);
3998
4103
  const respelled = other === null ? null : new Note(other.tonic);
3999
- return respelled === null || respelled.pitchClass !== _chunkS5BKZZGMcjs.pitchClassOf.call(void 0, this.#scale.rootPc) ? this : new _Key(this.#scale, respelled, this.#variant);
4104
+ return respelled === null || respelled.pitchClass !== _chunkS3QELJUEcjs.pitchClassOf.call(void 0, this.#scale.rootPc) ? this : new _Key(this.#scale, respelled, this.#variant);
4000
4105
  }
4001
4106
  /**
4002
4107
  * Whether this key is spelled the way keys are actually written, which is
@@ -4010,7 +4115,7 @@ var Key = class _Key {
4010
4115
  * drawn from the mode itself disagree.
4011
4116
  */
4012
4117
  #isWritten() {
4013
- return _chunk3R3QVKY5cjs.isWrittenTonic.call(void 0, this.#tonic.data, this.#scale);
4118
+ return _chunkYDGMWH43cjs.isWrittenTonic.call(void 0, this.#tonic.data, this.#scale);
4014
4119
  }
4015
4120
  /**
4016
4121
  * The key a transposing instrument's part is written in, for this key at
@@ -4046,7 +4151,7 @@ var Key = class _Key {
4046
4151
  * ```
4047
4152
  */
4048
4153
  forInstrument(instrument) {
4049
- const tonic = new Note(_chunk76ZBTRG2cjs.toWrittenPitch.call(void 0, this.#tonic.data, instrument));
4154
+ const tonic = new Note(_chunkU4EQTDGNcjs.toWrittenPitch.call(void 0, this.#tonic.data, instrument));
4050
4155
  return new _Key(
4051
4156
  { rootPc: tonic.pitchClass, modeMask12: this.#scale.modeMask12 },
4052
4157
  tonic,
@@ -4059,7 +4164,7 @@ var Key = class _Key {
4059
4164
  * @returns Spelled octave-less notes in scale-degree order.
4060
4165
  */
4061
4166
  notes() {
4062
- return _chunk3R3QVKY5cjs.spellScale.call(void 0, this.#tonic.data, this.#scale).map((note) => new Note(note));
4167
+ return _chunkYDGMWH43cjs.spellScale.call(void 0, this.#tonic.data, this.#scale).map((note) => new Note(note));
4063
4168
  }
4064
4169
  /**
4065
4170
  * Alias of {@link Key.notes}.
@@ -4113,8 +4218,17 @@ var Key = class _Key {
4113
4218
  * ```
4114
4219
  */
4115
4220
  spellPitchClasses(pcs, tonic) {
4116
- const anchor = tonic === void 0 ? this.#tonic.data : _chunkS5BKZZGMcjs.toNoteData.call(void 0, tonic);
4117
- return _chunk3R3QVKY5cjs.spellPitchClasses.call(void 0, [...pcs], anchor, this.#scale).map((note) => new Note(note));
4221
+ const anchor = tonic === void 0 ? this.#tonic.data : _chunkS3QELJUEcjs.toNoteData.call(void 0, tonic);
4222
+ return _chunkYDGMWH43cjs.spellPitchClasses.call(void 0, [...pcs], anchor, this.#scale).map((note) => new Note(note));
4223
+ }
4224
+ /**
4225
+ * A degree chord without the spelling its builder attached.
4226
+ *
4227
+ * The chord carries this key, which spells its root on read, so a chord
4228
+ * re-keyed later follows its new key instead of keeping these letters.
4229
+ */
4230
+ #withoutSpelling(chord) {
4231
+ return _chunkYDGMWH43cjs.makeChord.call(void 0, chord.rootPc, chord.quality);
4118
4232
  }
4119
4233
  /**
4120
4234
  * Build a chord on a scale degree, carrying this key as context.
@@ -4133,8 +4247,8 @@ var Key = class _Key {
4133
4247
  * an explicit `quality` for those.
4134
4248
  */
4135
4249
  chord(degree, quality) {
4136
- const data = quality === void 0 ? _chunk3R3QVKY5cjs.diatonicTriad.call(void 0, degree, this.#scale) : _chunk3R3QVKY5cjs.chordFromDegree.call(void 0, degree, quality, this.#scale);
4137
- return new Chord(data, this);
4250
+ const data = quality === void 0 ? _chunkYDGMWH43cjs.diatonicTriad.call(void 0, degree, this) : _chunkYDGMWH43cjs.chordFromDegree.call(void 0, degree, quality, this);
4251
+ return new Chord(this.#withoutSpelling(data), this);
4138
4252
  }
4139
4253
  /**
4140
4254
  * The diatonic triad on a scale degree, carrying this key as context.
@@ -4146,7 +4260,7 @@ var Key = class _Key {
4146
4260
  * degrees. Use {@link Key.chord} with an explicit quality instead.
4147
4261
  */
4148
4262
  diatonicTriad(degree) {
4149
- return new Chord(_chunk3R3QVKY5cjs.diatonicTriad.call(void 0, degree, this.#scale), this);
4263
+ return new Chord(this.#withoutSpelling(_chunkYDGMWH43cjs.diatonicTriad.call(void 0, degree, this)), this);
4150
4264
  }
4151
4265
  /**
4152
4266
  * The diatonic seventh chord on a scale degree, carrying this key as context.
@@ -4158,7 +4272,7 @@ var Key = class _Key {
4158
4272
  * degrees. Use {@link Key.chord} with an explicit quality instead.
4159
4273
  */
4160
4274
  diatonicSeventh(degree) {
4161
- return new Chord(_chunk3R3QVKY5cjs.diatonicSeventh.call(void 0, degree, this.#scale), this);
4275
+ return new Chord(this.#withoutSpelling(_chunkYDGMWH43cjs.diatonicSeventh.call(void 0, degree, this)), this);
4162
4276
  }
4163
4277
  /**
4164
4278
  * Build the chord denoted by a Roman numeral in this key (including applied
@@ -4169,7 +4283,7 @@ var Key = class _Key {
4169
4283
  * @throws If the numeral is not valid.
4170
4284
  */
4171
4285
  roman(text) {
4172
- return new Chord(_chunkIFZDWIKMcjs.romanToChord.call(void 0, text, this), this);
4286
+ return new Chord(_chunkLQZQDBCDcjs.romanToChord.call(void 0, text, this), this);
4173
4287
  }
4174
4288
  /**
4175
4289
  * The augmented sixth chord of a kind, built in this key.
@@ -4190,7 +4304,7 @@ var Key = class _Key {
4190
4304
  * ```
4191
4305
  */
4192
4306
  augmentedSixth(kind) {
4193
- return new Chord(_chunkIFZDWIKMcjs.augmentedSixthChord.call(void 0, kind, keyIdentity(this)), this);
4307
+ return new Chord(_chunkLQZQDBCDcjs.augmentedSixthChord.call(void 0, kind, keyIdentity(this)), this);
4194
4308
  }
4195
4309
  /**
4196
4310
  * Build a progression from Roman numerals in this key.
@@ -4223,7 +4337,7 @@ var Key = class _Key {
4223
4337
  * @returns True if the pitch class is a scale tone.
4224
4338
  */
4225
4339
  contains(x) {
4226
- return _chunk3R3QVKY5cjs.isScaleTone.call(void 0, typeof x === "number" ? x : x.pitchClass, this.#scale);
4340
+ return _chunkYDGMWH43cjs.isScaleTone.call(void 0, typeof x === "number" ? x : x.pitchClass, this.#scale);
4227
4341
  }
4228
4342
  /**
4229
4343
  * The nearest MIDI pitch whose pitch class is in the scale.
@@ -4242,7 +4356,7 @@ var Key = class _Key {
4242
4356
  * ```
4243
4357
  */
4244
4358
  nearestTone(pitch) {
4245
- return _chunk3R3QVKY5cjs.nearestScaleTone.call(void 0, pitch, this.#scale);
4359
+ return _chunkYDGMWH43cjs.nearestScaleTone.call(void 0, pitch, this.#scale);
4246
4360
  }
4247
4361
  /**
4248
4362
  * The scale degree a pitch sits on, counted from 1: the tonic is degree 1.
@@ -4260,7 +4374,7 @@ var Key = class _Key {
4260
4374
  * ```
4261
4375
  */
4262
4376
  degreeOf(pitch) {
4263
- const degree = _chunk3R3QVKY5cjs.pitchToScaleDegree.call(void 0, pitch, this.#scale);
4377
+ const degree = _chunkYDGMWH43cjs.pitchToScaleDegree.call(void 0, pitch, this.#scale);
4264
4378
  return degree === -1 ? null : degree;
4265
4379
  }
4266
4380
  /**
@@ -4268,12 +4382,11 @@ var Key = class _Key {
4268
4382
  *
4269
4383
  * Private class fields do not serialize, so an explicit `toJSON` keeps
4270
4384
  * `JSON.stringify(key)` from collapsing to `{}`. The result pairs the
4271
- * `KeyScale` with the spelled tonic and, for a detected harmonic or melodic
4272
- * minor, the scale form — everything {@link Key.fromJSON} needs to rebuild a
4273
- * key that reads and prints as this one.
4385
+ * `KeyScale` with the spelled tonic and the scale form — everything
4386
+ * {@link Key.fromJSON} needs to rebuild a key that reads and prints as this
4387
+ * one.
4274
4388
  *
4275
- * @returns The key/scale, its spelled tonic, and its scale form when it has
4276
- * one.
4389
+ * @returns The key/scale, its spelled tonic, and its scale form.
4277
4390
  */
4278
4391
  toJSON() {
4279
4392
  return { scale: this.scale, tonic: this.#tonic.data, variant: this.#variant };
@@ -4306,8 +4419,8 @@ var Key = class _Key {
4306
4419
  * ```
4307
4420
  */
4308
4421
  toString(opts) {
4309
- if (_optionalChain([opts, 'optionalAccess', _32 => _32.system]) !== void 0 && opts.system !== "english") {
4310
- return _chunkS5BKZZGMcjs.formatKeyName.call(void 0,
4422
+ if (_optionalChain([opts, 'optionalAccess', _33 => _33.system]) !== void 0 && opts.system !== "english") {
4423
+ return _chunkS3QELJUEcjs.formatKeyName.call(void 0,
4311
4424
  { tonic: this.#tonic.data, mode: this.isMinor ? "minor" : "major" },
4312
4425
  opts
4313
4426
  );
@@ -4324,13 +4437,13 @@ function toKey(value) {
4324
4437
  if (typeof data === "object" && data !== null) {
4325
4438
  const record = data;
4326
4439
  if (record.scale === void 0) {
4327
- const scale = _chunk3R3QVKY5cjs.toKeyScale.call(void 0, data);
4440
+ const scale = _chunkYDGMWH43cjs.toKeyScale.call(void 0, data);
4328
4441
  return record.tonic === void 0 ? new Key(scale, spelledTonicFor(scale), record.variant) : new Key(scale, new Note(record.tonic), record.variant);
4329
4442
  }
4330
- return record.tonic === void 0 ? Key.of(_chunk3R3QVKY5cjs.toKeyScale.call(void 0, record.scale)) : Key.fromJSON(record);
4443
+ return record.tonic === void 0 ? Key.of(_chunkYDGMWH43cjs.toKeyScale.call(void 0, record.scale)) : Key.fromJSON(record);
4331
4444
  }
4332
4445
  }
4333
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(`key must be a key name or a key/scale; received ${typeof value}`);
4446
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`key must be a key name or a key/scale; received ${typeof value}`);
4334
4447
  }
4335
4448
  function keyIdentity(key) {
4336
4449
  return { scale: key.scale, tonic: key.tonic.data, variant: key.variant };
@@ -4358,7 +4471,7 @@ function copyMeters(meters) {
4358
4471
  }
4359
4472
  function copyTempo(tempo) {
4360
4473
  assertDataObjects(tempo, "score tempo");
4361
- _chunkNM7UAMC3cjs.tempoAt.call(void 0, 0, tempo);
4474
+ _chunk3FDBMIPRcjs.tempoAt.call(void 0, 0, tempo);
4362
4475
  return tempo.map((event) => ({
4363
4476
  startBeat: withoutNegativeZero(event.startBeat),
4364
4477
  bpm: event.bpm
@@ -4370,7 +4483,7 @@ function copyScore(data) {
4370
4483
  notes: orderNotes(data.notes, "score notes"),
4371
4484
  // The map is validated by the same resolver every meter-aware entry point
4372
4485
  // reads its options through, so a score accepts exactly what they accept.
4373
- meters: copyMeters(_chunkS5BKZZGMcjs.resolveMeters.call(void 0, { meters: data.meters }, "score meters")),
4486
+ meters: copyMeters(_chunkS3QELJUEcjs.resolveMeters.call(void 0, { meters: data.meters }, "score meters")),
4374
4487
  tempo: copyTempo(data.tempo)
4375
4488
  };
4376
4489
  if (data.key !== void 0) {
@@ -4384,29 +4497,17 @@ function tempoFrom(tempo) {
4384
4497
  }
4385
4498
  return typeof tempo === "number" ? [{ startBeat: 0, bpm: tempo }] : tempo;
4386
4499
  }
4387
- function statedKeyRegions(key, notes, totalBeats) {
4500
+ function scoreKeyRegions(key, notes, totalBeats) {
4388
4501
  const first = notes[0];
4389
- if (first === void 0 || totalBeats <= first.startBeat) {
4390
- return [];
4391
- }
4392
- return [
4393
- {
4394
- // The region starts where the music does, as an inferred one does, so a
4395
- // pickup is covered by the key it sounds in.
4396
- startBeat: first.startBeat,
4397
- endBeat: totalBeats,
4398
- key: keyIdentity(key),
4399
- confidence: STATED_KEY_CONFIDENCE
4400
- }
4401
- ];
4502
+ return first === void 0 ? [] : _chunkLQZQDBCDcjs.statedKeyRegions.call(void 0, keyIdentity(key), first.startBeat, totalBeats);
4402
4503
  }
4403
4504
  function scoreData(notes, opts) {
4404
4505
  const data = {
4405
4506
  notes: [...assertDataArray(notes, "score notes")],
4406
- meters: _chunkS5BKZZGMcjs.resolveMeters.call(void 0, { meters: _optionalChain([opts, 'optionalAccess', _33 => _33.meters]) }, "score meters"),
4407
- tempo: tempoFrom(_optionalChain([opts, 'optionalAccess', _34 => _34.tempo]))
4507
+ meters: _chunkS3QELJUEcjs.resolveMeters.call(void 0, { meters: _optionalChain([opts, 'optionalAccess', _34 => _34.meters]) }, "score meters"),
4508
+ tempo: tempoFrom(_optionalChain([opts, 'optionalAccess', _35 => _35.tempo]))
4408
4509
  };
4409
- if (_optionalChain([opts, 'optionalAccess', _35 => _35.key]) !== void 0) {
4510
+ if (_optionalChain([opts, 'optionalAccess', _36 => _36.key]) !== void 0) {
4410
4511
  data.key = toKey(opts.key).toJSON();
4411
4512
  }
4412
4513
  return data;
@@ -4480,8 +4581,8 @@ var Score = class _Score {
4480
4581
  static fromTicks(events, ppq, opts) {
4481
4582
  const notes = assertDataObjects(events, "score notes").map((event) => ({
4482
4583
  ...event,
4483
- startBeat: _chunkNM7UAMC3cjs.ticksToBeats.call(void 0, event.startBeat, ppq),
4484
- durationBeat: _chunkNM7UAMC3cjs.ticksToBeats.call(void 0, event.durationBeat, ppq)
4584
+ startBeat: _chunk3FDBMIPRcjs.ticksToBeats.call(void 0, event.startBeat, ppq),
4585
+ durationBeat: _chunk3FDBMIPRcjs.ticksToBeats.call(void 0, event.durationBeat, ppq)
4485
4586
  }));
4486
4587
  return new _Score(scoreData(notes, opts));
4487
4588
  }
@@ -4530,8 +4631,8 @@ var Score = class _Score {
4530
4631
  * @returns The score holding those notes.
4531
4632
  */
4532
4633
  slice(fromBeat, toBeat) {
4533
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, fromBeat, "slice fromBeat");
4534
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, toBeat, "slice toBeat");
4634
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, fromBeat, "slice fromBeat");
4635
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, toBeat, "slice toBeat");
4535
4636
  return this.#withNotes(
4536
4637
  this.#data.notes.filter((note) => note.startBeat >= fromBeat && note.startBeat < toBeat)
4537
4638
  );
@@ -4563,7 +4664,7 @@ var Score = class _Score {
4563
4664
  * @returns The moved score.
4564
4665
  */
4565
4666
  shift(beats) {
4566
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, beats, "shift beats");
4667
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, beats, "shift beats");
4567
4668
  return this.#withNotes(
4568
4669
  this.#data.notes.map((note) => ({ ...note, startBeat: note.startBeat + beats }))
4569
4670
  );
@@ -4581,7 +4682,7 @@ var Score = class _Score {
4581
4682
  * @throws If a note would leave the MIDI range.
4582
4683
  */
4583
4684
  transpose(semitones) {
4584
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, semitones, "transpose semitones");
4685
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, semitones, "transpose semitones");
4585
4686
  return this.#moved(
4586
4687
  this.#data.notes.map((note) => ({ ...note, pitch: note.pitch + semitones })),
4587
4688
  (key) => key.transpose(semitones)
@@ -4601,7 +4702,7 @@ var Score = class _Score {
4601
4702
  * @returns The transposed score.
4602
4703
  */
4603
4704
  transposeBy(interval) {
4604
- const step = _chunkS5BKZZGMcjs.toSpelledInterval.call(void 0, interval);
4705
+ const step = _chunkS3QELJUEcjs.toSpelledInterval.call(void 0, interval);
4605
4706
  return this.#moved(
4606
4707
  this.#data.notes.map((note) => ({ ...note, pitch: note.pitch + step.semitones })),
4607
4708
  // Moved by the interval rather than by its semitone count, so a key taken
@@ -4612,7 +4713,7 @@ var Score = class _Score {
4612
4713
  }
4613
4714
  /** The same notes read against a different meter. */
4614
4715
  withMeters(meters) {
4615
- return new _Score({ ...this.#data, meters: _chunkS5BKZZGMcjs.resolveMeters.call(void 0, { meters }, "score meters") });
4716
+ return new _Score({ ...this.#data, meters: _chunkS3QELJUEcjs.resolveMeters.call(void 0, { meters }, "score meters") });
4616
4717
  }
4617
4718
  /** The same notes read against a different tempo. */
4618
4719
  withTempo(tempo) {
@@ -4641,7 +4742,7 @@ var Score = class _Score {
4641
4742
  * ```
4642
4743
  */
4643
4744
  quantize(grid) {
4644
- _chunkS5BKZZGMcjs.assertRange.call(void 0, grid, Number.MIN_VALUE, Number.MAX_SAFE_INTEGER, "quantize grid");
4745
+ _chunkS3QELJUEcjs.assertRange.call(void 0, grid, Number.MIN_VALUE, Number.MAX_SAFE_INTEGER, "quantize grid");
4645
4746
  return this.#withNotes(
4646
4747
  this.#data.notes.map((note) => ({
4647
4748
  ...note,
@@ -4653,43 +4754,42 @@ var Score = class _Score {
4653
4754
  /**
4654
4755
  * The notes pushed off the grid the way a player would.
4655
4756
  *
4656
- * The metric accents are read from the score's opening signature, since
4657
- * {@link HumanizeOptions} names one signature rather than a map; pass `ts`
4658
- * to read a later stretch of a score that changes meter.
4757
+ * The metric accents are read against the score's meter map, exactly as
4758
+ * {@link humanize} reads that map; pass `ts` to read against another meter.
4659
4759
  *
4660
4760
  * @param opts Jitter amounts, accent depth and the seed; see
4661
4761
  * {@link HumanizeOptions}.
4662
4762
  * @returns The humanized score.
4663
4763
  */
4664
4764
  humanize(opts) {
4665
- return this.#withNotes(_chunkB2PW6EHNcjs.humanize.call(void 0, this.#data.notes, { ts: this.meterAt(0), ...opts }));
4765
+ return this.#withNotes(_chunk6TTBEON3cjs.humanize.call(void 0, this.#data.notes, { ts: this.#data.meters, ...opts }));
4666
4766
  }
4667
4767
  /**
4668
4768
  * The notes with ornaments added.
4669
4769
  *
4670
- * Strong positions are read from the score's opening signature, since
4671
- * {@link OrnamentOptions} names one signature rather than a map.
4770
+ * Strong positions are read against the score's meter map, exactly as
4771
+ * {@link ornament} reads that map.
4672
4772
  *
4673
4773
  * @param opts The ornament style, how much is decorated, and the seed; see
4674
4774
  * {@link OrnamentOptions}.
4675
4775
  * @returns The ornamented score.
4676
4776
  */
4677
4777
  ornament(opts) {
4678
- return this.#withNotes(_chunkB2PW6EHNcjs.ornament.call(void 0, this.#data.notes, { ts: this.meterAt(0), ...opts }));
4778
+ return this.#withNotes(_chunk6TTBEON3cjs.ornament.call(void 0, this.#data.notes, { ts: this.#data.meters, ...opts }));
4679
4779
  }
4680
4780
  /**
4681
4781
  * The notes placed on a groove template's slots.
4682
4782
  *
4683
- * The template's per-bar grid is laid out against the score's opening
4684
- * signature, which is the signature the template must have been extracted
4685
- * under; a template carrying a different one is refused rather than drifting.
4783
+ * The template's per-bar grid is laid out against the score's meter map,
4784
+ * exactly as {@link applyGrooveTemplate} reads that map; a template extracted
4785
+ * under another meter is refused rather than drifting.
4686
4786
  *
4687
4787
  * @param template The groove template, from `extractGrooveTemplate`.
4688
4788
  * @returns The score with the template's feel imposed.
4689
4789
  * @throws If the template was extracted under another meter.
4690
4790
  */
4691
4791
  groove(template) {
4692
- return this.#withNotes(_chunkB2PW6EHNcjs.applyGrooveTemplate.call(void 0, this.#data.notes, template, this.meterAt(0)));
4792
+ return this.#withNotes(_chunk6TTBEON3cjs.applyGrooveTemplate.call(void 0, this.#data.notes, template, this.#data.meters));
4693
4793
  }
4694
4794
  /**
4695
4795
  * The feel of the score's own timing, as a template another score can take on.
@@ -4698,8 +4798,8 @@ var Score = class _Score {
4698
4798
  * slot by slot for how far ahead of or behind the grid it sits and how hard
4699
4799
  * it is struck, and the reading is handed back as a template. Only the
4700
4800
  * subdivision is named, because the score already holds the meter the grid is
4701
- * laid out against — its opening signature, which is the one the template
4702
- * records and the one an apply-time meter is checked against.
4801
+ * laid out against — its meter map, read exactly as
4802
+ * {@link extractGrooveTemplate} reads that map.
4703
4803
  *
4704
4804
  * @param subdivision Grid steps per quarter-note beat; a sixteenth-note grid
4705
4805
  * by default, which is where swing, push and drag are audible.
@@ -4713,7 +4813,7 @@ var Score = class _Score {
4713
4813
  * ```
4714
4814
  */
4715
4815
  grooveTemplate(subdivision) {
4716
- return _chunkB2PW6EHNcjs.extractGrooveTemplate.call(void 0, this.#data.notes, this.meterAt(0), subdivision);
4816
+ return _chunk6TTBEON3cjs.extractGrooveTemplate.call(void 0, this.#data.notes, this.#data.meters, subdivision);
4717
4817
  }
4718
4818
  /**
4719
4819
  * The harmony the notes spell out, in time.
@@ -4726,10 +4826,10 @@ var Score = class _Score {
4726
4826
  * and how sure it is of each segment.
4727
4827
  */
4728
4828
  timeline(opts) {
4729
- const result = opts === void 0 ? this.#chordAnalysis() : _chunkIFZDWIKMcjs.chordTimelineFromNotes.call(void 0, this.#data.notes, this.#analysisOptions(opts));
4829
+ const result = opts === void 0 ? this.#chordAnalysis() : _chunkLQZQDBCDcjs.chordTimelineFromNotes.call(void 0, this.#data.notes, this.#analysisOptions(opts));
4730
4830
  return Timeline.fromData({
4731
4831
  segments: result.timeline.segments,
4732
- totalBeats: _nullishCoalesce(_optionalChain([opts, 'optionalAccess', _36 => _36.totalBeats]), () => ( this.totalBeats)),
4832
+ totalBeats: _nullishCoalesce(_optionalChain([opts, 'optionalAccess', _37 => _37.totalBeats]), () => ( this.totalBeats)),
4733
4833
  keys: result.keys,
4734
4834
  segmentConfidence: result.segmentConfidence
4735
4835
  });
@@ -4748,7 +4848,7 @@ var Score = class _Score {
4748
4848
  if (this.#key !== void 0) {
4749
4849
  return this.#key;
4750
4850
  }
4751
- const prevailing = _chunkIFZDWIKMcjs.prevailingKeyOf.call(void 0, this.#keyRegions());
4851
+ const prevailing = _chunkLQZQDBCDcjs.prevailingKeyOf.call(void 0, this.#keyRegions());
4752
4852
  return prevailing === null ? void 0 : toKey(prevailing);
4753
4853
  }
4754
4854
  /**
@@ -4767,9 +4867,10 @@ var Score = class _Score {
4767
4867
  keys(opts) {
4768
4868
  if (opts !== void 0) {
4769
4869
  if (this.#key !== void 0) {
4770
- return statedKeyRegions(this.#key, this.#data.notes, _nullishCoalesce(opts.totalBeats, () => ( this.totalBeats)));
4870
+ const totalBeats = opts.totalBeats === void 0 || opts.totalBeats === null ? this.totalBeats : _chunkS3QELJUEcjs.assertRange.call(void 0, opts.totalBeats, 0, Number.MAX_SAFE_INTEGER, "key timeline totalBeats");
4871
+ return scoreKeyRegions(this.#key, this.#data.notes, totalBeats);
4771
4872
  }
4772
- return _chunkIFZDWIKMcjs.keyTimelineFromNotes.call(void 0, this.#data.notes, { meters: this.#data.meters, ...opts });
4873
+ return _chunkLQZQDBCDcjs.keyTimelineFromNotes.call(void 0, this.#data.notes, { meters: this.#data.meters, ...opts });
4773
4874
  }
4774
4875
  return this.#keyRegions().map(copyKeyRegion);
4775
4876
  }
@@ -4797,7 +4898,7 @@ var Score = class _Score {
4797
4898
  * ```
4798
4899
  */
4799
4900
  detectKeys(opts) {
4800
- return _chunkIFZDWIKMcjs.detectKeyFromNotes.call(void 0, this.#data.notes, opts).map(detectedKeyMatch);
4901
+ return _chunkLQZQDBCDcjs.detectKeyFromNotes.call(void 0, this.#data.notes, opts).map(detectedKeyMatch);
4801
4902
  }
4802
4903
  /**
4803
4904
  * The phrases the notes fall into.
@@ -4809,7 +4910,7 @@ var Score = class _Score {
4809
4910
  * @returns The phrases, in time order.
4810
4911
  */
4811
4912
  phrases(opts) {
4812
- return _chunkYFA7X2F6cjs.phrasesFromTimeline.call(void 0, this.#chordTimeline(), this.#data.notes, {
4913
+ return _chunk3MDOEFIQcjs.phrasesFromTimeline.call(void 0, this.#chordTimeline(), this.#data.notes, {
4813
4914
  meters: this.#data.meters,
4814
4915
  ...this.#key === void 0 ? {} : { key: keyIdentity(this.#key) },
4815
4916
  ...opts
@@ -4829,7 +4930,7 @@ var Score = class _Score {
4829
4930
  * @returns The cadences, heaviest first; ties keep the earlier one.
4830
4931
  */
4831
4932
  structuralCadences(opts) {
4832
- return _chunkYFA7X2F6cjs.structuralCadences.call(void 0, this.phrases(opts));
4933
+ return _chunk3MDOEFIQcjs.structuralCadences.call(void 0, this.phrases(opts));
4833
4934
  }
4834
4935
  /**
4835
4936
  * The sections the score divides into.
@@ -4838,7 +4939,7 @@ var Score = class _Score {
4838
4939
  * @returns The sections, in time order.
4839
4940
  */
4840
4941
  sections(opts) {
4841
- return _chunkYFA7X2F6cjs.sectionsFromNotes.call(void 0, this.#data.notes, { meters: this.#data.meters, ...opts });
4942
+ return _chunk3MDOEFIQcjs.sectionsFromNotes.call(void 0, this.#data.notes, { meters: this.#data.meters, ...opts });
4842
4943
  }
4843
4944
  /**
4844
4945
  * The bar-level pulse above the meter.
@@ -4851,10 +4952,16 @@ var Score = class _Score {
4851
4952
  * @returns The grouping, its downbeats, a confidence, and a rationale.
4852
4953
  */
4853
4954
  hypermeter(opts) {
4854
- return _chunkYFA7X2F6cjs.hypermeter.call(void 0, this.#data.notes, this.#data.meters, {
4855
- cadenceBeats: this.#cadenceBeats(),
4856
- ...opts
4857
- });
4955
+ const asked = { ...opts };
4956
+ if ((_nullishCoalesce(asked.cadenceBeats, () => ( null))) !== null) {
4957
+ return _chunk3MDOEFIQcjs.hypermeter.call(void 0, this.#data.notes, this.#data.meters, asked);
4958
+ }
4959
+ return _chunk3MDOEFIQcjs.hypermeterOver.call(void 0,
4960
+ this.#data.notes,
4961
+ this.#data.meters,
4962
+ asked,
4963
+ () => this.#cadenceSpans(asked.budget)
4964
+ );
4858
4965
  }
4859
4966
  /**
4860
4967
  * The motifs the melody repeats.
@@ -4869,8 +4976,9 @@ var Score = class _Score {
4869
4976
  *
4870
4977
  * A melody is one line, so a score holding several is read as its top voice:
4871
4978
  * notes struck together are one event and the highest of them stands for it.
4872
- * A piano part read whole therefore answers for the voice a listener follows
4873
- * rather than for a line assembled from the insides of its chords. Split the
4979
+ * A block-chord part read whole therefore answers for its top voice rather
4980
+ * than for a line assembled from the insides of its chords; a lower note
4981
+ * struck while a higher one still sounds stays in the line, though. Split the
4874
4982
  * score into lines first to have each of them answered for.
4875
4983
  *
4876
4984
  * @param opts Cell-length bounds and the recurrence threshold; see
@@ -4893,7 +5001,7 @@ var Score = class _Score {
4893
5001
  * ```
4894
5002
  */
4895
5003
  motifs(opts) {
4896
- return _chunkIFZDWIKMcjs.extractMotifs.call(void 0, this.#data.notes, opts);
5004
+ return _chunkLQZQDBCDcjs.extractMotifs.call(void 0, this.#data.notes, opts);
4897
5005
  }
4898
5006
  /**
4899
5007
  * The shape the melody traces.
@@ -4905,7 +5013,7 @@ var Score = class _Score {
4905
5013
  * answered for; {@link Score.voices} is what reads the polyphony as polyphony.
4906
5014
  */
4907
5015
  contour() {
4908
- return _chunkIFZDWIKMcjs.melodicContour.call(void 0, this.#data.notes);
5016
+ return _chunkLQZQDBCDcjs.melodicContour.call(void 0, this.#data.notes);
4909
5017
  }
4910
5018
  /**
4911
5019
  * The score's structural fingerprint: form, phrase shape, harmonic function
@@ -4955,7 +5063,7 @@ var Score = class _Score {
4955
5063
  ...keyed,
4956
5064
  ...opts
4957
5065
  };
4958
- const profile = _optionalChain([opts, 'optionalAccess', _37 => _37.timeline]) === void 0 ? _chunkYFA7X2F6cjs.referenceFromReadings.call(void 0, this.#data.notes, this.#chordAnalysis(), asked) : _chunkYFA7X2F6cjs.analyzeReference.call(void 0, this.#data.notes, asked);
5066
+ const profile = _optionalChain([opts, 'optionalAccess', _38 => _38.timeline]) === void 0 ? _chunk3MDOEFIQcjs.referenceFromReadings.call(void 0, this.#data.notes, this.#chordAnalysis(), asked) : _chunk3MDOEFIQcjs.analyzeReference.call(void 0, this.#data.notes, asked);
4959
5067
  if (opts === void 0) {
4960
5068
  this.#profile = profile;
4961
5069
  return copyPlain(profile, "reference profile");
@@ -4984,7 +5092,7 @@ var Score = class _Score {
4984
5092
  * ```
4985
5093
  */
4986
5094
  rhythm(opts) {
4987
- return _chunkIFZDWIKMcjs.analyzeRhythm.call(void 0, this.#data.notes, {
5095
+ return _chunkLQZQDBCDcjs.analyzeRhythm.call(void 0, this.#data.notes, {
4988
5096
  meters: this.#data.meters,
4989
5097
  totalBeats: this.totalBeats,
4990
5098
  ...opts
@@ -5018,7 +5126,7 @@ var Score = class _Score {
5018
5126
  * ```
5019
5127
  */
5020
5128
  motifGraph(opts) {
5021
- return _chunkIFZDWIKMcjs.motifGraph.call(void 0, this.#data.notes, _chunkIFZDWIKMcjs.extractMotifs.call(void 0, this.#data.notes, opts), {
5129
+ return _chunkLQZQDBCDcjs.motifGraph.call(void 0, this.#data.notes, _chunkLQZQDBCDcjs.extractMotifs.call(void 0, this.#data.notes, opts), {
5022
5130
  key: this.key(),
5023
5131
  ...opts
5024
5132
  });
@@ -5042,7 +5150,7 @@ var Score = class _Score {
5042
5150
  * ```
5043
5151
  */
5044
5152
  evaluate(plan, opts) {
5045
- return _chunkB2PW6EHNcjs.evaluateComposition.call(void 0, this.#data.notes, plan, opts);
5153
+ return _chunk6TTBEON3cjs.evaluateComposition.call(void 0, this.#data.notes, plan, opts);
5046
5154
  }
5047
5155
  /**
5048
5156
  * Each note's role in the harmony sounding under it.
@@ -5066,7 +5174,7 @@ var Score = class _Score {
5066
5174
  */
5067
5175
  voices(key) {
5068
5176
  const timeline = this.#chordTimeline();
5069
- return _chunkYFA7X2F6cjs.analyzePolyphony.call(void 0, this.#data.notes, timeline.at, this.#keyContext(key));
5177
+ return _chunk3MDOEFIQcjs.analyzePolyphony.call(void 0, this.#data.notes, timeline.at, this.#keyContext(key));
5070
5178
  }
5071
5179
  /**
5072
5180
  * The notes carrying the ids the voice analysis reports them back under.
@@ -5080,7 +5188,7 @@ var Score = class _Score {
5080
5188
  * @returns One voice note per note, in the score's own time order.
5081
5189
  */
5082
5190
  voiceNotes() {
5083
- return _chunkIFZDWIKMcjs.toVoiceNotes.call(void 0, this.#data.notes);
5191
+ return _chunkLQZQDBCDcjs.toVoiceNotes.call(void 0, this.#data.notes);
5084
5192
  }
5085
5193
  /**
5086
5194
  * Whether an instrument can play the score, and what makes it hard.
@@ -5104,14 +5212,14 @@ var Score = class _Score {
5104
5212
  * ```
5105
5213
  */
5106
5214
  playability(instrument) {
5107
- const profile = _chunkCGBADIO5cjs.toInstrumentProfile.call(void 0, instrument);
5215
+ const profile = _chunkWOMCXN2Wcjs.toInstrumentProfile.call(void 0, instrument);
5108
5216
  const tempo = this.#data.tempo;
5109
- const openingBpm = _chunkNM7UAMC3cjs.tempoAt.call(void 0, 0, tempo);
5217
+ const openingBpm = _chunk3FDBMIPRcjs.tempoAt.call(void 0, 0, tempo);
5110
5218
  if (tempo.length < 2) {
5111
- return _chunkCGBADIO5cjs.playability.call(void 0, this.#data.notes, profile, openingBpm);
5219
+ return _chunkWOMCXN2Wcjs.playability.call(void 0, this.#data.notes, profile, openingBpm);
5112
5220
  }
5113
- const played = _chunkNM7UAMC3cjs.tempoReader.call(void 0, tempo);
5114
- const evenly = _chunkNM7UAMC3cjs.tempoReader.call(void 0, [{ startBeat: 0, bpm: openingBpm }]);
5221
+ const played = _chunk3FDBMIPRcjs.tempoReader.call(void 0, tempo);
5222
+ const evenly = _chunk3FDBMIPRcjs.tempoReader.call(void 0, [{ startBeat: 0, bpm: openingBpm }]);
5115
5223
  const restate = (beat) => evenly.beatAt(played.secondsAt(beat));
5116
5224
  const scoreBeats = /* @__PURE__ */ new Map();
5117
5225
  const evenlyPaced = this.#data.notes.map((note) => {
@@ -5123,7 +5231,7 @@ var Score = class _Score {
5123
5231
  durationBeat: restate(note.startBeat + note.durationBeat) - startBeat
5124
5232
  };
5125
5233
  });
5126
- const report = _chunkCGBADIO5cjs.playability.call(void 0, evenlyPaced, profile, openingBpm);
5234
+ const report = _chunkWOMCXN2Wcjs.playability.call(void 0, evenlyPaced, profile, openingBpm);
5127
5235
  return {
5128
5236
  ...report,
5129
5237
  issues: report.issues.map((issue) => ({
@@ -5139,7 +5247,7 @@ var Score = class _Score {
5139
5247
  * @returns The index.
5140
5248
  */
5141
5249
  index(opts) {
5142
- return _chunk35NBV2FTcjs.createNoteEventIndex.call(void 0, this.#data.notes, {
5250
+ return _chunkKMYGRFZ6cjs.createNoteEventIndex.call(void 0, this.#data.notes, {
5143
5251
  allowNonPositiveDuration: true,
5144
5252
  name: "score notes",
5145
5253
  ...opts
@@ -5156,7 +5264,7 @@ var Score = class _Score {
5156
5264
  * @returns Elapsed seconds from the tempo map's origin.
5157
5265
  */
5158
5266
  secondsAt(beat) {
5159
- return _chunkNM7UAMC3cjs.beatsToSeconds.call(void 0, beat, this.#data.tempo);
5267
+ return _chunk3FDBMIPRcjs.beatsToSeconds.call(void 0, beat, this.#data.tempo);
5160
5268
  }
5161
5269
  /**
5162
5270
  * Where a beat falls in bars, read through the meter map.
@@ -5166,7 +5274,7 @@ var Score = class _Score {
5166
5274
  * reports bar -1.
5167
5275
  */
5168
5276
  barAt(beat) {
5169
- return _chunkS5BKZZGMcjs.beatToBarPosition.call(void 0, beat, this.#data.meters);
5277
+ return _chunkS3QELJUEcjs.beatToBarPosition.call(void 0, beat, this.#data.meters);
5170
5278
  }
5171
5279
  /**
5172
5280
  * The time signature sounding at a beat.
@@ -5175,7 +5283,7 @@ var Score = class _Score {
5175
5283
  * @returns The signature in force there.
5176
5284
  */
5177
5285
  meterAt(beat) {
5178
- return _chunkS5BKZZGMcjs.meterAt.call(void 0, beat, this.#data.meters);
5286
+ return _chunkS3QELJUEcjs.meterAt.call(void 0, beat, this.#data.meters);
5179
5287
  }
5180
5288
  /**
5181
5289
  * The score's beats as MIDI ticks, for a writer that counts in them.
@@ -5186,8 +5294,8 @@ var Score = class _Score {
5186
5294
  toTicks(ppq) {
5187
5295
  return this.#data.notes.map((note) => ({
5188
5296
  ...note,
5189
- startBeat: _chunkNM7UAMC3cjs.beatsToTicks.call(void 0, note.startBeat, ppq),
5190
- durationBeat: _chunkNM7UAMC3cjs.beatsToTicks.call(void 0, note.durationBeat, ppq)
5297
+ startBeat: _chunk3FDBMIPRcjs.beatsToTicks.call(void 0, note.startBeat, ppq),
5298
+ durationBeat: _chunk3FDBMIPRcjs.beatsToTicks.call(void 0, note.durationBeat, ppq)
5191
5299
  }));
5192
5300
  }
5193
5301
  /**
@@ -5260,7 +5368,7 @@ var Score = class _Score {
5260
5368
  * Score.timeline} hands all three to the class it builds.
5261
5369
  */
5262
5370
  #chordAnalysis() {
5263
- const analysis = _nullishCoalesce(this.#chords, () => ( _chunkIFZDWIKMcjs.chordTimelineFromNotes.call(void 0, this.#data.notes, this.#analysisOptions())));
5371
+ const analysis = _nullishCoalesce(this.#chords, () => ( _chunkLQZQDBCDcjs.chordTimelineFromNotes.call(void 0, this.#data.notes, this.#analysisOptions())));
5264
5372
  this.#chords = analysis;
5265
5373
  return analysis;
5266
5374
  }
@@ -5271,15 +5379,24 @@ var Score = class _Score {
5271
5379
  * Kept on first reading for the same reason the chord timeline is.
5272
5380
  */
5273
5381
  #keyRegions() {
5274
- const regions = _nullishCoalesce(this.#regions, () => ( (this.#key === void 0 ? _chunkIFZDWIKMcjs.keyTimelineFromNotes.call(void 0, this.#data.notes, { meters: this.#data.meters }) : statedKeyRegions(this.#key, this.#data.notes, this.totalBeats))));
5382
+ const regions = _nullishCoalesce(this.#regions, () => ( (this.#key === void 0 ? _chunkLQZQDBCDcjs.keyTimelineFromNotes.call(void 0, this.#data.notes, { meters: this.#data.meters }) : scoreKeyRegions(this.#key, this.#data.notes, this.totalBeats))));
5275
5383
  this.#regions = regions;
5276
5384
  return regions;
5277
5385
  }
5278
- /** Where the score's own harmony closes, as beats. */
5279
- #cadenceBeats() {
5280
- return _chunkIFZDWIKMcjs.detectCadences.call(void 0, this.#chordTimeline(), this.#keyContext(void 0)).map(
5281
- (hit) => hit.atBeat
5386
+ /**
5387
+ * Where the score's own harmony closes, as the spans its arrival chords sound
5388
+ * through, read in the key {@link Score.phrases} reads them in.
5389
+ */
5390
+ #cadenceSpans(budget) {
5391
+ const timeline = this.#chordTimeline();
5392
+ const key = _chunk3MDOEFIQcjs.keyContextFor.call(void 0,
5393
+ this.#key === void 0 ? void 0 : keyIdentity(this.#key),
5394
+ timeline,
5395
+ this.#data.meters,
5396
+ void 0,
5397
+ budget
5282
5398
  );
5399
+ return _chunk3MDOEFIQcjs.boundaryCadences.call(void 0, timeline, key).spans;
5283
5400
  }
5284
5401
  /** The score's context as chord-timeline options, with the caller's on top. */
5285
5402
  #analysisOptions(opts) {
@@ -5302,9 +5419,9 @@ var Score = class _Score {
5302
5419
  return keyIdentity(this.#key);
5303
5420
  }
5304
5421
  const regions = this.#keyRegions();
5305
- const prevailing = _nullishCoalesce(_chunkIFZDWIKMcjs.prevailingKeyOf.call(void 0, regions), () => ( keyIdentity(Key.major("C"))));
5306
- const keyAt = _chunkIFZDWIKMcjs.keyLookup.call(void 0, regions, prevailing);
5307
- return (beat) => _chunk3R3QVKY5cjs.scaleOf.call(void 0, keyAt(beat));
5422
+ const prevailing = _nullishCoalesce(_chunkLQZQDBCDcjs.prevailingKeyOf.call(void 0, regions), () => ( keyIdentity(Key.major("C"))));
5423
+ const keyAt = _chunkLQZQDBCDcjs.keyLookup.call(void 0, regions, prevailing);
5424
+ return (beat) => _chunkYDGMWH43cjs.scaleOf.call(void 0, keyAt(beat));
5308
5425
  }
5309
5426
  };
5310
5427
  function sameNote(note, other) {
@@ -5340,7 +5457,7 @@ function copyTrack(track, index, budget) {
5340
5457
  copy.name = track.name;
5341
5458
  }
5342
5459
  if (track.role !== void 0) {
5343
- copy.role = _chunkYFA7X2F6cjs.trackRoleOf.call(void 0, track.role, `tracks[${index}].role`);
5460
+ copy.role = _chunk3MDOEFIQcjs.trackRoleOf.call(void 0, track.role, `tracks[${index}].role`);
5344
5461
  }
5345
5462
  return copy;
5346
5463
  }
@@ -5355,21 +5472,21 @@ function copySegments(segments) {
5355
5472
  function chordTimelineOf(segments) {
5356
5473
  return new Timeline({ segments: [...segments], totalBeats: spanEnd(segments) }).chordTimeline;
5357
5474
  }
5358
- function copySettings(settings, trackCount) {
5475
+ function copySettings(settings, tracks) {
5359
5476
  if (settings === void 0) {
5360
5477
  return void 0;
5361
5478
  }
5362
5479
  assertDataObject(settings, "arrangement settings");
5363
5480
  const copy = {};
5364
- const meters = _chunkS5BKZZGMcjs.resolveMeters.call(void 0, { ts: settings.ts, meters: settings.meters }, "arrangement meters");
5481
+ const meters = _chunkS3QELJUEcjs.resolveMeters.call(void 0, { ts: settings.ts, meters: settings.meters }, "arrangement meters");
5365
5482
  if (settings.ts !== void 0) {
5366
- copy.ts = copyPlain(_chunkS5BKZZGMcjs.toMeterData.call(void 0, settings.ts, "arrangement ts"), "arrangement ts");
5483
+ copy.ts = copyPlain(_chunkS3QELJUEcjs.toMeterData.call(void 0, settings.ts, "arrangement ts"), "arrangement ts");
5367
5484
  }
5368
5485
  if (settings.meters !== void 0) {
5369
5486
  copy.meters = copyPlain(meters, "arrangement meters");
5370
5487
  }
5371
5488
  if (settings.key !== void 0) {
5372
- copy.key = _chunk3R3QVKY5cjs.resolveKey.call(void 0, settings.key);
5489
+ copy.key = _chunkYDGMWH43cjs.resolveKey.call(void 0, settings.key);
5373
5490
  }
5374
5491
  if (settings.keys !== void 0) {
5375
5492
  copy.keys = copyKeyRegions(settings.keys);
@@ -5382,11 +5499,12 @@ function copySettings(settings, trackCount) {
5382
5499
  settings.harmonyTracks,
5383
5500
  "arrangement harmonyTracks"
5384
5501
  ).map(
5385
- (track, index) => _chunkS5BKZZGMcjs.assertInteger.call(void 0, track, `arrangement harmonyTracks[${index}]`, 0, trackCount - 1)
5502
+ (track, index) => _chunkS3QELJUEcjs.assertInteger.call(void 0, track, `arrangement harmonyTracks[${index}]`, 0, tracks.length - 1)
5386
5503
  );
5504
+ _chunk3MDOEFIQcjs.harmonyTrackSet.call(void 0, copy.harmonyTracks, tracks, "arrangement harmonyTracks");
5387
5505
  }
5388
5506
  if (settings.minSeverity !== void 0) {
5389
- copy.minSeverity = _chunkS5BKZZGMcjs.assertInteger.call(void 0,
5507
+ copy.minSeverity = _chunkS3QELJUEcjs.assertInteger.call(void 0,
5390
5508
  settings.minSeverity,
5391
5509
  "arrangement minSeverity",
5392
5510
  0 /* Safe */,
@@ -5394,15 +5512,20 @@ function copySettings(settings, trackCount) {
5394
5512
  );
5395
5513
  }
5396
5514
  if (settings.pickupBeats !== void 0) {
5397
- copy.pickupBeats = _chunkS5BKZZGMcjs.assertRange.call(void 0,
5515
+ copy.pickupBeats = _chunkS3QELJUEcjs.assertRange.call(void 0,
5398
5516
  settings.pickupBeats,
5399
5517
  0,
5400
5518
  Number.MAX_SAFE_INTEGER,
5401
5519
  "arrangement pickupBeats"
5402
5520
  );
5521
+ _chunk3MDOEFIQcjs.assertTrackNotes.call(void 0, tracks, {
5522
+ allowNonPositiveDuration: true,
5523
+ minStartBeat: -copy.pickupBeats,
5524
+ budget: settings.budget
5525
+ });
5403
5526
  }
5404
5527
  if (settings.harmonicRhythm !== void 0) {
5405
- copy.harmonicRhythm = _chunkS5BKZZGMcjs.assertRange.call(void 0,
5528
+ copy.harmonicRhythm = _chunkS3QELJUEcjs.assertRange.call(void 0,
5406
5529
  settings.harmonicRhythm,
5407
5530
  Number.MIN_VALUE,
5408
5531
  Number.MAX_SAFE_INTEGER,
@@ -5410,20 +5533,20 @@ function copySettings(settings, trackCount) {
5410
5533
  );
5411
5534
  }
5412
5535
  if (settings.profile !== void 0) {
5413
- copy.profile = settings.profile;
5536
+ copy.profile = _chunk3MDOEFIQcjs.arrangementProfile.call(void 0, settings.profile);
5414
5537
  }
5415
5538
  if (settings.budget !== void 0) {
5416
- copy.budget = _chunkS5BKZZGMcjs.assertPositiveInt.call(void 0, settings.budget, "arrangement budget", Number.MAX_SAFE_INTEGER);
5539
+ copy.budget = _chunkS3QELJUEcjs.assertPositiveInt.call(void 0, settings.budget, "arrangement budget", Number.MAX_SAFE_INTEGER);
5417
5540
  }
5418
5541
  return Object.keys(copy).length === 0 ? void 0 : copy;
5419
5542
  }
5420
5543
  function copyArrangement(data) {
5421
5544
  assertDataObject(data, "arrangement data");
5422
- const budget = _optionalChain([data, 'access', _38 => _38.settings, 'optionalAccess', _39 => _39.budget]);
5545
+ const budget = _optionalChain([data, 'access', _39 => _39.settings, 'optionalAccess', _40 => _40.budget]);
5423
5546
  const tracks = assertDataArray(data.tracks, "arrangement tracks").map(
5424
5547
  (track, index) => copyTrack(track, index, budget)
5425
5548
  );
5426
- const settings = copySettings(data.settings, tracks.length);
5549
+ const settings = copySettings(data.settings, tracks);
5427
5550
  return settings === void 0 ? { tracks } : { tracks, settings };
5428
5551
  }
5429
5552
  function arrangementData(tracks, settings) {
@@ -5443,10 +5566,10 @@ function settingsFrom(setup) {
5443
5566
  const { key, meters, timeline, ...rest } = setup;
5444
5567
  const settings = { ...rest };
5445
5568
  if (key !== void 0) {
5446
- settings.key = _chunk3R3QVKY5cjs.resolveKey.call(void 0, key);
5569
+ settings.key = _chunkYDGMWH43cjs.resolveKey.call(void 0, key);
5447
5570
  }
5448
5571
  if (meters !== void 0) {
5449
- settings.meters = _chunkS5BKZZGMcjs.resolveMeters.call(void 0, { meters }, "arrangement meters");
5572
+ settings.meters = _chunkS3QELJUEcjs.resolveMeters.call(void 0, { meters }, "arrangement meters");
5450
5573
  }
5451
5574
  if (timeline !== void 0) {
5452
5575
  assertDataObject(timeline, "arrangement timeline");
@@ -5464,10 +5587,10 @@ function analysisOptionsOf(setup) {
5464
5587
  const { key, meters, ...rest } = setup;
5465
5588
  const opts = { ...rest };
5466
5589
  if (key !== void 0) {
5467
- opts.key = _chunk3R3QVKY5cjs.resolveKey.call(void 0, key);
5590
+ opts.key = _chunkYDGMWH43cjs.resolveKey.call(void 0, key);
5468
5591
  }
5469
5592
  if (meters !== void 0) {
5470
- opts.meters = _chunkS5BKZZGMcjs.resolveMeters.call(void 0, { meters }, "arrangement meters");
5593
+ opts.meters = _chunkS3QELJUEcjs.resolveMeters.call(void 0, { meters }, "arrangement meters");
5471
5594
  }
5472
5595
  return opts;
5473
5596
  }
@@ -5609,7 +5732,7 @@ var Arrangement = class _Arrangement {
5609
5732
  }
5610
5733
  copied.push({
5611
5734
  trackIndex: edit.trackIndex,
5612
- notes: copyNotes(edit.notes, `edits[${index}].notes`, _optionalChain([this, 'access', _40 => _40.#data, 'access', _41 => _41.settings, 'optionalAccess', _42 => _42.budget]))
5735
+ notes: copyNotes(edit.notes, `edits[${index}].notes`, _optionalChain([this, 'access', _41 => _41.#data, 'access', _42 => _42.settings, 'optionalAccess', _43 => _43.budget]))
5613
5736
  });
5614
5737
  }
5615
5738
  const session = this.#session().update(copied);
@@ -5634,7 +5757,7 @@ var Arrangement = class _Arrangement {
5634
5757
  * @returns One tension reading per sampled beat, in beat order.
5635
5758
  */
5636
5759
  tension(opts) {
5637
- return _chunkYFA7X2F6cjs.tensionCurveFrom.call(void 0,
5760
+ return _chunk3MDOEFIQcjs.tensionCurveFrom.call(void 0,
5638
5761
  [...this.#data.tracks],
5639
5762
  this.#session().analysis,
5640
5763
  this.#layered(analysisOptionsOf(opts))
@@ -5660,7 +5783,7 @@ var Arrangement = class _Arrangement {
5660
5783
  * tracks exceed the budget.
5661
5784
  */
5662
5785
  analyze(opts) {
5663
- return _chunkYFA7X2F6cjs.analyzeArrangement.call(void 0, [...this.#data.tracks], this.#layered(analysisOptionsOf(opts)));
5786
+ return _chunk3MDOEFIQcjs.analyzeArrangement.call(void 0, [...this.#data.tracks], this.#layered(analysisOptionsOf(opts)));
5664
5787
  }
5665
5788
  /**
5666
5789
  * The harmony the tracks spell out together, in time.
@@ -5720,7 +5843,7 @@ var Arrangement = class _Arrangement {
5720
5843
  */
5721
5844
  reference(opts) {
5722
5845
  const tracks = this.#data.tracks;
5723
- const harmonyTracks = _optionalChain([this, 'access', _43 => _43.#data, 'access', _44 => _44.settings, 'optionalAccess', _45 => _45.harmonyTracks]);
5846
+ const harmonyTracks = _optionalChain([this, 'access', _44 => _44.#data, 'access', _45 => _45.settings, 'optionalAccess', _46 => _46.harmonyTracks]);
5724
5847
  const harmony = [];
5725
5848
  const melody = [];
5726
5849
  for (let index = 0; index < tracks.length; index += 1) {
@@ -5735,8 +5858,9 @@ var Arrangement = class _Arrangement {
5735
5858
  melody.push(...track.notes);
5736
5859
  }
5737
5860
  }
5738
- return _chunkYFA7X2F6cjs.referenceFromReadings.call(void 0, harmony, this.#session().analysis, {
5739
- meters: _optionalChain([this, 'access', _46 => _46.#data, 'access', _47 => _47.settings, 'optionalAccess', _48 => _48.meters]),
5861
+ return _chunk3MDOEFIQcjs.referenceFromReadings.call(void 0, harmony, this.#session().analysis, {
5862
+ // The meter the arrangement's own analysis reads, `ts` included.
5863
+ meters: _nullishCoalesce(_optionalChain([this, 'access', _47 => _47.#data, 'access', _48 => _48.settings, 'optionalAccess', _49 => _49.meters]), () => ( _optionalChain([this, 'access', _50 => _50.#data, 'access', _51 => _51.settings, 'optionalAccess', _52 => _52.ts]))),
5740
5864
  totalBeats: this.timeline().totalBeats,
5741
5865
  ...melody.length === 0 ? {} : { melody },
5742
5866
  ...opts
@@ -5766,7 +5890,7 @@ var Arrangement = class _Arrangement {
5766
5890
  }
5767
5891
  /** The open reading, analysing the tracks on the first call. */
5768
5892
  #session() {
5769
- const open = _nullishCoalesce(this.#open, () => ( _chunkYFA7X2F6cjs.createArrangementSession.call(void 0, [...this.#data.tracks], this.#analysisOptions())));
5893
+ const open = _nullishCoalesce(this.#open, () => ( _chunk3MDOEFIQcjs.createArrangementSession.call(void 0, [...this.#data.tracks], this.#analysisOptions())));
5770
5894
  this.#open = open;
5771
5895
  return open;
5772
5896
  }
@@ -5806,12 +5930,12 @@ var Arrangement = class _Arrangement {
5806
5930
  #scoreOptions() {
5807
5931
  const settings = this.#data.settings;
5808
5932
  const opts = {};
5809
- if (_optionalChain([settings, 'optionalAccess', _49 => _49.meters]) !== void 0) {
5933
+ if (_optionalChain([settings, 'optionalAccess', _53 => _53.meters]) !== void 0) {
5810
5934
  opts.meters = settings.meters;
5811
- } else if (_optionalChain([settings, 'optionalAccess', _50 => _50.ts]) !== void 0) {
5935
+ } else if (_optionalChain([settings, 'optionalAccess', _54 => _54.ts]) !== void 0) {
5812
5936
  opts.meters = settings.ts;
5813
5937
  }
5814
- if (_optionalChain([settings, 'optionalAccess', _51 => _51.key]) !== void 0) {
5938
+ if (_optionalChain([settings, 'optionalAccess', _55 => _55.key]) !== void 0) {
5815
5939
  opts.key = settings.key;
5816
5940
  }
5817
5941
  return opts;
@@ -5847,7 +5971,9 @@ function copyProfile(profile) {
5847
5971
  }
5848
5972
  const reach = {};
5849
5973
  for (const [pitch, limbs] of Object.entries(profile.reach)) {
5850
- reach[Number(pitch)] = [...limbs];
5974
+ if (String(Number(pitch)) === pitch) {
5975
+ reach[Number(pitch)] = [...limbs];
5976
+ }
5851
5977
  }
5852
5978
  const percussion = {
5853
5979
  kind: "percussion",
@@ -5861,7 +5987,7 @@ function copyProfile(profile) {
5861
5987
  return percussion;
5862
5988
  }
5863
5989
  function checkedProfile(profile) {
5864
- return copyProfile(_chunkCGBADIO5cjs.toInstrumentProfile.call(void 0, profile));
5990
+ return copyProfile(_chunkWOMCXN2Wcjs.toInstrumentProfile.call(void 0, profile));
5865
5991
  }
5866
5992
  var Instrument = class _Instrument {
5867
5993
  #profile;
@@ -5897,7 +6023,7 @@ var Instrument = class _Instrument {
5897
6023
  * @returns The instrument.
5898
6024
  */
5899
6025
  static guitar() {
5900
- return _Instrument.of(_chunkCGBADIO5cjs.GUITAR_STANDARD);
6026
+ return _Instrument.of(_chunkWOMCXN2Wcjs.GUITAR_STANDARD);
5901
6027
  }
5902
6028
  /**
5903
6029
  * Six-string guitar in drop D: the lowest string down a tone to D2, the rest
@@ -5906,7 +6032,7 @@ var Instrument = class _Instrument {
5906
6032
  * @returns The instrument.
5907
6033
  */
5908
6034
  static guitarDropD() {
5909
- return _Instrument.of(_chunkCGBADIO5cjs.GUITAR_DROP_D);
6035
+ return _Instrument.of(_chunkWOMCXN2Wcjs.GUITAR_DROP_D);
5910
6036
  }
5911
6037
  /**
5912
6038
  * Electric bass in standard tuning: E1 A1 D2 G2.
@@ -5914,7 +6040,7 @@ var Instrument = class _Instrument {
5914
6040
  * @returns The instrument.
5915
6041
  */
5916
6042
  static bass4() {
5917
- return _Instrument.of(_chunkCGBADIO5cjs.BASS_4_STRING);
6043
+ return _Instrument.of(_chunkWOMCXN2Wcjs.BASS_4_STRING);
5918
6044
  }
5919
6045
  /**
5920
6046
  * Five-string bass with the low B: B0 E1 A1 D2 G2.
@@ -5927,7 +6053,7 @@ var Instrument = class _Instrument {
5927
6053
  * ```
5928
6054
  */
5929
6055
  static bass5() {
5930
- return _Instrument.of(_chunkCGBADIO5cjs.BASS_5_STRING);
6056
+ return _Instrument.of(_chunkWOMCXN2Wcjs.BASS_5_STRING);
5931
6057
  }
5932
6058
  /**
5933
6059
  * Rebuild an instrument from the plain profile {@link Instrument.data} hands
@@ -5985,7 +6111,7 @@ var Instrument = class _Instrument {
5985
6111
  * ```
5986
6112
  */
5987
6113
  range() {
5988
- return _chunkCGBADIO5cjs.rangeIn.call(void 0, this.#profile);
6114
+ return _chunkWOMCXN2Wcjs.rangeIn.call(void 0, this.#profile);
5989
6115
  }
5990
6116
  /**
5991
6117
  * Whether the instrument has this pitch at all.
@@ -5995,8 +6121,8 @@ var Instrument = class _Instrument {
5995
6121
  * produces it.
5996
6122
  */
5997
6123
  canSound(pitch) {
5998
- _chunkS5BKZZGMcjs.assertMidiPitch.call(void 0, pitch, "pitch");
5999
- return _chunkCGBADIO5cjs.soundsIn.call(void 0, this.#profile, pitch);
6124
+ _chunkS3QELJUEcjs.assertMidiPitch.call(void 0, pitch, "pitch");
6125
+ return _chunkWOMCXN2Wcjs.soundsIn.call(void 0, this.#profile, pitch);
6000
6126
  }
6001
6127
  /**
6002
6128
  * Every position on the neck that sounds a pitch, lowest string first.
@@ -6008,10 +6134,10 @@ var Instrument = class _Instrument {
6008
6134
  fingerings(pitch) {
6009
6135
  const profile = this.#profile;
6010
6136
  if (profile.kind !== "stringed") {
6011
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(`${profile.name} has no strings to finger`);
6137
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(`${profile.name} has no strings to finger`);
6012
6138
  }
6013
- _chunkS5BKZZGMcjs.assertMidiPitch.call(void 0, pitch, "pitch");
6014
- return _chunkCGBADIO5cjs.fingeringsIn.call(void 0, profile, pitch);
6139
+ _chunkS3QELJUEcjs.assertMidiPitch.call(void 0, pitch, "pitch");
6140
+ return _chunkWOMCXN2Wcjs.fingeringsIn.call(void 0, profile, pitch);
6015
6141
  }
6016
6142
  /**
6017
6143
  * Move a pitch by whole octaves until the instrument can sound it, which is
@@ -6028,8 +6154,8 @@ var Instrument = class _Instrument {
6028
6154
  * ```
6029
6155
  */
6030
6156
  foldIntoRange(pitch) {
6031
- _chunkS5BKZZGMcjs.assertMidiPitch.call(void 0, pitch, "pitch");
6032
- return _chunkCGBADIO5cjs.foldIn.call(void 0, pitch, this.#profile);
6157
+ _chunkS3QELJUEcjs.assertMidiPitch.call(void 0, pitch, "pitch");
6158
+ return _chunkWOMCXN2Wcjs.foldIn.call(void 0, pitch, this.#profile);
6033
6159
  }
6034
6160
  /**
6035
6161
  * The pitch this instrument sounds for a note written in its part.
@@ -6061,7 +6187,7 @@ var Instrument = class _Instrument {
6061
6187
  * ```
6062
6188
  */
6063
6189
  soundingPitch(note, transposition = this.#profile.name) {
6064
- return new Note(_chunk76ZBTRG2cjs.toSoundingPitch.call(void 0, _chunkS5BKZZGMcjs.toNoteData.call(void 0, note), transposition));
6190
+ return new Note(_chunkU4EQTDGNcjs.toSoundingPitch.call(void 0, _chunkS3QELJUEcjs.toNoteData.call(void 0, note), transposition));
6065
6191
  }
6066
6192
  /**
6067
6193
  * Judge whether a passage can be played on this instrument, and how hard it
@@ -6087,7 +6213,7 @@ var Instrument = class _Instrument {
6087
6213
  * ```
6088
6214
  */
6089
6215
  playability(notes, bpm) {
6090
- return _chunkCGBADIO5cjs.playability.call(void 0, notes, this.#profile, bpm);
6216
+ return _chunkWOMCXN2Wcjs.playability.call(void 0, notes, this.#profile, bpm);
6091
6217
  }
6092
6218
  /**
6093
6219
  * Whether another instrument is described identically.
@@ -6147,7 +6273,7 @@ function copyComplexity(complexity) {
6147
6273
  for (const dial of ["rhythmic", "harmonic", "ornament", "difficulty"]) {
6148
6274
  const value = complexity[dial];
6149
6275
  if (value !== void 0) {
6150
- copy[dial] = _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, value, `composer complexity ${dial}`);
6276
+ copy[dial] = _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, value, `composer complexity ${dial}`);
6151
6277
  }
6152
6278
  }
6153
6279
  return copy;
@@ -6163,10 +6289,10 @@ function copyInstruments(instruments) {
6163
6289
  function copyOptions(options) {
6164
6290
  assertDataObject(options, "composer options");
6165
6291
  const copy = {
6166
- meters: _chunkS5BKZZGMcjs.resolveMeters.call(void 0, { meters: options.meters }, "composer meters")
6292
+ meters: _chunkS3QELJUEcjs.resolveMeters.call(void 0, { meters: options.meters }, "composer meters")
6167
6293
  };
6168
6294
  if (options.key !== void 0) {
6169
- copy.key = _chunk3R3QVKY5cjs.resolveKey.call(void 0, options.key);
6295
+ copy.key = _chunkYDGMWH43cjs.resolveKey.call(void 0, options.key);
6170
6296
  }
6171
6297
  if (options.bpm !== void 0) {
6172
6298
  copy.bpm = options.bpm;
@@ -6192,7 +6318,7 @@ function copyOptions(options) {
6192
6318
  if (options.rng !== void 0) {
6193
6319
  copy.rng = options.rng;
6194
6320
  }
6195
- const resolved = _chunkB2PW6EHNcjs.resolveContext.call(void 0, contextOf(copy));
6321
+ const resolved = _chunk6TTBEON3cjs.resolveContext.call(void 0, contextOf(copy));
6196
6322
  copy.seed = resolved.seed;
6197
6323
  copy.algorithmVersion = resolved.algorithmVersion;
6198
6324
  return copy;
@@ -6249,8 +6375,8 @@ var Composer = class _Composer {
6249
6375
  */
6250
6376
  constructor(options) {
6251
6377
  this.#options = copyOptions(options);
6252
- this.#meters = _chunkS5BKZZGMcjs.resolveMeters.call(void 0, { meters: this.#options.meters }, "composer meters");
6253
- this.#key = this.#options.key === void 0 ? void 0 : _chunk3R3QVKY5cjs.resolveKey.call(void 0, this.#options.key);
6378
+ this.#meters = _chunkS3QELJUEcjs.resolveMeters.call(void 0, { meters: this.#options.meters }, "composer meters");
6379
+ this.#key = this.#options.key === void 0 ? void 0 : _chunkYDGMWH43cjs.resolveKey.call(void 0, this.#options.key);
6254
6380
  }
6255
6381
  /**
6256
6382
  * Start from a set of settings.
@@ -6307,8 +6433,8 @@ var Composer = class _Composer {
6307
6433
  progression(opts) {
6308
6434
  const key = this.#requireKey("progression");
6309
6435
  const ts = this.#unchangingMeter("progression");
6310
- const chords = _chunkB2PW6EHNcjs.generateProgression.call(void 0, { ...opts, key, ts, ctx: this.context });
6311
- return Timeline.fromChords(chords, opts.bars * _chunkS5BKZZGMcjs.beatsPerBar.call(void 0, ts), key);
6436
+ const chords = _chunk6TTBEON3cjs.generateProgression.call(void 0, { ...opts, key, ts, ctx: this.context });
6437
+ return Timeline.fromChords(chords, opts.bars * _chunkS3QELJUEcjs.beatsPerBar.call(void 0, ts), key);
6312
6438
  }
6313
6439
  /**
6314
6440
  * A drum part.
@@ -6327,7 +6453,7 @@ var Composer = class _Composer {
6327
6453
  * request is refused rather than answered with 4/4 bars over the change.
6328
6454
  */
6329
6455
  drums(opts) {
6330
- const hits = _chunkB2PW6EHNcjs.generateDrums.call(void 0, { ...opts, ts: this.#unchangingMeter("drums"), ctx: this.context });
6456
+ const hits = _chunk6TTBEON3cjs.generateDrums.call(void 0, { ...opts, ts: this.#unchangingMeter("drums"), ctx: this.context });
6331
6457
  return Score.of(hits, this.#scoreOptions());
6332
6458
  }
6333
6459
  /**
@@ -6354,12 +6480,12 @@ var Composer = class _Composer {
6354
6480
  const segments = Array.isArray(source) ? source : source.segments;
6355
6481
  const key = this.#requireKey("bass");
6356
6482
  const { instrument, ...rest } = _nullishCoalesce(opts, () => ( {}));
6357
- const notes = _chunkB2PW6EHNcjs.generateBassLine.call(void 0, {
6483
+ const notes = _chunk6TTBEON3cjs.generateBassLine.call(void 0, {
6358
6484
  ...rest,
6359
- ...instrument === void 0 ? {} : { instrument: _chunkCGBADIO5cjs.toStringedProfile.call(void 0, instrument, "bass instrument") },
6485
+ ...instrument === void 0 ? {} : { instrument: _chunkWOMCXN2Wcjs.toStringedProfile.call(void 0, instrument, "bass instrument") },
6360
6486
  segments,
6361
6487
  key,
6362
- ts: this.#openingMeter(),
6488
+ ts: this.#meters,
6363
6489
  ctx: this.context
6364
6490
  });
6365
6491
  return Score.of(notes, this.#scoreOptions(key));
@@ -6386,12 +6512,12 @@ var Composer = class _Composer {
6386
6512
  counterMelody(melody, opts) {
6387
6513
  const key = this.#requireKey("counterMelody");
6388
6514
  const { timeline, ...rest } = _nullishCoalesce(opts, () => ( {}));
6389
- const notes = _chunkB2PW6EHNcjs.generateCounterMelody.call(void 0, {
6515
+ const notes = _chunk6TTBEON3cjs.generateCounterMelody.call(void 0, {
6390
6516
  ...rest,
6391
6517
  ...timeline === void 0 ? {} : { timeline: toChordTimeline(timeline) },
6392
6518
  melody: melody.notes,
6393
6519
  key,
6394
- ts: this.#openingMeter(),
6520
+ ts: this.#meters,
6395
6521
  ctx: this.context
6396
6522
  });
6397
6523
  return Score.of(notes, this.#scoreOptions(key));
@@ -6417,18 +6543,19 @@ var Composer = class _Composer {
6417
6543
  * ```
6418
6544
  */
6419
6545
  harmonize(melody, opts) {
6420
- const result = _chunkB2PW6EHNcjs.harmonizeMelody.call(void 0, {
6546
+ const result = _chunk6TTBEON3cjs.harmonizeMelody.call(void 0, {
6421
6547
  ...opts,
6422
6548
  melody: melody.notes,
6423
6549
  ...this.#key === void 0 ? {} : { key: this.#key },
6424
- ts: this.#openingMeter(),
6550
+ ts: this.#meters,
6425
6551
  ctx: this.context
6426
6552
  });
6427
6553
  const moved = melody.transpose(result.transposeSemitones);
6554
+ const last = result.chords[result.chords.length - 1];
6428
6555
  const totalBeats = harmonizedSpan(
6429
6556
  moved.totalBeats,
6430
6557
  result.chords,
6431
- _chunkS5BKZZGMcjs.beatsPerBar.call(void 0, this.#openingMeter())
6558
+ _chunkS3QELJUEcjs.beatsPerBarAt.call(void 0, _nullishCoalesce(_optionalChain([last, 'optionalAccess', _56 => _56.startBeat]), () => ( 0)), this.#meters)
6432
6559
  );
6433
6560
  return {
6434
6561
  chords: Timeline.fromChords(result.chords, totalBeats, result.key),
@@ -6466,11 +6593,11 @@ var Composer = class _Composer {
6466
6593
  plan(reference, opts) {
6467
6594
  const ctx = this.context;
6468
6595
  if (ctx.rng !== void 0) {
6469
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
6596
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
6470
6597
  "composer plan cannot record a caller-held rng; give the composer a seed instead"
6471
6598
  );
6472
6599
  }
6473
- return _chunkB2PW6EHNcjs.deriveCompositionPlan.call(void 0, reference, {
6600
+ return _chunk6TTBEON3cjs.deriveCompositionPlan.call(void 0, reference, {
6474
6601
  ...this.#key === void 0 ? {} : { key: this.#key },
6475
6602
  ...opts,
6476
6603
  ctx
@@ -6498,7 +6625,7 @@ var Composer = class _Composer {
6498
6625
  * ```
6499
6626
  */
6500
6627
  melody(plan, opts) {
6501
- const notes = _chunkB2PW6EHNcjs.generateMelody.call(void 0, plan, opts);
6628
+ const notes = _chunk6TTBEON3cjs.generateMelody.call(void 0, plan, opts);
6502
6629
  const score = { meters: plan.meters, key: plan.keys[0] };
6503
6630
  if (this.#options.bpm !== void 0) {
6504
6631
  score.tempo = this.#options.bpm;
@@ -6557,22 +6684,12 @@ var Composer = class _Composer {
6557
6684
  */
6558
6685
  #requireKey(part) {
6559
6686
  if (this.#key === void 0) {
6560
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
6687
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
6561
6688
  `composer ${part} needs a key for the part it writes; the composer names none \u2014 give it one, or take the key harmonize reads off a melody and pass it on with with({ key })`
6562
6689
  );
6563
6690
  }
6564
6691
  return this.#key;
6565
6692
  }
6566
- /**
6567
- * The signature the parts are written against.
6568
- *
6569
- * Each generator names one time signature rather than a map, so a composer
6570
- * whose meter changes hands over the signature its music opens on — the same
6571
- * reading {@link Score.humanize} and its siblings take.
6572
- */
6573
- #openingMeter() {
6574
- return _chunkS5BKZZGMcjs.meterAt.call(void 0, 0, this.#meters);
6575
- }
6576
6693
  /**
6577
6694
  * The one signature a part laid out in bars is written against.
6578
6695
  *
@@ -6583,11 +6700,11 @@ var Composer = class _Composer {
6583
6700
  */
6584
6701
  #unchangingMeter(part) {
6585
6702
  if (this.#meters.length > 1) {
6586
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)(
6703
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)(
6587
6704
  `composer ${part} needs one meter for the whole part; the composer changes meter`
6588
6705
  );
6589
6706
  }
6590
- return this.#openingMeter();
6707
+ return _chunkS3QELJUEcjs.meterAt.call(void 0, 0, this.#meters);
6591
6708
  }
6592
6709
  /** The context every score a composer hands back is read against. */
6593
6710
  #scoreOptions(key) {
@@ -6604,7 +6721,7 @@ var Composer = class _Composer {
6604
6721
 
6605
6722
  // src/model/duration.ts
6606
6723
  function copyDuration(value) {
6607
- _chunkNM7UAMC3cjs.durationToBeats.call(void 0, value);
6724
+ _chunk3FDBMIPRcjs.durationToBeats.call(void 0, value);
6608
6725
  if (typeof value === "string") {
6609
6726
  return { base: value, dots: 0 };
6610
6727
  }
@@ -6655,7 +6772,7 @@ var Duration = class _Duration {
6655
6772
  * {@link Duration.tieChain} for those.
6656
6773
  */
6657
6774
  static ofBeats(beats, options = {}) {
6658
- return new _Duration(_chunkNM7UAMC3cjs.beatsToDuration.call(void 0, beats, options));
6775
+ return new _Duration(_chunk3FDBMIPRcjs.beatsToDuration.call(void 0, beats, options));
6659
6776
  }
6660
6777
  /**
6661
6778
  * Spell a length in beats as a chain of tied durations.
@@ -6679,7 +6796,7 @@ var Duration = class _Duration {
6679
6796
  * ```
6680
6797
  */
6681
6798
  static tieChain(beats, options = {}) {
6682
- return _chunkNM7UAMC3cjs.beatsToTiedDurations.call(void 0, beats, options).map((spelled) => new _Duration(spelled));
6799
+ return _chunk3FDBMIPRcjs.beatsToTiedDurations.call(void 0, beats, options).map((spelled) => new _Duration(spelled));
6683
6800
  }
6684
6801
  /**
6685
6802
  * Wrap a plain duration, or a bare base value as shorthand for an undotted
@@ -6743,7 +6860,7 @@ var Duration = class _Duration {
6743
6860
  * ```
6744
6861
  */
6745
6862
  beats(options = {}) {
6746
- return _chunkNM7UAMC3cjs.durationToBeats.call(void 0, this.toJSON(), options);
6863
+ return _chunk3FDBMIPRcjs.durationToBeats.call(void 0, this.toJSON(), options);
6747
6864
  }
6748
6865
  /**
6749
6866
  * Whether another duration is written identically.
@@ -6757,7 +6874,7 @@ var Duration = class _Duration {
6757
6874
  */
6758
6875
  equals(other) {
6759
6876
  const b = other.data;
6760
- return this.#base === b.base && this.#dots === b.dots && _optionalChain([this, 'access', _52 => _52.#tuplet, 'optionalAccess', _53 => _53.actual]) === _optionalChain([b, 'access', _54 => _54.tuplet, 'optionalAccess', _55 => _55.actual]) && _optionalChain([this, 'access', _56 => _56.#tuplet, 'optionalAccess', _57 => _57.normal]) === _optionalChain([b, 'access', _58 => _58.tuplet, 'optionalAccess', _59 => _59.normal]);
6877
+ return this.#base === b.base && this.#dots === b.dots && _optionalChain([this, 'access', _57 => _57.#tuplet, 'optionalAccess', _58 => _58.actual]) === _optionalChain([b, 'access', _59 => _59.tuplet, 'optionalAccess', _60 => _60.actual]) && _optionalChain([this, 'access', _61 => _61.#tuplet, 'optionalAccess', _62 => _62.normal]) === _optionalChain([b, 'access', _63 => _63.tuplet, 'optionalAccess', _64 => _64.normal]);
6761
6878
  }
6762
6879
  /**
6763
6880
  * The plain duration, for JSON serialization.
@@ -6824,7 +6941,7 @@ var Meter = class _Meter {
6824
6941
  * is ordinary, such as a meter field read on every keystroke.
6825
6942
  */
6826
6943
  static parse(text) {
6827
- return new _Meter(_chunkS5BKZZGMcjs.parseTimeSignature.call(void 0, text));
6944
+ return new _Meter(_chunkS3QELJUEcjs.parseTimeSignature.call(void 0, text));
6828
6945
  }
6829
6946
  /**
6830
6947
  * Parse a time signature, reporting failure instead of throwing it.
@@ -6843,7 +6960,7 @@ var Meter = class _Meter {
6843
6960
  * ```
6844
6961
  */
6845
6962
  static tryParse(text) {
6846
- const parsed = _chunkS5BKZZGMcjs.tryParseTimeSignature.call(void 0, text);
6963
+ const parsed = _chunkS3QELJUEcjs.tryParseTimeSignature.call(void 0, text);
6847
6964
  return parsed.ok ? { ok: true, value: new _Meter(parsed.value) } : parsed;
6848
6965
  }
6849
6966
  /**
@@ -6888,22 +7005,22 @@ var Meter = class _Meter {
6888
7005
  * neither is a signature whose grouping selects the additive reading.
6889
7006
  */
6890
7007
  get isCompound() {
6891
- return _chunkS5BKZZGMcjs.isCompound.call(void 0, this.#ts);
7008
+ return _chunkS3QELJUEcjs.isCompound.call(void 0, this.#ts);
6892
7009
  }
6893
7010
  /** Length of a bar in quarter-note beats. */
6894
7011
  get beatsPerBar() {
6895
- return _chunkS5BKZZGMcjs.beatsPerBar.call(void 0, this.#ts);
7012
+ return _chunkS3QELJUEcjs.beatsPerBar.call(void 0, this.#ts);
6896
7013
  }
6897
7014
  /** Main pulses (felt beats) in a bar: 2 in 6/8, 4 in 4/4. */
6898
7015
  get pulsesPerBar() {
6899
- return _chunkS5BKZZGMcjs.pulsesPerBar.call(void 0, this.#ts);
7016
+ return _chunkS3QELJUEcjs.pulsesPerBar.call(void 0, this.#ts);
6900
7017
  }
6901
7018
  /**
6902
7019
  * Length of one felt beat in quarter-note beats: a quarter note in simple
6903
7020
  * meters, a dotted quarter in compound ones.
6904
7021
  */
6905
7022
  get pulseBeats() {
6906
- return _chunkS5BKZZGMcjs.pulseBeats.call(void 0, this.#ts);
7023
+ return _chunkS3QELJUEcjs.pulseBeats.call(void 0, this.#ts);
6907
7024
  }
6908
7025
  /**
6909
7026
  * Render the signature as `'n/d'`, or as `'a+b+c/d'` when it carries an
@@ -6926,7 +7043,7 @@ var Meter = class _Meter {
6926
7043
  * ```
6927
7044
  */
6928
7045
  format(opts = {}) {
6929
- return _chunkS5BKZZGMcjs.formatTimeSignature.call(void 0, this.#ts, opts);
7046
+ return _chunkS3QELJUEcjs.formatTimeSignature.call(void 0, this.#ts, opts);
6930
7047
  }
6931
7048
  /**
6932
7049
  * Metric weight of a position within its bar, on a 0–3 scale: 3 the
@@ -6939,7 +7056,7 @@ var Meter = class _Meter {
6939
7056
  * @throws If the position is not finite.
6940
7057
  */
6941
7058
  weightAt(beatInQuarters) {
6942
- return _chunkS5BKZZGMcjs.metricWeight.call(void 0, beatInQuarters, this.#ts);
7059
+ return _chunkS3QELJUEcjs.metricWeight.call(void 0, beatInQuarters, this.#ts);
6943
7060
  }
6944
7061
  /**
6945
7062
  * Whether a position is metrically accented — a downbeat or a secondary
@@ -6950,7 +7067,7 @@ var Meter = class _Meter {
6950
7067
  * @throws If the position is not finite.
6951
7068
  */
6952
7069
  isStrongBeat(beatInQuarters) {
6953
- return _chunkS5BKZZGMcjs.isStrongBeat.call(void 0, beatInQuarters, this.#ts);
7070
+ return _chunkS3QELJUEcjs.isStrongBeat.call(void 0, beatInQuarters, this.#ts);
6954
7071
  }
6955
7072
  /**
6956
7073
  * Convert a position in quarter-note beats to a bar index and in-bar offset.
@@ -6960,7 +7077,7 @@ var Meter = class _Meter {
6960
7077
  * @throws If the position is not finite.
6961
7078
  */
6962
7079
  barPositionAt(beatInQuarters) {
6963
- return _chunkS5BKZZGMcjs.beatToBarPosition.call(void 0, beatInQuarters, this.#ts);
7080
+ return _chunkS3QELJUEcjs.beatToBarPosition.call(void 0, beatInQuarters, this.#ts);
6964
7081
  }
6965
7082
  /**
6966
7083
  * Render a position as the `bar.beat` a DAW or a score shows: 1-based bar,
@@ -6983,7 +7100,7 @@ var Meter = class _Meter {
6983
7100
  * ```
6984
7101
  */
6985
7102
  formatPosition(beatInQuarters, decimals = 2) {
6986
- return _chunkS5BKZZGMcjs.formatBarPosition.call(void 0, beatInQuarters, this.#ts, decimals);
7103
+ return _chunkS3QELJUEcjs.formatBarPosition.call(void 0, beatInQuarters, this.#ts, decimals);
6987
7104
  }
6988
7105
  /**
6989
7106
  * Subdivide a span into equal tuplet durations — an eighth-note triplet is
@@ -6995,7 +7112,7 @@ var Meter = class _Meter {
6995
7112
  * @throws If the span is negative or `count` is not a positive integer.
6996
7113
  */
6997
7114
  tuplet(totalBeats, count) {
6998
- return _chunkS5BKZZGMcjs.tuplet.call(void 0, totalBeats, count);
7115
+ return _chunkS3QELJUEcjs.tuplet.call(void 0, totalBeats, count);
6999
7116
  }
7000
7117
  /**
7001
7118
  * Whether another meter is the same signature, grouping included.
@@ -7013,7 +7130,7 @@ var Meter = class _Meter {
7013
7130
  if (grouping === void 0 || b.grouping === void 0) {
7014
7131
  return this.#ts.numerator === b.numerator && this.#ts.denominator === b.denominator && grouping === b.grouping;
7015
7132
  }
7016
- return this.#ts.numerator === b.numerator && this.#ts.denominator === b.denominator && grouping.length === b.grouping.length && grouping.every((entry, index) => entry === _optionalChain([b, 'access', _60 => _60.grouping, 'optionalAccess', _61 => _61[index]]));
7133
+ return this.#ts.numerator === b.numerator && this.#ts.denominator === b.denominator && grouping.length === b.grouping.length && grouping.every((entry, index) => entry === _optionalChain([b, 'access', _65 => _65.grouping, 'optionalAccess', _66 => _66[index]]));
7017
7134
  }
7018
7135
  /**
7019
7136
  * The plain time signature, for JSON serialization.
@@ -7052,7 +7169,7 @@ function copyCell(cell) {
7052
7169
  return { notes: assertNoteEventArray(cell.notes, "motif notes").map(copyNote2) };
7053
7170
  }
7054
7171
  function chordFrom(chord) {
7055
- return chord === void 0 || chord === null ? chord : _chunk3R3QVKY5cjs.toChordData.call(void 0, chord);
7172
+ return chord === void 0 || chord === null ? chord : _chunkYDGMWH43cjs.toChordData.call(void 0, chord);
7056
7173
  }
7057
7174
  var Motif = class _Motif {
7058
7175
  #cell;
@@ -7084,7 +7201,8 @@ var Motif = class _Motif {
7084
7201
  * ```
7085
7202
  */
7086
7203
  static generate(opts) {
7087
- return new _Motif(_chunkB2PW6EHNcjs.generateMotif.call(void 0, { ...opts, chord: chordFrom(opts.chord) }));
7204
+ _chunkS3QELJUEcjs.assertRecord.call(void 0, opts, "motif options");
7205
+ return new _Motif(_chunk6TTBEON3cjs.generateMotif.call(void 0, { ...opts, chord: chordFrom(opts.chord) }));
7088
7206
  }
7089
7207
  /**
7090
7208
  * Read a run of notes as a motif.
@@ -7098,7 +7216,7 @@ var Motif = class _Motif {
7098
7216
  * @throws If a note carries a value the transforms cannot hold.
7099
7217
  */
7100
7218
  static fromNotes(notes) {
7101
- return new _Motif({ notes: [...notes] });
7219
+ return new _Motif({ notes: [..._chunkS3QELJUEcjs.assertArray.call(void 0, notes, "motif notes")] });
7102
7220
  }
7103
7221
  /** Rebuild a motif from the plain data {@link Motif.data} hands out. */
7104
7222
  static fromData(cell) {
@@ -7114,7 +7232,7 @@ var Motif = class _Motif {
7114
7232
  }
7115
7233
  /** Where the cell stops sounding, measured from its own first onset. */
7116
7234
  get totalBeats() {
7117
- return _chunkB2PW6EHNcjs.cellSpan.call(void 0, this.#cell);
7235
+ return _chunk6TTBEON3cjs.cellSpan.call(void 0, this.#cell);
7118
7236
  }
7119
7237
  /** A copy of the underlying plain cell. */
7120
7238
  get data() {
@@ -7151,7 +7269,7 @@ var Motif = class _Motif {
7151
7269
  * ```
7152
7270
  */
7153
7271
  transform(kind, amount, key) {
7154
- return new _Motif(_chunkB2PW6EHNcjs.transformMotif.call(void 0, this.#cell, kind, amount, key));
7272
+ return new _Motif(_chunk6TTBEON3cjs.transformMotif.call(void 0, this.#cell, kind, amount, key));
7155
7273
  }
7156
7274
  /**
7157
7275
  * The cell laid across a span and snapped to the harmony under it.
@@ -7173,7 +7291,7 @@ var Motif = class _Motif {
7173
7291
  */
7174
7292
  develop(timeline, key, bars, ts) {
7175
7293
  const chords = "chordTimeline" in timeline ? timeline.chordTimeline : timeline;
7176
- return new _Motif(_chunkB2PW6EHNcjs.developMotif.call(void 0, this.#cell, chords, key, bars, ts));
7294
+ return new _Motif(_chunk6TTBEON3cjs.developMotif.call(void 0, this.#cell, chords, key, bars, ts));
7177
7295
  }
7178
7296
  /**
7179
7297
  * How this motif stands to another: the transformation that turns one into
@@ -7187,7 +7305,7 @@ var Motif = class _Motif {
7187
7305
  * @returns The relation, or null when the two stand in none.
7188
7306
  */
7189
7307
  relateTo(other, key) {
7190
- return _chunkIFZDWIKMcjs.relateMotifs.call(void 0, _chunkIFZDWIKMcjs.motifFromNotes.call(void 0, this.#cell.notes), _chunkIFZDWIKMcjs.motifFromNotes.call(void 0, other.notes), key);
7308
+ return _chunkLQZQDBCDcjs.relateMotifs.call(void 0, _chunkLQZQDBCDcjs.motifFromNotes.call(void 0, this.#cell.notes), _chunkLQZQDBCDcjs.motifFromNotes.call(void 0, other.notes), key);
7191
7309
  }
7192
7310
  /**
7193
7311
  * How alike two lines are, in [0, 1].
@@ -7200,7 +7318,7 @@ var Motif = class _Motif {
7200
7318
  * @returns The likeness: 1 for the same line, a transposition of it included.
7201
7319
  */
7202
7320
  similarityTo(other) {
7203
- return _chunkIFZDWIKMcjs.melodicSimilarity.call(void 0, this.#cell.notes, other.notes);
7321
+ return _chunkLQZQDBCDcjs.melodicSimilarity.call(void 0, this.#cell.notes, other.notes);
7204
7322
  }
7205
7323
  /**
7206
7324
  * The cell as a score, so it reaches the rest of the class API.
@@ -7210,7 +7328,7 @@ var Motif = class _Motif {
7210
7328
  * @returns The score holding the cell.
7211
7329
  */
7212
7330
  toScore(opts) {
7213
- return Score.of(_chunkB2PW6EHNcjs.motifToNoteEvents.call(void 0, this.#cell), opts);
7331
+ return Score.of(_chunk6TTBEON3cjs.motifToNoteEvents.call(void 0, this.#cell), opts);
7214
7332
  }
7215
7333
  /**
7216
7334
  * Whether another motif holds the same notes in the same order.
@@ -7243,10 +7361,10 @@ var PART = "rhythm";
7243
7361
  function copyEvent(event, name) {
7244
7362
  return {
7245
7363
  position: withoutNegativeZero(
7246
- _chunkS5BKZZGMcjs.assertRange.call(void 0, event.position, 0, Number.MAX_SAFE_INTEGER, `${name}.position`)
7364
+ _chunkS3QELJUEcjs.assertRange.call(void 0, event.position, 0, Number.MAX_SAFE_INTEGER, `${name}.position`)
7247
7365
  ),
7248
7366
  duration: withoutNegativeZero(
7249
- _chunkS5BKZZGMcjs.assertRange.call(void 0, event.duration, 0, Number.MAX_SAFE_INTEGER, `${name}.duration`)
7367
+ _chunkS3QELJUEcjs.assertRange.call(void 0, event.duration, 0, Number.MAX_SAFE_INTEGER, `${name}.duration`)
7250
7368
  )
7251
7369
  };
7252
7370
  }
@@ -7265,13 +7383,13 @@ function spanOf(events) {
7265
7383
  }
7266
7384
  function toGrid(events) {
7267
7385
  return events.map((event) => ({
7268
- step: event.position / _chunkB2PW6EHNcjs.STEP_BEATS,
7386
+ step: event.position / _chunk6TTBEON3cjs.STEP_BEATS,
7269
7387
  velocity: GRID_VELOCITY,
7270
7388
  source: event
7271
7389
  }));
7272
7390
  }
7273
7391
  function fromGrid(events, spanBeats) {
7274
- const positions = [...new Set(events.map((event) => event.step * _chunkB2PW6EHNcjs.STEP_BEATS))].sort(
7392
+ const positions = [...new Set(events.map((event) => event.step * _chunk6TTBEON3cjs.STEP_BEATS))].sort(
7275
7393
  (a, b) => a - b
7276
7394
  );
7277
7395
  return positions.map((position, index) => ({
@@ -7311,8 +7429,8 @@ var Rhythm = class _Rhythm {
7311
7429
  * ```
7312
7430
  */
7313
7431
  static generate(ts, opts) {
7314
- const meter = _chunkS5BKZZGMcjs.meterAt.call(void 0, 0, _chunkS5BKZZGMcjs.toMeterData.call(void 0, ts, "ts"));
7315
- return new _Rhythm({ events: _chunkB2PW6EHNcjs.generateRhythm.call(void 0, meter, opts), ts: meter });
7432
+ const meter = _chunkS3QELJUEcjs.meterAt.call(void 0, 0, _chunkS3QELJUEcjs.toMeterData.call(void 0, ts, "ts"));
7433
+ return new _Rhythm({ events: _chunk6TTBEON3cjs.generateRhythm.call(void 0, meter, opts), ts: meter });
7316
7434
  }
7317
7435
  /**
7318
7436
  * Build a pattern from onsets that already exist.
@@ -7332,7 +7450,7 @@ var Rhythm = class _Rhythm {
7332
7450
  static of(events, ts) {
7333
7451
  return new _Rhythm({
7334
7452
  events: [...assertDataArray(events, "rhythm events")],
7335
- ts: _chunkS5BKZZGMcjs.meterAt.call(void 0, 0, _chunkS5BKZZGMcjs.toMeterData.call(void 0, ts, "ts"))
7453
+ ts: _chunkS3QELJUEcjs.meterAt.call(void 0, 0, _chunkS3QELJUEcjs.toMeterData.call(void 0, ts, "ts"))
7336
7454
  });
7337
7455
  }
7338
7456
  /** Rebuild a pattern from the plain data {@link Rhythm.data} hands out. */
@@ -7368,7 +7486,7 @@ var Rhythm = class _Rhythm {
7368
7486
  * @returns The onset count divided by the number of bars it spans.
7369
7487
  */
7370
7488
  density() {
7371
- return _chunkB2PW6EHNcjs.rhythmDensity.call(void 0, this.#data.events, this.#data.ts);
7489
+ return _chunk6TTBEON3cjs.rhythmDensity.call(void 0, this.#data.events, this.#data.ts);
7372
7490
  }
7373
7491
  /**
7374
7492
  * Drop the onsets carrying the least of the metre.
@@ -7383,7 +7501,7 @@ var Rhythm = class _Rhythm {
7383
7501
  * @throws If the amount is outside [0, 1].
7384
7502
  */
7385
7503
  thin(amount) {
7386
- return this.#withGrid(_chunkB2PW6EHNcjs.thin.call(void 0, toGrid(this.#data.events), amount, this.#data.ts));
7504
+ return this.#withGrid(_chunk6TTBEON3cjs.thin.call(void 0, toGrid(this.#data.events), amount, this.#data.ts));
7387
7505
  }
7388
7506
  /**
7389
7507
  * Anticipate beats, one sixteenth early.
@@ -7402,10 +7520,10 @@ var Rhythm = class _Rhythm {
7402
7520
  */
7403
7521
  syncopate(amount, ctx) {
7404
7522
  return this.#withGrid(
7405
- _chunkB2PW6EHNcjs.syncopate.call(void 0,
7523
+ _chunk6TTBEON3cjs.syncopate.call(void 0,
7406
7524
  toGrid(this.#data.events),
7407
7525
  { amount, ts: this.#data.ts },
7408
- _chunkB2PW6EHNcjs.resolveContext.call(void 0, ctx).part(PART)
7526
+ _chunk6TTBEON3cjs.resolveContext.call(void 0, ctx).part(PART)
7409
7527
  )
7410
7528
  );
7411
7529
  }
@@ -7417,7 +7535,7 @@ var Rhythm = class _Rhythm {
7417
7535
  * @returns The compressed pattern.
7418
7536
  */
7419
7537
  doubleTime() {
7420
- return this.#withGrid(_chunkB2PW6EHNcjs.doubleTime.call(void 0, toGrid(this.#data.events), this.#spanSteps()));
7538
+ return this.#withGrid(_chunk6TTBEON3cjs.doubleTimeFigure.call(void 0, toGrid(this.#data.events), this.#spanSteps()));
7421
7539
  }
7422
7540
  /**
7423
7541
  * Stretch the pattern to twice its length: everything falls half as often.
@@ -7428,7 +7546,7 @@ var Rhythm = class _Rhythm {
7428
7546
  * @returns The stretched pattern.
7429
7547
  */
7430
7548
  halfTime() {
7431
- return this.#withGrid(_chunkB2PW6EHNcjs.halfTime.call(void 0, toGrid(this.#data.events), this.#spanSteps()));
7549
+ return this.#withGrid(_chunk6TTBEON3cjs.halfTimeFigure.call(void 0, toGrid(this.#data.events), this.#spanSteps()));
7432
7550
  }
7433
7551
  /**
7434
7552
  * Keep as much decoration as the ornament dial asks for.
@@ -7445,11 +7563,11 @@ var Rhythm = class _Rhythm {
7445
7563
  */
7446
7564
  ornamentBy(isOrnament, amount, ctx) {
7447
7565
  return this.#withGrid(
7448
- _chunkB2PW6EHNcjs.ornamentBy.call(void 0,
7566
+ _chunk6TTBEON3cjs.ornamentBy.call(void 0,
7449
7567
  toGrid(this.#data.events),
7450
7568
  (grid) => isOrnament(grid.source),
7451
7569
  amount,
7452
- _chunkB2PW6EHNcjs.resolveContext.call(void 0, ctx).part(PART)
7570
+ _chunk6TTBEON3cjs.resolveContext.call(void 0, ctx).part(PART)
7453
7571
  )
7454
7572
  );
7455
7573
  }
@@ -7469,20 +7587,22 @@ var Rhythm = class _Rhythm {
7469
7587
  * @throws If a dial is outside [0, 1].
7470
7588
  */
7471
7589
  deform(opts, ctx) {
7472
- const resolved = _chunkB2PW6EHNcjs.resolveContext.call(void 0, ctx);
7473
- const isOrnament = _optionalChain([opts, 'optionalAccess', _62 => _62.isOrnament]);
7590
+ const resolved = _chunk6TTBEON3cjs.resolveContext.call(void 0, ctx);
7591
+ const isOrnament = _optionalChain([opts, 'optionalAccess', _67 => _67.isOrnament]);
7474
7592
  const options = {
7475
7593
  rhythmic: resolved.rhythmic,
7476
7594
  ornament: resolved.ornament,
7477
- rate: _optionalChain([opts, 'optionalAccess', _63 => _63.rate]),
7478
- spanSteps: this.#spanSteps(),
7595
+ rate: _optionalChain([opts, 'optionalAccess', _68 => _68.rate]),
7479
7596
  ts: this.#data.ts,
7480
7597
  // The transform hands the predicate the events it was given, which carry
7481
7598
  // the onset each was built from; the parameter is declared over the bare
7482
7599
  // grid event the rule reads, so the field is named back here.
7483
7600
  isOrnament: isOrnament === void 0 ? void 0 : (grid) => isOrnament(grid.source)
7484
7601
  };
7485
- return this.#withGrid(_chunkB2PW6EHNcjs.deform.call(void 0, toGrid(this.#data.events), options, resolved.part(PART)));
7602
+ const dials = _chunk6TTBEON3cjs.resolveDials.call(void 0, options);
7603
+ return this.#withGrid(
7604
+ _chunk6TTBEON3cjs.deformFigure.call(void 0, toGrid(this.#data.events), this.#spanSteps(), dials, resolved.part(PART), [])
7605
+ );
7486
7606
  }
7487
7607
  /**
7488
7608
  * Whether one player can sustain the pattern at the context's tempo.
@@ -7496,8 +7616,8 @@ var Rhythm = class _Rhythm {
7496
7616
  * @returns True when the pattern is inside the ceiling.
7497
7617
  */
7498
7618
  withinCeiling(ctx) {
7499
- const resolved = _chunkB2PW6EHNcjs.resolveContext.call(void 0, ctx);
7500
- return _chunkB2PW6EHNcjs.withinCeiling.call(void 0, toGrid(this.#data.events), resolved.bpm, resolved.difficulty);
7619
+ const resolved = _chunk6TTBEON3cjs.resolveContext.call(void 0, ctx);
7620
+ return _chunk6TTBEON3cjs.withinCeiling.call(void 0, toGrid(this.#data.events), resolved.bpm, resolved.difficulty);
7501
7621
  }
7502
7622
  /**
7503
7623
  * The pattern as sounding notes at one pitch, in its own meter.
@@ -7521,7 +7641,7 @@ var Rhythm = class _Rhythm {
7521
7641
  * ```
7522
7642
  */
7523
7643
  toScore(pitch, velocity) {
7524
- return Score.of(_chunkB2PW6EHNcjs.rhythmToNoteEvents.call(void 0, this.#data.events, pitch, velocity), {
7644
+ return Score.of(_chunk6TTBEON3cjs.rhythmToNoteEvents.call(void 0, this.#data.events, pitch, velocity), {
7525
7645
  meters: this.#data.ts
7526
7646
  });
7527
7647
  }
@@ -7543,9 +7663,13 @@ var Rhythm = class _Rhythm {
7543
7663
  toJSON() {
7544
7664
  return this.data;
7545
7665
  }
7546
- /** The pattern's span as a count of sixteenths, for the transforms. */
7666
+ /**
7667
+ * The pattern's span as a count of sixteenths, for the transforms: whatever
7668
+ * span the pattern covers, an empty one or one ending off the straight grid
7669
+ * included.
7670
+ */
7547
7671
  #spanSteps() {
7548
- return spanOf(this.#data.events) / _chunkB2PW6EHNcjs.STEP_BEATS;
7672
+ return spanOf(this.#data.events) / _chunk6TTBEON3cjs.STEP_BEATS;
7549
7673
  }
7550
7674
  /** The same meter carrying the onsets a transform returned. */
7551
7675
  #withGrid(events) {
@@ -7570,7 +7694,7 @@ var MIN_BPM = 0.1;
7570
7694
  var Tempo = class _Tempo {
7571
7695
  #bpm;
7572
7696
  constructor(bpm) {
7573
- this.#bpm = _chunkS5BKZZGMcjs.assertRange.call(void 0, bpm, MIN_BPM, MAX_BPM, "bpm");
7697
+ this.#bpm = _chunkS3QELJUEcjs.assertRange.call(void 0, bpm, MIN_BPM, MAX_BPM, "bpm");
7574
7698
  }
7575
7699
  /**
7576
7700
  * The one-event tempo map every conversion here is measured against.
@@ -7630,7 +7754,7 @@ var Tempo = class _Tempo {
7630
7754
  * @throws If the position is not finite.
7631
7755
  */
7632
7756
  secondsAt(beat) {
7633
- return _chunkNM7UAMC3cjs.beatsToSeconds.call(void 0, beat, this.#map);
7757
+ return _chunk3FDBMIPRcjs.beatsToSeconds.call(void 0, beat, this.#map);
7634
7758
  }
7635
7759
  /**
7636
7760
  * The position reached after a number of seconds — the inverse of
@@ -7647,7 +7771,7 @@ var Tempo = class _Tempo {
7647
7771
  * ```
7648
7772
  */
7649
7773
  beatAtSeconds(seconds) {
7650
- return _chunkNM7UAMC3cjs.secondsToBeats.call(void 0, seconds, this.#map);
7774
+ return _chunk3FDBMIPRcjs.secondsToBeats.call(void 0, seconds, this.#map);
7651
7775
  }
7652
7776
  /**
7653
7777
  * Duration in seconds of a span of beats.
@@ -7660,7 +7784,7 @@ var Tempo = class _Tempo {
7660
7784
  * @throws If the length is negative or not finite.
7661
7785
  */
7662
7786
  secondsOf(lengthBeats) {
7663
- return _chunkNM7UAMC3cjs.durationToSeconds.call(void 0, 0, lengthBeats, this.#map);
7787
+ return _chunk3FDBMIPRcjs.durationToSeconds.call(void 0, 0, lengthBeats, this.#map);
7664
7788
  }
7665
7789
  /**
7666
7790
  * Convert quarter-note beats to MIDI ticks, rounded to the nearest tick.
@@ -7671,7 +7795,7 @@ var Tempo = class _Tempo {
7671
7795
  * @throws If the position is not finite or `ppq` is not a positive integer.
7672
7796
  */
7673
7797
  ticksAt(beat, ppq) {
7674
- return _chunkNM7UAMC3cjs.beatsToTicks.call(void 0, beat, ppq);
7798
+ return _chunk3FDBMIPRcjs.beatsToTicks.call(void 0, beat, ppq);
7675
7799
  }
7676
7800
  /**
7677
7801
  * Convert MIDI ticks to quarter-note beats.
@@ -7682,7 +7806,7 @@ var Tempo = class _Tempo {
7682
7806
  * @throws If `ticks` is not an integer or `ppq` is not a positive integer.
7683
7807
  */
7684
7808
  beatAtTicks(ticks, ppq) {
7685
- return _chunkNM7UAMC3cjs.ticksToBeats.call(void 0, ticks, ppq);
7809
+ return _chunk3FDBMIPRcjs.ticksToBeats.call(void 0, ticks, ppq);
7686
7810
  }
7687
7811
  /**
7688
7812
  * Whether another tempo carries the same marking.
@@ -7742,10 +7866,10 @@ var Tuning = class _Tuning {
7742
7866
  */
7743
7867
  static of(table) {
7744
7868
  const given = assertDataObject(table, "tuning table");
7745
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, given.divisions, "tuning table.divisions");
7746
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, given.refFreq, "tuning table.refFreq");
7747
- _chunkS5BKZZGMcjs.assertFiniteNumber.call(void 0, given.refStep, "tuning table.refStep");
7748
- return new _Tuning(_chunkNM7UAMC3cjs.edo.call(void 0, given.divisions, given.refFreq, given.refStep));
7869
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, given.divisions, "tuning table.divisions");
7870
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, given.refFreq, "tuning table.refFreq");
7871
+ _chunkS3QELJUEcjs.assertFiniteNumber.call(void 0, given.refStep, "tuning table.refStep");
7872
+ return new _Tuning(_chunk3FDBMIPRcjs.edo.call(void 0, given.divisions, given.refFreq, given.refStep));
7749
7873
  }
7750
7874
  /**
7751
7875
  * Build an equal temperament with `divisions` divisions of the octave.
@@ -7766,7 +7890,7 @@ var Tuning = class _Tuning {
7766
7890
  * ```
7767
7891
  */
7768
7892
  static edo(divisions, refFreq, refStep) {
7769
- return new _Tuning(_chunkNM7UAMC3cjs.edo.call(void 0, divisions, refFreq, refStep));
7893
+ return new _Tuning(_chunk3FDBMIPRcjs.edo.call(void 0, divisions, refFreq, refStep));
7770
7894
  }
7771
7895
  /**
7772
7896
  * Standard twelve-tone equal temperament, A4 (MIDI 69) = 440 Hz.
@@ -7779,7 +7903,7 @@ var Tuning = class _Tuning {
7779
7903
  * ```
7780
7904
  */
7781
7905
  static twelveTet() {
7782
- return _Tuning.of(_chunkNM7UAMC3cjs.TWELVE_TET);
7906
+ return _Tuning.of(_chunk3FDBMIPRcjs.TWELVE_TET);
7783
7907
  }
7784
7908
  /**
7785
7909
  * Rebuild a tuning from the plain table {@link Tuning.data} hands out.
@@ -7818,7 +7942,7 @@ var Tuning = class _Tuning {
7818
7942
  * ```
7819
7943
  */
7820
7944
  static ratioToCents(numerator, denominator) {
7821
- return _chunkNM7UAMC3cjs.ratioToCents.call(void 0, numerator, denominator);
7945
+ return _chunk3FDBMIPRcjs.ratioToCents.call(void 0, numerator, denominator);
7822
7946
  }
7823
7947
  /**
7824
7948
  * The frequency ratio an interval in cents spans, the inverse of
@@ -7836,7 +7960,7 @@ var Tuning = class _Tuning {
7836
7960
  * ```
7837
7961
  */
7838
7962
  static centsToRatio(cents) {
7839
- return _chunkNM7UAMC3cjs.centsToRatio.call(void 0, cents);
7963
+ return _chunk3FDBMIPRcjs.centsToRatio.call(void 0, cents);
7840
7964
  }
7841
7965
  /**
7842
7966
  * Interval in cents between two frequencies.
@@ -7852,7 +7976,7 @@ var Tuning = class _Tuning {
7852
7976
  * ```
7853
7977
  */
7854
7978
  static centsBetweenFreq(a, b) {
7855
- return _chunkNM7UAMC3cjs.centsBetweenFreq.call(void 0, a, b);
7979
+ return _chunk3FDBMIPRcjs.centsBetweenFreq.call(void 0, a, b);
7856
7980
  }
7857
7981
  /**
7858
7982
  * Cents by which a five-limit just interval departs from its 12-TET
@@ -7868,7 +7992,7 @@ var Tuning = class _Tuning {
7868
7992
  * ```
7869
7993
  */
7870
7994
  static justDeviationCents(semitoneClass) {
7871
- return _chunkNM7UAMC3cjs.justDeviationCents.call(void 0, semitoneClass);
7995
+ return _chunk3FDBMIPRcjs.justDeviationCents.call(void 0, semitoneClass);
7872
7996
  }
7873
7997
  /** Step index whose frequency is {@link Tuning.refFreq}. */
7874
7998
  get refStep() {
@@ -7910,7 +8034,7 @@ var Tuning = class _Tuning {
7910
8034
  * ```
7911
8035
  */
7912
8036
  frequencyOf(note, tuning = this.#table) {
7913
- return _chunkNM7UAMC3cjs.frequencyOf.call(void 0, _chunkS5BKZZGMcjs.noteToMidi.call(void 0, _chunkS5BKZZGMcjs.toNoteData.call(void 0, note)), tuning);
8037
+ return _chunk3FDBMIPRcjs.frequencyOf.call(void 0, _chunkS3QELJUEcjs.noteToMidi.call(void 0, _chunkS3QELJUEcjs.toNoteData.call(void 0, note)), tuning);
7914
8038
  }
7915
8039
  /**
7916
8040
  * Frequency in Hz of a step index.
@@ -7932,7 +8056,7 @@ var Tuning = class _Tuning {
7932
8056
  * ```
7933
8057
  */
7934
8058
  frequencyOfStep(step, tuning = this.#table) {
7935
- return _chunkNM7UAMC3cjs.frequencyOf.call(void 0, step, tuning);
8059
+ return _chunk3FDBMIPRcjs.frequencyOf.call(void 0, step, tuning);
7936
8060
  }
7937
8061
  /**
7938
8062
  * Nearest step index to a frequency, the rounded inverse of
@@ -7949,7 +8073,7 @@ var Tuning = class _Tuning {
7949
8073
  * ```
7950
8074
  */
7951
8075
  nearestStep(freq, tuning = this.#table) {
7952
- return _chunkNM7UAMC3cjs.nearestStep.call(void 0, freq, tuning);
8076
+ return _chunk3FDBMIPRcjs.nearestStep.call(void 0, freq, tuning);
7953
8077
  }
7954
8078
  /**
7955
8079
  * Step index of a frequency, unrounded.
@@ -7969,7 +8093,7 @@ var Tuning = class _Tuning {
7969
8093
  * ```
7970
8094
  */
7971
8095
  stepOf(freq, tuning = this.#table) {
7972
- return _chunkNM7UAMC3cjs.stepOf.call(void 0, freq, tuning);
8096
+ return _chunk3FDBMIPRcjs.stepOf.call(void 0, freq, tuning);
7973
8097
  }
7974
8098
  /**
7975
8099
  * How far a frequency sits from its nearest step, in cents; positive means
@@ -7986,7 +8110,7 @@ var Tuning = class _Tuning {
7986
8110
  * ```
7987
8111
  */
7988
8112
  centsFromNearestStep(freq, tuning = this.#table) {
7989
- return _chunkNM7UAMC3cjs.centsFromNearestStep.call(void 0, freq, tuning);
8113
+ return _chunk3FDBMIPRcjs.centsFromNearestStep.call(void 0, freq, tuning);
7990
8114
  }
7991
8115
  /**
7992
8116
  * Cents spanned by a number of steps.
@@ -8002,7 +8126,7 @@ var Tuning = class _Tuning {
8002
8126
  * ```
8003
8127
  */
8004
8128
  centsOfSteps(steps, tuning = this.#table) {
8005
- return _chunkNM7UAMC3cjs.centsOfSteps.call(void 0, steps, tuning);
8129
+ return _chunk3FDBMIPRcjs.centsOfSteps.call(void 0, steps, tuning);
8006
8130
  }
8007
8131
  /**
8008
8132
  * Steps spanned by an interval in cents, unrounded — the inverse of
@@ -8019,7 +8143,7 @@ var Tuning = class _Tuning {
8019
8143
  * ```
8020
8144
  */
8021
8145
  stepsOfCents(cents, tuning = this.#table) {
8022
- return _chunkNM7UAMC3cjs.stepsOfCents.call(void 0, cents, tuning);
8146
+ return _chunk3FDBMIPRcjs.stepsOfCents.call(void 0, cents, tuning);
8023
8147
  }
8024
8148
  /**
8025
8149
  * Whether another tuning divides the octave the same way from the same
@@ -8068,17 +8192,17 @@ var Tuning = class _Tuning {
8068
8192
  function copyPitches(pitches) {
8069
8193
  assertDataArray(pitches, "voicing pitches");
8070
8194
  if (pitches.length === 0) {
8071
- throw new (0, _chunkS5BKZZGMcjs.InvalidInputError)("a voicing must contain at least one pitch");
8195
+ throw new (0, _chunkS3QELJUEcjs.InvalidInputError)("a voicing must contain at least one pitch");
8072
8196
  }
8073
- return pitches.map((pitch, index) => _chunkS5BKZZGMcjs.assertMidiPitch.call(void 0, pitch, `pitches[${index}]`));
8197
+ return pitches.map((pitch, index) => _chunkS3QELJUEcjs.assertMidiPitch.call(void 0, pitch, `pitches[${index}]`));
8074
8198
  }
8075
8199
  function spellLine(line, key) {
8076
8200
  return line.map(
8077
- (value) => typeof value === "number" ? _chunk3R3QVKY5cjs.spellPitch.call(void 0, value, key.tonic, key) : _chunkS5BKZZGMcjs.toNoteData.call(void 0, value)
8201
+ (value) => typeof value === "number" ? _chunkYDGMWH43cjs.spellPitch.call(void 0, value, key.tonic, key) : _chunkS3QELJUEcjs.toNoteData.call(void 0, value)
8078
8202
  );
8079
8203
  }
8080
8204
  function lineOf(pitches, key) {
8081
- return key === void 0 ? pitches.map((pitch) => _chunkS5BKZZGMcjs.toNoteData.call(void 0, pitch)) : spellLine(pitches, key);
8205
+ return key === void 0 ? pitches.map((pitch) => _chunkS3QELJUEcjs.toNoteData.call(void 0, pitch)) : spellLine(pitches, key);
8082
8206
  }
8083
8207
  function carriedKeyOf(chord) {
8084
8208
  if (typeof chord !== "object" || chord === null) {
@@ -8088,7 +8212,7 @@ function carriedKeyOf(chord) {
8088
8212
  return typeof key === "object" && key !== null ? key : void 0;
8089
8213
  }
8090
8214
  function withCarriedKey(chord, opts) {
8091
- if (_optionalChain([opts, 'optionalAccess', _64 => _64.key]) !== void 0) {
8215
+ if (_optionalChain([opts, 'optionalAccess', _69 => _69.key]) !== void 0) {
8092
8216
  return opts;
8093
8217
  }
8094
8218
  const key = carriedKeyOf(chord);
@@ -8134,7 +8258,7 @@ var Voicing = class _Voicing {
8134
8258
  * ```
8135
8259
  */
8136
8260
  static forChord(chord, opts) {
8137
- return new _Voicing(_chunk76ZBTRG2cjs.voiceChordStyled.call(void 0, chord, opts));
8261
+ return new _Voicing(_chunkU4EQTDGNcjs.voiceChordStyled.call(void 0, chord, opts));
8138
8262
  }
8139
8263
  /**
8140
8264
  * Realize a chord as one pitch per voice inside the voice ranges, defaulting
@@ -8158,7 +8282,7 @@ var Voicing = class _Voicing {
8158
8282
  * ```
8159
8283
  */
8160
8284
  static satb(chord, opts) {
8161
- return new _Voicing(_chunk76ZBTRG2cjs.voiceChord.call(void 0, _chunk3R3QVKY5cjs.toChordData.call(void 0, chord), withCarriedKey(chord, opts)));
8285
+ return new _Voicing(_chunkU4EQTDGNcjs.voiceChord.call(void 0, _chunkYDGMWH43cjs.toChordData.call(void 0, chord), withCarriedKey(chord, opts)));
8162
8286
  }
8163
8287
  /**
8164
8288
  * Wrap a plain pitch array, as {@link Voicing.data} hands it out.
@@ -8186,7 +8310,7 @@ var Voicing = class _Voicing {
8186
8310
  * four-voice exercise against.
8187
8311
  */
8188
8312
  static get satbRanges() {
8189
- return _chunk76ZBTRG2cjs.SATB_RANGES.map((range) => ({ min: range.min, max: range.max }));
8313
+ return _chunkU4EQTDGNcjs.SATB_RANGES.map((range) => ({ min: range.min, max: range.max }));
8190
8314
  }
8191
8315
  /** A copy of the sounding MIDI pitches, lowest voice first. */
8192
8316
  get pitches() {
@@ -8229,7 +8353,7 @@ var Voicing = class _Voicing {
8229
8353
  */
8230
8354
  spell(key, chord) {
8231
8355
  assertKeyArgument(key, "voicing key");
8232
- return this.#spelled(_chunk3R3QVKY5cjs.resolveKey.call(void 0, key), chord).map((note) => new Note(note));
8356
+ return this.#spelled(_chunkYDGMWH43cjs.resolveKey.call(void 0, key), chord).map((note) => new Note(note));
8233
8357
  }
8234
8358
  /**
8235
8359
  * Voice a chord to follow smoothly from this voicing.
@@ -8259,7 +8383,7 @@ var Voicing = class _Voicing {
8259
8383
  * ```
8260
8384
  */
8261
8385
  next(chord, opts) {
8262
- return new _Voicing(_chunk76ZBTRG2cjs.nextVoicing.call(void 0, this.pitches, _chunk3R3QVKY5cjs.toChordData.call(void 0, chord), withCarriedKey(chord, opts)));
8386
+ return new _Voicing(_chunkU4EQTDGNcjs.nextVoicing.call(void 0, this.pitches, _chunkYDGMWH43cjs.toChordData.call(void 0, chord), withCarriedKey(chord, opts)));
8263
8387
  }
8264
8388
  /**
8265
8389
  * The voice-leading cost from this voicing to another: the summed absolute
@@ -8271,7 +8395,7 @@ var Voicing = class _Voicing {
8271
8395
  * voices and are therefore not comparable.
8272
8396
  */
8273
8397
  costTo(other) {
8274
- return _chunk76ZBTRG2cjs.voiceLeadingCost.call(void 0, this.pitches, other.pitches);
8398
+ return _chunkU4EQTDGNcjs.voiceLeadingCost.call(void 0, this.pitches, other.pitches);
8275
8399
  }
8276
8400
  /**
8277
8401
  * Check the motion from this voicing to another against the four-part rules,
@@ -8302,14 +8426,14 @@ var Voicing = class _Voicing {
8302
8426
  */
8303
8427
  checkTo(other, chords, key, opts) {
8304
8428
  assertKeyArgument(key, "voicing key");
8305
- const resolved = _chunk3R3QVKY5cjs.resolveKey.call(void 0, key);
8306
- const from = _chunk3R3QVKY5cjs.toChordData.call(void 0, chords[0]);
8307
- const to = _chunk3R3QVKY5cjs.toChordData.call(void 0, chords[1]);
8429
+ const resolved = _chunkYDGMWH43cjs.resolveKey.call(void 0, key);
8430
+ const from = _chunkYDGMWH43cjs.toChordData.call(void 0, chords[0]);
8431
+ const to = _chunkYDGMWH43cjs.toChordData.call(void 0, chords[1]);
8308
8432
  const voicings = [
8309
- _chunk76ZBTRG2cjs.spellVoicing.call(void 0, this.pitches, from, resolved),
8310
- _chunk76ZBTRG2cjs.spellVoicing.call(void 0, other.pitches, to, resolved)
8433
+ _chunkU4EQTDGNcjs.spellVoicing.call(void 0, this.pitches, from, resolved),
8434
+ _chunkU4EQTDGNcjs.spellVoicing.call(void 0, other.pitches, to, resolved)
8311
8435
  ];
8312
- return _chunk76ZBTRG2cjs.checkPartWriting.call(void 0, voicings, [from, to], resolved, opts);
8436
+ return _chunkU4EQTDGNcjs.checkPartWriting.call(void 0, voicings, [from, to], resolved, opts);
8313
8437
  }
8314
8438
  /**
8315
8439
  * Mark this voicing, read as a written counterpoint line, against a cantus
@@ -8339,8 +8463,8 @@ var Voicing = class _Voicing {
8339
8463
  */
8340
8464
  species(cantusFirmus, species, mode, opts) {
8341
8465
  assertKeyArgument(mode, "voicing mode");
8342
- const resolved = _chunk3R3QVKY5cjs.resolveKey.call(void 0, mode);
8343
- return _chunk76ZBTRG2cjs.checkSpecies.call(void 0,
8466
+ const resolved = _chunkYDGMWH43cjs.resolveKey.call(void 0, mode);
8467
+ return _chunkU4EQTDGNcjs.checkSpecies.call(void 0,
8344
8468
  spellLine(cantusFirmus, resolved),
8345
8469
  spellLine(this.#pitches, resolved),
8346
8470
  species,
@@ -8366,8 +8490,8 @@ var Voicing = class _Voicing {
8366
8490
  */
8367
8491
  independence(other, opts) {
8368
8492
  const { key, ...rest } = _nullishCoalesce(opts, () => ( {}));
8369
- const resolved = key === void 0 ? void 0 : _chunk3R3QVKY5cjs.resolveKey.call(void 0, key);
8370
- return _chunk3R3QVKY5cjs.voiceIndependence.call(void 0,
8493
+ const resolved = key === void 0 ? void 0 : _chunkYDGMWH43cjs.resolveKey.call(void 0, key);
8494
+ return _chunkYDGMWH43cjs.voiceIndependence.call(void 0,
8371
8495
  lineOf(this.#pitches, resolved),
8372
8496
  lineOf(other.pitches, resolved),
8373
8497
  rest
@@ -8398,7 +8522,7 @@ var Voicing = class _Voicing {
8398
8522
  * ```
8399
8523
  */
8400
8524
  safetyOf(pitch, query, opts) {
8401
- return _chunk3R3QVKY5cjs.evaluateSafety.call(void 0, { ...this.#context(query), candidatePitch: pitch }, opts);
8525
+ return _chunkYDGMWH43cjs.evaluateSafety.call(void 0, { ...this.#context(query), candidatePitch: pitch }, opts);
8402
8526
  }
8403
8527
  /**
8404
8528
  * Enumerate the pitches placeable against these voices in a range, chord
@@ -8413,7 +8537,7 @@ var Voicing = class _Voicing {
8413
8537
  * bound is not a MIDI pitch in 0..127 or is reversed.
8414
8538
  */
8415
8539
  safePitches(query, pitchLow, pitchHigh) {
8416
- return _chunk3R3QVKY5cjs.enumerateSafePitches.call(void 0, this.#context(query), pitchLow, pitchHigh);
8540
+ return _chunkYDGMWH43cjs.enumerateSafePitches.call(void 0, this.#context(query), pitchLow, pitchHigh);
8417
8541
  }
8418
8542
  /**
8419
8543
  * The n-th inversion of the voicing: the lowest voice taken up an octave, n
@@ -8437,7 +8561,7 @@ var Voicing = class _Voicing {
8437
8561
  * ```
8438
8562
  */
8439
8563
  invert(n) {
8440
- _chunkS5BKZZGMcjs.assertInteger.call(void 0, n, "voicing inversion", -128, 128);
8564
+ _chunkS3QELJUEcjs.assertInteger.call(void 0, n, "voicing inversion", -128, 128);
8441
8565
  if (n === 0) {
8442
8566
  return this;
8443
8567
  }
@@ -8446,7 +8570,7 @@ var Voicing = class _Voicing {
8446
8570
  const index = n > 0 ? 0 : pitches.length - 1;
8447
8571
  const pitch = pitches[index] + (n > 0 ? 12 : -12);
8448
8572
  pitches.splice(index, 1);
8449
- pitches.push(_chunkS5BKZZGMcjs.assertMidiPitch.call(void 0, pitch, "inverted voice"));
8573
+ pitches.push(_chunkS3QELJUEcjs.assertMidiPitch.call(void 0, pitch, "inverted voice"));
8450
8574
  pitches.sort((a, b) => a - b);
8451
8575
  }
8452
8576
  return new _Voicing(pitches);
@@ -8486,19 +8610,19 @@ var Voicing = class _Voicing {
8486
8610
  }
8487
8611
  /** Spell the voicing, by the key alone or against a chord as well. */
8488
8612
  #spelled(key, chord) {
8489
- return chord === void 0 ? spellLine(this.#pitches, key) : _chunk76ZBTRG2cjs.spellVoicing.call(void 0, this.pitches, _chunk3R3QVKY5cjs.toChordData.call(void 0, chord), key);
8613
+ return chord === void 0 ? spellLine(this.#pitches, key) : _chunkU4EQTDGNcjs.spellVoicing.call(void 0, this.pitches, _chunkYDGMWH43cjs.toChordData.call(void 0, chord), key);
8490
8614
  }
8491
8615
  /** The safety context these voices supply, minus the candidate pitch. */
8492
8616
  #context(query) {
8493
- const previous = _optionalChain([query, 'access', _65 => _65.previous, 'optionalAccess', _66 => _66.pitches]);
8617
+ const previous = _optionalChain([query, 'access', _70 => _70.previous, 'optionalAccess', _71 => _71.pitches]);
8494
8618
  const otherVoices = this.#pitches.map((pitch, index) => {
8495
- const prevPitch = _optionalChain([previous, 'optionalAccess', _67 => _67[index]]);
8619
+ const prevPitch = _optionalChain([previous, 'optionalAccess', _72 => _72[index]]);
8496
8620
  return prevPitch === void 0 ? { pitch } : { pitch, prevPitch };
8497
8621
  });
8498
8622
  return {
8499
8623
  profile: query.profile,
8500
- chord: query.chord === null ? null : _chunk3R3QVKY5cjs.toChordData.call(void 0, query.chord),
8501
- key: _chunk3R3QVKY5cjs.resolveKey.call(void 0, query.key).scale,
8624
+ chord: query.chord === null ? null : _chunkYDGMWH43cjs.toChordData.call(void 0, query.chord),
8625
+ key: _chunkYDGMWH43cjs.resolveKey.call(void 0, query.key).scale,
8502
8626
  otherVoices,
8503
8627
  strongBeat: query.strongBeat,
8504
8628
  prevPitch: query.prevPitch,
@@ -8527,4 +8651,4 @@ var Voicing = class _Voicing {
8527
8651
 
8528
8652
 
8529
8653
  exports.Interval = Interval; exports.Note = Note; exports.Timeline = Timeline; exports.Progression = Progression; exports.Chord = Chord; exports.Key = Key; exports.Score = Score; exports.Arrangement = Arrangement; exports.Instrument = Instrument; exports.Composer = Composer; exports.Duration = Duration; exports.Meter = Meter; exports.Motif = Motif; exports.Rhythm = Rhythm; exports.Tempo = Tempo; exports.Tuning = Tuning; exports.Voicing = Voicing;
8530
- //# sourceMappingURL=chunk-4R2LWV7E.cjs.map
8654
+ //# sourceMappingURL=chunk-HYSVSFNI.cjs.map