humdrum-tools / verovio-humdrum-viewer

Verovio Humdrum Viewer
http://verovio.humdrum.org
37 stars 9 forks source link

Mensural notation enhancement #554

Closed craigsapp closed 3 years ago

craigsapp commented 3 years ago

Allow for mensural parts to be aligned.

craigsapp commented 3 years ago

Implemented with commit https://github.com/rism-ch/verovio/commit/ad14f69480484767613657bd8ed465b8a444e497

Screen Shot 2021-02-01 at 7 37 17 PM

Test example:

**mens  **mens
*clefC3 *clefC3
*met(O) *met(O)
Sc  se
.   sd
.   Mc
.   mB
.   mA
Sei sd
.   se
sd  sd
Lc  Lc
Sc  se
.   sd
.   sc
SB  <se
.   sd+>
Lc  Lc
*met(C) *met(C)
Scp:    se
.   sd
.   sc:
Sc  sc
.   sd
Lc  Lc
=   =
*-  *-
!!!RDF**mens: i = marked note, color="limegreen", imperfected
!!!RDF**mens: p = marked note, color="orange", perfected
!!!RDF**mens: + = marked note, color="dodgerblue", altered
!!!verovio: spacingNonLinear 0.39

Rendering:

Screen Shot 2021-02-01 at 8 00 50 PM

Conversion to MEI:

<?xml version="1.0" encoding="UTF-8"?>
<?xml-model href="https://music-encoding.org/schema/4.0.0/mei-all.rng" type="application/xml" schematypens="http://relaxng.org/ns/structure/1.0"?>
<?xml-model href="https://music-encoding.org/schema/4.0.0/mei-all.rng" type="application/xml" schematypens="http://purl.oclc.org/dsdl/schematron"?>
<mei xmlns="http://www.music-encoding.org/ns/mei" meiversion="4.0.0">
 <meiHead>
  <fileDesc>
   <titleStmt>
    <title />
   </titleStmt>
   <pubStmt />
  </fileDesc>
  <encodingDesc>
   <appInfo>
    <application isodate="2021-02-01T19:38:13" version="3.2.0-dev-751456e-dirty">
     <name>Verovio</name>
     <p>Transcoded from Humdrum</p>
    </application>
   </appInfo>
  </encodingDesc>
  <workList>
   <work>
    <title />
   </work>
  </workList>
 </meiHead>
 <music>
  <body>
   <mdiv xml:id="mdiv-0000000183182524">
    <score xml:id="score-0000001724434336">
     <scoreDef xml:id="scoredef-0000000642097786" midi.bpm="400">
      <staffGrp xml:id="staffgrp-0000000459178095" bar.thru="true" symbol="brace">
       <staffDef xml:id="staffdef-0000001937822606" n="1" notationtype="mensural.white" lines="5">
        <clef xml:id="clef-L2F2" shape="C" line="3" />
       </staffDef>
       <staffDef xml:id="staffdef-0000001612419428" n="2" notationtype="mensural.white" lines="5">
        <clef xml:id="clef-L2F1" shape="C" line="3" />
       </staffDef>
      </staffGrp>
     </scoreDef>
     <section xml:id="section-L1F1">
      <staff xml:id="staff-0000001224437565" n="1">
       <layer xml:id="layer-L1F2N1" n="1">
        <mensur xml:id="mensur-L3F2" prolatio="2" tempus="3" sign="O" />
        <note xml:id="note-L4F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L5F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L6F2" dur="minima" oct="4" pname="c" />
        <note xml:id="note-L7F2" dur="semiminima" oct="3" pname="b" />
        <note xml:id="note-L8F2" dur="semiminima" oct="3" pname="a" />
        <note xml:id="note-L9F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L10F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L11F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L12F2" dur="longa" oct="4" pname="c" />
        <note xml:id="note-L13F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L14F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L15F2" dur="semibrevis" oct="4" pname="c" />
        <ligature xml:id="ligature-L16F2" form="obliqua">
         <note xml:id="note-L16F2" dur="semibrevis" oct="4" pname="e" />
         <note xml:id="note-L17F2" type="marked" dur="semibrevis" dur.quality="altera" oct="4" pname="d" color="dodgerblue" />
        </ligature>
        <note xml:id="note-L18F2" dur="longa" oct="4" pname="c" />
        <mensur xml:id="mensur-L19F2" prolatio="2" tempus="2" sign="C" />
        <note xml:id="note-L20F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L21F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L22F2" dur="semibrevis" oct="4" pname="c" />
        <dot xml:id="dot-0000001690383100" />
        <note xml:id="note-L23F2" dur="semibrevis" oct="4" pname="c" />
        <note xml:id="note-L24F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L25F2" dur="longa" oct="4" pname="c" />
       </layer>
      </staff>
      <staff xml:id="staff-0000001605562387" n="2">
       <layer xml:id="layer-L1F1N1" n="1">
        <mensur xml:id="mensur-L3F1" prolatio="2" tempus="3" sign="O" />
        <note xml:id="note-L4F1" dur="brevis" oct="4" pname="c" />
        <note xml:id="note-L9F1" type="marked" dur="brevis" dur.quality="imperfecta" num="3" numbase="2" oct="4" pname="e" color="limegreen" />
        <note xml:id="note-L11F1" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L12F1" dur="longa" oct="4" pname="c" />
        <note xml:id="note-L13F1" dur="brevis" oct="4" pname="c" />
        <note xml:id="note-L16F1" dur="brevis" oct="3" pname="b" />
        <note xml:id="note-L18F1" dur="longa" oct="4" pname="c" />
        <mensur xml:id="mensur-L19F1" prolatio="2" tempus="2" sign="C" />
        <note xml:id="note-L20F1" type="marked" dur="brevis" dur.quality="perfecta" num="2" numbase="3" oct="4" pname="c" color="orange" />
        <dot xml:id="dot-0000001794820269" />
        <note xml:id="note-L23F1" dur="brevis" oct="4" pname="c" />
        <note xml:id="note-L25F1" dur="longa" oct="4" pname="c" />
       </layer>
      </staff>
     </section>
    </score>
   </mdiv>
  </body>
 </music>
