Добавляем WiFi к Arduino Uno

В этом уроке мы подключим наш микроконтроллер Arduino Uno к Интернету, используя модуль ESP8266 WiFi.

Шаг 1. Комплектующие

Модуль ESP8266 WiFi представляет собой полноценную сеть Wi-Fi, а вы можете легко подключиться в качестве обслуживающего адаптера Wi-Fi, интерфейса беспроводного доступа в Интернет к любому устройству на основе микроконтроллера благодаря простому подключению через последовательный интерфейс или интерфейс UART.

Добавление этого модуля в проекты где используется Arduino откроет новые интересные возможности.

Детали, используемые в проекте Arduino WiFi мы перечислим ниже. Компоненты оборудования:

  • Arduino UNO × 1
  • ESP8266 ESP-01 × 1
  • Перемычки (на выбор) × 1
  • Резистор 10 кОм × 1
  • Резистор 1 кОм × 2

Программные приложения:

Шаг 2. Суть проекта

Есть много способов использовать ESP866 для коммуникаций. Некоторые могут использовать его для отправки/получения данных онлайн или регулярной загрузки данных. В этом уроке мы покажем, как мы можем общаться с Arduino по беспроводной связи, используя ваш телефон (Android или iPhone). Всё будет сделано в автономном режиме, поэтому не нужно иметь подключение к интернету.

ESP8266 будет служить точкой доступа (режим AP), то есть он будет предоставлять доступ к сети Wi-Fi другим устройствам (станциям) и далее подключать их к проводной сети. Процесс этот довольно прост.

Распиновка ESP
Распиновка ESP

Используйте свой телефон, чтобы отправить любую команду в Arduino, а с помощью ESP8266 все будет работать без проводов.

Шаг 3. Схема соединения

Мы можем соединить Ардуино и WiFi модуль двумя способами - первый с резисторами и второй вариант без резисторов. Остановимся на обеих схемах.

Вариант 1

Соединяем контакты, как описано на прилагаемой таблице контактов ниже:

Следуйте этим шагам:

  • подключите красный провод к VIN (3,3 В) к питанию + 3,3 В от микроконтроллера;
  • подключите черный провод к земле;
  • подключите зеленый провод к TX модуля Wifi и микроконтроллера;
  • подключите желтый провод к RX модуля Wi-Fi и микроконтроллера.
Важно! ESP8266 строго питается только до 3,3 В, при больших значениях можно испортить модуль. Не используйте напряжения более 3,3 В!

Подключите VIN к 3,3 В для включения питания, а также контакт ENABLE для включения модуля.

TX подключен к RX, что означает, что все, что мы хотим передать в ESP8266, получит Arduino UNO. И наоборот для RX в TX. Создав эту схему, мы теперь готовы запустить WiFi с Arduino UNO.

Вариант 2

Соедините контакты, соответственно этой таблице контактов ниже:

Следуй этим шагам:

  • подключите оба контакта ECC VCC / 3.3V / Power Pin и Enable (красные провода) к резистору 10 кОм, а затем к выводу питания Uno + 3.3V;
  • соедините контакт заземления / заземления ESP (черный провод) с выводом заземления / заземления Arduino Uno;
  • подключите TX ESP (зеленый провод) к контакту 3 Uno;
  • подключите RSP (синий провод) ESP к резистору 1 кОм, затем к контакту 2 Uno;
  • подключите RX (синий провод) ESP к резистору 1 кОм, затем к выводу GND заземления Uno.

О схеме

Вывод питания ESP на ESP11 имеет маркировку VIN, однако для некоторых версий это может быть 3,3 В или Power или VCC. Вам также нужно будет включить вывод ESP CH_EN или Enable, чтобы он работал.

Как мы уже обсуждали, - не используйте напряжение на ESP больше чем 3.3 В. ESP8266 строго использует 3,3 В. Более того, это разрушит модуль. Так как Arduino имеет 5 В, нам пришлось поставить делитель напряжения - это резисторы.

TX ESP подключен к RX Arduino Uno, что означает, что все, что мы хотим передать (TX) в ESP, получит (RX) от Uno, и наоборот. Создав эту схему, мы теперь готовы запустить WIFI с Arduino UNO.

Внимание! Если вы подключите последовательный отладчик через USB-кабель или откроете COM-порт, связь между ESP и Arduino будет нарушена и не сможет работать. Поэтому, прежде чем прошивать Uno, сначала удалите Rx / Tx из ESP.

Шаг 4. Настройка соединения

После того, как все настроено, вы заметите, что ваш ESP8266 Wifi будет доступен в радиусе действия вашего телефона.

