Metadata-Version: 2.1
Name: musiclib
Version: 2.5.1
Summary: set of tools to work with scales, modes, modulations, chord progressions, voice leading, rhythm and more
Author-email: Alexander Rodionov <tandav@tandav.me>
Project-URL: source, https://github.com/tandav/musiclib
Project-URL: issues, https://gitlab.tandav.me/tandav/notes/-/issues/?label_name=musiclib
Project-URL: release notes, https://github.com/tandav/musiclib/releases
Requires-Python: >=3.11
Description-Content-Type: text/markdown
Requires-Dist: colortool>=0.6.0
Requires-Dist: opseq>=0.1.2
Requires-Dist: mido>=1.3.0
Requires-Dist: svg.py
Requires-Dist: numpy
Provides-Extra: dev
Requires-Dist: bumpver==2023.1129; extra == "dev"
Requires-Dist: hypothesis==6.98.8; extra == "dev"
Requires-Dist: pre-commit==3.6.2; extra == "dev"
Requires-Dist: pytest==8.0.1; extra == "dev"
Requires-Dist: pytest-asyncio==0.23.5; extra == "dev"
Requires-Dist: pytest-cov==4.1.0; extra == "dev"
Provides-Extra: rtmidi
Requires-Dist: python-rtmidi; extra == "rtmidi"

![GitHub tag (latest by date)](https://img.shields.io/github/v/tag/tandav/musiclib)

# musiclib
set of tools to work with scales, modes, modulations, chord progressions, voice leading, rhythm and more

## install
### install from [pypi](https://pypi.org/project/musiclib/)
```sh
pip install musiclib
```

### or install the latest version from github
```sh
pip install git+https://github.com/tandav/musiclib
```

### development
```sh
pip install -e .[dev]
```

## examples

```py
>>> from musiclib.scale import Scale
>>> from musiclib.noteset import SpecificNoteSet
>>> from musiclib.noterange import NoteRange

>>> scale = Scale.from_name('C', 'major')

>>> scale.root
Note('C')

>>> scale.notes
frozenset({Note('C'),
           Note('D'),
           Note('E'),
           Note('F'),
           Note('G'),
           Note('A'),
           Note('B')})

>>> scale.bits
'101011010101'

>>> scale.intervals
frozenset({0, 2, 4, 5, 7, 9, 11})
```

```py
Scale.from_name('C', 'phrygian')
```
![](docs/svg_examples/C_phrygian.svg)

```py
SpecificNoteSet.from_str('C1_e1_G1_C2_b2_E3')
```
![](docs/svg_examples/C1_e1_G1_C2_b2_E3.svg)

```py
NoteRange(SpecificNote('C', 1), SpecificNote('B', 3))
```
![](docs/svg_examples/noterange_C1_B3.svg)
