#include <LedControl.h>
#define NOTE_C5 523
#define NOTE_CS5 554
#define NOTE_D5 587
#define NOTE_DS5 622
#define NOTE_E5 659
#define NOTE_F5 698
#define NOTE_FS5 740
#define NOTE_G5 784
#define NOTE_GS5 831
#define NOTE_A5 880
#define NOTE_AS5 932
#define NOTE_B5 988
#define NOTE_C6 1046
#define NOTE_CS6 1108
#define NOTE_D6 1174
#define NOTE_DS6 1244
#define NOTE_E6 1318
#define NOTE_F6 1396
#define NOTE_FS6 1479
#define NOTE_G6 1567
#define NOTE_GS6 1661
#define NOTE_A6 1760
#define NOTE_AS6 1864
#define NOTE_B6 1975
int DIN=4;
int CS=3;
int CLK=2;
LedControl lc=LedControl(DIN, CLK, CS,0);
class NoteTiming
{
public:
unsigned long startTime;
int note;
unsigned long endTime;
bool played=false;
};
int notes[24][2] = {
{53, NOTE_C5},
{52, NOTE_CS5},
{51, NOTE_D5},
{50, NOTE_DS5},
{49, NOTE_E5},
{48, NOTE_F5},
{47, NOTE_FS5},
{46, NOTE_G5},
{45, NOTE_GS5},
{44, NOTE_A5},
{43, NOTE_AS5},
{42, NOTE_B5},
{41, NOTE_C6},
{40, NOTE_CS6},
{39, NOTE_D6},
{38, NOTE_DS6},
{37, NOTE_E6},
{36, NOTE_F6},
{35, NOTE_FS6},
{34, NOTE_G6},
{33, NOTE_GS6},
{32, NOTE_A6},
{31, NOTE_AS6},
{30, NOTE_B6},
};
int SegmentNumbers[10][7]={
{1,1,1,1,1,1,0},
{0,1,1,0,0,0,0},
{1,1,0,1,1,0,1},
{1,1,1,1,0,0,1},
{0,1,1,0,0,1,1},
{1,0,1,1,0,1,1},
{1,0,1,1,1,1,1},
{1,1,1,0,0,0,0},
{1,1,1,1,1,1,1},
{1,1,1,1,0,1,1}
};
int recordingScreen[8][8]={
{0,0,0,1,1,0,0,0},
{0,0,1,1,1,1,0,0},
{0,1,1,1,1,1,1,0},
{1,1,1,1,1,1,1,1},
{1,1,1,1,1,1,1,1},
{0,1,1,1,1,1,1,0},
{0,0,1,1,1,1,0,0},
{0,0,0,1,1,0,0,0}
};
int playBackScreen[8][8]={
{1,1,0,0,0,0,0,0},
{1,1,1,1,0,0,0,0},
{1,1,1,1,1,1,0,0},
{1,1,1,1,1,1,1,1},
{1,1,1,1,1,1,1,1},
{1,1,1,1,1,1,0,0},
{1,1,1,1,0,0,0,0},
{1,1,0,0,0,0,0,0}
};
int segmentDisplayOrder[7]={A3,A4,A5,A6,A7,A8,A9};
int segmentDisplayDigits[3]={A0,A1,A2};
NoteTiming recordedMusic[500];
int BPMN=120;
int BPM = 60000/BPMN;
unsigned long lastMetronome=0;
int metronomeCounter=0;
unsigned long buttonHeldTime[24]{};
bool isPlaybackMode=false;
bool isRecording=false;
int recordIndex=0;
unsigned long recordStartTime;
unsigned long playbackStartTime;
void setup() {
recordedMusic[0].startTime=0;
recordedMusic[0].note=523;
recordedMusic[0].endTime=500;
recordedMusic[1].startTime=101;
recordedMusic[1].note=587;
recordedMusic[1].endTime=500;
recordedMusic[2].startTime=201;
recordedMusic[2].note=1174;
recordedMusic[2].endTime=500;
pinMode(13, OUTPUT);
pinMode(12, OUTPUT);
pinMode(11, OUTPUT);
pinMode(10, OUTPUT);
pinMode(4, OUTPUT);
pinMode(3, OUTPUT);
pinMode(2, OUTPUT);
pinMode(9, INPUT_PULLUP);
pinMode(A10, INPUT_PULLUP);
pinMode(A11, INPUT_PULLUP);
pinMode(8, INPUT_PULLUP);
pinMode(7, INPUT_PULLUP);
pinMode(A0, OUTPUT);
pinMode(A1, OUTPUT);
pinMode(A2, OUTPUT);
pinMode(A3, OUTPUT);
pinMode(A4, OUTPUT);
pinMode(A5, OUTPUT);
pinMode(A6, OUTPUT);
pinMode(A7, OUTPUT);
pinMode(A8, OUTPUT);
pinMode(A9, OUTPUT);
pinMode(7, INPUT_PULLUP);
for (int i = 53; i >= 30; i--) {
pinMode(i, INPUT_PULLUP);
}
lc.shutdown(0,false);
lc.setIntensity(0,0);
lc.clearDisplay(0);
}
void clearScreen()
{
for (int i=0;i<8;i++)
{
for (int j=0;j<8;j++)
{
lc.setLed(0,i,j,false);
}
}
}
void draw(int digit, int number) {
for (int i = 0; i < 7; i++) {
digitalWrite(segmentDisplayOrder[i], SegmentNumbers[number][i] ? LOW : HIGH);
}
digitalWrite(segmentDisplayDigits[digit], HIGH);
clearSegment();
delayMicroseconds(3);
}
void clearSegment()
{
for (int i=0;i<3;i++)
{
digitalWrite(segmentDisplayDigits[i],LOW);
}
for (int j=0;j<7;j++)
{
digitalWrite(segmentDisplayOrder[j], LOW);
}
}
void displayNumber(int num)
{
int digit = num%10;
draw(2,digit);
num/=10;
digit = num%10;
draw(1,digit);
num/=10;
digit=num%10;
draw(0,digit);
}
void loop() {
bool a_isPlaying=false;
bool b_isPlaying=false;
bool c_isPlaying=false;
displayNumber(BPMN);
if (digitalRead(7)==0)
{
if (isPlaybackMode==false && isRecording==false)
{
digitalWrite(5, HIGH);
isPlaybackMode=true;
for (int i =0;i<8;i++)
{
for (int j=0;j<8;j++)
{
lc.setLed(0,i,j,playBackScreen[i][j]);
}
}
delay(500);
playbackStartTime=millis();
}
else
{
clearScreen();
digitalWrite(5, LOW);
playbackStartTime=0;
isPlaybackMode=false;
delay(500);
}
}
if (digitalRead(8)==0)
{
if (isRecording==false && isPlaybackMode==false)
{
for (int i=0;i<500;i++)
{
recordedMusic[i].played=false;
recordedMusic[i].startTime=0;
recordedMusic[i].note=0;
recordedMusic[i].endTime=0;
}
digitalWrite(6, HIGH);
isRecording=true;
for (int i =0;i<8;i++)
{
for (int j=0;j<8;j++)
{
lc.setLed(0,i,j,recordingScreen[i][j]);
}
}
delay(500);
recordStartTime=millis();
}
else
{
clearScreen();
digitalWrite(6, LOW);
recordStartTime=0;
isRecording=false;
delay(500);
}
}
if (isPlaybackMode)
{
for (int i=0;i<500;i++)
{
if (!a_isPlaying && millis()-playbackStartTime>= recordedMusic[i].startTime && millis()-playbackStartTime<=recordedMusic[i].endTime)
{
a_isPlaying=true;
tone(13,recordedMusic[i].note);
delay(10);
noTone(13);
continue;
}
if (millis()-playbackStartTime>=recordedMusic[i].endTime)
{
a_isPlaying=false;
}
if (!b_isPlaying && millis()-playbackStartTime>= recordedMusic[i].startTime && millis()-playbackStartTime<=recordedMusic[i].endTime)
{
b_isPlaying=true;
tone(12,recordedMusic[i].note);
delay(10);
noTone(12);
continue;
}
if (millis()-playbackStartTime>=recordedMusic[i].endTime)
{
b_isPlaying=false;
}
if (!c_isPlaying && millis()-playbackStartTime>= recordedMusic[i].startTime && millis()-playbackStartTime<=recordedMusic[i].endTime)
{
recordedMusic[i]=recordedMusic[i];
c_isPlaying=true;
tone(11,recordedMusic[i].note);
delay(10);
noTone(11);
continue;
}
if (millis()-playbackStartTime>=recordedMusic[i].endTime)
{
c_isPlaying=false;
}
}
}
if (digitalRead(A10)==0 && BPMN<990)
{
delay(500);
BPMN+=10;
BPM = 60000/BPMN;
}
if (digitalRead(A11)==0 && BPMN>0)
{
delay(500);
BPMN-=10;
BPM = 60000/BPMN;
}
if (digitalRead(9)==0 && millis()-lastMetronome>BPM)
{
lastMetronome=millis();
if (metronomeCounter==0)
{
tone(10,440);
}
else
{
tone(10,300);
}
metronomeCounter++;
if (metronomeCounter>3)
{
metronomeCounter=0;
}
delay(10);
noTone(10);
}
if (!isPlaybackMode)
{
for (int i=0;i<24;i++)
{
if (digitalRead(notes[i][0])==LOW)
{
if (isRecording && buttonHeldTime[i]==0)
{
buttonHeldTime[i]=millis();
}
if(!a_isPlaying)
{
tone(13,notes[i][1]);
a_isPlaying=true;
delay(10);
noTone(13);
continue;
}
if(!b_isPlaying)
{
tone(12,notes[i][1]);
b_isPlaying=true;
delay(10);
noTone(12);
continue;
}
if(!c_isPlaying)
{
tone(11,notes[i][1]);
b_isPlaying=true;
delay(10);
noTone(11);
continue;
}
}
else
{
if (isRecording && buttonHeldTime[i]>10)
{
NoteTiming a;
a.startTime = buttonHeldTime[i] - recordStartTime;
a.note = notes[i][1];
a.endTime = millis()-buttonHeldTime[i] + a.startTime;
buttonHeldTime[i]=0;
recordedMusic[recordIndex]=a;
recordIndex++;
}
}
}
}
}