예제 #1
0
class BluesModality(Modality):
    """
    This class represents major and minor blues modalities - scales with 6 tones over the 12 tone chromatic partition.
    """
    BLUES_MODALITIES = [
        ModalityType.MajorBlues,
        ModalityType.MinorBlues,
    ]
    MODALITY_DEFINITION_MAP = {
        ModalityType.MajorBlues:
        ModalitySpec(
            ModalityType.MajorBlues,
            ['P:1', 'M:2', 'A:1', 'm:2', 'm:3', 'M:2', 'm:3']),  # Ascending
        ModalityType.MinorBlues:
        ModalitySpec(
            ModalityType.MinorBlues,
            ['P:1', 'm:3', 'M:2', 'A:1', 'm:2', 'm:3', 'M:2']),  # Ascending
    }

    @staticmethod
    def create(modality_type, modal_index=0):
        if modality_type not in BluesModality.BLUES_MODALITIES:
            raise Exception('Type parameter is not blues.')
        if modality_type not in BluesModality.MODALITY_DEFINITION_MAP:
            raise Exception(
                'Illegal diatonic modality value: {0} - Check Modality_definition_map'
                .format(str(modality_type)))
        return Modality(BluesModality.MODALITY_DEFINITION_MAP[modality_type],
                        modal_index)

    @staticmethod
    def blues_modality_types_as_string_array():
        answer = [str(t) for t in BluesModality.BLUES_MODALITIES]
        return answer
예제 #2
0
    def test_build_user_defined_tonality(self):
        modality_type = ModalityType('my_modality')
        incremental_interval_strs = [
            'P:1', 'm:2', 'M:3', 'm:2', 'm:2', 'M:2', 'A:2'
        ]
        modality_spec = ModalitySpec(modality_type, incremental_interval_strs)
        modality = Modality(modality_spec)

        tonality = Tonality(modality, 'A')

        assert 0 == tonality.modal_index
        assert 'A' == tonality.diatonic_tone.diatonic_symbol
        assert ['A', 'Bb', 'D', 'Eb', 'Fb', 'Gb',
                'A'] == [t.diatonic_symbol for t in tonality.annotation]
예제 #3
0
class OctatonicModality(Modality):
    """
    Defines the octatonic tonality.  The scale is uniform tone-alternating half and whole steps.
    """
    OCTATONIC_MODALITIES = [
        ModalityType.HWOctatonic,
        ModalityType.WHOctatonic,
    ]

    MODALITY_DEFINITION_MAP = {
        ModalityType.HWOctatonic:
        ModalitySpec(
            ModalityType.HWOctatonic,
            ['P:1', 'm:2', 'M:2', 'm:2', 'M:2', 'A:1', 'M:2', 'm:2', 'M:2']),
        ModalityType.WHOctatonic:
        ModalitySpec(
            ModalityType.WHOctatonic,
            ['P:1', 'M:2', 'm:2', 'M:2', 'A:1', 'M:2', 'm:2', 'M:2', 'm:2']),
    }

    @staticmethod
    def create(modality_type, modal_index=0):
        if modality_type not in OctatonicModality.OCTATONIC_MODALITIES:
            raise Exception('Type parameter is not diatonic.')
        if modality_type not in OctatonicModality.MODALITY_DEFINITION_MAP:
            raise Exception(
                'Illegal diatonic modality value: {0} - Check Modality_definition_map'
                .format(str(modality_type)))
        return Modality(
            OctatonicModality.MODALITY_DEFINITION_MAP[modality_type],
            modal_index)

    @staticmethod
    def octatonic_modality_types_as_string_array():
        answer = [str(t) for t in OctatonicModality.OCTATONIC_MODALITIES]
        return answer
예제 #4
0
class WholeToneModality(Modality):
    """
    This class represents whole tone modalities - scales with 6 tones over the 12 tone chromatic scale.
    All tones are 2 semitones apart.
    """

    WHOLE_TONE_SPEC = ModalitySpec(
        ModalityType.WholeTone,
        ['P:1', 'M:2', 'M:2', 'M:2', 'M:2', 'M:2', 'd:3'])

    @staticmethod
    def create(modality_type, modal_index=0):
        if modality_type != ModalityType.WholeTone:
            raise Exception('Type parameter is not WholeTone.')
        return Modality(WholeToneModality.WHOLE_TONE_SPEC, modal_index)
예제 #5
0
    def test_user_defined_modality(self):
        print('----- test_user_defined_modality -----')

        modality_type = ModalityType('MyModality')
        incremental_interval_strs = [
            'P:1', 'm:2', 'M:3', 'm:2', 'm:2', 'M:2', 'A:2'
        ]
        modality_spec = ModalitySpec(modality_type, incremental_interval_strs)
        ModalityFactory.register_modality(modality_type, modality_spec)

        music_text_line = LineGrammarExecutor()

        s = '{<C-!MyModality: I> F#:4 A D}'
        line, hct = music_text_line.parse(s)
        print(line)
        print('-----')
예제 #6
0
    def test_user_defined_modality(self):
        modality_type = ModalityType('my_modality')
        incremental_interval_strs = [
            'P:1', 'm:2', 'M:3', 'm:2', 'm:2', 'M:2', 'A:2'
        ]
        modality_spec = ModalitySpec(modality_type, incremental_interval_strs)
        modality = Modality(modality_spec)

        assert modality.modality_type == modality_type
        assert modality.get_number_of_tones() == 6

        intervals = modality.incremental_intervals
        assert len(intervals) == 7
        assert str(intervals[0]) == 'P:1'
        assert str(intervals[1]) == 'm:2'
        assert str(intervals[2]) == 'M:3'
        assert str(intervals[3]) == 'm:2'
        assert str(intervals[4]) == 'm:2'
        assert str(intervals[5]) == 'M:2'
        assert str(intervals[6]) == 'A:2'
예제 #7
0
    def test_book_examples(self):
        modality = ModalityFactory.create_modality(ModalityType.Major)
        assert modality is not None

        modality = ModalityFactory.create_modality(
            ModalityType.MajorPentatonic, 1)
        assert modality is not None

        my_modality = 'my_modality'
        modality_type = ModalityType(my_modality)
        incremental_interval_strs = [
            'P:1', 'm:2', 'M:3', 'm:2', 'm:2', 'M:2', 'A:2'
        ]
        modality_spec = ModalitySpec(modality_type, incremental_interval_strs)
        ModalityFactory.register_modality(modality_type, modality_spec)
        modality = ModalityFactory.create_modality(ModalityType(my_modality))
        assert modality is not None

        tones = modality.get_tonal_scale(DiatonicFoundation.get_tone('Eb'))
        print('[{0}]'.format(','.join(
            str(tone.diatonic_symbol) for tone in tones)))
