New Case Study:See how Anthropic automated 95% of dependency reviews with Socket.Learn More
Socket
Sign inDemoInstall
Socket

tonal-distance

Package Overview
Dependencies
Maintainers
1
Versions
30
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

tonal-distance - npm Package Compare versions

Comparing version 0.69.7 to 1.0.0-0

test/distance.spec.js

258

build/index.js

@@ -5,44 +5,213 @@ 'use strict';

var tonalPitch = require('tonal-pitch');
var index = require('tonal-note/index');
var index$1 = require('tonal-interval/index');
/**
* Functions to calculate distances between notes
* [![npm version](https://img.shields.io/npm/v/tonal-distance.svg)](https://www.npmjs.com/package/tonal-distance)
* [![tonal](https://img.shields.io/badge/tonal-distance-yellow.svg)](https://github.com/danigb/tonal/tree/master/packages/tonal/distance)
*
* Transpose notes by intervals and find distances between notes
*
* @example
* // using node's require
* var distance = require('tonal-distance')
* distance.interval('C4', 'G4') // => '5P'
*
* @example
* // using ES6 import
* import { interval, semitones } from 'tonal-distance'
* import { interval, semitones, transpose } from 'tonal-distance'
* semitones('C' ,'D') // => 2
* interval('C4', 'G4') // => '5P'
* transpose('C4', 'P5') // => 'G4'
*
* // included in tonal facade
* const tonal = require('tonal');
* tonal.distance.transpose('C4', 'P5')
* tonal.distance.transposeBy('P5', 'C4')
*
* @module distance
*/
// substract two pitches
function substr (a, b) {
if (!a || !b || a[1].length !== b[1].length) return null
var f = tonalPitch.fifths(b) - tonalPitch.fifths(a);
if (tonalPitch.isPC(a)) return tonalPitch.pitch(f, -Math.floor(f * 7 / 12), 1)
var o = tonalPitch.focts(b) - tonalPitch.focts(a);
var d = tonalPitch.height(b) - tonalPitch.height(a) < 0 ? -1 : 1;
return tonalPitch.pitch(d * f, d * o, d)
// Map from letter step to number of fifths starting from 'C':
// { C: 0, D: 2, E: 4, F: -1, G: 1, A: 3, B: 5 }
const FIFTHS = [0, 2, 4, -1, 1, 3, 5];
// Given a number of fifths, return the octaves they span
const fOcts = f => Math.floor(f * 7 / 12);
// Get the number of octaves it span each step
const FIFTH_OCTS = FIFTHS.map(fOcts);
const encode = ({ step, alt, oct, dir = 1 }) => {
const f = FIFTHS[step] + 7 * alt;
if (oct === null) return [dir * f];
const o = oct - FIFTH_OCTS[step] - 4 * alt;
return [dir * f, dir * o];
};
// We need to get the steps from fifths
// Fifths for CDEFGAB are [ 0, 2, 4, -1, 1, 3, 5 ]
// We add 1 to fifths to avoid negative numbers, so:
// for ['F', 'C', 'G', 'D', 'A', 'E', 'B'] we have:
const STEPS = [3, 0, 4, 1, 5, 2, 6];
// Return the number of fifths as if it were unaltered
function unaltered(f) {
const i = (f + 1) % 7;
return i < 0 ? 7 + i : i;
}
const decode = (f, o, dir) => {
const step = STEPS[unaltered(f)];
const alt = Math.floor((f + 1) / 7);
if (o === undefined) return { step, alt, dir };
const oct = o + 4 * alt + FIFTH_OCTS[step];
return { step, alt, oct, dir };
};
const memo = (fn, cache = {}) => str => cache[str] || (cache[str] = fn(str));
const encoder = props$$1 =>
memo(str => {
const p = props$$1(str);
return p.name === null ? null : encode(p);
});
const encodeNote = encoder(index.props);
const encodeIvl = encoder(index$1.props);
/**
* Find the interval between two pitches. Both pitches MUST be of the same type:
* Transpose a note by an interval. The note can be a pitch class.
*
* This function can be partially applied.
*
* @param {String} note
* @param {String} interval
* @return {String} the transposed note
* @example
* import { tranpose } from 'tonal-distance'
* transpose('d3', '3M') // => 'F#3'
* // it works with pitch classes
* transpose('D', '3M') // => 'F#'
* // can be partially applied
* ['C', 'D', 'E', 'F', 'G'].map(transpose('M3)) // => ['E', 'F#', 'G#', 'A', 'B']
*/
function transpose(note, interval) {
if (arguments.length === 1) return i => transpose(note, i);
const n = encodeNote(note);
const i = encodeIvl(interval);
if (n === null || i === null) return null;
const tr = n.length === 1 ? [n[0] + i[0]] : [n[0] + i[0], n[1] + i[1]];
return index.build(decode(tr[0], tr[1]));
}
/**
* Transpose a pitch class by a number of perfect fifths.
*
* It can be partially applied.
*
* - notes: it returns the interval between the first and the second
* - pitch classes: it returns the __ascending__ interval between both
* - intervals: substract one from the other
* @function
* @param {String} pitchClass - the pitch class
* @param {Integer} fifhts - the number of fifths
* @return {String} the transposed pitch class
*
* @example
* import { trFifths } from 'tonal-transpose'
* [0, 1, 2, 3, 4].map(trFifths('C')) // => ['C', 'G', 'D', 'A', 'E']
* // or using tonal
* tonal.trFifths('G4', 1) // => 'D'
*/
function trFifths(note, fifths) {
if (arguments.length === 1) return f => trFifths(note, f);
const n = encodeNote(note);
if (n === null) return null;
return index.build(decode(n[0] + fifths));
}
/**
* Get the distance in fifths between pitch classes
*
* Can be partially applied.
*
* @param {String} to - note or pitch class
* @param {String} from - note or pitch class
*/
function fifths(from, to) {
if (arguments.length === 1) return to => fifths(from, to);
const f = encodeNote(from);
const t = encodeNote(to);
if (t === null || f === null) return null;
return t[0] - f[0];
}
/**
* The same as transpose with the arguments inverted.
*
* Can be partially applied.
*
* @param {String} note
* @param {String} interval
* @return {String} the transposed note
* @example
* import { tranposeBy } from 'tonal-distance'
* transposeBy('3m', '5P') // => '7m'
*/
function transposeBy(interval, note) {
if (arguments.length === 1) return n => transpose(n, interval);
return transpose(note, interval);
}
const isDescending = e => e[0] * 7 + e[1] * 12 < 0;
const decodeIvl = i =>
isDescending(i) ? decode(-i[0], -i[1], -1) : decode(i[0], i[1], 1);
function addIntervals(ivl1, ivl2, dir) {
const i1 = encodeIvl(ivl1);
const i2 = encodeIvl(ivl2);
if (i1 === null || i2 === null) return null;
const i = [i1[0] + dir * i2[0], i1[1] + dir * i2[1]];
return index$1.build(decodeIvl(i));
}
/**
* Add two intervals
*
* Can be partially applied.
*
* @param {String} interval1
* @param {String} interval2
* @return {String} the resulting interval
* @example
* import { add } from 'tonal-distance'
* add('3m', '5P') // => '7m'
*/
function add(ivl1, ivl2) {
if (arguments.length === 1) return i2 => add(ivl1, i2);
return addIntervals(ivl1, ivl2, 1);
}
/**
* Subtract two intervals
*
* Can be partially applied
*
* @param {String} minuend
* @param {String} subtrahend
* @return {String} interval diference
*/
function subtract(ivl1, ivl2) {
if (arguments.length === 1) return i2 => add(ivl1, i2);
return addIntervals(ivl1, ivl2, -1);
}
/**
* Find the interval between two pitches. It works with pitch classes
* (both must be pitch classes and the interval is always ascending)
*
* Can be partially applied
*
* @param {Pitch|String} from - distance from
* @param {Pitch|String} to - distance to
* @return {Interval} the distance between pitches
* @param {String} from - distance from
* @param {String} to - distance to
* @return {String} the interval distance
*
* @example
* var distance = require('tonal-distance')
* distance.interval('C2', 'C3') // => 'P8'
* distance.interval('G', 'B') // => 'M3'
* import { interval } from 'tonal-distance'
* interval('C2', 'C3') // => 'P8'
* interval('G', 'B') // => 'M3'
*
* // or use tonal

@@ -52,9 +221,12 @@ * var tonal = require('tonal')

*/
function interval (a, b) {
if (arguments.length === 1) return function (b) { return interval(a, b) }
var pa = tonalPitch.asPitch(a);
var pb = tonalPitch.asPitch(b);
var i = substr(pa, pb);
// if a and b are in array notation, no conversion back
return a === pa && b === pb ? i : tonalPitch.strIvl(i)
function interval(from, to) {
if (arguments.length === 1) return t => interval(from, t);
const f = encodeNote(from);
const t = encodeNote(to);
if (f === null || t === null || f.length !== t.length) return null;
const d =
f.length === 1
? [t[0] - f[0], -Math.floor((t[0] - f[0]) * 7 / 12)]
: [t[0] - f[0], t[1] - f[1]];
return index$1.build(decodeIvl(d));
}

@@ -64,2 +236,3 @@

* Get the distance between two notes in semitones
*
* @param {String|Pitch} from - first note

@@ -74,8 +247,21 @@ * @param {String|Pitch} to - last note

*/
function semitones (a, b) {
var i = substr(tonalPitch.asPitch(a), tonalPitch.asPitch(b));
return i ? tonalPitch.height(i) : null
function semitones(from, to) {
if (arguments.length === 1) return t => semitones(from, t);
const f = index.props(from);
const t = index.props(to);
return f.midi !== null && t.midi !== null
? t.midi - f.midi
: f.chroma !== null && t.chroma !== null
? (t.chroma - f.chroma + 12) % 12
: null;
}
exports.transpose = transpose;
exports.trFifths = trFifths;
exports.fifths = fifths;
exports.transposeBy = transposeBy;
exports.addIntervals = addIntervals;
exports.add = add;
exports.subtract = subtract;
exports.interval = interval;
exports.semitones = semitones;
/**
* Functions to calculate distances between notes
* [![npm version](https://img.shields.io/npm/v/tonal-distance.svg)](https://www.npmjs.com/package/tonal-distance)
* [![tonal](https://img.shields.io/badge/tonal-distance-yellow.svg)](https://github.com/danigb/tonal/tree/master/packages/tonal/distance)
*
* Transpose notes by intervals and find distances between notes
*
* @example
* // using node's require
* var distance = require('tonal-distance')
* distance.interval('C4', 'G4') // => '5P'
*
* @example
* // using ES6 import
* import { interval, semitones } from 'tonal-distance'
* import { interval, semitones, transpose } from 'tonal-distance'
* semitones('C' ,'D') // => 2
* interval('C4', 'G4') // => '5P'
* transpose('C4', 'P5') // => 'G4'
*
* // included in tonal facade
* const tonal = require('tonal');
* tonal.distance.transpose('C4', 'P5')
* tonal.distance.transposeBy('P5', 'C4')
*
* @module distance
*/
import { isPC, fifths, focts, pitch, height, asPitch, strIvl } from 'tonal-pitch'
import { props as nprops, build as nbuild } from "tonal-note/index";
import { props as iprops, build as ibuild } from "tonal-interval/index";
// substract two pitches
function substr (a, b) {
if (!a || !b || a[1].length !== b[1].length) return null
var f = fifths(b) - fifths(a)
if (isPC(a)) return pitch(f, -Math.floor(f * 7 / 12), 1)
var o = focts(b) - focts(a)
var d = height(b) - height(a) < 0 ? -1 : 1
return pitch(d * f, d * o, d)
// Map from letter step to number of fifths starting from 'C':
// { C: 0, D: 2, E: 4, F: -1, G: 1, A: 3, B: 5 }
const FIFTHS = [0, 2, 4, -1, 1, 3, 5];
// Given a number of fifths, return the octaves they span
const fOcts = f => Math.floor(f * 7 / 12);
// Get the number of octaves it span each step
const FIFTH_OCTS = FIFTHS.map(fOcts);
const encode = ({ step, alt, oct, dir = 1 }) => {
const f = FIFTHS[step] + 7 * alt;
if (oct === null) return [dir * f];
const o = oct - FIFTH_OCTS[step] - 4 * alt;
return [dir * f, dir * o];
};
// We need to get the steps from fifths
// Fifths for CDEFGAB are [ 0, 2, 4, -1, 1, 3, 5 ]
// We add 1 to fifths to avoid negative numbers, so:
// for ['F', 'C', 'G', 'D', 'A', 'E', 'B'] we have:
const STEPS = [3, 0, 4, 1, 5, 2, 6];
// Return the number of fifths as if it were unaltered
function unaltered(f) {
const i = (f + 1) % 7;
return i < 0 ? 7 + i : i;
}
const decode = (f, o, dir) => {
const step = STEPS[unaltered(f)];
const alt = Math.floor((f + 1) / 7);
if (o === undefined) return { step, alt, dir };
const oct = o + 4 * alt + FIFTH_OCTS[step];
return { step, alt, oct, dir };
};
const memo = (fn, cache = {}) => str => cache[str] || (cache[str] = fn(str));
const encoder = props =>
memo(str => {
const p = props(str);
return p.name === null ? null : encode(p);
});
const encodeNote = encoder(nprops);
const encodeIvl = encoder(iprops);
/**
* Find the interval between two pitches. Both pitches MUST be of the same type:
* Transpose a note by an interval. The note can be a pitch class.
*
* This function can be partially applied.
*
* @param {String} note
* @param {String} interval
* @return {String} the transposed note
* @example
* import { tranpose } from 'tonal-distance'
* transpose('d3', '3M') // => 'F#3'
* // it works with pitch classes
* transpose('D', '3M') // => 'F#'
* // can be partially applied
* ['C', 'D', 'E', 'F', 'G'].map(transpose('M3)) // => ['E', 'F#', 'G#', 'A', 'B']
*/
export function transpose(note, interval) {
if (arguments.length === 1) return i => transpose(note, i);
const n = encodeNote(note);
const i = encodeIvl(interval);
if (n === null || i === null) return null;
const tr = n.length === 1 ? [n[0] + i[0]] : [n[0] + i[0], n[1] + i[1]];
return nbuild(decode(tr[0], tr[1]));
}
/**
* Transpose a pitch class by a number of perfect fifths.
*
* It can be partially applied.
*
* - notes: it returns the interval between the first and the second
* - pitch classes: it returns the __ascending__ interval between both
* - intervals: substract one from the other
* @function
* @param {String} pitchClass - the pitch class
* @param {Integer} fifhts - the number of fifths
* @return {String} the transposed pitch class
*
* @example
* import { trFifths } from 'tonal-transpose'
* [0, 1, 2, 3, 4].map(trFifths('C')) // => ['C', 'G', 'D', 'A', 'E']
* // or using tonal
* tonal.trFifths('G4', 1) // => 'D'
*/
export function trFifths(note, fifths) {
if (arguments.length === 1) return f => trFifths(note, f);
const n = encodeNote(note);
if (n === null) return null;
return nbuild(decode(n[0] + fifths));
}
/**
* Get the distance in fifths between pitch classes
*
* Can be partially applied.
*
* @param {String} to - note or pitch class
* @param {String} from - note or pitch class
*/
export function fifths(from, to) {
if (arguments.length === 1) return to => fifths(from, to);
const f = encodeNote(from);
const t = encodeNote(to);
if (t === null || f === null) return null;
return t[0] - f[0];
}
/**
* The same as transpose with the arguments inverted.
*
* Can be partially applied.
*
* @param {String} note
* @param {String} interval
* @return {String} the transposed note
* @example
* import { tranposeBy } from 'tonal-distance'
* transposeBy('3m', '5P') // => '7m'
*/
export function transposeBy(interval, note) {
if (arguments.length === 1) return n => transpose(n, interval);
return transpose(note, interval);
}
const isDescending = e => e[0] * 7 + e[1] * 12 < 0;
const decodeIvl = i =>
isDescending(i) ? decode(-i[0], -i[1], -1) : decode(i[0], i[1], 1);
export function addIntervals(ivl1, ivl2, dir) {
const i1 = encodeIvl(ivl1);
const i2 = encodeIvl(ivl2);
if (i1 === null || i2 === null) return null;
const i = [i1[0] + dir * i2[0], i1[1] + dir * i2[1]];
return ibuild(decodeIvl(i));
}
/**
* Add two intervals
*
* Can be partially applied.
*
* @param {String} interval1
* @param {String} interval2
* @return {String} the resulting interval
* @example
* import { add } from 'tonal-distance'
* add('3m', '5P') // => '7m'
*/
export function add(ivl1, ivl2) {
if (arguments.length === 1) return i2 => add(ivl1, i2);
return addIntervals(ivl1, ivl2, 1);
}
/**
* Subtract two intervals
*
* Can be partially applied
*
* @param {String} minuend
* @param {String} subtrahend
* @return {String} interval diference
*/
export function subtract(ivl1, ivl2) {
if (arguments.length === 1) return i2 => add(ivl1, i2);
return addIntervals(ivl1, ivl2, -1);
}
/**
* Find the interval between two pitches. It works with pitch classes
* (both must be pitch classes and the interval is always ascending)
*
* Can be partially applied
*
* @param {Pitch|String} from - distance from
* @param {Pitch|String} to - distance to
* @return {Interval} the distance between pitches
* @param {String} from - distance from
* @param {String} to - distance to
* @return {String} the interval distance
*
* @example
* var distance = require('tonal-distance')
* distance.interval('C2', 'C3') // => 'P8'
* distance.interval('G', 'B') // => 'M3'
* import { interval } from 'tonal-distance'
* interval('C2', 'C3') // => 'P8'
* interval('G', 'B') // => 'M3'
*
* // or use tonal

@@ -47,9 +216,12 @@ * var tonal = require('tonal')

*/
export function interval (a, b) {
if (arguments.length === 1) return function (b) { return interval(a, b) }
var pa = asPitch(a)
var pb = asPitch(b)
var i = substr(pa, pb)
// if a and b are in array notation, no conversion back
return a === pa && b === pb ? i : strIvl(i)
export function interval(from, to) {
if (arguments.length === 1) return t => interval(from, t);
const f = encodeNote(from);
const t = encodeNote(to);
if (f === null || t === null || f.length !== t.length) return null;
const d =
f.length === 1
? [t[0] - f[0], -Math.floor((t[0] - f[0]) * 7 / 12)]
: [t[0] - f[0], t[1] - f[1]];
return ibuild(decodeIvl(d));
}

@@ -59,2 +231,3 @@

* Get the distance between two notes in semitones
*
* @param {String|Pitch} from - first note

@@ -69,5 +242,11 @@ * @param {String|Pitch} to - last note

*/
export function semitones (a, b) {
var i = substr(asPitch(a), asPitch(b))
return i ? height(i) : null
export function semitones(from, to) {
if (arguments.length === 1) return t => semitones(from, t);
const f = nprops(from);
const t = nprops(to);
return f.midi !== null && t.midi !== null
? t.midi - f.midi
: f.chroma !== null && t.chroma !== null
? (t.chroma - f.chroma + 12) % 12
: null;
}

26

package.json
{
"name": "tonal-distance",
"version": "0.69.7",
"description": "Find distances between musical notes",
"version": "1.0.0-0",
"description": "Transpose notes and find intervals between them",
"keywords": [
"transpose",
"interval",
"distance",
"semitones",
"music",
"theory",
"interval",
"distance",
"tonal"
],
"scripts": {
"test": "jest --coverage"
"test": "jest --coverage",
"docs": "jsdoc2md -d 1 --name-format --member-index-format grouped index.js > README.md"
},

@@ -20,4 +23,15 @@ "main": "build/index.js",

"dependencies": {
"tonal-pitch": "^0.69.7"
"tonal-interval": "^1.0.0-0",
"tonal-note": "^1.0.0-0"
},
"babel": {
"presets": [
"es2015"
]
},
"jest": {
"transformIgnorePatterns": [
"<rootDir>/node_modules/(?!tonal)"
]
}
}

@@ -1,57 +0,180 @@

# tonal-distance [![npm version](https://img.shields.io/npm/v/tonal-distance.svg)](https://www.npmjs.com/package/tonal-distance)
<a name="module_distance"></a>
[![tonal](https://img.shields.io/badge/tonal-distance-yellow.svg)](https://www.npmjs.com/browse/keyword/tonal)
# distance
[![npm version](https://img.shields.io/npm/v/tonal-distance.svg)](https://www.npmjs.com/package/tonal-distance)
[![tonal](https://img.shields.io/badge/tonal-distance-yellow.svg)](https://github.com/danigb/tonal/tree/master/packages/tonal/distance)
`tonal-distance` is a collection of functions to find distances between music notes.
Transpose notes by intervals and find distances between notes
This is part of [tonal](https://www.npmjs.com/package/tonal) music theory library.
**Example**
```js
// using ES6 import
import { interval, semitones, transpose } from 'tonal-distance'
semitones('C' ,'D') // => 2
interval('C4', 'G4') // => '5P'
transpose('C4', 'P5') // => 'G4'
You can install via npm: `npm i --save tonal-distance`
// included in tonal facade
const tonal = require('tonal');
tonal.distance.transpose('C4', 'P5')
tonal.distance.transposeBy('P5', 'C4')
```
## API Reference
* [distance](#module_distance)
* [`.transpose(note, interval)`](#module_distance.transpose) ⇒ <code>String</code>
* [`.trFifths(pitchClass, fifhts)`](#module_distance.trFifths) ⇒ <code>String</code>
* [`.fifths(to, from)`](#module_distance.fifths)
* [`.transposeBy(note, interval)`](#module_distance.transposeBy) ⇒ <code>String</code>
* [`.add(interval1, interval2)`](#module_distance.add) ⇒ <code>String</code>
* [`.subtract(minuend, subtrahend)`](#module_distance.subtract) ⇒ <code>String</code>
* [`.interval(from, to)`](#module_distance.interval) ⇒ <code>String</code>
* [`.semitones(from, to)`](#module_distance.semitones) ⇒ <code>Integer</code>
<dl>
<dt><a href="#distance">distance(from, to)</a> ⇒ <code>Interval</code></dt>
<dd><p>Find distance between two pitches. Both pitches MUST be of the same type.
Distances between pitch classes always returns ascending intervals.
Distances between intervals substract one from the other.</p>
</dd>
<dt><a href="#distInSemitones">distInSemitones(from, to)</a> ⇒ <code>Integer</code></dt>
<dd><p>Get the distance between two notes in semitones</p>
</dd>
<dt><a href="#interval">interval()</a></dt>
<dd><p>An alias for <code>distance</code></p>
</dd>
</dl>
<a name="module_distance.transpose"></a>
<a name="distance"></a>
## `distance.transpose(note, interval)` ⇒ <code>String</code>
Transpose a note by an interval. The note can be a pitch class.
## distance(from, to) ⇒ <code>Interval</code>
Find distance between two pitches. Both pitches MUST be of the same type.
Distances between pitch classes always returns ascending intervals.
Distances between intervals substract one from the other.
This function can be partially applied.
**Kind**: global function
**Returns**: <code>Interval</code> - the distance between pitches
**Kind**: static method of [<code>distance</code>](#module_distance)
**Returns**: <code>String</code> - the transposed note
| Param | Type |
| --- | --- |
| note | <code>String</code> |
| interval | <code>String</code> |
**Example**
```js
import { tranpose } from 'tonal-distance'
transpose('d3', '3M') // => 'F#3'
// it works with pitch classes
transpose('D', '3M') // => 'F#'
// can be partially applied
['C', 'D', 'E', 'F', 'G'].map(transpose('M3)) // => ['E', 'F#', 'G#', 'A', 'B']
```
<a name="module_distance.trFifths"></a>
## `distance.trFifths(pitchClass, fifhts)` ⇒ <code>String</code>
Transpose a pitch class by a number of perfect fifths.
It can be partially applied.
**Kind**: static method of [<code>distance</code>](#module_distance)
**Returns**: <code>String</code> - the transposed pitch class
| Param | Type | Description |
| --- | --- | --- |
| from | <code>Pitch</code> &#124; <code>String</code> | distance from |
| to | <code>Pitch</code> &#124; <code>String</code> | distance to |
| pitchClass | <code>String</code> | the pitch class |
| fifhts | <code>Integer</code> | the number of fifths |
**Example**
```js
import { distance } from 'tonal-distance'
distance('C2', 'C3') // => 'P8'
distance('G', 'B') // => 'M3'
import { trFifths } from 'tonal-transpose'
[0, 1, 2, 3, 4].map(trFifths('C')) // => ['C', 'G', 'D', 'A', 'E']
// or using tonal
tonal.trFifths('G4', 1) // => 'D'
```
<a name="module_distance.fifths"></a>
## `distance.fifths(to, from)`
Get the distance in fifths between pitch classes
Can be partially applied.
**Kind**: static method of [<code>distance</code>](#module_distance)
| Param | Type | Description |
| --- | --- | --- |
| to | <code>String</code> | note or pitch class |
| from | <code>String</code> | note or pitch class |
<a name="module_distance.transposeBy"></a>
## `distance.transposeBy(note, interval)` ⇒ <code>String</code>
The same as transpose with the arguments inverted.
Can be partially applied.
**Kind**: static method of [<code>distance</code>](#module_distance)
**Returns**: <code>String</code> - the transposed note
| Param | Type |
| --- | --- |
| note | <code>String</code> |
| interval | <code>String</code> |
**Example**
```js
import { tranposeBy } from 'tonal-distance'
transposeBy('3m', '5P') // => '7m'
```
<a name="module_distance.add"></a>
## `distance.add(interval1, interval2)` ⇒ <code>String</code>
Add two intervals
Can be partially applied.
**Kind**: static method of [<code>distance</code>](#module_distance)
**Returns**: <code>String</code> - the resulting interval
| Param | Type |
| --- | --- |
| interval1 | <code>String</code> |
| interval2 | <code>String</code> |
**Example**
```js
import { add } from 'tonal-distance'
add('3m', '5P') // => '7m'
```
<a name="module_distance.subtract"></a>
## `distance.subtract(minuend, subtrahend)` ⇒ <code>String</code>
Subtract two intervals
Can be partially applied
**Kind**: static method of [<code>distance</code>](#module_distance)
**Returns**: <code>String</code> - interval diference
| Param | Type |
| --- | --- |
| minuend | <code>String</code> |
| subtrahend | <code>String</code> |
<a name="module_distance.interval"></a>
## `distance.interval(from, to)` ⇒ <code>String</code>
Find the interval between two pitches. It works with pitch classes
(both must be pitch classes and the interval is always ascending)
Can be partially applied
**Kind**: static method of [<code>distance</code>](#module_distance)
**Returns**: <code>String</code> - the interval distance
| Param | Type | Description |
| --- | --- | --- |
| from | <code>String</code> | distance from |
| to | <code>String</code> | distance to |
**Example**
```js
import { interval } from 'tonal-distance'
interval('C2', 'C3') // => 'P8'
interval('G', 'B') // => 'M3'
// or use tonal
var tonal = require('tonal')
tonal.distance('M2', 'P5') // => 'P4'
tonal.distance.interval('M2', 'P5') // => 'P4'
```
<a name="distInSemitones"></a>
<a name="module_distance.semitones"></a>
## distInSemitones(from, to) ⇒ <code>Integer</code>
## `distance.semitones(from, to)` ⇒ <code>Integer</code>
Get the distance between two notes in semitones
**Kind**: global function
**Kind**: static method of [<code>distance</code>](#module_distance)
**Returns**: <code>Integer</code> - the distance in semitones or null if not valid notes

@@ -61,17 +184,11 @@

| --- | --- | --- |
| from | <code>String</code> &#124; <code>Pitch</code> | first note |
| to | <code>String</code> &#124; <code>Pitch</code> | last note |
| from | <code>String</code> \| <code>Pitch</code> | first note |
| to | <code>String</code> \| <code>Pitch</code> | last note |
**Example**
```js
import { distInSemitones } from 'tonal-distance'
distInSemitones('C3', 'A2') // => -3
import { semitones } from 'tonal-distance'
semitones('C3', 'A2') // => -3
// or use tonal
tonal.distInSemitones('C3', 'G3') // => 7
tonal.distance.semitones('C3', 'G3') // => 7
```
<a name="interval"></a>
## interval()
An alias for `distance`
**Kind**: global function
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc