def testCleanFlat(self):
        from music21 import pitch

        cs = harmony.ChordSymbol(root='eb', bass='bb', kind='dominant')
        self.assertEqual(cs.bass(), pitch.Pitch('B-2'))
        self.assertIs(cs.pitches[0], cs.bass())

        cs = harmony.ChordSymbol('e-7/b-')
        self.assertEqual(cs.root(), pitch.Pitch('E-3'))
        self.assertEqual(cs.bass(), pitch.Pitch('B-2'))
        self.assertEqual(cs.pitches[0], pitch.Pitch('B-2'))

        # common.cleanedFlatNotation() shouldn't be called by
        # the following calls, which what is being tested here:

        cs = harmony.ChordSymbol('b-3')
        self.assertEqual(cs.root(), pitch.Pitch('b-3'))
        self.assertEqual(cs.pitches[0], pitch.Pitch('B-3'))
        self.assertEqual(cs.pitches[1], pitch.Pitch('D4'))

        cs = harmony.ChordSymbol('bb3')
        # B, not B-flat
        self.assertEqual(cs.root(), pitch.Pitch('b2'))
        # b3 alteration applied to B major triad
        self.assertEqual(cs.pitches[0], pitch.Pitch('B2'))
        self.assertEqual(cs.pitches[1], pitch.Pitch('D3'))
        self.assertEqual(cs.pitches[2], pitch.Pitch('F#3'))
Example #2
0
    def testExportChordSymbolsWithRealizedDurations(self):
        gex = GeneralObjectExporter()

        def realizeDurationsAndAssertTags(mm: stream.Measure,
                                          forwardTag=False,
                                          offsetTag=False):
            mm = copy.deepcopy(mm)
            harmony.realizeChordSymbolDurations(mm)
            obj = gex.fromGeneralObject(mm)
            tree = self.getET(obj)
            self.assertIs(bool(tree.findall('.//forward')), forwardTag)
            self.assertIs(bool(tree.findall('.//offset')), offsetTag)

        # Two consecutive chord symbols, no rests
        cs1 = harmony.ChordSymbol('C7')
        cs2 = harmony.ChordSymbol('F7')
        m = stream.Measure()
        m.insert(0, cs1)
        m.insert(2, cs2)
        realizeDurationsAndAssertTags(m, forwardTag=True, offsetTag=False)

        # Two consecutive chord symbols, rest coinciding with first one
        r1 = note.Rest(type='half')
        m.insert(0, r1)
        realizeDurationsAndAssertTags(m, forwardTag=False, offsetTag=False)

        # One chord symbol midmeasure, no rests
        m.remove(cs1)
        m.remove(r1)
        realizeDurationsAndAssertTags(m, forwardTag=True, offsetTag=False)

        # One chord symbol midmeasure coinciding with whole note
        n1 = note.Note(type='whole')
        m.insert(0, n1)
        # Need an offset tag to show the -2.0 offset to get from end to midmeasure
        realizeDurationsAndAssertTags(m, forwardTag=False, offsetTag=True)

        # One chord symbol at beginning of measure coinciding with whole note
        m.remove(cs2)
        m.insert(0, cs1)
        realizeDurationsAndAssertTags(m, forwardTag=False, offsetTag=False)

        # One chord symbol at beginning of measure with writeAsChord=True
        # followed by a half note
        cs1.writeAsChord = True
        n1.offset = 2
        n1.quarterLength = 2
        realizeDurationsAndAssertTags(m, forwardTag=False, offsetTag=False)
Example #3
0
    def testHarmonyC(self):
        from music21 import harmony

        h = harmony.ChordSymbol()
        h.root('E-')
        h.bass('B-')
        h.inversion(2, transposeOnSet=False)
        #h.romanNumeral = 'I64'
        h.chordKind = 'major'
        h.chordKindStr = 'M'

        hd = harmony.ChordStepModification()
        hd.modType = 'alter'
        hd.interval = -1
        hd.degree = 3
        h.addChordStepModification(hd)

        s = stream.Stream()
        s.append(h)
        #s.show()
        raw = fromMusic21Object(s)
        self.assertEqual(raw.find('<root-alter>-1</root-alter>') > 0, True)
        self.assertEqual(raw.find('<degree-value>3</degree-value>') > 0, True)
        self.assertEqual(
            raw.find('<degree-type>alter</degree-type>') > 0, True)
