Hallo Nachteulen,
ein lieber Kollege im Forum hat mich gebeten zu erklären wie „Es ward Licht“ funktioniert. Meine Erklärung ist nicht so spannend wie das andere Leute vor mir beschrieben haben, aber sie passt zu 1:87 (und vermutlich auch für 1:160).
Leider ist der „Prog_Generator“ noch nicht so weit, dass man das damit, ohne zu programmieren, konfigurieren kann. Gebt mir noch mal 7 Tage (oder vielleicht ein paar mehr) bis ich das für das Excel Sheet implementiert habe.
Basis ist das Beispiel „17.Darkness_Detection.ino“.
Ich habe eben auch noch mal versucht zu verstehen was sich das kranke Hirn da ausgedacht hat...
Am besten Ihr schaut Euch zunächst die Ausgabe des seriellen Monitors der Arduino IDE an (Baud Rate 9600):
Das Bild zeigt einen kurzen Ausschnitt in dem es dunkler wird. Zum Test habe ich den LDR einfach abgedeckt. Der "" zeigt an, dass sich das Programm den "Sonnenuntergang" erkannt hat. Der LDR misst eine "Dunkelheit" von 106. Wenn es Stockdunkel ist sind es etwa 240.
Die fallenden Zahlen beschreiben den gefilterten "Dunkelheitswert" (32 bis 105 in dem Ausschnitt).
Wenn Ihr keinen LDR habt (z.B. GL5537 von https://www.amazon.de/dp/B01MR2YJ2S/ref=...9395811_TE_dp_2), dann könnt Ihr die „Tag/Nacht“ Pins auf der Hauptplatine auch mit einem Schalter verbinden (Schalter geschlossen = Tag). In dem Fall wird die Helligkeit langsam verändert.
Diese „Dunkelheitswerte“ werden von der "Schedule()" Funktion ausgewertet. In dem Beispiel habe ich 4 verschiedene Funktionen verwendet.
Die erste Funktion
1
Schedule(INCH0, INCH2, SI_1, 60, 110) // Random activated houses
aktiviert die Lichter in den Häusern, wenn die Dunkelheit zwischen 60 und 110 ist. Die Zeile schaltet 3 verschiedene Häuser. Diese werden über INCH0 – INCH2 zufällig gesteuert, wenn die Dunkelheit einsetzt.
Gesteuert bedeutet, dass der „Hauptschalter“ für die einzelnen Häuser aktiviert wird. In dem Moment werden die Lichter in dem entsprechenden Haus wiederrum von einem eignen Zufallsprogramm gesteuert.
Für das Verständnis der "Schedule()" Funktion ist das zunächst hinderlich, weil hier zu viele Zufälle mitspielen. Darum habe ich in dem Beispiel den Kompilerschalter „SINGLE_LEDS_EXAMPLE“ eingebaut mit dem man die „Hauptschalter“ der Häuser zunächst einzeln untersuchen kann bevor man dann damit Tatsächlich die Preiserleins erleuchtet. Dieser Schalter ist zunächst aktiviert.
Zum Test werden 6 RGB LEDs benötigt. Die ersten drei LEDs werden von dem „Schedule()“ Makro oben gesteuert. Sie gehen nacheinander zufällig an (Blau), wenn die „Dunkelheit“ zwischen 60 und 110 ist. Entsprechend gehen sie wieder aus, wenn es wieder Heller wird.
Im dem Beispiel gibt es noch weiter „Schedule()“ Zeilen:
1
2
3
4
5
Schedule(INCH3, INCH3, SI_1, 150, 150) // Light in the shop
Schedule(INCH4, INCH4, SI_1, 50, 50) // Gas lights are turned on early in the evening
Schedule(INCH5, INCH5, SI_1, 200, 200) // Late in the night the traffic light is disabled (Yellow flashing)
Auch hier werden zunächst nur die „Hauptschalter“ betrachtet.
Das Licht in dem Laden wird immer genau bei der „Dunkelheit“ 150 geschaltet (Der Ladenbesitzer verwendet einen Helligkeitssensor oder eine Schaltuhr). In der Testkonfiguration wird dieser „Hauptschalter“ mit der 4. blauen LED dargestellt.
Bei den Straßenlaternen wird es genau so gemacht. Hier ist als Schwelle der Wert 50 vorgegeben. Zur Visualisierung wird die 5. LED Weis angesteuert.
Schließlich wird mit der Letzen „Schedule()“ Zeile die Verkehrsampel deaktiviert. Ganz spät in der Nacht soll diese nur noch Gelb blinken. Der Steuerkanal wird mit einer roten LED gezeigt. Hier ist die Steuerung per „Dunkelheit“ eigentlich nicht geeignet denn es wird ja in der Realität auch nicht erst um Mitternacht ganz dunkel. Die Ampel sollte eigentlich von einer „Modellbahnzeit“ gesteuert werden.
Am besten Ihr spielt das Beispiel mal auf den Arduino und schaut euch das in Ruhe an.
Im nächsten Schritt könnt Ihr die „#define SINGLE_LEDS_EXAMPLE” Zeile auskommentieren:
1
//#define SINGLE_LEDS_EXAMPLE // If this line is enabled single LEDs are used to demonstrate the Schedule() function. Otherwise "real" houses, lamps, ... are used
Dann wird es so chaotisch wie im echten Leben.
Solange es Tag ist geht es noch. Die Ampel regelt fleißig den Verkehr und im Geschäft brennt das Licht damit die Kunden die Waren im besten Licht sehen.
Wenn es dunkel wird dann schalten sich ab einem Wert von 50 die Straßenlaternen nacheinander an. Da es Gaslampen sind dauert es eine gewisse Zeit bis sie die volle Helligkeit erreichen.
Danach gehen langsam die ersten Lichter in den Häusern an. Jetzt kann man kaum mehr nachvollziehen welche LED zu welchem Haus gehört. Die LEDs werden entsprechend den „House()“ Zeilen mit verschiedenen Funktionen aktiviert (TV, Neon Licht, Offener Kamin, warmes oder kaltes Licht…). So wie im wirklichen Leben mit einer Ausnahme. Auf der Anlage können wir bestimmen wie viele Lichter gleichzeitig in einem Haus brennen dürfen. Bei mir Zuhause kann ich das nicht ;-( Wenn ich abends heim komme brennen immer alle möglichen Lichter auch wenn die gesamte Familie am Abendessen sitzt.
Achtung es dauert recht lange bis mehrere Lichter in einem Haus angeschaltet werden. Die Preiser sind ja recht Energiebewusst.
Das Licht in dem Geschäft wird spät abends abgedunkelt da eh keine Kunden mehr kommen aber die Einbrecher sich nicht verletzen sollen, wenn sie ganz im Dunklen durch dem Laden schleichen.
Schließlich wird auch noch die Ampel deaktiviert.
Wenn es wieder Heller wird läuft das Ganze in umgekehrter Reihenfolge wieder ab. Dabei wird nicht simuliert, dass die Preiser irgendwann schlafen gehen und die Lichter ganz ausgehen. Aus gut unterrichteten Kreisen wird berichtet, dass Preiser viel weniger Schlaf benötigen als 1:1 Menschen. Das ist für den Betrachter der Anlage auch ganz gut so. Sonst würden am Ende auch noch Nachtfahrverbote für die Züge eingeführt was dann doch relativ langweilig würde…
Ist noch jemand da?
Jetzt geht es ans Eingemachte!
Nur noch für HACKER:
Wenn man die Helligkeitssteuerung der LEDs über das Excel Programm „Prog_Generator_MobaLedLib.xlsm“ machen will, dann muss man einige Angaben von Hand machen. Das werde ich in einer der nächsten Versionen des Programms automatisieren, aber es gibt ungeduldige unter Euch (Nein, ich werde keine Namen nennen) die das jetzt schon haben wollen.
Eigentlich muss man dazu nur ein paar Zeilen von Hand eingeben. Zunächst benötigen wir die „#define INCH…“ Zeilen. Dazu aktiviert man bei der Makro Auswahl den „Expertenmodus“ und wählt das Makro „Next_LEDs“:
Im folgenden Dialog gibt man bei „Änderung von StartLedNr“ eine 0 an.
Diese Zeile brauchen wir eigentlich nur zur Eingabe der „#define“ Zeilen. Wir ersetzen das „// Next_LED(0)“ mit „#define INCH0 100“.
Für das Beispiel benötigen wir die Konstanten INCH0 bis INCH5. Darum kopieren wir die Zeile über den „Kopiere Zeilen“ Knopf fünfmal und passen die Werte so an:
1
2
3
4
5
6
7
8
#define INCH0 100
#define INCH1 101
#define INCH2 102
#define INCH3 103
#define INCH4 104
#define INCH5 105
Als nächstes wählen wir in der Makroauswahl die „Schedule()“ Funktion und geben folgende Werte an:
Die Zahlen 1, 2 und 3 ersetzen wir anschließend manuell in der Excel Tabelle durch:
INCH0, INCH2, SI_1. Das Ergebnis sollte so aussehen:
1
2
3
Schedule(INCH0, INCH2, SI_1, 60, 110)
Auch diese Zeile wird dreimal kopiert und angepasst:
1
2
3
4
5
6
Schedule(INCH0, INCH2, SI_1, 60, 110)
Schedule(INCH3, INCH3, SI_1, 150, 150)
Schedule(INCH4, INCH4, SI_1, 50, 50)
Schedule(INCH5, INCH5, SI_1, 200, 200)
Jetzt können die drei Häuser eingegeben werden. Das kann fast ganz normal gemacht werden. Lediglich die Konstante „#InCh“ muss manuell ersetzt werden.
Achtung: Die neuen Konstanten müssen in Großbuchstaben geschrieben werden.
Nach den Häusern kommt ein „Const()“ Makro mit dem die Beleuchtung im Geschäft gesteuert wird. Achtung: Hier wird bei „Helligkeit wenn deaktiv“ eine 255 und bei „aktiv“ eine 10 eingetragen. Damit ist das Licht im Laden normalerweise ganz an und wenn der „Hauptschalter“ betätigt wird leuchten die Lampen nur noch schwach.
Bei der „Const()“ Funktion und bei der folgenden „GasLights()“ muss wiederrum die „#Inch“ durch „INCH3“ bzw. „INCH4“ ersetzet werden.
Eine letzte Hürde ist noch die Eingabe der Ampel Zeile. Diese spezielle Ampel kann nicht über die Makroauswahl selektiert werden. Da wir inzwischen mutiger sind machen wir das ganz von Hand. Der erste Schritt ist leicht. In die „Beleuchtung, Sound, oder andere Effekte“ kommt dieses hier:
1
2
3
RGB_AmpelX_Fade_IO(#LED, INCH5)
In Spalte LEDs muss jetzt noch eine 6 eingetragen werden. Aber das geht nicht so einfach. Da hat sich der fiese Programmierer was ganz Besonderes einfallen lassen. Immer wenn man die Spalte anklickt hüpft der Cursor wieder raus !?!
Das habe ich gemacht damit man diese Werte nicht versehentlich verändert. Aber es gibt einen Trick. Man klickt in die Spalte neben der Tabelle und geht dann mit der „Cursortaste“ nach links. Hier gibt man in Spalte „Loc InCh“ eine 0, in „InCnt“ eine 1 und in „LEDs“ eine 6 ein. Nach der Eingabe einer Zahl betätigt man die „linke Cursortaste“ und nicht „Enter“.
(Excel Kenner werden anmerken, dass man versehentliche Eingaben auch über den Excel Blattschutz hätte verhindern können… Ich fand diese Lösung pfiffiger, weil man evtl. vergisst den Blattschutz zu aktivieren.)
Danach sollte die Tabelle so aussehen:
Die von Hand einzugebenden Teile habe ich blau hervorgehoben. Die Farbe ist für die Funktion nicht wichtig.
Die Beschreibungsspalte habe ich für Euch absichtlich leer gelassen damit Ihr mit Euren Kommentaren Beweisen könnt, dass Ihr verstanden habt was die einzelnen Zeilen bedeuten. Ihr könnt Eure Lösungen im Forum posten und der Beste bekommt einen wertvollen Preis!
Aber das ist immer noch nicht alles ;-(
Wozu schreibe ich eigentlich noch weiter? Bis hier her kommt keiner mehr oder?
Ergänzungen am „23_B.LEDs_AutoProg.ino“ Programm
Jetzt müssen noch ein paar Zeilen in das „23_B.LEDs_AutoProg.ino“ Programm eingefügt werden.
Diese Zeilen werden nach der „#include „MobaLedLib.h“ Zeile eingefügt:
1
2
3
4
5
6
7
8
9
#define SWITCH_DAMPING_FACT 1 // 1 = Slow, 100 Fast (Normal 1)
#include "Read_LDR.h" // Darkness sensor
#define LDR_PIN A7 // Use A7 if the MobaLedLib "LEDs Main Module" is used
#define RGB_AmpelX_Fade_IO(LED, InNr) /* Fading Traffic light for tests with RGB LEDs */
APatternT8(LED,0,InNr,18,0,255,0,PF_NO_SWITCH_OFF|PF_INVERT_INP,200 ms,2 Sec,200 ms,1 Sec,200 ms,10 Sec,200 ms,3 Sec,1,2,4,8,144,33,64,134,0,128,2,0,10,128,33,0,134,0,1,2,4,8,16,32,67,128,12,1,0,5,0,20,0,67,0,12)
APatternT4(LED,0,InNr,18,0,255,0,PF_NO_SWITCH_OFF, 100 ms,300 ms,100 ms,500 ms,24,48,96,192,0,0,0,0,0)
An das Ende der “setup()“ Funktion kommt dieses hier:
1
2
3
Init_DarknessSensor(LDR_PIN); // Attention: The analogRead() function can't be used together with the darkness sensor !
Und wenn man die Anzeige der „Dunkelheit“ im seriellen Monitor der IDE sehen will dann kommen diese Zeilen an das Ende der „loop()“ Funktion:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
// Debug
static uint32_t Next_LDR_Update = 1000;
if (millis() > Next_LDR_Update)
{
Next_LDR_Update = millis() + 1000;
char ds = '-';
switch (DayState)
{
case Unknown: ds ='-'; break;
case SunRise: ds ='/'; break;
case SunSet: ds ='\'; break;
}
char Buf[30];
sprintf(Buf, "%c Inp:%3i damped:%3i %s", ds, Get_Act_Darkness(), Darkness, AD_Flags.SwitchMode?"SW":"LDR");
Serial.println(Buf);
}
Achtung: In dem Programm wird die Baudrate 115200 benutzt.
Wenn Ihr alles richtig gemacht habt, dann sollte es jetzt funktionieren.
Achtung: Bevor Ihr auf den „Z. Arduino schicken“ Knopf drückt muss der serielle Monitor der IDE geschlossen werden, weil dieser sonst den Zugriff auf die serielle Schnittstelle blockiert.
Wenn es nicht klappt, dann überprüft alles noch mal 37mal. Wenn Ihr den Fehler trotzdem nicht findet, dann schickt mir Euer Excel Programm und die „23_B.LEDs_AutoProg.ino“ Datei per Mail (Die Adresse findet ihr hier: [User]Hardi[/User])
Wenn es Funktioniert, dann schlage ich Euch zum MobaLedLib Ritter!
Hardi