</mei>

Mensural music rhythm is not parsed during the conversion to MEI. This allows the rhythmic qualities to be added to the music until they are correctly aligned. Once correctly aligned the music can be rhythmically processed. I will add rhythmic parsing of mensural music to the rhythm analysis functions in humlib so that mensural music can be aligned with **kern data.

For example, Here the perfection p, imperfection i and alteration + are remove from the music, causing a misalignment since the perfection/imperfection of the mensuration is used instead:

**mens  **mens
*clefC3 *clefC3
*met(O) *met(O)
Sc  se
.   sd
.   Mc
.   mB
.   mA
Se  sd
.   se
sd  sd
Lc  Lc
Sc  se
.   sd
.   sc
SB  <se
.   sd>
Lc  Lc
*met(C) *met(C)
Sc: se
.   sd
.   sc:
Sc  sc
.   sd
Lc  Lc
=   =
*-  *-
!!!RDF**mens: i = marked note, color="limegreen", imperfected
!!!RDF**mens: p = marked note, color="orange", perfected
!!!RDF**mens: + = marked note, color="dodgerblue", altered
!!!verovio: spacingNonLinear 0.39

Rendering (notice the notes are misaligned):

Screen Shot 2021-02-01 at 7 43 44 PM

The duration of each part is now unequal, but since rhythmic analysis is turned off, the Humdrum converter allows conversion into MEI (unlike CMN where it must be strictly correct and aligned properly). Probably I will add a strict mode for mensural music, but the loose mode will be more useful for data entry.

The line

!!!verovio: spacingNonLinear 0.39

is a verovio option for spacing the music which looks good for mensural music. Perhaps I will auto-set that option when mensural music is detected in the editor.


Also note a recommended, but not required, system is to use ii for notes that need to be imperfected, and pp for notes that need to be perfected. Then i and p are used to explicitly indicate the state of a note's quality based on the mensuration.

Here is an example where all notes are given i and p with the required ones set to ii and pp (altered notes + do not follow this sytem).

**mens  **mens
*clefC3 *clefC3
*met(O) *met(O)
Scp sei
.   sdi
.   Mci
.   mBi
.   mAi
Seii    sdi
.   sei
sdi sdi
Lci Lci
Scp sei
.   sdi
.   sci
SBp <sei
.   sd+>
Lci Lci
*met(C) *met(C)
Scpp:   sei
.   sdi
.   sci:
Sci sci
.   sdi
Lci Lci
=   =
*-  *-
!!!verovio: spacingNonLinear 0.39
Screen Shot 2021-02-01 at 7 53 42 PM

I will write a tool that converts between implicit and explicit perfections, so marking with ii/pp will be easy to do automatically since they will be on notes that have an opposite perfection compared to the mensuration.

MIDI rendering of correctly aligned music will need fixing.

There also seems to be problems with perfect/imperfect note qualities in ligatures (the semibreve ligature in the above example does not have a problem).

craigsapp commented 3 years ago

Also note that only the necessary perfect/imperfect qualities will be encoded in the MEI conversion (not the ones that agree with the mensuration):

Here is the example where every note is given an i or p (or + for the altered note):

**mens  **mens
*clefC3 *clefC3
*met(O) *met(O)
Scp sei
.   sdi
.   Mci
.   mBi
.   mAi
Seii    sdi
.   sei
sdi sdi
Lci Lci
Scp sei
.   sdi
.   sci
SBp <sei
.   sd+>
Lci Lci
*met(C) *met(C)
Scpp:   sei
.   sdi
.   sci:
Sci sci
.   sdi
Lci Lci
=   =
*-  *-
!!!verovio: spacingNonLinear 0.39

MEI conversion, which only has one added imperfecta and one imperfecta added:

