Zum Inhalt springen
Arduino RailFX Raumbeleuchtung RGB RGBW Strip Modellbahn

RailFX-Raumbeleuchtung: Tag und Nacht für die Modellbahn

    Dieses Modul des RailFX-Systems steuert die Raumbeleuchtung der Modellbahn-Anlage. Dazu wird ein RGBW-LED-Strip als Lichtquelle verwendet. Natürlich ist auch dieses Modul vom Miniatur-Wunderland inspiriert :-)

    Schaltplan

    RailFX-Raumbeleuchtung Modellbahn Modellbau Lichtsystem Arduino RGB RGBW

    Der LED-Strip besteht aus vier Parallelschaltungen von LEDs (Rot, Grün, Blau, Weiß). Bei meinem Strip sind Rot, Grün und Blau in einem LED-Gehäuse zusammengefasst, während die weiße LED ein Extra-Bauteil ist. Alle LEDs teilen sich die Anode (Plus-Pol). Man nennt sie Common-Anode (gemeinsame Anode).

    Beim Kauf muss man also auf den Verbindungsstellen der LED-Strips irgendwo einen Hinweis finden, z.B. ein +, ein 5V+ oder ein 12V+.


    Sieh dir jetzt meinen neuen Arduino-Videokurs an: Jetzt ansehen!


    Arduino RGBW-LED Strip Common Anode

    Mein LED-Strip hatte Female-Pinheader als Anschluss, die sehr leicht mit Patch-Kabeln verbinden ließen.

    Wie im Schaltplan zu sehen, muss der GND des externen Netzteils mit dem GND des Arduino-Boards verbunden werden. Der Plus darf dagegen nur mit dem LED-Strip verbunden werden!

    Gesteuert werden die LEDs nun durch N-Channel MOS-FET-Transistoren. Ich verwende hierfür die IRF630N Transistoren. Sie benötigen im Gegensatz zu normalen Transistoren keine Vorwiderstände. Die Beinchen heißen Gate, Drain und Source. Der Source-Anschluss wird mit dem GND verbunden. Der Drain-Anschluss ist mit der jeweiligen LED-Farbe verbunden und würd über das Gate gesteuert. Das Gate ist mit den PWM-Pins des Arduino-Nano-Boards verbunden (D6 – Blau, D9 – Grün, D10 – Rot, D11 – Weiß).

    Achtung: Am Pin A4 ist das Control-Signal des RailFX Control-Moduls angelegt. Es steuert die Tageszeit und ist zwingend erforderlich.

    Bauteile

    Einstellungen im Code

    Es werden vier Phasen des Raumlichts durchlaufen: Sonnenaufgang, Tag, Sonnenuntergang, Nacht. Im Code lassen sich mehrere Einstellungen vornehmen. Diese sind in dem Code-Abschnitt näher erläutert. Es handelt sich um die Lichtfarben der jeweiligen Phasen und die Geschwindigkeit des Übergangs (frameSpeed).

    /* ***** ***** Einstellungen ***** ***** */
    int frameSpeed = 100;                    // Verzögerung der Lichtübergänge (je höher, desto langsamer)
    float lichtFarben[4][4] = {
      {200.0, 50.0, 0.0, 0.0},               // Sonnenaufgang
      {0.0 , 0.0 , 0.0, 255.0},              // Tag
      {150.0, 0.0, 60.0, 50.0},              // Sonnenuntergang
      {0.0 , 0.0 , 60.0, 0.0}                // Nacht
    };

    Beim Upload muss man darauf achten, dass das richtige Board im Arduino-Menü ausgewählt ist. Dazu muss ebenfalls im Werkzeuge-Menü im Unterpunkt Prozessor »ATmega328P (Old Bootlaoder)« ausgewählt sein.

    Der folgende Programmcode kann mit den oben erwähnten Änderungen einfach kopiert und auf das Arduino-Nano geladen werden.

    Code für das Modul: RailFX-Raumbeleuchtung

    /*
        Rail-FX Raumbeleuchtung
        StartHardware.org
    */
    
    /* ***** ***** Einstellungen ***** ***** ***** *****  ***** ***** ***** *****  ***** ***** ***** ***** */
    
    int frameSpeed = 100;                    // Verzögerung der Lichtübergänge (je höher, je langsamer)
    float lichtFarben[4][4] = {
      {200.0, 50.0, 0.0, 0.0},               // Sonnenaufgang
      {0.0 , 0.0 , 0.0, 255.0},              // Tag
      {150.0, 0.0, 60.0, 50.0},              // Sonnenuntergang
      {0.0 , 0.0 , 60.0, 0.0}                // Nacht
    };
    
    /* ***** ***** Ab hier beginnt der Programmcode, der nicht angepasst werden muss ***** ***** ***** ***** */
    
    int bluePin = 6;                         // an diesem Pin ist der blaue Kanal der RGBW-LEDs angeschlossen
    int greenPin = 9;                        // an diesem Pin ist der grüne Kanal der RGBW-LEDs angeschlossen
    int redPin = 10;                         // an diesem Pin ist der rote Kanal der RGBW-LEDs angeschlossen
    int whitePin = 11;                       // an diesem Pin ist der weiße Kanal der RGBW-LEDs angeschlossen
    
    /* Variablen für Lichtfarben*/
    float aktuelleFarbe[4];
    float farbSchritte[4][4];
    int samples = 255;
    
    int frameNumber = 0;
    long frameTimer = 0;
    
    boolean transitionDone = false;
    
    int phase = 3;
    
    /* Variablen vom Controlmodul um die Uhrzeit festzustellen*/
    boolean receive = false;
    boolean receiveStarted = false;
    int receiveTimeout = 10;
    long receiveTimer = 0;
    int receivedTime = 0;
    int receivePulse = 0;
    int lastReceivePulse = 0;
    int receivePin = 18;
    int myTime = 23;
    int myOldTime = 0;
    
    #define PAYLOAD_SIZE 2                   // nötig für die Kommunikation zum Master
    int uhrzeit = 0;                         // speichert die uhrzeit vom Master-Modul (0 und 255)
    byte nodePayload[PAYLOAD_SIZE];          // speichert die Daten vom Master-Modul zwischen
    
    void setup() {
      Serial.begin(115200);                  // started die serielle Kommunikation
      pinMode(receivePin, INPUT);            // Empfangspin vom Control-Modul
    
      for (int i = 0; i < 4; i++) {
        if (phase != 3) {
          if (lichtFarben[phase][i] < lichtFarben[phase + 1][i]) {
            farbSchritte[phase][i] = (lichtFarben[phase + 1][i] - lichtFarben[phase][i]) / 255;
          } else if (lichtFarben[phase][i] > lichtFarben[phase + 1][i]) {
            farbSchritte[phase][i] = (lichtFarben[phase][i] - lichtFarben[phase + 1][i]) / -255;
          }
        } else {
          if (lichtFarben[phase][i] < lichtFarben[0][i]) {
            farbSchritte[phase][i] = (lichtFarben[0][i] - lichtFarben[phase][i]) / 255;
          } else if (lichtFarben[phase][i] > lichtFarben[0][i]) {
            farbSchritte[phase][i] = (lichtFarben[phase][i] - lichtFarben[0][i]) / -255;
          }
    
        }
        Serial.println(farbSchritte[phase][i]);
      }
    }
    
    void loop() {
      receiveFunction();                    // Führe Anweisungen für Empfang aus
      if (receiveStarted == false) {        // Falls gerade keine Daten empfangen werden:
        if (myTime == 20) {                 // ***** Sonnenuntergang *****
          if (myOldTime != myTime) {        // wenn die Stunde umschaltet
            phase = 1;                      // setzt Übergangsphase
            transitionDone = false;         // Übergangsphase wird ausgeführt
            Serial.println("Sonnenuntergang");
          }
        } else if (myTime == 6) {           // ***** Sonnenaufgang *****
          if (myOldTime != myTime) {        // wenn die Stunde umschaltet
            phase = 3;                      // setzt Übergangsphase
            transitionDone = false;         // Übergangsphase wird ausgeführt
            Serial.println("Sonnenaufgang");
          }
        }
      }
    
      if ((frameTimer + frameSpeed < millis()) && (transitionDone == false)) {
    
        for (int i = 0; i < 4; i++) {
          if (phase != 3) {
            aktuelleFarbe[i] = map(frameNumber, 0, 255, lichtFarben[phase][i], lichtFarben[phase + 1][i]);
          } else {
            aktuelleFarbe[i] = map(frameNumber, 0, 255, lichtFarben[phase][i], lichtFarben[0][i]);
          }
        }
    
        frameNumber++;
        if (frameNumber > samples) {
          frameNumber = 0; 
          if (phase == 3) {                       // Automatischer Übergang von Sonnenaufgang zu Tag
            phase = 0;
          } else if (phase == 1) {                // Automatischer Übergang von Sonnenuntergang zu Nacht
            phase = 2;
          } else {
            transitionDone = true;
          }
        }
        frameTimer = millis();
      }
    
      analogWrite(redPin, aktuelleFarbe[0]);      // Setzen der LED-Farbe
      analogWrite(greenPin, aktuelleFarbe[1]);    // Setzen der LED-Farbe
      analogWrite(bluePin, aktuelleFarbe[2]);     // Setzen der LED-Farbe
      analogWrite(whitePin, aktuelleFarbe[3]);    // Setzen der LED-Farbe
    
      myOldTime = myTime;
    }
    
    void receiveFunction() {                      // Empfängt die Uhrzeit vom Control-Modul
      receivePulse = digitalRead(receivePin);     // Lies den Empfangspin aus
    
      if ((receiveTimer + receiveTimeout < millis()) && (receiveStarted == true)) {
        // Bei Timeout und aktivem Empfang
        receiveStarted = false;                   // beende aktiven Empfang
        myTime = receivedTime - 1;                // speichere die empfangene Zeit
        receivedTime = 0;                         // setze die Hilfsvariable zum Zeitempfang zurück
        Serial.println(myTime);                   // serielle Ausgabe
      }
      // falls ein Puls am Empfangspin erfasst wird, der vorher nicht da war
      if ((receivePulse == 0) && (lastReceivePulse == 1)) {
        receiveTimer = millis();                  // starte Timer neu
        if (receiveStarted == false) receiveStarted = true;  // starte aktiven Empfang, wenn noch nicht geschehen
        receivedTime++;                           // es gab einen Puls, also erhöhe die Hilfsvariable zum Zeitempfang
      }
      lastReceivePulse = receivePulse;            // aktuellen Zustand am Pin für nächsten Durchlauf merken
    }

    Wenn dir das Projekt gefallen hat und du von weiteren interessanten Projekten inspiriert werden willst, sieh dir doch mal mein neues E-Book »Arduino Projekte Volume 1« an!

    • Die beliebtesten Arduino-Projekte von StartHardware
    • Inklusive Schaltplan, Beschreibung und Code
    • Arduino-Schnellstart-Kapitel
    • Kompakter Programmierkurs


    15 Gedanken zu „RailFX-Raumbeleuchtung: Tag und Nacht für die Modellbahn“

    1. Schade,
      leider kommt hier keine Reaktion mehr auf eine Anfrage. Seit 2 Wochen warte ich auf eine Antwort, da die Schaltung nicht funktioniert. Mittlerweile habe ich noch eine 2. Schaltung aufgebaut, um vielleicht Fehler in der Hardware auszuschließen, aber das gleiche Ergebnis. Kein Lichtwechsel findet statt.

    2. Hallo Stefan,
      ich verwende die von dir angegebenen Bauteile. Leider läuft es nicht wie gewünscht. Das Control-Modul startet mit 5:00 Uhr, das Licht ist Bläulich. Um 6:00 Uhr startet die Mörgendämmerung. Gegen 8:00 Uhr ist nur noch das weiße Licht an. Um 22:00 Uhr kommt nicht der Wechsel zur Abenddämmerung. Es bleibt nur noch das weiße Licht an. Selbst, wenn ich 2-3 Durchläufe schalten lasse. Es bleibt nur noch das weiße Licht an. An dem Control-Modul liegt es nicht. Damit schalte ich die Kirchenbeleuchtung und die Glocken. Da funktioniert alles perfekt. Es kann nur an dem Modul für Tag und Nacht liegen bzw. der Steuerungssoftware.

      Beste Grüße
      Dieter

    3. Hallo Stefan, ich bin begeistert von Deinen Schaltungen und habe mir jetzt die Tag-Nacht-Raumbeleuchtung nachgebaut.
      Ich habe aber mal eine Frage, da ich absoluter Arduino-Anfänger bin.
      Wie müsste der Arduino-Sketch aussehen, wenn man in der Tag-/Nacht-Steuerung zusätzlich eine Gewittersimulation realisieren wollte.

    4. Hallo Stefan, Schaltung läuft. Ich habe nur sehr lange daran gesessen, da Deine Schaltung falsch ist. Ich hatte erst Die Vermutung, dass das Programm falsch war, es ist aber die Schaltung. Ich habe mich entschlossen nur rot und weiß einzustellen, das kommt der Eisenbahn in Hamburg am nähesten.
      Gruß Volker

      1. Hi Volker,

        das ist ja merkwürdig. Ich hab die Schaltung gerade noch mal mit meiner abgeglichen und sie sind gleich. Die Schaltung vor mir läuft einwandfrei. Welche Transistoren hast du verwendet? Manchmal sind die unterschiedlich gedrahtet. Ich würde der Sache gern auf den Grund gehen.

        Liebe Grüße

        Stefan

        1. Hallo Stefan, wenn Du auf den Plan schaust, sind die Ausgänge D6, D9, D10 und D11 belegt. Dies stimmt aber nicht mit Deiner Schaltung überein. zusätzlich musste ich bei meinem Strip (den, den Du empfohlen hast) die Farben grün und blau tauschen.
          Dies ist zwar Peanuts zur Qualität der Schaltung, aber vielleicht hilft das diese Schaltung besser nach zu bauen.
          Gruß Volker

          1. Hi Volker, danke für die Info! Das hilft mir echt weiter. Die Pins sind tatsächlich durcheinander gekommen. Ich hab das jetzt in der Grafik angepasst. Klar, man braucht für das Dimmen natürlich PWM-Pins. Die Farbbelegung der Pins ist übrigens von Strip zu Strip unterschiedlich und die ändern sich selbst beim gleichen Produkt manchmal. Das kann man wahrscheinlich schnell im Code tauschen:

            int bluePin = 6; // an diesem Pin ist der blaue Kanal der RGBW-LEDs angeschlossen
            int greenPin = 9; // an diesem Pin ist der grüne Kanal der RGBW-LEDs angeschlossen
            int redPin = 10; // an diesem Pin ist der rote Kanal der RGBW-LEDs angeschlossen
            int whitePin = 11; // an diesem Pin ist der weiße Kanal der RGBW-LEDs angeschlossen

            Also, vielen Dank nochmal und hab ein schönes Wochenende. Liebe Grüße Stefan

      2. Hallo Volker,
        ich taste mich auch gerade an die Schaltung heran. Sie läuft auch, aber meine Modellzeit beginnt um 5 Uhr mit der Nacht. Die Licht ist bläulich. Um 8 Uhr ist nur noch das weiße Licht an und das bleibt auch so. Es passiert kein Wechsel von Tag zur Nacht und auch Morgens keine Veränderung mehr. Ist einmal das weiße Licht an, bleibt auch nur dieses an.
        Welcher Fehler liegt denn in der Software vor und welche Einstellungen für die Farbe brauche ich, damit es optisch in Richtung Miniatur Wunderland geht?
        Viele Grüße
        Dieter

    5. Hallo Stefan, ich bin begeistert, dass Du meine Anregung angenommen hast.. Teile sind bestellt und Ende der Woche werde ich das Ergebnis sehen.
      Das Einzige was jetzt noch fehlt ist eine Bahnsteig bzw. Busbahnhofanzeige mit einem 0.96 Oled Display. Ich habe dies schon mal programmiert, wenn da aber noch Leben reinkommen würde über da Controlmodul, wäre das der Hammer. Spreche ich Dich damit an?

    Schreibe einen Kommentar

    Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert

     

    Diese Website verwendet Akismet, um Spam zu reduzieren. Erfahre mehr darüber, wie deine Kommentardaten verarbeitet werden.