ESP8266 WiFi Voice control Multilanguage Car
The solution requires HTTPS connection to a webserver with Google Chrome, the only one that supports Webkit!

RC car controlled by voice - Try online HERE!!!


  • Solution uses the ESP8266 microcontroller, which connects to the HTTPS website at regular intervals, where it downloads the contents of a text file.
  • Commands that ESP8266 executes on the RC car are written to the text file individually.
  • Commands are entered by the system user connected via HTTPS protocol in the web interface via the browser Google Chrome. Any world language can be used, including the language region. The current program implementation uses English in the US region.
  • The process of converting voice to text is performed by Google servers on an Xhr request that is automatically triggered by the user.
  • There are four supported commands for move forward, backward, and to sides.
  • There is a 2000 millisecond pause between the two connections until the connection is terminated and the current voice command is executed.
  • System response is connection is virtually instantaneous within 30 milliseconds.
  • ESP8266 uses HTTPS connectivity with the webserver through the implementation of the WifiClientSecure library and the webserver certificate.
  • The system is suitable for school projects as well as autonomous vehicles controlled from anywhere on the ground. The project can be completed with a camera record and various other sensors.
  • Compatibility for (in version Arduino Core 2.3.0):

  • ESP8266-Generic
  • NodeMCU (v1 - v3)
  • Wemos D1
  • Wemos D1 mini
  • Program for ESP8266

    /*|-------------------------------------------------|*/
    /*| RC CAR VOICE CONTROL VIA WEB INTERFACE          |*/
    /*| Webkit (GOOGLE) technology for voice-to-text    |*/
    /*| Author: Martin Chlebovec (martinius96)          |*/
    /*| LANGUAGE English - region US --> en-US          |*/
    /*| Revison: 21. Jan. 2020                          |*/
    /*| Arduino Core 2.5.0/2.5.2 compatible             |*/
    /*|-------------------------------------------------|*/
    #include <ESP8266WiFi.h>
    #include <WiFiClientSecure.h>
    const char * ssid = "WIFI_NAME";
    const char * password = "WIFI_PASS";
    const char * host = "arduino.php5.sk"; //yourdomain
    const int httpsPort = 443; //https port
    const char fingerprint[] PROGMEM = "b0 6d 7f 8c 98 78 8e 6e 0a 57 a8 2f 7e d1 40 2a 1e 3f 48 f7";
    void setup() {
      Serial.begin(115200);
      Serial.println();
      Serial.print("Connecting to WiFi: ");
      Serial.println(ssid);
      WiFi.begin(ssid, password);
      while (WiFi.status() != WL_CONNECTED) {
        delay(500);
        Serial.print(".");
      }
      Serial.println("");
      Serial.println("WiFi connected");
      Serial.println("IP address: ");
      Serial.println(WiFi.localIP());
    }
    void executed_command() {
      WiFiClientSecure client;
      Serial.printf("Using fingerprint '%s'\n", fingerprint);
      client.setFingerprint(fingerprint);
      if (client.connect(host, httpsPort)) {
        String url = "/php_car/command_executed.php";
        client.print(String("GET ") + url + " HTTP/1.0\r\n" + "Host: " + host + "\r\n" + "User-Agent: NodeMCU\r\n" + "Connection: close\r\n\r\n");
        Serial.println("Connection sucessful");
        Serial.println("Command executed to PHP service");
      } else {
        Serial.println("Error connecting to PHP service for verifying action");
      }
      client.stop();
    }
    void loop() {
      WiFiClientSecure client;
      Serial.printf("Using fingerprint '%s'\n", fingerprint);
      client.setFingerprint(fingerprint);
      if (client.connect(host, httpsPort)) {
        String url = "/php_car/translation.txt";
        client.print(String("GET ") + url + " HTTP/1.0\r\n" + "Host: " + host + "\r\n" + "User-Agent: NodeMCU\r\n" + "Connection: close\r\n\r\n");
        Serial.println("Connection sucessful");
        while (client.connected()) {
          String line = client.readStringUntil('\n');
          if (line == "\r") {
            break;
          }
        }
        String line = client.readStringUntil('\n');
        Serial.println("RC control command: ");
        Serial.println(line);
        if (line == "UP") { //if command == go UP
          Serial.println("Moving forward...");
          // PUT CODE FOR MOVE FORWARD THERE
          client.stop();
          executed_command();
        } else if (line == "DOWN") { //if command == go DOWN
          Serial.println("Moving backward...");
          // PUT CODE FOR MOVE BACKWARD THERE
          client.stop();
          executed_command();
        } else if (line == "LEFT") { //if command == TURN LEFT
          Serial.println("Turning left...");
          // PUT CODE FOR TURN LEFT THERE
          client.stop();
          executed_command();
        } else if (line == "RIGHT") { //if command == TURN RIGHT
          Serial.println("Turning right...");
          // PUT CODE FOR TURN RIGHT THERE
          client.stop();
          executed_command();
        } else if (line == "Last command executed by ESP8266. Waiting for new command.") { //if command == NO_MORE_COMMAND
          client.stop();
          Serial.println("No voice command set yet");
        } else {
          client.stop();
          Serial.println("This command is not suported");
          executed_command();
        }
      } else {
        Serial.println("Connection was not sucessful");
      }
      client.stop();
      delay(2000); // WAIT () miliseconds before next reading of variable
    }
    

    Program - ESP32

    /*|-------------------------------------------------|*/
    /*| RC CAR VOICE CONTROL VIA WEB INTERFACE          |*/
    /*| Webkit (GOOGLE) technology for voice-to-text    |*/
    /*| Author: Martin Chlebovec (martinius96)          |*/
    /*| LANGUAGE English - region US --> en-US          |*/
    /*| Revision: 22. Jan. 2020                         |*/
    /*| Arduino Core 1.0.1+                             |*/
    /*|-------------------------------------------------|*/
    #include <WiFi.h>
    #include <WiFiClientSecure.h>
    const char* ssid     =    "WIFI_NAME";
    const char* pass     =    "WIFI_PASS";
    const char* host     =    "arduino.php5.sk";
    const int httpsPort = 443; //http port
    //DIGICERT ROOT CA
    const char* test_root_ca = \
                               "-----BEGIN CERTIFICATE-----\n" \
                               "MIIEsTCCA5mgAwIBAgIQCKWiRs1LXIyD1wK0u6tTSTANBgkqhkiG9w0BAQsFADBh\n" \
                               "MQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\n" \
                               "d3cuZGlnaWNlcnQuY29tMSAwHgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBD\n" \
                               "QTAeFw0xNzExMDYxMjIzMzNaFw0yNzExMDYxMjIzMzNaMF4xCzAJBgNVBAYTAlVT\n" \
                               "MRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5j\n" \
                               "b20xHTAbBgNVBAMTFFJhcGlkU1NMIFJTQSBDQSAyMDE4MIIBIjANBgkqhkiG9w0B\n" \
                               "AQEFAAOCAQ8AMIIBCgKCAQEA5S2oihEo9nnpezoziDtx4WWLLCll/e0t1EYemE5n\n" \
                               "+MgP5viaHLy+VpHP+ndX5D18INIuuAV8wFq26KF5U0WNIZiQp6mLtIWjUeWDPA28\n" \
                               "OeyhTlj9TLk2beytbtFU6ypbpWUltmvY5V8ngspC7nFRNCjpfnDED2kRyJzO8yoK\n" \
                               "MFz4J4JE8N7NA1uJwUEFMUvHLs0scLoPZkKcewIRm1RV2AxmFQxJkdf7YN9Pckki\n" \
                               "f2Xgm3b48BZn0zf0qXsSeGu84ua9gwzjzI7tbTBjayTpT+/XpWuBVv6fvarI6bik\n" \
                               "KB859OSGQuw73XXgeuFwEPHTIRoUtkzu3/EQ+LtwznkkdQIDAQABo4IBZjCCAWIw\n" \
                               "HQYDVR0OBBYEFFPKF1n8a8ADIS8aruSqqByCVtp1MB8GA1UdIwQYMBaAFAPeUDVW\n" \
                               "0Uy7ZvCj4hsbw5eyPdFVMA4GA1UdDwEB/wQEAwIBhjAdBgNVHSUEFjAUBggrBgEF\n" \
                               "BQcDAQYIKwYBBQUHAwIwEgYDVR0TAQH/BAgwBgEB/wIBADA0BggrBgEFBQcBAQQo\n" \
                               "MCYwJAYIKwYBBQUHMAGGGGh0dHA6Ly9vY3NwLmRpZ2ljZXJ0LmNvbTBCBgNVHR8E\n" \
                               "OzA5MDegNaAzhjFodHRwOi8vY3JsMy5kaWdpY2VydC5jb20vRGlnaUNlcnRHbG9i\n" \
                               "YWxSb290Q0EuY3JsMGMGA1UdIARcMFowNwYJYIZIAYb9bAECMCowKAYIKwYBBQUH\n" \
                               "AgEWHGh0dHBzOi8vd3d3LmRpZ2ljZXJ0LmNvbS9DUFMwCwYJYIZIAYb9bAEBMAgG\n" \
                               "BmeBDAECATAIBgZngQwBAgIwDQYJKoZIhvcNAQELBQADggEBAH4jx/LKNW5ZklFc\n" \
                               "YWs8Ejbm0nyzKeZC2KOVYR7P8gevKyslWm4Xo4BSzKr235FsJ4aFt6yAiv1eY0tZ\n" \
                               "/ZN18bOGSGStoEc/JE4ocIzr8P5Mg11kRYHbmgYnr1Rxeki5mSeb39DGxTpJD4kG\n" \
                               "hs5lXNoo4conUiiJwKaqH7vh2baryd8pMISag83JUqyVGc2tWPpO0329/CWq2kry\n" \
                               "qv66OSMjwulUz0dXf4OHQasR7CNfIr+4KScc6ABlQ5RDF86PGeE6kdwSQkFiB/cQ\n" \
                               "ysNyq0jEDQTkfa2pjmuWtMCNbBnhFXBYejfubIhaUbEv2FOQB3dCav+FPg5eEveX\n" \
                               "TVyMnGo=\n" \
                               "-----END CERTIFICATE-----\n";
    WiFiClientSecure client;
    void setup() {
      Serial.begin(115200);
      delay(10);
      Serial.print("Connecting to ssid: ");
      Serial.println(ssid);
      WiFi.disconnect(true);
      WiFi.mode(WIFI_STA);
      WiFi.begin(ssid, pass);
      while (WiFi.waitForConnectResult() != WL_CONNECTED) {
        delay(500);
        Serial.print(".");
      }
      client.setCACert(test_root_ca);
      Serial.println("");
      Serial.println("WiFi uspesne pripojene");
      Serial.println("IP adresa: ");
      Serial.println(WiFi.localIP());
      Serial.println("Ready");
    }
    
    void translation() {
      if (client.connect(host, httpsPort)) {
        String url = "/php_car/translation.txt";
        client.print(String("GET ") + url + " HTTP/1.0\r\n" + "Host: " + host + "\r\n" + "User-Agent: ESP32\r\n" + "Connection: close\r\n\r\n");
        while (client.connected()) {
          String hlavicka = client.readStringUntil('\n');
          if (hlavicka == "\r") {
            break;
          }
        }
        String line = client.readStringUntil('\n');
        Serial.println(line);
        if (line == "UP") { //if command == go UP
          Serial.println("Moving forward...");
          // PUT CODE FOR MOVE FORWARD THERE
          client.stop();
          executed_command();
        } else if (line == "DOWN") { //if command == go DOWN
          Serial.println("Moving backward...");
          // PUT CODE FOR MOVE BACKWARD THERE
          client.stop();
          executed_command();
        } else if (line == "LEFT") { //if command == TURN LEFT
          Serial.println("Turning left...");
          // PUT CODE FOR TURN LEFT THERE
          client.stop();
          executed_command();
        } else if (line == "RIGHT") { //if command == TURN RIGHT
          Serial.println("Turning right...");
          client.stop();
          executed_command();
          // PUT CODE FOR TURN RIGHT THERE
        } else if (line == "Last command executed by ESP8266. Waiting for new command.") { //if command == NO_MORE_COMMAND
          Serial.println("No voice command set yet");
        }
      } else {
        Serial.println("Problem connecting to GET voice command");
      }
      client.stop();
    }
    
    void executed_command() {
      if (client.connect(host, httpsPort)) {
        Serial.println("RESET VOICE COMMAND SUCESSFUL");
        String url = "/php_car/command_executed.php";
        client.print(String("GET ") + url + " HTTP/1.0\r\n" + "Host: " + host + "\r\n" + "User-Agent: ESP32\r\n" + "Connection: close\r\n\r\n");
      } else {
        Serial.println("CONNECTION FAILED");
      }
      client.stop();
    }
    
    void loop() {
      while (WiFi.status() != WL_CONNECTED) {
        delay(500);
        Serial.print(".");
    
      }
      translation();
      delay(2000); // WAIT () miliseconds before next reading of variable
    }
    

    Program - Arduino + Ethernet Wiznet W5100

    /*|-------------------------------------------------|*/
    /*| RC CAR VOICE CONTROL VIA WEB INTERFACE          |*/
    /*| Webkit (GOOGLE) technology for voice-to-text    |*/
    /*| Author: Martin Chlebovec (martinius96)          |*/
    /*| LANGUAGE English - region US --> en-US          |*/
    /*| Revision: 21. Jan. 2020                         |*/
    /*|-------------------------------------------------|*/
    #include <SPI.h>
    #include <Ethernet.h>
    
    byte mac[] = { 0xAA, 0xBB, 0xCC, 0x81, 0x7B, 0x4A }; //fyzicka adresa MAC
    char* serverName = "www.arduino.php5.sk"; // webserver
    
    EthernetClient client;
    void setup() {
      Serial.begin(115200);
      if (Ethernet.begin(mac) == 0) {
        Serial.println("DHCP nepridelilo adresu, skusam so statickou...");
        Ethernet.begin(mac);
      }
      Serial.print("  DHCP assigned IP ");
      Serial.println(Ethernet.localIP());
    }
    void executed_command() {
      client.stop();
      if (client.connect(serverName, 80)) {
        client.println("GET /php_car/command_executed.php HTTP/1.0");
        client.println("Host: www.arduino.php5.sk");
        client.println("Connection: close");
        client.println();
      } else {
        Serial.println("Connection failed");
      }
      client.stop();
    }
    void loop() {
      if (Ethernet.begin(mac) == 0) {
        Serial.println("DHCP nepridelilo adresu, skusam so statickou...");
        Ethernet.begin(mac);
      }
      if (client.connect(serverName, 80)) {
        client.println("GET /php_car/translation.txt HTTP/1.0");
        client.println("Host: www.arduino.php5.sk");
        client.println("Connection: close");
        client.println();
        while (client.connected()) {
          String hlavicka = client.readStringUntil('\n');
          Serial.println(hlavicka);
          if (hlavicka == "\r") {
            break;
          }
        }
        String line = client.readStringUntil('\n');
        Serial.println("Command is:");
        Serial.println(line);
        if (line == "UP") { //if command == go UP
          Serial.println("Moving forward...");
          // PUT CODE FOR MOVE FORWARD THERE
          executed_command();
        } else if (line == "DOWN") { //if command == go DOWN
          Serial.println("Moving backward...");
          // PUT CODE FOR MOVE BACKWARD THERE
          executed_command();
        } else if (line == "LEFT") { //if command == TURN LEFT
          Serial.println("Turning left...");
          // PUT CODE FOR TURN LEFT THERE
          executed_command();
        } else if (line == "RIGHT") { //if command == TURN RIGHT
          Serial.println("Turning right...");
          // PUT CODE FOR TURN RIGHT THERE
          executed_command();
        } else if (line == "Last command executed by ESP8266. Waiting for new command.") { //if command == NO_MORE_COMMAND
          Serial.println("No voice command set yet");
        } else {
    
          Serial.println("This command is not suported");
          executed_command();
        }
      }
      else {
        Serial.println("Connection failed");
        Serial.println();
      }
      client.stop();
      delay(5000);
    }