ESP32 отправляет данные на другой ESP32 без установления соединения Wi-Fi
Изначально я создавал проект, состоящий из Atmega328P и NRF24L01, чтобы создать несколько Arduino, которые могли бы общаться друг с другом. В основном я создавал что-то вроде этого:
По мере роста сети мне начинает не хватать памяти при использовании atmega328P. Я должен быть осторожен с выделением памяти и многим другим. Поэтому я хотел бы заменить NRF24L01 на ESP32. Цена ESP-WROOM-32 сама по себе также дешевле, чем покупка NRF24L01 + atmega328.
Вопрос
Как я могу отправлять данные с одного ESP32 на другой ESP32 без установления соединения WiFi? Так же, как в NRF24L01, где вы указываете канал записи, куда вы хотите отправить данные, а другой NRF24L01 прослушивает на этой трубе.
Я знаю, что могу сделать это с помощью ESP-NOW. В этом видео объясняется, как это сделать. Проблема с ESP NOW заключается в том, что мне нужно заранее знать mac-адрес ESP32, на который я собираюсь отправить сообщение. Я планирую иметь возможность добавлять устройства для умного дома, не зная MAC-адреса.
Мой алгоритм работы с NRF24, который я уже создал, выглядит следующим образом:
- Главный узел прослушивает адрес 2.
- Если я добавлю в сеть новый узел
A
, он будет прослушивать адрес 1. - Мастер обнаруживает все устройства с адресом 1 каждые несколько секунд.
- Итак, в конечном итоге узел
A
получает сообщение пакета обнаружения, которое исходит от мастера. Теперь узелA
прослушивает случайный адрес и отвечает мастеру с этим случайным адресом. - Итак, узел
A
теперь подключен к сети.
Самое замечательное в этом алгоритме то, что я могу добавлять в сеть новые узлы, не зная заранее их адреса. Я хотел бы сделать то же самое с ESP32. Как отправить простое сообщение между двумя модулями ESP32?
@Tono Nam, 👍0
Обсуждение1 ответ
Лучший ответ:
Наконец-то я нашел способ, как это сделать. Если вы используете mac-адрес FF:FF:FF:FF:FF:FF, который работает как широковещательный адрес. Это рабочий код о том, как отправить сообщение от мастера на другой esp32, не зная его mac-адреса. Позже ведомое устройство может ответить своим реальным MAC-адресом:
Код для мастера (tx)
#include <Arduino.h>
#include <esp_now.h>
#include "WiFi.h"
uint8_t broadcastAddress[] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status) {
Serial.println(status == ESP_NOW_SEND_SUCCESS ? "Delivery Success 1" : "Delivery Fail 1");
if (status ==0){
Serial.println("Delivery Success 2");
}
else{
Serial.println("Delivery fail 2");
}
Serial.println();
}
void setup()
{
Serial.begin(115200);
Serial.println("Starting...\n");
// Установить устройство в качестве станции Wi-Fi
WiFi.mode(WIFI_STA);
Serial.println(WiFi.macAddress());
// Инициируем ESP-СЕЙЧАС
if (esp_now_init() != ESP_OK) {
Serial.println("Error initializing ESP-NOW");
for(;;) { delay(1); } // не инициализировать ждать вечно
}
Serial.println("initialized ESP-NOW");
// После успешной инициализации ESPNow мы зарегистрируемся для отправки CB на
// получаем статус переданного пакета
esp_now_register_send_cb(OnDataSent);
// Регистрация пира
esp_now_peer_info_t peerInfo;
memcpy(peerInfo.peer_addr, broadcastAddress, 6);
peerInfo.channel = 0;
peerInfo.encrypt = false;
// Добавляем пир
if (esp_now_add_peer(&peerInfo) != ESP_OK){
Serial.println("Failed to add peer");
for(;;) { delay(1); } // не инициализировать ждать вечно
}
}
int dataToSend = 1;
void loop()
{
dataToSend++;
// Отправляем сообщение через ESP-NOW (размер int 4 байта на ESP32)
esp_err_t result = esp_now_send(broadcastAddress, (uint8_t *) &dataToSend, 4);
if (result == ESP_OK) {
Serial.println("Sent with success");
}
else {
Serial.println("Error sending the data");
}
//Serial.println(WiFi.macAddress());
delay(1000);
}
Код подчиненного устройства (Rx)
#include <Arduino.h>
#include <esp_now.h>
#include "WiFi.h"
// Обратный вызов при получении данных
void OnDataRecv(const uint8_t * mac, const uint8_t *incomingData, int len)
{
int dataReceived;
memcpy(&dataReceived, incomingData, sizeof(dataReceived));
Serial.print("Data Received: ");
Serial.println(dataReceived);
Serial.println();
}
void setup()
{
Serial.begin(115200);
delay(100);
Serial.println("Starting...\n");
// Установить устройство в качестве станции Wi-Fi
WiFi.mode(WIFI_STA);
// печатаем наш mac адрес
Serial.println(WiFi.macAddress());
// Инициируем ESP-СЕЙЧАС
if (esp_now_init() != ESP_OK) {
Serial.println("Error initializing ESP-NOW");
for(;;) { delay(1); } // не инициализировать ждать вечно
}
Serial.println("initialized ESP-NOW");
// Зарегистрируйтесь для callback-функции, которая будет вызываться при получении данных
esp_now_register_recv_cb(OnDataRecv);
}
void loop()
{
}
Вы также можете ответить кодом получателя, если хотите. Это будет тот же код.
погуглите «уровень канала данных модели OSI» для получения дополнительной информации о уровне модели osi 2 ... доступно несколько протоколов связи ... я не знаю, какие из них реализованы модулем esp32., @jsotola
Вам даже не нужно устанавливать macAddress в FF:FF:FF:FF:FF:FF
, функция esp_now_send()
позволяет вам передать NULL
в качестве macAddress для трансляции esp_now_send(NULL , *данные, длина)
. См. [документацию] (https://docs.espressif.com/projects/esp-idf/en/latest/esp32/api-reference/network/esp_now.html#_CPPv412esp_now_sendPK7uint8_tPK7uint8_t6size_t)., @hcheung
Для пиров вам также не нужно использовать физический macAddress, вы можете просто назначить локальный адрес пира каждому пиру. Преимущество этого заключается не только в том, что вы избавляетесь от проблем с поиском macAddress каждого узла, когда вы заменяете одноранговый узел и заменяете другим в будущем, вам даже не нужно изменять список одноранговых macAddresses в вашем мастер-коде., @hcheung
- Отправить только один пакет с одного ESP32 на другой ESP32 без подтверждения
- esp32 Stack canary watchpoint срабатывает
- Почему функция server.on() из "ESPAsyncWebServer.h" выполняется на стороне setup(), а не на стороне loop()?
- Модуль nRF24L01 с использованием библиотеки Mirf работал, а затем остановился
- Передача нестатической функции-члена с помощью bind
- Увеличить частоту дискретизации на плате ESP32
- Использование лямбд в качестве функций обратного вызова
- Понимание спецификаций NRF24L01
Вы должны проверить режим сетки ..., @Majenko
если они имеют постоянную мощность, вы можете подключиться к Wi-Fi при загрузке, получить «телефонную книгу» с сервера, затем отключить Wi-Fi и запустить esp-now. Если они говорят только в одну сторону, как мои выключатели (кнопки), вам не нужно менять конфигурацию, чтобы добавить больше единиц., @dandavis