<?xml version="1.0" encoding="UTF-8"?>
<?xml-model href="https://music-encoding.org/schema/4.0.0/mei-all.rng" type="application/xml" schematypens="http://relaxng.org/ns/structure/1.0"?>
<?xml-model href="https://music-encoding.org/schema/4.0.0/mei-all.rng" type="application/xml" schematypens="http://purl.oclc.org/dsdl/schematron"?>
<mei xmlns="http://www.music-encoding.org/ns/mei" meiversion="4.0.0">
 <meiHead>
  <fileDesc>
   <titleStmt>
    <title />
   </titleStmt>
   <pubStmt />
  </fileDesc>
  <encodingDesc>
   <appInfo>
    <application isodate="2021-02-01T20:06:46" version="3.2.0-dev-751456e-dirty">
     <name>Verovio</name>
     <p>Transcoded from Humdrum</p>
    </application>
   </appInfo>
  </encodingDesc>
  <workList>
   <work>
    <title />
   </work>
  </workList>
 </meiHead>
 <music>
  <body>
   <mdiv xml:id="mdiv-0000000372056104">
    <score xml:id="score-0000000872724404">
     <scoreDef xml:id="scoredef-0000000642097786" midi.bpm="400">
      <staffGrp xml:id="staffgrp-0000000039027905" bar.thru="true" symbol="brace">
       <staffDef xml:id="staffdef-0000001304587121" n="1" notationtype="mensural.white" lines="5">
        <clef xml:id="clef-L2F2" shape="C" line="3" />
       </staffDef>
       <staffDef xml:id="staffdef-0000001096741328" n="2" notationtype="mensural.white" lines="5">
        <clef xml:id="clef-L2F1" shape="C" line="3" />
       </staffDef>
      </staffGrp>
     </scoreDef>
     <section xml:id="section-L1F1">
      <staff xml:id="staff-0000000561644327" n="1">
       <layer xml:id="layer-L1F2N1" n="1">
        <mensur xml:id="mensur-L3F2" prolatio="2" tempus="3" sign="O" />
        <note xml:id="note-L4F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L5F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L6F2" dur="minima" oct="4" pname="c" />
        <note xml:id="note-L7F2" dur="semiminima" oct="3" pname="b" />
        <note xml:id="note-L8F2" dur="semiminima" oct="3" pname="a" />
        <note xml:id="note-L9F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L10F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L11F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L12F2" dur="longa" oct="4" pname="c" />
        <note xml:id="note-L13F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L14F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L15F2" dur="semibrevis" oct="4" pname="c" />
        <ligature xml:id="ligature-L16F2" form="obliqua">
         <note xml:id="note-L16F2" dur="semibrevis" oct="4" pname="e" />
         <note xml:id="note-L17F2" dur="semibrevis" dur.quality="altera" oct="4" pname="d" />
        </ligature>
        <note xml:id="note-L18F2" dur="longa" oct="4" pname="c" />
        <mensur xml:id="mensur-L19F2" prolatio="2" tempus="2" sign="C" />
        <note xml:id="note-L20F2" dur="semibrevis" oct="4" pname="e" />
        <note xml:id="note-L21F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L22F2" dur="semibrevis" oct="4" pname="c" />
        <dot xml:id="dot-0000000402482158" />
        <note xml:id="note-L23F2" dur="semibrevis" oct="4" pname="c" />
        <note xml:id="note-L24F2" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L25F2" dur="longa" oct="4" pname="c" />
       </layer>
      </staff>
      <staff xml:id="staff-0000002024192543" n="2">
       <layer xml:id="layer-L1F1N1" n="1">
        <mensur xml:id="mensur-L3F1" prolatio="2" tempus="3" sign="O" />
        <note xml:id="note-L4F1" dur="brevis" oct="4" pname="c" />
        <note xml:id="note-L9F1" dur="brevis" dur.quality="imperfecta" num="3" numbase="2" oct="4" pname="e" />
        <note xml:id="note-L11F1" dur="semibrevis" oct="4" pname="d" />
        <note xml:id="note-L12F1" dur="longa" oct="4" pname="c" />
        <note xml:id="note-L13F1" dur="brevis" oct="4" pname="c" />
        <note xml:id="note-L16F1" dur="brevis" oct="3" pname="b" />
        <note xml:id="note-L18F1" dur="longa" oct="4" pname="c" />
        <mensur xml:id="mensur-L19F1" prolatio="2" tempus="2" sign="C" />
        <note xml:id="note-L20F1" dur="brevis" dur.quality="perfecta" num="2" numbase="3" oct="4" pname="c" />
        <dot xml:id="dot-0000001049991184" />
        <note xml:id="note-L23F1" dur="brevis" oct="4" pname="c" />
        <note xml:id="note-L25F1" dur="longa" oct="4" pname="c" />
       </layer>
      </staff>
     </section>
    </score>
   </mdiv>
  </body>
 </music>
</mei>