public class Metronome extends Object implements Snapshot
A beat management tool. Tell it what BPM you want, and it will compute beat, bar, and phrase timestamps
accordingly. If you only need a single piece of information, you can obtain it directly from the metronome.
If you need to work with two or more values, you need to call getSnapshot() and ask the snapshot
for them or you will see inconsistent results, since time will move on between each question you ask the
metronome itself.
Inspired by Jeff Rose's work in Overtone.
| Constructor and Description |
|---|
Metronome() |
| Modifier and Type | Method and Description |
|---|---|
void |
adjustStart(long ms)
Adds a number of milliseconds to the start time of the metronome.
|
static double |
beatsToMilliseconds(long beats,
double tempo)
Calculate the number of milliseconds taken by the specified number of beats at the specified tempo.
|
double |
distanceFromBar()
Determine how far in time the metronome is from its closest bar boundary.
|
double |
distanceFromBeat()
Determine how far in time the metronome is from the closest beat.
|
double |
distanceFromPhrase()
Determine how far in time the metronome is from its closest phrase boundary.
|
static double |
enhancedPhase(long markerNumber,
double markerPhase,
double desiredRatio)
Helper function to calculate phase with respect to multiples or fractions of a marker
(beat, bar, or phrase), given the phase with respect to that marker, the marker number,
and the desired ratio.
|
static double |
enhancedPhase(long markerNumber,
double markerPhase,
long numerator,
long denominator)
Helper function to calculate phase with respect to multiples or fractions of a marker
(beat, bar, or phrase), given the phase with respect to that marker, the marker number,
and the desired ratio.
|
static double |
findClosestDelta(double delta)
Figures out the least disruptive phase shift that ends up in a target phase.
|
long |
getBar()
Get the current bar being played.
|
double |
getBarInterval()
Get the number of milliseconds a bar lasts given the current configuration and tempo.
|
double |
getBarPhase()
Determine the distance traveled into the current bar as a phase number in the range [0.0, 1.0).
|
int |
getBarsPerPhrase()
Get the number of bars per phrase in the metronome's beat grid.
|
int |
getBarWithinPhrase()
Return the current bar number relative to the start of the phrase: the phrase starts with bar 1, and the
range goes up to the value of
getBarsPerPhrase(). |
long |
getBeat()
Get the current beat being played.
|
double |
getBeatInterval()
Get the number of milliseconds a beat lasts given the current tempo.
|
double |
getBeatPhase()
Determine the distance traveled into the current beat as a phase number in the range [0.0, 1.0).
|
int |
getBeatsPerBar()
Get the number of beats per bar in the metronome's beat grid.
|
int |
getBeatWithinBar()
Return the current beat number relative to the start of the bar: the down beat is 1, and the range
goes up to the value of
getBeatsPerBar(). |
int |
getBeatWithinPhrase()
Return the current beat number relative to the start of the phrase: the phrase starts with beat 1, and
the range goes up to the value of
getBeatsPerBar() times getBarsPerPhrase(). |
long |
getInstant()
Checks when a snapshot was taken; since you are working with a live metronome, always returns the current
time.
|
String |
getMarker()
Returns the current count of the metronome as "phrase.bar.beat".
|
long |
getPhrase()
Get the current phrase being played.
|
double |
getPhraseInterval()
Get the number of milliseconds a phrase lasts given the current configuration and tempo.
|
double |
getPhrasePhase()
Determine the distance traveled into the current phrase as a phase number in the range [0.0, 1.0).
|
Snapshot |
getSnapshot()
Take a snapshot of the current beat, bar, phrase, and phase state, so coherent calculations about them can be
performed with respect to a static point in time.
|
Snapshot |
getSnapshot(long instant)
Take a snapshot of the beat, bar, phrase, and phase state that the metronome would have at the specified
millisecond timestamp, so coherent calculations about them can be performed with respect to that static point
in time.
|
long |
getStartTime()
Returns the time at which this metronome was effectively started (tempo changes will shift this, as will
a variety of methods which adjust the timeline).
|
double |
getTempo()
Get the tempo at which this metronome is running.
|
long |
getTimeOfBar(long bar)
Determine the millisecond timestamp at which a particular bar will occur.
|
long |
getTimeOfBeat(long beat)
Determine the millisecond timestamp at which a particular beat will occur.
|
long |
getTimeOfPhrase(long phrase)
Determine the millisecond timestamp at which a particular phrase will occur.
|
boolean |
isDownBeat()
Checks whether the current beat is the first beat in its bar.
|
boolean |
isPhraseStart()
Checks whether the current beat is the first beat in its phrase.
|
void |
jumpToBar(long bar)
Restarts the metronome at the start of the specified bar, keeping the beat phase unchanged in case
it is being synchronized to an external source.
|
void |
jumpToBeat(long beat)
Restarts the metronome at the beginning of the specified beat number.
|
void |
jumpToPhrase(long phrase)
Restarts the metronome at the start of the specified phrase, keeping the beat phase unchanged in case
it is being synchronized to an external source.
|
static long |
markerNumber(long instant,
long start,
double interval)
Helper function to calculate the beat, bar, or phrase number in effect at a given instant (in milliseconds)
given a timeline starting point (start, also in milliseconds), and the interval (also in milliseconds) between
beats, bars, or phrases.
|
static double |
markerPhase(long instant,
long start,
double interval)
Helper function to calculate the beat, bar, or phrase phase at a given instant (in milliseconds),
given a timeline starting point (start, also in milliseconds), and the interval (also in milliseconds) between
beats, bars, or phrases.
|
static double |
normalizePhase(double phase)
Ensure that a phase falls in the range [0.0, 1.0).
|
void |
setBarPhase(double phase)
Nudge the metronome so that it has reached the specified part of its current bar.
|
void |
setBarsPerPhrase(int barsPerPhrase)
Establish a new number of bars per phrase in the metronome's beat grid.
|
void |
setBeatPhase(double phase)
Nudge the metronome so that it has reached the specified part of its current beat.
|
void |
setBeatsPerBar(int beatsPerBar)
Establish a new number of beats per bar in the metronome's beat grid.
|
void |
setPhrasePhase(double phase)
Nudge the metronome so that it has reached the specified part of its current phrase.
|
void |
setTempo(double bpm)
Establish a new tempo for the metronome.
|
String |
toString() |
public long getStartTime()
getStartTime in interface Snapshotpublic void adjustStart(long ms)
ms - the number of milliseconds to add to the start timepublic double getTempo()
public void setTempo(double bpm)
bpm - the number of beats per minute at which the metronome should now runpublic int getBeatsPerBar()
getBeatsPerBar in interface Snapshotpublic void setBeatsPerBar(int beatsPerBar)
beatsPerBar - a positive number of beats per bar being countedIllegalArgumentException - if beatsPerBar is not greater than zeropublic int getBarsPerPhrase()
getBarsPerPhrase in interface Snapshotpublic void setBarsPerPhrase(int barsPerPhrase)
barsPerPhrase - a positive number of bars per phrase being countedIllegalArgumentException - if barsPerPhrase is not greater than zeropublic static double beatsToMilliseconds(long beats,
double tempo)
beats - the number of beats to timetempo - the number of that play in a minutepublic static long markerNumber(long instant,
long start,
double interval)
instant - the time (in milliseconds) for which a marker number is desiredstart - the time (in milliseconds) at which the metronome started countinginterval - the time (in milliseconds) between markerspublic static double markerPhase(long instant,
long start,
double interval)
instant - the time (in milliseconds) for which a marker phase is desiredstart - the time (in milliseconds) at which the metronome started countinginterval - the time (in milliseconds) between markerspublic static double enhancedPhase(long markerNumber,
double markerPhase,
double desiredRatio)
Helper function to calculate phase with respect to multiples or fractions of a marker
(beat, bar, or phrase), given the phase with respect to that marker, the marker number,
and the desired ratio. A desiredRatio of 1.0 returns the phase unchanged;
0.5 (1/2) oscillates twice as fast, 0.75 (3/4) oscillates 4 times every 3 markers...
See the Ratios illustration in the Afterglow documentation for more details with graphs.
Only positive values were considered for the ratio when writing this algorithm, the results you'll get if you pass in zero or a negative value, are not likely meaningful.
markerNumber - the current marker number being considered, as returned by markerNumber(long, long, double)markerPhase - the current phase with respect to the marker, as returned by markerPhase(long, long, double)desiredRatio - the ratio by which to oscillate the phaseenhancedPhase(long, double, long, long)public static double enhancedPhase(long markerNumber,
double markerPhase,
long numerator,
long denominator)
Helper function to calculate phase with respect to multiples or fractions of a marker (beat, bar, or phrase), given the phase with respect to that marker, the marker number, and the desired ratio. A ration of 1/1 returns the phase unchanged; 1/2 oscillates twice as fast, 3/4 oscillates 4 times every 3 markers...
See the Ratios illustration in the Afterglow documentation for more details with graphs.
Only positive values were considered for the numerator and denominator when writing this algorithm, the results you'll get if you pass in zero or a negative value, are not likely meaningful.
markerNumber - the current marker number being considered, as returned by markerNumber(long, long, double)markerPhase - the current phase with respect to the marker, as returned by markerPhase(long, long, double)numerator - over how many markers should an oscillation cycle spandenominator - how many oscillations should occur in that spanenhancedPhase(long, double, double)public static double normalizePhase(double phase)
phase - a phase value that may require normalization to within the unit rangepublic double getBeatInterval()
getBeatInterval in interface Snapshotpublic double getBarInterval()
getBarInterval in interface Snapshotpublic double getPhraseInterval()
getPhraseInterval in interface Snapshotpublic long getBeat()
public void jumpToBeat(long beat)
beat - the beat to which the metronome should jump; the first beat is beat 1public long getTimeOfBeat(long beat)
getTimeOfBeat in interface Snapshotbeat - the number of the beat whose start time is desiredpublic double getBeatPhase()
getBeatPhase in interface Snapshotpublic static double findClosestDelta(double delta)
delta - the amount to be added to our current phase to achieve a desired phasepublic void setBeatPhase(double phase)
phase - the desired beat phase, in the range [0.0, 1.0).public long getBar()
public void jumpToBar(long bar)
bar - the bar to which the metronome should jump; the first bar is bar 1public long getTimeOfBar(long bar)
getTimeOfBar in interface Snapshotbar - the number of the bar whose start time is desiredpublic double getBarPhase()
getBarPhase in interface Snapshotpublic void setBarPhase(double phase)
phase - the desired bar phase, in the range [0.0, 1.0).public long getPhrase()
public void jumpToPhrase(long phrase)
phrase - the phrase to which the metronome should jump; the first phrase is phrase 1public long getTimeOfPhrase(long phrase)
getTimeOfPhrase in interface Snapshotphrase - the number of the phrase whose start time is desiredpublic double getPhrasePhase()
getPhrasePhase in interface Snapshotpublic void setPhrasePhase(double phase)
phase - the desired phrase phase, in the range [0.0, 1.0).public Snapshot getSnapshot()
public Snapshot getSnapshot(long instant)
instant - the point in time which this snapshot should capturepublic String getMarker()
public long getInstant()
getSnapshot() and work
with that instead.getInstant in interface Snapshotpublic int getBeatWithinBar()
getBeatsPerBar().getBeatWithinBar in interface Snapshotpublic boolean isDownBeat()
isDownBeat in interface Snapshottrue we are currently in the first beat of a barpublic int getBeatWithinPhrase()
getBeatsPerBar() times getBarsPerPhrase().getBeatWithinPhrase in interface Snapshotpublic boolean isPhraseStart()
isPhraseStart in interface Snapshottrue if we are currently in the first beat of a phrasepublic int getBarWithinPhrase()
getBarsPerPhrase().getBarWithinPhrase in interface Snapshotpublic double distanceFromBeat()
distanceFromBeat in interface Snapshotpublic double distanceFromBar()
distanceFromBar in interface Snapshotpublic double distanceFromPhrase()
distanceFromPhrase in interface SnapshotCopyright © 2018 Deep Symmetry, LLC. All rights reserved.