Cuprins:
2025 Autor: John Day | [email protected]. Modificat ultima dată: 2025-01-13 06:58
Subiectul de astăzi se referă la un test la distanță cu un ESP32 cu antenă externă. Să folosim două module astăzi: de la Espressif și TTGO. Să verificăm apoi RSSI între aceste două antene ESP32, să generăm un grafic din istoric și să scriem un jurnal al valorilor într-un fișier.csv.
Apoi avem ESP32 Wrover ca AP și ESP32 al TTGO ca Station. Am folosit o antenă pe care am luat-o de la un TP-Link ceva mai mare și un alt router cunoscut sub numele de antenă de 9dbm. Nu am observat nicio diferență între cele două.
În cele din urmă, cele două microcontrolere se conectează prin socket și, la fiecare trimitere a pachetelor de date, imprimăm pe un afișaj un grafic cu bare care indică raportul dbm.
Pasul 1: Montarea AP-ului cu Wrover
Pasul 2: Asamblarea stației cu TTGO
Pasul 3: REZULTAT
Distanța maximă cu 2x antene externe: 315 metri
Distanta maxima cu antena externa si interna: 157 metri
Pasul 4: Arhivați LOG. CSV
Am înregistrat datele pe un card SD, cu date în milis, dbm și șirul pachetului.
Pasul 5: Biblioteca Adafruit GFX
În IDE-ul Arduino, accesați Schiță-> Includeți bibliotecă-> Gestionați bibliotecile …
Instalați Biblioteca Adafruit GFX
Pasul 6: Biblioteca Adafruit ST7735
În IDE-ul Arduino, accesați Schiță-> Includeți bibliotecă-> Gestionați bibliotecile …
Instalați Adafruit ST7735
Pasul 7: Configurarea cardurilor
Rămâneți la curent pentru diferențe:
Pasul 8: AP.ino
Am inclus bibliotecile necesare și am definit câțiva parametri.
#include #include #include #include #include #include // Rede que o ESP criará. No Station deve ser igual #define SSID "RSSI_Test" #define PASSWORD "87654321" // Tempo de timeout pentru a considera o conexiune pedidă #define TIMEOUT 2000 // Largura e altura do display #define DISPLAY_WIDTH 160 #define DISPLAY_HEIGHT 128 // Configurações de cor, margem e tamanho do gráfico #define PLOT_COLOR ST77XX_GREEN #define PLOT_MARGIN 20 #define PLOT_SIZE (DISPLAY_HEIGHT - 2 * PLOT_MARGIN) // Arquivo de log no SD #define FILE_PATH "/log.csv"
Definim pinii, printre alte variabile
// Pinos afișează # define DISPLAY_DC 12 // A0 #define DISPLAY_CS 13 // CS #define DISPLAY_MOSI 14 // SDA #define DISPLAY_CLK 27 // SCK #define DISPLAY_RST 0 // Pino do SDCard. Os pinos mosi, miso e sck são os nativos (23, 19 și 18 respectiv) #define SDCARD_CS 15 // Pixel unde o graphic começa horizontalmente int currentX = PLOT_MARGIN; // Objeto responsável pelo display Adafruit_ST7735 display = Adafruit_ST7735 (DISPLAY_CS, DISPLAY_DC, DISPLAY_MOSI, DISPLAY_CLK, DISPLAY_RST); // Criamos um server (qualquer porta válida serve contanto that o client utilize a same porta) WiFiServer server (80); // Variável para armazenar o client (no case o ESP32 em modo station) conectat WiFiClient client; // String que recebemos do client String primit; // RSSI enviado pelo cliente para este ESP32 long rssi = 0; // Faz o controle do temporizador (interrupção por tempo) hw_timer_t * timer = NULL; // Utilizat pentru a păstra ultimele std:: vector rssiHistory;
Înființat
void setup () {Serial.begin (115200); setupDisplay (); // Inicializa o SD if (! SD.begin (SDCARD_CS)) {display.println ("Erro ao inițializa lib SD!"); } // Cria a rede WiFi, inițializa serverul și aștepta clientul conecta setupWiFi (); server.begin (); waitForClient (); // Espera 3 segundos, limpa a tela și inițializa o Watchdog delay (3000); display.fillScreen (ST77XX_BLACK); display.setCursor (0, 0); setupWatchdog (); }
Configurați WiFi
// Cria um Access Point e configura o IPvoid setupWiFi () {display.println ("Creating softAP" + String (SSID)); WiFi.disconnect (); WiFi.mode (WIFI_AP); WiFi.softAPConfig (IPAddress (192, 168, 0, 1), IPAddress (192, 168, 0, 1), IPAddress (255, 255, 255, 0)); WiFi.softAP (SSID, PAROLĂ); display.println ("softAP" + Șir (SSID) + "creat!"); }
Afișare configurare
// Incializa o display, muda a orientação e limpa a telavoid setupDisplay () {// Inicializa o display display.initR (INITR_BLACKTAB); // Rotaciona o conteúdo mostrado display.setRotation (3); // Pinta a tela de preto display.fillScreen (ST77XX_BLACK); }
waitForClient
void waitForClient () {display.println ("Se așteaptă clientul"); // Aguarda o client conectează while (! (Client = server.available ())) {display.print ("."); întârziere (500); } display.println ("Client conectat"); // Tempo máximo que o cliente debe demorar para responder // antes de dizermos que a conexão foi perdida client.setTimeout (TIMEOUT); }
IRAM_ATTR resetModule și setupWatchdog
// função que o temporizador irá chamar, para reiniciar o ESP32void IRAM_ATTR resetModule () {ets_printf ("(watchdog) reiniciar / n"); esp_restart_noos (); // reinicia o chip} void setupWatchdog () {timer = timerBegin (0, 80, true); // timerID 0, div 80 // timer, callback, interrupção de borda timerAttachInterrupt (timer, & resetModule, true); // timer, tempo (us), repetição timerAlarmWrite (timer, 10000000, true); timerAlarmEnable (timer); // habilita a interrupção}
Buclă
bucla void () {timerWrite (timer, 0); // reseta o temporizador (alimenta o watchdog) checkConnection (); // checa se possui conexão com o client readFromClient (); // lê os dados do client sendToClient (); // envia confirmação para o cliente plot (); // mostra o gráfico de histórico de rssi log (); // salva um log no cartão SD}
checkConnection
void checkConnection () {// Se o client nu este conectat if (! client.connected ()) {// Limpa a tela e espera pelo client display.fillScreen (ST77XX_BLACK); display.println („Client deconectat”); waitForClient (); }}
readFromClient
void readFromClient () {// Espera até o client trimite ceva sau desconectar while (client.connected () &&! client.available ()) {delay (100); } // Se chegou aqui e ainda estiver conectado é porque possui algo para receber do cliente if (client.connected ()) {received = client.readStringUntil ('\ n'); // Lê o texto care o client vă încurajează jasot.remove (recepționat.lungime () - 1); // Eliminați o / n do final rssi = client.parseInt (); // Lê o rssi care o client vă invită clearText (); // Limpa o texto display.setCursor (0, 0); // Mutați cursorul textului pentru afișarea afișării display.println ("RSSI:" + String (rssi)); // Show o RSSI no display display.println ("Received:" + primit); // Show a mensagem recebida do client // Se a quantitate de barras do gráfico passou do limite apagamos o registro mais antigo if (rssiHistory.size () == (DISPLAY_WIDTH - 2 * PLOT_MARGIN) / 2) {rssiHistory.erase (rssiHistory.începe()); } // Adiciona no final do histórico (mais recente) rssiHistory.push_back (rssi); }}
sendToClient
void sendToClient () {// Se o client estiver conectado enviamos de volta a mensagem com um OK if (client.connected ()) {String Send = received + "OK"; client.println (trimiterea); }}
complot
void plot () {// Coloca no ponto inicial și limpamos o gráfico currentX = PLOT_MARGIN; display.fillRect (PLOT_MARGIN, 2 * PLOT_MARGIN, DISPLAY_WIDTH - 2 * PLOT_MARGIN, DISPLAY_HEIGHT - 2 * PLOT_MARGIN, ST77XX_BLACK); // Para cada valor do histórico fazemos o cálculo do tamanho da barra do gráfico, desenhamos și avansamos for the next for (int i = 0; i -120? Map (rssiHistory , -120, 0, 0, PLOT_SIZE): 0; display.drawFastVLine (currentX, DISPLAY_HEIGHT - valoare, valoare, PLOT_COLOR); currentX + = 2;}}
clearText și jurnal
void clearText () {// Limpa a area com o text da mensagem vinda do client display.fillRect (0, 0, DISPLAY_WIDTH, 2 * PLOT_MARGIN, ST77XX_BLACK); } void log () {// Abrimos o arquivo para escrevermos no final dele File file = SD.open (FILE_PATH, FILE_APPEND); // Se nu reușește să deschidă arhiva mostramos uma mensagem de erro if (! File) {Serial.println ("Fail to open file"); întoarcere; } // Gravamos uma linha com o tempo since o boot, o rssi atual e a mensagem recebida String data = String (millis ()) + ";" + Șir (rssi) + ";" + primit; file.println (date); file.close (); }
Pasul 9: Station.ino
Am inclus bibliotecile necesare și am definit câțiva parametri.
#include #include #include #include #include #include // Nome da rede que nos conectaremos. Criado pelo AP #define SSID "RSSI_Test" #define PASSWORD "87654321" #define HOST "192.168.0.1" // IP care a fost configurat fără setup do AP #define PORT 80 // Porta do sever. Qualquer porta válida contanto que seja igual nos dois arquivos // Tempo de timeout pentru considerarea unei conexiuni pedale #define TIMEOUT 2000 // Largura e altura do display #define DISPLAY_WIDTH 160 #define DISPLAY_HEIGHT 128 // Configurações de cor, margem și tamanho do gráfico #define PLOT_COLOR ST77XX_GREEN #define PLOT_MARGIN 20 #define PLOT_SIZE (DISPLAY_HEIGHT - 2 * PLOT_MARGIN) // Arquivo de log no SD #define FILE_PATH "/log.csv"
Definim setările care implică afișajul și cardul SD.
număr lung = 0; // Contador de mensagens enviadaslong rssi = 0; // RSSI calculado Șir primit; // Mensagem de confirmare că o AP nos envia // Pixel unde o grafic vine horizontal horizontal int currentX = PLOT_MARGIN; // Utilizat pentru conexiunea cu serverul socket WiFiClient; #define DISPLAY_DC 12 // A0 #define DISPLAY_CS 13 // CS #define DISPLAY_MOSI 14 // SDA #define DISPLAY_CLK 27 // SCK #define DISPLAY_RST 0 // Pino do SDCard. Os pinos mosi, miso e sck são os nativos (23, 19 și 18 respectiv) #define SDCARD_CS 15 // Objeto responsável pelo display Adafruit_ST7735 display = Adafruit_ST7735 (DISPLAY_CS, DISPLAY_DC, DISPLAY_MOSI, DISPLAY_CLK, DISPLAY_RST); hw_timer_t * timer = NULL; // faz o controle do temporizador (interrupção por tempo) // Utilizat pentru a păstra ultimii std:: vector rssiHistory;
Înființat
void setup () {setupDisplay (); // Inicializa o SD if (! SD.begin (SDCARD_CS)) {display.println ("Erro ao inițializa lib SD!"); } // Conecta no access point criado pelo outro ESP32 și conecta la server setupWiFi (); connectToServer (); // Espera 3 segundos, limpa a tela și inițializa o Watchdog delay (3000); display.fillScreen (ST77XX_BLACK); display.setCursor (0, 0); setupWatchdog (); }
setupDisplay
// Incializa o display, muda a orientação e limpa a telavoid setupDisplay () {// Inicializa o display display.initR (INITR_BLACKTAB); // Rotaciona o conteúdo mostrado display.setRotation (1); // Pinta a tela de branco display.fillScreen (ST77XX_BLACK); display.setTextColor (ST77XX_WHITE); }
setupWiFi
// Conecta ao AP void setupWiFi () {WiFi.disconnect (); WiFi.mode (WIFI_STA); WiFi.begin (SSID, PAROLĂ); display.println ("Conectarea la" + Șir (SSID)); // Enquanto não estiver conectado à rede WiFi while (WiFi.status ()! = WL_CONNECTED) {delay (500); display.print ("."); } display.println (""); display.print ("Conectat la"); display.println (SSID); }
connectToServer
void connectToServer () {display.println ("Încercarea conexiunii socket"); // Espera o conexiune cu serverul while (! Socket.connect (HOST, PORT)) {display.print ("."); întârziere (500); } display.println (); display.println ("Conectat!"); // Tempo máximo que o cliente debe demorar para responder // antes de dizermos que a conexão foi perdida socket.setTimeout (TIMEOUT); }
IRAM_ATTR resetModule și setupWatchdog
// função que o temporizador irá chamar, para reiniciar o ESP32void IRAM_ATTR resetModule () {ets_printf ("(watchdog) reiniciar / n"); esp_restart_noos (); // reinicia o chip} void setupWatchdog () {timer = timerBegin (0, 80, true); // timerID 0, div 80 // timer, callback, interrupção de borda timerAttachInterrupt (timer, & resetModule, true); // timer, tempo (us), repetição timerAlarmWrite (timer, 10000000, true); timerAlarmEnable (timer); // habilita a interrupção}
buclă
bucla void () {timerWrite (timer, 0); // reseta o temporizador (alimenta o watchdog) checkConnection (); // checa se possui conexão com o server checkRSSI (); // verifica o rssi plot (); // mostra o grafic de istoric de rssi sendToServer (); // envia uma mensagem com um contador pentru server readFromServer (); // espera a confirmmação do server log (); // salva um log no cartão SD delay (1000); // espera um segundo}
checkConnection
void checkConnection () {// Verifică o conexiune cu AP dacă (WiFi.status ()! = WL_CONNECTED) {display.fillScreen (ST77XX_BLACK); display.setCursor (0, 0); display.println ("WiFi deconectat"); setupWiFi (); întârziere (1000); } // verificați conexiunea cu socketul dacă (! socket.connected ()) {display.fillScreen (ST77XX_BLACK); display.setCursor (0, 0); display.println ("Socket deconectat"); connectToServer (); întârziere (3000); display.fillScreen (ST77XX_BLACK); }}
verificați RSI
void checkRSSI () {// Verifica o RSSI rssi = WiFi. RSSI (); // Limpa o text e mostra o RSSI no display clearText (); display.setCursor (0, 0); display.print ("RSSI:" + Șir (rssi)); // Se a quantitate de barras do gráfico passou do limite apagamos o registro mais antigo if (rssiHistory.size () == (DISPLAY_WIDTH - 2 * PLOT_MARGIN) / 2) {rssiHistory.erase (rssiHistory.begin ()); } // Adiciona no final do histórico (mais recente) rssiHistory.push_back (rssi); }
complot
void plot () {// Coloca no ponto inicial și limpamos o gráfico currentX = PLOT_MARGIN; display.fillRect (PLOT_MARGIN, 2 * PLOT_MARGIN, DISPLAY_WIDTH - 2 * PLOT_MARGIN, DISPLAY_HEIGHT - 2 * PLOT_MARGIN, ST77XX_BLACK); // Para cada valor do histórico fazemos o cálculo do tamanho da barra do gráfico, desenhamos și avansamos for the next for (int i = 0; i -120? Map (rssiHistory , -120, 0, 0, PLOT_SIZE): 0; display.drawFastVLine (currentX, DISPLAY_HEIGHT - valoare, valoare, PLOT_COLOR); currentX + = 2;}}
sendToServer
void sendToServer () {// Se estiver conectat cu serverul if (socket.connected ()) {// Envia um hello com um contador, mostra no display e incrementa o contador String writing = "Hello" + String (count); display.setCursor (0, 10); display.println ("Trimiterea:" + trimiterea); socket.println (trimiterea); socket.print (String (rssi)); conta ++; }}
readFromServer
void readFromServer () {// Espera até o server trimite ceva sau desconectar while (socket.connected () &&! socket.available ()) {delay (100); } // Se tem ceva pentru receber if (socket.available ()) {// Faz a leitura, remove o / n do final e mostra no display received = socket.readStringUntil ('\ n'); primit.remove (primit.lungime () - 1); display.println ("Primit:" + primit); }}
clearText și jurnal
void clearText () {// Limpa a area com o text da mensagem vinda do client display.fillRect (0, 0, DISPLAY_WIDTH, 2 * PLOT_MARGIN, ST77XX_BLACK); } void log () {// Abrimos o arquivo para escrevermos no final dele File file = SD.open (FILE_PATH, FILE_APPEND); // Se nu reușește să deschidă arhivul mostramos uma mensagem de erro if (! File) {Serial.println ("Fail to open file"); întoarcere; } // Gravamos uma linha com o tempo since o boot, o rssi atual e a mensagem recebida String data = String (millis ()) + ";" + Șir (rssi) + ";" + primit; file.println (date); file.close (); }
Pasul 10: Fișiere
Descărcați fișierele:
EU NU