Erste Schritte mit dem Microcontroller ESP8266/NodeMCU
https://oer-informatik.de/helloworld_nodemcu
tl/dr; (ca. 12 min Lesezeit): Keine neue Programmiersprache ohne ein “Hello World”, kein Microcontroller-Projekt ohne LED-Blinken. Hier geht es nur um die ersten Schritte mit dem NodeMCU-Board: Einrichtung und zwei kleine Beispielprogramme zur Nutzung der internen LED und Taster.
Treiber für das NodeMCU-Board installieren
Damit der Microcontroller auf dem NodeMCU erkannt wird, muss zunächst ein Treiber in der Arduino-IDE nachinstalliert werden (oder geprüft werden, ob die Einstellungen bereits vorhanden sind).
Unter Datei/Einstellungen
(bzw. File/Preferences
) gibt es unten den Punkt “Additional boards manager URLs”, in dem (ggf. neben weiteren) auch die folgende URL eingetragen werden muss:
http://arduino.esp8266.com/stable/package_esp8266com_index.json

Nach dem Klick auf “ok” wird die verlinkte JSON-Datei geladen. Kann im Boardmanager der entsprechende Treiber geladen werden. Boardsmanager öffnen (Tools/Board/BoardsManager
):

Im Boards-Manager nach “ESP8266” suchen und die Boards installieren:

Port und Board
Der häufigste Fehler bei der Programmierung in der Arduino-IDE ist die Auswahl eines falschen Boards / Ports. Immer, wenn Fehler beim Übertragen eines Programms auftauchen, sollte überprüft werden, ob die folgenden Einstellungen stimmen.
An welchem Port hängt mein NodeMCU?
Unter Windows-Systemen wird dem NodeMCU ein COM-Port zugewiesen. Die zugewiesene Nummer weicht dabei ab, wenn unterschiedliche weitere Geräte angemeldet sind. An welchem COM-Port an NodeMCU hängt, lässt sich nach Anschluss der Boards per USB z.B. mit Hilfe der PowerShell und des folgenden Befehls ermitteln:
Class Name Description PNPDeviceID
----- ---- ----------- -----------
Ports Silicon Labs CP210x USB to UART Bridge (COM4) Silicon Labs CP210x USB to UART Bridge U
In meinem Fall wurde dem Board COM4
zugewiesen. Sollte dem ESP kein Port zugewiesen werden (Port ist dann oft ausgegraut), dann ist möglicherweise der USB-Treiber für den verwendeten Chip nicht installiert (USB-zu UART-Bridge). Die Software ist schnell nachinstalliert - mit etwas Mut, denn die Herstellerseiten sind mitunter komplett chinesisch:
Am häufigsten sind CP210x-Chips verbaut. Die Treiber sind meistens bereits im System vorhanden. Falls nicht bietet deren Hersteller SiliconLabs auf dieser Internetseite die Treiber an.
Etwas seltener findet man CH340 oder ähnliche Chips. Deren Treiber müssen meistens noch installiert werden. Der Hersteller bietet sie auf dieser Seite (falls Darstellung chinesisch: unten CH341SER.EXE)
In der IDE wird der entsprechende Port über Tools/Port
eingetragen:

Das zugehörige (und eben installierte) Board wird ebenso unter Tools
eingetragen. Unter Tools/Board/esp8266
öffnet sich eine lange Liste:

Aus dieser Liste sollte der neuste NodeMCU-Treiber gewählt werden:

Damit ist alles Startbereit für den ersten Sketch!
Microcontroller “Hello World” - Blinken!!!
Für ein erstes “Hello World” nutzen wir die intern verbauten LED und Taster des nodeMCU: Eine LED auf dem Microcontrollerboard, die mit dem Ausgang D4
verschaltet ist, eine LED auf dem nodeMCU-Board, die mit dem Ausgang D0
verschaltet ist und ein Taster (“FLASH”), der am Eingang D3 angeschlossen ist:

