Motivation

Der Raspberry Pi ist ein populärer, vollwertiger und kostengünstiger Einplatinencomputer. Durch seine Vielfalt an Schnittstellen (IO, SPI, PWM, I2C) bietet dieses Gerät umfangreiche Möglichkeiten Werte von Sensoren zu erfassen, mit Aktoren Geräte zu steuern und zu schalten. Durch das Linux Betriebssystem, LAN, WLAN und Bluetooth kann er in das heimische Netzwerk und in das Internet integriert werden. Mit fast beliebigen Programmiersprachen lassen sich einfache und komplexe Anforderungen umsetzen. Die in diesem Kurs eingesetzte Software ist enthalten.

Um Automation, allgemein die Steuerung von Systemen mit dem Gerät durchführen zu können, ist es wichtig zu wissen welche Daten der Raspberry Pi auf welche Art erfassen kann und wie er mit der Außenwelt kommuniziert

Raspberry Pi Zero im Gehäuse

Kursinhalt in der Übersicht

Tag 1

  • Vorbereiten der SD Card (Optional: Wer hat sollte ein Notebook mitbringen)
  • Installation des Raspberry Pi
  • Grundkonfiguration des Betriebssystems
  • Anmelden am Netzwerk
  • Update des Betriebssystems
  • wichtige Linux Befehle und grundlegende Administration des Systems

Tag 2

  • kurze Wiederholung/ Zusammenfassung vom Vortag
  • Installation von Node Red
  • Installation der Nodes und Module/ Paletten
  • Navigation in Node RED
  • Erstes einfaches Programm
  • Installation weitere Services
  • weitere Linux Befehle und Systemadministration

Tag 3

  • Durchsprache der unterschiedlichen BUS- und IO- Systeme
  • Verbindung mit Aktoren und Sensoren
  • Verknüpfung von Sensoren und Aktoren
  • Programmierung
  • weitere Linux Befehle und Systemadministration

Tag 4

  • Vertiefung der Programmierung
  • Was ist MQTT und Einbindung von MQTT (MQTT = MQ Telemetry Transport)
  • Dashboard im Internet auf dem Handy
  • allgemeine Fragen

WLAN Infrastruktur

Anforderungen

Die WLAN Infrastruktur in der VHS hat ein offenes WLAN, es müssen hier vor der Verwendung die Nutzungsbedingungen akzeptiert werden. Für den Kurs ist das hinderlich. Für die Einrichtung der Raspi´s ist es notwendig Zugriff auf den Router und die Liste der Geräte mit den zugehörigen IP Adressen zu haben. Des weiteren ist es notwendig, das die am WLAN angeschlossenen Geräte untereinander kommunizieren können. Nur so kann mit einem anderen Gerät eine Anmeldung auf den Raspberry Pi erfolgen.

Die Verwendung eines Mobiltelefons mit HotSpot Funktion wäre eine denkbare Alternative, jedoch ist diese Funktion bei vielen Telefonen und/ oder Tarifen begrenzt. Durch die nachfolgende Lösung wird dieses Problem ebenfalls gelöst.

Lösung

Eine Fritz Box 7390 wird als WLAN Access Point und Router mit DHCP Service verwendet. Die Fritz Box stellt die Internetverbindung über eine bestehende WLAN Verbindung her. Der Internetanbieter kann dabei ein Handy mit Hotspot Funktion oder ein anderes WLAN sein. Als Ergebnis sind alle im Kurs eingesetzten Geräte im selbst verwalteten Netzwerk und können in der Fritz Box administriert werden.
Diese Umgebung simuliert ist eine typische Installation zu Hause.

Netzwerkinfrastruktur

Internetzugang in Fritz Box

Fritz Box Zugang zum Internet
WLAN QR Code

Design Thinking Prozess

In diesem Kurs werden wir mit einem Raspberry Pi exemplarisch eine Steuerung aufbauen, welche die verschiedenen IO Ports und BUS Systeme verwendet. Dabei werden wir mit Sensoren Daten erfassen und auf Basis der Messergebnisse Relais, allgemein Aktivitäten, ansteuern.

Die fünf Phasen sind: Verstehen, Definieren, Ideation, Bauen, Testen

Design Thinking beschreibt eine Entwicklungsmethode mit der in 5 Phasen von der Idee bis zum fertigen Produkt geleitet wird.

Um möglichst flexibel zu sein, bauen wir die Steuerung auf einem Entwicklungsboard/ einem Steckbrett zusammen. Die entsprechenden elektrischen Module und Verbindungen werden wir besprechen. Die Spannungsversorgung erfolgt über das Raspberry Pi Netzteil.

  • Verstehen was das Problem und die Wünsche, Ziele sind
  • Definieren des Standpunktes
  • Ideation, Ideen entwickeln wie eine Umsetzung zur Lösung des Problems führen kann
  • Bauen, Umsetzen der Idee und aufbauen eines Prototypen
  • Testen, Inbetriebnahme und verproben der aufgebauten Lösung
Die Loop als Treiber

Beobachten
Die reale Welt beobachten und aufnehmen

Reflektieren
Beobachtungen Zusammenfassen und auf die eigene Situation abbilden

Machen
Der eigenen Idee eine Form und Gestalt verpassen


MQTT (Message Queue Telemetry Transport)

Den Status von einem Sensor abfragen oder ein Relais etc. schalten sollte verlässlich und mit geringem Aufwand erfolgen. Gleichzeitig ist es wichtig die Kommunikation standardisiert zu führen. MQTT ist ein schlankes Protokoll und konsolidiert die Werte von Sensoren in einem Broker.

Was macht MQTT so interessant?

