Kann man diesen Code kürzer schreiben ?

Hallo zusammen,

ich versuche mich grad etwas im Code kürzer schreiben. Der Code funktioniert soweit. Ich möchte diesen aber irgendwie kürzer schreiben. Mit kürzer versuche ich auch Zeilentechnisch sowie "weniger" Speicherplatz zu verwenden. Evtl. geht es ja auch gar nicht bei diesem Code?

Ich habe auch versucht den Code als Funktion zu schreiben, jedoch scheint der Complier meinen Code nicht zu schlucken. Ich Habe versucht sämtliche "Operatoren" mit zu übergeben. Was natürlich nicht funktioniert hat.

Kann man den überhaupt Werte + Operatoren an eine Funktion oder einer "for-Schleife" übergeben?

Hier der Code

void AutoBacklight() // Loop für Automatische Backlight Steuerung
{ 
  if (Backlight == true) { // Wenn Backlight auf (HIGH) Automatisch steht, dann....
    LDR = analogRead(analogPin);   // ... den Analogen Pin einlesen und den Wert in "LED" speichern (Bereich 0(ganz Hell) - 1023(ganz Dunkel))
    if (LDR >850) { // Wenn der "LDR" Wert >850 ( Also sehr Dunkel)
      for(Blight ; Blight >= 80; Blight -=5) { // Fahre Backlight herunter von Wert x zu Wert 80 per increment in 5er Schritten:
        analogWrite(BlightLED, Blight); // Schreibe neuen Wert von "Blight"      
        delay(15);  // Warte 15ms um den Dimmungseffekt zu sehen
      } 
      for(Blight ; Blight >= 1 && Blight <= 75; Blight -=1) { // Fahre Backlight herunter von Wert 75 zu Wert 1 per increment in 1er Schritten:
        analogWrite(BlightLED, Blight); // Schreibe neuen Wert von "Blight"    
        delay(15);  // Warte 15ms um den Dimmungseffekt zu sehen
      }
    }
    if (LDR <700) { // Wenn der "LDR" Wert <700 ( Also wenns Dämmert bis Dunkel)
      for(Blight ; Blight <= 15; Blight +=1) { // Fahre Backlight rauf bis Wert 15 per decrement in 1er Schritten:
        analogWrite(BlightLED, Blight); // Schreibe neuen Wert von "Blight"   
        delay(15);  // Warte 15ms um den Dimmungseffekt zu sehen
      } 
    }
    if (LDR >=550 && LDR <=650) { // Wenn der "LDR" Wert zwischen 550 und 650 liegt ( Also Hell bis Dämmert)
      for(Blight ; Blight >= 20; Blight -=5) { // Fahre Backlight herunter bis auf Wert 20 per increment in 5er Schritten:
        analogWrite(BlightLED, Blight); // Schreibe neuen Wert von "Blight"        
        delay(15);  // Warte 15ms um den Dimmungseffekt zu sehen
      } 
    }
    if (LDR <=450) { // Wenn der "LDR" Wert zwischen <=450 liegt ( Also sehr Hell)
      for(Blight ; Blight <= 250; Blight +=5) { // Fahre Backlight rauf bis Wert 255 per decrement in 5er Schritten:
        analogWrite(BlightLED, Blight); // Schreibe neuen Wert von "Blight"     
        delay(15);  // Warte 15ms um den Dimmungseffekt zu sehen 
      }
    }
  }
}

Ich würde anstatt die Funktion weiter zu kürzen, erst einmal die for-Schleifen mit den delays umschreiben.

  1. LDR Werte zusammenfassen
    static int ldrMap;

if(LDR >=550 && LDR <=650) ldrMap = 2;
...

static unsigned long lastMillis;

if(millis() - lastMillis >= 15) {
switch(ldeMap) {case 2: Blight += 1; break; }
}

Klar kann man das vereinfachen.

Wobei ich sagen muß, dass mir die Logik, nach der du PWM-Werte in Abhängigkeit vom LDR erzeugst nicht klar ist. Was passiert z.B. bei einem LDR-Wert von 800?

Mein Vorschlag wäre dieser:

void Autobacklight(){
  static unsigned long LastDim;
  static int Blightakt;
  int Blight_Ziel;
  if (millis() - LastDim < 15) return;  // Funktion nur alle 15ms durchlaufen
  LastDim = millis();
  
  int LDR = analogRead(analogPin);
 // abhängig von der Helligkeit wird ein Blight PWM-Zielwert ausgewählt.  
  if      (LDR < 450) Blight_Ziel = 255;   // unter 450
  else if (LDR < 650) Blight_Ziel = 20;    // zwischen 450 und 650
  else if (LDR < 850) Blight_Ziel = 15;    // zwischen 650 und 850
  else                Blight_Ziel = 1;     // über 850
  
      
  if (Blight_Ziel < Blightakt)  Blightakt -= 2;   // je nach dem, ob der gewünschte Blight PWM-Wert größer oder kleiner 
  if (Blight_Ziel > Blightakt)  Blightakt += 2;   // als der aktuelle ist, Blightakt  Wert verändern.
  analogWrite(BlightLED, Blightakt); 
}

Genereller Unterschied: Wenn deine Funktion aufgerufen wird, dann bleibt der Arduino so lange in der Funktion, bis der Ziel-PWM Wert erreicht ist.
diese Funktion wird nur alle 15ms ausgeführt. (muß in der Loop stehen, delay() ist verboten)
bei jedem Durchlauf wird der PWM-Wert nur einmal verändert.

Optimierungsmöglichkeiten:
a) Inkrement an die Helligkeit anpassen:
Du hast in deinem Code an einer Stelle ja deinen Inkrement mit dem du die PWM änderst unterschiedlich.
Sowas kann man natürlich auch hier einbauen, sonst dauert eine kompletter Durchlauf über 2min und wirkt nicht linear.

....
 // abhängig von der Helligkeit wird der Inkrementwert bestimmt
  int inkrement;   
  if      (Blightakt < 40 ) inkrement = 1;   // unter 40
  else if (Blightakt < 80 ) inkrement = 2;   // zwischen 40 und 80
  else                      inkrement = 5;   // über 80
  
  if (Blight_Ziel < Blightakt)  Blightakt -= inkrement;   // je nach dem, ob der gewünschte Blight PWM-Wert größer oder kleiner 
  if (Blight_Ziel > Blightakt)  Blightakt += inkrement;   // als der aktuelle ist, Blightakt  Wert verändern.
....

b) stetige Funktion für Helligkeit statt Stufen.
Wie schon Eingangs erwähnt, verstehe ich deine Logik LDR zu PWM nicht.
man könnte hier auch, anstelle einer Stufenfunktion eine echte, stetige Funktion nehmen.
Also anstelle der if-else Kette am Anfang z.B.

  // abhängig von der Helligkeit wird ein Blight PWM- ZielWert ausgewählt.  
  float x = (1023-LDR)/100.0;         // es wird hier der linke Zweig einer kubischen Funktion nachgebildet,
  Blight_Ziel = x * x * x;            // die bei etwa LDR=390 den Wert 255 erreicht.
  Blight_Ziel = constrain(Blight_Ziel, 1, 255);

Ich habe dir im Anhang mal verschieden Funktionen gegenübergestellt.

Zwischenablage01.jpg

Hallo Ihr beiden,

wow. Was soll ich sagen. Danke für die Denkanstöße. Ich wollte mit den "Lückenhaften" LDR Werten eine Art Hysterese verwirklichen. Das mit dem Unterschiedlichen Inkrement hatte folgenden Hintergrund. Die Funktion AutoBacklight ist die Hintergrunds Beleuchtung meiner Basis. Meine Idee war folgende: Wenn Umgebung sehr Hell, dann Beleuchtung auf 100%. Wenns Dämmert sollte die Beleuchtung nochmals gedimmt werden. Nachts soll auf Minimum gedimmt werden (Ich will ja Nachts schlafen ;)) Jetzt hatte ich aber einen Unschönen Effekt. Wenn man Nachts das Licht anmachte und anschließend ausmachte, Dimmte es nicht sauber (Damit meine ich das Visuelle, was ja aus deinem Chart sehr deutlich wird.) Ich hatte mir damit beholfen nochmals ab einen gewissen Wert anders zu dimmen. Also eine missglückte 3 Stufen Dimmer :slight_smile:

P.s. Die for Schleife hatte ich aus einem Beispiel Code und fand sie brauchbar da man nach "Harten" (Licht ein / Licht aus) den Dimm Effekt sofort gesehen hat. Mir ist bewusst das solange die for Schleife läuft, nichts anderes vom Arduino ausgeführt werden kann.

ht81:
Hallo Ihr beiden,

wow. Was soll ich sagen. Danke für die Denkanstöße. Ich wollte mit den "Lückenhaften" LDR Werten eine Art Hysterese verwirklichen.

Hysterese brauchst du eigentlich nicht. Wenn sauber programmiert ist, dann folgt das Backlight immer der Umgebungshelligkeit. Egal ob es heller oder dunkler wird.

ht81:
Das mit dem Unterschiedlichen Inkrement hatte folgenden Hintergrund. Die Funktion AutoBacklight ist die Hintergrunds Beleuchtung meiner Basis. Meine Idee war folgende: Wenn Umgebung sehr Hell, dann Beleuchtung auf 100%. Wenns Dämmert sollte die Beleuchtung nochmals gedimmt werden. Nachts soll auf Minimum gedimmt werden (Ich will ja Nachts schlafen ;)) Jetzt hatte ich aber einen Unschönen Effekt. Wenn man Nachts das Licht anmachte und anschließend ausmachte, Dimmte es nicht sauber (Damit meine ich das Visuelle, was ja aus deinem Chart sehr deutlich wird.) Ich hatte mir damit beholfen nochmals ab einen gewissen Wert anders zu dimmen. Also eine missglückte 3 Stufen Dimmer :slight_smile:

Siehe oben. Einfach der Umgebung folgen lassen.

ht81:
P.s. Die for Schleife hatte ich aus einem Beispiel Code und fand sie brauchbar da man nach "Harten" (Licht ein / Licht aus) den Dimm Effekt sofort gesehen hat. Mir ist bewusst das solange die for Schleife läuft, nichts anderes vom Arduino ausgeführt werden kann.

Siehe oben. Das Backlight folgt der Umgebungshelligkeit. Immer. (und der Arduino kann noch anderes machen!)