1. Скачать TCP Client для Android

Вы можете скачать любой TCP-клиент, доступный в Play Store, но я использовал TCP-клиент от Sollae Systems

2. Со своего телефона подключитесь к вашему ESP8266 Wifi

Если ваш Wi-Fi ESP8266 не отображается в доступных сетях Wi-Fi, убедитесь, что ваш Arduino работает и все подключено правильно. Если нет, устраните неполадки вашего ESP, следуя документации модуля.

Обычно имя wifi / ssid начинается в ESP после его названия версии, у меня ESP11.

3. После подключения получите статический IP-адрес.

Важно! Вы можете проверить IP-адрес ESP, зайдя в настройки Wi-Fi своего телефона и щелкнув информацию о сети.

IP-адрес по умолчанию в режиме AP - 192.168.4.1.

Вы можете изменить статический IP-адрес, следуя этой Wifi.config() ссылке.

4. Откройте TCP Client, который вы загрузили ранее.

Создайте соединение, нажав кнопку «Подключить», добавьте IP-адрес ESP и порт 80 следующим образом:

80 - это порт, который я использовал для нашего сервера ESP, но вы можете изменить его, заменив 80 на любой номер порта из нашего кода в строке 23.

5. Подождите, пока на консоли TCP появится сообщение «Подключено».

Шаг 5. Общаемся с Arduino Uno через смартфон

После подключения отправьте запрос, введя следующий код для клиента TCP:

esp8266: <any AT Commands>
Связь с ESP8266 осуществляется через Attention Command или AT Commands (AT команды). Посмотрите таблицу AT команд выше, прилагаемую для просмотра кодов.

Или включите встроенный светодиод с помощью команды:

LEDON

Или выключите встроенный светодиод с помощью команды:

LEDOFF

Или просто скажите:

HELLO

Вы можете изменить ответ от того, что отправляете, в зависимости от логики, которую вы вставили в код.

Важно: esp8266, LEDON, LEDOFF и HELLO - пользовательский идентификатор команды. Если вы используете что-то кроме этих, он вернет ErrRead. ErrRead означает, что из отправленного вами сообщения не найдено ни одного идентификатора команды. Сообщение ErrRead кодируется в строке 64.

Шаг 6. Код проекта

Скачать или скопировать код вы можете ниже:

#include <SoftwareSerial.h>

SoftwareSerial wifiSerial(2, 3);      // RX, TX for ESP8266

bool DEBUG = true;   //show more logs
int responseTime = 10; //communication timeout

void setup()
{
  pinMode(13,OUTPUT);  //set build in led as output
  // Open serial communications and wait for port to open esp8266:
  Serial.begin(115200);
  while (!Serial) {
    ; // wait for serial port to connect. Needed for Leonardo only
  }
  wifiSerial.begin(115200);
  while (!wifiSerial) {
    ; // wait for serial port to connect. Needed for Leonardo only
  }
  sendToWifi("AT+CWMODE=2",responseTime,DEBUG); // configure as access point
  sendToWifi("AT+CIFSR",responseTime,DEBUG); // get ip address
  sendToWifi("AT+CIPMUX=1",responseTime,DEBUG); // configure for multiple connections
  sendToWifi("AT+CIPSERVER=1,80",responseTime,DEBUG); // turn on server on port 80
 
  sendToUno("Wifi connection is running!",responseTime,DEBUG);
  

}


void loop()
{
  if(Serial.available()>0){
     String message = readSerialMessage();
    if(find(message,"debugEsp8266:")){
      String result = sendToWifi(message.substring(13,message.length()),responseTime,DEBUG);
      if(find(result,"OK"))
        sendData("\nOK");
      else
        sendData("\nEr");
    }
  }
  if(wifiSerial.available()>0){
    
    String message = readWifiSerialMessage();
    
    if(find(message,"esp8266:")){
       String result = sendToWifi(message.substring(8,message.length()),responseTime,DEBUG);
      if(find(result,"OK"))
        sendData("\n"+result);
      else
        sendData("\nErrRead");               //At command ERROR CODE for Failed Executing statement
    }else
    if(find(message,"HELLO")){  //receives HELLO from wifi
        sendData("\\nHI!");    //arduino says HI
    }else if(find(message,"LEDON")){
      //turn on built in LED:
      digitalWrite(13,HIGH);
    }else if(find(message,"LEDOFF")){
      //turn off built in LED:
      digitalWrite(13,LOW);
    }
    else{
      sendData("\nErrRead");                 //Command ERROR CODE for UNABLE TO READ
    }
  }
  delay(responseTime);
}


