LCD Display smarter Reset des Displays im Loop umsetzen

Hallo Zusammen,

ich habe folgendes Display an meinem Arduino Nano laufen:

mit folgendem Code:

// Einbinden der Libraries
#include <Wire.h>
#include <LiquidCrystal_I2C.h>            // LCD-Anzeige: Library einbinden

// Konstanten für LCD-Display setzen:
LiquidCrystal_I2C lcd(0x27, 16, 2);       // LCD-Display: Setzen der Adresse 0x27 für das 16 character mit 2 lines

// Konstanten für Füllstandssensor setzen:
const int trigPin = 8;                    // Füllstandssensor: Setzen von Pin8 als Trigger
const int echoPin = 7;                    // Füllstandssensor: Setzen von Pin7 als Echo
long duration;                            // Füllstandssensor: Definition des long duration (wie lange das Siganl unterwegs ist)
int wasserstand_ist;                      // Füllstandssensor: Definition des int wasserstand_ist (Gibt tatsächlichen Wasserstand an)
int wasserstand_soll = 6;                 // Füllstandssensor: Definition des Sollwertes (Schaltgrenze) des Wasserstandes
int wasserstand_ok = 0;                   // Füllstandssensor: wasserstand_ok = 1: Mindestwasserstand erreicht || wasserstand_ok = 0: Mindestwasserstand nicht erreicht

// RTC definieren:
RTC_PCF8523 rtc;
char daysOfTheWeek[7][12] = {"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"};
int aktuelleSekunde = 0;                // übergreifender Wert der die aktuelle Sekunde von der RTC abfragt

/***************************************** Ende Deklaration **********************************************/

void setup() {
Serial.begin(9600);                     // Serielle Kommunikation starten; Baud-Rate 9600
Fuellstandssensor_Task();               // Füllstandssensor: setup Routine aufrufen
LCD_Task();                             // LCD-Anzeige: setup Routine aufrufen
RTC_Task();
}

void loop() {
Fuellstandssensor_loop();               // Füllstandssensor: loop Routine aufrufen
LCD_loop();                             // LCD-Anzeige: loop Routine aufrufen
RTC_loop();
}

/*****************************************Beginn Task Routinen der Bauteile****************************/

void LCD_Task() {
lcd.begin();
}

void RTC_Task() {

while (!Serial) {
  delay(1);  // for Leonardo/Micro/Zero
}

if (! rtc.begin()) {
  Serial.println("Couldn't find RTC");
  while (1);
}

if (! rtc.initialized()) {
  Serial.println("RTC is NOT running!");
  // following line sets the RTC to the date & time this sketch was compiled
  // rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));
  // This line sets the RTC with an explicit date & time, for example to set
  // January 21, 2014 at 3am you would call:
  // rtc.adjust(DateTime(2014, 1, 21, 3, 0, 0));
}
}

/*****************************************Beginn Loop Routinen der Bauteile****************************/


void LCD_loop() {
if (aktuelleSekunde % 15 == 0) { // alle 15 Sekunden LCD-Display zurücksetzen
  lcd.clear();
}

if (wasserstand_ok == 1) {
  lcd.setCursor(0, 0);                       // Cursor in obere linke Ecke setzen
  lcd.print("Modul");
  lcd.setCursor(0, 1);                       // Cursor in untere linke Ecke setzen
  lcd.print("fehlerfrei");
} else {
  lcd.setCursor(0, 0);                       // Cursor in obere linke Ecke setzen
  lcd.print("Bitte Behälter");
  lcd.setCursor(0, 1);                       // Cursor in untere linke Ecke setzen
  lcd.print("fuellen");
}

}

void Fuellstandssensor_loop() {
if (aktuelleSekunde % 5 == 0) {            // alle 5 Sekunden den Wasserstand abfragen
  digitalWrite(trigPin, LOW);                // Zurücksetzen (LOW) des Trigger Pins
  delayMicroseconds(2);
  digitalWrite(trigPin, HIGH);              // trigPin für 10 micro Sekunden auf HIGH setzen
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  duration = pulseIn(echoPin, HIGH);        // Auslesen des echoPin, die Zeit wie lange die Ultraschall-Welle unterwegs war wird zurückgegeben
  wasserstand_ist = duration * 0.034 / 2;   // Berechnung des aktuellen Wasserstands im Becken wasserstand_ist
  Serial.print("Wasserstand: ");             // aktuellen Wasserstand auf seriellem Monitor ausgeben
  Serial.println(wasserstand_ist);          // aktuellen Wasserstand auf seriellem Monitor ausgeben
}
if (wasserstand_ist >= wasserstand_soll) { // Wenn der Wasserstand im Becken größer ist als der Schaltwert: Einschalten der Wasserpumpe und der Sauerstoffpumpe
  wasserstand_ok = 1;
  Serial.println("Wasserstand ist i.O.");
}
else {
  wasserstand_ok = 0;
  Serial.println("Wasserstand ist n.i.O.");
}
}

void RTC_loop() {
DateTime now = rtc.now();

Serial.println();                               // Aktuelle Uhrzeit auf seriellem Monitor ausgeben
Serial.print("Aktuelle Uhrzeit:");
Serial.print(now.year(), DEC);
Serial.print('/');
Serial.print(now.month(), DEC);
Serial.print('/');
Serial.print(now.day(), DEC);
Serial.print(" (");
Serial.print(daysOfTheWeek[now.dayOfTheWeek()]);
Serial.print(") ");
Serial.print(now.hour(), DEC);
Serial.print(':');
Serial.print(now.minute(), DEC);
Serial.print(':');
Serial.print(now.second(), DEC);
Serial.println();

aktuelleSekunde = now.second();                 // Übergabe der aktuellen Sekunde aus der RTC an den int aktuelleSekunde

}

Das Problem, welches ich habe ist folgendes:
Wenn nun mein wasserstand_ok = 1 ist steht auf meinem Display:
Modul
fehlerfrei

wenn nun wasserstand_ok = 0 ist, ändert sich die Anzeige auf:
Bitte Behälter
fuellenrei

also bleibt dieses "rei" stehen.

Dies möchte ich natürlich nicht.

Daher habe ich die Zeilen:

if (aktuelleSekunde % 15 == 0) { // alle 15 Sekunden LCD-Display zurücksetzen
  lcd.clear();

eingefügt.

Jetzt flackert die Schrift auf der LCD-Anzeige allerdings 1 Sekunde lang, und das eben alle 15 Sekunden.
Das sieht natürlich auch bescheuert aus.

Daher jetzt meine Frage:
Wie kann ich dies besser lösen?

LG

Bitte setze Deinen Sketch in Codetags (</> oben links im Editor), damit er lesbar und scrollbar ist.

Gruß Tommy

Mach anstatt
lcd.print("fuellen");

lcd.print("fuellen ");

Mach anstatt
lcd.print("fuellen");

lcd.print("fuellen ");

Danke für die Antwort, das würde in diesem spezifischen Fall ja auch klappen, aber es muss doch noch eine generellere Möglichkeit dafür geben oder?

Zum Beispiel wenn ich analoge Werte auf dem LCD ausgebe:

Jetzt ist beispielsweise der Wert meines analogen Inputs 123 dann steht auf dem Display:
123

wenn jetzt mein analoger Input einen Wert von 4 empfängt, steht ja auf der Anzeige nun:
423

Jetzt kann sich ja der analoge Input beliebig ändern.
Daher kann ich die stehengebliebenen Nummern ja nicht einfach durch Leerzeichen "hinpfuschen" (nicht böse gemeint).

LG

Hallo,

dafür musst du die Arbeitsweise des Display verstehen. Ab der Position worauf der Cursor das letztemal gesetzt wurde, schreibt das Display hintereinander seine empfangene Zeichen auf das Display.

Permanentes Display löschen führt zum flackern, wie du mitbekommen hast, was logisch ist, wenn man den Ablauf kennt.

Wenn man den Cursor wieder nach links setzt und weniger neue Zeichen kommen wie zuvor, dann bleibt der Rest im Display stehen. Ist auch normal so.

Deswegen schickt man am Ende nach einer neuen Ausgabe immer Leerzeichen mit zum löschen der störenden "falschen/alten" Zeichen. Das ist auch von allen am schnellsten was möglich ist für das Display. Das ist kein Pfusch.

Wenn du also Zahlen ausgibts
lcd.print(value1), dann schickste ein lcd.print(' ') hinterher oder für 2 und mehr Leerzeichen lcd.print(" ") und den nächsten Wert meinetwegen hintenran lcd.print(value2) wieder mit "Löschzeichen" rangestellt lcd.print(" ")

Musst natürlich aufpassen wenn du auf der letzten Zeile am Ende angekommen bist, dass du nicht auf Postion 0,0 Zeichen überschreibst.

Deswegen schickt man am Ende nach einer neuen Ausgabe immer Leerzeichen mit zum löschen der störenden "falschen/alten" Zeichen. Das ist auch von allen am schnellsten was möglich ist für das Display. Das ist kein Pfusch.

Habe gar nicht gedacht, dass ich dass mit dem Leerzeichen hinterherschicken machen könnte. Dann werde ich das damit mal angehen.

Danke und LG

Standard.User.:
Zum Beispiel wenn ich analoge Werte auf dem LCD ausgebe:

Jetzt ist beispielsweise der Wert meines analogen Inputs 123 dann steht auf dem Display:
123

wenn jetzt mein analoger Input einen Wert von 4 empfängt, steht ja auf der Anzeige nun:
423

Jetzt kann sich ja der analoge Input beliebig ändern.
Daher kann ich die stehengebliebenen Nummern ja nicht einfach durch Leerzeichen "hinpfuschen" (nicht böse gemeint).

Bei analogen (also bis zu 4stelligen) Werten mach ich das zum Beispiel so - die Werte werden dann immer rechtsbündig ausgegeben:
Edit: ACHTUNG der folgende Code ist nicht korrekt (siehe #7). Richtiger Code siehe #8!

...
// Ausgabe rechtsbuendig:
int readA0 = analogRead(A0);
if (readA0 < 999) {
  lcd.print(' ');
}
if (readA0 < 99) {
  lcd.print(' ');
}
if (readA0 < 9) {
  lcd.print(' ');
}
lcd.print(readA0);
...

Da wird, je nach Zahlenwert, mit Leerzeichen links aufgefüllt.

Es gibt natürlich auch elegantere Coldeschnippsel, die dasselbe in weniger Zeilen erledigen, aber diese Variante finde ich recht anschaulich :slight_smile:

Hier habe ich zwei allgemeine Varianten für Text und Integer gezeigt:
http://forum.arduino.cc/index.php?topic=303009.msg2108779#msg2108779
Etwas darunter ist die Text-Version

Ist etwas aufwendiger. Für Zahlen ist das aus #6 meist am praktischsten. Wobei es eigentlich <= heißen sollte

Serenifly:
Für Zahlen ist das aus #6 meist am praktischsten. Wobei es eigentlich <= heißen sollte

Stimmt natürlich oder < 1000 etc.
Mein Fehler.

Hier noch die korrigierte Variante:

...
// Ausgabe rechtsbuendig:
int readA0 = analogRead(A0);
if (readA0 < 1000) {
  lcd.print(' ');
}
if (readA0 < 100) {
  lcd.print(' ');
}
if (readA0 < 10) {
  lcd.print(' ');
}
lcd.print(readA0);
...