Wir nutzen die Arduino-IDE, um diese internen LED und Taster anzusteuern. Ein Arduino-Sketch besteht im wesentlichen aus fünf Komponenten, von denen drei durch uns konfigurierbar sind:
Nach dem Start wird eine Funktion
init()
aufgerufen, die alle nötigen Bibliotheken lädt und konfiguriert. Diese Methode wird uns nicht angezeigt und ist nicht konfigurierbar.Danach kommt ein Bereich, in dem wir eigene Variablen erzeugen können, die wir in unserem Sketch benötigen. Das werden wir später nutzen.
Darauf folgt eine
setup
-Methode, in der wir alle Konfigurationen vornehmen können, die für unser Programm erforderlich sind. Diesetup()
-Methode wird genau einmal aufgerufen.Nach der
setup()
-Methode folgt eine Dauerschleife. Die Schleife selbst sehen wir nicht, wir wissen nur, dass in ihr eine weitere Methode aufgerufen wird:Die
loop()
-Methode befindet sich in der Dauerschleife. In derloop()
-Methode befindet sich die eigentliche Programmlogik - entweder direkt, oder in Form von Funktionsaufrufen.
Grafisch lässt sich das ganze als Programm-Ablaufplan (PAP) darstellen:1

LED am Prozessorchip ESP-12
Eine interne LED ist am ESP-12 über 470 Ohm mit dem GPIO D4
verbunden. Wir können sie mit ein paar Zeilen Code ein- und ausschalten.

Das Programm besteht aus wenigen Zeilen Code:
In der setup()
-Methode werden alle Operationen aufgerufen, die genau ein einziges Mal beim Starten ausgeführt werden müssen. Hier wird konfiguriert, dass es sich bei dem an D4
angeschlossenen Gerät um ein Ausgabedevice handelt:
In einer zweiten Methode, die in Arduino-Sketches immer vorkommt, werden alle Operationen aufgerufen, die in einer Dauerschleife laufen sollen. Hier wird an den Ausgabepin D4
abwechselnd ein HIGH
- (3,3V) und ein LOW
-(0V) Potenzial angelegt. Die LED sollte also blinken.
void loop() {
digitalWrite(D4, HIGH); // set HIGH potential on D4 (3,3V)
delay(1000); // wait for a second (1000ms)
digitalWrite(D4, LOW); // set LOW potential on D4 (0V)
delay(100); // wait for 0,1 seconds (100ms)
}
Das Potezial wird lange auf HIGH
und kurz auf LOW
gelegt - wir erwarten also ein langes leuchten und eine kurze Pause. Wie blinkt die LED aber wirlich?
Es ist genau umgekehrt: lange Pause, kurzes Leuchten! Um das Verhalten zu verstehen müssen wir uns die interne Schaltung ansehen:

Sobald an D4
ein LOW
-Signal anliegt ergibt sich eine Spannungs-Potenzialdifferenz (3,3V - 0V), die zu einem Stromfluss durch die LED führt. Liegt an D4
ein HIGH
-Potenzial an, so ergibt sich keine Potenzialdifferenz (beide Seiten auf 3,3V) und die LED leuchtet nicht. Die LED verhält sich also gerade umgekehrt, als man es erwarten würde: sie ist bei einem anliegenden LOW
-Potenzial aktiv, man nennt dies auch low-active.
LED am nodeMCU-Board (nahe des Micro-USB-Ports)
Es gibt eine zweite LED am nodeMCU-Board, zwischen dem “RST”-Taster und den gelben Bauelementen:

Diese LED ist genauso an D0
verschaltet wie die vorige LED an D4
:

Wir können daher alle Überlegungen von oben übernehmen, auch das Programm sieht genauso aus, wir müssen lediglich D4
durch D0
ersetzen:
void setup() {
pinMode(D0, OUTPUT); // define Pin D0 as an Output
}
void loop() {
digitalWrite(D0, HIGH); // set HIGH potential on D0 (3,3V) => LED off (3V3-3V3, no current)
delay(1000); // wait for a second (1000ms)
digitalWrite(D0, LOW); // set LOW potential on D0 (0V) => LED on (GND-3V3, current)
delay(100); // wait for 0,1 seconds (100ms)
}
Taster am nodeMCU-Board
Der FLASH
-Taster, der neben dem Micro-USB-Port sitzt, lässt sich ebenfalls direkt für Programme nutzen. Er darf nur beim Booten des ESP-Boards nicht betätigt sein, danach kann er frei genutzt werden:

Intern ist er mit dem D3
-Eingang verschaltet und verfügt über einen Pull-Up-Widerstand. Das heißt: wenn der Taster nicht betätigt ist, liegt ein HIGH
-Signal an D3
an.