MQTT standardisiert die Kommunikation von IoT Geräten untereinander, hilft einfache Applikationen auf Endgeräten zu erstellen und vereinfacht die Interoperabilität. MQTT ist auf vielen IoT Geräten, Microcontrollern, etc. etabliert.

Begriffe und wesentliche Bestandteile

BegriffBeschreibung
BrokerDer Broker ist das Herzstück von MQTT. Hier laufen die Informationen zusammen, der Broker enthält alle Informationen und sorgt für die Verteilung der Informationen an die Clients.
ClientEin Client kommuniziert mit dem Broker. Der Client kann Informationen an den Broker senden oder Daten empfangen. Ein Client kann jedes beliebige Endgerät sein, welches mit dem Broker kommunizieren kann. Beispiele sind: Mobiltelefone, Microcontroller, IoT Geräte. Clients kommunizieren niemals mit anderen Clients, sondern immer nur mit dem Broker.
MQTT ProtokollDas MQTT Protokoll basiert auf dem TCP/IP Framework, Layer 5-7.
ClientIDJeder Client erhält vom Broker eine eindeutige ClientID. Zu diesem Client speichert der Broker unter anderen auch den Status
Will MessageEin Client kann dem Broker eine spezielle Message mit dem „letzten Willen“, Testament senden. Diese Message dient dazu anderen Clients (über den Broker) mitzuteilen wie das Verhalten des Clients ist, falls dieser ungeplant ausfällt. Der Broker sendet dann diese Nachricht stellvertretend für den Client
Keep AliveKeep Alive dient dazu die Kommunikation mit dem Broker aufrecht zu erhalten. Der Broker erkennt unter anderem daran, ob der Client noch aktiv (am Leben) ist.
QoSDas QoS Flag bestimmt die Qualität einer Verbindung zwischen Client und Broker. Es gibt die Zustände 0,1,2.
0 = „at most once„; enspricht „fire and forget“
1 = „at least once„; Nachricht wird min. 1x gesendet und kann mehrfach beim Empfänger ankommen
2 = „exactly once„; Nachricht kommt garantiert nur einmal beim Empfänger an. Die Nachricht kann sich verzögern und muss bestätigt werden, aufwendigere Kommunikation
TopicTopics definieren den Pfad zur Abspeicherung der Daten, quasi die Datenstruktur. Topics können frei gewählt werden. Es gibt allerdings Ausnahmen:
– $ : Beginnt ein Topic mit einen $ Zeichen, so handelt es sich um interne Statistiken des Brokers. Diese Topics können Nicht beschrieben werden
Grundsätzliche Regeln zur Namensregelung eines Topics:
– Kein / am Anfang verwenden
– Kurz wie möglich halten
– keine Leerzeichen verwenden
– keine Sonderzeichen verwenden, nur ASCII Zeichen und Zahlen 0-9

MQTT Begriffe und Grundlagen

MQTT Server Mosquitto

Auf dem Raspberry Pi kann der Server „Mosquitto“ verwendet werden. Die Installation ist einfach und wenn keine speziellen Konfigurationen gewünscht sind, erfolgt die Inbetriebnahme in wenigen Schritten. Nachfolgende Schritte einfach komplett oder einzeln kopieren und auf dem Raspberry Pi ausführen:

sudo apt-get update
sudo apt-get upgrade
sudo apt-get install mosquitto
sudo apt-get install mosquitto-clients
sudo systemctl enable mosquitto

Anpassung hier für den Kurs

Der Einfachheit halber aktivieren wir den Zugriff auf allen IP-Interfaces und geben auch den „nicht angemeldeten“ Zugang (Anonymous) frei. Die folgenden Zeilen werden dazu der Konfigurationsdatei /etc/mosquitto/mosquitto.conf angehängt. Wie die Konfiguration im Detail angepasst werden kann, ist in der Dokumentation des Projektes enthalten.


#Hier startet die Anpassung
#
allow_anonymous true
bind_address 0.0.0.0

Danach am besten den Raspberry Pi neu starten und mit dem MQTT Explorer den Zugriff testen.

MQTT Explorer

MQTT Clients


LCD2004A mit I2C

Der Anschluss eines LCD Displays ist ebenfalls möglich. Wie dieses angeschlossen und in Node-RED eingebunden wird ist in folgendem Blogartikel zu lesen.


Arbeitsmaterial

Für den Kurs wird folgendes Arbeitsmaterial benötigt und muss vom Teilnehmer beschafft werden, zum Kurs mitzubringen:

Um unsere Steuerung mit dem Raspberry Pi zu entwickeln orientieren wir uns am „Design Thinking Prozess„.

  1. Raspberry Pi (Pi Zero WH, Raspberry PI3+ B, Raspberry Pi 4), inkl. Netzteil und min. 16GB micro SD Card
  2. Steckbrett mit 800 Kontakten, Verbindungskabel und Steckbrücken
  3. GPIO Verbinder mit Flachbandkabel
  4. Relaiskarte
  5. ADS1115 ADC Modul I2C
  6. Sensor DHT11 oder DHT22, BME280 als I2C Versionen
  7. OLED Display 0.96″ I2C
  8. ggf. HDMI Adapter (Pi4 hat einen Micro HDMI Anschluss, hier wird ein Adapter auf HDMI benötigt), USB-Tastatur, USB-Maus
  9. falls Vorhanden elektronische Bauteile: Widerstände, LEDs, Trimmpotentiometer, …
  10. falls vorhanden, Elektronikwerkzeug: Schraubendreher, Flachzange, Seitenschneider
  11. falls vorhanden: Notebook mit WLAN, SD Karten Lese/ Schreibadapter

Übersicht Steckbrett

Labor Aufbau mit Steckbrett (Auf das Bild klicken für größere Ansicht)

Verkabelung des Streckbrettes