Example #4
0
def writeHalfDim(MyMeasure, RootNote, Duration, Kind):
    MySymbol = harmony.ChordSymbol(root=RootNote,
                                   bass=RootNote,
                                   kind='half-diminished')
    MySymbol.duration = Duration
    MyMeasure.append(MySymbol)
    return (MySymbol)
Example #5
0
def writeSharpEleven(MyMeasure, RootNote, Duration, Kind):
    MySymbol = harmony.ChordSymbol(root=RootNote, bass=RootNote, kind=Kind)
    MySymbol.duration = Duration
    hd = harmony.ChordStepModification()
    hd.type = 'add'
    hd.interval = 1
    hd.degree = 11
    MySymbol.addChordStepModification(hd)
    MyMeasure.append(MySymbol)
    return (MySymbol)
Example #6
0
    def testExportNC(self):
        s = stream.Score()
        p = stream.Part()
        m = stream.Measure()
        m.append(harmony.ChordSymbol('C'))
        m.repeatAppend(note.Note('C'), 4)
        p.append(m)
        m = stream.Measure()
        m.append(harmony.NoChord())
        m.repeatAppend(note.Note('C'), 2)
        m.append(harmony.ChordSymbol('C'))
        m.repeatAppend(note.Note('C'), 2)
        p.append(m)
        s.append(p)

        self.assertEqual(3, self.getXml(s).count('<harmony'))
        self.assertEqual(1,
                         self.getXml(s).count('<kind text="N.C.">none</kind>'))
        self.assertEqual(1, self.getXml(s).count('<root-step text="">'))

        s = stream.Score()
        p = stream.Part()
        m = stream.Measure()
        m.append(harmony.NoChord())
        m.repeatAppend(note.Note('C'), 2)
        m.append(harmony.ChordSymbol('C'))
        m.repeatAppend(note.Note('C'), 2)
        p.append(m)
        m = stream.Measure()
        m.append(harmony.NoChord('No Chord'))
        m.repeatAppend(note.Note('C'), 2)
        m.append(harmony.ChordSymbol('C'))
        m.repeatAppend(note.Note('C'), 2)
        p.append(m)
        s.append(p)

        self.assertEqual(1,
                         self.getXml(s).count('<kind text="N.C.">none</kind>'))
        self.assertEqual(
            1,
            self.getXml(s).count('<kind text="No Chord">none</kind>'))
Example #7
0
    def testCleanFlat(self):
        from music21 import harmony, pitch

        cs = harmony.ChordSymbol(root='eb', bass='bb', kind='dominant')
        self.assertEquals(cs.bass(), pitch.Pitch('B-'))
        self.assertEquals(cs.pitches[0], pitch.Pitch('B-2'))

        cs = harmony.ChordSymbol('e-7/b-')
        self.assertEquals(cs.root(), pitch.Pitch('E-3'))
        self.assertEquals(cs.bass(), pitch.Pitch('B-2'))
        self.assertEquals(cs.pitches[0], pitch.Pitch('B-2'))

        # common.cleanedFlatNotation() shouldn't be called by
        # the following calls, which what is being tested here:

        cs = harmony.ChordSymbol('b-3')
        self.assertEquals(cs.root(), pitch.Pitch('b-3'))
        self.assertEquals(cs.pitches[0], pitch.Pitch('B-3'))
        self.assertEquals(cs.pitches[1], pitch.Pitch('D4'))

        cs = harmony.ChordSymbol('bb3')
        self.assertEquals(cs.root(), pitch.Pitch('b3'))
        self.assertEquals(cs.pitches[0], pitch.Pitch('B3'))
        self.assertEquals(cs.pitches[1], pitch.Pitch('D#4'))
