Matrix Display, Servos und Klimasensoren - AZ-Delivery

Dieser Beitrag wurde uns von unserem Gastautoren Miguel Torres Gordo zugesandt. Viel Spaß beim Lesen und Nachbauen:

Dies ist ein einfaches und nützliches Projekt, um mit wenigen Modulen die Zeit, Temperatur und Luftfeuchtigkeit in einem Raum anzuzeigen. Für die Uhrzeit habe ich mich entschieden, nur die Stunde und die Minuten anzuzeigen, da die Sekunden meiner Meinung nach nicht relevant sind. Das Foto zeigt eine mögliche Verteilung der Anzeige, aber es bleibt der Phantasie des Lesers überlassen, wie sie z.B. in einer mit einem 3D-Drucker hergestellten Box eingesetzt werden könnten.

fertiges Projekt

Benötigte Materialien

Erforderliche Software

Suchen Sie die fehlenden Bibliotheken in der Arduino IDE über "Werkzeuge -> Bibliotheken verwalten..."

Schaltung und Beschreibung der Funktionsweise

Das RTC-Modul DS1302 ist für die Bereitstellung der Uhrzeit am Mikrocontroller zuständig, während das DHT-11-Modul die Temperatur und die Luftfeuchtigkeit misst. Der Mikrocontroller steuert dann mit den Informationen die 8x8-LED-Modulgruppe für die Uhrzeit und die Servomotoren für die Anzeige von Temperatur und Luftfeuchtigkeit.

Es ist sehr wichtig, dass wir eine entsprechende Batterie einsetzen, denn obwohl dieses Modul ohne sie korrekt funktioniert, wird die Zeit zurückgesetzt, wenn wir das Modul vom Stromkreis trennen.

Um die aktuelle Uhrzeit und das Datum einzustellen, müssen wir die folgende Schaltung aufbauen:

RTC Setup

RTC (I2C)

Nano V3

VCC

5V

GND

GND

CLK

A5 (SCL)

DAT

A4 (SDA)

RST

-

Wir führen dann den Sketch DS1307_setup.ino aus, wir öffnen den Serial Monitor und können sowohl das Datum als auch die Uhrzeit sehen, die das Modul gespeichert hat. Diese Daten sind die, die das Betriebssystem des PCs im Moment der Ausführung des Sketches zur Verfügung stellt. Wenn wir uns die Skizze anschauen, können wir sehen, dass die Codezeile

clock.setDateTime(__DATE__, __TIME__);

diejenige ist, die das Modul mit den beiden Daten aus dem System lädt. Von diesem Moment an haben wir das Modul mit Uhrzeit und Datum konfiguriert und dank der Batterie werden diese Daten nicht aus dem Modul gelöscht, wenn die Spannung entfernt wird.

Nachdem wir die Uhrzeit und das Datum eingestellt haben, installieren wir das Modul DS1302 zusammen mit den anderen Modulen in der Schaltung und führen den Sketch clock_temperature_humidity.ino aus. Wenn wir das Laden beendet haben, sollten wir die genaue Uhrzeit auf der LED-Matrix sehen und die beiden Servomotoren sollten sich bewegen, bis sie auf den Wert der Temperatur und der Luftfeuchtigkeit in der Umgebung positioniert sind.

Schaltung

Um den Sketch auf den Mikrocontroller zu laden, entfernen Sie die Leitung zwischen +5V und Vin.

Zoomed

Wir haben die 5V Gleichspannungsversorgung, den Mikrocontroller, das RTC Modul DS1302, DHT-11, das LED Array und die 2 Servomotoren.

Foto vom Aufbau

Analysieren wir den Code:

Als erstes laden wir die Bibliotheken, die für die Ausführung des Sketches notwendig sind. Die ersten drei sind für die LED-Matrix, die nächsten zwei für die Verwendung des DS1307-Moduls, die vorletzte ist die Bibliothek für das DHT-11-Modul und die letzte ist für die Verwendung der Servomotoren:

#include <MD_Parola.h>
#include <MD_MAX72xx.h>
#include <SPI.h>
#include <Wire.h>
#include <DS3231.h>
#include <DHT.h>
#include <Servo.h>

Nach den Bibliotheken müssen wir die Verbindungen der Module mit den Pins des Mikrocontrollers konfigurieren. Anschließend den Typ des Controllers und die Anzahl der LED-Module der Matrix (4 in unserem Fall). Dann den Typ des DHT-Moduls. Wir erstellen die Instanzen jedes Moduls und die notwendigen Variablen, um die Daten dafür zu speichern:

// Define hardware type, size, and output pins MAX7219 8x32 4 in 1 Dot Matrix LED Display Module
#define HARDWARE_TYPE MD_MAX72XX::FC16_HW
#define MAX_DEVICES 4
#define CS_PIN 10

// Define hardware type andi pins DHT-11
#define DHTPIN 2
#define DHTTYPE DHT11

// Create a new instance of the MD_Parola class with hardware SPI connection:
MD_Parola reloj = MD_Parola(HARDWARE_TYPE, CS_PIN, MAX_DEVICES);