Verkabelung der Module und Komponenten (Auf das Bild klicken für größere Ansicht)

Die Leuchtdioden können grün, gelb oder rot sein. Der lange Pin ist die Anode (+Pol). Die Widerstande sollten nicht zu niedrig gewählt werden. Die GPIOs gilt es so wenig wie möglich zu belasten. Ein Strom von 5mA ist ein guter Wert. Damit ergibt sich als Vorwiderstand für die LED nach folgender Formel R = U/I = (3.3V – 2VLED) / 0.005A = 1.3V / 0.005A = 260Ohm. Der nächste Normwert ist 270Ohm. Werte bis zu 1.5kOhm sind ebenfalls in Ordnung.

Der Wert für den Widerstand R2 kann ebenfalls 270 Ohm aufwärts sein. Hierbei handelt es sich um einen PULL UP Widerstand, es kommt nicht auf den Strom an, sondern nur das der Port ein definiertes Potenzial hat.


Als Sensoren verwenden wir Schalter, Spannungswandler, Temperatur, Luftfeuchtigkeit, LCD Displays, etc. (Siehe Stückliste unten)

Steckbrett mit Verbindungskabel

Als Aktoren verwenden wir eine Relais Karte zur Ansteuerung von kleinen und großen Lasten.

LCD Anzeige 128×64 Pixel

Zur Visualisierung wird eine Oberfläche im Webbrowser erstellt, diese kann auf dem Handy im hauseigenen WLAN oder auch über das Internet erreicht werden. Die Anzeige auf einem LCD Display direkt am Raspberry Pi angeschlossen ist ebenfalls möglich.

Für den Aufbau der Testumgebung wird folgendes Material benötigt. Dazu habe ich eine Liste vorbereitet. Einige der Komponenten lassen sich deutlich günstiger Beschaffen, wenn anstatt einem mehrere gekauft werden. So lassen sich auch durch eine Sammelbestellung Einsparungen vornehmen und auch Versandkosten sparen.


Stückliste | Bauteileliste

AnzahlArtikelBeschreibungLieferantPreis ca.
1Raspberry Pi Zero WHEinplatinencomputer, Alternativ geht auch ein Raspberry Pi 3B+, 4Berrybase, und diverseab 15,00€
1Gehäuse Pi ZEROEin Minigehäuse für den Raspberry Pi Zero (OPTIONAL)AZ-Deliveryab 2,00€
140 Pins GPIO Breakout BoardVerbindung zwischen dem Raspberry Pi und dem Breakout Board (Link)AZ-Delivery8,00€
1ADS1115 ADC Modul 16bit 4 Kanäle I2CAnalog Digitalwandler mit 4 Kanälen und 16Bit Auflösung I2C (Link)AZ-Delivery5,00€
1IO-PORT Expander I2C
(Optional für den Raspi Kurs nicht zwingend notwendig)
Entweder als Modul oder als IC, eventuell Lieferengpass beachten
Microchip Technology MCP23017-E/SP Schnittstellen-IC – E-A-Erweiterungen POR I²C 1.7 MHz SPDIP-28. Wenn als IC-Version, dann bitte unbedingt ALS DIP Package und kein SMD!!!
Diverseab 2,80€
1DHT22 AM2302 Temperatursensor und LuftfeuchtigkeitssensorSensor mit 1-Port Anschluss für Temperatur und Luftfeuchtigkeit (Link)AZ-Delivery5,00€
1DHT11 Temperatursensor und LuftfeuchtigkeitssensorAlternativ: Sensor mit 1-Port Anschluss für Temperatur und Luftfeuchtigkeit (Link)AZ-Delivery5,00€
1Raspberry Pi GPIO Breakout KitBeinhaltet Breakout Board, GPIO-T-Erweiterungsplatine, 40pol Flachbandkabel, Prototyp Board (Link)Amazon11,00€
1RelaiskarteRelaisboard mit 2 Relais, Optokoppler, 3,3V/ 5V (Link)AZ-Delivery6,00€
1Set SteckbrückenDiese Steckbrücken ermöglichen die lötfreie elektrische Verbindung auf dem Steckbrett (Link AZ-Delivery) (Link Amazon)Amazon7,00€
1LCD Display (OPTIONAL)0,96 Zoll OLED SSD1306 Display I2C 128 x 64 Pixel kompatibel mit Arduino und Raspberry Pi, es geht auch ein anderes Display, sollte jedoch I2C Bus haben (Link)AZ-Delivery7,49€
1AdapterUSB, HDMI Adapter (Zum Anschluss von Tastatur, Maus, Monitor wird abhängig vom verwendeten Raspberry Pi ein Adapter benötigt. Im Schulungsraum werden wir USB Tastatur, Maus und Standard HDMI am Monitor haben)Diverse
1NetzteilRaspberry Pi – offizielles Netzteil für Raspberry Pi 4 Model B, USB-C, 5.1V, 3A weiß (Link)Amazon10,00€
1microSD SpeicherkarteBeispielsweise SANDISK 32GBDiverse11,00€
1ElektronikbauteileVerschiedene Widerstände, LEDs, Transistoren, Taster, TrimmpotentiometerDiverse10,00€
*) alle Preise und Links sind NUR Anhaltspunkte und können abweichen

Die Preise sind eventuell nicht mehr aktuell. Aufgrund von Lieferengpässen und Verfügbarkeiten können die Preise abweichen.


Neben diesen Bauteilen (Hardware) wird auch noch etwas Software benötigt. Diese Software kostet nichts, muss aber installiert sein.

Imager zum initialen beschreiben der microSD Card und zum Übertragen des OS auf die SDCard

Putty eine Terminalemulation um die Administration des Raspberry Pi durchführen zu können


Installierte Module (Pallette)

Die Liste der installierten Module kann aus der Datei ~/.node-red/package.json entnommen werden. Die Daten liegen im Klartext-JSON Format vor.

"ncd-red-ads1115": "~1.2.7",
"node-red-contrib-dht-sensor": "~1.0.4",
"node-red-contrib-oled": "~1.0.5",
"node-red-contrib-toggle": "~0.1.1",
"node-red-dashboard": "~3.1.7",
"node-red-node-pi-gpio": "~2.0.5"

Flow: OUTPUT

[
    {
        "id": "c7fdce3b4d809aa9",
        "type": "tab",
        "label": "OUTPUT",
        "disabled": false,
        "info": "",
        "env": []
    },
    {
        "id": "30fb84ac126efa34",
        "type": "inject",
        "z": "c7fdce3b4d809aa9",
        "name": "OFF",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "1",
        "payloadType": "num",
        "x": 190,
        "y": 120,
        "wires": [
            [
                "657af6ca92a39936"
            ]
        ]
    },
    {
        "id": "657af6ca92a39936",
        "type": "rpi-gpio out",
        "z": "c7fdce3b4d809aa9",
        "name": "",
        "pin": "26",
        "set": "",
        "level": "0",
        "freq": "",
        "out": "out",
        "bcm": true,
        "x": 740,
        "y": 120,
        "wires": []
    },
    {
        "id": "32a3af1f8309fab1",
        "type": "inject",
        "z": "c7fdce3b4d809aa9",
        "name": "ON",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "0",
        "payloadType": "num",
        "x": 190,
        "y": 180,
        "wires": [
            [
                "657af6ca92a39936"
            ]
        ]
    },
    {
        "id": "cc5e0c23e162b002",
        "type": "random",
        "z": "c7fdce3b4d809aa9",
        "d": true,
        "name": "",
        "low": "0",
        "high": "1",
        "inte": "true",
        "property": "payload",
        "x": 490,
        "y": 240,
        "wires": [
            [
                "657af6ca92a39936"
            ]
        ]
    },
    {
        "id": "6fbc194cccafd5a6",
        "type": "inject",
        "z": "c7fdce3b4d809aa9",
        "d": true,
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "3",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "SWITCH",
        "payload": "",
        "payloadType": "date",
        "x": 210,
        "y": 240,
        "wires": [
            [
                "cc5e0c23e162b002",
                "c9c77f8e1fea09d6",
                "a2f4732df6c9ee60"
            ]
        ]
    },
    {
        "id": "c9c77f8e1fea09d6",
        "type": "toggle",
        "z": "c7fdce3b4d809aa9",
        "name": "Toggle",
        "onOffTopic": "",
        "onValue": "0",
        "onType": "num",
        "offValue": "1",
        "offType": "num",
        "toggleTopic": "",
        "toggleValue": "",
        "toggleType": "any",
        "passOnOff": "ifChanged",
        "x": 540,
        "y": 280,
        "wires": [
            [
                "657af6ca92a39936",
                "f50f93d3b6439d78"
            ]
        ]
    },
    {
        "id": "f50f93d3b6439d78",
        "type": "debug",
        "z": "c7fdce3b4d809aa9",
        "name": "",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "false",
        "statusVal": "",
        "statusType": "auto",
        "x": 720,
        "y": 280,
        "wires": []
    },
    {
        "id": "a2f4732df6c9ee60",
        "type": "debug",
        "z": "c7fdce3b4d809aa9",
        "name": "",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "false",
        "statusVal": "",
        "statusType": "auto",
        "x": 600,
        "y": 340,
        "wires": []
    },
    {
        "id": "1e7a76a3bf0570fc",
        "type": "inject",
        "z": "c7fdce3b4d809aa9",
        "name": "Init",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": true,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "1",
        "payloadType": "num",
        "x": 510,
        "y": 60,
        "wires": [
            [
                "657af6ca92a39936"
            ]
        ]
    },
    {
        "id": "8faf75c3cfd6304b",
        "type": "comment",
        "z": "c7fdce3b4d809aa9",
        "name": "Relais Active LOW",
        "info": "",
        "x": 770,
        "y": 60,
        "wires": []
    }
]

Flow: OLED+Temperatur

[
    {
        "id": "aaa84f52c7096a57",
        "type": "subflow",
        "name": "SubFlow Lüftersteuerung",
        "info": "",
        "category": "",
        "in": [
            {
                "x": 180,
                "y": 60,
                "wires": [
                    {
                        "id": "cc220dae172d85e1"
                    }
                ]
            }
        ],
        "out": [],
        "env": [],
        "meta": {},
        "color": "#DDAA99"
    },
    {
        "id": "cc220dae172d85e1",
        "type": "function",
        "z": "aaa84f52c7096a57",
        "name": "Zeichenkette ==> Fließkommazahl ",
        "func": "var TEMPERATUR = (parseFloat(msg.payload))\nmsg.payload = {}\nmsg.payload = TEMPERATUR\nreturn msg;",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 380,
        "y": 60,
        "wires": [
            [
                "02a212b7bba91af5"
            ]
        ]
    },
    {
        "id": "02a212b7bba91af5",
        "type": "switch",
        "z": "aaa84f52c7096a57",
        "name": "25.5",
        "property": "payload",
        "propertyType": "msg",
        "rules": [
            {
                "t": "lte",
                "v": "25.5",
                "vt": "num"
            },
            {
                "t": "gt",
                "v": "25.5",
                "vt": "num"
            }
        ],
        "checkall": "true",
        "repair": false,
        "outputs": 2,
        "x": 610,
        "y": 60,
        "wires": [
            [
                "8f52d64302c90590"
            ],
            [
                "0b15ee8ae7c8098d"
            ]
        ]
    },
    {
        "id": "8f52d64302c90590",
        "type": "function",
        "z": "aaa84f52c7096a57",
        "name": "ON",
        "func": "msg.payload = {}\nmsg.payload = 1\nreturn msg;",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 750,
        "y": 40,
        "wires": [
            [
                "51aa262bc6a47b16"
            ]
        ]
    },
    {
        "id": "0b15ee8ae7c8098d",
        "type": "function",
        "z": "aaa84f52c7096a57",
        "name": "OFF",
        "func": "msg.payload = {}\nmsg.payload = 0\nreturn msg;",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 750,
        "y": 100,
        "wires": [
            [
                "51aa262bc6a47b16"
            ]
        ]
    },
    {
        "id": "51aa262bc6a47b16",
        "type": "rpi-gpio out",
        "z": "aaa84f52c7096a57",
        "name": "Lüfter",
        "pin": "19",
        "set": "",
        "level": "0",
        "freq": "",
        "out": "out",
        "bcm": true,
        "x": 890,
        "y": 60,
        "wires": []
    },
    {
        "id": "57fdae4b1e2fa017",
        "type": "subflow",
        "name": "SubFlow Anzeige OLED",
        "info": "",
        "category": "",
        "in": [
            {
                "x": 140,
                "y": 180,
                "wires": [
                    {
                        "id": "9707ef783df859b1"
                    },
                    {
                        "id": "a17db50f3b5c8350"
                    }
                ]
            }
        ],
        "out": [],
        "env": [],
        "meta": {},
        "color": "#DDAA99"
    },
    {
        "id": "9707ef783df859b1",
        "type": "function",
        "z": "57fdae4b1e2fa017",
        "name": "Temperatur",
        "func": "TEXT                = msg.payload\nSIZE                = 1\nX                   = 1\nY                   = 20\n\n\n\nmsg.payload             = {}\nmsg.payload.size        = SIZE\nmsg.payload.x           = X\nmsg.payload.y           = Y\nmsg.payload.text        = \"\" + TEXT + \" Grad Celsius\"\nmsg.payload.wrapping    = true\n\nreturn msg;",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 290,
        "y": 180,
        "wires": [
            [
                "2e6ba72f6720e80a",
                "d14fb288b85055d6",
                "9ce219e5b55e8fae"
            ]
        ]
    },
    {
        "id": "27fed66061ed1c9f",
        "type": "String",
        "z": "57fdae4b1e2fa017",
        "name": "",
        "display": "9a9363f402e61cc3",
        "x": 810,
        "y": 180,
        "wires": []
    },
    {
        "id": "adc07d4d308a28bb",
        "type": "Clear",
        "z": "57fdae4b1e2fa017",
        "name": "",
        "display": "9a9363f402e61cc3",
        "x": 810,
        "y": 80,
        "wires": []
    },
    {
        "id": "2e6ba72f6720e80a",
        "type": "delay",
        "z": "57fdae4b1e2fa017",
        "name": "Delay 1ms",
        "pauseType": "delay",
        "timeout": "2",
        "timeoutUnits": "milliseconds",
        "rate": "1",
        "nbRateUnits": "1",
        "rateUnits": "second",
        "randomFirst": "1",
        "randomLast": "5",
        "randomUnits": "seconds",
        "drop": false,
        "allowrate": false,
        "outputs": 1,
        "x": 510,
        "y": 180,
        "wires": [
            [
                "27fed66061ed1c9f"
            ]
        ]
    },
    {
        "id": "d14fb288b85055d6",
        "type": "change",
        "z": "57fdae4b1e2fa017",
        "name": "Clear",
        "rules": [
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "true",
                "tot": "bool"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 490,
        "y": 80,
        "wires": [
            [
                "adc07d4d308a28bb"
            ]
        ]
    },
    {
        "id": "fef3940f983fb2f0",
        "type": "Line",
        "z": "57fdae4b1e2fa017",
        "name": "",
        "display": "9a9363f402e61cc3",
        "x": 810,
        "y": 140,
        "wires": []
    },
    {
        "id": "9ce219e5b55e8fae",
        "type": "delay",
        "z": "57fdae4b1e2fa017",
        "name": "Delay 1ms",
        "pauseType": "delay",
        "timeout": "1",
        "timeoutUnits": "milliseconds",
        "rate": "1",
        "nbRateUnits": "1",
        "rateUnits": "second",
        "randomFirst": "1",
        "randomLast": "5",
        "randomUnits": "seconds",
        "drop": false,
        "allowrate": false,
        "outputs": 1,
        "x": 510,
        "y": 140,
        "wires": [
            [
                "b02d1d028e0afbd6"
            ]
        ]
    },
    {
        "id": "b02d1d028e0afbd6",
        "type": "change",
        "z": "57fdae4b1e2fa017",
        "name": "Line",
        "rules": [
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "{\"x0\":1,\"y0\":10,\"x1\":128,\"y1\":10,\"color\":1}",
                "tot": "json"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 670,
        "y": 140,
        "wires": [
            [
                "fef3940f983fb2f0"
            ]
        ]
    },
    {
        "id": "a17db50f3b5c8350",
        "type": "function",
        "z": "57fdae4b1e2fa017",
        "name": "Feuchtigkeit",
        "func": "Luftfeuchtigkeit = msg.humidity\nmsg.payload = Luftfeuchtigkeit\n\n\nTEXT                = msg.payload\nSIZE                = 1\nX                   = 1\nY                   = 45\n\n\n\nmsg.payload             = {}\nmsg.payload.size        = SIZE\nmsg.payload.x           = X\nmsg.payload.y           = Y\nmsg.payload.text        = \"\" + TEXT + \" % rel. LFK\"\nmsg.payload.wrapping    = true\n\n\n\nreturn msg;\n",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 290,
        "y": 260,
        "wires": [
            [
                "d81d370390ccac58"
            ]
        ]
    },
    {
        "id": "d81d370390ccac58",
        "type": "delay",
        "z": "57fdae4b1e2fa017",
        "name": "Delay 1ms",
        "pauseType": "delay",
        "timeout": "3",
        "timeoutUnits": "milliseconds",
        "rate": "1",
        "nbRateUnits": "1",
        "rateUnits": "second",
        "randomFirst": "1",
        "randomLast": "5",
        "randomUnits": "seconds",
        "drop": false,
        "allowrate": false,
        "outputs": 1,
        "x": 510,
        "y": 260,
        "wires": [
            [
                "7d512863d9788267"
            ]
        ]
    },
    {
        "id": "7d512863d9788267",
        "type": "String",
        "z": "57fdae4b1e2fa017",
        "name": "",
        "display": "9a9363f402e61cc3",
        "x": 810,
        "y": 260,
        "wires": []
    },
    {
        "id": "9a9363f402e61cc3",
        "type": "oled-config",
        "name": "OLED",
        "width": "128",
        "height": "64",
        "address": "3c"
    },
    {
        "id": "6b76d7edc2b91f8b",
        "type": "tab",
        "label": "OLED+Temperatur",
        "disabled": false,
        "info": "",
        "env": []
    },
    {
        "id": "b91d5addc2b04530",
        "type": "rpi-dht22",
        "z": "6b76d7edc2b91f8b",
        "name": "DHT22",
        "topic": "rpi-dht22",
        "dht": 22,
        "pintype": "0",
        "pin": "6",
        "x": 410,
        "y": 180,
        "wires": [
            [
                "19807cb9dff8ddae",
                "9ff972b204f8b75f"
            ]
        ]
    },
    {
        "id": "ca1197c938141691",
        "type": "inject",
        "z": "6b76d7edc2b91f8b",
        "name": "Alle 5 Sekunden",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "5",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "",
        "payloadType": "date",
        "x": 230,
        "y": 180,
        "wires": [
            [
                "b91d5addc2b04530"
            ]
        ]
    },
    {
        "id": "7875175a2c5f07b7",
        "type": "inject",
        "z": "6b76d7edc2b91f8b",
        "name": "Test hohe Temperatur 26,34Grad",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            },
            {
                "p": "humidity",
                "v": "100,00",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "26.34",
        "payloadType": "str",
        "x": 330,
        "y": 240,
        "wires": [
            [
                "19807cb9dff8ddae",
                "9ff972b204f8b75f"
            ]
        ]
    },
    {
        "id": "19807cb9dff8ddae",
        "type": "subflow:57fdae4b1e2fa017",
        "z": "6b76d7edc2b91f8b",
        "name": "Temperaturanzeige",
        "x": 630,
        "y": 180,
        "wires": []
    },
    {
        "id": "9ff972b204f8b75f",
        "type": "subflow:aaa84f52c7096a57",
        "z": "6b76d7edc2b91f8b",
        "name": "",
        "x": 650,
        "y": 240,
        "wires": []
    }
]

Flow: AD-Converter

[
    {
        "id": "cc56fb1587c17034",
        "type": "tab",
        "label": "AD-Converter",
        "disabled": false,
        "info": "",
        "env": []
    },
    {
        "id": "42f39cbea1d89c21",
        "type": "ncd-ads1115",
        "z": "cc56fb1587c17034",
        "name": "",
        "connection": "79a792c067515fbc",
        "addr": "72",
        "interval": "1000",
        "outputs": 1,
        "output_all": 0,
        "output_mult": "0.00013",
        "channel_1": "4",
        "channel_2": "_none",
        "channel_3": "_none",
        "channel_4": "_none",
        "gain": "1",
        "mode": "2",
        "rate": 4,
        "compMode": 0,
        "compPol": 0,
        "compLat": 0,
        "compQueue": 3,
        "delay": "100",
        "x": 400,
        "y": 140,
        "wires": [
            [
                "ca8b82b7b730e641",
                "a603b2dc4475470e"
            ]
        ]
    },
    {
        "id": "ca8b82b7b730e641",
        "type": "debug",
        "z": "cc56fb1587c17034",
        "name": "",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "false",
        "statusVal": "",
        "statusType": "auto",
        "x": 610,
        "y": 40,
        "wires": []
    },
    {
        "id": "a603b2dc4475470e",
        "type": "switch",
        "z": "cc56fb1587c17034",
        "name": "",
        "property": "payload.channel_1",
        "propertyType": "msg",
        "rules": [
            {
                "t": "gte",
                "v": "2.0",
                "vt": "num"
            },
            {
                "t": "lt",
                "v": "2.0",
                "vt": "num"
            }
        ],
        "checkall": "true",
        "repair": false,
        "outputs": 2,
        "x": 570,
        "y": 140,
        "wires": [
            [
                "a37a31267fadb774"
            ],
            [
                "52ac92ae4304a6c2"
            ]
        ]
    },
    {
        "id": "81485dfcc03030dd",
        "type": "rpi-gpio out",
        "z": "cc56fb1587c17034",
        "name": "Relais GPIO21",
        "pin": "21",
        "set": true,
        "level": "1",
        "freq": "",
        "out": "out",
        "bcm": true,
        "x": 940,
        "y": 140,
        "wires": []
    },
    {
        "id": "a37a31267fadb774",
        "type": "change",
        "z": "cc56fb1587c17034",
        "name": "ON",
        "rules": [
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "0",
                "tot": "num"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 730,
        "y": 120,
        "wires": [
            [
                "81485dfcc03030dd"
            ]
        ]
    },
    {
        "id": "52ac92ae4304a6c2",
        "type": "change",
        "z": "cc56fb1587c17034",
        "name": "OFF",
        "rules": [
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "1",
                "tot": "str"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 730,
        "y": 160,
        "wires": [
            [
                "81485dfcc03030dd"
            ]
        ]
    },
    {
        "id": "79a792c067515fbc",
        "type": "ncd-comm",
        "name": "ADS1115",
        "bus": "1",
        "busManual": "",
        "commType": "standard",
        "addr": "0",
        "useMux": false,
        "muxAddr": "112",
        "muxPort": "0"
    }
]

Flow MQTT

[
    {
        "id": "f543440dadec5d68",
        "type": "tab",
        "label": "MQTT",
        "disabled": false,
        "info": "",
        "env": []
    },
    {
        "id": "9d2aaa480cf32295",
        "type": "mqtt out",
        "z": "f543440dadec5d68",
        "name": "",
        "topic": "VHS/MQTT/Alarm",
        "qos": "2",
        "retain": "",
        "respTopic": "",
        "contentType": "",
        "userProps": "",
        "correl": "",
        "expiry": "",
        "broker": "b7d218c25bdfaada",
        "x": 330,
        "y": 40,
        "wires": []
    },
    {
        "id": "febb9d5853b71934",
        "type": "mqtt in",
        "z": "f543440dadec5d68",
        "name": "",
        "topic": "VHS/MQTT/Alarm",
        "qos": "2",
        "datatype": "auto",
        "broker": "b7d218c25bdfaada",
        "nl": false,
        "rap": true,
        "rh": 0,
        "inputs": 0,
        "x": 330,
        "y": 100,
        "wires": [
            [
                "6ee0096770ed3510"
            ]
        ]
    },
    {
        "id": "7d57576fb9cfe7b7",
        "type": "inject",
        "z": "f543440dadec5d68",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "1",
        "payloadType": "num",
        "x": 90,
        "y": 40,
        "wires": [
            [
                "9d2aaa480cf32295"
            ]
        ]
    },
    {
        "id": "de77706e848bebb8",
        "type": "inject",
        "z": "f543440dadec5d68",
        "name": "0",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "0",
        "payloadType": "num",
        "x": 90,
        "y": 80,
        "wires": [
            [
                "9d2aaa480cf32295"
            ]
        ]
    },
    {
        "id": "6ee0096770ed3510",
        "type": "rpi-gpio out",
        "z": "f543440dadec5d68",
        "name": "",
        "pin": "20",
        "set": "",
        "level": "0",
        "freq": "",
        "out": "out",
        "bcm": true,
        "x": 560,
        "y": 100,
        "wires": []
    },
    {
        "id": "b7d218c25bdfaada",
        "type": "mqtt-broker",
        "name": "PI400",
        "broker": "localhost",
        "port": "1883",
        "clientid": "",
        "autoConnect": true,
        "usetls": false,
        "protocolVersion": "4",
        "keepalive": "60",
        "cleansession": true,
        "birthTopic": "",
        "birthQos": "0",
        "birthPayload": "",
        "birthMsg": {},
        "closeTopic": "",
        "closeQos": "0",
        "closePayload": "",
        "closeMsg": {},
        "willTopic": "",
        "willQos": "0",
        "willPayload": "1",
        "willMsg": {},
        "userProps": "",
        "sessionExpiry": ""
    }
]

Flow MotionDetect

[
    {
        "id": "d9a2c059971278a0",
        "type": "tab",
        "label": "MotionDetect",
        "disabled": false,
        "info": "",
        "env": []
    },
    {
        "id": "174aedc7a52e0361",
        "type": "rpi-gpio in",
        "z": "d9a2c059971278a0",
        "name": "PIR",
        "pin": "22",
        "intype": "down",
        "debounce": "25",
        "read": true,
        "bcm": true,
        "x": 110,
        "y": 40,
        "wires": [
            [
                "7cdffcdfcfea74c8"
            ]
        ]
    },
    {
        "id": "7cdffcdfcfea74c8",
        "type": "rpi-gpio out",
        "z": "d9a2c059971278a0",
        "name": "GPIO13",
        "pin": "13",
        "set": true,
        "level": "0",
        "freq": "",
        "out": "out",
        "bcm": true,
        "x": 400,
        "y": 40,
        "wires": []
    }
]

NCD COM

[
    {
        "id": "611d45c260d9d6f3",
        "type": "ncd-ads1115",
        "z": "cc56fb1587c17034",
        "name": "ADS1115",
        "connection": "f2cc0d60de7dda42",
        "addr": "72",
        "interval": 0,
        "outputs": 1,
        "output_all": 0,
        "output_mult": "0.000628",
        "channel_1": "4",
        "channel_2": "_none",
        "channel_3": "_none",
        "channel_4": "_none",
        "gain": "1",
        "mode": 1,
        "rate": 4,
        "compMode": 0,
        "compPol": 0,
        "compLat": 0,
        "compQueue": 3,
        "delay": "100",
        "x": 360,
        "y": 140,
        "wires": [
            [
                "ca8b82b7b730e641",
                "a603b2dc4475470e"
            ]
        ]
    },
    {
        "id": "f2cc0d60de7dda42",
        "type": "ncd-comm",
        "name": "ADS1115",
        "bus": "1",
        "busManual": "",
        "commType": "standard",
        "addr": "0",
        "useMux": false,
        "muxAddr": "112",
        "muxPort": "0"
    }
]

AD Flow II

[
    {
        "id": "cc56fb1587c17034",
        "type": "tab",
        "label": "AD-Converter",
        "disabled": false,
        "info": "",
        "env": []
    },
    {
        "id": "42f39cbea1d89c21",
        "type": "ncd-ads1115",
        "z": "cc56fb1587c17034",
        "name": "",
        "connection": "79a792c067515fbc",
        "addr": "72",
        "interval": "1000",
        "outputs": 1,
        "output_all": 0,
        "output_mult": "0.00013",
        "channel_1": "4",
        "channel_2": "_none",
        "channel_3": "_none",
        "channel_4": "_none",
        "gain": "1",
        "mode": "2",
        "rate": 4,
        "compMode": 0,
        "compPol": 0,
        "compLat": 0,
        "compQueue": 3,
        "delay": "100",
        "x": 80,
        "y": 120,
        "wires": [
            [
                "ca8b82b7b730e641",
                "a603b2dc4475470e",
                "409f97b13a03adeb"
            ]
        ]
    },
    {
        "id": "ca8b82b7b730e641",
        "type": "debug",
        "z": "cc56fb1587c17034",
        "name": "",
        "active": true,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "false",
        "statusVal": "",
        "statusType": "auto",
        "x": 290,
        "y": 20,
        "wires": []
    },
    {
        "id": "a603b2dc4475470e",
        "type": "switch",
        "z": "cc56fb1587c17034",
        "name": "",
        "property": "payload.channel_1",
        "propertyType": "msg",
        "rules": [
            {
                "t": "gte",
                "v": "2.2",
                "vt": "num"
            },
            {
                "t": "lt",
                "v": "2.2",
                "vt": "num"
            }
        ],
        "checkall": "true",
        "repair": false,
        "outputs": 2,
        "x": 250,
        "y": 120,
        "wires": [
            [
                "a37a31267fadb774"
            ],
            [
                "52ac92ae4304a6c2"
            ]
        ]
    },
    {
        "id": "81485dfcc03030dd",
        "type": "rpi-gpio out",
        "z": "cc56fb1587c17034",
        "name": "Relais GPIO21",
        "pin": "21",
        "set": true,
        "level": "1",
        "freq": "",
        "out": "out",
        "bcm": true,
        "x": 620,
        "y": 120,
        "wires": []
    },
    {
        "id": "a37a31267fadb774",
        "type": "change",
        "z": "cc56fb1587c17034",
        "name": "ON",
        "rules": [
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "0",
                "tot": "num"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 410,
        "y": 100,
        "wires": [
            [
                "81485dfcc03030dd"
            ]
        ]
    },
    {
        "id": "52ac92ae4304a6c2",
        "type": "change",
        "z": "cc56fb1587c17034",
        "name": "OFF",
        "rules": [
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "1",
                "tot": "str"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 410,
        "y": 140,
        "wires": [
            [
                "81485dfcc03030dd"
            ]
        ]
    },
    {
        "id": "2c715fd55456b74f",
        "type": "ui_gauge",
        "z": "cc56fb1587c17034",
        "name": "",
        "group": "1e1d6be91e7e9a07",
        "order": 0,
        "width": 0,
        "height": 0,
        "gtype": "gage",
        "title": "ADC",
        "label": "Volt",
        "format": "{{value}}",
        "min": 0,
        "max": "3.5",
        "colors": [
            "#00b500",
            "#e6e600",
            "#ca3838"
        ],
        "seg1": "",
        "seg2": "",
        "className": "",
        "x": 810,
        "y": 220,
        "wires": []
    },
    {
        "id": "dea84712781dae9a",
        "type": "debug",
        "z": "cc56fb1587c17034",
        "name": "debug 2",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "false",
        "statusVal": "",
        "statusType": "auto",
        "x": 640,
        "y": 300,
        "wires": []
    },
    {
        "id": "409f97b13a03adeb",
        "type": "change",
        "z": "cc56fb1587c17034",
        "name": "",
        "rules": [
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "payload.channel_1",
                "tot": "msg"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 390,
        "y": 220,
        "wires": [
            [
                "dea84712781dae9a",
                "3db18b84ac5fa03c"
            ]
        ]
    },
    {
        "id": "3db18b84ac5fa03c",
        "type": "function",
        "z": "cc56fb1587c17034",
        "name": "function 1",
        "func": "msg.payload = msg.payload.toFixed(2);\nreturn msg;",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 640,
        "y": 220,
        "wires": [
            [
                "2c715fd55456b74f",
                "f0536348264b4341"
            ]
        ]
    },
    {
        "id": "f0536348264b4341",
        "type": "ui_text",
        "z": "cc56fb1587c17034",
        "group": "1e1d6be91e7e9a07",
        "order": 4,
        "width": 0,
        "height": 0,
        "name": "",
        "label": "text",
        "format": "{{msg.payload}}",
        "layout": "row-spread",
        "className": "",
        "x": 810,
        "y": 260,
        "wires": []
    },
    {
        "id": "1e1d6be91e7e9a07",
        "type": "ui_group",
        "name": "Standard",
        "tab": "07727bd1bea89cbc",
        "order": 1,
        "disp": true,
        "width": "6",
        "collapse": false,
        "className": ""
    },
    {
        "id": "07727bd1bea89cbc",
        "type": "ui_tab",
        "name": "Home",
        "icon": "dashboard",
        "disabled": false,
        "hidden": false
    }
]

Dateien

Die beiden Dateien „package.json“ und „flows.json“ beinhalten die Informationen welche Module zur Palette hinzugefügt wurden und sind eine Kopie der flows. Sind die Module alle hinzugefügt, kann die Datei flows.json


Bilder

Entwicklungsumgebung Pi400de
Steckbrett bestückt
Flow OUTPUT
Flow OLED+Temperatur
Flow AD-Converter
Flow MQTT
Flow Motion Detect

Netzwerkports

PortService, Beschreibung
22SSH (Terminalemulation)
1880Node-Red
1883Mosquitto
3389RDP
5900VNC
Netzwerkports