Ciao e benvenuto al nostro post oggi.
Dopo ieri su HTML e parentesi quadre, oggi vogliamo usare un piccolo circuito per vedere cosa puoi fare con un po 'di HTML e un piccolo script.
Per questo abbiamo bisogno dei seguenti componenti:
Un microcontrollore con chip ESP8266 come ilAmica V2
Un modulo relè come il nostroModulo a 2 relè
un Modulo step-up DC-DC, perché l'Amica fornisce solo 3,3 V, ma il nostro relè ha bisogno di 5 V.
Una breadboard con cavi jumper, come ad esempio il nostro preferitoset
Naturalmente, è anche possibile fornire il modulo relè direttamente con un 5V e salvare il modulo step-up. Questo ha più senso per un progetto finito in un unico alloggiamento, poiché l'Amica può anche essere fornito con lo stesso alimentatore.
Come utilizzare e impostare il modulo step-up, abbiamo già nel nostro post sul blog "Regolatore di tensione CC-CC step-up MT3608descritto".
Colleghiamo i componenti come segue:
Amica V2 |
MT3608 |
relè |
3V3 |
IN + |
|
GND |
IN- |
|
|
OUT + |
VCC |
|
OUT |
GND |
D1 |
|
IN1 |
D2 |
|
IN2 |
Nell'ultimo post abbiamo discusso di come colleghiamo l'ESP a una WLAN esistente e di come rispondiamo a una query dal browser, incluso l'output di un piccolo file HTML.
Ho citato con alcuni tag HTML che non dovrebbero essere usati da HTML5. Nei siti Web moderni, il design è spesso implementato utilizzando fogli di stile a cascata (CSS).
Prima che tutti scappino con la paura che un corso CSS stia arrivando, va detto che è possibile progettare bellissimi pulsanti, testi, cursori e moduli utilizzando CSS.
Se cerchi "pulsanti css" nella ricerca di immagini di Google, vengono visualizzati alcuni esempi.
Ora si tratta dell'implementazione: quale codice cariciamo sul nostro ESP?
Prendiamo il codice dal tutorial come basehttps://randomnerdtutorials.com/esp8266-web-server/e adattare il codice:
/********* Rui Santos Dettagli completi sul progetto a http://randomnerdtutorials.com *********/ // Carichiamo la libreria WiFi che già conosciamo #include <ESP8266WiFi.B> // Qui inseriamo il nome WLAN (SSID) e la chiave di accesso const carbonizzare* ssid = "MeineFritzBox"; const carbonizzare* password = "La mia chiave WiFi"; // Impostiamo il web server sulla porta 80 Server WiFi server(80); // Una variabile per salvare la richiesta HTTP stringa testata; // Qui viene registrato lo stato corrente del relè stringa output5State = "Off"; stringa output4State = "Off"; // I pin GPIO usati // D1 = GPIO5 e D2 = GPIO4 - cerca "Amica Pinout" su Google const int Output5 = 5; const int OUTPUT4 = 4; vuoto configurazione() { serial.iniziare(115200); // Definisce i pin GPIO definiti come output ... pinMode(Output5, USCITA); pinMode(OUTPUT4, USCITA); // ... e prima impostalo su BASSO digitalWrite(Output5, LOW); digitalWrite(OUTPUT4, LOW); // Connessione alla rete tramite WiFi serial.stampare("Connessione a"); serial.println(ssid); WiFi.iniziare(ssid, password); mentre (WiFi.stato() != WL_CONNECTED) { ritardo(500); serial.stampare("."); } // Emette l'IP dal web server sul monitor seriale serial.println(""); serial.println("WiFi connesso."); serial.println("Indirizzo IP:"); serial.println(WiFi.LocalIP()); server.iniziare(); } vuoto cappio(){ WiFiClient cliente = server.disponibile(); // ascolta le richieste dei clienti se (cliente) { // Se si connette un nuovo client, serial.println("Nuovo cliente."); // output su monitor seriale stringa linea corrente = ""; // crea una stringa con i dati in arrivo dal client while (client.connected()) { // ripetere finché il Client è collegato if (client.available()) { // Caso C'è un Byte da leggere, char c = client.read(); / Leggi il Byte e poi ... Seriale.write(c); // lo esponi sul Monitor seriale header += c; if (c == '\n') { // se il Byte è una nuova riga Char // quando la riga corrente è vuota, ne arrivano due di fila. // questa è la fine della richiesta del Client HTTP, quindi inviamo una risposta: if (currentLine.length() == 0) { // Header HTTP iniziano sempre con un codice di risposta (per esempio HTTP / 1.1 200 OK)) // seguito da un tipo di Content che permette al Client di sapere cosa segue, seguito da una riga vuota: client.println("HTTP / 1.1 200 OK"); client.println("Content-type: text/html"); client.println("Connection: close"); client.println(); // Qui i GPIO Pins sono accesi o spenti if (header.indexOf("GET / 5 / on") >= 0) { Seriale.println("GPIO 5 on"); output 5state = "on"; writer digitali(output 5, Alto); } else if (header.indexOf("GET / 5 / off") >= 0) { Seriale.println("GPIO 5 off"); output 5state = "off"; writer digitali(output 5, LOW); } else if (header.indexOf("GET / 4 / One") >= 0) { Seriale.println("GPIO 4 on"); output 4state = "on"; writer digitali(output 4, Alto); } else if (header.indexOf("GET / 4 / off") >= 0) { Seriale.println("GPIO 4 off"); output 4state = "off"; writer digitali(output 4, LOW); } // Visualizza la pagina HTML: client.println("<!DOCTYPE html>< html>"); client.println("<head>< meta name=\ "viewport\" content=\ "width=device-width, initial-scale=1\" >"); client.println("<link rel=\ "icon\" href=\ " data:,\" & gt;"); // Segue il codice CSS per progettare gli on/off // In questo caso è possibile adattare la felce di fondo e la dimensione del carattere (font-size) client.println("<style> html { font-family: Helvetica; display: block inline; margin: 0px auto; text-align: center;}"); client.println(".button {background color: #333344; border: none; color: white; padding: 16px 40px;"); client.println("text-decoration: none; font-size: 30px; margin: 2px; cursor: pointer;}"); client.println(".button2 {background color: #888899;}< / style>< / head>"); // Titolo Del Sito Web client.println("< body>< h1 & gt; ESP8266 Web Server< / h1 & gt;"); // Mostra lo stato attuale e AN / da Buttons for GPIO 5 client.println("<p> GPIO 5-State " + output 5state + "< / p & gt;"); // se output5State = off, mostra una spilla if (output 5state=="off") { client.println("<p><a href=\"/5/on\"><button class=\"button\">UN</button></a></p>"); } else { client.println("<p><a href=\"/5/off\"><button class=\"button button2\">DI</button></a></p>"); } // Lo stesso per GPIO 4 client.println("<p> GPIO 4-Stato " + output 4state + "< / p & gt;"); // Se output4State = off, mostra una spilla if (output 4state=="off") { client.println("<p><a href=\"/4/on\"><button class=\"button\">UN</button></a></p>"); } else { client.println("<p><a href=\"/4/off\"><button class=\"button button2\">DI</button></a></p>"); } client.println("< / body>< / html>"); // Terminare la risposta HTTP con una riga a vuoto client.println(); /# e ce ne andremo con un break # break; } else { // in caso di creazione di una nuova riga, cancella la riga corrente currentLine = ""; } } else if (c != "\r") { / se succede qualcosa che non è una rottura di Riga, currentLine += c; // inserirlo alla fine di currentLine } } } // Elimina la variabile Header per il prossimo ciclo header = ""; // Chiudere il collegamento client.arresto(); serial.println("Client disconnesso."); serial.println(""); } }
Carichiamo il codice sul nostro Amica e apriamo il monitor seriale nell'IDE di Arduino:
Successivamente digitiamo nel browser, ad es. sul telefono cellulare, l'indirizzo IP del server. (Attenzione, il PC o lo smartphone devono essere collegati alla stessa rete dell'ESP).
Ora possiamo facilmente cambiare i relè dallo smartphone (o dal PC).
E se dai un'occhiata a Internet, puoi anche trovare pulsanti più belli, come questo:
Il codice HTML e il codice CSS per questi pulsanti sono disponibili all'indirizzohttp://jsfiddle.net/tovic/ve8mU/light/
Spero che questo articolo ti abbia dato un'idea delle possibilità del server web ESP.
Se ti è piaciuto questo post, apprezzerei un breve feedback. Scrivici se sei interessato all'argomento SVG per la visualizzazione di barre e piccoli grafici vettoriali con il web server ESP.
Spero che ti piaccia costruirlo e dire addio al prossimo articolo.
10 commenti
Andreas Wolter
@Thomas Schultz: ab Zeile 60
if (client.available()) {
beginnt die aktualisierung der Webseite. Mein Vorschlag wäre, die Bedingung durch ein ODER zu erweitern, damit auf die Inputs reagiert werden kann. Folglich müsste man vorher die Inputs auslesen und falls sich diese geändert haben, müsste man dann in die Bedingung diese Änderung einbringen. Als Beispiel:
int inputA_new = 0;
int inputA_old = 0;
inputA_new = digitalRead(EINGANG);
if (client.available() || inputA_new != inputA_old) {
….
//zeige Werte aus Input A
}
inputA_old = inputA_new;
für zwei Eingänge wäre das dann wie folgt:
int inputA_new = 0;
int inputA_old = 0;
int inputB_new = 0;
int inputB_old = 0;
inputA_new = digitalRead(EINGANG_A);
inputB_new = digitalRead(EINGANG_B);
if (client.available() || inputA_new != inputA_old || inputB_new != inputB_old) {
….
//zeige Werte aus Input A
//zeige Werte aus Input B
}
inputA_old = inputA_new;
inputB_old = inputB_new;
@Georg: etwas spät, aber: der AsynchWebserver ist anders gelöst. eventuell hilft Ihnen das weiter: https://techtutorialsx.com/2018/01/01/esp8266-arduino-asynchronous-http-web-server/
Thomas Schultz
Hallo und vielen Dank für dieses schöne Beispiel.
Ich habe es mal direkt für mein aktuelles Project benutzt.
Ich habe nur ein kleine Problem, zusätzlich würde ich gerne noch zwei
Kontaktausgänge eines anderen Moduls auslesen. Das auslesen ist kein
Problem, auch das anzeigen nicht… aber die Webseite wird im vorliegenden
ja nur bei Änderungen eines Relais neu aufgebaut.
Wie kann ich das auch mit zwei INPUTS bewerkstelligen?
Für entsprechende Hilfe wäre ich sehr dankbar
Thomas
Phil Phras
Ich bin bei der IdeenSuche für eins meiner Projekte auf diesen Blog gestoßen und bin begeistert!
Ich habe auch in anderen Blogs hier gestöbert und möchte ein großes Lob aussprechen.
Hier werde ich StammLeser :-) Und wenn ich mal wieder eins meiner Projekte veröffentliche geb ich auf jeden Fall diese Seite hier an als Ideen- und CodeQuelle an.
Vielen Dank
georg
hallo,
das thema ist inzwischen recht alt :-( , für mich aber noch aktuell…
habe versucht den code mit einem asyncwebserver zu kombinieren (die verwendung dieser art des webservers lässt sich aus anderen gründen nicht mehr ändern) – beim compileren wurde die kombination unter anderem mit – ‘class AsyncWebServer’ has no member named ‘available’ – quitiert…
Was kann ich da machen?
gruss
Thmas Nimpsch
Hallo ,
Vielen Dank für dieses Beispiel, genau danach hab ich gesucht.
Gruß
Thomas Nimpsch
N1d45
Schalter die sich automatisch aktualisieren währen nicht schlecht.
Sprich wenn ich von mehreren Geräten auf die Webseite zugreife. Zum Beispiel schalte ich mit dem Smartphone Kanal 1 ein, wird auf dem PC automatisch angezeigt das der Schalter 1 auch ein ist.
Oder das wenn ich per Taster Kanal 1 ein schalte, das auch auf der Webseite automatisch angezeigt wird das der Kanal 1 eingeschaltet ist.
Bisher muss man immer die Webseite neuladen, z.B. mit F5 um das aktuelle Ergebniss zu sehen.
Tobî
an Herbert.
Versuche doch den Taster mal mit einem Interrupt aus.
Ich hoffe ich darf hier einen Link posten, wenn nicht:
Herbert suche mal auf deiner Suchmaschine deines Vertrauens nach: ESP8266 External Interrupt.
https://techtutorialsx.com/2016/12/11/esp8266-external-interrupts/
Herbert
Toller Beitrag, soweit funktioniert auch alles.
Mein Problem ist das ich zusätzlich noch einen Hardware Taster einbauen wollte.
Der aber nicht funktioniert wenn der Client mit dem ESP8266 verbunden ist.
Ich vermute das Problem ist die while (client.connected() funktion. Die verhindert das auf die Tastereingabe parrallel zur Verbindung eines Client funktioniert.
Gibt es dafür eine Lösung? Und warum benötigt man eigentlich die while?
Chris
Hallo Markus,
wäre es möglich noch einen Slider zu integrieren, mit Bsp. Sketch?
LG
K. Dobler
Hallo Markus,
dein Beispiel hat mir sehr geholfen.
Mit ihm habe ich des geschafft mein Garagentor vom Handy aus zu steuern.
Jetzt geht es nur noch um kleine Anpassungen und Verschönerungen.
Vielen Dank
Kurt Dobler