예제 #8
0
class DiatonicModality(Modality):
    """
    This class represents diatonic modalities - scales with 7 tones over the 12 tone chromatic scale.
    These include Major, Minor, and Modal scales.
    """
    DIATONIC_MODALITIES = [
        ModalityType.Major,
        ModalityType.NaturalMinor,
        ModalityType.MelodicMinor,
        ModalityType.HarmonicMinor,
        ModalityType.HarmonicMajor,
        ModalityType.Ionian,
        ModalityType.Dorian,
        ModalityType.Phrygian,
        ModalityType.Lydian,
        ModalityType.Mixolydian,
        ModalityType.Aeolian,
        ModalityType.Locrian,
    ]

    MODALITY_DEFINITION_MAP = {
        ModalityType.Major:
        ModalitySpec(ModalityType.Major,
                     ['P:1', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2', 'M:2', 'm:2']),
        ModalityType.NaturalMinor:
        ModalitySpec(ModalityType.NaturalMinor,
                     ['P:1', 'M:2', 'm:2', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2']),
        ModalityType.MelodicMinor:
        ModalitySpec(ModalityType.MelodicMinor,
                     ['P:1', 'M:2', 'm:2', 'M:2', 'M:2', 'M:2', 'M:2', 'm:2']),
        ModalityType.HarmonicMinor:
        ModalitySpec(ModalityType.HarmonicMinor,
                     ['P:1', 'M:2', 'm:2', 'M:2', 'M:2', 'm:2', 'A:2', 'm:2']),
        ModalityType.HarmonicMajor:
        ModalitySpec(ModalityType.HarmonicMajor,
                     ['P:1', 'M:2', 'M:2', 'm:2', 'M:2', 'm:2', 'A:2', 'm:2']),
        ModalityType.Ionian:
        ModalitySpec(ModalityType.Ionian,
                     ['P:1', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2', 'M:2', 'm:2']),
        ModalityType.Dorian:
        ModalitySpec(ModalityType.Dorian,
                     ['P:1', 'M:2', 'm:2', 'M:2', 'M:2', 'M:2', 'm:2', 'M:2']),
        ModalityType.Phrygian:
        ModalitySpec(ModalityType.Phrygian,
                     ['P:1', 'm:2', 'M:2', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2']),
        ModalityType.Lydian:
        ModalitySpec(ModalityType.Lydian,
                     ['P:1', 'M:2', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2', 'm:2']),
        ModalityType.Mixolydian:
        ModalitySpec(ModalityType.Mixolydian,
                     ['P:1', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2', 'm:2', 'M:2']),
        ModalityType.Aeolian:
        ModalitySpec(ModalityType.Aeolian,
                     ['P:1', 'M:2', 'm:2', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2']),
        ModalityType.Locrian:
        ModalitySpec(ModalityType.Locrian,
                     ['P:1', 'm:2', 'M:2', 'M:2', 'm:2', 'M:2', 'M:2', 'M:2']),
    }

    @staticmethod
    def create(modality_type, modal_index=0):
        if modality_type not in DiatonicModality.DIATONIC_MODALITIES:
            raise Exception('Type parameter is not diatonic.')
        if modality_type not in DiatonicModality.MODALITY_DEFINITION_MAP:
            raise Exception(
                'Illegal diatonic modality value: {0} - Check Modality_definition_map'
                .format(str(modality_type)))
        return Modality(
            DiatonicModality.MODALITY_DEFINITION_MAP[modality_type],
            modal_index)

    @staticmethod
    def diatonic_modality_types_as_string_array():
        answer = [t.name for t in DiatonicModality.DIATONIC_MODALITIES]
        return answer

    @staticmethod
    def find_modality(tones):
        answers = list()
        if len(tones) == 7:
            for t in [
                    ModalityType.Major, ModalityType.NaturalMinor,
                    ModalityType.MelodicMinor, ModalityType.HarmonicMinor,
                    ModalityType.HarmonicMajor
            ]:
                modality_spec = DiatonicModality.MODALITY_DEFINITION_MAP[t]

                p1 = Interval.parse('P:1')
                for scale_start in range(0, 7):
                    intervals = [p1] + [
                        Interval.calculate_tone_interval(
                            tones[(scale_start + i) % 7],
                            tones[(scale_start + i + 1) % 7])
                        for i in range(0, len(tones))
                    ]
                    if intervals == modality_spec.incremental_intervals:
                        answers.append(
                            DiatonicModality.create(t, (-scale_start) %
                                                    len(tones)))
        return answers
예제 #9
0
class PentatonicModality(Modality):
    """
    This class represents 5 pentatonic modalities - scales with 5 tones over the 12 tone chromatic partition.
    With circular succession, each is a rotation of the prior.
    """
    PENTATONIC_MODALITIES = [
        ModalityType.MajorPentatonic,
        ModalityType.EgyptianPentatonic,
        ModalityType.MinorBluesPentatonic,
        ModalityType.MajorBluesPentatonic,
        ModalityType.MinorPentatonic,
    ]

    MODALITY_DEFINITION_MAP = {
        ModalityType.MajorPentatonic:
        ModalitySpec(ModalityType.MajorPentatonic,
                     ['P:1', 'M:2', 'M:2', 'm:3', 'M:2', 'm:3']),
        ModalityType.EgyptianPentatonic:
        ModalitySpec(ModalityType.EgyptianPentatonic,
                     ['P:1', 'M:2', 'm:3', 'M:2', 'm:3', 'M:2']),
        ModalityType.MinorBluesPentatonic:
        ModalitySpec(ModalityType.MinorBluesPentatonic,
                     ['P:1', 'm:3', 'M:2', 'm:3', 'M:2', 'M:2']),
        ModalityType.MajorBluesPentatonic:
        ModalitySpec(ModalityType.MajorBluesPentatonic,
                     ['P:1', 'M:2', 'm:3', 'M:2', 'M:2', 'm:3']),
        ModalityType.MinorPentatonic:
        ModalitySpec(ModalityType.MinorPentatonic,
                     ['P:1', 'm:3', 'M:2', 'M:2', 'm:3', 'M:2']),
    }

    @staticmethod
    def create(modality_type, modal_index=0):
        if modality_type not in PentatonicModality.PENTATONIC_MODALITIES:
            raise Exception('Type parameter is not diatonic.')
        if modality_type not in PentatonicModality.MODALITY_DEFINITION_MAP:
            raise Exception(
                'Illegal diatonic modality value: {0} - Check Modality_definition_map'
                .format(str(modality_type)))
        return Modality(
            PentatonicModality.MODALITY_DEFINITION_MAP[modality_type],
            modal_index)

    @staticmethod
    def pentatonic_modality_types_as_string_array():
        answer = [str(t) for t in PentatonicModality.PENTATONIC_MODALITIES]
        return answer

    @staticmethod
    def find_modality(tones):
        answers = list()
        if len(tones) == 5:
            for t in [ModalityType.MajorPentatonic]:
                modality_spec = PentatonicModality.MODALITY_DEFINITION_MAP[t]

                p1 = Interval.parse('P:1')
                for scale_start in range(0, 5):
                    intervals = [p1] + [
                        Interval.calculate_tone_interval(
                            tones[(scale_start + i) % 5],
                            tones[(scale_start + i + 1) % 5])
                        for i in range(0, len(tones))
                    ]
                    if intervals == modality_spec.incremental_intervals:
                        answers.append(
                            PentatonicModality.create(t, (-scale_start) %
                                                      len(tones)))
        return answers