Example #8
0
def parseTokens(mh, dst, p, useMeasures):
    '''
    parses all the tokens in a measure or part.
    '''
    # in case need to transpose due to clef indication
    from music21 import abcFormat

    postTransposition = 0
    clefSet = False
    for t in mh.tokens:
        if isinstance(t, abcFormat.ABCMetadata):
            if t.isMeter():
                ts = t.getTimeSignatureObject()
                if ts is not None:  # can be None
                    # should append at the right position
                    if useMeasures:  # assume at start of measures
                        dst.timeSignature = ts
                    else:
                        dst.coreAppend(ts)
            elif t.isKey():
                ks = t.getKeySignatureObject()
                if useMeasures:  # assume at start of measures
                    dst.keySignature = ks
                else:
                    dst.coreAppend(ks)
                # check for clef information sometimes stored in key
                clefObj, transposition = t.getClefObject()
                if clefObj is not None:
                    clefSet = False
                    #environLocal.printDebug(['found clef in key token:', t,
                    #     clefObj, transposition])
                    if useMeasures:  # assume at start of measures
                        dst.clef = clefObj
                    else:
                        dst.coreAppend(clefObj)
                    postTransposition = transposition
            elif t.isTempo():
                mmObj = t.getMetronomeMarkObject()
                dst.coreAppend(mmObj)

        # as ABCChord is subclass of ABCNote, handle first
        elif isinstance(t, abcFormat.ABCChord):
            # may have more than notes?
            pitchNameList = []
            accStatusList = []  # accidental display status list
            for tSub in t.subTokens:
                # notes are contained as subtokens are already parsed
                if isinstance(tSub, abcFormat.ABCNote):
                    pitchNameList.append(tSub.pitchName)
                    accStatusList.append(tSub.accidentalDisplayStatus)
            c = chord.Chord(pitchNameList)
            c.duration.quarterLength = t.quarterLength
            if t.activeTuplet:
                thisTuplet = copy.deepcopy(t.activeTuplet)
                if thisTuplet.durationNormal is None:
                    thisTuplet.setDurationType(c.duration.type,
                                               c.duration.dots)
                c.duration.appendTuplet(thisTuplet)
            # adjust accidental display for each contained pitch
            for pIndex in range(len(c.pitches)):
                if c.pitches[pIndex].accidental is None:
                    continue
                c.pitches[pIndex].accidental.displayStatus = accStatusList[
                    pIndex]
            dst.coreAppend(c)

            #ql += t.quarterLength

        elif isinstance(t, abcFormat.ABCNote):
            # add the attached chord symbol
            if t.chordSymbols:
                cs_name = t.chordSymbols[0]
                cs_name = re.sub('["]', '', cs_name).lstrip().rstrip()
                cs_name = re.sub('[()]', '', cs_name)
                cs_name = common.cleanedFlatNotation(cs_name)
                try:
                    if cs_name in ('NC', 'N.C.', 'No Chord', 'None'):
                        cs = harmony.NoChord(cs_name)
                    else:
                        cs = harmony.ChordSymbol(cs_name)
                    dst.coreAppend(cs, setActiveSite=False)
                    dst.coreElementsChanged()
                except ValueError:
                    pass  # Exclude malformed chord
            if t.isRest:
                n = note.Rest()
            else:
                n = note.Note(t.pitchName)
                if n.pitch.accidental is not None:
                    n.pitch.accidental.displayStatus = t.accidentalDisplayStatus

            n.duration.quarterLength = t.quarterLength
            if t.activeTuplet:
                thisTuplet = copy.deepcopy(t.activeTuplet)
                if thisTuplet.durationNormal is None:
                    thisTuplet.setDurationType(n.duration.type,
                                               n.duration.dots)
                n.duration.appendTuplet(thisTuplet)

            # start or end a tie at note n
            if t.tie is not None:
                if t.tie in ('start', 'continue'):
                    n.tie = tie.Tie(t.tie)
                    n.tie.style = 'normal'
                elif t.tie == 'stop':
                    n.tie = tie.Tie(t.tie)
            ### Was: Extremely Slow for large Opus files... why?
            ### Answer: some pieces didn't close all their spanners, so
            ###         everything was in a Slur/Diminuendo, etc.
            for span in t.applicableSpanners:
                span.addSpannedElements(n)

            if t.inGrace:
                n = n.getGrace()

            n.articulations = []
            while any(t.artic):
                tmp = t.artic.pop()
                if tmp == "staccato":
                    n.articulations.append(articulations.Staccato())
                elif tmp == "upbow":
                    n.articulations.append(articulations.UpBow())
                elif tmp == "downbow":
                    n.articulations.append(articulations.DownBow())
                elif tmp == "accent":
                    n.articulations.append(articulations.Accent())
                elif tmp == "strongaccent":
                    n.articulations.append(articulations.StrongAccent())
                elif tmp == "tenuto":
                    n.articulations.append(articulations.Tenuto())

            dst.coreAppend(n, setActiveSite=False)

        elif isinstance(t, abcFormat.ABCSlurStart):
            p.coreAppend(t.slurObj)
        elif isinstance(t, abcFormat.ABCCrescStart):
            p.coreAppend(t.crescObj)
        elif isinstance(t, abcFormat.ABCDimStart):
            p.coreAppend(t.dimObj)
    dst.coreElementsChanged()
    return postTransposition, clefSet
Example #9
0
def generateChords(numChords, kind=''):
    '''
    Randomly generate a score of chords for use with the perceived dissonances
    app. These chords may be dissonant or consonant. if kind = 'diatonicTriads',
    only diatonic triads will be generated


    >>> sc = alpha.webapps.commands.generateChords(4, 'diatonicTriads')
    >>> a = alpha.webapps.commands.runPerceivedDissonanceAnalysis(sc, [1.2, 3.2, 5.2])
    >>> chords = a['fullScore']['stream'].flat.getElementsByClass('Chord')
    >>> chords[0].style.color != None
    True
    >>> chords[1].style.color != None
    True
    >>> chords[2].style.color != None
    True
    >>> chords[3].style.color in [None, '#cc3300']
    True
    >>> sc2 = alpha.webapps.commands.generateChords(4)
    >>> a = alpha.webapps.commands.runPerceivedDissonanceAnalysis(sc2, [1.2, 3.2])
    >>> chords = a['fullScore']['stream'].flat.getElementsByClass('Chord')
    >>> chords[0].style.color != None
    True
    >>> chords[1].style.color != None
    True
    >>> chords[2].style.color in [None, '#cc3300']
    True
    >>> chords[3].style.color in [None, '#cc3300']
    True
    '''
    sc = stream.Score()
    p = stream.Part()
    scl = scale.MajorScale('C')
    #possibleChordTypes = [l[0] for l in harmony.CHORD_TYPES.values()]
    possibleChordTypes = ['53', '63', '64']
    if kind == 'diatonicTriads':
        for i in range(numChords):
            startDegree = random.randrange(0, 8)
            inversion = random.randrange(0, 3)
            chordPitches = []
            #testDegrees = [d + startDegree - 1 for d in traidInversions[inversion] ]
            chordPitches = [
                scl.pitchFromDegree(d + startDegree - 1)
                for d in traidInversions[inversion]
            ]
            chordType = possibleChordTypes[random.randrange(
                0, len(possibleChordTypes))]
            c = chord.Chord(chordPitches)
            c.quarterLength = 2
            p.append(c)
        p.makeMeasures(inPlace=True)
        sc.append(p)
        return sc
    else:
        for i in range(numChords):
            loPs = pitch.Pitch("C4").ps
            hiPs = pitch.Pitch("C#5").ps
            startPs = random.randrange(loPs, hiPs)
            startPitch = pitch.Pitch(ps=startPs)
            startPitchName = startPitch.name
            chordType = possibleChordTypes[random.randrange(
                0, len(possibleChordTypes))]
            c = harmony.ChordSymbol(startPitchName + ',' + chordType)
            c.writeAsChord = True
            c.quarterLength = 2
            c.volume.velocity = 127
            p.append(c)
        p.makeMeasures(inPlace=True)
        sc.append(p)
        return sc
Example #10
0
    def testHarmonyB(self):
        from music21 import harmony
        from music21 import key
        s = stream.Stream()
        s.append(key.KeySignature(-2))

        h1 = harmony.ChordSymbol()
        h1.root('c')
        h1.chordKind = 'minor-seventh'
        h1.chordKindStr = 'm7'
        h1.duration.quarterLength = 4
        s.append(h1)

        h2 = harmony.ChordSymbol()
        h2.root('f')
        h2.chordKind = 'dominant'
        h2.chordKindStr = '7'
        h2.duration.quarterLength = 4
        s.append(h2)

        h3 = harmony.ChordSymbol()
        h3.root('B-')
        h3.chordKind = 'major-seventh'
        h3.chordKindStr = 'Maj7'
        h3.duration.quarterLength = 4
        s.append(h3)

        h4 = harmony.ChordSymbol()
        h4.root('e-')
        h4.chordKind = 'major-seventh'
        h4.chordKindStr = 'Maj7'
        h4.duration.quarterLength = 4
        s.append(h4)

        h5 = harmony.ChordSymbol()
        h5.root('a')
        h5.chordKind = 'half-diminished'
        h5.chordKindStr = 'm7b5'
        h5.duration.quarterLength = 4
        s.append(h5)

        h6 = harmony.ChordSymbol()
        h6.root('d')
        h6.chordKind = 'dominant'
        h6.chordKindStr = '7'
        h6.duration.quarterLength = 4
        s.append(h6)

        h7 = harmony.ChordSymbol()
        h7.root('g')
        h7.chordKind = 'minor-sixth'
        h7.chordKindStr = 'm6'
        h7.duration.quarterLength = 4
        s.append(h7)

        #s.show()
        raw = fromMusic21Object(s)
        self.assertEqual(
            raw.find('<kind text="m7">minor-seventh</kind>') > 0, True)
        self.assertEqual(raw.find('<kind text="7">dominant</kind>') > 0, True)
        self.assertEqual(
            raw.find('<kind text="Maj7">major-seventh</kind>') > 0, True)
        self.assertEqual(
            raw.find('<kind text="Maj7">major-seventh</kind>') > 0, True)
        self.assertEqual(
            raw.find('<kind text="m7b5">half-diminished</kind>') > 0, True)

        self.assertEqual(raw.find('<root-step>C</root-step>') > 0, True)
        self.assertEqual(raw.find('<root-alter>-1</root-alter>') > 0, True)
Example #11
0
def writePedal(MyMeasure, RootNote, Duration, Kind):
    MySymbol = harmony.ChordSymbol(root=RootNote, bass=RootNote, kind='major')
    MySymbol.duration = Duration
    MyMeasure.append(MySymbol)
    return (MySymbol)
Example #12
0
def transpose_chs(chs, key):
    # make into actual chords, and transpose each wrt the song's key
    key = chord.Chord(harmony.ChordSymbol(key))
    return [transpose(c, key) for c in chs]
Example #13
0
def tomusic21(ch):
    # flatten human-written chords into music21 chord objects
    return [chord.Chord(harmony.ChordSymbol(c)) for c in ch]
Example #14
0
def get_pitch(chord):
  return [str(p) for p in harmony.ChordSymbol(chord).pitches]
Example #15
0
from music21.scale import ChromaticScale
import music21.harmony as harmony
from orbichord.identify import chordSymbolIndex

from pprint import pprint

chords = OrderedDict()

# Get chromatic scale
pitches = ChromaticScale().getPitches('C', 'B')

# Loop over all possible roots
for add1 in range(13):
    for kind in harmony.CHORD_TYPES.keys():
        for root in pitches:
            ref = harmony.ChordSymbol(root=root, kind=kind)
            basses = [None] + list(ref.pitches)[1:]
            inversions = []
            for bass in basses:
                bass = bass.name if bass else None
                chord = harmony.ChordSymbol(root=root, kind=kind, bass=bass)
                if add1 > 0: chord.add(add1 - 1)
                key = chordSymbolIndex(chord)
                try:
                    name = harmony.chordSymbolFigureFromChord(chord)
                except:
                    continue
                if name == 'Chord Symbol Cannot Be Identified':
                    continue
                if key not in chords:
                    inversions.append(key)