music21 v8
I'm proud to release v8 of music21, the toolkit for computer-aided music analysis, score manipulation, computational musicology, etc. This release (technically 8.1) builds on 12.5 months of work from v7, and like all new big number releases has a few backwards incompatible changes from before, in exchange for cool new features.
Version 8 supports Python 3.8+, if you need Python 3.7 (such as on Google Colab which is now 3+ Python versions behind) stick to music21 v7. V8 is the first to fully support Python 3.10 and will receive patches to support Python 3.11 in the future. As Python 3.11 is due to be released any day now, keeping with the m21 policy of supporting three versions of Python, music21 v9 (work starts tomorrow!) will support Python 3.9 and above only.
Big Changes
- The biggest new improvement in v8 is an all new Dublin-Core / MARC based metadata system that allows for encoding a huge amount of information about a score. Look at the new docs for music21.metadata for more information. Thanks to Greg Chapman for the big amount of work on this. (@gregchapman-dev in #1266)
- Modern installation system, based on Hatch. If you have problems, please let me know -- I expect some growing pains on this.
- ArpeggioMark and ArpeggioMarkSpanner classes. by @gregchapman-dev in #1337
- Adding DCML v2 parsing to tsvConverter.py by @malcolmsailor in #1267
- Explicit Keywords on all music21 objects by @mscuthbert in #1377
- Continued Major improvements in Typing across music21. by @mscuthbert and @jacobtylerwalls. If you are using a modern IDE, you will find the number of music21-related bugs you create will go down hugely.
- Ever more docs and more relevant (and diverse examples)
Other changes/fixes since v7.3
- opFrac speedup by @mscuthbert in #1278
- Fix MIDI in Google Colab Notebooks (v8) by @mscuthbert in #1281
- Use more classes in getElementsByClass by @mscuthbert in #1283
- Improve graphing docs and options by @mscuthbert in #1285
- Accidentals never and if-absolutely-necessary by @mscuthbert in #1148
- Add typing to key.py by @mscuthbert in #1289
- makeRests(inPlace=True) returns None for scores by @jacobtylerwalls in #1288
- StreamCore is now a Music21Object; Iterator improvements by @mscuthbert in #1295
- Avoid
<forward>
tags from expressions out of measure bounds by @jacobtylerwalls in #1261 - Avoid writing empty
<movement-title />
and<creator />
tags when title and author have no defaults by @jacobtylerwalls in #1248 - harmonicFunction. maps between RN figures and function labels by @MarkGotham in #1130
- Make cautionaryPitchClass=True work with chords by @jacobtylerwalls in #1299
- Export Unpitched to MIDI by @jacobtylerwalls in #1315
- Fix
getPitches(direction=DESCENDING)
returning ascending scales by @jacobtylerwalls in #1311 - Make
Key
instances compare equal regardless of tonic octave by @jacobtylerwalls in #1316 - optimize opFrac by @mscuthbert in #1322
- Fix midmeasure clef export regression involving voices by @jacobtylerwalls in #1330
- Fix a bug in musicxml/partStaffExporter.py where a clef-octave-change… by @gregchapman-dev in #1334
- [Musicxml export] Preserve whitespace in TextBox by @jacobtylerwalls in #1331
- Fix bug in Capella parsing. by @mscuthbert in #1342
- Patch duration linked bugs by @mscuthbert in #1341
- deprecate gcd in favor of C math by @mscuthbert in #1343
- makeTies within makeNotation; getTimeSignatures recurse by @mscuthbert in #1346
- First docs and improvements to trees by @mscuthbert in #1312
- Fix shiftElements docs by @jacobtylerwalls in #1326
- SixthMinor carries to secondary dominants @mscuthbert in #1354
- Add makeNotation routines for completing or consolidating tuplets by @jacobtylerwalls in #1242
- Demonstrate ties in
splitElementsToCompleteTuplets
doctest by @jacobtylerwalls in #1362 - MusicXML export: Make rests before making notation by @jacobtylerwalls in #1361
- Validate figures provided to
RomanNumeral()
by @jacobtylerwalls in #1340 - Clear cache when adding notes w/o sort by @mscuthbert in #1357
- match d43, d65, etc. by @malcolmsailor in #1363
- Use requests lib. for URL getting by @mscuthbert in #1367
- Allow iterables of qualified class names in
Stream.__getitem__
searches by @jacobtylerwalls in #1359 - Fix problem with add#7 by @mscuthbert in #1373
- Add
makeNotation
argument to test utility by @jacobtylerwalls in #1376 - Prevent too large
<backup>
values in PartStaffExporter by @jacobtylerwalls in #1375 - Prevent zero-duration ChordSymbols from matching stripTies algorithm by @jacobtylerwalls in #1381
- fixed up romanText repeats by @malcolmsailor in #1378
- Remove *arguments where not used by @mscuthbert in #1394
- Standardize DatePrimitive -> Date interaction by @mscuthbert in #1395
- Emphasize Pitches in Interval classes by @mscuthbert in #1396
- Fix issue #1335: voice numbers written in MusicXML must be unique… by @gregchapman-dev in #1336
- Parse double flats in RomanText by @malcolmsailor in #1405
- Fix (and test) writing of multi-measure RepeatBrackets to MusicXML. by @gregchapman-dev in #1401
- romanText write to file-like objects by @malcolmsailor in #1416
- Closing too many states should be a TNException by @mscuthbert in #1421
- Fix loss of forward repeat marks when exporting PartStaffs by @jacobtylerwalls in #1420
- Add typing for contextSites, yieldSites by @mscuthbert in #1423
- Get rid of imp / load_source() by @mscuthbert in #1424
- Remove tons of unnecessary imports in doctests by @mscuthbert in #1425
- Clarify copyright entities by @mscuthbert in #1430
- Use hatch for building by @mscuthbert in #1429
Significant Improvements and bugs Fixed from 7.1 to 7.3.3
- Fix improper call to locale library in multiprocess test text output by @jacobtylerwalls
- Fix
stripTies()
crash in certain scenario with matchByPitch=False by @jacobtylerwalls - Support multiple figures in single lyric (e.g "64") in
figuredBassFromStream()
by @jacobtylerwalls - Add safety and more characters to
figuredBassFromStream()
by @jacobtylerwalls - Fix accentSequence for 3/8 by @jacobtylerwalls
- Use matchByPitch=True in MIDI export by @jacobtylerwalls
- Cleanup chord.tables by @mscuthbert
- Prevent some superfluous naturals when updating accidental displayStatus by @jacobtylerwalls
- MusicXML import: Stop duplicating MetronomeMarks in multi-staff parts by @jacobtylerwalls
- Clear previous result of attachIntervalsBetweenStreams() by @jacobtylerwalls
- Documentation and improvements to tree by @mscuthbert
- Export style attributes from chord members by @jacobtylerwalls
- Fix zero-duration chords and coreInsert crash in reduceChordsOld by @jacobtylerwalls
- Braille: export bowing symbols by @jacobtylerwalls
- Import/export unpitched percussion instruments <--> MusicXML by @jacobtylerwalls
- Explict imports in init.py; support 3.10 by @mscuthbert
- Replace bèmol with bemol in Spanish translation of flat by @yaph
- Fix dissonance score for compound intervals by @jacobtylerwalls
- Fix parsing of add, alter, omit, and subtract in chord symbol figures by @jacobtylerwalls
- Respect Accidental.displayType option 'never' by @jacobtylerwalls
- Clean up temporary attributes set by braille translator by @jacobtylerwalls
- allow classes in getSpannerSites by @mscuthbert
- Small style upgrades and beams by @mscuthbert
- Fix accidental status overriding for initial diatonic naturals by @jacobtylerwalls
- Fix accidental display after note intervenes between identical chromatic pitches by @jacobtylerwalls
- MIDI import: create Unpitched and PercussionChord instances by @jacobtylerwalls
- Fix chord symbol duration realization edge case by @jacobtylerwalls
- Speed up MIDI enum membership tests by @jacobtylerwalls
- Fix numbering of crescendos and diminuendos in musicXML export by @jacobtylerwalls
- Don't choke on conductor tracks lacking meters by @jacobtylerwalls
- Avoid exporting superfluous meters and keys in staff groups by @jacobtylerwalls
- Realize NoChords as rests if writeAsChord = True by @jacobtylerwalls
- Improve ChordSymbol construction from keywords by @jacobtylerwalls
- Fix export of chord symbols with realized durations by @jacobtylerwalls
- Make GarageBand default MIDI player on MacOS by @jacobtylerwalls
- Represent inexpressible gaps as
<forward>
tags by @jacobtylerwalls - Make all import warnings MusicXMLWarning by @jacobtylerwalls
- Clearing bracketedAlterations in RomanNumeral.figure.setter. by @jacobtylerwalls
- Make full scores containing piano parts exportable to braille by @jacobtylerwalls
- Fix MIDI export of meter changes by @jacobtylerwalls
- Import ottava objects from musicXML (as non-transposing) by @jacobtylerwalls
- Improvements to single measure extraction to musicxml by @jacobtylerwalls
- Export music in voices to braille by @jacobtylerwalls
- Fix next(activeSiteOnly=True) finding things in other streams by @jacobtylerwalls
- Import non-default instrument transpositions (musicxml) by @jacobtylerwalls
- Surface
__eq__()
and__getitem__()
in doc builds by @jacobtylerwalls - Set sixthMinor and seventhMinor to CAUTIONARY in romanNumeralFromChord() by @jacobtylerwalls
- Distinguish which figures imply a bass note by @jacobtylerwalls
- Implement N53 (root position Neapolitan) #1210 by @MarkGotham
- Only set a default TempoText style if there is no style already set. by @gregchapman-dev
- Clarify enharmonic equivalents for common sevenths and ninths (commonName) by @jacobtylerwalls
- Raise instead of writing invalid musicxml duration types by @jacobtylerwalls
- Force MEI parser to create unique elements by @jacobtylerwalls
- expandRepeats() partname (Fixes #1165) by @kir12
- getAllNamesForInstrument (completes #1064) by @MarkGotham
- [musicxml import] Prevent loss of inner tuplet's type by @jacobtylerwalls
- [musicxml import] Catch BarException from presence of "times" attribute on start repeats by @gregchapman-dev
- Stop storing id(x) as .id by @mscuthbert
- Audit exceptions in duration module by @jacobtylerwalls
New Contributors
- @gregchapman-dev (Greg Chapman)
- @yaph (Ramiro Gómez)
- @kir12 (Brian Lee)
- @malcolmsailor
As always, thanks to the Seaver Institute and the National Endowment for the Humanities for supporting music21. And MIT, SHASS/Music and Theater Arts.
Full Changelog: v7.1.0...v8.1.0