Bei Betätigung liegt an D3
eine sehr niedrige Spannung an, die als LOW
-Signal interpretiert wird. Es sind nicht exakt 0 V
, da zwischen D3
und GND
noch ein 470\ \Omega Widerstand liegt. Die Potenzialdifferenz zwischen GND
(0V) und 3V3
(3,3V) teilt sich im Verhältnis der Widerstände auf, an D3
liegen also 0,11V an:
U_{D3} = 3,3 V \cdot \frac{430 \Omega}{12.000 \Omega + 430 \Omega} = 0,11 V
Gemäß Datenblatt erkennt der ESP8266 Eingangssignale zwischen -0,3V und 0,8 V gesichert als LOW
, wir sind somit also auf der sicheren Seite. Der Arduino-Sketch ist folgendermaßen aufgebaut:
In der
setup()
-Methode wird der PinD3
als Eingang festgelegt:pinMode(D3, INPUT);
. Die LED an PinD4
wird wieder als Ausgang genutzt.In der Dauerschleife (
loop()
) wird ausgelesen, ob das anliegende Potenzial anD3
einLOW
-Pegel ist:if (digitalRead(D3)==LOW){...}
.Bei anliegendem
LOW
-Pegel wird die LED anD4
aktiviert (wie im obigen Beispiel).Für alle anderen Fälle (also bei anliegendem
HIGH
-Pegel) wird imelse{...}
-Block die LED deaktiviert.
Im Ganzen sieht das so aus:
void setup() {
pinMode(D3, INPUT);
pinMode(D4, OUTPUT);
}
void loop() {
if (digitalRead(D3)==LOW){
digitalWrite(D4, LOW); // set LOW potential on D4 (0V) => LED on (GND-3V3, current)
}else{
digitalWrite(D4, HIGH); // set HIGH potential on D4 (3,3V) => LED off (3V3-3V3, no current)
}
}
Wo befinden sich die versteckten Programmbestandteile?
Für alle, die es genau wissen wollen (alle anderen können diesen Absatz getrost überspringen):
Eingangs wurde erwähnt, dass es über die beiden oben genannten Funktionen setup()
und loop()
hinaus noch weiteren Programmcode gibt, den die Arduino-IDE aber vor uns versteckt. Gibt es eine Möglichkeit danach zu forschen? Gibt es beispielsweise eine main()
-Methode, wie sie die Java und C/C++ Programmierer kennen?
Ja, die gibt es, man kann sie tief im Arduino-Ordner aufspüren, bei den 1.8.x-Versionen der Arduino-IDE in Windows liegt sie beispielsweise hier:
In dieser main.cpp
-Datei befindet sich die main()
-Methode des C++-Programms. Und darin befinden sich die eingangs erwähnten Methodenaufrufe (siehe Programmablaufplan oben) init()
, setup()
und loop()
, sowie die Dauerschleife (hier über for (;;) {
…}` umgesetzt):
int main(void)
{
init();
initVariant();
#if defined(USBCON)
USBDevice.attach();
#endif
setup();
for (;;) {
loop();
if (serialEventRun) serialEventRun();
}
return 0;
}
Für den ESP ist dieser Aufruf nicht ganz so einfach aufzuspüren - und das umgebende Programm etwas aufwändiger. Der Grundaufbau ist aber identisch: setup()
wird einmal aufgerufen, loop()
immer wieder.
Wie geht es weiter?
Weiter geht es im zweiten Teil, in dem digitale Ausgänge genutzt und externe LED angesteuert werden.
Weitere Literatur und Quellen
- Primärquelle ist immer das Datenblatt und die API-Dokumentation von Espressif (dem Chiphersteller)
Quellen und offene Ressourcen (OER)
Die Ursprungstexte (als Markdown), Grafiken und zugrunde liegende Diagrammquelltexte finden sich (soweit möglich in weiterbearbeitbarer Form) in folgendem git-Repository:
https://gitlab.com/oer-informatik/mcu/arduino-esp.
Sofern nicht explizit anderweitig angegeben sind sie zur Nutzung als Open Education Resource (OER) unter Namensnennung (H. Stein, oer-informatik.de) freigegeben gemäß der Creative Commons Namensnennung 4.0 International Lizenz (CC BY 4.0).
Grafik wurde erstellt mit dem PAP-Designer von Friedrich Folkmann: http://friedrich-folkmann.de/papdesigner/Hauptseite.html↩