/*
* Name: sendData
* Description: Function used to send string to tcp client using cipsend
* Params: 
* Returns: void
*/
void sendData(String str){
  String len="";
  len+=str.length();
  sendToWifi("AT+CIPSEND=0,"+len,responseTime,DEBUG);
  delay(100);
  sendToWifi(str,responseTime,DEBUG);
  delay(100);
  sendToWifi("AT+CIPCLOSE=5",responseTime,DEBUG);
}


/*
* Name: find
* Description: Function used to match two string
* Params: 
* Returns: true if match else false
*/
boolean find(String string, String value){
  return string.indexOf(value)>=0;
}


/*
* Name: readSerialMessage
* Description: Function used to read data from Arduino Serial.
* Params: 
* Returns: The response from the Arduino (if there is a reponse)
*/
String  readSerialMessage(){
  char value[100]; 
  int index_count =0;
  while(Serial.available()>0){
    value[index_count]=Serial.read();
    index_count++;
    value[index_count] = '\0'; // Null terminate the string
  }
  String str(value);
  str.trim();
  return str;
}



/*
* Name: readWifiSerialMessage
* Description: Function used to read data from ESP8266 Serial.
* Params: 
* Returns: The response from the esp8266 (if there is a reponse)
*/
String  readWifiSerialMessage(){
  char value[100]; 
  int index_count =0;
  while(wifiSerial.available()>0){
    value[index_count]=wifiSerial.read();
    index_count++;
    value[index_count] = '\0'; // Null terminate the string
  }
  String str(value);
  str.trim();
  return str;
}
/*
* Name: sendToWifi
* Description: Function used to send data to ESP8266.
* Params: command - the data/command to send; timeout - the time to wait for a response; debug - print to Serial window?(true = yes, false = no)
* Returns: The response from the esp8266 (if there is a reponse)
*/
String sendToWifi(String command, const int timeout, boolean debug){
  String response = "";
  wifiSerial.println(command); // send the read character to the esp8266
  long int time = millis();
  while( (time+timeout) > millis())
  {
    while(wifiSerial.available())
    {
    // The esp has data so display its output to the serial window 
    char c = wifiSerial.read(); // read the next character.
    response+=c;
    }  
  }
  if(debug)
  {
    Serial.println(response);
  }
  return response;
}

/*
* Name: sendToUno
* Description: Function used to send data to Arduino.
* Params: command - the data/command to send; timeout - the time to wait for a response; debug - print to Serial window?(true = yes, false = no)
* Returns: The response from the esp8266 (if there is a reponse)
*/
String sendToUno(String command, const int timeout, boolean debug){
  String response = "";
  Serial.println(command); // send the read character to the esp8266
  long int time = millis();
  while( (time+timeout) > millis())
  {
    while(Serial.available())
    {
      // The esp has data so display its output to the serial window 
      char c = Serial.read(); // read the next character.
      response+=c;
    }  
  }
  if(debug)
  {
    Serial.println(response);
  }
  return response;
}

Существуют разные типы ESP8266. Измените скорость передачи в коде в строке 16 в зависимости от того, что использует ваш ESP8266.

Весь наш запрос будет прочитан и разобран в функции loop():

if(wifiSerial.available()>0){ 
   String message = readWifiSerialMessage(); 
   if(find(message,"esp8266:")){ 
      String result = sendToWifi(message.substring(8,message.length()),responseTime,DEBUG); 
     if(find(result,"OK")) 
       sendData("\n"+result); 
     else 
       sendData("\nErrRead");               //At command ERROR CODE for Failed Executing statement 
   }else 
   if(find(message,"HELLO")){  //receives HELLO from wifi 
       sendData("\\nHI!");    //arduino says HI 
   }else if(find(message,"LEDON")){ 
     digitalWrite(13,HIGH); 
   }else if(find(message,"LEDOFF")){ 
     digitalWrite(13,LOW); 
   } 
   else{ 
     sendData("\nErrRead");                 //Command ERROR CODE for UNABLE TO READ 
   } 
 } 

Вы можете увидеть, что я использовал функцию find(<received message>, <message you want to find>), чтобы интерпретировать сообщение и сообщить Arduino, какой код вызывать. Если вы хотите связаться с Arduino UNO или попросить что-то сделать, просто добавьте свое условие. например:

if(find(message,"MY CODE")){
     // I found 'MY CODE' from received message
     // lets do something here
}
if(find(message,"A")){
     // I found 'A' from received message
     // lets do something here
}

Мы добавили некоторую функцию для связи с ESP8266:

/*
* Name: sendData
* Description: Function used to send string to tcp client using cipsend
* Params: 
* Returns: void
*/
void sendData(String str){
 String len="";
 len+=str.length();
 sendToWifi("AT+CIPSEND=0,"+len,responseTime,DEBUG);
 delay(100);
 sendToWifi(str,responseTime,DEBUG);
 delay(100);
 sendToWifi("AT+CIPCLOSE=5",responseTime,DEBUG);
}
/*
* Name: find
* Description: Function used to match two string
* Params: 
* Returns: true if match else false
*/
boolean find(String string, String value){
 if(string.indexOf(value)>=0)
   return true;
 return false;
}
/*
* Name: readSerialMessage
* Description: Function used to read data from Arduino Serial.
* Params: 
* Returns: The response from the Arduino (if there is a reponse)
*/
String  readSerialMessage(){
 char value[100]; 
 int index_count =0;
 while(Serial.available()>0){
   value[index_count]=Serial.read();
   index_count++;
   value[index_count] = '\0'; // Null terminate the string
 }
 String str(value);
 str.trim();
 return str;
}
/*
* Name: readWifiSerialMessage
* Description: Function used to read data from ESP8266 Serial.
* Params: 
* Returns: The response from the esp8266 (if there is a reponse)
*/
String  readWifiSerialMessage(){
 char value[100]; 
 int index_count =0;
 while(wifiSerial.available()>0){
   value[index_count]=wifiSerial.read();
   index_count++;
   value[index_count] = '\0'; // Null terminate the string
 }
 String str(value);
 str.trim();
 return str;
}
/*
* Name: sendToWifi
* Description: Function used to send data to ESP8266.
* Params: command - the data/command to send; timeout - the time to wait for a response; debug - print to Serial window?(true = yes, false = no)
* Returns: The response from the esp8266 (if there is a reponse)
*/
String sendToWifi(String command, const int timeout, boolean debug){
 String response = "";
 wifiSerial.println(command); // send the read character to the esp8266
 long int time = millis();
 while( (time+timeout) > millis())
 {
   while(wifiSerial.available())
   {
   // The esp has data so display its output to the serial window 
   char c = wifiSerial.read(); // read the next character.
   response+=c;
   }  
 }
 if(debug)
 {
   Serial.println(response);
 }
 return response;
}
/*
* Name: sendToUno
* Description: Function used to send data to Arduino.
* Params: command - the data/command to send; timeout - the time to wait for a response; debug - print to Serial window?(true = yes, false = no)
* Returns: The response from the esp8266 (if there is a reponse)
*/
String sendToUno(String command, const int timeout, boolean debug){
 String response = "";
 Serial.println(command); // send the read character to the esp8266
 long int time = millis();
 while( (time+timeout) > millis())
 {
   while(Serial.available())
   {
     // The esp has data so display its output to the serial window 
     char c = Serial.read(); // read the next character.
     response+=c;
   }  
 }
 if(debug)
 {
   Serial.println(response);
 }
 return response;

Если вы знакомы с созданием мобильных приложений, веб-приложений, веб-служб или веб-разработкой в целом, вы можете создавать клиентские приложения, которые могут отправлять TCP-запросы в ESP. Примеры приложений, которые вы можете сделать: удаленное управление устройствами, веб-панель управления, чат-бот, приложение с кнопками и т.д

28 марта 2019 в 14:55 | Обновлено 13 июля 2020 в 13:38 (редакция)
Опубликовано:
Уроки, ,

3 комментария

  1. Yurnik
    15 января 2021 в 20:43

    Непонятно для кого написано. Если для опытного пользователя, то много лишнего. Для новичка — вообще ничего непонятно… В каком порядке нужно проводить тестирование. Вдруг появляются новые фрагменты, которые автор куда-то добавил, а куда? И т.д. К тому же ошибки…
    Я загрузил код. Законектился по WiFi. А программа пишет в любом случае Fail to connect, Поищу другое описание…

    Ответить
  2. Виктор
    30 ноября 2022 в 13:54

    Зачем в питание VCC 8266 от 3.3V Uno врезан резистор аж на 10кОм? Там и так тока нет, а так вообще не будет.

    Ответить
  3. Wins
    15 августа 2023 в 23:18

    В первом варианте подключении совершенно не понятно как в результате подключать RX и TX ESP и ардуино (RX-RX,TX-TX или RX-TX, TX-RX), точнее объяснение только запутывает читателя, потому что оба варианта присутствуют по два раза (в таблице, на схеме, в тексте).

    Ответить

Добавить комментарий

Ваш E-mail не будет никому виден. Обязательные поля отмечены *