HardwareSerial ATdevice(D2, D8); // RX, TX 

typedef struct {
  long vitesse;
  char* nom;  
} conf;

conf module;
bool flag_infos = true;
unsigned long previousMillis = 0; 
const long interval = 1500;
int compteur = 0;
String msg, inputString, AT;

String commande_AT() {
  if (module.nom == "esp8266") {
    AT += "\n Commande utile pour l'ESP\n";
    AT += "AT                          ->  Statut\n";  
    AT += "AT+GMR                      ->  Version du firmware\n";
    AT += "AT+RST                      ->  reboot du module\n";
    AT += "AT+RESTORE                  ->  remet tous les paramètres d'usine\n";
    AT += "AT+CWMODE=?                 ->  Mode du wifi, 1: Station mode, 2: SoftAP mode, 3: SoftAP+Station mode\n";
    AT += "AT+CWLAP                    ->  Liste les réseaux wifi disponible\n";
    AT += "AT+CWJAP=\"SSID\",\"pwd\"   ->  Connection à un réseau\n";
    AT += "AT+CWLIF                    ->  Asresse IP du module\n";
    AT += "AT+CWQAP                    ->  déconnection du réseau\n";
    AT += "plus d'infos :  https://www.espressif.com/sites/default/files/documentation/4a-esp8266_at_instruction_set_en.pdf\n";
    AT += "\n";    
    AT += "Vous devez régler la com serie sur \"les deux, NL et CR\" pour ce programme\n";
  } 
  else if (module.nom == "bluetooth_maitre") {
    AT += "\n Commande utile pour le module bluetooth maitre/esclave HC-05\n";
    AT += "AT                          ->  Statut\n";  
    AT += "AT+VERSION?                 ->  Version du firmware\n";
    AT += "AT+RESET                    ->  reboot du module\n";
    AT += "AT+RESTORE                  ->  remet tous les paramètres d'usine\n";
    AT += "AT+NAME=BTmoduleHC-05       ->  Renome le module en BTmoduleHC-05\n";
    AT += "AT+PSWD=0000                ->  Change le mot de passe en 0000\n";
    AT += "AT+PSWD?                    ->  Voir le mot de passe\n";
    AT += "AT+ROLE=1                   ->  Passer en mode maitre 1 ou esclave 0\n";
    AT += "AT+UART=9600,0,0            ->  Change la vitesse de comunication\n";
    AT += "plus d'infos :  https://cdn.instructables.com/ORIG/FQ1/CUVZ/HXA9PUVQ/FQ1CUVZHXA9PUVQ.pdf\n";
    AT += "\n"; 
    AT += "Vous devez changer la com serie en \"les deux, NL et CR\" pour ce programme avant de tapez vos commande !!!\n";  
  }  
  else if (module.nom == "bluetooth_esclave") {
    AT += "\n Commande pour le module bluetooth esclave HC-06\n";
    AT += "AT                          ->  Statut\n";  
    AT += "AT+VERSION                  ->  Version du firmware\n";
    AT += "AT+NAMEBTmoduleHC-06        ->  Renome le module en BTmoduleHC-05\n";
    AT += "AT+PIN0000                  ->  Change le mot de passe en 0000\n";
    AT += "AT+BAUD4                    ->  Change la vitesse de comunication (DE 1 -> 1200 à 8 -> 115200, 4 par default: 9600 bauds\n"; 
    AT += "plus d'infos :  https://cdn.instructables.com/ORIG/FQ1/CUVZ/HXA9PUVQ/FQ1CUVZHXA9PUVQ.pdf\n";  
    AT += "\n";    
  }  
  AT += "Vous pouvez tapez vos commandes\n";
  return AT;
}

   
void setup() {
  Serial.begin(115200); // port série    
  delay(1000);
  Serial.println("*************************************");
  Serial.println("W - esp8266");
  Serial.println("M - bluetooth_maitre HC-05"); 
  Serial.println("E - bluetooth_esclave HC-06"); 
  Serial.println("*************************************");   
  Serial.println();
  Serial.println("Avec quelle apareil voulez-vous communiquer ?");
  Serial.println();
  while (true) {  
    if (Serial.available() > 0) {
      int message = Serial.read();     
      if (message == 'W') {
        module.nom = "esp8266";      
        module.vitesse = 115200;           
      }               
      else if (message == 'M') {
        module.nom = "bluetooth_maitre";      
        module.vitesse = 38400;          
      }
      else if (message == 'E') {
        module.nom = "bluetooth_esclave";      
        module.vitesse = 9600;                    
      }
      ATdevice.begin(module.vitesse);   
      break;   
    }    
  }
  Serial.print("Communication avec le module ");
  Serial.println(module.nom);  
}


void infos(){
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    previousMillis = currentMillis;
    if (flag_infos) {      
      String split = module.nom;
      if (compteur == 0) {
        if (split.endsWith("esclave")) {
          ATdevice.print("AT");           
        } else {
          ATdevice.println("AT");      
        }       
      }
      if (compteur == 1) {          
        if (split.endsWith("maitre")) {
          ATdevice.println("AT+VERSION?");
        }
        if (split.endsWith("esclave")) {
          ATdevice.print("AT+VERSION");           
        }
        else {
          ATdevice.println("AT+GMR");            
        }
      }      
      if (compteur == 2) {        
        compteur = 0;  
        Serial.println(commande_AT()); 
        flag_infos = false;            
      }
      compteur++;      
    }
  }  
}


void readSerialPort(){
  msg="";
  while (Serial.available()) {
    delay(10);  
    if (Serial.available() > 0) {
      char c = Serial.read();  //gets one byte from serial buffer
      msg += c; //makes the string readString      
    }
  }  
}

void loop() {    
  readSerialPort();
  if(msg != "") {
    ATdevice.print(msg); 
    Serial.print("-->  "); 
    Serial.println(msg); 
  }  
  if (ATdevice.available() > 0) {
    String inputString = ATdevice.readString();
    Serial.println(inputString);  
  }  
  infos();
}