/*
Store call directly in eeprom 1 for space, 2 for dot,3 for dash, 4 for end callsign
 */

#include <EEPROM.h>

int redled = 5;
int greenled = 8;
int button1 = 2;
int button2 = 4;
int button3 = 7;
int button4 = 9;
int tonepin =  10;
int pttpin =  12;

int cwspeeddelay = 70;
long cwinterval = 300000;

int onoffstate = 0;  
int toneenable = 0; 
int oldtoneenable = 0;
int tonefreq = 1000;         
unsigned long previousMillis = 0;        
unsigned long previousMilliscwinterval = 0;  
long menucounter = 0;
int menuoption = 1;
int debounce = 0;
int eepromwritepos = 0;

void dot() {
  tone(tonepin, 1000);
  digitalWrite(greenled, HIGH);
  digitalWrite(redled, HIGH);
  delay(cwspeeddelay);
  noTone(tonepin);
  digitalWrite(greenled, LOW);
  digitalWrite(redled, LOW);
  delay(cwspeeddelay);  
}

void dash() {
  tone(tonepin, 1000);
  digitalWrite(greenled, HIGH);
  digitalWrite(redled, HIGH);
  delay(cwspeeddelay * 3);
  noTone(tonepin);
  digitalWrite(greenled, LOW);
  digitalWrite(redled, LOW);
  delay(cwspeeddelay);
}

void menu() {
  if (menuoption == 1) menu1();
  if (menuoption == 2) menu2();
}

void menu1() {
  unsigned long currentMillis = millis();
  if (digitalRead(button1) == LOW) onoff();
  if (digitalRead(button2) == LOW) toneenable = 1;
  if (digitalRead(button3) == LOW) toneenable = 2;
  if (digitalRead(button4) == LOW) {
    menucounter ++;
    sendcw();
  }
  if (digitalRead(button4) == HIGH) menucounter = 0;
  if (toneenable == 0) noTone(tonepin);
  if (toneenable == 1) sendtone(1000);
  if (toneenable == 2) sendtone(500);
  if (menucounter == 1 ) {
    digitalWrite(pttpin, HIGH);
    digitalWrite(redled, LOW);
    digitalWrite(greenled, LOW);
    noTone(tonepin);
    menuoption = 2;
  }
  if (currentMillis - previousMilliscwinterval >= cwinterval) {
    previousMilliscwinterval = currentMillis;
    sendcw();
    
  }
}

void onoff() {
  if (onoffstate == 0) {
    digitalWrite(pttpin, LOW);
    onoffstate = 1;
  }
  else {
    digitalWrite(pttpin, HIGH);
    onoffstate = 0;    
    digitalWrite(redled, LOW);
    digitalWrite(greenled, LOW);
  }
  delay(400);
}

void sendtone(int toneinterval) {
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= toneinterval) {
    if(tonefreq == 1000) tonefreq = 2000;
    else tonefreq = 1000;
    previousMillis = currentMillis;
  }
  if (tonefreq == 1000) {
    tone(tonepin, tonefreq);
    digitalWrite(greenled, HIGH);
    digitalWrite(redled, LOW);
  }
  if (tonefreq == 2000) {
    tone(tonepin, tonefreq);
    digitalWrite(greenled, LOW);
    digitalWrite(redled, HIGH);
  }
}

void sendcw(){
  oldtoneenable = toneenable;
  toneenable = 0;
  sendcall();
  toneenable = oldtoneenable;
}

void sendcall(){
  noTone(tonepin);
  for ( int eepromreadpos = 0; eepromreadpos < 1024; eepromreadpos++) {
    int eepromvalue = EEPROM.read(eepromreadpos);
    if (eepromvalue == 1) delay(cwspeeddelay * 3);
    if (eepromvalue == 2) dot();
    if (eepromvalue == 3) dash();
    if (eepromvalue == 4) eepromreadpos = 1024;
  }
  noTone(tonepin);
}

void menu2(){
  digitalWrite(redled, HIGH);
  if (digitalRead(button1) == LOW) writeeeprom(1);
  else if (digitalRead(button2) == LOW) writeeeprom(2);
  else if (digitalRead(button3) == LOW) writeeeprom(3);
  else debounce = 0;
  if (digitalRead(button4) == LOW) menucounter ++;
  if (digitalRead(button4) == HIGH) menucounter = 0;
  if (menucounter == 200000 ) {
    writeeeprom(1);
    debounce = 0;
    writeeeprom(4);
    eepromwritepos = 0;
    digitalWrite(redled, LOW);
    digitalWrite(greenled, LOW);
    debounce = 0;
    menuoption = 1;
  }
}

void writeeeprom(int eepromvalue){
  if (debounce == 0) {
    EEPROM.write(eepromwritepos, eepromvalue); 
    eepromwritepos ++;
  }
  debounce = 1;
  digitalWrite(greenled, HIGH);
  delay(200);
  digitalWrite(greenled, LOW);
}

void setup() {
  Serial.begin(9600);
  pinMode(button1, INPUT_PULLUP);
  pinMode(button2, INPUT_PULLUP);
  pinMode(button3, INPUT_PULLUP);
  pinMode(button4, INPUT_PULLUP);
  pinMode (redled, OUTPUT);
  pinMode (greenled, OUTPUT);
  pinMode(tonepin, OUTPUT);
  digitalWrite(tonepin, LOW);
  pinMode(pttpin, OUTPUT);
  digitalWrite(pttpin, HIGH);
}

void loop() {
  menu();
}
