{
"cells": [
{
"cell_type": "code",
"execution_count": 113,
"metadata": {},
"outputs": [],
"source": [
"import automuse as am\n",
"import automuse.chord as chord\n",
"import automuse.modes as modes\n",
"from automuse.scale import scale\n",
"from automuse import note_i2s\n",
"from automuse import note_s2i\n",
"from automuse import interval_s2i\n",
"from automuse import interval_i2s\n",
"from automuse import name_interval\n",
"from automuse import reach\n",
"from automuse import same_class"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# An Introduction to Music Theory\n",
"\n",
"This notebook covers the basics of music theory, namely intervals, modes, scales, and chords."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Intervals\n",
"\n",
"An **interval** is the musical distance between two notes. An interval between two notes is **harmonic** if these notes are played at the same time; otherwise, the interval is **melodic**. These intervals are important -- all music is the combination of melodies and harmonies.\n",
"\n",
"The **half-step**, (also **semitone**) is the smallest apartness commonly used in Western music. A **whole-step** equals two half-steps.\n",
"\n",
"In integer notation, an interval is denoted by a simple integer. In text however, intervals are often communicated by name. The following sections explain how these names are constructed."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Generic Intervals\n",
"\n",
"**Generic intervals** measure the difference between the staff positions of two notes. In practice, this measure ignores accidentals: $\\mathrm{C}\\text{--}\\mathrm{D}$ are one genetic step apart, but so are $\\mathrm{C}\\text{--}\\mathrm{D}\\#$. This is because $\\mathrm{D}$ and $\\mathrm{D}\\#$ are on the same staff.\n",
"\n",
"Generic intervals, like people, have names. \n",
"For example, $\\mathrm{C}\\text{--}\\mathrm{D}$ are a second apart. The following table lists these names.\n",
"\n",
"|Step difference|Name of Interval|\n",
"|-|-|\n",
"| 0 | First / Prime / Unison |\n",
"| 1 | Second |\n",
"| 2 | Third |\n",
"| 3 | Fourth |\n",
"| 4 | Fifth |\n",
"| 5 | Sixth |\n",
"| 6 | Seven |\n",
"| 7 | Eight |"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Specific Intervals\n",
"\n",
"**Specific intervals** are measured on both staff and half steps. For example, recall that $\\mathrm{C}\\text{--}\\mathrm{D}$ are a generic second apart. Because they are also 2 half steps apart, they are a _major second_ apart in specific intervals. $\\mathrm{B}\\text{--}\\mathrm{C}$ on the other hand are a _minor second_ apart because they are a genetic second apart while being just one half step apart.\n",
"\n",
"The terms \"major\" and \"minor\" refer to the interval's **quality**. Only the 2nds, 3rds, 4ths, 6ths, and 7ths can be **major interval**s. The rest (1sts, 4ths, 5ths, and 8ths) are **perfect interval**s instead.\n",
"\n",
"A **minor interval** has 1 fewer half step than a major interval. An **augmented interval** has one more than a major interval. An **augmented interval** has one more half step than a perfect interval. A **diminished interval** has one less half step. Minor intervals can be diminished by subtracting yet another half-step. The following figure illustrates these relations:\n",
"\n",
"\n",
"\n",
"Some examples follow:\n",
"\n",
"|Apartness|Name|\n",
"|-|-|\n",
"| 0 | Prime |\n",
"| 1 | Minor Second |\n",
"| 3 | Minor Third |\n",
"| 5 | Perfect Fourth |\n",
"| 7 | Perfect Fifth |\n",
"| 9 | Major Sixth |\n",
"| 11 | Major Seventh |\n",
"| 12 | Perfect Eighth (Perfect octave) |\n",
"\n",
"To add, **compound intervals** are larger than an octave. These intervals are named by adding 7 to the generic interval."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Following these rules, there exists a injective mapping between names and integers (difference in semitones). A set of utilities in AutoMuse work with this fact:\n",
"\n",
"* `INTERVALS` maps every name to an integer.\n",
"\n",
"* `name_interval` takes two notes and returns a name for their interval."
]
},
{
"cell_type": "code",
"execution_count": 114,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Augmented 2 is 3 in semitones.\n",
"The interval from C# to D is minor 2\n",
"The interval from C to D is major 2\n",
"The interval from C to D# is augmented 2\n",
"The interval from B to C is minor 2\n"
]
}
],
"source": [
"print(f\"Augmented 2 is {am.INTERVALS[\"augmented 2\"]} in semitones.\")\n",
"_test_pairs: list[tuple[str, str]] = [\n",
" ('C#', 'D'),\n",
" ('C', 'D'),\n",
" ('C', 'D#'),\n",
" ('B', 'C'),\n",
"]\n",
"\n",
"for __from, to in _test_pairs:\n",
" print(f\"The interval from {__from}\"\n",
" f\" to {to} is\"\n",
" f\" {name_interval(__from, to)}\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"#### Interval Cheat Sheet\n",
"\n",
"The following generated cheat sheet gives possible names for an interval in half steps. To find out the actual name, choose one that corresponds to the general interval."
]
},
{
"cell_type": "code",
"execution_count": 115,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"
\n",
"\n",
"| Half-Step Difference | Name | Half-Step Difference | Name |
\n",
"\n",
"\n",
"| 0 | diminished 2 | 7 | diminished 6 |
\n",
"| 0 | prime 1 | 7 | perfect 5 |
\n",
"| 1 | augmented 1 | 8 | augmented 5 |
\n",
"| 1 | minor 2 | 8 | minor 6 |
\n",
"| 2 | diminished 3 | 9 | diminished 7 |
\n",
"| 2 | major 2 | 9 | major 6 |
\n",
"| 3 | augmented 2 | 10 | augmented 6 |
\n",
"| 3 | minor 3 | 10 | minor 7 |
\n",
"| 4 | diminished 4 | 11 | diminished 1 |
\n",
"| 4 | major 3 | 11 | diminished 8 |
\n",
"| 5 | augmented 3 | 11 | major 7 |
\n",
"| 5 | perfect 4 | 12 | augmented 7 |
\n",
"| 6 | augmented 4 | 12 | perfect 8 |
\n",
"| 6 | diminished 5 | 13 | augmented 8 |
\n",
"\n",
"
"
],
"text/plain": [
"'\\n\\n| Half-Step Difference | Name | Half-Step Difference | Name |
\\n\\n\\n| 0 | diminished 2 | 7 | diminished 6 |
\\n| 0 | prime 1 | 7 | perfect 5 |
\\n| 1 | augmented 1 | 8 | augmented 5 |
\\n| 1 | minor 2 | 8 | minor 6 |
\\n| 2 | diminished 3 | 9 | diminished 7 |
\\n| 2 | major 2 | 9 | major 6 |
\\n| 3 | augmented 2 | 10 | augmented 6 |
\\n| 3 | minor 3 | 10 | minor 7 |
\\n| 4 | diminished 4 | 11 | diminished 1 |
\\n| 4 | major 3 | 11 | diminished 8 |
\\n| 5 | augmented 3 | 11 | major 7 |
\\n| 5 | perfect 4 | 12 | augmented 7 |
\\n| 6 | augmented 4 | 12 | perfect 8 |
\\n| 6 | diminished 5 | 13 | augmented 8 |
\\n\\n
'"
]
},
"execution_count": 115,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"persephone: list[tuple[int, str]]\\\n",
" = sorted([(b, a) for a, b\n",
" in am.INTERVALS.items()])\n",
"\n",
"import tabulate\n",
"tabulate.tabulate((p := persephone,\n",
" [(*x, *y) for (x, y)\n",
" in zip(p[:int(len(p)/2)],\n",
" p[int(len(p)/2):])])[1],\n",
"\n",
" headers=[\"Half-Step Difference\",\n",
" \"Name\"]*2,\n",
" tablefmt=\"html\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The table shows an interesting fact: that the same semitone difference can have different names, depending on the generic interval. This is an instance of **enharmonic equivalence** in music where two things sound the same yet write differently."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Reaching by Intervals\n",
"\n",
"The `reach` function \"reaches up\" from a given note by either an integer or an interval name.\n",
"\n",
"To demonstrate the correctness of `reach`, assuming that `name_interval` is correct, let's reach from every note to every other note by the name of the interval between them."
]
},
{
"cell_type": "code",
"execution_count": 116,
"metadata": {},
"outputs": [],
"source": [
"for name_x in am.NOTE_NAMES:\n",
" for name_y in am.NOTE_NAMES:\n",
" same_class(reach(name_x, name_interval(name_x, name_y)), name_y)\n"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Scales\n",
"\n",
"A **scale** is an ordered sequence of notes. In western music, a scale (particularly a **diatonic scale**) is constructed by counting notes from a starting note. This starting note is its **home note** (or _**tonic**_); the pattern of counting is either its **key** (if the pattern is major or minor) or its **mode** (otherwise). These inconsistencies are due to historical reasons.\n",
"\n",
"Mathematically, both keys and modes are patterns of intervals. These patterns can be found in `automuse.modes`.\n",
"\n",
"Parts of this section are based on [MusicTheory.net](www.musictheory.net) and [_Play Guitar in 14 Days_](https://troynelsonmusic.com/)."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Aside: Major and Minor\n",
"\n",
"Scales, for example the **major scale**s and **minor scale**s, are constructed from a pattern of intervals. In this context, the word **key** can communicate two things: (a) if a scale is major or minor (e.g. \"the scale is in major key\"), or (b) the tonic (e.g. \"the scale is in the key of A\"). Better not think too hard about it.\n",
"\n",
"Here, you see another use of the terms \"major\" and \"minor\". These two terms can apply to a great many things, but one rule remains consistent: a _sound_, be it a chord, a scale, or a juxtaposition of two pitches, is major if it is stable or bright; on the other hand, sounds that are not are minor."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Aside: Scale Degrees\n",
"\n",
"The **scale degree** of a note is its position on a scale, up from the tonic. The $i^\\mathrm{th}$ degree is denoted as $\\hat{i}$.\n",
"\n",
"For a heptatonic scale, these degrees are named:\n",
"\n",
"| Position | Name |\n",
"| -------- | ----------------------- |\n",
"| 8 (out of scale) | Tonic (again) |\n",
"| 7 | Leading Tone / Subtonic |\n",
"| 6 | Submediant |\n",
"| 5 | Dominant |\n",
"| 4 | Subdominant |\n",
"| 3 | Mediant |\n",
"| 2 | Supertonic |\n",
"| 1 | Tonic |\n",
"\n",
"Note that the submediant ($\\hat{6}$) does not lead into the mediant ($\\hat{3}$); rather, it is the \"mediant\" of the dominant ($\\hat{5}$) and the subtonic ($\\hat{7}$).\n",
"\n",
"Also, the $\\hat{7}$ note can have two names: If it is one half step below the tonic, then it is the leading tone; if it is one whole step below the tonic, then it is the subtonic. These names are often used interchangeably."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Constructing Scales\n",
"\n",
"To construct a scale from a tonic and a mode, start counting semitones from the tonic according to the mode. The `scale.scale` function constructs scales in this manner.\n",
"\n",
"At minimum, the function requires a tonic and a mode."
]
},
{
"cell_type": "code",
"execution_count": 117,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"['C0', 'D0', 'E0', 'F0', 'G0', 'A0', 'B0']"
]
},
"execution_count": 117,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"scale(\"C\", modes.MAJOR)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Alternatively, setting `use_offsets=True` lets `scale` use semitone offsets instead of intervals. This is also known as the integer notation."
]
},
{
"cell_type": "code",
"execution_count": 118,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"['C0', 'D0', 'E0', 'F0', 'G0', 'A0', 'B0']"
]
},
"execution_count": 118,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"scale(\"C\", [0, 2, 4, 5, 7, 9, 11], use_offsets=True)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"A set of functions, `modes.intervals_to_offsets` and `modes.offsets_to_intervals`, translate between intervals and offset notations:"
]
},
{
"cell_type": "code",
"execution_count": 119,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"True"
]
},
"execution_count": 119,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"modes.offsets_to_intervals(\n",
" modes.intervals_to_offsets(modes.MAJOR)) ==\\\n",
" modes.MAJOR"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Relative Scales\n",
"\n",
"Relative scales contain the same notes, though not arranged in the same order. To build evidence that `scale` is correct, see if it correctly constructs relatives.\n",
"\n",
"Here's every pair of relatives from the circle of fifthssss. Ssss. Hisssss. For more on the circle, see the [Circle of Fifths](./circle_of_fifths.ipynb) tutorial."
]
},
{
"cell_type": "code",
"execution_count": 120,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Interval from C to A is major 6, or 9 half steps.\n",
"Interval from G to E is major 6, or 9 half steps.\n",
"Interval from D to B is major 6, or 9 half steps.\n",
"Interval from A to F# is major 6, or 9 half steps.\n",
"Interval from E to C# is major 6, or 9 half steps.\n",
"Interval from B to G# is major 6, or 9 half steps.\n",
"Interval from F# to D# is major 6, or 9 half steps.\n",
"Interval from C# to A# is major 6, or 9 half steps.\n",
"Interval from G# to F is diminished 7, or 9 half steps.\n",
"Interval from D# to C is diminished 7, or 9 half steps.\n",
"Interval from A# to G is diminished 7, or 9 half steps.\n"
]
}
],
"source": [
"from automuse import same_class, name_interval\n",
"\n",
"CIRCLE_OF_LIFE: list[tuple[str, str]]\\\n",
" = [(\"C\", \"A\"),\n",
" (\"G\", \"E\"),\n",
" (\"D\", \"B\"),\n",
" (\"A\", \"F#\"),\n",
" (\"E\", \"C#\"),\n",
" (\"B\", \"G#\"),\n",
" (\"F#\", \"D#\"),\n",
" (\"C#\", \"A#\"),\n",
" (\"G#\", \"F\"),\n",
" (\"D#\", \"C\"),\n",
" (\"A#\", \"G\")]\n",
"\n",
"for major_key, minor_key in CIRCLE_OF_LIFE:\n",
" assert same_class(\n",
" scale(major_key, modes.MAJOR),\n",
" scale(minor_key, modes.MINOR),)\n",
"\n",
" interval_name: str = name_interval(major_key, minor_key)\n",
"\n",
" print(f\"Interval from {major_key} to {minor_key}\"\n",
" f\" is {name_interval(major_key, minor_key)},\"\n",
" f\" or {am.INTERVALS[interval_name]} half steps.\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Pentatonic Scales\n",
"\n",
"A pentatonic scale is a scale with five tones instead of seven. To construct a pentatonic scale from a major heptatonic scale, take items at $\\{1, 2, 3, 5, 6\\}$ (assuming 1-based indexing). Constructing pentatonic minor scales is similar, but uses $\\{1, 3, 4, 5, 7\\}$ instead.\n",
"\n",
"The `pentatonic_major` and `pentatonic_minor` functions construct pentatonic \"modes\", which can then be used to construct pentatonic scales. These functions can also scales from other modes.\n",
"\n",
"You can also construct scales from two pre-made modes, `MAJOR_PENTATONIC` and `MINOR_PENTATONIC`."
]
},
{
"cell_type": "code",
"execution_count": 121,
"metadata": {},
"outputs": [],
"source": [
"assert modes.MAJOR_PENTATONIC == modes.pentatonic_major(modes.MAJOR)\n",
"assert modes.MINOR_PENTATONIC == modes.pentatonic_minor(modes.MINOR)"
]
},
{
"cell_type": "code",
"execution_count": 122,
"metadata": {},
"outputs": [],
"source": [
"assert same_class(\n",
" scale(\"C\", modes.pentatonic_major(modes.MAJOR)),\n",
" ['C', 'D', 'E', 'G', 'A']\n",
")\n",
"\n",
"assert same_class(\n",
" scale(\"A\", modes.pentatonic_minor(modes.MINOR)),\n",
" ['A', 'C', 'D', 'E', 'G']\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Blues Scales\n",
"\n",
"A blues minor scale is the pentatonic scale with an extra flat $\\hat{5}$. For example, whereas the A pentatonic scale is $[\\text{A}, \\text{C}, \\text{D}, \\text{E}, \\text{G}]$, the A blues scale is $[\\text{A}, \\text{C}, \\text{D}, \\text{D}\\#, \\text{E}, \\text{G}]$. A blues major scale gets a flat third instead.\n",
"\n",
"The `blues_major` and `blues_minor` functions construct blue modes. As usual, pre-made modes for major and minor are also available."
]
},
{
"cell_type": "code",
"execution_count": 123,
"metadata": {},
"outputs": [],
"source": [
"assert modes.MAJOR_BLUES == modes.blues_major(modes.MAJOR)\n",
"assert modes.MINOR_BLUES == modes.blues_minor(modes.MINOR)\n",
"\n",
"assert same_class(\n",
" scale('C', modes.blues_major(modes.MAJOR)),\n",
" ['C', 'D', 'D#', 'E', 'G', 'A']\n",
")\n",
"\n",
"assert same_class(\n",
" scale('A', modes.blues_minor(modes.MINOR)),\n",
" ['A', 'C', 'D', 'D#', 'E', 'G']\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Harmonic and Melodic Minors\n",
"\n",
"I see your harmonic minor and raise you a melodic minor.\n",
"\n",
"A harmonic minor has a raised $\\hat{7}$. A melodic minor has both its $\\hat{6}$ and $\\hat{7}$ raised.\n",
"\n",
"The `harmonic_minor` and `melodic_minor` functions construct these modes."
]
},
{
"cell_type": "code",
"execution_count": 124,
"metadata": {},
"outputs": [],
"source": [
"assert modes.MINOR_HARMONIC == modes.harmonic_minor(modes.MINOR)\n",
"assert modes.MINOR_MELODIC == modes.melodic_minor(modes.MINOR)\n",
"\n",
"assert same_class(\n",
" scale(\"A\", modes.melodic_minor(modes.MINOR)),\n",
" ['A', 'B', 'C', 'D', 'E', 'F#', 'G#'])\n",
"\n",
"assert same_class(\n",
" scale(\"A\", modes.harmonic_minor(modes.MINOR)),\n",
" ['A', 'B', 'C', 'D', 'E', 'F', 'G#'])"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Augmented and Diminished Scales\n",
"\n",
"There are two kinds of diminished scales: the\n",
"typical whole-half diminished scale (of \n",
"intervals $[2, 1, 2, 1, ...]$) and the half-whole diminished scale (of intervals $[1, 2, 1, 2, ...]$).\n"
]
},
{
"cell_type": "code",
"execution_count": 125,
"metadata": {},
"outputs": [],
"source": [
"from automuse.modes import DIMINISHED_WHOLE_HALF\n",
"from automuse.modes import DIMINISHED_HALF_WHOLE\n",
"from automuse.modes import AUGMENTED"
]
},
{
"cell_type": "code",
"execution_count": 126,
"metadata": {},
"outputs": [],
"source": [
"assert same_class(\n",
" scale(\"A\", modes.DIMINISHED_HALF_WHOLE),\n",
" ['A', 'A#', 'C', 'C#', 'D#', 'E', 'F#', 'G'])"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Chords\n",
"\n",
"Simply put, a **chord** is a collection of tones. There are several ways to construct harmonically interesting chords. Let's start with the triad:\n",
"\n",
"As you know, a triad is a triple of topological spaces $\\{P, A, B\\};~A,B\\prec P$ where $P=\\mathrm{int}(A)\\cup\\mathrm{int}(B)$.\n",
"\n",
"To construct a triad, select a scale then pick its $\\hat{1}$, $\\hat{3}$, and $\\hat{5}$. The $\\hat{1}$ is the root of the chord and remains so even if it is, after the triad is transformed, no longer the lowest note."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Constructing a Triad\n",
"\n",
"AutoMuse implements two ways to construct chords. Let us begin with the easiest: `chord.chord`. This function implements all you need to construct a chord from specifications.\n",
"\n",
"To see how it works, let's construct this abomination of a C chord:"
]
},
{
"cell_type": "code",
"execution_count": 127,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"['E4', 'F4', 'G4', 'A4', 'A#4', 'B4', 'C5', 'E5']"
]
},
"execution_count": 127,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"chord.chord(\n",
" tonic=\"C4\",\n",
" mode=modes.IONIAN,\n",
" order=0,\n",
" add=[6, 8, 10],\n",
" sus=[0],\n",
" sharp=[2],\n",
" flat=[4],\n",
" raw_offsets=[\"augmented 1\"]\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Alternatively, you can construct chords with `scale.scale`. `modes` has several options that specify chords, instead of scales:"
]
},
{
"cell_type": "code",
"execution_count": 128,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"['C4', 'E4', 'G4']"
]
},
"execution_count": 128,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"scale(\"C4\", modes.TRIAD_MAJOR)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Seventh Chords\n",
"\n",
"A seventh chord combines a triad with an interval of a seventh. The `chord.seventh` function construct seventh chords.\n",
"\n",
"You can simple pick $\\hat{1}$, $\\hat{3}$, $\\hat{5}$, and $\\hat{7}$ from a scale, or choose the quality for the $\\hat{7}$:"
]
},
{
"cell_type": "code",
"execution_count": 129,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"['C0', 'D#0', 'F#0', 'A#0']\n",
"['C0', 'E0', 'G0', 'B0']\n"
]
}
],
"source": [
"print(chord.seventh(\"C\", modes.LOCRIAN))\n",
"print(chord.seventh(\"C\", modes.LYDIAN))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Diatonic Triads; Better Constructors\n",
"\n",
"Every major and minor scale have seven **diatonic triads**, which are formed from notes on that scale.\n",
"\n",
"The first triad uses the 1st, 3rd, and 5th notes counting up from the root (the root itself being the 1st). The nth triad instead counts from the nth note instead.\n",
"\n",
"Both `chord.chord` and `chord.seventh` can construct chords of the given `order`. To make $\\text{ii}^7$, write:"
]
},
{
"cell_type": "code",
"execution_count": 130,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"['D0', 'F0', 'A0', 'C1']"
]
},
"execution_count": 130,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"chord.seventh(\"C\", modes.MAJOR, order=1)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Neapolitan Chords\n",
"\n",
"To construct a Neapolitan chord, construct a major triad (1, 3, 5) starting with a flat second of the major scale. We can see that it is equivalent to the second triad on a Phrygian scale:"
]
},
{
"cell_type": "code",
"execution_count": 140,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"['A#0', 'D1', 'F1']\n",
"['A#0', 'D1', 'F1']\n"
]
}
],
"source": [
"print(chord.chord(\"A\", modes.PHRYGIAN, order=1))\n",
"print(chord.neapolitan_chord(\"A\", modes.MAJOR))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Only because it is possible ... you can construct a Neapolitan chord on the Phrygian scale."
]
},
{
"cell_type": "code",
"execution_count": 143,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"['A0', 'C#1', 'E1']\n"
]
}
],
"source": [
"print(chord.neapolitan_chord(\"A\", modes.PHRYGIAN))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Inverting Triads\n",
"\n",
"Like inverting intervals, inverting a triad moves the lowest note up an octave.\n",
"\n",
"When the **bass note**, the lowest note in the triad, is its root, the triad is in **root position**. Inverting the triad once moves it into **first inversion**; inverting again moves it to the **second inversion**. After inversion, the chord's base note remains the same, but its bass note becomes the new lowest note.\n",
"\n",
"Alternatively, the degree of inversion can be denoted by its bass note. For example, the F major triad is $[\\text{F}, \\text{A}, \\text{C}]$; its first inversion $[\\text{A}, \\text{C}, \\text{F}]$ can be denoted by $\\text{F}/\\text{A}$. This notation is called a **slash chord**.\n",
"\n",
"The `automuse.transform` module contains several such transforms. It supports both notations by `invert_chord_by` and `invert_triad_to`."
]
},
{
"cell_type": "code",
"execution_count": 146,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"['E4', 'G4', 'C4']\n",
"['E4', 'G4', 'C4']\n"
]
}
],
"source": [
"from automuse.transforms import invert_chord_to, invert_chord_by\n",
"_c_4_triad = chord.chord(\"C4\", modes.MAJOR)\n",
"print(invert_chord_to(_c_4_triad, _c_4_triad[1]))\n",
"print(invert_chord_by(_c_4_triad, 1))"
]
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.12.10"
}
},
"nbformat": 4,
"nbformat_minor": 2
}