@tspro/web-music-score 3.2.0 → 4.0.1

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 (51) hide show
  1. package/CHANGELOG.md +38 -10
  2. package/README.md +189 -331
  3. package/dist/audio/index.d.mts +40 -1
  4. package/dist/audio/index.d.ts +40 -1
  5. package/dist/audio/index.js +1 -1
  6. package/dist/audio/index.mjs +2 -2
  7. package/dist/audio-cg/index.d.mts +3 -0
  8. package/dist/audio-cg/index.d.ts +3 -0
  9. package/dist/audio-cg/index.js +1 -1
  10. package/dist/audio-cg/index.mjs +2 -2
  11. package/dist/{chunk-LCTM7BID.mjs → chunk-YFPLOHP2.mjs} +2 -2
  12. package/dist/core/index.d.mts +12 -0
  13. package/dist/core/index.d.ts +12 -0
  14. package/dist/core/index.js +3 -2
  15. package/dist/core/index.mjs +4 -3
  16. package/dist/guitar-CaZJDA05.d.ts +35 -0
  17. package/dist/guitar-DdexKdN6.d.mts +35 -0
  18. package/dist/iife/index.global.js +11 -11
  19. package/dist/{interface-Bn5HFt_U.d.mts → music-objects-DJQ4d2OA.d.mts} +640 -136
  20. package/dist/{interface-BlNl69uT.d.ts → music-objects-Dc3kR-XF.d.ts} +640 -136
  21. package/dist/note-eA2xPPiG.d.mts +294 -0
  22. package/dist/note-eA2xPPiG.d.ts +294 -0
  23. package/dist/pieces/index.d.mts +22 -3
  24. package/dist/pieces/index.d.ts +22 -3
  25. package/dist/pieces/index.js +7 -7
  26. package/dist/pieces/index.mjs +11 -11
  27. package/dist/react-ui/index.d.mts +166 -17
  28. package/dist/react-ui/index.d.ts +166 -17
  29. package/dist/react-ui/index.js +78 -1
  30. package/dist/react-ui/index.mjs +79 -2
  31. package/dist/scale-B2Icbetz.d.ts +230 -0
  32. package/dist/scale-BbDJTbrG.d.mts +230 -0
  33. package/dist/score/index.d.mts +359 -39
  34. package/dist/score/index.d.ts +359 -39
  35. package/dist/score/index.js +1252 -594
  36. package/dist/score/index.mjs +1255 -599
  37. package/dist/tempo-CtUhvJbr.d.mts +369 -0
  38. package/dist/tempo-Dt8aHpol.d.ts +369 -0
  39. package/dist/theory/index.d.mts +29 -13
  40. package/dist/theory/index.d.ts +29 -13
  41. package/dist/theory/index.js +583 -96
  42. package/dist/theory/index.mjs +580 -94
  43. package/package.json +2 -2
  44. package/dist/guitar-C2Cp71NZ.d.ts +0 -17
  45. package/dist/guitar-DggbM2UL.d.mts +0 -17
  46. package/dist/note-BFa43I86.d.mts +0 -85
  47. package/dist/note-BFa43I86.d.ts +0 -85
  48. package/dist/scale-DRR-t4Kr.d.mts +0 -74
  49. package/dist/scale-ebJm37q1.d.ts +0 -74
  50. package/dist/tempo-B4h5Ktob.d.mts +0 -104
  51. package/dist/tempo-DgqDEsn0.d.ts +0 -104
@@ -1,7 +1,7 @@
1
- /* WebMusicScore v3.2.0 | (c) 2023 PahkaSoft | MIT License | Includes: Tone.js (MIT License) */
1
+ /* WebMusicScore v4.0.1 | (c) 2023 PahkaSoft | MIT License | Includes: Tone.js (MIT License) */
2
2
  import {
3
3
  __publicField
4
- } from "../chunk-LCTM7BID.mjs";
4
+ } from "../chunk-YFPLOHP2.mjs";
5
5
 
6
6
  // src/score/pub/div-rect.ts
7
7
  import { Utils } from "@tspro/ts-utils-lib";
@@ -277,16 +277,16 @@ var DivRect = class _DivRect {
277
277
  };
278
278
 
279
279
  // src/score/pub/document-builder.ts
280
- import { Utils as Utils11 } from "@tspro/ts-utils-lib";
280
+ import { Utils as Utils13 } from "@tspro/ts-utils-lib";
281
281
 
282
282
  // src/score/pub/types.ts
283
283
  var StaffPreset = /* @__PURE__ */ ((StaffPreset3) => {
284
- StaffPreset3[StaffPreset3["Treble"] = 1] = "Treble";
285
- StaffPreset3[StaffPreset3["Bass"] = 2] = "Bass";
286
- StaffPreset3[StaffPreset3["Grand"] = 3] = "Grand";
287
- StaffPreset3[StaffPreset3["GuitarTreble"] = 4] = "GuitarTreble";
288
- StaffPreset3[StaffPreset3["GuitarTab"] = 8] = "GuitarTab";
289
- StaffPreset3[StaffPreset3["GuitarCombined"] = 12] = "GuitarCombined";
284
+ StaffPreset3["Treble"] = "treble";
285
+ StaffPreset3["Bass"] = "bass";
286
+ StaffPreset3["Grand"] = "grand";
287
+ StaffPreset3["GuitarTreble"] = "guitarTreble";
288
+ StaffPreset3["GuitarTab"] = "guitarTab";
289
+ StaffPreset3["GuitarCombined"] = "guitarCombined";
290
290
  return StaffPreset3;
291
291
  })(StaffPreset || {});
292
292
  var Clef = /* @__PURE__ */ ((Clef2) => {
@@ -301,77 +301,98 @@ function getStringNumbers() {
301
301
  return [1, 2, 3, 4, 5, 6];
302
302
  }
303
303
  var Stem = /* @__PURE__ */ ((Stem2) => {
304
- Stem2[Stem2["Auto"] = 0] = "Auto";
305
- Stem2[Stem2["Up"] = 1] = "Up";
306
- Stem2[Stem2["Down"] = 2] = "Down";
304
+ Stem2["Auto"] = "auto";
305
+ Stem2["Up"] = "up";
306
+ Stem2["Down"] = "down";
307
307
  return Stem2;
308
308
  })(Stem || {});
309
309
  var Arpeggio = /* @__PURE__ */ ((Arpeggio2) => {
310
- Arpeggio2[Arpeggio2["Up"] = 0] = "Up";
311
- Arpeggio2[Arpeggio2["Down"] = 1] = "Down";
310
+ Arpeggio2["Up"] = "up";
311
+ Arpeggio2["Down"] = "down";
312
312
  return Arpeggio2;
313
313
  })(Arpeggio || {});
314
314
  var TieType = /* @__PURE__ */ ((TieType2) => {
315
- TieType2[TieType2["Stub"] = -1] = "Stub";
316
- TieType2[TieType2["ToMeasureEnd"] = -2] = "ToMeasureEnd";
315
+ TieType2["Stub"] = "stub";
316
+ TieType2["ToMeasureEnd"] = "toMeasureEnd";
317
317
  return TieType2;
318
318
  })(TieType || {});
319
319
  var NoteAnchor = /* @__PURE__ */ ((NoteAnchor2) => {
320
- NoteAnchor2[NoteAnchor2["Auto"] = 0] = "Auto";
321
- NoteAnchor2[NoteAnchor2["Above"] = 1] = "Above";
322
- NoteAnchor2[NoteAnchor2["Center"] = 2] = "Center";
323
- NoteAnchor2[NoteAnchor2["Below"] = 3] = "Below";
324
- NoteAnchor2[NoteAnchor2["StemTip"] = 4] = "StemTip";
320
+ NoteAnchor2["Auto"] = "auto";
321
+ NoteAnchor2["Above"] = "above";
322
+ NoteAnchor2["Center"] = "center";
323
+ NoteAnchor2["Below"] = "below";
324
+ NoteAnchor2["StemTip"] = "stemTip";
325
325
  return NoteAnchor2;
326
326
  })(NoteAnchor || {});
327
327
  var Connective = /* @__PURE__ */ ((Connective2) => {
328
- Connective2[Connective2["Tie"] = 0] = "Tie";
329
- Connective2[Connective2["Slur"] = 1] = "Slur";
330
- Connective2[Connective2["Slide"] = 2] = "Slide";
328
+ Connective2["Tie"] = "tie";
329
+ Connective2["Slur"] = "slur";
330
+ Connective2["Slide"] = "slide";
331
331
  return Connective2;
332
332
  })(Connective || {});
333
333
  var VerticalPosition = /* @__PURE__ */ ((VerticalPosition4) => {
334
- VerticalPosition4[VerticalPosition4["Above"] = 0] = "Above";
335
- VerticalPosition4[VerticalPosition4["Below"] = 1] = "Below";
336
- VerticalPosition4[VerticalPosition4["Both"] = 2] = "Both";
337
- VerticalPosition4[VerticalPosition4["Auto"] = 3] = "Auto";
334
+ VerticalPosition4["Auto"] = "auto";
335
+ VerticalPosition4["Above"] = "above";
336
+ VerticalPosition4["Below"] = "below";
337
+ VerticalPosition4["Both"] = "both";
338
338
  return VerticalPosition4;
339
339
  })(VerticalPosition || {});
340
- var PlayState = /* @__PURE__ */ ((PlayState2) => {
341
- PlayState2[PlayState2["Playing"] = 0] = "Playing";
342
- PlayState2[PlayState2["Paused"] = 1] = "Paused";
343
- PlayState2[PlayState2["Stopped"] = 2] = "Stopped";
344
- return PlayState2;
345
- })(PlayState || {});
346
340
  var Fermata = /* @__PURE__ */ ((Fermata2) => {
347
- Fermata2[Fermata2["AtNote"] = 0] = "AtNote";
348
- Fermata2[Fermata2["AtMeasureEnd"] = 1] = "AtMeasureEnd";
341
+ Fermata2["AtNote"] = "atNote";
342
+ Fermata2["AtMeasureEnd"] = "atMeasureEnd";
349
343
  return Fermata2;
350
344
  })(Fermata || {});
351
345
  var Navigation = /* @__PURE__ */ ((Navigation2) => {
352
- Navigation2[Navigation2["DC_al_Fine"] = 0] = "DC_al_Fine";
353
- Navigation2[Navigation2["DC_al_Coda"] = 1] = "DC_al_Coda";
354
- Navigation2[Navigation2["DS_al_Fine"] = 2] = "DS_al_Fine";
355
- Navigation2[Navigation2["DS_al_Coda"] = 3] = "DS_al_Coda";
356
- Navigation2[Navigation2["Coda"] = 4] = "Coda";
357
- Navigation2[Navigation2["toCoda"] = 5] = "toCoda";
358
- Navigation2[Navigation2["Segno"] = 6] = "Segno";
359
- Navigation2[Navigation2["Fine"] = 7] = "Fine";
360
- Navigation2[Navigation2["StartRepeat"] = 8] = "StartRepeat";
361
- Navigation2[Navigation2["EndRepeat"] = 9] = "EndRepeat";
362
- Navigation2[Navigation2["Ending"] = 10] = "Ending";
346
+ Navigation2["DC_al_Fine"] = "D.C. al Fine";
347
+ Navigation2["DC_al_Coda"] = "D.C. al Coda";
348
+ Navigation2["DS_al_Fine"] = "D.S. al Fine";
349
+ Navigation2["DS_al_Coda"] = "D.S. al Coda";
350
+ Navigation2["Coda"] = "Coda";
351
+ Navigation2["toCoda"] = "toCoda";
352
+ Navigation2["Segno"] = "Segno";
353
+ Navigation2["Fine"] = "Fine";
354
+ Navigation2["StartRepeat"] = "startRepeat";
355
+ Navigation2["EndRepeat"] = "endRepeat";
356
+ Navigation2["Ending"] = "ending";
363
357
  return Navigation2;
364
358
  })(Navigation || {});
365
359
  var Annotation = /* @__PURE__ */ ((Annotation2) => {
366
- Annotation2[Annotation2["Dynamics"] = 0] = "Dynamics";
367
- Annotation2[Annotation2["Tempo"] = 1] = "Tempo";
360
+ Annotation2["Dynamics"] = "dynamics";
361
+ Annotation2["Tempo"] = "tempo";
368
362
  return Annotation2;
369
363
  })(Annotation || {});
364
+ var DynamicsAnnotation = /* @__PURE__ */ ((DynamicsAnnotation2) => {
365
+ DynamicsAnnotation2["cresc"] = "cresc.";
366
+ DynamicsAnnotation2["decresc"] = "decresc.";
367
+ DynamicsAnnotation2["dim"] = "dim.";
368
+ DynamicsAnnotation2["ppp"] = "ppp";
369
+ DynamicsAnnotation2["pp"] = "pp";
370
+ DynamicsAnnotation2["p"] = "p";
371
+ DynamicsAnnotation2["mp"] = "mp";
372
+ DynamicsAnnotation2["m"] = "m";
373
+ DynamicsAnnotation2["mf"] = "mf";
374
+ DynamicsAnnotation2["f"] = "f";
375
+ DynamicsAnnotation2["ff"] = "ff";
376
+ DynamicsAnnotation2["fff"] = "fff";
377
+ return DynamicsAnnotation2;
378
+ })(DynamicsAnnotation || {});
379
+ var TempoAnnotation = /* @__PURE__ */ ((TempoAnnotation2) => {
380
+ TempoAnnotation2["accel"] = "accel.";
381
+ TempoAnnotation2["rit"] = "rit.";
382
+ TempoAnnotation2["a_tempo"] = "a tempo";
383
+ return TempoAnnotation2;
384
+ })(TempoAnnotation || {});
370
385
  var Label = /* @__PURE__ */ ((Label2) => {
371
- Label2[Label2["Note"] = 0] = "Note";
372
- Label2[Label2["Chord"] = 1] = "Chord";
386
+ Label2["Note"] = "note";
387
+ Label2["Chord"] = "chord";
373
388
  return Label2;
374
389
  })(Label || {});
390
+ var PlayState = /* @__PURE__ */ ((PlayState2) => {
391
+ PlayState2[PlayState2["Playing"] = 0] = "Playing";
392
+ PlayState2[PlayState2["Paused"] = 1] = "Paused";
393
+ PlayState2[PlayState2["Stopped"] = 2] = "Stopped";
394
+ return PlayState2;
395
+ })(PlayState || {});
375
396
 
376
397
  // src/score/engine/music-object.ts
377
398
  var MusicObjectLink = class {
@@ -870,11 +891,11 @@ var Renderer = class {
870
891
 
871
892
  // src/score/engine/obj-staff-and-tab.ts
872
893
  import { MusicError as MusicError15, MusicErrorType as MusicErrorType15 } from "@tspro/web-music-score/core";
873
- import { Utils as Utils9 } from "@tspro/ts-utils-lib";
894
+ import { Utils as Utils11 } from "@tspro/ts-utils-lib";
874
895
 
875
896
  // src/score/engine/obj-measure.ts
876
- import { Utils as Utils8 } from "@tspro/ts-utils-lib";
877
- import { getScale, Scale, validateScaleType, Note as Note7, NoteLength as NoteLength6, RhythmProps as RhythmProps4, KeySignature as KeySignature2, getDefaultKeySignature, PitchNotation, SymbolSet } from "@tspro/web-music-score/theory";
897
+ import { Utils as Utils10 } from "@tspro/ts-utils-lib";
898
+ import { getScale, Scale, validateScaleType, Note as Note7, RhythmProps as RhythmProps4, KeySignature as KeySignature2, getDefaultKeySignature, PitchNotation, SymbolSet, validateNoteLength, NoteLengthProps as NoteLengthProps4 } from "@tspro/web-music-score/theory";
878
899
  import { getDefaultTempo, TimeSignature, getDefaultTimeSignature } from "@tspro/web-music-score/theory";
879
900
 
880
901
  // src/score/engine/acc-state.ts
@@ -1462,12 +1483,12 @@ var ObjSignature = class extends MusicObject {
1462
1483
  };
1463
1484
 
1464
1485
  // src/score/engine/player.ts
1465
- import { Utils as Utils5 } from "@tspro/ts-utils-lib";
1486
+ import { Utils as Utils6 } from "@tspro/ts-utils-lib";
1466
1487
  import { NoteLength as NoteLength5, RhythmProps as RhythmProps3, alterTempoSpeed } from "@tspro/web-music-score/theory";
1467
1488
  import * as Audio from "@tspro/web-music-score/audio";
1468
1489
 
1469
1490
  // src/score/engine/obj-rhythm-column.ts
1470
- import { Note as Note5, NoteLength as NoteLength4 } from "@tspro/web-music-score/theory";
1491
+ import { Note as Note5 } from "@tspro/web-music-score/theory";
1471
1492
 
1472
1493
  // src/score/engine/obj-arpeggio.ts
1473
1494
  var ObjArpeggio = class extends MusicObject {
@@ -1492,8 +1513,8 @@ var ObjArpeggio = class extends MusicObject {
1492
1513
  }
1493
1514
  layout(renderer) {
1494
1515
  let { unitSize } = renderer;
1495
- this.topArrowHeight = this.arpeggioDir === 0 /* Up */ ? unitSize : 0;
1496
- this.bottomArrowHeight = this.arpeggioDir === 1 /* Down */ ? unitSize : 0;
1516
+ this.topArrowHeight = this.arpeggioDir === "up" /* Up */ ? unitSize : 0;
1517
+ this.bottomArrowHeight = this.arpeggioDir === "down" /* Down */ ? unitSize : 0;
1497
1518
  let top = this.line.getTopLineY();
1498
1519
  let bottom = this.line.getBottomLineY();
1499
1520
  this.cycleHeight = unitSize * 2;
@@ -1540,7 +1561,7 @@ var ObjArpeggio = class extends MusicObject {
1540
1561
  };
1541
1562
 
1542
1563
  // src/score/engine/obj-rest.ts
1543
- import { Note as Note3, NoteLength, RhythmProps } from "@tspro/web-music-score/theory";
1564
+ import { Note as Note3, NoteLength, NoteLengthProps, RhythmProps, Tuplet } from "@tspro/web-music-score/theory";
1544
1565
  import { MusicError as MusicError5, MusicErrorType as MusicErrorType5 } from "@tspro/web-music-score/core";
1545
1566
  function getDiatonicIdFromStaffPos(staffPos) {
1546
1567
  if (typeof staffPos === "number") {
@@ -1559,7 +1580,7 @@ var ObjStaffRest = class extends MusicObject {
1559
1580
  this.staff = staff;
1560
1581
  this.rest = rest;
1561
1582
  __publicField(this, "restRect", new DivRect());
1562
- __publicField(this, "dotRect");
1583
+ __publicField(this, "dotRects", []);
1563
1584
  __publicField(this, "mi");
1564
1585
  staff.addObject(this);
1565
1586
  this.mi = new MStaffRest(this);
@@ -1571,21 +1592,18 @@ var ObjStaffRest = class extends MusicObject {
1571
1592
  return this.getRect().contains(x, y) ? [this] : [];
1572
1593
  }
1573
1594
  offset(dx, dy) {
1574
- var _a;
1575
1595
  this.restRect.offsetInPlace(dx, dy);
1576
- (_a = this.dotRect) == null ? void 0 : _a.offsetInPlace(dx, dy);
1596
+ this.dotRects.forEach((r) => r.offsetInPlace(dx, dy));
1577
1597
  this.requestRectUpdate();
1578
1598
  this.rest.requestRectUpdate();
1579
1599
  }
1580
1600
  updateRect() {
1581
1601
  this.rect = this.restRect.copy();
1582
- if (this.dotRect) {
1583
- this.rect.expandInPlace(this.dotRect);
1584
- }
1602
+ this.dotRects.forEach((r) => this.rect.expandInPlace(r));
1585
1603
  }
1586
1604
  };
1587
1605
  var ObjRest = class extends MusicObject {
1588
- constructor(col, voiceId, noteLength, options) {
1606
+ constructor(col, voiceId, noteLength, options, tupletRatio) {
1589
1607
  var _a, _b;
1590
1608
  super(col);
1591
1609
  this.col = col;
@@ -1594,6 +1612,7 @@ var ObjRest = class extends MusicObject {
1594
1612
  __publicField(this, "ownDiatonicId");
1595
1613
  __publicField(this, "color");
1596
1614
  __publicField(this, "hide");
1615
+ __publicField(this, "oldStyleTriplet");
1597
1616
  __publicField(this, "rhythmProps");
1598
1617
  __publicField(this, "beamGroup");
1599
1618
  __publicField(this, "staffObjects", []);
@@ -1617,7 +1636,9 @@ var ObjRest = class extends MusicObject {
1617
1636
  }
1618
1637
  this.color = (_a = options == null ? void 0 : options.color) != null ? _a : "black";
1619
1638
  this.hide = (_b = options == null ? void 0 : options.hide) != null ? _b : false;
1620
- this.rhythmProps = new RhythmProps(noteLength, options == null ? void 0 : options.dotted, options == null ? void 0 : options.triplet);
1639
+ this.oldStyleTriplet = tupletRatio === void 0 && ((options == null ? void 0 : options.triplet) === true || NoteLengthProps.get(noteLength).isTriplet);
1640
+ let dotCount = typeof (options == null ? void 0 : options.dotted) === "number" ? options.dotted > 0 ? options.dotted : void 0 : (options == null ? void 0 : options.dotted) === true ? 1 : void 0;
1641
+ this.rhythmProps = RhythmProps.get(noteLength, dotCount, (tupletRatio != null ? tupletRatio : this.oldStyleTriplet) ? Tuplet.Triplet : void 0);
1621
1642
  this.mi = new MRest(this);
1622
1643
  }
1623
1644
  getMusicInterface() {
@@ -1635,15 +1656,9 @@ var ObjRest = class extends MusicObject {
1635
1656
  get noteLength() {
1636
1657
  return this.rhythmProps.noteLength;
1637
1658
  }
1638
- get dotted() {
1639
- return this.rhythmProps.dotted;
1640
- }
1641
1659
  get stemDir() {
1642
1660
  return this.beamGroup ? this.beamGroup.stemDir : this.ownStemDir;
1643
1661
  }
1644
- get triplet() {
1645
- return this.rhythmProps.triplet;
1646
- }
1647
1662
  getStaticObjects(line) {
1648
1663
  let staticObjects = [];
1649
1664
  this.staffObjects.forEach((obj) => {
@@ -1668,8 +1683,8 @@ var ObjRest = class extends MusicObject {
1668
1683
  getBeamGroup() {
1669
1684
  return this.beamGroup;
1670
1685
  }
1671
- setBeamGroup(beam) {
1672
- this.beamGroup = beam;
1686
+ setBeamGroup(beamGroup) {
1687
+ this.beamGroup = beamGroup;
1673
1688
  }
1674
1689
  resetBeamGroup() {
1675
1690
  this.beamGroup = void 0;
@@ -1678,7 +1693,7 @@ var ObjRest = class extends MusicObject {
1678
1693
  return this.staffObjects.map((obj) => {
1679
1694
  let staff = obj.staff;
1680
1695
  let x = obj.getRect().centerX;
1681
- let y = this.stemDir === 1 /* Up */ ? obj.getRect().top : obj.getRect().bottom;
1696
+ let y = this.stemDir === "up" /* Up */ ? obj.getRect().top : obj.getRect().bottom;
1682
1697
  let stemHeight = Math.abs(obj.getRect().centerY - y);
1683
1698
  return { staff, x, y, stemHeight };
1684
1699
  });
@@ -1719,7 +1734,7 @@ var ObjRest = class extends MusicObject {
1719
1734
  }
1720
1735
  let { unitSize } = renderer;
1721
1736
  let { ownDiatonicId } = this;
1722
- let { noteLength, dotted, flagCount } = this.rhythmProps;
1737
+ let { noteLength, dotCount, flagCount } = this.rhythmProps;
1723
1738
  let leftw = 0;
1724
1739
  let rightw = 0;
1725
1740
  let toph = 0;
@@ -1752,11 +1767,11 @@ var ObjRest = class extends MusicObject {
1752
1767
  }
1753
1768
  let obj = new ObjStaffRest(staff, this);
1754
1769
  obj.restRect = new DivRect(-leftw, 0, rightw, -toph, 0, bottomh);
1755
- if (dotted) {
1770
+ for (let i = 0; i < dotCount; i++) {
1756
1771
  let dotWidth = DocumentSettings.DotSize * unitSize;
1757
- let dotX = rightw + (DocumentSettings.RestDotSpace + DocumentSettings.DotSize / 2) * unitSize;
1772
+ let dotX = rightw + (DocumentSettings.RestDotSpace + DocumentSettings.DotSize * unitSize) + i * DocumentSettings.DotSize * unitSize * 1.5;
1758
1773
  let dotY = this.getRestDotVerticalDisplacement(noteLength) * unitSize;
1759
- obj.dotRect = DivRect.createCentered(dotX, dotY, dotWidth, dotWidth);
1774
+ obj.dotRects.push(DivRect.createCentered(dotX, dotY, dotWidth, dotWidth));
1760
1775
  }
1761
1776
  obj.offset(0, staff.getDiatonicIdY(ownDiatonicId));
1762
1777
  this.staffObjects.push(obj);
@@ -1790,7 +1805,7 @@ var ObjRest = class extends MusicObject {
1790
1805
  ctx.strokeStyle = ctx.fillStyle = color;
1791
1806
  ctx.lineWidth = lineWidth;
1792
1807
  this.staffObjects.forEach((obj) => {
1793
- let { dotRect, restRect } = obj;
1808
+ let { dotRects, restRect } = obj;
1794
1809
  let x = restRect.centerX;
1795
1810
  let y = restRect.centerY;
1796
1811
  if (noteLength === NoteLength.Whole) {
@@ -1855,20 +1870,20 @@ var ObjRest = class extends MusicObject {
1855
1870
  ctx.fill();
1856
1871
  }
1857
1872
  }
1858
- if (dotRect) {
1859
- renderer.fillCircle(dotRect.centerX, dotRect.centerY, dotRect.width / 2);
1860
- }
1873
+ dotRects.forEach((r) => {
1874
+ renderer.fillCircle(r.centerX, r.centerY, r.width / 2);
1875
+ });
1861
1876
  });
1862
1877
  }
1863
1878
  };
1864
1879
 
1865
1880
  // src/score/engine/obj-note-group.ts
1866
1881
  import { Utils as Utils4 } from "@tspro/ts-utils-lib";
1867
- import { Note as Note4, NoteLength as NoteLength3, RhythmProps as RhythmProps2 } from "@tspro/web-music-score/theory";
1882
+ import { Note as Note4, NoteLengthProps as NoteLengthProps3, RhythmProps as RhythmProps2, Tuplet as Tuplet3 } from "@tspro/web-music-score/theory";
1868
1883
 
1869
1884
  // src/score/engine/obj-beam-group.ts
1870
1885
  import { Utils as Utils3 } from "@tspro/ts-utils-lib";
1871
- import { MinNoteLength, NoteLength as NoteLength2 } from "@tspro/web-music-score/theory";
1886
+ import { NoteLength as NoteLength2, Tuplet as Tuplet2, NoteLengthProps as NoteLengthProps2 } from "@tspro/web-music-score/theory";
1872
1887
  import { MusicError as MusicError6, MusicErrorType as MusicErrorType6 } from "@tspro/web-music-score/core";
1873
1888
  var adjustBeamAngle = (dx, dy) => {
1874
1889
  let T = DocumentSettings.BeamAngleFactor;
@@ -1905,8 +1920,8 @@ var ObjStaffBeamGroup = class extends MusicObject {
1905
1920
  super(staff);
1906
1921
  this.staff = staff;
1907
1922
  this.beamGroup = beamGroup;
1908
- __publicField(this, "tripletNumber");
1909
- __publicField(this, "tripletNumberOffsetY", 0);
1923
+ __publicField(this, "tupletNumber");
1924
+ __publicField(this, "tupletNumberOffsetY", 0);
1910
1925
  __publicField(this, "points", []);
1911
1926
  __publicField(this, "mi");
1912
1927
  staff.addObject(this);
@@ -1921,48 +1936,47 @@ var ObjStaffBeamGroup = class extends MusicObject {
1921
1936
  offset(dx, dy) {
1922
1937
  var _a;
1923
1938
  this.points.forEach((p) => p.offset(dx, 0));
1924
- (_a = this.tripletNumber) == null ? void 0 : _a.offset(dx, dy);
1939
+ (_a = this.tupletNumber) == null ? void 0 : _a.offset(dx, dy);
1925
1940
  this.requestRectUpdate();
1926
1941
  this.beamGroup.requestRectUpdate();
1927
1942
  }
1928
1943
  updateRect() {
1929
1944
  if (this.points.length > 0) {
1930
1945
  this.rect = this.points[0].getRect().copy();
1931
- } else if (this.tripletNumber) {
1932
- this.rect = this.tripletNumber.getRect().copy();
1946
+ } else if (this.tupletNumber) {
1947
+ this.rect = this.tupletNumber.getRect().copy();
1933
1948
  }
1934
1949
  this.points.forEach((pt) => this.rect.expandInPlace(pt.getRect()));
1935
- if (this.tripletNumber) {
1936
- this.rect.expandInPlace(this.tripletNumber.getRect());
1950
+ if (this.tupletNumber) {
1951
+ this.rect.expandInPlace(this.tupletNumber.getRect());
1937
1952
  }
1938
1953
  }
1939
1954
  };
1940
1955
  var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
1941
- constructor(symbols, triplet) {
1956
+ constructor(symbols, tupletRatio) {
1942
1957
  super(symbols[0].measure);
1943
1958
  this.symbols = symbols;
1959
+ this.tupletRatio = tupletRatio;
1944
1960
  __publicField(this, "mi");
1945
1961
  __publicField(this, "type");
1946
1962
  __publicField(this, "staffObjects", []);
1947
1963
  this.mi = new MBeamGroup(this);
1964
+ let beamGroupName = tupletRatio ? "Tuplet" : "BeamGroup";
1948
1965
  if (!symbols.every((s) => s.measure === symbols[0].measure)) {
1949
- throw new MusicError6(MusicErrorType6.Score, "All beam group symbols are not in same measure.");
1966
+ throw new MusicError6(MusicErrorType6.Score, `All ${beamGroupName} symbols are not in same measure.`);
1950
1967
  } else if (symbols.length < 2) {
1951
- throw new MusicError6(MusicErrorType6.Score, "Beam group need minimum 2 symbols, but " + symbols.length + " given.");
1968
+ throw new MusicError6(MusicErrorType6.Score, `${beamGroupName} needs minimum 2 symbols, but ${symbols.length} given.`);
1952
1969
  }
1953
- if (triplet) {
1954
- if (!symbols.every((s) => s.triplet)) {
1955
- throw new MusicError6(MusicErrorType6.Score, "Not every symbol's triplet property is true.");
1956
- }
1970
+ if (tupletRatio !== void 0) {
1957
1971
  let isGroup = symbols.length < 3 || symbols.some((s) => !(s instanceof ObjNoteGroup)) || symbols.some((s) => s.rhythmProps.flagCount !== symbols[0].rhythmProps.flagCount);
1958
- if (symbols.length === 3 && symbols[0] instanceof ObjNoteGroup && symbols[symbols.length - 1] instanceof ObjNoteGroup && symbols[0].rhythmProps.flagCount === symbols[symbols.length - 1].rhythmProps.flagCount) {
1972
+ if (symbols.length >= 3 && symbols[0] instanceof ObjNoteGroup && symbols[symbols.length - 1] instanceof ObjNoteGroup && symbols[0].rhythmProps.flagCount === symbols[symbols.length - 1].rhythmProps.flagCount) {
1959
1973
  isGroup = false;
1960
1974
  }
1961
- if (symbols.some((s) => s.rhythmProps.noteLength >= NoteLength2.Quarter)) {
1975
+ if (symbols.some((s) => NoteLengthProps2.cmp(s.rhythmProps.noteLength, NoteLength2.Quarter) >= 0)) {
1962
1976
  isGroup = true;
1963
1977
  }
1964
- this.type = isGroup ? 2 /* TripletGroup */ : 1 /* TripletBeam */;
1965
- ObjNoteGroup.setTripletBeamCounts(this);
1978
+ this.type = isGroup ? 2 /* TupletGroup */ : 1 /* TupletBeam */;
1979
+ ObjNoteGroup.setTupletBeamCounts(this);
1966
1980
  } else {
1967
1981
  this.type = 0 /* RegularBeam */;
1968
1982
  }
@@ -1970,29 +1984,35 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
1970
1984
  symbols.forEach((s) => s.setBeamGroup(this));
1971
1985
  symbols[0].measure.addBeamGroup(this);
1972
1986
  } else {
1973
- throw new MusicError6(MusicErrorType6.Score, "Cannot add beam group because some symbol already has one.");
1987
+ throw new MusicError6(MusicErrorType6.Score, `Cannot add ${beamGroupName} because some symbol already has one.`);
1974
1988
  }
1975
1989
  }
1990
+ get showTupletRatio() {
1991
+ var _a;
1992
+ return ((_a = this.tupletRatio) == null ? void 0 : _a.showRatio) === true;
1993
+ }
1976
1994
  static createBeam(noteGroups) {
1977
1995
  if (noteGroups.length > 1) {
1978
- new _ObjBeamGroup(noteGroups, false);
1996
+ new _ObjBeamGroup(noteGroups, void 0);
1979
1997
  }
1980
1998
  }
1981
- static createTriplet(symbols) {
1982
- let MaxTripletNoteLenght = NoteLength2.Half;
1983
- let len = symbols.map((s) => s.rhythmProps.noteLength);
1984
- if (symbols.length == 2) {
1985
- if (len[0] <= MaxTripletNoteLenght && len[1] === len[0] / 2 && len[0] / 2 >= MinNoteLength || len[1] <= MaxTripletNoteLenght && len[0] === len[1] / 2 && len[1] / 2 >= MinNoteLength) {
1986
- new _ObjBeamGroup(symbols, true);
1987
- return true;
1988
- }
1989
- } else if (symbols.length === 3) {
1990
- if (len[0] <= MaxTripletNoteLenght && len.every((l) => l === len[0])) {
1991
- new _ObjBeamGroup(symbols, true);
1992
- return true;
1993
- }
1999
+ static createOldStyleTriplet(symbols) {
2000
+ let s2 = symbols.slice(0, 2);
2001
+ let n2 = s2.map((s) => s.rhythmProps.noteSize);
2002
+ if (s2.length === 2 && s2.every((s) => s.oldStyleTriplet && s.getBeamGroup() === void 0) && (n2[0] * 2 === n2[1] || n2[1] * 2 === n2[0])) {
2003
+ new _ObjBeamGroup(s2, Tuplet2.Triplet);
2004
+ return 2;
1994
2005
  }
1995
- return false;
2006
+ let s3 = symbols.slice(0, 3);
2007
+ let n3 = s3.map((s) => s.rhythmProps.noteSize);
2008
+ if (s3.length === 3 && s3.every((s) => s.oldStyleTriplet && s.getBeamGroup() === void 0) && n3.every((n) => n === n3[0])) {
2009
+ new _ObjBeamGroup(s3, Tuplet2.Triplet);
2010
+ return 3;
2011
+ }
2012
+ return 0;
2013
+ }
2014
+ static createTuplet(symbols, tupletRatio) {
2015
+ new _ObjBeamGroup(symbols, tupletRatio);
1996
2016
  }
1997
2017
  getMusicInterface() {
1998
2018
  return this.mi;
@@ -2018,8 +2038,8 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2018
2038
  getType() {
2019
2039
  return this.type;
2020
2040
  }
2021
- isTriplet() {
2022
- return this.type === 1 /* TripletBeam */ || this.type === 2 /* TripletGroup */;
2041
+ isTuplet() {
2042
+ return this.type === 1 /* TupletBeam */ || this.type === 2 /* TupletGroup */;
2023
2043
  }
2024
2044
  getSymbols() {
2025
2045
  return this.symbols;
@@ -2081,10 +2101,10 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2081
2101
  }
2082
2102
  let leftStemHeight = (_a = symbolStemHeight[0]) != null ? _a : 0;
2083
2103
  let rightStemHeight = (_b = symbolStemHeight[symbolStemHeight.length - 1]) != null ? _b : 0;
2084
- if (this.type !== 2 /* TripletGroup */) {
2104
+ if (this.type !== 2 /* TupletGroup */) {
2085
2105
  let leftDy = leftStemHeight < rightStemHeight ? Math.sqrt(rightStemHeight - leftStemHeight) : 0;
2086
2106
  let rightDy = rightStemHeight < leftStemHeight ? Math.sqrt(leftStemHeight - rightStemHeight) : 0;
2087
- if (stemDir === 1 /* Up */) {
2107
+ if (stemDir === "up" /* Up */) {
2088
2108
  leftDy *= -1;
2089
2109
  rightDy *= -1;
2090
2110
  }
@@ -2097,7 +2117,7 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2097
2117
  symbolY[symbolY.length - 1] += rightDy;
2098
2118
  }
2099
2119
  }
2100
- let groupLineDy = unitSize * 2 * (stemDir === 1 /* Up */ ? -1 : 1);
2120
+ let groupLineDy = unitSize * 2 * (stemDir === "up" /* Up */ ? -1 : 1);
2101
2121
  let centerY = (rightY + leftY) / 2;
2102
2122
  let halfDy = adjustBeamAngle(rightX - leftX, rightY - leftY) / 2;
2103
2123
  leftY = centerY - halfDy;
@@ -2108,9 +2128,9 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2108
2128
  if (symX !== void 0 && symY !== void 0) {
2109
2129
  let beamY = Utils3.Math.interpolateY(leftX, leftY, rightX, rightY, symX);
2110
2130
  let raiseY = symY - beamY;
2111
- if (stemDir === 1 /* Up */ && raiseY < 0) {
2131
+ if (stemDir === "up" /* Up */ && raiseY < 0) {
2112
2132
  raiseBeamY = Math.min(raiseBeamY, raiseY);
2113
- } else if (stemDir === 2 /* Down */ && raiseY > 0) {
2133
+ } else if (stemDir === "down" /* Down */ && raiseY > 0) {
2114
2134
  raiseBeamY = Math.max(raiseBeamY, raiseY);
2115
2135
  }
2116
2136
  }
@@ -2119,21 +2139,21 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2119
2139
  rightY += raiseBeamY;
2120
2140
  symbolY = symbolY.map((y) => y === void 0 ? void 0 : y + raiseBeamY);
2121
2141
  let obj = new ObjStaffBeamGroup(mainStaff, this);
2122
- if (this.type === 2 /* TripletGroup */) {
2142
+ if (this.type === 2 /* TupletGroup */) {
2123
2143
  let ef = unitSize / (rightX - leftX);
2124
2144
  let l = Utils3.Math.interpolateCoord(leftX, leftY + groupLineDy, rightX, rightY + groupLineDy, -ef);
2125
2145
  let r = Utils3.Math.interpolateCoord(leftX, leftY + groupLineDy, rightX, rightY + groupLineDy, 1 + ef);
2126
2146
  obj.points.push(new BeamPoint(leftStaff, this, leftSymbol, l.x, l.y));
2127
2147
  obj.points.push(new BeamPoint(rightStaff, this, rightSymbol, r.x, r.y));
2128
- obj.tripletNumberOffsetY = 0;
2129
- } else if (this.type === 0 /* RegularBeam */ || this.type === 1 /* TripletBeam */) {
2148
+ obj.tupletNumberOffsetY = 0;
2149
+ } else if (this.type === 0 /* RegularBeam */ || this.type === 1 /* TupletBeam */) {
2130
2150
  raiseBeamY *= 0.5;
2131
2151
  let { beamThickness } = renderer;
2132
2152
  const beamHeight = (i) => {
2133
2153
  let sym = symbols[i];
2134
2154
  if (sym instanceof ObjNoteGroup) {
2135
2155
  let beamCount = sym instanceof ObjNoteGroup ? Math.max(sym.getLeftBeamCount(), sym.getRightBeamCount()) : 0;
2136
- return DocumentSettings.BeamSeparation * unitSize * (this.stemDir === 1 /* Up */ ? beamCount - 1 : 0);
2156
+ return DocumentSettings.BeamSeparation * unitSize * (this.stemDir === "up" /* Up */ ? beamCount - 1 : 0);
2137
2157
  } else {
2138
2158
  return 0;
2139
2159
  }
@@ -2144,17 +2164,18 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2144
2164
  let symY = symbolY[i];
2145
2165
  if (symStaff && symX !== void 0 && symY !== void 0) {
2146
2166
  let pt = new BeamPoint(symStaff, this, sym, symX, symY);
2147
- pt.topBeamsHeight = beamThickness / 2 + (stemDir === 2 /* Down */ ? beamHeight(i) : 0);
2148
- pt.bottomBeamsHeight = beamThickness / 2 + (stemDir === 1 /* Up */ ? beamHeight(i) : 0);
2167
+ pt.topBeamsHeight = beamThickness / 2 + (stemDir === "down" /* Down */ ? beamHeight(i) : 0);
2168
+ pt.bottomBeamsHeight = beamThickness / 2 + (stemDir === "up" /* Up */ ? beamHeight(i) : 0);
2149
2169
  obj.points.push(pt);
2150
2170
  }
2151
2171
  });
2152
- obj.tripletNumberOffsetY = groupLineDy;
2172
+ obj.tupletNumberOffsetY = groupLineDy;
2153
2173
  }
2154
- if (this.isTriplet()) {
2155
- obj.tripletNumber = new ObjText(this, "3", 0.5, 0.5);
2156
- obj.tripletNumber.layout(renderer);
2157
- obj.tripletNumber.offset((leftX + rightX) / 2, (leftY + rightY) / 2 + obj.tripletNumberOffsetY);
2174
+ if (this.isTuplet() && this.tupletRatio) {
2175
+ let txt = this.showTupletRatio ? String(this.tupletRatio.parts) + ":" + String(this.tupletRatio.inTimeOf) : String(this.tupletRatio.parts);
2176
+ obj.tupletNumber = new ObjText(this, txt, 0.5, 0.5);
2177
+ obj.tupletNumber.layout(renderer);
2178
+ obj.tupletNumber.offset((leftX + rightX) / 2, (leftY + rightY) / 2 + obj.tupletNumberOffsetY);
2158
2179
  }
2159
2180
  if (obj.points.length >= 2) {
2160
2181
  this.staffObjects.push(obj);
@@ -2176,7 +2197,7 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2176
2197
  this.staffObjects.forEach((obj) => {
2177
2198
  let left = obj.points[0];
2178
2199
  let right = obj.points[obj.points.length - 1];
2179
- if (this.type !== 2 /* TripletGroup */) {
2200
+ if (this.type !== 2 /* TupletGroup */) {
2180
2201
  obj.points.forEach((pt) => {
2181
2202
  if (pt.symbol instanceof ObjNoteGroup) {
2182
2203
  if (pt !== left && pt !== right) {
@@ -2186,9 +2207,9 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2186
2207
  }
2187
2208
  });
2188
2209
  }
2189
- if (obj.tripletNumber) {
2190
- let y = (left.y + right.y) / 2 + obj.tripletNumberOffsetY;
2191
- obj.tripletNumber.offset(0, -obj.tripletNumber.getRect().centerY + y);
2210
+ if (obj.tupletNumber) {
2211
+ let y = (left.y + right.y) / 2 + obj.tupletNumberOffsetY;
2212
+ obj.tupletNumber.offset(0, -obj.tupletNumber.getRect().centerY + y);
2192
2213
  }
2193
2214
  });
2194
2215
  }
@@ -2200,21 +2221,21 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2200
2221
  let { unitSize, beamThickness, lineWidth } = renderer;
2201
2222
  let color = "black";
2202
2223
  this.staffObjects.forEach((obj) => {
2203
- if (this.type === 2 /* TripletGroup */) {
2224
+ if (this.type === 2 /* TupletGroup */) {
2204
2225
  let l = obj.points[0];
2205
2226
  let r = obj.points[obj.points.length - 1];
2206
2227
  if (l && r) {
2207
- let tf = obj.tripletNumber ? obj.tripletNumber.getRect().width / (r.x - l.x) * 1.2 : 0;
2228
+ let tf = obj.tupletNumber ? obj.tupletNumber.getRect().width / (r.x - l.x) * 1.2 : 0;
2208
2229
  let lc = Utils3.Math.interpolateCoord(l.x, l.y, r.x, r.y, 0.5 - tf / 2);
2209
2230
  let rc = Utils3.Math.interpolateCoord(l.x, l.y, r.x, r.y, 0.5 + tf / 2);
2210
- let tipH = this.stemDir === 1 /* Up */ ? unitSize : -unitSize;
2231
+ let tipH = this.stemDir === "up" /* Up */ ? unitSize : -unitSize;
2211
2232
  renderer.drawLine(l.x, l.y, lc.x, lc.y, color, lineWidth);
2212
2233
  renderer.drawLine(rc.x, rc.y, r.x, r.y, color, lineWidth);
2213
2234
  renderer.drawLine(l.x, l.y, l.x, l.y + tipH, color, lineWidth);
2214
2235
  renderer.drawLine(r.x, r.y, r.x, r.y + tipH, color, lineWidth);
2215
2236
  }
2216
- } else if (this.type === 0 /* RegularBeam */ || this.type === 1 /* TripletBeam */) {
2217
- let beamSeparation = DocumentSettings.BeamSeparation * unitSize * (this.stemDir === 1 /* Up */ ? 1 : -1);
2237
+ } else if (this.type === 0 /* RegularBeam */ || this.type === 1 /* TupletBeam */) {
2238
+ let beamSeparation = DocumentSettings.BeamSeparation * unitSize * (this.stemDir === "up" /* Up */ ? 1 : -1);
2218
2239
  let noteGroupPoints = obj.points.filter((p) => p.symbol instanceof ObjNoteGroup);
2219
2240
  for (let i = 0; i < noteGroupPoints.length - 1; i++) {
2220
2241
  let left = noteGroupPoints[i];
@@ -2241,8 +2262,8 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2241
2262
  }
2242
2263
  }
2243
2264
  }
2244
- if (obj.tripletNumber) {
2245
- obj.tripletNumber.draw(renderer);
2265
+ if (obj.tupletNumber) {
2266
+ obj.tupletNumber.draw(renderer);
2246
2267
  }
2247
2268
  });
2248
2269
  }
@@ -2250,6 +2271,12 @@ var ObjBeamGroup = class _ObjBeamGroup extends MusicObject {
2250
2271
 
2251
2272
  // src/score/engine/obj-note-group.ts
2252
2273
  import { MusicError as MusicError7, MusicErrorType as MusicErrorType7 } from "@tspro/web-music-score/core";
2274
+ function getStem(stem) {
2275
+ return Utils4.Is.isEnumValue(stem, Stem) ? stem : void 0;
2276
+ }
2277
+ function getArpeggio(a) {
2278
+ return Utils4.Is.isEnumValue(a, Arpeggio) ? a : a === true ? "up" /* Up */ : void 0;
2279
+ }
2253
2280
  function sortNoteStringData(notes, strings) {
2254
2281
  let stringArr = Utils4.Arr.isArray(strings) ? strings : strings !== void 0 ? [strings] : [];
2255
2282
  let noteStringData = notes.map((note, i) => {
@@ -2261,9 +2288,6 @@ function sortNoteStringData(notes, strings) {
2261
2288
  strings: noteStringData.every((e) => e.string === void 0) ? void 0 : noteStringData.map((e) => e.string)
2262
2289
  };
2263
2290
  }
2264
- function solveArpeggio(a) {
2265
- return a === true || a === 0 /* Up */ ? 0 /* Up */ : a === 1 /* Down */ ? 1 /* Down */ : void 0;
2266
- }
2267
2291
  var ObjStaffNoteGroup = class extends MusicObject {
2268
2292
  constructor(staff, noteGroup) {
2269
2293
  super(staff);
@@ -2353,7 +2377,7 @@ var ObjTabNoteGroup = class extends MusicObject {
2353
2377
  }
2354
2378
  };
2355
2379
  var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2356
- constructor(col, voiceId, notes, noteLength, options) {
2380
+ constructor(col, voiceId, notes, noteLength, options, tupletRatio) {
2357
2381
  var _a, _b, _c;
2358
2382
  super(col);
2359
2383
  this.col = col;
@@ -2369,6 +2393,7 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2369
2393
  __publicField(this, "staccato");
2370
2394
  __publicField(this, "diamond");
2371
2395
  __publicField(this, "arpeggio");
2396
+ __publicField(this, "oldStyleTriplet");
2372
2397
  __publicField(this, "rhythmProps");
2373
2398
  __publicField(this, "startConnnectives", []);
2374
2399
  __publicField(this, "runningConnectives", []);
@@ -2386,13 +2411,15 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2386
2411
  this.minDiatonicId = this.notes[0].diatonicId;
2387
2412
  this.maxDiatonicId = this.notes[this.notes.length - 1].diatonicId;
2388
2413
  this.ownDiatonicId = this.measure.updateOwnDiatonicId(voiceId, Math.round((this.minDiatonicId + this.maxDiatonicId) / 2));
2389
- this.ownStemDir = this.measure.updateOwnStemDir(this, options == null ? void 0 : options.stem);
2414
+ this.ownStemDir = this.measure.updateOwnStemDir(this, getStem(options == null ? void 0 : options.stem));
2390
2415
  this.ownString = this.measure.updateOwnString(this, noteStringData.strings);
2391
2416
  this.color = (_a = options == null ? void 0 : options.color) != null ? _a : "black";
2392
2417
  this.staccato = (_b = options == null ? void 0 : options.staccato) != null ? _b : false;
2393
2418
  this.diamond = (_c = options == null ? void 0 : options.diamond) != null ? _c : false;
2394
- this.arpeggio = solveArpeggio(options == null ? void 0 : options.arpeggio);
2395
- this.rhythmProps = new RhythmProps2(noteLength, options == null ? void 0 : options.dotted, options == null ? void 0 : options.triplet);
2419
+ this.arpeggio = getArpeggio(options == null ? void 0 : options.arpeggio);
2420
+ this.oldStyleTriplet = tupletRatio === void 0 && ((options == null ? void 0 : options.triplet) === true || NoteLengthProps3.get(noteLength).isTriplet);
2421
+ let dotCount = typeof (options == null ? void 0 : options.dotted) === "number" ? options.dotted > 0 ? options.dotted : void 0 : (options == null ? void 0 : options.dotted) === true ? 1 : void 0;
2422
+ this.rhythmProps = RhythmProps2.get(noteLength, dotCount, (tupletRatio != null ? tupletRatio : this.oldStyleTriplet) ? Tuplet3.Triplet : void 0);
2396
2423
  this.mi = new MNoteGroup(this);
2397
2424
  }
2398
2425
  getMusicInterface() {
@@ -2410,16 +2437,13 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2410
2437
  get stemDir() {
2411
2438
  return this.beamGroup ? this.beamGroup.stemDir : this.ownStemDir;
2412
2439
  }
2413
- get triplet() {
2414
- return this.rhythmProps.triplet;
2415
- }
2416
2440
  enableConnective(line) {
2417
2441
  return line.containsVoiceId(this.voiceId) && (line instanceof ObjTab || line.containsDiatonicId(this.ownDiatonicId));
2418
2442
  }
2419
2443
  startConnective(connectiveProps) {
2420
- if (!this.row.hasStaff && connectiveProps.connective === 0 /* Tie */) {
2444
+ if (!this.row.hasStaff && connectiveProps.connective === "tie" /* Tie */) {
2421
2445
  throw new MusicError7(MusicErrorType7.Score, "Ties not implemented for guitar tabs alone, staff is required!");
2422
- } else if (!this.row.hasStaff && connectiveProps.connective === 1 /* Slur */) {
2446
+ } else if (!this.row.hasStaff && connectiveProps.connective === "slur" /* Slur */) {
2423
2447
  throw new MusicError7(MusicErrorType7.Score, "Slurs not implemented for guitar tabs alone, staff is required!");
2424
2448
  }
2425
2449
  this.startConnnectives.push(connectiveProps);
@@ -2478,7 +2502,7 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2478
2502
  let stemTip = obj.stemTip;
2479
2503
  let stemDir = this.stemDir;
2480
2504
  let hasStem = stemTip !== void 0;
2481
- let stemSide = !hasStem ? void 0 : stemDir === 1 /* Up */ ? "right" : "left";
2505
+ let stemSide = !hasStem ? void 0 : stemDir === "up" /* Up */ ? "right" : "left";
2482
2506
  let padding = noteHeadRect.height / 2;
2483
2507
  let centerX = noteHeadRect.centerX;
2484
2508
  let centerY = noteHeadRect.centerY;
@@ -2486,16 +2510,16 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2486
2510
  let rightX = noteHeadRect.right + padding;
2487
2511
  let aboveY = noteHeadRect.top - padding;
2488
2512
  let belowY = noteHeadRect.bottom + padding;
2489
- if (noteAnchor === 0 /* Auto */) {
2490
- noteAnchor = 3 /* Below */;
2491
- } else if (noteAnchor === 4 /* StemTip */ && !hasStem) {
2492
- noteAnchor = stemDir === 1 /* Up */ ? 1 /* Above */ : 3 /* Below */;
2513
+ if (noteAnchor === "auto" /* Auto */) {
2514
+ noteAnchor = "below" /* Below */;
2515
+ } else if (noteAnchor === "stemTip" /* StemTip */ && !hasStem) {
2516
+ noteAnchor = stemDir === "up" /* Up */ ? "above" /* Above */ : "below" /* Below */;
2493
2517
  }
2494
2518
  switch (noteAnchor) {
2495
- case 2 /* Center */:
2519
+ case "center" /* Center */:
2496
2520
  return side === "left" ? { x: rightX, y: centerY } : { x: leftX, y: centerY };
2497
- case 1 /* Above */:
2498
- if (!hasStem || stemDir === 2 /* Down */) {
2521
+ case "above" /* Above */:
2522
+ if (!hasStem || stemDir === "down" /* Down */) {
2499
2523
  return { x: centerX, y: aboveY };
2500
2524
  } else {
2501
2525
  return {
@@ -2503,8 +2527,8 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2503
2527
  y: aboveY
2504
2528
  };
2505
2529
  }
2506
- case 3 /* Below */:
2507
- if (!hasStem || stemDir === 1 /* Up */) {
2530
+ case "below" /* Below */:
2531
+ if (!hasStem || stemDir === "up" /* Up */) {
2508
2532
  return { x: centerX, y: belowY };
2509
2533
  } else {
2510
2534
  return {
@@ -2512,8 +2536,8 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2512
2536
  y: belowY
2513
2537
  };
2514
2538
  }
2515
- case 4 /* StemTip */:
2516
- return { x: centerX, y: stemTip.centerY + (stemDir === 1 /* Up */ ? -padding : padding) };
2539
+ case "stemTip" /* StemTip */:
2540
+ return { x: centerX, y: stemTip.centerY + (stemDir === "up" /* Up */ ? -padding : padding) };
2517
2541
  default:
2518
2542
  throw new MusicError7(MusicErrorType7.Score, "Invalid noteAnchor: " + noteAnchor);
2519
2543
  }
@@ -2528,7 +2552,7 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2528
2552
  let x = side === "right" ? r.left : r.right;
2529
2553
  let y;
2530
2554
  let s = 0.9;
2531
- if (connectiveProps.connective === 2 /* Slide */) {
2555
+ if (connectiveProps.connective === "slide" /* Slide */) {
2532
2556
  let leftFretNumber = connectiveProps.noteGroups[0].getFretNumber(obj, 0);
2533
2557
  let rightFretNumber = connectiveProps.noteGroups[1].getFretNumber(obj, 0);
2534
2558
  let slideUp = leftFretNumber === void 0 || rightFretNumber === void 0 || leftFretNumber <= rightFretNumber;
@@ -2582,7 +2606,7 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2582
2606
  this.runningConnectives = [];
2583
2607
  }
2584
2608
  getPlaySlur() {
2585
- let slurs = this.runningConnectives.filter((c) => c.connective === 1 /* Slur */).map((c) => c.startsWith(this) ? "first" : "slurred");
2609
+ let slurs = this.runningConnectives.filter((c) => c.connective === "slur" /* Slur */).map((c) => c.startsWith(this) ? "first" : "slurred");
2586
2610
  if (slurs.indexOf("first") >= 0) {
2587
2611
  return "first";
2588
2612
  } else if (slurs.indexOf("slurred") >= 0) {
@@ -2594,8 +2618,8 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2594
2618
  getBeamGroup() {
2595
2619
  return this.beamGroup;
2596
2620
  }
2597
- setBeamGroup(beam) {
2598
- this.beamGroup = beam;
2621
+ setBeamGroup(beamGroup) {
2622
+ this.beamGroup = beamGroup;
2599
2623
  }
2600
2624
  resetBeamGroup() {
2601
2625
  this.leftBeamCount = this.rightBeamCount = 0;
@@ -2606,19 +2630,19 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2606
2630
  var _a, _b, _c, _d;
2607
2631
  let staff = obj.staff;
2608
2632
  let x = (_b = (_a = obj.stemTip) == null ? void 0 : _a.centerX) != null ? _b : obj.noteHeadRects[0].centerX;
2609
- let y = (_d = (_c = obj.stemTip) == null ? void 0 : _c.centerY) != null ? _d : this.stemDir === 1 /* Up */ ? obj.getRect().top : obj.getRect().bottom;
2610
- let stemHeight = this.stemDir === 1 /* Up */ ? Math.abs(obj.noteHeadRects[0].centerY - y) : Math.abs(obj.noteHeadRects[obj.noteHeadRects.length - 1].centerY - y);
2633
+ let y = (_d = (_c = obj.stemTip) == null ? void 0 : _c.centerY) != null ? _d : this.stemDir === "up" /* Up */ ? obj.getRect().top : obj.getRect().bottom;
2634
+ let stemHeight = this.stemDir === "up" /* Up */ ? Math.abs(obj.noteHeadRects[0].centerY - y) : Math.abs(obj.noteHeadRects[obj.noteHeadRects.length - 1].centerY - y);
2611
2635
  return { staff, x, y, stemHeight };
2612
2636
  });
2613
2637
  }
2614
2638
  getStemHeight(renderer) {
2615
2639
  let { unitSize } = renderer;
2616
- let { noteLength, flagCount } = this.rhythmProps;
2617
- if (noteLength >= NoteLength3.Whole) {
2618
- return 0;
2619
- } else {
2640
+ let { flagCount, hasStem } = this.rhythmProps;
2641
+ if (hasStem) {
2620
2642
  let addY = this.hasBeamCount() ? DocumentSettings.BeamSeparation : DocumentSettings.FlagSeparation;
2621
2643
  return (DocumentSettings.StemHeight + Math.max(0, flagCount - 1) * addY) * unitSize;
2644
+ } else {
2645
+ return 0;
2622
2646
  }
2623
2647
  }
2624
2648
  hasBeamCount() {
@@ -2637,13 +2661,13 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2637
2661
  return staff.containsVoiceId(this.voiceId) && this.staffObjects.some((obj) => obj instanceof ObjStaffNoteGroup && obj.staff === staff);
2638
2662
  }
2639
2663
  getPlayTicks(note) {
2640
- let tiedTicks = this.runningConnectives.filter((c) => c.connective === 0 /* Tie */).map((tie) => {
2664
+ let tiedTicks = this.runningConnectives.filter((c) => c.connective === "tie" /* Tie */).map((tie) => {
2641
2665
  let tieNoteGroups = tie.noteGroups;
2642
2666
  let j = tieNoteGroups.indexOf(this);
2643
2667
  if (j < 0) {
2644
2668
  return 0;
2645
2669
  }
2646
- if (tie.span === -1 /* Stub */ || tie.span === -2 /* ToMeasureEnd */) {
2670
+ if (tie.span === "stub" /* Stub */ || tie.span === "toMeasureEnd" /* ToMeasureEnd */) {
2647
2671
  return Math.max(this.rhythmProps.ticks, this.measure.getMeasureTicks() - this.col.positionTicks);
2648
2672
  }
2649
2673
  let prev = tieNoteGroups[j - 1];
@@ -2670,7 +2694,7 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2670
2694
  this.requestRectUpdate();
2671
2695
  let { unitSize } = renderer;
2672
2696
  let { row, stemDir } = this;
2673
- let { dotted, flagCount } = this.rhythmProps;
2697
+ let { dotCount, flagCount, hasStem } = this.rhythmProps;
2674
2698
  let dotWidth = DocumentSettings.DotSize * unitSize;
2675
2699
  let noteHeadWidth = (this.diamond ? DocumentSettings.DiamondNoteHeadSize : DocumentSettings.NoteHeadWidth) * unitSize;
2676
2700
  let noteHeadHeight = (this.diamond ? DocumentSettings.DiamondNoteHeadSize : DocumentSettings.NoteHeadHeight) * unitSize;
@@ -2690,10 +2714,10 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2690
2714
  let noteX = this.col.getNoteHeadDisplacement(this, note) * noteHeadWidth;
2691
2715
  let noteY = noteStaff.getDiatonicIdY(note.diatonicId);
2692
2716
  let isNoteOnLine = noteStaff.isLine(note.diatonicId);
2693
- if (isBottomNote && stemDir === 1 /* Up */) stemBaseStaff = noteStaff;
2694
- if (isTopNote && stemDir === 1 /* Up */) stemTipStaff = noteStaff;
2695
- if (isBottomNote && stemDir === 2 /* Down */) stemTipStaff = noteStaff;
2696
- if (isTopNote && stemDir === 2 /* Down */) stemBaseStaff = noteStaff;
2717
+ if (isBottomNote && stemDir === "up" /* Up */) stemBaseStaff = noteStaff;
2718
+ if (isTopNote && stemDir === "up" /* Up */) stemTipStaff = noteStaff;
2719
+ if (isBottomNote && stemDir === "down" /* Down */) stemTipStaff = noteStaff;
2720
+ if (isTopNote && stemDir === "down" /* Down */) stemBaseStaff = noteStaff;
2697
2721
  let noteHeadRect = obj.noteHeadRects[noteIndex] = DivRect.createCentered(noteX, noteY, noteHeadWidth, noteHeadHeight);
2698
2722
  noteStaff.addObject(noteHeadRect);
2699
2723
  if (accState.needAccidental(note)) {
@@ -2704,21 +2728,21 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2704
2728
  }
2705
2729
  noteStaff.addObject(acc);
2706
2730
  }
2707
- if (dotted) {
2708
- let dotX = noteHeadRect.right + DocumentSettings.NoteDotSpace * unitSize + dotWidth / 2;
2731
+ for (let i = 0; i < dotCount; i++) {
2732
+ let dotX = noteHeadRect.right + DocumentSettings.NoteDotSpace * unitSize + dotWidth / 2 + i * dotWidth * 1.5;
2709
2733
  let dotY = noteY + this.getDotVerticalDisplacement(staff, note.diatonicId, stemDir) * unitSize;
2710
2734
  let r = DivRect.createCentered(dotX, dotY, dotWidth, dotWidth);
2711
2735
  obj.dotRects.push(r);
2712
2736
  noteStaff.addObject(r);
2713
2737
  }
2714
2738
  if (this.staccato) {
2715
- if (stemDir === 1 /* Up */ && isBottomNote) {
2739
+ if (stemDir === "up" /* Up */ && isBottomNote) {
2716
2740
  let dotX = noteX;
2717
2741
  let dotY = noteY + unitSize * (isNoteOnLine ? 3 : 2);
2718
2742
  let r = DivRect.createCentered(dotX, dotY, dotWidth, dotWidth);
2719
2743
  obj.dotRects.push(r);
2720
2744
  stemBaseStaff.addObject(r);
2721
- } else if (stemDir === 2 /* Down */ && isTopNote) {
2745
+ } else if (stemDir === "down" /* Down */ && isTopNote) {
2722
2746
  let dotX = noteX;
2723
2747
  let dotY = noteY - unitSize * (isNoteOnLine ? 3 : 2);
2724
2748
  let r = DivRect.createCentered(dotX, dotY, dotWidth, dotWidth);
@@ -2729,11 +2753,11 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2729
2753
  });
2730
2754
  let bottomNoteY = obj.noteHeadRects[0].centerY;
2731
2755
  let topNoteY = obj.noteHeadRects[obj.noteHeadRects.length - 1].centerY;
2732
- let stemX = stemDir === 1 /* Up */ ? noteHeadWidth / 2 : -noteHeadWidth / 2;
2756
+ let stemX = stemDir === "up" /* Up */ ? noteHeadWidth / 2 : -noteHeadWidth / 2;
2733
2757
  let stemHeight = this.getStemHeight(renderer);
2734
- let stemTipY = stemDir === 1 /* Up */ ? topNoteY - stemHeight : bottomNoteY + stemHeight;
2735
- let stemBaseY = stemDir === 1 /* Up */ ? bottomNoteY : topNoteY;
2736
- if (this.rhythmProps.hasStem()) {
2758
+ let stemTipY = stemDir === "up" /* Up */ ? topNoteY - stemHeight : bottomNoteY + stemHeight;
2759
+ let stemBaseY = stemDir === "up" /* Up */ ? bottomNoteY : topNoteY;
2760
+ if (hasStem) {
2737
2761
  obj.stemTip = new DivRect(stemX, stemX, stemTipY, stemTipY);
2738
2762
  obj.stemBase = new DivRect(stemX, stemX, stemBaseY, stemBaseY);
2739
2763
  stemTipStaff.addObject(obj.stemTip);
@@ -2744,7 +2768,7 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2744
2768
  let flagHeight = flagCount === 0 ? 0 : DocumentSettings.FlagHeight * unitSize;
2745
2769
  for (let i = 0; i < flagCount; i++) {
2746
2770
  let flagAddY = i * unitSize * DocumentSettings.FlagSeparation;
2747
- let r = obj.flagRects[i] = stemDir === 1 /* Up */ ? new DivRect(stemX, stemX + flagWidth, stemTipY + flagAddY, stemTipY + flagHeight + flagAddY) : new DivRect(stemX, stemX + flagWidth, stemTipY - flagHeight - flagAddY, stemTipY - flagAddY);
2771
+ let r = obj.flagRects[i] = stemDir === "up" /* Up */ ? new DivRect(stemX, stemX + flagWidth, stemTipY + flagAddY, stemTipY + flagHeight + flagAddY) : new DivRect(stemX, stemX + flagWidth, stemTipY - flagHeight - flagAddY, stemTipY - flagAddY);
2748
2772
  stemTipStaff.addObject(r);
2749
2773
  }
2750
2774
  }
@@ -2757,7 +2781,6 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2757
2781
  }
2758
2782
  let obj = new ObjTabNoteGroup(tab, this);
2759
2783
  this.notes.forEach((note, noteIndex) => {
2760
- var _a, _b;
2761
2784
  if (this.ownString[noteIndex] !== void 0) {
2762
2785
  let stringId = this.ownString[noteIndex] - 1;
2763
2786
  let fretId = note.chromaticId - tab.getTuningStrings()[stringId].chromaticId;
@@ -2765,9 +2788,7 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2765
2788
  let fretNumber = new ObjText(this, { text: String(fretId), color, bgcolor: "white" }, 0.5, 0.5);
2766
2789
  obj.fretNumbers.push(fretNumber);
2767
2790
  fretNumber.layout(renderer);
2768
- let noteX = this.col.getNoteHeadDisplacement(this, note) * noteHeadWidth;
2769
- let stemX = (_b = (_a = this.staffObjects[0]) == null ? void 0 : _a.stemBase) == null ? void 0 : _b.centerX;
2770
- let x = stemX != null ? stemX : noteX;
2791
+ let x = this.col.getRect().centerX;
2771
2792
  let y = tab.getStringY(stringId);
2772
2793
  fretNumber.offset(x, y);
2773
2794
  }
@@ -2810,15 +2831,22 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2810
2831
  renderer.drawDebugRect(this.getRect());
2811
2832
  let { lineWidth } = renderer;
2812
2833
  let { color, stemDir } = this;
2813
- let { noteLength } = this.rhythmProps;
2834
+ let { isSolidNoteHead } = this.rhythmProps;
2814
2835
  this.staffObjects.forEach((obj) => {
2815
2836
  obj.accidentals.forEach((d) => d.draw(renderer));
2816
2837
  ctx.strokeStyle = ctx.fillStyle = color;
2817
2838
  ctx.lineWidth = lineWidth;
2818
2839
  obj.noteHeadRects.forEach((r) => {
2819
- let outlinedNoteHead = noteLength >= NoteLength3.Half;
2820
2840
  if (this.diamond) {
2821
- if (outlinedNoteHead) {
2841
+ if (isSolidNoteHead) {
2842
+ ctx.beginPath();
2843
+ ctx.moveTo(r.centerX, r.top);
2844
+ ctx.lineTo(r.right, r.centerY);
2845
+ ctx.lineTo(r.centerX, r.bottom);
2846
+ ctx.lineTo(r.left, r.centerY);
2847
+ ctx.lineTo(r.centerX, r.top);
2848
+ ctx.fill();
2849
+ } else {
2822
2850
  ctx.beginPath();
2823
2851
  ctx.lineWidth = lineWidth * 2.5;
2824
2852
  ctx.moveTo(r.centerX, r.top);
@@ -2833,22 +2861,14 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2833
2861
  ctx.moveTo(r.centerX, r.top);
2834
2862
  ctx.lineTo(r.left, r.centerY);
2835
2863
  ctx.stroke();
2836
- } else {
2837
- ctx.beginPath();
2838
- ctx.moveTo(r.centerX, r.top);
2839
- ctx.lineTo(r.right, r.centerY);
2840
- ctx.lineTo(r.centerX, r.bottom);
2841
- ctx.lineTo(r.left, r.centerY);
2842
- ctx.lineTo(r.centerX, r.top);
2843
- ctx.fill();
2844
2864
  }
2845
2865
  } else {
2846
2866
  ctx.beginPath();
2847
2867
  ctx.ellipse(r.centerX, r.centerY, r.leftw, r.toph, -0.3, 0, Math.PI * 2);
2848
- if (outlinedNoteHead) {
2849
- ctx.stroke();
2850
- } else {
2868
+ if (isSolidNoteHead) {
2851
2869
  ctx.fill();
2870
+ } else {
2871
+ ctx.stroke();
2852
2872
  }
2853
2873
  }
2854
2874
  });
@@ -2863,8 +2883,8 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2863
2883
  let left = rect.left;
2864
2884
  let right = rect.right;
2865
2885
  let width = right - left;
2866
- let top = stemDir === 1 /* Up */ ? rect.top : rect.bottom;
2867
- let bottom = stemDir === 1 /* Up */ ? rect.bottom : rect.top;
2886
+ let top = stemDir === "up" /* Up */ ? rect.top : rect.bottom;
2887
+ let bottom = stemDir === "up" /* Up */ ? rect.bottom : rect.top;
2868
2888
  ctx.beginPath();
2869
2889
  ctx.moveTo(left, top);
2870
2890
  ctx.bezierCurveTo(
@@ -2878,13 +2898,13 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2878
2898
  ctx.stroke();
2879
2899
  });
2880
2900
  });
2881
- this.tabObjects.forEach((obj) => {
2882
- obj.fretNumbers.forEach((fn) => fn.draw(renderer));
2883
- });
2901
+ this.tabObjects.forEach((obj) => obj.fretNumbers.forEach((fn) => fn.draw(renderer)));
2884
2902
  }
2885
2903
  static setBeamCounts(groupNotes) {
2886
2904
  const isADottedBHalf = (a, b) => {
2887
- return a.rhythmProps.noteLength === b.rhythmProps.noteLength * 2 && a.rhythmProps.dotted && !b.rhythmProps.dotted && a.rhythmProps.flagCount > 0 && b.rhythmProps.flagCount > 0;
2905
+ let { flagCount: aFlagCount, noteSize: aNoteSize, dotCount: aDotCount } = a.rhythmProps;
2906
+ let { flagCount: bFlagCount, noteSize: bNoteSize, dotCount: bDotCount } = b.rhythmProps;
2907
+ return aFlagCount > 0 && bFlagCount > 0 && aDotCount > 0 && bDotCount === 0 && aNoteSize * Math.pow(2, aDotCount) === bNoteSize;
2888
2908
  };
2889
2909
  for (let i = 0; i < groupNotes.length; i++) {
2890
2910
  let center = groupNotes[i];
@@ -2930,29 +2950,27 @@ var ObjNoteGroup = class _ObjNoteGroup extends MusicObject {
2930
2950
  }
2931
2951
  } while (fixAgain);
2932
2952
  }
2933
- static setTripletBeamCounts(triplet) {
2934
- let type = triplet.getType();
2935
- let symbols = triplet.getSymbols();
2936
- if (type === 1 /* TripletBeam */) {
2953
+ static setTupletBeamCounts(tuplet) {
2954
+ let type = tuplet.getType();
2955
+ let symbols = tuplet.getSymbols();
2956
+ if (type === 1 /* TupletBeam */) {
2937
2957
  symbols.forEach((s, i) => {
2938
2958
  if (s instanceof _ObjNoteGroup) {
2939
2959
  s.leftBeamCount = i === 0 ? 0 : s.rhythmProps.flagCount;
2940
2960
  s.rightBeamCount = i === symbols.length - 1 ? 0 : s.rhythmProps.flagCount;
2941
2961
  }
2942
2962
  });
2943
- } else if (type === 2 /* TripletGroup */) {
2963
+ } else if (type === 2 /* TupletGroup */) {
2944
2964
  symbols.forEach((s) => {
2945
2965
  if (s instanceof _ObjNoteGroup) {
2946
2966
  s.leftBeamCount = s.rightBeamCount = 0;
2947
2967
  }
2948
2968
  });
2949
- } else {
2950
- throw new MusicError7(MusicErrorType7.Score, "Cannot set triplet beam count because triplet beam group type is invalid.");
2951
2969
  }
2952
2970
  }
2953
2971
  getDotVerticalDisplacement(staff, diatonicId, stemDir) {
2954
2972
  if (staff.isLine(diatonicId)) {
2955
- return stemDir === 1 /* Up */ ? -1 : 1;
2973
+ return stemDir === "up" /* Up */ ? -1 : 1;
2956
2974
  } else {
2957
2975
  return 0;
2958
2976
  }
@@ -2977,7 +2995,7 @@ import { MusicError as MusicError8, MusicErrorType as MusicErrorType8 } from "@t
2977
2995
  var noteHeadDataCompareFunc = (a, b) => {
2978
2996
  let cmp = Note5.compareFunc(a.note, b.note);
2979
2997
  if (cmp === 0) {
2980
- cmp = a.noteGroup.stemDir === b.noteGroup.stemDir ? 0 : a.noteGroup.stemDir === 1 /* Up */ ? 1 : -1;
2998
+ cmp = a.noteGroup.stemDir === b.noteGroup.stemDir ? 0 : a.noteGroup.stemDir === "up" /* Up */ ? 1 : -1;
2981
2999
  }
2982
3000
  return cmp;
2983
3001
  };
@@ -3090,16 +3108,14 @@ var ObjRhythmColumn = class extends MusicObject {
3090
3108
  }
3091
3109
  getArpeggioDir() {
3092
3110
  var _a;
3093
- return (_a = this.arpeggioDir) != null ? _a : 0 /* Up */;
3111
+ return (_a = this.arpeggioDir) != null ? _a : "up" /* Up */;
3094
3112
  }
3095
3113
  setVoiceSymbol(voiceId, symbol) {
3096
3114
  validateVoiceId(voiceId);
3097
3115
  this.voiceSymbol[voiceId] = symbol;
3098
- if (symbol instanceof ObjRest) {
3099
- if (!symbol.hide && symbol.noteLength >= NoteLength4.Half) {
3100
- this.minDiatonicId = this.minDiatonicId === void 0 ? symbol.ownDiatonicId : Math.min(this.minDiatonicId, symbol.ownDiatonicId);
3101
- this.maxDiatonicId = this.maxDiatonicId === void 0 ? symbol.ownDiatonicId : Math.max(this.maxDiatonicId, symbol.ownDiatonicId);
3102
- }
3116
+ if (symbol instanceof ObjRest && !symbol.hide) {
3117
+ this.minDiatonicId = this.minDiatonicId === void 0 ? symbol.ownDiatonicId : Math.min(this.minDiatonicId, symbol.ownDiatonicId);
3118
+ this.maxDiatonicId = this.maxDiatonicId === void 0 ? symbol.ownDiatonicId : Math.max(this.maxDiatonicId, symbol.ownDiatonicId);
3103
3119
  } else if (symbol instanceof ObjNoteGroup) {
3104
3120
  this.minDiatonicId = this.minDiatonicId === void 0 ? symbol.notes[0].diatonicId : Math.min(this.minDiatonicId, symbol.notes[0].diatonicId);
3105
3121
  this.maxDiatonicId = this.maxDiatonicId === void 0 ? symbol.notes[symbol.notes.length - 1].diatonicId : Math.max(this.maxDiatonicId, symbol.notes[symbol.notes.length - 1].diatonicId);
@@ -3115,15 +3131,18 @@ var ObjRhythmColumn = class extends MusicObject {
3115
3131
  return this.voiceSymbol[voiceId];
3116
3132
  }
3117
3133
  getMinWidth() {
3118
- let maxNoteLength = Math.max(...this.voiceSymbol.map((s) => s.rhythmProps.noteLength));
3134
+ let maxNoteSize = Math.max(...this.voiceSymbol.map((s) => s.rhythmProps.noteSize));
3119
3135
  let w = DocumentSettings.NoteHeadWidth;
3120
- switch (maxNoteLength) {
3121
- case NoteLength4.Whole:
3136
+ switch (maxNoteSize) {
3137
+ case 1:
3122
3138
  return w * 5;
3123
- case NoteLength4.Half:
3139
+ // whole note
3140
+ case 2:
3124
3141
  return w * 3;
3125
- case NoteLength4.Quarter:
3142
+ // half note
3143
+ case 4:
3126
3144
  return w * 2;
3145
+ // quarter note
3127
3146
  default:
3128
3147
  return w;
3129
3148
  }
@@ -3155,7 +3174,7 @@ var ObjRhythmColumn = class extends MusicObject {
3155
3174
  if (cur.displacement !== void 0) {
3156
3175
  continue;
3157
3176
  }
3158
- let d = cur.noteGroup.stemDir === 2 /* Down */ ? -1 : 1;
3177
+ let d = cur.noteGroup.stemDir === "down" /* Down */ ? -1 : 1;
3159
3178
  if (prev && cur.note.diatonicId - prev.note.diatonicId <= 1) {
3160
3179
  cur.displacement = prev.displacement === 0 ? d : 0;
3161
3180
  } else if (next && next.note.diatonicId - cur.note.diatonicId <= 1) {
@@ -3209,7 +3228,7 @@ var ObjRhythmColumn = class extends MusicObject {
3209
3228
  }
3210
3229
  });
3211
3230
  playerNotes.sort((a, b) => Note5.compareFunc(a.note, b.note));
3212
- if (this.hasArpeggio() && this.getArpeggioDir() === 1 /* Down */) {
3231
+ if (this.hasArpeggio() && this.getArpeggioDir() === "down" /* Down */) {
3213
3232
  playerNotes.reverse();
3214
3233
  }
3215
3234
  return playerNotes;
@@ -3326,6 +3345,12 @@ var ObjRhythmColumn = class extends MusicObject {
3326
3345
  }
3327
3346
  };
3328
3347
 
3348
+ // src/score/engine/extension.ts
3349
+ import { MusicError as MusicError9, MusicErrorType as MusicErrorType9 } from "@tspro/web-music-score/core";
3350
+
3351
+ // src/score/engine/element-data.ts
3352
+ import { Utils as Utils5 } from "@tspro/ts-utils-lib";
3353
+
3329
3354
  // src/score/engine/obj-special-text.ts
3330
3355
  var _ObjSpecialText = class _ObjSpecialText extends MusicObject {
3331
3356
  constructor(parent, text) {
@@ -3423,40 +3448,53 @@ __publicField(_ObjSpecialText, "Segno", "\u{1D10B}");
3423
3448
  var ObjSpecialText = _ObjSpecialText;
3424
3449
 
3425
3450
  // src/score/engine/element-data.ts
3426
- function getNavigationString(n) {
3427
- switch (n) {
3428
- case 1 /* DC_al_Coda */:
3451
+ function getNavigationString(navigation) {
3452
+ switch (navigation) {
3453
+ case "D.C. al Coda" /* DC_al_Coda */:
3429
3454
  return "D.C. al Coda";
3430
- case 0 /* DC_al_Fine */:
3455
+ case "D.C. al Fine" /* DC_al_Fine */:
3431
3456
  return "D.C. al Fine";
3432
- case 3 /* DS_al_Coda */:
3457
+ case "D.S. al Coda" /* DS_al_Coda */:
3433
3458
  return "D.S. al Coda";
3434
- case 2 /* DS_al_Fine */:
3459
+ case "D.S. al Fine" /* DS_al_Fine */:
3435
3460
  return "D.S. al Fine";
3436
- case 7 /* Fine */:
3461
+ case "Fine" /* Fine */:
3437
3462
  return "Fine";
3438
- case 6 /* Segno */:
3463
+ case "Segno" /* Segno */:
3439
3464
  return ObjSpecialText.Segno;
3440
- case 4 /* Coda */:
3465
+ case "Coda" /* Coda */:
3441
3466
  return ObjSpecialText.Coda;
3442
- case 5 /* toCoda */:
3467
+ case "toCoda" /* toCoda */:
3443
3468
  return ObjSpecialText.toCoda;
3444
3469
  default:
3445
- return Navigation[n];
3470
+ return navigation[0].toUpperCase() + navigation.substring(1);
3446
3471
  }
3447
3472
  }
3448
3473
  function isDynamicsText(text) {
3449
- return ["ppp", "pp", "p", "mp", "m", "mf", "f", "ff", "fff", "cresc.", "decresc.", "dim."].indexOf(text) >= 0;
3474
+ return Utils5.Is.isEnumValue(text, DynamicsAnnotation);
3450
3475
  }
3451
- function isDynamicsLevelText(text) {
3452
- return ["ppp", "pp", "p", "mp", "m", "mf", "f", "ff", "fff"].indexOf(text) >= 0;
3476
+ function getDynamicsVolume(text) {
3477
+ if (/^(p+|f+|m|mp|mf)$/.test(text)) {
3478
+ let volume = 0.5 - Utils5.Str.charCount(text, "p") * 0.1 + Utils5.Str.charCount(text, "f") * 0.1;
3479
+ return Utils5.Math.clamp(volume, 0, 1);
3480
+ } else {
3481
+ return void 0;
3482
+ }
3453
3483
  }
3454
3484
  function isTempoText(text) {
3455
- return ["accel.", "rit.", "a tempo"].indexOf(text) >= 0;
3485
+ return Utils5.Is.isEnumValue(text, TempoAnnotation);
3486
+ }
3487
+ function getAnnotation(text) {
3488
+ if (Utils5.Is.isEnumValue(text, DynamicsAnnotation)) {
3489
+ return "dynamics" /* Dynamics */;
3490
+ } else if (Utils5.Is.isEnumValue(text, TempoAnnotation)) {
3491
+ return "tempo" /* Tempo */;
3492
+ } else {
3493
+ return void 0;
3494
+ }
3456
3495
  }
3457
3496
 
3458
3497
  // src/score/engine/extension.ts
3459
- import { MusicError as MusicError9, MusicErrorType as MusicErrorType9 } from "@tspro/web-music-score/core";
3460
3498
  function getTextAnchorY(linePos) {
3461
3499
  switch (linePos) {
3462
3500
  case "bottom":
@@ -3511,7 +3549,7 @@ var Extension = class extends MusicObjectLink {
3511
3549
  if (prevMeasure.hasEndSection() || prevMeasure.hasEndSong()) {
3512
3550
  return "section-break";
3513
3551
  }
3514
- let elemArr = [9 /* EndRepeat */, 10 /* Ending */];
3552
+ let elemArr = ["endRepeat" /* EndRepeat */, "ending" /* Ending */];
3515
3553
  for (let i = 0; i < elemArr.length; i++) {
3516
3554
  if (prevMeasure.hasNavigation(elemArr[i])) {
3517
3555
  return "section-break";
@@ -3572,35 +3610,12 @@ var RitardandoSpeedDiv = 2;
3572
3610
  var CrescendoVolumeAdd = 0.5;
3573
3611
  var DiminuendoVolumeSub = 0.5;
3574
3612
  function calcTicksDuration(ticks, tempo) {
3575
- let beatTicks = new RhythmProps3(tempo.options.beatLength, tempo.options.dotted).ticks;
3613
+ let beatTicks = RhythmProps3.get(tempo.options.beatLength, tempo.options.dotCount).ticks;
3576
3614
  let ticksPerMinute = tempo.beatsPerMinute * beatTicks;
3577
3615
  return 60 * ticks / ticksPerMinute;
3578
3616
  }
3579
- function getVolume(dynamicsLevelText) {
3580
- switch (dynamicsLevelText) {
3581
- case "fff":
3582
- return 0.9;
3583
- case "ff":
3584
- return 0.8;
3585
- case "f":
3586
- return 0.7;
3587
- case "mf":
3588
- return 0.6;
3589
- default:
3590
- case "m":
3591
- return 0.5;
3592
- case "mp":
3593
- return 0.4;
3594
- case "p":
3595
- return 0.3;
3596
- case "pp":
3597
- return 0.2;
3598
- case "ppp":
3599
- return 0.1;
3600
- }
3601
- }
3602
3617
  function getDefaultVolume() {
3603
- return getVolume("m");
3618
+ return getDynamicsVolume("m");
3604
3619
  }
3605
3620
  function adjustVolume(linearVolume) {
3606
3621
  return linearVolume * 1.25;
@@ -3628,7 +3643,7 @@ var PlayerColumnProps = class {
3628
3643
  return this.speed;
3629
3644
  }
3630
3645
  getTempo() {
3631
- let speed = Utils5.Math.clamp(this.getSpeed(), 0.1, 10);
3646
+ let speed = Utils6.Math.clamp(this.getSpeed(), 0.1, 10);
3632
3647
  return alterTempoSpeed(this.measure.getTempo(), speed);
3633
3648
  }
3634
3649
  setVolume(volume) {
@@ -3653,7 +3668,7 @@ var PlayerColumnProps = class {
3653
3668
  if (symbolsTicks.length === 0) {
3654
3669
  return 0;
3655
3670
  } else {
3656
- return Utils5.Math.sum(symbolsTicks) / symbolsTicks.length;
3671
+ return Utils6.Math.sum(symbolsTicks) / symbolsTicks.length;
3657
3672
  }
3658
3673
  }
3659
3674
  }
@@ -3716,34 +3731,34 @@ var Player = class _Player {
3716
3731
  continue;
3717
3732
  }
3718
3733
  measureSequence.push(curMeasure);
3719
- if (curMeasure.hasNavigation(8 /* StartRepeat */)) {
3734
+ if (curMeasure.hasNavigation("startRepeat" /* StartRepeat */)) {
3720
3735
  startRepeatMeasure = curMeasure;
3721
3736
  }
3722
- if (curMeasure.hasNavigation(6 /* Segno */)) {
3737
+ if (curMeasure.hasNavigation("Segno" /* Segno */)) {
3723
3738
  segnoMeasure = curMeasure;
3724
3739
  }
3725
- if (alCoda && curMeasure.hasNavigation(5 /* toCoda */)) {
3726
- while (curMeasure && !curMeasure.hasNavigation(4 /* Coda */)) {
3740
+ if (alCoda && curMeasure.hasNavigation("toCoda" /* toCoda */)) {
3741
+ while (curMeasure && !curMeasure.hasNavigation("Coda" /* Coda */)) {
3727
3742
  curMeasure = curMeasure.getNextMeasure();
3728
3743
  }
3729
- } else if (alFine && curMeasure.hasNavigation(7 /* Fine */)) {
3744
+ } else if (alFine && curMeasure.hasNavigation("Fine" /* Fine */)) {
3730
3745
  curMeasure = void 0;
3731
- } else if (curMeasure.hasNavigation(1 /* DC_al_Coda */)) {
3746
+ } else if (curMeasure.hasNavigation("D.C. al Coda" /* DC_al_Coda */)) {
3732
3747
  alCoda = true;
3733
3748
  curMeasure = this.doc.getFirstMeasure();
3734
- } else if (curMeasure.hasNavigation(0 /* DC_al_Fine */)) {
3749
+ } else if (curMeasure.hasNavigation("D.C. al Fine" /* DC_al_Fine */)) {
3735
3750
  alFine = true;
3736
3751
  curMeasure = this.doc.getFirstMeasure();
3737
- } else if (curMeasure.hasNavigation(3 /* DS_al_Coda */)) {
3752
+ } else if (curMeasure.hasNavigation("D.S. al Coda" /* DS_al_Coda */)) {
3738
3753
  alCoda = true;
3739
3754
  curMeasure = segnoMeasure;
3740
- } else if (curMeasure.hasNavigation(2 /* DS_al_Fine */)) {
3755
+ } else if (curMeasure.hasNavigation("D.S. al Fine" /* DS_al_Fine */)) {
3741
3756
  alFine = true;
3742
3757
  curMeasure = segnoMeasure;
3743
- } else if (curMeasure.hasNavigation(9 /* EndRepeat */)) {
3758
+ } else if (curMeasure.hasNavigation("endRepeat" /* EndRepeat */)) {
3744
3759
  let passage = curMeasure.getPassCount();
3745
3760
  let repeatCount = curMeasure.getEndRepeatPlayCount() - 1;
3746
- let cannotPassThrough = ((_a = curMeasure.getNextMeasure()) == null ? void 0 : _a.hasNavigation(10 /* Ending */)) === true;
3761
+ let cannotPassThrough = ((_a = curMeasure.getNextMeasure()) == null ? void 0 : _a.hasNavigation("ending" /* Ending */)) === true;
3747
3762
  if (passage <= repeatCount || cannotPassThrough) {
3748
3763
  curMeasure = startRepeatMeasure;
3749
3764
  } else {
@@ -3794,14 +3809,15 @@ var Player = class _Player {
3794
3809
  col.getAnchoredLayoutObjects().forEach((layoutObj) => {
3795
3810
  var _a2;
3796
3811
  let text = (_a2 = layoutObj.getTextContent()) != null ? _a2 : "";
3797
- if (text === "a tempo") {
3812
+ let vol;
3813
+ if (text === "a tempo" /* a_tempo */) {
3798
3814
  curSpeed = 1;
3799
- } else if (isDynamicsLevelText(text)) {
3800
- curVolume = getVolume(text);
3815
+ } else if ((vol = getDynamicsVolume(text)) !== void 0) {
3816
+ curVolume = vol;
3801
3817
  } else if (layoutObj.musicObj.getLink() instanceof Extension) {
3802
3818
  let extension = layoutObj.musicObj.getLink();
3803
3819
  let { columnRange, extensionBreakText } = extension.getExtensionRangeInfo();
3804
- let totalTicks = Utils5.Math.sum(columnRange.map((c) => c.getTicksToNextColumn()));
3820
+ let totalTicks = Utils6.Math.sum(columnRange.map((c) => c.getTicksToNextColumn()));
3805
3821
  switch (text) {
3806
3822
  case "accel." /* accel */: {
3807
3823
  let startSpeed = curSpeed;
@@ -3826,8 +3842,8 @@ var Player = class _Player {
3826
3842
  case "cresc." /* cresc */: {
3827
3843
  let startVol = curVolume;
3828
3844
  let endVol = startVol + CrescendoVolumeAdd;
3829
- if (extensionBreakText && isDynamicsLevelText(extensionBreakText) && getVolume(extensionBreakText) > startVol) {
3830
- endVol = getVolume(extensionBreakText);
3845
+ if (extensionBreakText && (vol = getDynamicsVolume(extensionBreakText)) !== void 0 && vol > startVol) {
3846
+ endVol = vol;
3831
3847
  }
3832
3848
  let accuTicks = 0;
3833
3849
  columnRange.forEach((c) => {
@@ -3840,8 +3856,8 @@ var Player = class _Player {
3840
3856
  case "dim." /* dim */: {
3841
3857
  let startVol = curVolume;
3842
3858
  let endVol = startVol - DiminuendoVolumeSub;
3843
- if (extensionBreakText && isDynamicsLevelText(extensionBreakText) && getVolume(extensionBreakText) < startVol) {
3844
- endVol = getVolume(extensionBreakText);
3859
+ if (extensionBreakText && (vol = getDynamicsVolume(extensionBreakText)) !== void 0 && vol < startVol) {
3860
+ endVol = vol;
3845
3861
  }
3846
3862
  let accuTicks = 0;
3847
3863
  columnRange.forEach((c) => {
@@ -3855,11 +3871,11 @@ var Player = class _Player {
3855
3871
  });
3856
3872
  let speedArr = (_a = speedMap.get(col)) != null ? _a : [];
3857
3873
  if (speedArr.length > 0) {
3858
- curSpeed = Utils5.Math.sum(speedArr) / speedArr.length;
3874
+ curSpeed = Utils6.Math.sum(speedArr) / speedArr.length;
3859
3875
  }
3860
3876
  let volumeArr = (_b = volumeMap.get(col)) != null ? _b : [];
3861
3877
  if (volumeArr.length > 0) {
3862
- curVolume = Utils5.Math.sum(volumeArr) / volumeArr.length;
3878
+ curVolume = Utils6.Math.sum(volumeArr) / volumeArr.length;
3863
3879
  }
3864
3880
  col.getPlayerProps().setSpeed(curSpeed);
3865
3881
  col.getPlayerProps().setVolume(curVolume);
@@ -3872,7 +3888,7 @@ var Player = class _Player {
3872
3888
  return m;
3873
3889
  }
3874
3890
  let next = m == null ? void 0 : m.getNextMeasure();
3875
- if (!m || m.hasEndSong() || m.hasEndSection() || !next || next.hasNavigation(8 /* StartRepeat */)) {
3891
+ if (!m || m.hasEndSong() || m.hasEndSection() || !next || next.hasNavigation("startRepeat" /* StartRepeat */)) {
3876
3892
  return void 0;
3877
3893
  }
3878
3894
  }
@@ -3897,11 +3913,11 @@ var Player = class _Player {
3897
3913
  } else {
3898
3914
  let playerNotes = col.getPlayerNotes();
3899
3915
  playerNotes.forEach((note, i) => {
3900
- let arpeggioDelayTicks = col.hasArpeggio() ? NoteLength5.ThirtySecond * i : 0;
3916
+ let arpeggioDelayTicks = col.hasArpeggio() ? RhythmProps3.get(NoteLength5.ThirtySecond).ticks * i : 0;
3901
3917
  let noteSeconds = getDuration(note.ticks + fermataHoldTicks - arpeggioDelayTicks, tempo);
3902
3918
  if (noteSeconds > 0) {
3903
3919
  if (note.staccato) {
3904
- noteSeconds = Math.min(getDuration(NoteLength5.Eighth, tempo) / 2, noteSeconds / 2);
3920
+ noteSeconds = Math.min(getDuration(RhythmProps3.get(NoteLength5.Eighth).ticks, tempo) / 2, noteSeconds / 2);
3905
3921
  }
3906
3922
  let volume = adjustVolume(col.getPlayerProps().getVolume());
3907
3923
  if (note.slur === "slurred") {
@@ -4139,8 +4155,8 @@ var ObjBarLineLeft = class extends ObjBarLine {
4139
4155
  solveBarLineType() {
4140
4156
  let m = this.measure;
4141
4157
  let prev = m.getPrevMeasure();
4142
- if (m.hasNavigation(8 /* StartRepeat */)) {
4143
- if (prev && prev.row === m.row && prev.hasNavigation(9 /* EndRepeat */)) {
4158
+ if (m.hasNavigation("startRepeat" /* StartRepeat */)) {
4159
+ if (prev && prev.row === m.row && prev.hasNavigation("endRepeat" /* EndRepeat */)) {
4144
4160
  return 0 /* None */;
4145
4161
  } else {
4146
4162
  return 4 /* StartRepeat */;
@@ -4167,8 +4183,8 @@ var ObjBarLineRight = class extends ObjBarLine {
4167
4183
  solveBarLineType() {
4168
4184
  let m = this.measure;
4169
4185
  let next = m.getNextMeasure();
4170
- if (m.hasNavigation(9 /* EndRepeat */)) {
4171
- if (next && next.row === m.row && next.hasNavigation(8 /* StartRepeat */)) {
4186
+ if (m.hasNavigation("endRepeat" /* EndRepeat */)) {
4187
+ if (next && next.row === m.row && next.hasNavigation("startRepeat" /* StartRepeat */)) {
4172
4188
  return 6 /* EndStartRepeat */;
4173
4189
  } else {
4174
4190
  return 5 /* EndRepeat */;
@@ -4178,10 +4194,10 @@ var ObjBarLineRight = class extends ObjBarLine {
4178
4194
  } else if (m.hasEndSection()) {
4179
4195
  return 2 /* Double */;
4180
4196
  }
4181
- if (m === m.row.getLastMeasure() && next && next.row === m.row.getNextRow() && next.hasNavigation(8 /* StartRepeat */)) {
4197
+ if (m === m.row.getLastMeasure() && next && next.row === m.row.getNextRow() && next.hasNavigation("startRepeat" /* StartRepeat */)) {
4182
4198
  return 2 /* Double */;
4183
4199
  }
4184
- if (next && next.hasNavigation(8 /* StartRepeat */)) {
4200
+ if (next && next.hasNavigation("startRepeat" /* StartRepeat */)) {
4185
4201
  return 0 /* None */;
4186
4202
  }
4187
4203
  return 1 /* Single */;
@@ -4189,7 +4205,7 @@ var ObjBarLineRight = class extends ObjBarLine {
4189
4205
  };
4190
4206
 
4191
4207
  // src/score/engine/obj-ending.ts
4192
- import { Utils as Utils6 } from "@tspro/ts-utils-lib";
4208
+ import { Utils as Utils7 } from "@tspro/ts-utils-lib";
4193
4209
  import { MusicError as MusicError10, MusicErrorType as MusicErrorType10 } from "@tspro/web-music-score/core";
4194
4210
  var ObjEnding = class extends MusicObject {
4195
4211
  constructor(measure, passages) {
@@ -4200,9 +4216,9 @@ var ObjEnding = class extends MusicObject {
4200
4216
  __publicField(this, "shapeRects", []);
4201
4217
  __publicField(this, "mi");
4202
4218
  this.mi = new MEnding(this);
4203
- if (!Utils6.Is.isIntegerGte(passages.length, 1)) {
4219
+ if (!Utils7.Is.isIntegerGte(passages.length, 1)) {
4204
4220
  throw new MusicError10(MusicErrorType10.Score, "Passages is empty.");
4205
- } else if (!this.passages.every((p) => Utils6.Is.isIntegerGte(p, 1))) {
4221
+ } else if (!this.passages.every((p) => Utils7.Is.isIntegerGte(p, 1))) {
4206
4222
  throw new MusicError10(MusicErrorType10.Score, "Invalid passages: " + this.passages);
4207
4223
  }
4208
4224
  this.passages.sort((a, b) => a - b);
@@ -4218,7 +4234,7 @@ var ObjEnding = class extends MusicObject {
4218
4234
  isSingleMeasureEnding() {
4219
4235
  let { measure } = this;
4220
4236
  let next = measure.getNextMeasure();
4221
- return (next == null ? void 0 : next.hasNavigation(10 /* Ending */)) === true || measure.hasNavigation(9 /* EndRepeat */) || measure.isLastMeasure();
4237
+ return (next == null ? void 0 : next.hasNavigation("ending" /* Ending */)) === true || measure.hasNavigation("endRepeat" /* EndRepeat */) || measure.isLastMeasure();
4222
4238
  }
4223
4239
  hasPassage(pass) {
4224
4240
  return this.passages.some((p) => p === pass);
@@ -4417,7 +4433,7 @@ import { MusicError as MusicError13, MusicErrorType as MusicErrorType13 } from "
4417
4433
  import { Note as Note6 } from "@tspro/web-music-score/theory";
4418
4434
 
4419
4435
  // src/score/engine/obj-connective.ts
4420
- import { Utils as Utils7 } from "@tspro/ts-utils-lib";
4436
+ import { Utils as Utils8 } from "@tspro/ts-utils-lib";
4421
4437
  import { MusicError as MusicError11, MusicErrorType as MusicErrorType11 } from "@tspro/web-music-score/core";
4422
4438
  var ObjConnective = class extends MusicObject {
4423
4439
  constructor(connectiveProps, line, measure, leftNoteGroup, leftNoteId, ...args) {
@@ -4446,7 +4462,7 @@ var ObjConnective = class extends MusicObject {
4446
4462
  this.rightNoteGroup = args[0];
4447
4463
  this.rightNoteId = args[1];
4448
4464
  this.tieType = void 0;
4449
- } else if (Utils7.Is.isEnumValue(args[0], TieType)) {
4465
+ } else if (Utils8.Is.isEnumValue(args[0], TieType)) {
4450
4466
  this.rightNoteGroup = void 0;
4451
4467
  this.rightNoteId = void 0;
4452
4468
  this.tieType = args[0];
@@ -4477,7 +4493,7 @@ var ObjConnective = class extends MusicObject {
4477
4493
  if (rightNoteGroup !== void 0 && rightNoteId !== void 0) {
4478
4494
  rightPos = rightNoteGroup.getConnectiveAnchorPoint(connectiveProps, line, rightNoteId, noteAnchor, "right");
4479
4495
  } else {
4480
- rightPos = this.tieType === -2 /* ToMeasureEnd */ ? { x: measure.getColumnsContentRect().right, y: leftPos.y } : { x: leftPos.x + unitSize * DocumentSettings.StubTieLength, y: leftPos.y };
4496
+ rightPos = this.tieType === "toMeasureEnd" /* ToMeasureEnd */ ? { x: measure.getColumnsContentRect().right, y: leftPos.y } : { x: leftPos.x + unitSize * DocumentSettings.StubTieLength, y: leftPos.y };
4481
4497
  }
4482
4498
  let lx, ly, rx, ry;
4483
4499
  if (rightNoteGroup === void 0) {
@@ -4515,8 +4531,8 @@ var ObjConnective = class extends MusicObject {
4515
4531
  this.ly = ly;
4516
4532
  this.rx = rx;
4517
4533
  this.ry = ry;
4518
- this.arcHeight = this.connectiveProps.connective === 2 /* Slide */ ? 0 : arcHeight;
4519
- let { nx, ny } = Utils7.Math.calcNormal(lx, ly, rx, ry);
4534
+ this.arcHeight = this.connectiveProps.connective === "slide" /* Slide */ ? 0 : arcHeight;
4535
+ let { nx, ny } = Utils8.Math.calcNormal(lx, ly, rx, ry);
4520
4536
  this.cp1x = lx * 0.7 + rx * 0.3 + nx * this.arcHeight;
4521
4537
  this.cp1y = ly * 0.7 + ry * 0.3 + ny * this.arcHeight;
4522
4538
  this.cp2x = lx * 0.3 + rx * 0.7 + nx * this.arcHeight;
@@ -4577,6 +4593,7 @@ var ObjConnective = class extends MusicObject {
4577
4593
 
4578
4594
  // src/score/engine/connective-props.ts
4579
4595
  import { MusicError as MusicError12, MusicErrorType as MusicErrorType12 } from "@tspro/web-music-score/core";
4596
+ import { Utils as Utils9 } from "@tspro/ts-utils-lib";
4580
4597
  var ConnectiveProps = class {
4581
4598
  constructor(connective, span, noteAnchor, startNoteGroup) {
4582
4599
  this.connective = connective;
@@ -4598,7 +4615,7 @@ var ConnectiveProps = class {
4598
4615
  * @returns true if noteGroup was added, false if not.
4599
4616
  */
4600
4617
  addNoteGroup(noteGroup) {
4601
- if (this.span === -1 /* Stub */ || this.span === -2 /* ToMeasureEnd */) {
4618
+ if (this.span === "stub" /* Stub */ || this.span === "toMeasureEnd" /* ToMeasureEnd */) {
4602
4619
  return false;
4603
4620
  } else if (this.span > this.noteGroups.length) {
4604
4621
  this.noteGroups.push(noteGroup);
@@ -4608,29 +4625,29 @@ var ConnectiveProps = class {
4608
4625
  }
4609
4626
  }
4610
4627
  computeParams() {
4611
- let stemDir = this.noteGroups[0].stemDir;
4612
- let hasStem = this.noteGroups[0].rhythmProps.hasStem;
4613
- if (this.noteAnchor === 4 /* StemTip */) {
4614
- this.arcDir = stemDir === 1 /* Up */ ? "up" : "down";
4615
- } else if (this.noteAnchor === 0 /* Auto */) {
4616
- this.arcDir = stemDir === 1 /* Up */ || !hasStem ? "down" : "up";
4628
+ let { stemDir } = this.noteGroups[0];
4629
+ let { hasStem } = this.noteGroups[0].rhythmProps;
4630
+ if (this.noteAnchor === "stemTip" /* StemTip */) {
4631
+ this.arcDir = stemDir === "up" /* Up */ ? "up" : "down";
4632
+ } else if (this.noteAnchor === "auto" /* Auto */) {
4633
+ this.arcDir = stemDir === "up" /* Up */ || !hasStem ? "down" : "up";
4617
4634
  if (this.noteGroups[0].notes.length > 1) {
4618
- this.noteAnchor = 2 /* Center */;
4619
- } else if (this.connective === 2 /* Slide */) {
4620
- this.noteAnchor = 2 /* Center */;
4635
+ this.noteAnchor = "center" /* Center */;
4636
+ } else if (this.connective === "slide" /* Slide */) {
4637
+ this.noteAnchor = "center" /* Center */;
4621
4638
  } else if (this.arcDir === "up") {
4622
- this.noteAnchor = 1 /* Above */;
4639
+ this.noteAnchor = "above" /* Above */;
4623
4640
  } else {
4624
- this.noteAnchor = 3 /* Below */;
4641
+ this.noteAnchor = "below" /* Below */;
4625
4642
  }
4626
- } else if (this.noteAnchor === 2 /* Center */) {
4643
+ } else if (this.noteAnchor === "center" /* Center */) {
4627
4644
  let { row } = this.noteGroups[0].measure;
4628
4645
  let diatonicId = this.noteGroups[0].ownDiatonicId;
4629
4646
  let staff = row.getStaff(diatonicId);
4630
4647
  this.arcDir = !staff || diatonicId < staff.middleLineDiatonicId ? "down" : "up";
4631
- } else if (this.noteAnchor === 1 /* Above */) {
4648
+ } else if (this.noteAnchor === "above" /* Above */) {
4632
4649
  this.arcDir = "up";
4633
- } else if (this.noteAnchor === 3 /* Below */) {
4650
+ } else if (this.noteAnchor === "below" /* Below */) {
4634
4651
  this.arcDir = "down";
4635
4652
  }
4636
4653
  }
@@ -4645,8 +4662,8 @@ var ConnectiveProps = class {
4645
4662
  this.getStartNoteGroup().collectConnectiveProps();
4646
4663
  this.computeParams();
4647
4664
  let { connective, span } = this;
4648
- if (connective === 0 /* Tie */) {
4649
- if (span === -1 /* Stub */ || span === -2 /* ToMeasureEnd */) {
4665
+ if (connective === "tie" /* Tie */) {
4666
+ if (Utils9.Is.isEnumValue(span, TieType)) {
4650
4667
  let leftNoteGroup = this.noteGroups[0];
4651
4668
  for (let noteId = 0; noteId < leftNoteGroup.notes.length; noteId++) {
4652
4669
  this.createObjConnectiveWithTieType(leftNoteGroup, noteId, span);
@@ -4663,13 +4680,13 @@ var ConnectiveProps = class {
4663
4680
  });
4664
4681
  }
4665
4682
  }
4666
- } else if (connective === 1 /* Slur */) {
4683
+ } else if (connective === "slur" /* Slur */) {
4667
4684
  if (typeof span === "number" && span >= 2 && this.noteGroups.length === span) {
4668
4685
  let leftNoteGroup = this.noteGroups[0];
4669
4686
  let rightNoteGroup = this.noteGroups[this.noteGroups.length - 1];
4670
4687
  this.createObjConnective(leftNoteGroup, 0, rightNoteGroup, 0);
4671
4688
  }
4672
- } else if (connective === 2 /* Slide */) {
4689
+ } else if (connective === "slide" /* Slide */) {
4673
4690
  if (this.noteGroups.length >= 2) {
4674
4691
  for (let i = 0; i < this.noteGroups.length - 1; i++) {
4675
4692
  let leftNoteGroup = this.noteGroups[i];
@@ -4699,7 +4716,7 @@ var ConnectiveProps = class {
4699
4716
  } else {
4700
4717
  let leftString = leftNoteGroup2.getFretNumberString(leftNoteId2);
4701
4718
  let rightString = rightNoteGroup2.getFretNumberString(rightNoteId2);
4702
- if (leftString !== void 0 && rightString !== void 0 && (leftString === rightString || this.connective === 1 /* Slur */)) {
4719
+ if (leftString !== void 0 && rightString !== void 0 && (leftString === rightString || this.connective === "slur" /* Slur */)) {
4703
4720
  new ObjConnective(this, line, measure, leftNoteGroup2, leftNoteId2, rightNoteGroup2, rightNoteId2);
4704
4721
  }
4705
4722
  }
@@ -4724,6 +4741,32 @@ function validateVoiceId(voiceId) {
4724
4741
  return voiceId;
4725
4742
  }
4726
4743
  }
4744
+ function getExtensionTicks(extensionLength) {
4745
+ if (typeof extensionLength === "string") {
4746
+ extensionLength = [extensionLength];
4747
+ }
4748
+ if (Utils10.Is.isArray(extensionLength)) {
4749
+ let totalTicks = 0;
4750
+ for (let i = 0; i < extensionLength.length; ) {
4751
+ let str = extensionLength[i];
4752
+ let num = extensionLength[i + 1];
4753
+ if (typeof str === "string") {
4754
+ i++;
4755
+ let ticks = RhythmProps4.get(str).ticks;
4756
+ if (typeof num === "number") {
4757
+ i++;
4758
+ ticks *= num;
4759
+ }
4760
+ totalTicks += ticks;
4761
+ } else {
4762
+ i++;
4763
+ }
4764
+ }
4765
+ return totalTicks;
4766
+ } else {
4767
+ return extensionLength;
4768
+ }
4769
+ }
4727
4770
  var _ObjMeasure = class _ObjMeasure extends MusicObject {
4728
4771
  constructor(row) {
4729
4772
  super(row);
@@ -4827,15 +4870,15 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
4827
4870
  if (setStemDir !== void 0) {
4828
4871
  this.useStemDir[voiceId] = setStemDir;
4829
4872
  } else if (this.useStemDir[voiceId] === void 0) {
4830
- this.useStemDir[voiceId] = (_b = (_a = this.getPrevMeasure()) == null ? void 0 : _a.useStemDir[voiceId]) != null ? _b : 0 /* Auto */;
4873
+ this.useStemDir[voiceId] = (_b = (_a = this.getPrevMeasure()) == null ? void 0 : _a.useStemDir[voiceId]) != null ? _b : "auto" /* Auto */;
4831
4874
  }
4832
4875
  let stemDir = this.useStemDir[voiceId];
4833
- if (stemDir === 0 /* Auto */ || stemDir === void 0) {
4876
+ if (stemDir === "auto" /* Auto */ || stemDir === void 0) {
4834
4877
  let staff = this.row.getStaff(symbol.ownDiatonicId);
4835
4878
  if (staff) {
4836
- return symbol.ownDiatonicId > staff.middleLineDiatonicId ? 2 /* Down */ : 1 /* Up */;
4879
+ return symbol.ownDiatonicId > staff.middleLineDiatonicId ? "down" /* Down */ : "up" /* Up */;
4837
4880
  } else {
4838
- return 1 /* Up */;
4881
+ return "up" /* Up */;
4839
4882
  }
4840
4883
  } else {
4841
4884
  return stemDir;
@@ -4942,6 +4985,7 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
4942
4985
  // See MMeasure interface
4943
4986
  //setKeySignature(tonic: string, scaleType: ScaleType): void;
4944
4987
  //setKeySignature(keySignature: KeySignature): void;
4988
+ //setKeySignature(keySignature: string): void;
4945
4989
  //setKeySignature(scale: Scale): void;
4946
4990
  setKeySignature(...args) {
4947
4991
  var _a;
@@ -4950,13 +4994,17 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
4950
4994
  this.alterKeySignature = args[0];
4951
4995
  } else if (args[0] instanceof Scale) {
4952
4996
  this.alterKeySignature = args[0];
4953
- } else {
4954
- try {
4955
- let tonic = "" + args[0];
4956
- let scaleType = validateScaleType("" + args[1]);
4957
- this.alterKeySignature = getScale(tonic, scaleType);
4958
- } catch (e) {
4959
- throw new MusicError13(MusicErrorType13.Score, "Cannot set key signature because invalid args: " + args);
4997
+ } else if (Utils10.Is.isNonEmptyString(args[0])) {
4998
+ if (args.length === 1) {
4999
+ this.alterKeySignature = getScale(args[0]);
5000
+ } else if (args.length === 2) {
5001
+ try {
5002
+ let tonic = "" + args[0];
5003
+ let scaleType = validateScaleType("" + args[1]);
5004
+ this.alterKeySignature = getScale(tonic, scaleType);
5005
+ } catch (e) {
5006
+ throw new MusicError13(MusicErrorType13.Score, "Cannot set key signature because invalid args: " + args);
5007
+ }
4960
5008
  }
4961
5009
  }
4962
5010
  this.updateKeySignature();
@@ -4996,8 +5044,16 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
4996
5044
  setTempo(beatsPerMinute, beatLength, dotted) {
4997
5045
  var _a;
4998
5046
  (_a = this.getPrevMeasure()) == null ? void 0 : _a.endSection();
4999
- let options = beatLength !== void 0 ? { beatLength, dotted } : void 0;
5000
- this.alterTempo = { beatsPerMinute, options };
5047
+ if (beatLength === void 0) {
5048
+ this.alterTempo = { beatsPerMinute };
5049
+ } else {
5050
+ let dotCount = typeof dotted === "number" && dotted > 0 ? dotted : dotted === true ? 1 : NoteLengthProps4.get(beatLength).dotCount;
5051
+ let options = {
5052
+ beatLength: validateNoteLength(beatLength),
5053
+ dotCount: dotCount > 0 ? dotCount : void 0
5054
+ };
5055
+ this.alterTempo = { beatsPerMinute, options };
5056
+ }
5001
5057
  this.updateTempo();
5002
5058
  }
5003
5059
  updateTempo() {
@@ -5006,18 +5062,18 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5006
5062
  if (this.alterTempo) {
5007
5063
  let beatsPerMinute = this.alterTempo.beatsPerMinute;
5008
5064
  let beatLength;
5009
- let dotted;
5065
+ let dotCount;
5010
5066
  if (this.alterTempo.options) {
5011
5067
  beatLength = this.alterTempo.options.beatLength;
5012
- dotted = (_a = this.alterTempo.options.dotted) != null ? _a : false;
5068
+ dotCount = (_a = this.alterTempo.options.dotCount) != null ? _a : 0;
5013
5069
  } else if (this.alterTimeSignature) {
5014
5070
  beatLength = this.alterTimeSignature.beatLength;
5015
- dotted = false;
5071
+ dotCount = 0;
5016
5072
  } else {
5017
5073
  beatLength = this.tempo.options.beatLength;
5018
- dotted = this.tempo.options.dotted;
5074
+ dotCount = this.tempo.options.dotCount;
5019
5075
  }
5020
- this.tempo = { beatsPerMinute, options: { beatLength, dotted } };
5076
+ this.tempo = { beatsPerMinute, options: { beatLength, dotCount } };
5021
5077
  }
5022
5078
  if (this.nextMeasure) {
5023
5079
  this.nextMeasure.updateTempo();
@@ -5049,19 +5105,19 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5049
5105
  let grp = this.doc.getStaffGroup(staffTabOrGroup);
5050
5106
  if (grp && !prevGroups.includes(staffTabOrGroup)) {
5051
5107
  let curGroups = [...prevGroups, staffTabOrGroup];
5052
- (Utils8.Is.isArray(grp.staffsTabsAndGroups) ? grp.staffsTabsAndGroups : [grp.staffsTabsAndGroups]).forEach((staffTabOrGroup2) => {
5108
+ (Utils10.Is.isArray(grp.staffsTabsAndGroups) ? grp.staffsTabsAndGroups : [grp.staffsTabsAndGroups]).forEach((staffTabOrGroup2) => {
5053
5109
  switch (grp.verticalPosition) {
5054
- case 0 /* Above */:
5110
+ case "above" /* Above */:
5055
5111
  addToStaffTabOrGroup(staffTabOrGroup2, 0 /* Above */, curGroups);
5056
5112
  break;
5057
- case 1 /* Below */:
5113
+ case "below" /* Below */:
5058
5114
  addToStaffTabOrGroup(staffTabOrGroup2, 1 /* Below */, curGroups);
5059
5115
  break;
5060
- case 2 /* Both */:
5116
+ case "both" /* Both */:
5061
5117
  addToStaffTabOrGroup(staffTabOrGroup2, 0 /* Above */, curGroups);
5062
5118
  addToStaffTabOrGroup(staffTabOrGroup2, 1 /* Below */, curGroups);
5063
5119
  break;
5064
- case 3 /* Auto */:
5120
+ case "auto" /* Auto */:
5065
5121
  addToStaffTabOrGroup(staffTabOrGroup2, defaultVerticalPos, curGroups);
5066
5122
  break;
5067
5123
  }
@@ -5076,14 +5132,14 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5076
5132
  } else {
5077
5133
  addToStaffTabOrGroup(0, defaultVerticalPos);
5078
5134
  }
5079
- } else if (Utils8.Is.isArray(staffTabOrGroups)) {
5135
+ } else if (Utils10.Is.isArray(staffTabOrGroups)) {
5080
5136
  staffTabOrGroups.forEach((staffTabOrGroup) => addToStaffTabOrGroup(staffTabOrGroup, defaultVerticalPos));
5081
5137
  } else {
5082
5138
  addToStaffTabOrGroup(staffTabOrGroups, defaultVerticalPos);
5083
5139
  }
5084
5140
  }
5085
5141
  addFermata(staffTabOrGroups, fermata) {
5086
- let anchor = fermata === 1 /* AtMeasureEnd */ ? this.barLineRight : this.lastAddedRhythmColumn;
5142
+ let anchor = fermata === "atMeasureEnd" /* AtMeasureEnd */ ? this.barLineRight : this.lastAddedRhythmColumn;
5087
5143
  if (!anchor) {
5088
5144
  throw new MusicError13(MusicErrorType13.Score, "Cannot add Fermata because anchor is undefined.");
5089
5145
  }
@@ -5099,7 +5155,7 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5099
5155
  addNavigation(staffTabOrGroups, navigation, ...args) {
5100
5156
  let addLayoutObjectProps = void 0;
5101
5157
  switch (navigation) {
5102
- case 10 /* Ending */:
5158
+ case "ending" /* Ending */:
5103
5159
  if (this.navigationSet.has(navigation)) {
5104
5160
  throw new MusicError13(MusicErrorType13.Score, "Cannot add ending beasure measure already has one.");
5105
5161
  }
@@ -5111,10 +5167,10 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5111
5167
  defaultVerticalPos: 0 /* Above */
5112
5168
  };
5113
5169
  break;
5114
- case 1 /* DC_al_Coda */:
5115
- case 0 /* DC_al_Fine */:
5116
- case 3 /* DS_al_Coda */:
5117
- case 2 /* DS_al_Fine */: {
5170
+ case "D.C. al Coda" /* DC_al_Coda */:
5171
+ case "D.C. al Fine" /* DC_al_Fine */:
5172
+ case "D.S. al Coda" /* DS_al_Coda */:
5173
+ case "D.S. al Fine" /* DS_al_Fine */: {
5118
5174
  let anchor2 = this.barLineRight;
5119
5175
  let text = getNavigationString(navigation);
5120
5176
  addLayoutObjectProps = {
@@ -5122,11 +5178,11 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5122
5178
  layoutGroupId: 2 /* Navigation */,
5123
5179
  defaultVerticalPos: 0 /* Above */
5124
5180
  };
5125
- this.addNavigation(staffTabOrGroups, 9 /* EndRepeat */);
5181
+ this.addNavigation(staffTabOrGroups, "endRepeat" /* EndRepeat */);
5126
5182
  this.endSong();
5127
5183
  break;
5128
5184
  }
5129
- case 7 /* Fine */: {
5185
+ case "Fine" /* Fine */: {
5130
5186
  let anchor2 = this.barLineRight;
5131
5187
  let text = getNavigationString(navigation);
5132
5188
  addLayoutObjectProps = {
@@ -5136,8 +5192,8 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5136
5192
  };
5137
5193
  break;
5138
5194
  }
5139
- case 6 /* Segno */:
5140
- case 4 /* Coda */: {
5195
+ case "Segno" /* Segno */:
5196
+ case "Coda" /* Coda */: {
5141
5197
  let anchor2 = this.barLineLeft;
5142
5198
  let text = getNavigationString(navigation);
5143
5199
  addLayoutObjectProps = {
@@ -5147,7 +5203,7 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5147
5203
  };
5148
5204
  break;
5149
5205
  }
5150
- case 5 /* toCoda */: {
5206
+ case "toCoda" /* toCoda */: {
5151
5207
  let anchor2 = this.barLineRight;
5152
5208
  let text = getNavigationString(navigation);
5153
5209
  addLayoutObjectProps = {
@@ -5157,10 +5213,10 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5157
5213
  };
5158
5214
  break;
5159
5215
  }
5160
- case 9 /* EndRepeat */:
5216
+ case "endRepeat" /* EndRepeat */:
5161
5217
  if (args.length === 0) {
5162
5218
  this.endRepeatPlayCount = 2;
5163
- } else if (Utils8.Is.isIntegerGte(args[0], 2)) {
5219
+ } else if (Utils10.Is.isIntegerGte(args[0], 2)) {
5164
5220
  this.endRepeatPlayCount = args[0];
5165
5221
  } else {
5166
5222
  throw new MusicError13(MusicErrorType13.Score, "Invalid end repeat play count (should be 2 or greater integer): " + args[0]);
@@ -5196,17 +5252,18 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5196
5252
  let layoutGroupId;
5197
5253
  let defaultVerticalPos;
5198
5254
  switch (annotation) {
5199
- case 0 /* Dynamics */:
5255
+ case "dynamics" /* Dynamics */:
5200
5256
  layoutGroupId = 5 /* DynamicsAnnotation */;
5201
5257
  defaultVerticalPos = 0 /* Above */;
5202
5258
  textProps.italic = true;
5203
5259
  break;
5204
- case 1 /* Tempo */:
5260
+ case "tempo" /* Tempo */:
5205
5261
  layoutGroupId = 4 /* TempoAnnotation */;
5206
5262
  defaultVerticalPos = 0 /* Above */;
5207
5263
  textProps.italic = true;
5208
5264
  break;
5209
5265
  }
5266
+ this.disableExtension();
5210
5267
  this.forEachStaffGroup(staffTabOrGroups, defaultVerticalPos, (line, vpos) => {
5211
5268
  let textObj = new ObjText(anchor, textProps, 0.5, 1);
5212
5269
  this.addLayoutObject(textObj, line, layoutGroupId, vpos);
@@ -5224,15 +5281,16 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5224
5281
  let layoutGroupId;
5225
5282
  let defaultVerticalPos;
5226
5283
  switch (label) {
5227
- case 0 /* Note */:
5284
+ case "note" /* Note */:
5228
5285
  layoutGroupId = 1 /* NoteLabel */;
5229
5286
  defaultVerticalPos = 1 /* Below */;
5230
5287
  break;
5231
- case 1 /* Chord */:
5288
+ case "chord" /* Chord */:
5232
5289
  layoutGroupId = 6 /* ChordLabel */;
5233
5290
  defaultVerticalPos = 0 /* Above */;
5234
5291
  break;
5235
5292
  }
5293
+ this.disableExtension();
5236
5294
  this.forEachStaffGroup(staffTabOrGroups, defaultVerticalPos, (line, vpos) => {
5237
5295
  let textObj = new ObjText(anchor, textProps, 0.5, 1);
5238
5296
  this.addLayoutObject(textObj, line, layoutGroupId, vpos);
@@ -5244,17 +5302,17 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5244
5302
  if (!(anchor instanceof ObjNoteGroup)) {
5245
5303
  throw new MusicError13(MusicErrorType13.Score, "Connective can be added to note group only.");
5246
5304
  }
5247
- if (connective === 0 /* Tie */) {
5248
- let tieSpan = Utils8.Is.isInteger(args[0]) || Utils8.Is.isEnumValue(args[0], TieType) ? args[0] : 2;
5249
- let noteAnchor = Utils8.Is.isEnumValue(args[1], NoteAnchor) ? args[1] : 0 /* Auto */;
5250
- anchor.startConnective(new ConnectiveProps(0 /* Tie */, tieSpan, noteAnchor, anchor));
5251
- } else if (connective === 1 /* Slur */) {
5252
- let slurSpan = Utils8.Is.isInteger(args[0]) ? args[0] : 2;
5253
- let noteAnchor = Utils8.Is.isEnumValue(args[1], NoteAnchor) ? args[1] : 0 /* Auto */;
5254
- anchor.startConnective(new ConnectiveProps(1 /* Slur */, slurSpan, noteAnchor, anchor));
5255
- } else if (connective === 2 /* Slide */) {
5256
- let noteAnchor = Utils8.Is.isEnumValue(args[0], NoteAnchor) ? args[0] : 0 /* Auto */;
5257
- anchor.startConnective(new ConnectiveProps(2 /* Slide */, 2, noteAnchor, anchor));
5305
+ if (connective === "tie" /* Tie */) {
5306
+ let tieSpan = Utils10.Is.isInteger(args[0]) || Utils10.Is.isEnumValue(args[0], TieType) ? args[0] : 2;
5307
+ let noteAnchor = Utils10.Is.isEnumValue(args[1], NoteAnchor) ? args[1] : "auto" /* Auto */;
5308
+ anchor.startConnective(new ConnectiveProps("tie" /* Tie */, tieSpan, noteAnchor, anchor));
5309
+ } else if (connective === "slur" /* Slur */) {
5310
+ let slurSpan = Utils10.Is.isInteger(args[0]) ? args[0] : 2;
5311
+ let noteAnchor = Utils10.Is.isEnumValue(args[1], NoteAnchor) ? args[1] : "auto" /* Auto */;
5312
+ anchor.startConnective(new ConnectiveProps("slur" /* Slur */, slurSpan, noteAnchor, anchor));
5313
+ } else if (connective === "slide" /* Slide */) {
5314
+ let noteAnchor = Utils10.Is.isEnumValue(args[0], NoteAnchor) ? args[0] : "auto" /* Auto */;
5315
+ anchor.startConnective(new ConnectiveProps("slide" /* Slide */, 2, noteAnchor, anchor));
5258
5316
  }
5259
5317
  }
5260
5318
  addExtension(extensionLength, extensionVisible) {
@@ -5263,7 +5321,7 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5263
5321
  if (musicObj instanceof ObjText && anchor instanceof ObjRhythmColumn) {
5264
5322
  let lineStyle = "dashed";
5265
5323
  let linePos = "bottom";
5266
- let extension = new Extension(musicObj, anchor, extensionLength, extensionVisible, lineStyle, linePos);
5324
+ let extension = new Extension(musicObj, anchor, getExtensionTicks(extensionLength), extensionVisible, lineStyle, linePos);
5267
5325
  musicObj.setLink(extension);
5268
5326
  } else {
5269
5327
  throw new MusicError13(MusicErrorType13.Score, "Cannot add extension becaue no compatible music object to attach it to.");
@@ -5312,21 +5370,25 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5312
5370
  col.setVoiceSymbol(voiceId, symbol);
5313
5371
  this.getVoiceSymbols(voiceId);
5314
5372
  this.voiceSymbols[voiceId].push(symbol);
5315
- if (symbol.triplet) {
5373
+ if (symbol.oldStyleTriplet) {
5316
5374
  this.createOldStyleTriplets(voiceId);
5317
5375
  }
5318
5376
  this.requestBeamsUpdate();
5319
5377
  this.lastAddedRhythmColumn = col;
5320
5378
  this.lastAddedRhythmSymbol = symbol;
5321
5379
  }
5322
- addNoteGroup(voiceId, notes, noteLength, options) {
5323
- let notes2 = notes.map((note) => typeof note === "string" ? Note7.getNote(note) : note);
5380
+ addNoteGroup(voiceId, notes, noteLength, options, tupletRatio) {
5381
+ let realNotes = notes.map((note) => typeof note === "string" ? Note7.getNote(note) : note);
5324
5382
  let col = this.getRhythmColumn(voiceId);
5325
- this.addRhythmSymbol(voiceId, new ObjNoteGroup(col, voiceId, notes2, noteLength, options));
5383
+ let noteGroup = new ObjNoteGroup(col, voiceId, realNotes, noteLength, options, tupletRatio);
5384
+ this.addRhythmSymbol(voiceId, noteGroup);
5385
+ return noteGroup;
5326
5386
  }
5327
- addRest(voiceId, restLength, options) {
5387
+ addRest(voiceId, restLength, options, tupletRatio) {
5328
5388
  let col = this.getRhythmColumn(voiceId);
5329
- this.addRhythmSymbol(voiceId, new ObjRest(col, voiceId, restLength, options));
5389
+ let rest = new ObjRest(col, voiceId, restLength, options, tupletRatio);
5390
+ this.addRhythmSymbol(voiceId, rest);
5391
+ return rest;
5330
5392
  }
5331
5393
  /**
5332
5394
  *
@@ -5468,18 +5530,13 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5468
5530
  requestBeamsUpdate() {
5469
5531
  this.needBeamsUpdate = true;
5470
5532
  }
5533
+ // Create triplets by triplet property of NoteOptions/RestOptions.
5471
5534
  createOldStyleTriplets(voiceId) {
5472
5535
  let symbols = this.getVoiceSymbols(voiceId);
5473
- if (symbols.length <= 2) {
5474
- return;
5475
- }
5476
5536
  for (let i = 0; i < symbols.length; ) {
5477
- let s2 = symbols.slice(i, i + 2);
5478
- let s3 = symbols.slice(i, i + 3);
5479
- if (s2.length === 2 && s2.every((s) => s.triplet) && s2.every((s) => s.getBeamGroup() === void 0) && ObjBeamGroup.createTriplet(s2)) {
5480
- i += 2;
5481
- } else if (s3.length === 3 && s3.every((s) => s.triplet) && s3.every((s) => s.getBeamGroup() === void 0) && ObjBeamGroup.createTriplet(s3)) {
5482
- i += 3;
5537
+ if (symbols[i].oldStyleTriplet) {
5538
+ let n = ObjBeamGroup.createOldStyleTriplet(symbols.slice(i, i + 3));
5539
+ i += n === 0 ? 1 : n;
5483
5540
  } else {
5484
5541
  i++;
5485
5542
  }
@@ -5491,11 +5548,11 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5491
5548
  return;
5492
5549
  }
5493
5550
  this.beamGroups = this.beamGroups.filter((beamGroup) => {
5494
- if (beamGroup.getType() === 0 /* RegularBeam */) {
5551
+ if (beamGroup.isTuplet()) {
5552
+ return true;
5553
+ } else {
5495
5554
  beamGroup.detach();
5496
5555
  return false;
5497
- } else {
5498
- return true;
5499
5556
  }
5500
5557
  });
5501
5558
  getVoiceIds().forEach((voiceId) => {
@@ -5531,7 +5588,7 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5531
5588
  static setupBeamGroup(groupSymbols) {
5532
5589
  let groupNotes = groupSymbols.map((s) => {
5533
5590
  var _a;
5534
- return s instanceof ObjNoteGroup && ((_a = s.getBeamGroup()) == null ? void 0 : _a.isTriplet()) !== true ? s : void 0;
5591
+ return s instanceof ObjNoteGroup && ((_a = s.getBeamGroup()) == null ? void 0 : _a.isTuplet()) !== true ? s : void 0;
5535
5592
  });
5536
5593
  ObjNoteGroup.setBeamCounts(groupNotes);
5537
5594
  let beamNotes = [];
@@ -5563,36 +5620,32 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5563
5620
  if (this.getConsumedTicks() === 0) {
5564
5621
  this.completeRests(0);
5565
5622
  } else {
5566
- getVoiceIds().forEach((voiceId2) => {
5567
- if (this.getConsumedTicks(voiceId2) > 0) {
5568
- this.completeRests(voiceId2);
5569
- }
5570
- });
5623
+ this.completeRests(getVoiceIds().filter((id) => this.getConsumedTicks(id) > 0));
5571
5624
  }
5572
5625
  return;
5573
- }
5574
- let measureTicks = this.getMeasureTicks();
5575
- let consumedTicks = this.getConsumedTicks(voiceId);
5576
- let remainingTicks = measureTicks - consumedTicks;
5577
- let rests = [];
5578
- let noteLengthValues = Utils8.Enum.getEnumValues(NoteLength6);
5579
- while (remainingTicks > 0) {
5580
- noteLengthValues.forEach((restLength) => {
5581
- let restValue = new RhythmProps4(restLength, false);
5582
- if (restValue.canDot()) {
5583
- let dottedRestValue = new RhythmProps4(restLength, true);
5584
- while (dottedRestValue.ticks <= remainingTicks) {
5585
- rests.push(dottedRestValue);
5586
- remainingTicks -= dottedRestValue.ticks;
5626
+ } else if (Utils10.Is.isArray(voiceId)) {
5627
+ voiceId.forEach((id) => this.completeRests(id));
5628
+ return;
5629
+ } else {
5630
+ validateVoiceId(voiceId);
5631
+ let measureTicks = this.getMeasureTicks();
5632
+ let consumedTicks = this.getConsumedTicks(voiceId);
5633
+ let remainingTicks = measureTicks - consumedTicks;
5634
+ let rests = [];
5635
+ while (remainingTicks > 0) {
5636
+ for (let noteSize = NoteLengthProps4.LongestNoteSize; noteSize <= NoteLengthProps4.ShortestNoteSize; noteSize *= 2) {
5637
+ let restLength = NoteLengthProps4.create(noteSize).noteLength;
5638
+ for (let dotCount = NoteLengthProps4.get(restLength).maxDotCount; dotCount >= 0; dotCount--) {
5639
+ let restProps = RhythmProps4.get(restLength, dotCount);
5640
+ while (restProps.ticks <= remainingTicks) {
5641
+ rests.push(restProps);
5642
+ remainingTicks -= restProps.ticks;
5643
+ }
5587
5644
  }
5588
5645
  }
5589
- while (restValue.ticks <= remainingTicks) {
5590
- rests.push(restValue);
5591
- remainingTicks -= restValue.ticks;
5592
- }
5593
- });
5646
+ }
5647
+ rests.reverse().forEach((rest) => this.addRest(voiceId, rest.noteLength, { dotted: rest.dotCount }));
5594
5648
  }
5595
- rests.reverse().forEach((rest) => this.addRest(voiceId, rest.noteLength, { dotted: rest.dotted }));
5596
5649
  }
5597
5650
  requestLayout() {
5598
5651
  if (!this.needLayout) {
@@ -5685,7 +5738,7 @@ var _ObjMeasure = class _ObjMeasure extends MusicObject {
5685
5738
  let columnsAreaLeft = this.rect.left + this.leftSolidAreaWidth;
5686
5739
  let columnsAreaRight = this.rect.right - this.rightSolidAreaWidth;
5687
5740
  let columnsAreaWidth = columnsAreaRight - columnsAreaLeft;
5688
- let columnsWidth = Utils8.Math.sum(this.columns.map((col) => col.getRect().width));
5741
+ let columnsWidth = Utils10.Math.sum(this.columns.map((col) => col.getRect().width));
5689
5742
  let columnScale = columnsAreaWidth / columnsWidth;
5690
5743
  let columnLeft = columnsAreaLeft;
5691
5744
  this.columns.forEach((col) => {
@@ -6025,10 +6078,12 @@ var ObjStaff = class extends ObjNotationLine4 {
6025
6078
  this.clefImageAsset = 0 /* TrebleClefPng */;
6026
6079
  this.clefLineDiatonicId = getDiatonicId("G4", staffConfig.isOctaveDown === true);
6027
6080
  this.middleLineDiatonicId = this.clefLineDiatonicId + 2;
6028
- } else {
6081
+ } else if (staffConfig.clef === "F" /* F */) {
6029
6082
  this.clefImageAsset = 1 /* BassClefPng */;
6030
6083
  this.clefLineDiatonicId = getDiatonicId("F3", staffConfig.isOctaveDown === true);
6031
6084
  this.middleLineDiatonicId = this.clefLineDiatonicId - 2;
6085
+ } else {
6086
+ throw new MusicError15(MusicErrorType15.Score, `Invalid staffConfig.clef ${staffConfig.clef}.`);
6032
6087
  }
6033
6088
  this.topLineDiatonicId = this.middleLineDiatonicId + 4;
6034
6089
  this.bottomLineDiatonicId = this.middleLineDiatonicId - 4;
@@ -6164,7 +6219,7 @@ var ObjTab = class extends ObjNotationLine4 {
6164
6219
  __publicField(this, "tuningName");
6165
6220
  __publicField(this, "tuningStrings");
6166
6221
  __publicField(this, "mi");
6167
- if (Utils9.Is.isArray(tabConfig.tuning)) {
6222
+ if (Utils11.Is.isArray(tabConfig.tuning)) {
6168
6223
  this.tuningName = void 0;
6169
6224
  this.tuningStrings = tabConfig.tuning.map((noteName) => Note8.getNote(noteName)).reverse();
6170
6225
  } else if (typeof tabConfig.tuning === "string") {
@@ -6619,7 +6674,7 @@ var ObjHeader = class extends MusicObject {
6619
6674
  };
6620
6675
 
6621
6676
  // src/score/engine/obj-document.ts
6622
- import { Utils as Utils10 } from "@tspro/ts-utils-lib";
6677
+ import { Utils as Utils12 } from "@tspro/ts-utils-lib";
6623
6678
  var ObjDocument = class extends MusicObject {
6624
6679
  constructor() {
6625
6680
  super(void 0);
@@ -6640,35 +6695,35 @@ var ObjDocument = class extends MusicObject {
6640
6695
  return this.mi;
6641
6696
  }
6642
6697
  setScoreConfiguration(config) {
6643
- if (Utils10.Is.isEnumValue(config, StaffPreset)) {
6698
+ if (Utils12.Is.isEnumValue(config, StaffPreset)) {
6644
6699
  switch (config) {
6645
6700
  default:
6646
- case 1 /* Treble */:
6701
+ case "treble" /* Treble */:
6647
6702
  this.curScoreConfig = [{ type: "staff", clef: "G" /* G */ }];
6648
6703
  break;
6649
- case 2 /* Bass */:
6704
+ case "bass" /* Bass */:
6650
6705
  this.curScoreConfig = [{ type: "staff", clef: "F" /* F */ }];
6651
6706
  break;
6652
- case 3 /* Grand */:
6707
+ case "grand" /* Grand */:
6653
6708
  this.curScoreConfig = [
6654
6709
  { type: "staff", clef: "G" /* G */, isGrand: true },
6655
6710
  { type: "staff", clef: "F" /* F */, isGrand: true }
6656
6711
  ];
6657
6712
  break;
6658
- case 4 /* GuitarTreble */:
6713
+ case "guitarTreble" /* GuitarTreble */:
6659
6714
  this.curScoreConfig = [{ type: "staff", clef: "G" /* G */, isOctaveDown: true }];
6660
6715
  break;
6661
- case 8 /* GuitarTab */:
6716
+ case "guitarTab" /* GuitarTab */:
6662
6717
  this.curScoreConfig = [{ type: "tab", tuning: "Standard" }];
6663
6718
  break;
6664
- case 12 /* GuitarCombined */:
6719
+ case "guitarCombined" /* GuitarCombined */:
6665
6720
  this.curScoreConfig = [
6666
6721
  { type: "staff", clef: "G" /* G */, isOctaveDown: true },
6667
6722
  { type: "tab", tuning: "Standard" }
6668
6723
  ];
6669
6724
  break;
6670
6725
  }
6671
- } else if (Utils10.Is.isArray(config)) {
6726
+ } else if (Utils12.Is.isArray(config)) {
6672
6727
  this.curScoreConfig = config;
6673
6728
  } else {
6674
6729
  this.curScoreConfig = [config];
@@ -6894,7 +6949,7 @@ var ObjDocument = class extends MusicObject {
6894
6949
  };
6895
6950
 
6896
6951
  // src/score/pub/document-builder.ts
6897
- import { KeySignature as KeySignature3, Note as Note10, NoteLength as NoteLength7, Scale as Scale2, ScaleType, SymbolSet as SymbolSet2, TimeSignature as TimeSignature2, TuningNameList } from "@tspro/web-music-score/theory";
6952
+ import { KeySignature as KeySignature3, Note as Note10, NoteLength as NoteLength7, RhythmProps as RhythmProps5, Scale as Scale2, ScaleType, SymbolSet as SymbolSet2, TimeSignature as TimeSignature2, TuningNameList, validateNoteLength as validateNoteLength2, validateTupletRatio } from "@tspro/web-music-score/theory";
6898
6953
  import { MusicError as MusicError17, MusicErrorType as MusicErrorType17 } from "@tspro/web-music-score/core";
6899
6954
  function assertArg(condition, argName, argValue) {
6900
6955
  if (!condition) {
@@ -6910,180 +6965,318 @@ function isNote(note) {
6910
6965
  }
6911
6966
  }
6912
6967
  function isVoiceId(value) {
6913
- return Utils11.Is.isNumber(value) && getVoiceIds().indexOf(value) >= 0;
6968
+ return Utils13.Is.isNumber(value) && getVoiceIds().indexOf(value) >= 0;
6914
6969
  }
6915
6970
  function isStringNumber(value) {
6916
- return Utils11.Is.isNumber(value) && getStringNumbers().indexOf(value) >= 0;
6971
+ return Utils13.Is.isNumber(value) && getStringNumbers().indexOf(value) >= 0;
6917
6972
  }
6918
6973
  function assertStaffConfig(staffConfig) {
6919
- assertArg(Utils11.Is.isObject(staffConfig), "staffConfig", staffConfig);
6974
+ assertArg(Utils13.Is.isObject(staffConfig), "staffConfig", staffConfig);
6920
6975
  assertArg(staffConfig.type === "staff", "staffConfig.type", staffConfig.type);
6921
- assertArg(Utils11.Is.isEnumValue(staffConfig.clef, Clef), "staffConfig.clef", staffConfig.clef);
6922
- assertArg(Utils11.Is.isBooleanOrUndefined(staffConfig.isOctaveDown), "staffConfig.isOctaveDown", staffConfig.isOctaveDown);
6923
- assertArg(Utils11.Is.isUndefined(staffConfig.minNote) || isNote(staffConfig.minNote), "staffConfig.minNote", staffConfig.minNote);
6924
- assertArg(Utils11.Is.isUndefined(staffConfig.maxNote) || isNote(staffConfig.maxNote), "staffConfig.maxNote", staffConfig.maxNote);
6925
- assertArg(Utils11.Is.isUndefined(staffConfig.voiceIds) || Utils11.Is.isArray(staffConfig.voiceIds) && staffConfig.voiceIds.every((voiceId) => Utils11.Is.isNumber(voiceId)), "staffConfig.voiceIds", staffConfig.voiceIds);
6926
- assertArg(Utils11.Is.isBooleanOrUndefined(staffConfig.isGrand), "staffConfig.isGrand", staffConfig.isGrand);
6976
+ assertArg(Utils13.Is.isEnumValue(staffConfig.clef, Clef), "staffConfig.clef", staffConfig.clef);
6977
+ assertArg(Utils13.Is.isBooleanOrUndefined(staffConfig.isOctaveDown), "staffConfig.isOctaveDown", staffConfig.isOctaveDown);
6978
+ assertArg(Utils13.Is.isUndefined(staffConfig.minNote) || isNote(staffConfig.minNote), "staffConfig.minNote", staffConfig.minNote);
6979
+ assertArg(Utils13.Is.isUndefined(staffConfig.maxNote) || isNote(staffConfig.maxNote), "staffConfig.maxNote", staffConfig.maxNote);
6980
+ assertArg(Utils13.Is.isUndefined(staffConfig.voiceIds) || Utils13.Is.isArray(staffConfig.voiceIds) && staffConfig.voiceIds.every((voiceId) => Utils13.Is.isNumber(voiceId)), "staffConfig.voiceIds", staffConfig.voiceIds);
6981
+ assertArg(Utils13.Is.isBooleanOrUndefined(staffConfig.isGrand), "staffConfig.isGrand", staffConfig.isGrand);
6927
6982
  }
6928
6983
  function assertTabConfig(tabConfig) {
6929
- assertArg(Utils11.Is.isObject(tabConfig), "tabConfig", tabConfig);
6984
+ assertArg(Utils13.Is.isObject(tabConfig), "tabConfig", tabConfig);
6930
6985
  assertArg(tabConfig.type === "tab", "tabConfig.type", tabConfig.type);
6931
6986
  if (typeof tabConfig.tuning === "string") {
6932
6987
  assertArg(TuningNameList.includes(tabConfig.tuning), "tabConfig.tuning", tabConfig.tuning);
6933
- } else if (Utils11.Is.isArray(tabConfig.tuning)) {
6934
- assertArg(tabConfig.tuning.length === 6 && tabConfig.tuning.every((s) => isNote(s)), "tabConfig.tuning", tabConfig.tuning);
6988
+ } else if (Utils13.Is.isArray(tabConfig.tuning)) {
6989
+ assertArg(tabConfig.tuning.length === getStringNumbers().length && tabConfig.tuning.every((s) => isNote(s)), "tabConfig.tuning", tabConfig.tuning);
6935
6990
  }
6936
- assertArg(Utils11.Is.isUndefined(tabConfig.voiceIds) || Utils11.Is.isArray(tabConfig.voiceIds) && tabConfig.voiceIds.every((voiceId) => Utils11.Is.isNumber(voiceId)), "tabConfig.voiceIds", tabConfig.voiceIds);
6991
+ assertArg(Utils13.Is.isUndefined(tabConfig.voiceIds) || Utils13.Is.isArray(tabConfig.voiceIds) && tabConfig.voiceIds.every((voiceId) => Utils13.Is.isNumber(voiceId)), "tabConfig.voiceIds", tabConfig.voiceIds);
6937
6992
  }
6938
6993
  function assertNoteOptions(options) {
6939
- assertArg(Utils11.Is.isObject(options), "noteOptions", options);
6940
- assertArg(Utils11.Is.isBooleanOrUndefined(options.dotted), "noteOptions.dotted", options.dotted);
6941
- assertArg(Utils11.Is.isEnumValueOrUndefined(options.stem, Stem), "noteOptions.stem", options.stem);
6942
- assertArg(Utils11.Is.isStringOrUndefined(options.color), "noteOptions.color", options.color);
6943
- assertArg(Utils11.Is.isBooleanOrUndefined(options.arpeggio) || Utils11.Is.isEnumValue(options.arpeggio, Arpeggio), "noteOptions.arpeggio", options.arpeggio);
6944
- assertArg(Utils11.Is.isBooleanOrUndefined(options.staccato), "noteOptions.staccato", options.staccato);
6945
- assertArg(Utils11.Is.isBooleanOrUndefined(options.diamond), "noteOptions.diamond", options.diamond);
6946
- assertArg(Utils11.Is.isBooleanOrUndefined(options.triplet), "noteOptions.triplet", options.triplet);
6947
- assertArg(Utils11.Is.isUndefined(options.string) || isStringNumber(options.string) || Utils11.Is.isArray(options.string) && options.string.length > 0 && options.string.every((string) => isStringNumber(string)), "noteOptions.string", options.string);
6994
+ assertArg(Utils13.Is.isObject(options), "noteOptions", options);
6995
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.dotted) || Utils13.Is.isIntegerGte(options.dotted, 0), "noteOptions.dotted", options.dotted);
6996
+ assertArg(Utils13.Is.isEnumValueOrUndefined(options.stem, Stem), "noteOptions.stem", options.stem);
6997
+ assertArg(Utils13.Is.isStringOrUndefined(options.color), "noteOptions.color", options.color);
6998
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.arpeggio) || Utils13.Is.isEnumValue(options.arpeggio, Arpeggio), "noteOptions.arpeggio", options.arpeggio);
6999
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.staccato), "noteOptions.staccato", options.staccato);
7000
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.diamond), "noteOptions.diamond", options.diamond);
7001
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.triplet), "noteOptions.triplet", options.triplet);
7002
+ assertArg(Utils13.Is.isUndefined(options.string) || isStringNumber(options.string) || Utils13.Is.isNonEmptyArray(options.string) && options.string.every((string) => isStringNumber(string)), "noteOptions.string", options.string);
7003
+ assertArg(Utils13.Is.isUndefined(options.tieSpan), 'NoteOptions.tieSpan was removed. Use addConnective("tie", tieSpan)', "");
7004
+ assertArg(Utils13.Is.isUndefined(options.slurSpan), 'NoteOptions.slurSpan was removed. Use addConnective("slur", slurSpan)', "");
6948
7005
  }
6949
7006
  function assertRestOptions(options) {
6950
- assertArg(Utils11.Is.isObject(options), "restOptions", options);
6951
- assertArg(Utils11.Is.isBooleanOrUndefined(options.dotted), "restOptions.dotted", options.dotted);
6952
- assertArg(Utils11.Is.isStringOrUndefined(options.staffPos) || Utils11.Is.isInteger(options.staffPos) || options.staffPos instanceof Note10, "restOptions.staffPos", options.staffPos);
6953
- assertArg(Utils11.Is.isStringOrUndefined(options.color), "restOptions.color", options.color);
6954
- assertArg(Utils11.Is.isBooleanOrUndefined(options.hide), "restOptions.hide", options.hide);
6955
- assertArg(Utils11.Is.isBooleanOrUndefined(options.triplet), "restOptions.triplet", options.triplet);
7007
+ assertArg(Utils13.Is.isObject(options), "restOptions", options);
7008
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.dotted) || Utils13.Is.isIntegerGte(options.dotted, 0), "restOptions.dotted", options.dotted);
7009
+ assertArg(Utils13.Is.isStringOrUndefined(options.staffPos) || Utils13.Is.isInteger(options.staffPos) || options.staffPos instanceof Note10, "restOptions.staffPos", options.staffPos);
7010
+ assertArg(Utils13.Is.isStringOrUndefined(options.color), "restOptions.color", options.color);
7011
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.hide), "restOptions.hide", options.hide);
7012
+ assertArg(Utils13.Is.isBooleanOrUndefined(options.triplet), "restOptions.triplet", options.triplet);
6956
7013
  }
6957
7014
  function assertStaffTabOrGRoups(staffTabOrGroups) {
6958
7015
  assertArg(
6959
- Utils11.Is.isStringOrUndefined(staffTabOrGroups) || Utils11.Is.isIntegerGte(staffTabOrGroups, 0) || Utils11.Is.isArray(staffTabOrGroups) && staffTabOrGroups.every(
6960
- (staffTabOrGroup) => Utils11.Is.isString(staffTabOrGroup) || Utils11.Is.isIntegerGte(staffTabOrGroup, 0)
7016
+ Utils13.Is.isStringOrUndefined(staffTabOrGroups) || Utils13.Is.isIntegerGte(staffTabOrGroups, 0) || Utils13.Is.isNonEmptyArray(staffTabOrGroups) && staffTabOrGroups.every(
7017
+ (staffTabOrGroup) => Utils13.Is.isString(staffTabOrGroup) || Utils13.Is.isIntegerGte(staffTabOrGroup, 0)
6961
7018
  ),
6962
7019
  "staffTabOrGroup",
6963
7020
  staffTabOrGroups
6964
7021
  );
6965
7022
  }
7023
+ function isNoteLength(noteLen) {
7024
+ try {
7025
+ validateNoteLength2(noteLen);
7026
+ return true;
7027
+ } catch (e) {
7028
+ return false;
7029
+ }
7030
+ }
7031
+ function isTupletRatio(tupletRatio) {
7032
+ try {
7033
+ validateTupletRatio(tupletRatio);
7034
+ return true;
7035
+ } catch (e) {
7036
+ return false;
7037
+ }
7038
+ }
6966
7039
  var DocumentBuilder = class {
7040
+ /**
7041
+ * Create new document builder instance.
7042
+ */
6967
7043
  constructor() {
6968
7044
  __publicField(this, "doc");
6969
7045
  this.doc = new ObjDocument();
6970
7046
  }
6971
7047
  setScoreConfiguration(config) {
6972
- if (Utils11.Is.isEnumValue(config, StaffPreset)) {
6973
- } else if (Utils11.Is.isObject(config) && config.type === "staff") {
7048
+ if (Utils13.Is.isEnumValue(config, StaffPreset)) {
7049
+ this.doc.setScoreConfiguration(config);
7050
+ } else if (Utils13.Is.isObject(config) && config.type === "staff") {
6974
7051
  assertStaffConfig(config);
6975
- } else if (Utils11.Is.isObject(config) && config.type === "tab") {
7052
+ this.doc.setScoreConfiguration(config);
7053
+ } else if (Utils13.Is.isObject(config) && config.type === "tab") {
6976
7054
  assertTabConfig(config);
6977
- } else if (Utils11.Is.isArray(config)) {
6978
- assertArg(config.length > 0, "config", config);
7055
+ this.doc.setScoreConfiguration(config);
7056
+ } else if (Utils13.Is.isNonEmptyArray(config)) {
6979
7057
  config.forEach((c) => {
6980
- if (Utils11.Is.isObject(c) && c.type === "staff") {
7058
+ if (Utils13.Is.isObject(c) && c.type === "staff") {
6981
7059
  assertStaffConfig(c);
6982
- } else if (Utils11.Is.isObject(c) && c.type === "tab") {
7060
+ } else if (Utils13.Is.isObject(c) && c.type === "tab") {
6983
7061
  assertTabConfig(c);
6984
7062
  } else {
6985
7063
  assertArg(false, "config", config);
6986
7064
  }
6987
7065
  });
7066
+ this.doc.setScoreConfiguration(config);
6988
7067
  } else {
6989
7068
  assertArg(false, "config", config);
6990
7069
  }
6991
- this.doc.setScoreConfiguration(config);
6992
7070
  return this;
6993
7071
  }
6994
7072
  getMeasure() {
6995
7073
  var _a;
6996
7074
  return (_a = this.doc.getLastMeasure()) != null ? _a : this.doc.addMeasure();
6997
7075
  }
7076
+ /**
7077
+ * Get music document after finished building.
7078
+ * @returns - Music document.
7079
+ */
6998
7080
  getDocument() {
6999
7081
  return this.doc.getMusicInterface();
7000
7082
  }
7083
+ /**
7084
+ * Set header texts.
7085
+ * @param title - Title of this docmument/musical piece.
7086
+ * @param composer - Composer of this document/musical piece.
7087
+ * @param arranger - Arranger of this document/musical piece.
7088
+ * @returns - This document builder instance.
7089
+ */
7001
7090
  setHeader(title, composer, arranger) {
7002
- assertArg(Utils11.Is.isStringOrUndefined(title), "title", title);
7003
- assertArg(Utils11.Is.isStringOrUndefined(composer), "composer", composer);
7004
- assertArg(Utils11.Is.isStringOrUndefined(arranger), "arranger", arranger);
7091
+ assertArg(Utils13.Is.isStringOrUndefined(title), "title", title);
7092
+ assertArg(Utils13.Is.isStringOrUndefined(composer), "composer", composer);
7093
+ assertArg(Utils13.Is.isStringOrUndefined(arranger), "arranger", arranger);
7005
7094
  this.doc.setHeader(title, composer, arranger);
7006
7095
  return this;
7007
7096
  }
7097
+ /**
7098
+ * Automatically limit number of measures per score row.
7099
+ * @param measuresPerRow - Number of measures per row. Must be integer >=1 or Infinity.
7100
+ * @returns - This document builder instance.
7101
+ */
7008
7102
  setMeasuresPerRow(measuresPerRow) {
7009
- assertArg(Utils11.Is.isIntegerGte(measuresPerRow, 1) || measuresPerRow === Infinity, "measuresPerRow", measuresPerRow);
7103
+ assertArg(Utils13.Is.isIntegerGte(measuresPerRow, 1) || Utils13.Is.isPosInfinity(measuresPerRow), "measuresPerRow", measuresPerRow);
7010
7104
  this.doc.setMeasuresPerRow(measuresPerRow);
7011
7105
  return this;
7012
7106
  }
7107
+ /**
7108
+ * Add new measure.
7109
+ * @returns - This document builder instance.
7110
+ */
7013
7111
  addMeasure() {
7014
7112
  this.doc.addMeasure();
7015
7113
  return this;
7016
7114
  }
7017
7115
  setKeySignature(...args) {
7018
- assertArg(args[0] instanceof Scale2 || args[0] instanceof KeySignature3 || Utils11.Is.isString(args[0]) && Utils11.Is.isEnumValue(args[1], ScaleType), "keySignature", args);
7116
+ assertArg(args[0] instanceof Scale2 || args[0] instanceof KeySignature3 || Utils13.Is.isNonEmptyString(args[0]) && (args.length === 1 || Utils13.Is.isEnumValue(args[1], ScaleType)), "keySignature", args);
7019
7117
  this.getMeasure().setKeySignature(...args);
7020
7118
  return this;
7021
7119
  }
7120
+ /**
7121
+ * Set time signature for current measure and forward.
7122
+ * @param timeSignature - TimeSignature object instance or string (e.g. "3/4").
7123
+ * @returns - This document builder instance.
7124
+ */
7022
7125
  setTimeSignature(timeSignature) {
7023
- assertArg(timeSignature instanceof TimeSignature2 || Utils11.Is.isString(timeSignature), "timeSignature", timeSignature);
7126
+ assertArg(timeSignature instanceof TimeSignature2 || Utils13.Is.isNonEmptyString(timeSignature), "timeSignature", timeSignature);
7024
7127
  this.getMeasure().setTimeSignature(timeSignature);
7025
7128
  return this;
7026
7129
  }
7027
7130
  setTempo(beatsPerMinute, beatLength, dotted) {
7028
- assertArg(Utils11.Is.isIntegerGte(beatsPerMinute, 1), "beatsPerMinute", beatsPerMinute);
7131
+ assertArg(Utils13.Is.isIntegerGte(beatsPerMinute, 1), "beatsPerMinute", beatsPerMinute);
7029
7132
  if (beatLength === void 0) {
7030
- assertArg(Utils11.Is.isUndefined(dotted), "dotted", dotted);
7133
+ assertArg(Utils13.Is.isUndefined(dotted), "dotted", dotted);
7031
7134
  } else {
7032
- assertArg(Utils11.Is.isEnumValue(beatLength, NoteLength7), "beatLength", beatLength);
7033
- assertArg(Utils11.Is.isBooleanOrUndefined(dotted), "dotted", dotted);
7135
+ assertArg(Utils13.Is.isEnumValue(beatLength, NoteLength7) || isNoteLength(beatLength), "beatLength", beatLength);
7136
+ assertArg(Utils13.Is.isBooleanOrUndefined(dotted) || Utils13.Is.isIntegerGte(dotted, 0), "dotted", dotted);
7034
7137
  }
7035
7138
  this.getMeasure().setTempo(beatsPerMinute, beatLength, dotted);
7036
7139
  return this;
7037
7140
  }
7141
+ /**
7142
+ * Add note o current measure.
7143
+ * @param voiceId - Voice id to add note to.
7144
+ * @param note - Note instance of Note or string (e.g. "D4").
7145
+ * @param noteLength - Note length (e.g. "4n").
7146
+ * @param options - Note options.
7147
+ * @returns - This document builder instance.
7148
+ */
7038
7149
  addNote(voiceId, note, noteLength, options) {
7039
7150
  assertArg(isVoiceId(voiceId), "voiceId", voiceId);
7040
- assertArg(note instanceof Note10 || Utils11.Is.isString(note), "note", note);
7041
- assertArg(Utils11.Is.isEnumValue(noteLength, NoteLength7), "noteLength", noteLength);
7151
+ assertArg(note instanceof Note10 || Utils13.Is.isNonEmptyString(note), "note", note);
7152
+ assertArg(Utils13.Is.isEnumValue(noteLength, NoteLength7) || isNoteLength(noteLength), "noteLength", noteLength);
7042
7153
  if (options !== void 0) {
7043
7154
  assertNoteOptions(options);
7044
7155
  }
7045
7156
  this.getMeasure().addNoteGroup(voiceId, [note], noteLength, options);
7046
7157
  return this;
7047
7158
  }
7159
+ /**
7160
+ * @param voiceId - Voice id to add chord to.
7161
+ * @param notes - Array of notes, each instance of Note or string (e.g. "D4").
7162
+ * @param noteLength - Note length (e.g. "4n").
7163
+ * @param options - Note options.
7164
+ * @returns - This document builder instance.
7165
+ */
7048
7166
  addChord(voiceId, notes, noteLength, options) {
7049
7167
  assertArg(isVoiceId(voiceId), "voiceId", voiceId);
7050
- assertArg(Utils11.Is.isArray(notes) && notes.length >= 1 && notes.every((note) => note instanceof Note10 || Utils11.Is.isString(note)), "notes", notes);
7051
- assertArg(Utils11.Is.isEnumValue(noteLength, NoteLength7), "noteLength", noteLength);
7168
+ assertArg(Utils13.Is.isNonEmptyArray(notes) && notes.every((note) => note instanceof Note10 || Utils13.Is.isNonEmptyString(note)), "notes", notes);
7169
+ assertArg(Utils13.Is.isEnumValue(noteLength, NoteLength7) || isNoteLength(noteLength), "noteLength", noteLength);
7052
7170
  if (options !== void 0) {
7053
7171
  assertNoteOptions(options);
7054
7172
  }
7055
7173
  this.getMeasure().addNoteGroup(voiceId, notes, noteLength, options);
7056
7174
  return this;
7057
7175
  }
7176
+ /**
7177
+ *
7178
+ * @param voiceId - Voice id to add rest to.
7179
+ * @param restLength - Rest length (e.g. "4n").
7180
+ * @param options - Rest options.
7181
+ * @returns - This document builder instance.
7182
+ */
7058
7183
  addRest(voiceId, restLength, options) {
7059
7184
  assertArg(isVoiceId(voiceId), "voiceId", voiceId);
7060
- assertArg(Utils11.Is.isEnumValue(restLength, NoteLength7), "restLength", restLength);
7185
+ assertArg(Utils13.Is.isEnumValue(restLength, NoteLength7) || isNoteLength(restLength), "restLength", restLength);
7061
7186
  if (options !== void 0) {
7062
7187
  assertRestOptions(options);
7063
7188
  }
7064
7189
  this.getMeasure().addRest(voiceId, restLength, options);
7065
7190
  return this;
7066
7191
  }
7192
+ /**
7193
+ * Usage:
7194
+ * <pre>
7195
+ * addTuplet(0, Theory.Tuplet.Triplet, notes => {
7196
+ * notes.addNote("G3", Theory.NoteLength.Eighth);
7197
+ * notes.addNote("B3", Theory.NoteLength.Eighth);
7198
+ * notes.addNote("D4", Theory.NoteLength.Eighth);
7199
+ * });
7200
+ * </pre>
7201
+ *
7202
+ * @param voiceId - Voice id to add tuplet to.
7203
+ * @param tupletRatio - You can also use Theory.Tuplet presets (e.g. Theory.Tuplet.Triplet).
7204
+ * @param tupletBuilder - Tuplet builder function to build tuplet.
7205
+ * @returns - This document builder instance.
7206
+ */
7207
+ addTuplet(voiceId, tupletRatio, tupletBuilder) {
7208
+ assertArg(isVoiceId(voiceId), "voiceId", voiceId);
7209
+ assertArg(Utils13.Is.isFunction(tupletBuilder), "tupletBuilder", tupletBuilder);
7210
+ assertArg(isTupletRatio(tupletRatio) && Utils13.Is.isBooleanOrUndefined(tupletRatio.showRatio), "tupletRatio", tupletRatio);
7211
+ let tupletSymbols = [];
7212
+ const helper = {
7213
+ addNote: (note, noteLength, options) => {
7214
+ assertArg(note instanceof Note10 || Utils13.Is.isNonEmptyString(note), "note", note);
7215
+ assertArg(Utils13.Is.isEnumValue(noteLength, NoteLength7) || isNoteLength(noteLength), "noteLength", noteLength);
7216
+ if (options !== void 0) {
7217
+ delete options.triplet;
7218
+ assertNoteOptions(options);
7219
+ }
7220
+ let s = this.getMeasure().addNoteGroup(voiceId, [note], noteLength, options, tupletRatio);
7221
+ tupletSymbols.push(s);
7222
+ return helper;
7223
+ },
7224
+ addChord: (notes, noteLength, options) => {
7225
+ assertArg(Utils13.Is.isNonEmptyArray(notes) && notes.every((note) => note instanceof Note10 || Utils13.Is.isNonEmptyString(note)), "notes", notes);
7226
+ assertArg(Utils13.Is.isEnumValue(noteLength, NoteLength7) || isNoteLength(noteLength), "noteLength", noteLength);
7227
+ if (options !== void 0) {
7228
+ delete options.triplet;
7229
+ assertNoteOptions(options);
7230
+ }
7231
+ let s = this.getMeasure().addNoteGroup(voiceId, notes, noteLength, options, tupletRatio);
7232
+ tupletSymbols.push(s);
7233
+ return helper;
7234
+ },
7235
+ addRest: (restLength, options) => {
7236
+ assertArg(Utils13.Is.isEnumValue(restLength, NoteLength7) || isNoteLength(restLength), "restLength", restLength);
7237
+ if (options !== void 0) {
7238
+ delete options.triplet;
7239
+ assertRestOptions(options);
7240
+ }
7241
+ let s = this.getMeasure().addRest(voiceId, restLength, options, tupletRatio);
7242
+ tupletSymbols.push(s);
7243
+ return helper;
7244
+ }
7245
+ };
7246
+ tupletBuilder(helper);
7247
+ ObjBeamGroup.createTuplet(tupletSymbols, tupletRatio);
7248
+ return this;
7249
+ }
7067
7250
  addFermataInternal(staffTabOrGroups, fermata) {
7068
7251
  assertStaffTabOrGRoups(staffTabOrGroups);
7069
- assertArg(Utils11.Is.isEnumValue(fermata, Fermata), "fermata", fermata);
7252
+ assertArg(Utils13.Is.isEnumValue(fermata, Fermata), "fermata", fermata);
7070
7253
  this.getMeasure().addFermata(staffTabOrGroups, fermata);
7071
7254
  return this;
7072
7255
  }
7073
- addFermata(fermata = 0 /* AtNote */) {
7256
+ /**
7257
+ * Add fermata to current measure.
7258
+ * @param fermata - Fermata type (e.g. "atNote" or Fermata.AtrNote).
7259
+ * @returns - This document builder instance.
7260
+ */
7261
+ addFermata(fermata = "atNote" /* AtNote */) {
7074
7262
  return this.addFermataInternal(void 0, fermata);
7075
7263
  }
7076
- /** @param staffTabOrGroups - staff/tab index (0=top), staff/tab name, or staff group name. */
7077
- addFermataTo(staffTabOrGroups, fermata = 0 /* AtNote */) {
7264
+ /**
7265
+ * Add Fermata to current measure to given staff/tab/group.
7266
+ * @param staffTabOrGroups - staff/tab index (0=top), staff/tab name, or staff group name.
7267
+ * @param fermata - Fermata type (e.g. "atNote" or Fermata.AtrNote).
7268
+ * @returns - This document builder instance.
7269
+ */
7270
+ addFermataTo(staffTabOrGroups, fermata = "atNote" /* AtNote */) {
7078
7271
  return this.addFermataInternal(staffTabOrGroups, fermata);
7079
7272
  }
7080
7273
  addNavigationInternal(staffTabOrGroups, navigation, ...args) {
7081
7274
  assertStaffTabOrGRoups(staffTabOrGroups);
7082
- assertArg(Utils11.Is.isEnumValue(navigation, Navigation), "navigation", navigation);
7083
- if (navigation === 9 /* EndRepeat */ && args.length > 0) {
7084
- assertArg(Utils11.Is.isIntegerGte(args[0], 1), "playCount", args[0]);
7085
- } else if (navigation === 10 /* Ending */ && args.length > 0) {
7086
- assertArg(args.every((passage) => Utils11.Is.isIntegerGte(passage, 1)), "passages", args);
7275
+ assertArg(Utils13.Is.isEnumValue(navigation, Navigation), "navigation", navigation);
7276
+ if (navigation === "endRepeat" /* EndRepeat */ && args.length > 0) {
7277
+ assertArg(Utils13.Is.isIntegerGte(args[0], 1), "playCount", args[0]);
7278
+ } else if (navigation === "ending" /* Ending */ && args.length > 0) {
7279
+ assertArg(args.every((passage) => Utils13.Is.isIntegerGte(passage, 1)), "passages", args);
7087
7280
  }
7088
7281
  this.getMeasure().addNavigation(staffTabOrGroups, navigation, ...args);
7089
7282
  return this;
@@ -7094,100 +7287,186 @@ var DocumentBuilder = class {
7094
7287
  addNavigationTo(staffTabOrGroups, navigation, ...args) {
7095
7288
  return this.addNavigationInternal(staffTabOrGroups, navigation, ...args);
7096
7289
  }
7290
+ addAnnotationInternal(staffTabOrGroups, annotation, text) {
7291
+ annotation != null ? annotation : annotation = getAnnotation(text);
7292
+ if (annotation === void 0) {
7293
+ throw new MusicError17(MusicErrorType17.Score, `Annotation text "${text}" is not known annotation.`);
7294
+ }
7295
+ assertStaffTabOrGRoups(staffTabOrGroups);
7296
+ assertArg(Utils13.Is.isEnumValue(annotation, Annotation), "annotation", annotation);
7297
+ assertArg(Utils13.Is.isNonEmptyString(text), "text", text);
7298
+ this.getMeasure().addAnnotation(staffTabOrGroups, annotation, text);
7299
+ return this;
7300
+ }
7301
+ addAnnotation(...args) {
7302
+ if (args.length === 1) {
7303
+ return this.addAnnotationInternal(void 0, void 0, args[0]);
7304
+ } else {
7305
+ return this.addAnnotationInternal(void 0, args[0], args[1]);
7306
+ }
7307
+ }
7308
+ addAnnotationTo(staffTabOrGroups, ...args) {
7309
+ if (args.length === 1) {
7310
+ return this.addAnnotationInternal(staffTabOrGroups, void 0, args[0]);
7311
+ } else {
7312
+ return this.addAnnotationInternal(staffTabOrGroups, args[0], args[1]);
7313
+ }
7314
+ }
7097
7315
  addLabelInternal(staffTabOrGroups, label, text) {
7098
7316
  assertStaffTabOrGRoups(staffTabOrGroups);
7099
- assertArg(Utils11.Is.isEnumValue(label, Label), "label", label);
7100
- assertArg(Utils11.Is.isString(text), "text", text);
7317
+ assertArg(Utils13.Is.isEnumValue(label, Label), "label", label);
7318
+ assertArg(Utils13.Is.isNonEmptyString(text), "text", text);
7101
7319
  this.getMeasure().addLabel(staffTabOrGroups, label, text);
7102
7320
  return this;
7103
7321
  }
7322
+ /**
7323
+ * Add label text to column of last added note/chord/rest in current measure.
7324
+ * @param label - Label type (e.g. "chord" or Label.Chord).
7325
+ * @param text - label text (e.g. "Am").
7326
+ * @returns - This document builder instance.
7327
+ */
7104
7328
  addLabel(label, text) {
7105
7329
  return this.addLabelInternal(void 0, label, text);
7106
7330
  }
7107
- /** @param staffTabOrGroups - staff/tab index (0=top), staff/tab name, or staff group name. */
7331
+ /**
7332
+ * Add label text to column of last added note/chord/rest in current measure to given staff/tab/group.
7333
+ * @param staffTabOrGroups - staff/tab index (0=top), staff/tab name, or staff group name.
7334
+ * @param label - Label type (e.g. "chord" or Label.Chord).
7335
+ * @param text - label text (e.g. "Am").
7336
+ * @returns - This document builder instance.
7337
+ */
7108
7338
  addLabelTo(staffTabOrGroups, label, text) {
7109
7339
  return this.addLabelInternal(staffTabOrGroups, label, text);
7110
7340
  }
7111
- addAnnotationInternal(staffTabOrGroups, annotation, text) {
7112
- assertStaffTabOrGRoups(staffTabOrGroups);
7113
- assertArg(Utils11.Is.isEnumValue(annotation, Annotation), "annotation", annotation);
7114
- assertArg(Utils11.Is.isString(text), "text", text);
7115
- this.getMeasure().addAnnotation(staffTabOrGroups, annotation, text);
7116
- return this;
7117
- }
7118
- addAnnotation(annotation, text) {
7119
- return this.addAnnotationInternal(void 0, annotation, text);
7120
- }
7121
- /** @param staffTabOrGroups - staff/tab index (0=top), staff/tab name, or staff group name. */
7122
- addAnnotationTo(staffTabOrGroups, annotation, text) {
7123
- return this.addAnnotationInternal(staffTabOrGroups, annotation, text);
7124
- }
7125
7341
  addConnective(connective, ...args) {
7126
- assertArg(Utils11.Is.isEnumValue(connective, Connective), "connective", connective);
7127
- if (connective === 0 /* Tie */) {
7128
- assertArg(Utils11.Is.isUndefined(args[0]) || Utils11.Is.isInteger(args[0]) || Utils11.Is.isEnumValue(args[0], TieType), "tieSpan", args[0]);
7129
- assertArg(Utils11.Is.isEnumValueOrUndefined(args[1], NoteAnchor), "noteAnchor", args[1]);
7342
+ assertArg(Utils13.Is.isEnumValue(connective, Connective), "connective", connective);
7343
+ if (connective === "tie" /* Tie */) {
7344
+ assertArg(Utils13.Is.isIntegerOrUndefined(args[0]) || Utils13.Is.isEnumValue(args[0], TieType), "tieSpan", args[0]);
7345
+ assertArg(Utils13.Is.isEnumValueOrUndefined(args[1], NoteAnchor), "noteAnchor", args[1]);
7130
7346
  let tieSpan = args[0];
7131
7347
  let noteAnchor = args[1];
7132
7348
  this.getMeasure().addConnective(connective, tieSpan, noteAnchor);
7133
- } else if (connective === 1 /* Slur */) {
7134
- assertArg(Utils11.Is.isUndefined(args[0]) || Utils11.Is.isInteger(args[0]), "slurSpan", args[0]);
7135
- assertArg(Utils11.Is.isEnumValueOrUndefined(args[1], NoteAnchor), "noteAnchor", args[1]);
7349
+ } else if (connective === "slur" /* Slur */) {
7350
+ assertArg(Utils13.Is.isIntegerOrUndefined(args[0]), "slurSpan", args[0]);
7351
+ assertArg(Utils13.Is.isEnumValueOrUndefined(args[1], NoteAnchor), "noteAnchor", args[1]);
7136
7352
  let slurSpan = args[0];
7137
7353
  let noteAnchor = args[1];
7138
7354
  this.getMeasure().addConnective(connective, slurSpan, noteAnchor);
7139
- } else if (connective === 2 /* Slide */) {
7140
- assertArg(Utils11.Is.isEnumValueOrUndefined(args[0], NoteAnchor), "noteAnchor", args[0]);
7355
+ } else if (connective === "slide" /* Slide */) {
7356
+ assertArg(Utils13.Is.isEnumValueOrUndefined(args[0], NoteAnchor), "noteAnchor", args[0]);
7141
7357
  let noteAnchor = args[0];
7142
7358
  this.getMeasure().addConnective(connective, noteAnchor);
7143
7359
  }
7144
7360
  return this;
7145
7361
  }
7146
- addExtension(extensionLength, extensionVisible) {
7147
- assertArg(Utils11.Is.isIntegerGte(extensionLength, 0) || extensionLength === Infinity || Utils11.Is.isEnumValue(extensionLength, NoteLength7), "extendionLength", extensionLength);
7148
- assertArg(Utils11.Is.isBooleanOrUndefined(extensionVisible), "extensionVisible", extensionVisible);
7149
- this.getMeasure().addExtension(extensionLength, extensionVisible != null ? extensionVisible : true);
7362
+ /**
7363
+ * Add extension line to previously added annotation or label element.
7364
+ * <pre>
7365
+ * // Example
7366
+ * addExtension(ext => ext.notes("1n", 2)) // length is 2 whole notes
7367
+ * addExtension(ext => ext.measures(3).hide()) // length is 3 measures, hidden
7368
+ * addExtension(ext => ext.measures(1).notes("8n")) // length is 1 measure + 1 eigth note
7369
+ * addExtension(ext => ext.infinity()) // length is as long as possible
7370
+ * </pre>
7371
+ * @param extensionBuilder - Extension builder function used to build exstension.
7372
+ * @returns - This document builder instance.
7373
+ */
7374
+ addExtension(extensionBuilder) {
7375
+ assertArg(Utils13.Is.isFunctionOrUndefined(extensionBuilder), "addExtension() has new usage, for e.g. addExtension(ext => ext.measures(2)). Please refer to README or API Reference.", extensionBuilder);
7376
+ let ticks = 0;
7377
+ let visible = true;
7378
+ const helper = {
7379
+ notes: (noteLength, noteCount) => {
7380
+ assertArg(Utils13.Is.isEnumValue(noteLength, NoteLength7) || isNoteLength(noteLength), "noteLength", noteLength);
7381
+ assertArg(Utils13.Is.isUndefined(noteCount) || Utils13.Is.isNumber(noteCount) && noteCount >= 0, "noteCount", noteCount);
7382
+ ticks += RhythmProps5.get(noteLength).ticks * (noteCount != null ? noteCount : 1);
7383
+ return helper;
7384
+ },
7385
+ measures: (measureCount) => {
7386
+ assertArg(Utils13.Is.isNumber(measureCount) && measureCount >= 1, "measureCount", measureCount);
7387
+ ticks += this.getMeasure().getMeasureTicks() * measureCount;
7388
+ return helper;
7389
+ },
7390
+ infinity: () => {
7391
+ ticks = Infinity;
7392
+ return helper;
7393
+ },
7394
+ hide: () => {
7395
+ visible = false;
7396
+ return helper;
7397
+ }
7398
+ };
7399
+ if (extensionBuilder) {
7400
+ extensionBuilder(helper);
7401
+ } else {
7402
+ ticks = Infinity;
7403
+ }
7404
+ this.getMeasure().addExtension(ticks, visible);
7150
7405
  return this;
7151
7406
  }
7152
7407
  /**
7153
- *
7408
+ * Add staff group.
7154
7409
  * @param groupName - Name of staff group.
7155
7410
  * @param staffsTabsAndGroups - staff/tab index (0=top), staff/tab name, or staff group name. Single value or array.
7156
7411
  * @param verticalPosition - Vertical position, are elements added above, below or both.
7157
- * @returns
7412
+ * @returns - This document builder instance.
7158
7413
  */
7159
- addStaffGroup(groupName, staffsTabsAndGroups, verticalPosition = 3 /* Auto */) {
7160
- assertArg(Utils11.Is.isString(groupName) && groupName.length > 0, "groupName", groupName);
7414
+ addStaffGroup(groupName, staffsTabsAndGroups, verticalPosition = "auto" /* Auto */) {
7415
+ assertArg(Utils13.Is.isNonEmptyString(groupName), "groupName", groupName);
7161
7416
  assertArg(
7162
- Utils11.Is.isString(staffsTabsAndGroups) && staffsTabsAndGroups.length > 0 || Utils11.Is.isIntegerGte(staffsTabsAndGroups, 0) || Utils11.Is.isArray(staffsTabsAndGroups) && staffsTabsAndGroups.every((line) => Utils11.Is.isString(line) && line.length > 0 || Utils11.Is.isIntegerGte(line, 0)),
7417
+ Utils13.Is.isNonEmptyString(staffsTabsAndGroups) || Utils13.Is.isIntegerGte(staffsTabsAndGroups, 0) || Utils13.Is.isNonEmptyArray(staffsTabsAndGroups) && staffsTabsAndGroups.every((line) => Utils13.Is.isNonEmptyString(line) || Utils13.Is.isIntegerGte(line, 0)),
7163
7418
  "staffsTabsAndGroups",
7164
7419
  staffsTabsAndGroups
7165
7420
  );
7166
- assertArg(Utils11.Is.isEnumValue(verticalPosition, VerticalPosition), "verticalPosition", verticalPosition);
7421
+ assertArg(Utils13.Is.isEnumValue(verticalPosition, VerticalPosition), "verticalPosition", verticalPosition);
7167
7422
  this.doc.addStaffGroup(groupName, staffsTabsAndGroups, verticalPosition);
7168
7423
  return this;
7169
7424
  }
7425
+ /**
7426
+ * Add song end. Adds certain bar line at the end of measure.
7427
+ * @returns - This document builder instance.
7428
+ */
7170
7429
  endSong() {
7171
7430
  this.getMeasure().endSong();
7172
7431
  return this;
7173
7432
  }
7433
+ /**
7434
+ * Add section end. Adds certain bar line at the end of measure.
7435
+ * @returns - This document builder instance.
7436
+ */
7174
7437
  endSection() {
7175
7438
  this.getMeasure().endSection();
7176
7439
  return this;
7177
7440
  }
7441
+ /**
7442
+ * End current score row. Next measure will start new row.
7443
+ * @returns - This document builder instance.
7444
+ */
7178
7445
  endRow() {
7179
7446
  var _a;
7180
7447
  (_a = this.doc.getLastMeasure()) == null ? void 0 : _a.endRow();
7181
7448
  return this;
7182
7449
  }
7450
+ /**
7451
+ * Add rests to fill current measure.
7452
+ * @param voiceId - Voice id to add rests to. Single value, array or all if omitted.
7453
+ * @returns - This document builder instance.
7454
+ */
7183
7455
  completeRests(voiceId) {
7184
- assertArg(Utils11.Is.isUndefined(voiceId) || isVoiceId(voiceId), "voiceId", voiceId);
7456
+ assertArg(Utils13.Is.isUndefined(voiceId) || isVoiceId(voiceId) || Utils13.Is.isArray(voiceId) && voiceId.every((id) => isVoiceId(id)), "voiceId", voiceId);
7185
7457
  this.getMeasure().completeRests(voiceId);
7186
7458
  return this;
7187
7459
  }
7460
+ /**
7461
+ * Add notes of given scale in ascending order.
7462
+ * @param scale - Scale.
7463
+ * @param bottomNote - Scale starts from note >= bottom note.
7464
+ * @param numOctaves - Number of octaves to add.
7465
+ * @returns - This document builder instance.
7466
+ */
7188
7467
  addScaleArpeggio(scale, bottomNote, numOctaves) {
7189
- assertArg(Utils11.Is.isString(bottomNote), "bottomNote", bottomNote);
7190
- assertArg(Utils11.Is.isIntegerGte(numOctaves, 1), "numOctaves", numOctaves);
7468
+ assertArg(Utils13.Is.isNonEmptyString(bottomNote), "bottomNote", bottomNote);
7469
+ assertArg(Utils13.Is.isIntegerGte(numOctaves, 1), "numOctaves", numOctaves);
7191
7470
  let ts = this.getMeasure().getTimeSignature();
7192
7471
  let notes = scale.getScaleNotes(bottomNote, numOctaves);
7193
7472
  for (let i = 0; i < notes.length; i++) {
@@ -7196,7 +7475,7 @@ var DocumentBuilder = class {
7196
7475
  }
7197
7476
  let note = notes[i];
7198
7477
  this.addNote(0, note, ts.beatLength);
7199
- this.addLabel(0 /* Note */, note.formatOmitOctave(SymbolSet2.Unicode));
7478
+ this.addLabel("note" /* Note */, note.formatOmitOctave(SymbolSet2.Unicode));
7200
7479
  }
7201
7480
  return this;
7202
7481
  }
@@ -7205,11 +7484,22 @@ var DocumentBuilder = class {
7205
7484
  // src/score/pub/event.ts
7206
7485
  import { MusicError as MusicError18, MusicErrorType as MusicErrorType18 } from "@tspro/web-music-score/core";
7207
7486
  var ScoreEvent = class {
7487
+ /**
7488
+ * Create new score event instance.
7489
+ * @param type - Score event type.
7490
+ */
7208
7491
  constructor(type) {
7209
7492
  this.type = type;
7210
7493
  }
7211
7494
  };
7212
7495
  var ScoreStaffPosEvent = class extends ScoreEvent {
7496
+ /**
7497
+ * Create new score staff position event.
7498
+ * @param type - Score event type.
7499
+ * @param renderer - Renderer.
7500
+ * @param scoreRow - Score row.
7501
+ * @param diatonicId - Diatonic id that was clicked/entered/left.
7502
+ */
7213
7503
  constructor(type, renderer, scoreRow, diatonicId) {
7214
7504
  super(type);
7215
7505
  this.renderer = renderer;
@@ -7218,6 +7508,12 @@ var ScoreStaffPosEvent = class extends ScoreEvent {
7218
7508
  }
7219
7509
  };
7220
7510
  var ScoreObjectEvent = class extends ScoreEvent {
7511
+ /**
7512
+ * Create new score object event.
7513
+ * @param type - Score event type.
7514
+ * @param renderer - Renderer.
7515
+ * @param objects - Array of objects, last object in this array is the top object that was clicked/entered/left, previous objects are it's parent objects.
7516
+ */
7221
7517
  constructor(type, renderer, objects) {
7222
7518
  super(type);
7223
7519
  this.renderer = renderer;
@@ -7226,32 +7522,34 @@ var ScoreObjectEvent = class extends ScoreEvent {
7226
7522
  throw new MusicError18(MusicErrorType18.Score, "Empty array in score object event!");
7227
7523
  }
7228
7524
  }
7525
+ /** Top object getter. */
7229
7526
  get topObject() {
7230
7527
  return this.objects[this.objects.length - 1];
7231
7528
  }
7529
+ /**
7530
+ * Find object.
7531
+ * @param fn - Compare function.
7532
+ * @returns - First object that matched compare function, or undefined if no match.
7533
+ */
7232
7534
  findObject(fn) {
7233
7535
  return this.objects.find((obj) => fn(obj));
7234
7536
  }
7235
7537
  };
7236
7538
 
7237
- // src/score/pub/interface.ts
7539
+ // src/score/pub/music-interface.ts
7238
7540
  import * as Audio2 from "@tspro/web-music-score/audio";
7239
- import { Utils as Utils12 } from "@tspro/ts-utils-lib";
7541
+ import { Utils as Utils15 } from "@tspro/ts-utils-lib";
7542
+
7543
+ // src/score/pub/music-objects.ts
7544
+ import { Utils as Utils14 } from "@tspro/ts-utils-lib";
7240
7545
  import { MusicError as MusicError19, MusicErrorType as MusicErrorType19 } from "@tspro/web-music-score/core";
7241
7546
  function assertArg2(condition, argName, argValue) {
7242
7547
  if (!condition) {
7243
7548
  throw new MusicError19(MusicErrorType19.Score, `Invalid arg: ${argName} = ${argValue}`);
7244
7549
  }
7245
7550
  }
7246
- function require_t(t, message) {
7247
- if (t === void 0 || t === null) {
7248
- throw new TypeError(message);
7249
- } else {
7250
- return t;
7251
- }
7252
- }
7253
7551
  function isVoiceId2(value) {
7254
- return Utils12.Is.isNumber(value) && getVoiceIds().indexOf(value) >= 0;
7552
+ return Utils14.Is.isNumber(value) && getVoiceIds().indexOf(value) >= 0;
7255
7553
  }
7256
7554
  function getNotationLine(line) {
7257
7555
  if (line instanceof ObjStaff || line instanceof ObjTab) {
@@ -7261,9 +7559,17 @@ function getNotationLine(line) {
7261
7559
  }
7262
7560
  }
7263
7561
  var MusicInterface6 = class {
7562
+ /**
7563
+ * Create new music interface object.
7564
+ * @param name - OBject name.
7565
+ */
7264
7566
  constructor(name) {
7265
7567
  this.name = name;
7266
7568
  }
7569
+ /**
7570
+ * Get parent object.
7571
+ * @returns - Parent object or undefined.
7572
+ */
7267
7573
  getParent() {
7268
7574
  var _a;
7269
7575
  return (_a = this.getMusicObject().getParent()) == null ? void 0 : _a.getMusicInterface();
@@ -7279,10 +7585,15 @@ var _MAccidental = class _MAccidental extends MusicInterface6 {
7279
7585
  getMusicObject() {
7280
7586
  return this.obj;
7281
7587
  }
7588
+ /**
7589
+ * Get accidental.
7590
+ * @returns - Accidental (e.g. 1 = #).
7591
+ */
7282
7592
  getAccidental() {
7283
7593
  return this.obj.accidental;
7284
7594
  }
7285
7595
  };
7596
+ /** Object name. */
7286
7597
  __publicField(_MAccidental, "Name", "Accidental");
7287
7598
  var MAccidental = _MAccidental;
7288
7599
  var _MConnective = class _MConnective extends MusicInterface6 {
@@ -7296,6 +7607,7 @@ var _MConnective = class _MConnective extends MusicInterface6 {
7296
7607
  return this.obj;
7297
7608
  }
7298
7609
  };
7610
+ /** Object name. */
7299
7611
  __publicField(_MConnective, "Name", "Connective");
7300
7612
  var MConnective = _MConnective;
7301
7613
  var _MArpeggio = class _MArpeggio extends MusicInterface6 {
@@ -7308,13 +7620,22 @@ var _MArpeggio = class _MArpeggio extends MusicInterface6 {
7308
7620
  getMusicObject() {
7309
7621
  return this.obj;
7310
7622
  }
7623
+ /**
7624
+ * Get rhythm column this arpeggio is in.
7625
+ * @returns - Rhythm column.
7626
+ */
7311
7627
  getRhythmColumn() {
7312
7628
  return this.obj.col.getMusicInterface();
7313
7629
  }
7630
+ /**
7631
+ * Get notation line this arpeggio is in.
7632
+ * @returns - Staff or tab object.
7633
+ */
7314
7634
  getNotationLine() {
7315
7635
  return getNotationLine(this.obj.line);
7316
7636
  }
7317
7637
  };
7638
+ /** Object name. */
7318
7639
  __publicField(_MArpeggio, "Name", "Arpeggio");
7319
7640
  var MArpeggio = _MArpeggio;
7320
7641
  var _MBeamGroup = class _MBeamGroup extends MusicInterface6 {
@@ -7328,6 +7649,7 @@ var _MBeamGroup = class _MBeamGroup extends MusicInterface6 {
7328
7649
  return this.obj;
7329
7650
  }
7330
7651
  };
7652
+ /** OBject name. */
7331
7653
  __publicField(_MBeamGroup, "Name", "BeamGroup");
7332
7654
  var MBeamGroup = _MBeamGroup;
7333
7655
  var _MStaffBeamGroup = class _MStaffBeamGroup extends MusicInterface6 {
@@ -7340,10 +7662,15 @@ var _MStaffBeamGroup = class _MStaffBeamGroup extends MusicInterface6 {
7340
7662
  getMusicObject() {
7341
7663
  return this.obj;
7342
7664
  }
7665
+ /**
7666
+ * Get staff this beam group is in.
7667
+ * @returns - Staff object.
7668
+ */
7343
7669
  getStaff() {
7344
7670
  return this.obj.staff.getMusicInterface();
7345
7671
  }
7346
7672
  };
7673
+ /** Object name. */
7347
7674
  __publicField(_MStaffBeamGroup, "Name", "StaffBeamGroup");
7348
7675
  var MStaffBeamGroup = _MStaffBeamGroup;
7349
7676
  var _MDocument = class _MDocument extends MusicInterface6 {
@@ -7356,27 +7683,53 @@ var _MDocument = class _MDocument extends MusicInterface6 {
7356
7683
  getMusicObject() {
7357
7684
  return this.obj;
7358
7685
  }
7686
+ /**
7687
+ * Get title.
7688
+ * @returns - Title string or undefined.
7689
+ */
7359
7690
  getTitle() {
7360
7691
  return this.obj.getTitle();
7361
7692
  }
7693
+ /**
7694
+ * Get composer.
7695
+ * @returns - Composer string or undefined.
7696
+ */
7362
7697
  getComposer() {
7363
7698
  return this.obj.getComposer();
7364
7699
  3;
7365
7700
  }
7701
+ /**
7702
+ * Get arranger.
7703
+ * @returns - Arranger string or undefined.
7704
+ */
7366
7705
  getArranger() {
7367
7706
  return this.obj.getArranger();
7368
7707
  }
7708
+ /**
7709
+ * Get score rows.
7710
+ * @returns - Array or score rows.
7711
+ */
7369
7712
  getRows() {
7370
7713
  return this.obj.getRows().map((r) => r.getMusicInterface());
7371
7714
  }
7715
+ /**
7716
+ * Get measures.
7717
+ * @returns - Array of measures.
7718
+ */
7372
7719
  getMeasures() {
7373
7720
  return this.obj.getMeasures().map((m) => m.getMusicInterface());
7374
7721
  }
7375
- play(fn) {
7376
- assertArg2(Utils12.Is.isFunctionOrUndefined(fn), "playStateChangeListener", fn);
7377
- return new MPlayer(this, fn).play();
7722
+ /**
7723
+ * Play this document.
7724
+ * @param playStateChangeListener - Play state change listener function or undefined.
7725
+ * @returns - Player instance.
7726
+ */
7727
+ play(playStateChangeListener) {
7728
+ assertArg2(Utils14.Is.isFunctionOrUndefined(playStateChangeListener), "playStateChangeListener", playStateChangeListener);
7729
+ return new MPlayer(this, playStateChangeListener).play();
7378
7730
  }
7379
7731
  };
7732
+ /** Object name. */
7380
7733
  __publicField(_MDocument, "Name", "Document");
7381
7734
  var MDocument2 = _MDocument;
7382
7735
  var _MEnding = class _MEnding extends MusicInterface6 {
@@ -7389,14 +7742,24 @@ var _MEnding = class _MEnding extends MusicInterface6 {
7389
7742
  getMusicObject() {
7390
7743
  return this.obj;
7391
7744
  }
7745
+ /**
7746
+ * Get passages.
7747
+ * @returns - Array of passage numbers, e.g. passage number 1 means that this ending is played on first pass.
7748
+ */
7392
7749
  getPassages() {
7393
7750
  return this.obj.passages;
7394
7751
  }
7752
+ /**
7753
+ * Has passage number?
7754
+ * @param passage - Passage number to find out.
7755
+ * @returns - Boolean whether this ending has asked passage number.
7756
+ */
7395
7757
  hasPassage(passage) {
7396
- assertArg2(Utils12.Is.isIntegerGte(passage, 1), "passage", passage);
7758
+ assertArg2(Utils14.Is.isIntegerGte(passage, 1), "passage", passage);
7397
7759
  return this.obj.hasPassage(passage);
7398
7760
  }
7399
7761
  };
7762
+ /** Object name. */
7400
7763
  __publicField(_MEnding, "Name", "Ending");
7401
7764
  var MEnding = _MEnding;
7402
7765
  var _MFermata = class _MFermata extends MusicInterface6 {
@@ -7410,6 +7773,7 @@ var _MFermata = class _MFermata extends MusicInterface6 {
7410
7773
  return this.obj;
7411
7774
  }
7412
7775
  };
7776
+ /** OBject name. */
7413
7777
  __publicField(_MFermata, "Name", "Fermata");
7414
7778
  var MFermata = _MFermata;
7415
7779
  var _MHeader = class _MHeader extends MusicInterface6 {
@@ -7422,16 +7786,29 @@ var _MHeader = class _MHeader extends MusicInterface6 {
7422
7786
  getMusicObject() {
7423
7787
  return this.obj;
7424
7788
  }
7789
+ /**
7790
+ * Get title.
7791
+ * @returns - Title string or undefined.
7792
+ */
7425
7793
  getTitle() {
7426
7794
  return this.obj.title;
7427
7795
  }
7796
+ /**
7797
+ * Get composer.
7798
+ * @returns - Composer string or undefined.
7799
+ */
7428
7800
  getComposer() {
7429
7801
  return this.obj.composer;
7430
7802
  }
7803
+ /**
7804
+ * Get arranger.
7805
+ * @returns - Arranger string or undefined.
7806
+ */
7431
7807
  getArranger() {
7432
7808
  return this.obj.arranger;
7433
7809
  }
7434
7810
  };
7811
+ /** OBject name. */
7435
7812
  __publicField(_MHeader, "Name", "Header");
7436
7813
  var MHeader = _MHeader;
7437
7814
  var _MImage = class _MImage extends MusicInterface6 {
@@ -7445,6 +7822,7 @@ var _MImage = class _MImage extends MusicInterface6 {
7445
7822
  return this.obj;
7446
7823
  }
7447
7824
  };
7825
+ /** Object name. */
7448
7826
  __publicField(_MImage, "Name", "Image");
7449
7827
  var MImage = _MImage;
7450
7828
  var _MMeasure = class _MMeasure extends MusicInterface6 {
@@ -7457,16 +7835,29 @@ var _MMeasure = class _MMeasure extends MusicInterface6 {
7457
7835
  getMusicObject() {
7458
7836
  return this.obj;
7459
7837
  }
7838
+ /**
7839
+ * Get measure number.
7840
+ * @returns - Measure number starting from 1, or 0 if upbeat.
7841
+ */
7460
7842
  getMeasureNumber() {
7461
7843
  return this.obj.getMeasureNumber();
7462
7844
  }
7845
+ /**
7846
+ * Get rhythm columns.
7847
+ * @returns - Array of rhythm columns.
7848
+ */
7463
7849
  getRhythmColumns() {
7464
7850
  return this.obj.getColumns().map((col) => col.getMusicInterface());
7465
7851
  }
7852
+ /**
7853
+ * Get score row that this measure is in.
7854
+ * @returns - Score row.
7855
+ */
7466
7856
  getRow() {
7467
7857
  return this.obj.row.getMusicInterface();
7468
7858
  }
7469
7859
  };
7860
+ /** OBject name. */
7470
7861
  __publicField(_MMeasure, "Name", "Measure");
7471
7862
  var MMeasure = _MMeasure;
7472
7863
  var _MBarLineRight = class _MBarLineRight extends MusicInterface6 {
@@ -7480,6 +7871,7 @@ var _MBarLineRight = class _MBarLineRight extends MusicInterface6 {
7480
7871
  return this.obj;
7481
7872
  }
7482
7873
  };
7874
+ /** OBject name. */
7483
7875
  __publicField(_MBarLineRight, "Name", "BarLineRight");
7484
7876
  var MBarLineRight = _MBarLineRight;
7485
7877
  var _MBarLineLeft = class _MBarLineLeft extends MusicInterface6 {
@@ -7493,6 +7885,7 @@ var _MBarLineLeft = class _MBarLineLeft extends MusicInterface6 {
7493
7885
  return this.obj;
7494
7886
  }
7495
7887
  };
7888
+ /** Object name. */
7496
7889
  __publicField(_MBarLineLeft, "Name", "BarLineLeft");
7497
7890
  var MBarLineLeft = _MBarLineLeft;
7498
7891
  var _MStaffTabBarLine = class _MStaffTabBarLine extends MusicInterface6 {
@@ -7505,6 +7898,10 @@ var _MStaffTabBarLine = class _MStaffTabBarLine extends MusicInterface6 {
7505
7898
  getMusicObject() {
7506
7899
  return this.obj;
7507
7900
  }
7901
+ /**
7902
+ * Get parent bar line object.
7903
+ * @returns - Parent bar line object.
7904
+ */
7508
7905
  getBarLine() {
7509
7906
  let barLine = this.obj.barLine;
7510
7907
  if (barLine instanceof ObjBarLineLeft || barLine instanceof ObjBarLineRight) {
@@ -7513,10 +7910,15 @@ var _MStaffTabBarLine = class _MStaffTabBarLine extends MusicInterface6 {
7513
7910
  throw new MusicError19(MusicErrorType19.Score, `Bar line not let nor right.`);
7514
7911
  }
7515
7912
  }
7913
+ /**
7914
+ * Get staff or tab this bar lien object is in.
7915
+ * @returns - Staff or tab.
7916
+ */
7516
7917
  getNotationLine() {
7517
7918
  return getNotationLine(this.obj.line);
7518
7919
  }
7519
7920
  };
7921
+ /** Object name. */
7520
7922
  __publicField(_MStaffTabBarLine, "Name", "StaffTabBarLine");
7521
7923
  var MStaffTabBarLine = _MStaffTabBarLine;
7522
7924
  var _MNoteGroup = class _MNoteGroup extends MusicInterface6 {
@@ -7529,19 +7931,36 @@ var _MNoteGroup = class _MNoteGroup extends MusicInterface6 {
7529
7931
  getMusicObject() {
7530
7932
  return this.obj;
7531
7933
  }
7934
+ /**
7935
+ * Get notes of this note group.
7936
+ * @returns - Array of Note instances.
7937
+ */
7532
7938
  getNotes() {
7533
7939
  return this.obj.notes;
7534
7940
  }
7941
+ /**
7942
+ * Get rhythm props of this note group.
7943
+ * @returns - Rhythm props.
7944
+ */
7535
7945
  getRhythmProps() {
7536
7946
  return this.obj.rhythmProps;
7537
7947
  }
7948
+ /**
7949
+ * Get rhythm column this note group is in.
7950
+ * @returns - Rhythm column.
7951
+ */
7538
7952
  getRhythmColumn() {
7539
7953
  return this.obj.col.getMusicInterface();
7540
7954
  }
7955
+ /**
7956
+ * Get the measure this note group is in.
7957
+ * @returns - Measure.
7958
+ */
7541
7959
  getMeasure() {
7542
7960
  return this.obj.measure.getMusicInterface();
7543
7961
  }
7544
7962
  };
7963
+ /** Object name. */
7545
7964
  __publicField(_MNoteGroup, "Name", "NoteGroup");
7546
7965
  var MNoteGroup = _MNoteGroup;
7547
7966
  var _MStaffNoteGroup = class _MStaffNoteGroup extends MusicInterface6 {
@@ -7554,19 +7973,36 @@ var _MStaffNoteGroup = class _MStaffNoteGroup extends MusicInterface6 {
7554
7973
  getMusicObject() {
7555
7974
  return this.obj;
7556
7975
  }
7976
+ /**
7977
+ * Get parent note group.
7978
+ * @returns - Parent note group.
7979
+ */
7557
7980
  getNoteGroup() {
7558
7981
  return this.obj.noteGroup.getMusicInterface();
7559
7982
  }
7983
+ /**
7984
+ * Get rhythm column this note group is in.
7985
+ * @returns - Rhythm column.
7986
+ */
7560
7987
  getRhythmColumn() {
7561
7988
  return this.getNoteGroup().getRhythmColumn();
7562
7989
  }
7990
+ /**
7991
+ * Get the measure this note group is in.
7992
+ * @returns - Measure.
7993
+ */
7563
7994
  getMeasure() {
7564
7995
  return this.getNoteGroup().getMeasure();
7565
7996
  }
7997
+ /**
7998
+ * Get staff notation line this note group is in.
7999
+ * @returns - Staff object.
8000
+ */
7566
8001
  getStaff() {
7567
8002
  return this.obj.staff.getMusicInterface();
7568
8003
  }
7569
8004
  };
8005
+ /** Object name. */
7570
8006
  __publicField(_MStaffNoteGroup, "Name", "StaffNoteGroup");
7571
8007
  var MStaffNoteGroup = _MStaffNoteGroup;
7572
8008
  var _MTabNoteGroup = class _MTabNoteGroup extends MusicInterface6 {
@@ -7579,19 +8015,36 @@ var _MTabNoteGroup = class _MTabNoteGroup extends MusicInterface6 {
7579
8015
  getMusicObject() {
7580
8016
  return this.obj;
7581
8017
  }
8018
+ /**
8019
+ * Get parent note group.
8020
+ * @returns - Parent note group.
8021
+ */
7582
8022
  getNoteGroup() {
7583
8023
  return this.obj.noteGroup.getMusicInterface();
7584
8024
  }
8025
+ /**
8026
+ * Get rhythm column this note group is in.
8027
+ * @returns - Rhythm column.
8028
+ */
7585
8029
  getRhythmColumn() {
7586
8030
  return this.getNoteGroup().getRhythmColumn();
7587
8031
  }
8032
+ /**
8033
+ * Get the measure this note group is in.
8034
+ * @returns - Measure.
8035
+ */
7588
8036
  getMeasure() {
7589
8037
  return this.getNoteGroup().getMeasure();
7590
8038
  }
8039
+ /**
8040
+ * Get guitar tab this note group is in.
8041
+ * @returns - Tab object.
8042
+ */
7591
8043
  getTab() {
7592
8044
  return this.obj.tab.getMusicInterface();
7593
8045
  }
7594
8046
  };
8047
+ /** OBject name. */
7595
8048
  __publicField(_MTabNoteGroup, "Name", "TabNoteGroup");
7596
8049
  var MTabNoteGroup = _MTabNoteGroup;
7597
8050
  var _MRest = class _MRest extends MusicInterface6 {
@@ -7604,16 +8057,29 @@ var _MRest = class _MRest extends MusicInterface6 {
7604
8057
  getMusicObject() {
7605
8058
  return this.obj;
7606
8059
  }
8060
+ /**
8061
+ * Get rhythm props of this rest.
8062
+ * @returns - Rhythm props.
8063
+ */
7607
8064
  getRhythmProps() {
7608
8065
  return this.obj.rhythmProps;
7609
8066
  }
8067
+ /**
8068
+ * Get rhythm column this rest is in.
8069
+ * @returns - Rhythm column.
8070
+ */
7610
8071
  getRhythmColumn() {
7611
8072
  return this.obj.col.getMusicInterface();
7612
8073
  }
8074
+ /**
8075
+ * Get the measure this rest is in.
8076
+ * @returns - Measure.
8077
+ */
7613
8078
  getMeasure() {
7614
8079
  return this.obj.measure.getMusicInterface();
7615
8080
  }
7616
8081
  };
8082
+ /** OBject name. */
7617
8083
  __publicField(_MRest, "Name", "Rest");
7618
8084
  var MRest = _MRest;
7619
8085
  var _MStaffRest = class _MStaffRest extends MusicInterface6 {
@@ -7626,19 +8092,36 @@ var _MStaffRest = class _MStaffRest extends MusicInterface6 {
7626
8092
  getMusicObject() {
7627
8093
  return this.obj;
7628
8094
  }
8095
+ /**
8096
+ * Get parent rest object.
8097
+ * @returns - Parent rest object.
8098
+ */
7629
8099
  getRest() {
7630
8100
  return this.obj.rest.getMusicInterface();
7631
8101
  }
8102
+ /**
8103
+ * Get rhythm column this rest is in.
8104
+ * @returns - Rhythm column.
8105
+ */
7632
8106
  getRhythmColumn() {
7633
8107
  return this.getRest().getRhythmColumn();
7634
8108
  }
8109
+ /**
8110
+ * Get the measure this rest is in.
8111
+ * @returns - Measure.
8112
+ */
7635
8113
  getMeasure() {
7636
8114
  return this.getRest().getMeasure();
7637
8115
  }
8116
+ /**
8117
+ * Get staff notation line this rest is in.
8118
+ * @returns - Staff object.
8119
+ */
7638
8120
  getStaff() {
7639
8121
  return this.obj.staff.getMusicInterface();
7640
8122
  }
7641
8123
  };
8124
+ /** Object name. */
7642
8125
  __publicField(_MStaffRest, "Name", "StaffRest");
7643
8126
  var MStaffRest = _MStaffRest;
7644
8127
  var _MRhythmColumn = class _MRhythmColumn extends MusicInterface6 {
@@ -7651,19 +8134,36 @@ var _MRhythmColumn = class _MRhythmColumn extends MusicInterface6 {
7651
8134
  getMusicObject() {
7652
8135
  return this.obj;
7653
8136
  }
8137
+ /**
8138
+ * Get symbol (note group or rest) of this column for given voice id.
8139
+ * @param voiceId - Voice id.
8140
+ * @returns - Note group, rest or undefined.
8141
+ */
7654
8142
  getRhythmSymbol(voiceId) {
7655
8143
  var _a;
7656
8144
  assertArg2(isVoiceId2(voiceId), "voiceId", voiceId);
7657
8145
  return (_a = this.obj.getVoiceSymbol(voiceId)) == null ? void 0 : _a.getMusicInterface();
7658
8146
  }
8147
+ /**
8148
+ * Get symbol (note group or rest) of this column for given voice id.
8149
+ * @deprecated - Use getRhythmSymbol(voiceId) instead.
8150
+ * @param voiceId - Voice id.
8151
+ * @returns - Note group, rest or undefined.
8152
+ */
8153
+ getVoiceSymbol(voiceId) {
8154
+ var _a;
8155
+ assertArg2(isVoiceId2(voiceId), "voiceId", voiceId);
8156
+ return (_a = this.obj.getVoiceSymbol(voiceId)) == null ? void 0 : _a.getMusicInterface();
8157
+ }
8158
+ /**
8159
+ * Get the measure this rhythm column is in.
8160
+ * @returns - Measure.
8161
+ */
7659
8162
  getMeasure() {
7660
8163
  return this.obj.measure.getMusicInterface();
7661
8164
  }
7662
- getVoiceSymbol(voiceId) {
7663
- let s = this.obj.getVoiceSymbol(voiceId);
7664
- return s instanceof ObjNoteGroup || s instanceof ObjRest ? s.getMusicInterface() : void 0;
7665
- }
7666
8165
  };
8166
+ /** OBject name. */
7667
8167
  __publicField(_MRhythmColumn, "Name", "RhythmColumn");
7668
8168
  var MRhythmColumn = _MRhythmColumn;
7669
8169
  var _MScoreRow = class _MScoreRow extends MusicInterface6 {
@@ -7676,16 +8176,29 @@ var _MScoreRow = class _MScoreRow extends MusicInterface6 {
7676
8176
  getMusicObject() {
7677
8177
  return this.obj;
7678
8178
  }
8179
+ /**
8180
+ * Parent music document.
8181
+ * @returns - Parent music document.
8182
+ */
7679
8183
  getDocument() {
7680
8184
  return this.obj.doc.getMusicInterface();
7681
8185
  }
8186
+ /**
8187
+ * Get measures of this score row.
8188
+ * @returns - Array of measures.
8189
+ */
7682
8190
  getMeasures() {
7683
8191
  return this.obj.getMeasures().map((m) => m.getMusicInterface());
7684
8192
  }
8193
+ /**
8194
+ * Get notation lines (staves and tabs) of this score row.
8195
+ * @returns - Array of staves and tabs.
8196
+ */
7685
8197
  getNotationLines() {
7686
8198
  return this.obj.getNotationLines().map((line) => getNotationLine(line));
7687
8199
  }
7688
8200
  };
8201
+ /** Object name. */
7689
8202
  __publicField(_MScoreRow, "Name", "ScoreRow");
7690
8203
  var MScoreRow = _MScoreRow;
7691
8204
  var _MStaff = class _MStaff extends MusicInterface6 {
@@ -7698,16 +8211,29 @@ var _MStaff = class _MStaff extends MusicInterface6 {
7698
8211
  getMusicObject() {
7699
8212
  return this.obj;
7700
8213
  }
8214
+ /**
8215
+ * Get index of this staff in score row.
8216
+ * @returns - Index (0=top notation line).
8217
+ */
7701
8218
  getId() {
7702
8219
  return this.obj.id;
7703
8220
  }
8221
+ /**
8222
+ * Get name of this staff.
8223
+ * @returns - Staff name.
8224
+ */
7704
8225
  getName() {
7705
8226
  return this.obj.name.length > 0 ? this.obj.name : void 0;
7706
8227
  }
8228
+ /**
8229
+ * Get the score row this staff is in.
8230
+ * @returns - Score row.
8231
+ */
7707
8232
  getRow() {
7708
8233
  return this.obj.row.getMusicInterface();
7709
8234
  }
7710
8235
  };
8236
+ /** Object name. */
7711
8237
  __publicField(_MStaff, "Name", "Staff");
7712
8238
  var MStaff = _MStaff;
7713
8239
  var _MTab = class _MTab extends MusicInterface6 {
@@ -7720,16 +8246,29 @@ var _MTab = class _MTab extends MusicInterface6 {
7720
8246
  getMusicObject() {
7721
8247
  return this.obj;
7722
8248
  }
8249
+ /**
8250
+ * Get index of this guitar tab in score row.
8251
+ * @returns - Index (0=top notation line).
8252
+ */
7723
8253
  getId() {
7724
8254
  return this.obj.id;
7725
8255
  }
8256
+ /**
8257
+ * Get name of this guitar tab.
8258
+ * @returns - Staff name.
8259
+ */
7726
8260
  getName() {
7727
8261
  return this.obj.name.length > 0 ? this.obj.name : void 0;
7728
8262
  }
8263
+ /**
8264
+ * Get the score row this guitar tab is in.
8265
+ * @returns - Score row.
8266
+ */
7729
8267
  getRow() {
7730
8268
  return this.obj.row.getMusicInterface();
7731
8269
  }
7732
8270
  };
8271
+ /** Object name. */
7733
8272
  __publicField(_MTab, "Name", "Tab");
7734
8273
  var MTab = _MTab;
7735
8274
  var _MSignature = class _MSignature extends MusicInterface6 {
@@ -7742,10 +8281,15 @@ var _MSignature = class _MSignature extends MusicInterface6 {
7742
8281
  getMusicObject() {
7743
8282
  return this.obj;
7744
8283
  }
8284
+ /**
8285
+ * Get staff notation line this signature is in.
8286
+ * @returns - Staff object.
8287
+ */
7745
8288
  getStaff() {
7746
8289
  return this.obj.staff.getMusicInterface();
7747
8290
  }
7748
8291
  };
8292
+ /** Object name. */
7749
8293
  __publicField(_MSignature, "Name", "Signature");
7750
8294
  var MSignature = _MSignature;
7751
8295
  var _MSpecialText = class _MSpecialText extends MusicInterface6 {
@@ -7758,10 +8302,15 @@ var _MSpecialText = class _MSpecialText extends MusicInterface6 {
7758
8302
  getMusicObject() {
7759
8303
  return this.obj;
7760
8304
  }
8305
+ /**
8306
+ * Get text content.
8307
+ * @returns - Text content.
8308
+ */
7761
8309
  getText() {
7762
8310
  return this.obj.getText();
7763
8311
  }
7764
8312
  };
8313
+ /** Object name. */
7765
8314
  __publicField(_MSpecialText, "Name", "SpecialText");
7766
8315
  var MSpecialText = _MSpecialText;
7767
8316
  var _MText = class _MText extends MusicInterface6 {
@@ -7774,10 +8323,15 @@ var _MText = class _MText extends MusicInterface6 {
7774
8323
  getMusicObject() {
7775
8324
  return this.obj;
7776
8325
  }
8326
+ /**
8327
+ * Get text content.
8328
+ * @returns - Text content.
8329
+ */
7777
8330
  getText() {
7778
8331
  return this.obj.getText();
7779
8332
  }
7780
8333
  };
8334
+ /** Object name. */
7781
8335
  __publicField(_MText, "Name", "Text");
7782
8336
  var MText = _MText;
7783
8337
  var _MExtensionLine = class _MExtensionLine extends MusicInterface6 {
@@ -7791,33 +8345,69 @@ var _MExtensionLine = class _MExtensionLine extends MusicInterface6 {
7791
8345
  return this.obj;
7792
8346
  }
7793
8347
  };
8348
+ /** OBject name. */
7794
8349
  __publicField(_MExtensionLine, "Name", "ExtensionLine");
7795
8350
  var MExtensionLine = _MExtensionLine;
8351
+
8352
+ // src/score/pub/music-interface.ts
8353
+ import { MusicError as MusicError20, MusicErrorType as MusicErrorType20 } from "@tspro/web-music-score/core";
8354
+ function assertArg3(condition, argName, argValue) {
8355
+ if (!condition) {
8356
+ throw new MusicError20(MusicErrorType20.Score, `Invalid arg: ${argName} = ${argValue}`);
8357
+ }
8358
+ }
8359
+ function require_t(t, message) {
8360
+ if (t === void 0 || t === null) {
8361
+ throw new TypeError(message);
8362
+ } else {
8363
+ return t;
8364
+ }
8365
+ }
7796
8366
  var _MPlayer = class _MPlayer {
7797
- constructor(doc, fn) {
8367
+ /**
8368
+ * Create new music player.
8369
+ * @param doc - Music document to play.
8370
+ * @param playStateChangeListener - Play state change listener.
8371
+ */
8372
+ constructor(doc, playStateChangeListener) {
7798
8373
  __publicField(this, "player");
7799
- assertArg2(doc instanceof MDocument2, "doc", doc);
7800
- assertArg2(Utils12.Is.isFunctionOrUndefined(fn), "playStateChangeListener", fn);
8374
+ assertArg3(doc instanceof MDocument2, "doc", doc);
8375
+ assertArg3(Utils15.Is.isFunctionOrUndefined(playStateChangeListener), "playStateChangeListener", playStateChangeListener);
7801
8376
  this.player = new Player();
7802
8377
  this.player.setDocument(doc.getMusicObject());
7803
8378
  this.player.setCursorPositionChangeListener((cursorRect) => doc.getMusicObject().updateCursorRect(cursorRect));
7804
- if (fn) {
7805
- this.player.setPlayStateChnageListener(fn);
8379
+ if (playStateChangeListener) {
8380
+ this.player.setPlayStateChnageListener(playStateChangeListener);
7806
8381
  }
7807
8382
  }
8383
+ /**
8384
+ * Stop all playing.
8385
+ */
7808
8386
  static stopAll() {
7809
8387
  this.currentlyPlaying.forEach((p) => p.stop());
7810
8388
  Audio2.stop();
7811
8389
  }
8390
+ /**
8391
+ * Playe attached document.
8392
+ * @returns - This player instance.
8393
+ */
7812
8394
  play() {
7813
8395
  _MPlayer.currentlyPlaying.add(this);
7814
8396
  this.player.play();
7815
8397
  return this;
7816
8398
  }
8399
+ /**
8400
+ * Pause playback of attached document.
8401
+ * @returns - This player instance.
8402
+ */
7817
8403
  pause() {
7818
8404
  this.player.pause();
7819
8405
  return this;
7820
8406
  }
8407
+ /**
8408
+ * Stop playback of attached document.
8409
+ * @returns - This player instance.
8410
+ */
7821
8411
  stop() {
7822
8412
  this.player.stop();
7823
8413
  _MPlayer.currentlyPlaying.delete(this);
@@ -7827,33 +8417,61 @@ var _MPlayer = class _MPlayer {
7827
8417
  __publicField(_MPlayer, "currentlyPlaying", /* @__PURE__ */ new Set());
7828
8418
  var MPlayer = _MPlayer;
7829
8419
  var MRenderer2 = class {
8420
+ /**
8421
+ * Create new renderer instance.
8422
+ */
7830
8423
  constructor() {
7831
8424
  __publicField(this, "renderer");
7832
8425
  this.renderer = new Renderer(this);
7833
8426
  }
8427
+ /**
8428
+ * Attach music document to this renderer.
8429
+ * @param doc - Music document.
8430
+ * @returns - This renderer instance.
8431
+ */
7834
8432
  setDocument(doc) {
7835
- assertArg2(Utils12.Is.isUndefined(doc) || doc instanceof MDocument2, "doc", doc);
8433
+ assertArg3(Utils15.Is.isUndefined(doc) || doc instanceof MDocument2, "doc", doc);
7836
8434
  this.renderer.setDocument(doc);
7837
8435
  return this;
7838
8436
  }
8437
+ /**
8438
+ * Set target canvas html element for this renderer.
8439
+ * @param canvas - HTML canvas element or element id.
8440
+ * @returns - This renderer instance.
8441
+ */
7839
8442
  setCanvas(canvas) {
7840
- canvas = require_t(Utils12.Dom.getCanvas(canvas), typeof canvas === "string" ? "Cannot set renderer canvas because invalid canvas id: " + canvas : "Cannot set renderer canvas because given canvas is undefined.");
8443
+ canvas = require_t(Utils15.Dom.getCanvas(canvas), typeof canvas === "string" ? "Cannot set renderer canvas because invalid canvas id: " + canvas : "Cannot set renderer canvas because given canvas is undefined.");
7841
8444
  this.renderer.setCanvas(canvas);
7842
8445
  return this;
7843
8446
  }
7844
- setScoreEventListener(fn) {
7845
- assertArg2(Utils12.Is.isFunctionOrUndefined(fn), "scoreEventListener", fn);
7846
- this.renderer.setScoreEventListener(fn);
8447
+ /**
8448
+ * Set score event listener.
8449
+ * @param scoreEventListener - Score event listener.
8450
+ */
8451
+ setScoreEventListener(scoreEventListener) {
8452
+ assertArg3(Utils15.Is.isFunctionOrUndefined(scoreEventListener), "scoreEventListener", scoreEventListener);
8453
+ this.renderer.setScoreEventListener(scoreEventListener);
7847
8454
  }
8455
+ /**
8456
+ * Draw given music object hilighted.
8457
+ * @param obj - Music object or undefined to remove hilighting.
8458
+ */
7848
8459
  hilightObject(obj) {
7849
8460
  this.renderer.hilightObject(obj == null ? void 0 : obj.getMusicObject());
7850
8461
  }
8462
+ /**
8463
+ * Draw given staff position hilighted.
8464
+ * @param staffPos - Staff position (score row and diatonic id) or undefined to remove hilighting.
8465
+ */
7851
8466
  hilightStaffPos(staffPos) {
7852
8467
  this.renderer.hilightStaffPos(staffPos ? {
7853
8468
  scoreRow: staffPos.scoreRow.getMusicObject(),
7854
8469
  diatonicId: staffPos.diatonicId
7855
8470
  } : void 0);
7856
8471
  }
8472
+ /**
8473
+ * Draw contents of attached music document to attached canvas.
8474
+ */
7857
8475
  draw() {
7858
8476
  try {
7859
8477
  this.renderer.draw();
@@ -7864,6 +8482,9 @@ var MRenderer2 = class {
7864
8482
  }
7865
8483
  };
7866
8484
  var _MPlaybackButtons = class _MPlaybackButtons {
8485
+ /**
8486
+ * Create new playback buttons helper class instance.
8487
+ */
7867
8488
  constructor() {
7868
8489
  __publicField(this, "playButton");
7869
8490
  __publicField(this, "stopButton");
@@ -7896,8 +8517,13 @@ var _MPlaybackButtons = class _MPlaybackButtons {
7896
8517
  };
7897
8518
  this.updateButtons();
7898
8519
  }
8520
+ /**
8521
+ * Attach music document whose playcak will be controlled by this playback buttons helper class instance.
8522
+ * @param doc - Music document.
8523
+ * @returns
8524
+ */
7899
8525
  setDocument(doc) {
7900
- assertArg2(Utils12.Is.isUndefined(doc) || doc instanceof MDocument2, "doc", doc);
8526
+ assertArg3(Utils15.Is.isUndefined(doc) || doc instanceof MDocument2, "doc", doc);
7901
8527
  this.onStop();
7902
8528
  if (doc) {
7903
8529
  this.player = new MPlayer(doc, (playState) => {
@@ -7910,6 +8536,9 @@ var _MPlaybackButtons = class _MPlaybackButtons {
7910
8536
  this.updateButtons();
7911
8537
  return this;
7912
8538
  }
8539
+ /**
8540
+ * Detach attached music document.
8541
+ */
7913
8542
  detachDocument() {
7914
8543
  this.setDocument(void 0);
7915
8544
  }
@@ -7931,31 +8560,50 @@ var _MPlaybackButtons = class _MPlaybackButtons {
7931
8560
  this.pauseButton.innerText = this.pauseLabel;
7932
8561
  }
7933
8562
  }
8563
+ /**
8564
+ * Set play button.
8565
+ * @param btn - HTML button element or element id.
8566
+ * @param btnLabel - Custom button label (e.g. "Play").
8567
+ * @returns - This playback buttons class instance.
8568
+ */
7934
8569
  setPlayButton(btn, btnLabel) {
7935
- assertArg2(Utils12.Is.isStringOrUndefined(btnLabel), "btnLabel", btnLabel);
8570
+ assertArg3(Utils15.Is.isStringOrUndefined(btnLabel), "btnLabel", btnLabel);
7936
8571
  _MPlaybackButtons.removeOnClickListeners(this.playButton, this.onPlay);
7937
- this.playButton = require_t(Utils12.Dom.getButton(btn), "Play button required!");
8572
+ this.playButton = require_t(Utils15.Dom.getButton(btn), "Play button required!");
7938
8573
  this.playLabel = btnLabel != null ? btnLabel : "Play";
7939
8574
  _MPlaybackButtons.removeOnClickListeners(this.playButton, "all");
7940
8575
  _MPlaybackButtons.addOnClickListener(this.playButton, this.onPlay);
7941
8576
  this.updateButtons();
7942
8577
  return this;
7943
8578
  }
8579
+ /**
8580
+ * Set stop button.
8581
+ * @param btn - HTML button element or element id.
8582
+ * @param btnLabel - Custom button label (e.g. "Stop").
8583
+ * @returns - This playback buttons class instance.
8584
+ */
7944
8585
  setStopButton(btn, btnLabel) {
7945
- assertArg2(Utils12.Is.isStringOrUndefined(btnLabel), "btnLabel", btnLabel);
8586
+ assertArg3(Utils15.Is.isStringOrUndefined(btnLabel), "btnLabel", btnLabel);
7946
8587
  _MPlaybackButtons.removeOnClickListeners(this.stopButton, this.onStop);
7947
- this.stopButton = require_t(Utils12.Dom.getButton(btn), "Stop button required!");
8588
+ this.stopButton = require_t(Utils15.Dom.getButton(btn), "Stop button required!");
7948
8589
  this.stopLabel = btnLabel != null ? btnLabel : "Stop";
7949
8590
  _MPlaybackButtons.removeOnClickListeners(this.stopButton, "all");
7950
8591
  _MPlaybackButtons.addOnClickListener(this.stopButton, this.onStop);
7951
8592
  this.updateButtons();
7952
8593
  return this;
7953
8594
  }
8595
+ /**
8596
+ * Set play/stop button.
8597
+ * @param btn - HTML button element or element id.
8598
+ * @param playLabel - Custom button label for play action (e.g. "Play").
8599
+ * @param stopLabel - Custom button label for stop action (e.g. "Stop").
8600
+ * @returns - This playback buttons class instance.
8601
+ */
7954
8602
  setPlayStopButton(btn, playLabel, stopLabel) {
7955
- assertArg2(Utils12.Is.isStringOrUndefined(playLabel), "playLabel", playLabel);
7956
- assertArg2(Utils12.Is.isStringOrUndefined(stopLabel), "stopLabel", stopLabel);
8603
+ assertArg3(Utils15.Is.isStringOrUndefined(playLabel), "playLabel", playLabel);
8604
+ assertArg3(Utils15.Is.isStringOrUndefined(stopLabel), "stopLabel", stopLabel);
7957
8605
  _MPlaybackButtons.removeOnClickListeners(this.playStopButton, this.onPlayStop);
7958
- this.playStopButton = require_t(Utils12.Dom.getButton(btn), "Play/stop button required!");
8606
+ this.playStopButton = require_t(Utils15.Dom.getButton(btn), "Play/stop button required!");
7959
8607
  this.playLabel = playLabel != null ? playLabel : "Play";
7960
8608
  this.stopLabel = stopLabel != null ? stopLabel : "Stop";
7961
8609
  _MPlaybackButtons.removeOnClickListeners(this.playStopButton, "all");
@@ -7963,10 +8611,16 @@ var _MPlaybackButtons = class _MPlaybackButtons {
7963
8611
  this.updateButtons();
7964
8612
  return this;
7965
8613
  }
8614
+ /**
8615
+ * Set pause button.
8616
+ * @param btn - HTML button element or element id.
8617
+ * @param btnLabel - Custom button label (e.g. "Pause").
8618
+ * @returns - This playback buttons class instance.
8619
+ */
7966
8620
  setPauseButton(btn, btnLabel) {
7967
- assertArg2(Utils12.Is.isStringOrUndefined(btnLabel), "btnLabel", btnLabel);
8621
+ assertArg3(Utils15.Is.isStringOrUndefined(btnLabel), "btnLabel", btnLabel);
7968
8622
  _MPlaybackButtons.removeOnClickListeners(this.pauseButton, this.onPause);
7969
- this.pauseButton = require_t(Utils12.Dom.getButton(btn), "Pause button required!");
8623
+ this.pauseButton = require_t(Utils15.Dom.getButton(btn), "Pause button required!");
7970
8624
  this.pauseLabel = btnLabel != null ? btnLabel : "Pause";
7971
8625
  _MPlaybackButtons.removeOnClickListeners(this.pauseButton, "all");
7972
8626
  _MPlaybackButtons.addOnClickListener(this.pauseButton, this.onPause);
@@ -7988,7 +8642,7 @@ var _MPlaybackButtons = class _MPlaybackButtons {
7988
8642
  }
7989
8643
  }
7990
8644
  static addOnClickListener(btn, onClick) {
7991
- assertArg2(Utils12.Is.isFunction(onClick), "onClick", onClick);
8645
+ assertArg3(Utils15.Is.isFunction(onClick), "onClick", onClick);
7992
8646
  btn.addEventListener("click", onClick);
7993
8647
  let clickListeners = this.savedOnClickListeners.get(btn) || [];
7994
8648
  this.savedOnClickListeners.set(btn, [...clickListeners, onClick]);
@@ -8007,6 +8661,7 @@ export {
8007
8661
  Connective,
8008
8662
  DivRect,
8009
8663
  DocumentBuilder,
8664
+ DynamicsAnnotation,
8010
8665
  Fermata,
8011
8666
  Label,
8012
8667
  MAccidental,
@@ -8048,6 +8703,7 @@ export {
8048
8703
  ScoreStaffPosEvent,
8049
8704
  StaffPreset,
8050
8705
  Stem,
8706
+ TempoAnnotation,
8051
8707
  TieType,
8052
8708
  VerticalPosition,
8053
8709
  getStringNumbers,