示例#1
0
Author: Nikolay Lysenko
"""

import itertools
import math
import random
from dataclasses import dataclass
from typing import Any, Optional

from sinethesizer.utils.music_theory import get_note_to_position_mapping

from .music_theory import (N_SEMITONES_PER_OCTAVE, TONE_ROW_LEN,
                           get_smallest_intervals_between_pitch_classes,
                           invert_tone_row, revert_tone_row, validate_tone_row)

NOTE_TO_POSITION_MAPPING = get_note_to_position_mapping()
SMALLEST_INTERVALS_MAPPING = get_smallest_intervals_between_pitch_classes()

SUPPORTED_DURATIONS = [0.25, 0.5, 0.75, 1.0, 1.5, 2.0, 3.0, 4.0, 6.0]
DURATION_SPLITS = {
    6.0: [[4.0, 2.0], [3.0, 3.0]],
    4.0: [[2.0, 2.0], [3.0, 1.0]],
    3.0: [[2.0, 1.0], [1.5, 1.5]],
    2.0: [[1.0, 1.0], [1.5, 0.5]],
    1.5: [[1.0, 0.5], [0.75, 0.75]],
    1.0: [[0.5, 0.5], [0.75, 0.25]],
    0.75: [[0.5, 0.25]],
    0.5: [[0.25, 0.25]],
    0.25: [[0.25]],
}
示例#2
0
"""
Help to work with notions from music theory.

Author: Nikolay Lysenko
"""

from typing import List, NamedTuple

from sinethesizer.utils.music_theory import get_note_to_position_mapping

NOTE_TO_POSITION = get_note_to_position_mapping()
TONIC_TRIAD_DEGREES = (1, 3, 5)


class ScaleElement(NamedTuple):
    """A pitch from a diatonic scale."""

    note: str
    position_in_semitones: int
    position_in_degrees: int
    degree: int
    is_from_tonic_triad: bool


class Scale:
    """A diatonic scale."""
    def __init__(self, tonic: str, scale_type: str):
        """
        Initialize an instance.

        :param tonic: