119 lines
3.0 KiB
C++
119 lines
3.0 KiB
C++
#ifndef _MUSIC_PROGRESSION_HPP_
|
|
#define _MUSIC_PROGRESSION_HPP_
|
|
#ifndef _COMMON_BLOCK_HPP_
|
|
#include <common/block.hpp>
|
|
#endif
|
|
#ifndef _MUSIC_CHORD_HPP_
|
|
#include <music/chord.hpp>
|
|
#endif
|
|
#ifndef _MUSIC_SCALES_HPP_
|
|
#include <music/scales.hpp>
|
|
#endif
|
|
|
|
namespace Music
|
|
{
|
|
class Progression : public Block<Chord>
|
|
{
|
|
public:
|
|
typedef enum ProgressionType{PII_V_I,PV_V,PI_VI_II_V,PIII_VI_II_V};
|
|
void createProgression(ProgressionType progressionType,const Note &rootNote);
|
|
void play(MIDIOutputDevice &midiOut);
|
|
private:
|
|
void handleIII_VI_II_V(const Note &rootNote);
|
|
void handleII_V_I(const Note &rootNote);
|
|
void handleI_VI_II_V(const Note &rootNote);
|
|
void handleV_V(const Note &rootNote);
|
|
};
|
|
|
|
void Progression::createProgression(ProgressionType progressionType,const Note &rootNote)
|
|
{
|
|
remove();
|
|
switch(progressionType)
|
|
{
|
|
case PII_V_I :
|
|
handleII_V_I(rootNote);
|
|
break;
|
|
case PV_V :
|
|
handleV_V(rootNote);
|
|
break;
|
|
case PI_VI_II_V :
|
|
handleI_VI_II_V(rootNote);
|
|
break;
|
|
case PIII_VI_II_V :
|
|
handleIII_VI_II_V(rootNote);
|
|
break;
|
|
}
|
|
}
|
|
|
|
inline
|
|
void Progression::handleII_V_I(const Note &rootNote)
|
|
{
|
|
LydianScale lydianScale;
|
|
MixolydianScale mixolydianScale;
|
|
DorianScale dorianScale;
|
|
|
|
lydianScale.setRoot(rootNote);
|
|
dorianScale.setRoot(rootNote.getSecond());
|
|
mixolydianScale.setRoot(rootNote.getFifth());
|
|
insert(&dorianScale.getI7Chord()); // insert the minor7/II chord
|
|
insert(&mixolydianScale.getI7Chord()); // insert the dominant/V chord
|
|
insert(&lydianScale.getI7Chord()); // insert the maj7th/I chord
|
|
}
|
|
|
|
|
|
inline
|
|
void Progression::handleI_VI_II_V(const Note &rootNote)
|
|
{
|
|
LydianScale lydianScale;
|
|
MixolydianScale mixolydianScale;
|
|
DorianScale dorianScale;
|
|
|
|
lydianScale.setRoot(rootNote);
|
|
mixolydianScale.setRoot(rootNote.getSixth());
|
|
dorianScale.setRoot(rootNote.getSecond());
|
|
insert(&lydianScale.getI7Chord());
|
|
insert(&mixolydianScale.getI7Chord());
|
|
insert(&dorianScale.getI7Chord());
|
|
mixolydianScale.setRoot(rootNote.getFifth());
|
|
insert(&mixolydianScale.getI7Chord());
|
|
}
|
|
|
|
inline
|
|
void Progression::handleIII_VI_II_V(const Note &rootNote)
|
|
{
|
|
DorianScale dorianScale;
|
|
PhrygianScale phrygianScale;
|
|
MixolydianScale mixolydianScale;
|
|
phrygianScale.setRoot(rootNote.getThird());
|
|
insert(&phrygianScale.getI7Chord());
|
|
mixolydianScale.setRoot(rootNote.getSixth());
|
|
insert(&mixolydianScale.getI7Chord());
|
|
dorianScale.setRoot(rootNote.getSecond());
|
|
insert(&dorianScale.getI7Chord());
|
|
mixolydianScale.setRoot(rootNote.getFifth());
|
|
insert(&mixolydianScale.getI7Chord());
|
|
}
|
|
|
|
inline
|
|
void Progression::handleV_V(const Note &rootNote)
|
|
{
|
|
MixolydianScale mixolydianScale;
|
|
mixolydianScale.setRoot(rootNote.getFifth());
|
|
insert(&mixolydianScale.getI7Chord()); // insert the dominant7/V chord
|
|
mixolydianScale.setRoot(rootNote);
|
|
insert(&mixolydianScale.getI7Chord()); // insert the dominant7/I chord
|
|
}
|
|
|
|
inline
|
|
void Progression::play(MIDIOutputDevice &midiOut)
|
|
{
|
|
for(int index=0;index<size();index++)
|
|
{
|
|
operator[](index).play(midiOut);
|
|
::OutputDebugString(operator[](index).toString()+String("\n"));
|
|
::Sleep(750);
|
|
}
|
|
}
|
|
};
|
|
#endif
|