// Create a instance of DHT-11 sensor and variables for temperature and humidity
DHT dht(DHTPIN, DHTTYPE);
float t, hu;

// Instances of the servos for humidity and temperature
Servo servoTemperature;
Servo servoHumidity;

// Instance for the DS3231 clock
DS3231 clock;
RTCDateTime dt;

Nachdem wir die Modulparameter konfiguriert haben, initialisieren wir die Module in der setup()-Funktion des Sketches:

      // Initialization of Monitor Serial
      Serial.begin(9600);
      Serial.println("Initialize RTC module");
  
      // Initialization of DS3231 Module
      clock.begin();

      // Initialization MAX7219 LED Matrix Display
      reloj.begin();                // Intialize the object
      reloj.setIntensity(0);        // Set the intensity (brightness) of the display (0-15)
      reloj.displayClear();         // Clear the display

      // Initialization DHT-11 module
      dht.begin();

      // Servo pins connections
      servoTemperature.attach(3);
      servoHumidity.attach(4);

In der loop()-Funktion werden die Messwerte und die Berechnungen erzeugt, die für die Anzeige erforderlich sind.

Zunächst werden wir die Temperatur- und Luftfeuchtigkeitsdaten analysieren. Wir ordnen den Temperaturwert der Variablen t und den Feuchtigkeitswert der Variablen hu zu. Wenn wir keine Daten erhalten, teilen wir das über den seriellen Monitor mit. Die Wertebereiche, mit denen wir arbeiten werden, reichen von 0 bis 50 Grad Celsius Temperatur und von 0 % bis 100 % Luftfeuchtigkeit. Wir wissen, dass die Servomotoren normalerweise einen Winkelbereich von 180 Grad haben. Damit die Servomotoren die Daten richtig markieren, führen wir eine einfache mathematische Operation durch, um die Maximalwerte der Bereiche den 180 Grad des Winkels der Servomotoren zuzuordnen.

     // Temperature and humidity reading
      t = dht.readTemperature();
      hu = dht.readHumidity();
      if (isnan(hu) || isnan(t)) {
              Serial.println("DHT sensor reading failure !!!");
      }

...

      servoTemperature.write((t*180)/50);   // Move the servos to value
      servoHumidity.write((hu*180)/100);

Als Alternative können Sie die map()-Funktion einsetzen.

Das Verfahren zur Erfassung und Anzeige der Stunden und Minuten ist sehr einfach. Nur eine Anmerkung: Wenn das Modul DS1302 die Stunden und Minuten sendet, sendet es die minimal notwendigen Ziffern, also von 0 bis 9 nur eine Ziffer. Wenn wir also weniger als 10 Stunden oder 10 Minuten erhalten, wird jeweils nur eine Ziffer angezeigt. Das würde den Eindruck einer Fehlfunktion erwecken, oder sieht nicht schön aus. Also müssen wir immer zwei Ziffern in den Stunden und Minuten anzeigen.

Mit der ersten Zeile fordern wir das DS1302-Modul auf, die Zeit- und Datumsdaten abzurufen. Dann erstellen wir zwei Variablen (h und m), um die Daten im String-Format der Stunde und der Minuten zu speichern. Sind die Werte jeweils kleiner als 10, wird mit der if-Anweisung eine 0 als Zeichen, nicht als Ziffer, mit concat vorangestellt. Jetzt müssen wir diese Daten nur noch auf der LED-Matrix anzeigen. Um zu zeigen, dass die Uhr läuft, zeigen wir zwei sehr ähnliche Strings an. Einen mit der Trennung zwischen Stunden und Minuten mit einem Doppelpunkt und einen anderen ohne den Doppelpunkt. Die Anzeige erfolgt im Wechsel von 500ms, was einer halben Sekunde entspricht. Somit blinken die Doppelpunkte.

Die delay()-Funktion blockiert den Programmablauf, was in diesem Fall nicht weiter relevant ist, da genug Zeit bleibt, die Daten auszulesen und anzuzeigen.

      dt = clock.getDateTime();               // Reading data from the RTC module

      String h;                               // Variable for the hours
      String m;                               // Variable for the minutes
  
      int hora = (dt.hour);                   // The variable "hora" is used 
      if (dt.hour<10) {                       // to set the time to always show two digits 
	            h = "0";                        // two digits in the clock hours.
	            h.concat((String) hora);
      } else {
	            h = (String) hora;
      }

      int minuto = (dt.minute);               // The variable "minuto" is used
      if (dt.minute<10) {                     // to set the minutes to always
	            m ="0";                         // two digits en the clock minutes
	            m.concat((String) minuto);
      } else {
	            m = (String) minuto;
      }
      
      String r = h + ":" + m;                 // Hour and minutes with colon separation
      String q = h + " " + m;                 // Hour and minutes without colon separation

      Serial.print("Hora: ");
      Serial.print(dt.hour);   	Serial.print(":");
      Serial.print(dt.minute); 	Serial.print(":");
      Serial.print(dt.second); 	Serial.println("");
      Serial.print( "T = " );
      Serial.print(t);
      Serial.print(" ºC, H = ");
      Serial.print(hu);
      Serial.print( "%, " );

      reloj.setTextAlignment(PA_CENTER);    // Configuration the text centered
      reloj.print(r);                       // We change the text showing the separation
      delay(500);                           // and without it every half second for the
      reloj.print(q);                       // sensation of movement.
      delay(500);
 

Komplette Sketches als Download:

DS1307_setup.ino

clock_temperature_humidity.ino

Fertiges Projekt
Ich wünsche Ihnen viel Spaß mit diesem Projekt.
DisplaysFür arduinoProjekte für anfängerSensoren

6 Kommentare

Andreas Wolter

Andreas Wolter

@Veit Burmester: Danke für den Hinweis. Das hier verwendete RTC Modul war das DS1307, welches genauso angeschlossen wird, wie das DS3231. Ich habe das im Beitrag in der Komponentenliste geändert. Entschuldigung, wenn das zu Verwirrungen geführt hat. Der Autor des Beitrags hatte das so nicht vorgesehen. Ich wollte eine Alternative hinzufügen, falls das RTC Modul nicht verfügbar ist.
Sie haben also völlig Recht. DS3231 und DS1307 sollten funktionieren. Für das DS1302 müssen Änderungen vorgenommen werden.

Grüße,
Andreas Wolter

Veit Burmester

Veit Burmester

Hallo Herr Wolter
Nach längerer Auszeit konnte ich mich wieder um obiges Projekt kümmern. Ich möchte Ihnen auch ungern die Zeit stehlen.
Ich habe alles genau so Aufgebaut wie beschrieben. Funktion gleich Null. Habe den Fehler erst bei mir gesucht. Jedoch nach genaueren Kontrolle kam ich zu dem Schluss das das von Ihnen benutzte RTC 1302 Modul nicht für diese Verdrahtung und Programm geeignet ist. Das Modul DS 3231 hingegen funktioniert. Auch Modul DS 1307 sollte funktioniert. Nachschlagen auf Ihrer Produktseite zeigt eine andere Verdrahtung ( 3Datenkabel auf Digitale IO ) des RTC 1302 und auch die Librarie ist ganz anders. So wie ich die Produktbeschreibung verstehe hat das Modul 1302 keine I²C Schnittstelle. Das kleine Programm zum Zeit-Einstellen heißt ja auch DS 1307 setup. ino.
Sollte ich hier falsch liegen bitte ich schon im Vorfeld um Entschuligung.
Mit Freundlichen Grüßen aus dem hohen Norden
Veit Burmester

Andreas Wolter

Andreas Wolter

@Veit Burmeister: danke für den Hinweis. Es handelt sich nicht um die Bibliothek DS3231 aus der Bibliotheksverwaltung von Andrew Wickert. Ich habe den Link zum Download ergänzt. Ich konnte es tatsächlich auch erst kompilieren, wenn ich die besagte Bibliothek DS3231 gelöscht habe. Die kommt sich mit der Arduino 3231 Bibliothek stark in die Quere. Sorry für das Missverständnis.

Grüße,
Andreas Wolter
AZ-Delivery Blog

Veit Burmester

Veit Burmester

Hallo
Ich habe Probleme mit der Bibliothek DS3231. So wie ich die Fehlerliste lese passt sie nicht zu der Programmierung. Ein Keyword1 RTCDateTime gibt es nicht in der Bibliothek.
Vielleicht habe ich auch die falsche Bibliothek heruntergeladen. die ich in Benutzung habe ist genau so geschrieben wie im Sketch benötigt.
Diese gilt für beide DS1307_setup.ino und
clock_temperature_humidity.ino Bitte um kurze Info

Andreas Wolter

Andreas Wolter

@jue: an dieser Stelle werden die Werte ausgelesen:
t = dht.readTemperature();
hu = dht.readHumidity();

und an dieser Stelle an die Servos gegeben:
servoTemperature.write((t*180)/50);
servoHumidity.write((hu*180)/100);

statt der Servos müssen Sie jetzt die Werte t und hu an das Display (ich nehme an, Sie meinten 7-Segment-Anzeigen) geben. Wie Sie diese verwenden können, zeigt dieser Blogbeitrag. Eventuell hilft Ihnen das weiter:
https://www.az-delivery.de/blogs/azdelivery-blog-fur-arduino-und-raspberry-pi/echtzeituhr-mit-display-am-nano-v3

jue

jue

gute idee. wie würde das programm und das schaltbild aussehen, wenn man statt der servos 2 digianzeigen verwendet?

Kommentar hinterlassen

Alle Kommentare werden von einem Moderator vor der Veröffentlichung überprüft

Empfohlene Blogbeiträge

  1. ESP32 jetzt über den Boardverwalter installieren - AZ-Delivery
  2. Internet-Radio mit dem ESP32 - UPDATE - AZ-Delivery
  3. Arduino IDE - Programmieren für Einsteiger - Teil 1 - AZ-Delivery
  4. ESP32 - das Multitalent - AZ-Delivery