Forum: Mikrocontroller und Digitale Elektronik Probem mit Arduino DMXSerial und WS2812 / Triac Steuerung


von Heiko (Gast)


Angehängte Dateien:

Lesenswert?

Hallo liebe Community,
ich bin gerade dabei eine DMX Box zu bauen die universell als Demux, 
Strobe Controller oder als Dimmersteuerung verwendet werden kann. 
Hierfür verwende ich einen Arduino nano, 3 Buttons und für die 
Einstellungen usw. einen0,96“ OLED Display.
Für den DMX Empfang benutze ich DMXSerial.h welches mir jedoch einige 
Probleme bereitet.
Sobald ich in mein Programm die WS2812 Pixels als Status-Leds einbinde 
kommen die Kanäle von DMX-Serial nicht mehr sauber an und sowohl die 
Status-LEDs flackern und auch der Output ist gestört.

Auch habe ich es mit Milis versucht, dass die WS2812 nicht andauernd 
aktualisiert werden.
Wenn in der Main Loop Schleife auch Taster abfragen oder ähnliches steht 
bringt mir das den Output von DMXSerial durcheinander. Kanal 1 
funktioniert immer einwandfrei. Ab Kanal 2 spinnt dann alles irgendwie 
rum. Mir scheint es auch, dass sich die Kanäle irgendwie verschieben und 
dann teilweise für den Kanal 2 der Wert von Kanal 3 genommen wird und 
dieser dann an die Status LEDs und den Output gesendet werden.
Ein weiteres Problem bekomme ich wenn ich in die ISR des Timers mit 
welchem ich die Triacs des Dimmers anspreche eine Abfrage reinsetze. Die 
Outputs fangen dann oftmals zum Flackern an.
Einen kleinen Programmauszug habe ich mal beigepackt.



Ich hoffe Ihr könnt mir helfen ?

LG Heiko

von Mick (Gast)


Lesenswert?

Habe deinen Quellcode nicht angeschaut, aber das Problem liegt in den 
verwendeten Timern. Schaue mal nach, welche Timer in den jeweiligen 
Bibliotheken verwendet werden. Evtl. findest du alternative 
Bibliotheken, die sich nicht gegenseitig "beissen".

von fop (Gast)


Lesenswert?

Hi,
ich denke auch da beissen sich die verwendeten Bibliotheken. Ich 
vermute, dass es eher was zeitliches ist. Die Ansteuerung der WS2812 
wird bestimmt mangels spezialisierter Hardware komplett per Bitbanging 
in Software realisiert. In dieser Zeit geht nichts anderes.
Der DMX - Empfang läuft hoffentlich zu 97% über die UART, so dass ein 
bis zwei Byte in dieser Zeit empfangen werden können. Wenn Du den Pin, 
auf dem die DMX-Daten ankommen, frei wählen kannst, spricht das jedoch 
dafür, dass auch diese Library alles in Software macht.
Weil Du aber nur einen Kern hast, geht nur eins zur gleichen Zeit.
Diese beiden Librarys können also nicht gleichzeitig eingesetzt werden.
Versuche es zunächst mit einer anderen DMX-Library. Wie gesagt, bei der 
Led-Ansteuerung geht wohl nur Software. Schlimmstenfalls musst Du die 
Routinen mehr oder weniger selbst schreiben, um den Überblick zu haben, 
wer wann zum Zug kommt. Dabei kannst Du natürlich aus den Librarys 
abkupfern.

von Heiko S. (heikoxxxx)


Angehängte Dateien:

Lesenswert?

Vielen Dank für eure Antworten.

Ich habe mittlerweile den ganzen Nachmittag damit verbracht alternativen 
zu DMXSerial zu suchen aber bin nicht wirklich fündig geworden. Die 
WS2812 steuere ich nun über FastLED an. Damit scheint es wohl ein wenig 
besser zu funktionieren, aber eine wirkliche Lösung ist das auch nicht.

DMX Serial arbeitet wohl definitiv über UART. Einen anderen Port kann 
ich nicht Wählen. Das MAX485 board schließe ich direkt am Arduino Nano 
am RX Pin an. Auch bzgl. Timern habe ich dort überall in den Dateien 
nichts gefunden. Mir ist nun auch zudem noch aufgefallen, dass selbst 
wenn ich die LED Stripes weg lasse der Triac hin und wieder einfach 
falsch zündet und die Lampe kurz aufflackert.

Um die Libraries umzuschreiben fehlen mir leider wirklich die Kenntnisse 
hierzu. In den Download habe ich mal mein komplettes Script gepackt.

Früher hatte ich schon mit dem Dimmer von Hoelscher Hi gearbeitet( 
http://www.hoelscher-hi.de/hendrik/light/dmxdimmer.htm )

aber dort fand ich es immer etwas Mühselig die Platinen zu ätzen und der 
Arduino bringt ja im Grunde auch alles dirket auf einem Board mit. Auch 
eine Möglichkeit die Daten direkt am OLED einzustellen und das Board für 
verschiedenen Verwendungen direkt umstellen zu können würden mir 
gefallen.

Eventuell hat ja einer eine Idee wie ich die drei Sachen (DMX Empfang / 
Steuerung der WS2812 Status LEDs / Ausgabe der DMX Werte an den Triac 
Dimmer) unter einen Hut bekomme.

von Heiko S. (heikoxxxx)



Lesenswert?

Und hier noch ein kleines Video und Bild von meinem Testaufbau.

Leider erkennt mann das flackern kaum.

https://youtu.be/9q9e4_Lo-rE

von Heiko S. (heikoxxxx)


Lesenswert?

Also es gibt ein Update. So wie ich das verstanden habe, sind die 
Timings von den WS2812 so eng, dass die Libary FastLED oder auch die 
Neopixel Libary während des schreibens alle Interrups blockiert und 
dadurch die Triacs während des LED Updates nicht mehr angesprochen 
werden.

Hierdurch ist wohl das konstante flimmern gekommen. Ich habe das jetzt 
mal auf die WS2801 Leds umgeschrieben und seither ist das konstante 
flackern weg.

Aber das Problem mit den "verschobenen" DMX Kanälen ist immernoch da.

Wenn ich z.B als Dimmerkanal den Kanal 12 definiere und diesen Kanal 12 
auf 50% und Kanal 13 mit 100% am Lichtpult setze leuchtet die Lampe 
meist mit 50% aber blitzt hin und wieder mit 100% kurz auf.

Wenn ich den Kanal 13 auf 0% setze erlischt die Lampe hin und wieder 
kurzzeitig.

Sieht wirklich so aus als ob dann statt Kanal 12 der Kanal 13 kurz 
eingelesen wird.

von Daniel W. (danielwohlmuth)


Lesenswert?

Wichtig ist wie schon erwähnt, dass die Empfangsroutine des UART nicht 
durch einen höheren Interrupt zu lang blockiert werden, dann 
verschmeisst er schon mal ein Byte.
Ich habe das mal so gelöst einen Timer IRQ aufzusetzen, der in der ISR 
über ein PWM Modul jeweils die 1 oder 0 Flanke des WS28xx ausgibt.
Müsstest halt zum Test einen Timer auswählen dessen ISR Priorität 
unterhalb der des UART liegt und dann schauen ob stattdessen jetzt die 
WS28xx flackern anstelle des DMX Empfangs. Dann bist schonmal einen 
Schritt weiter.

von Heiko S. (heikoxxxx)


Angehängte Dateien:

Lesenswert?

Hallo,

vielen Dank für eure zahlreichen Antworten.

Heute ist mein neuer APA102 Stripe gekommen. Dieser hat 4 Anschlüsse und 
soll wohl mit den engen Timings besser funktionieren.

Was mich doch etwas verwundert ist, dass laut dieser Liste:

https://courses.cs.washington.edu/courses/csep567/10wi/lectures/Lecture7.pdf

die UART Interrupts doch schon ziemlich die höchste prio haben und 
eigentlich nicht blockiert werden dürften.

Aber seis drum, der neue Stripe ist angeschlossen und funktioniert 
einwandfrei...Solange die Triacs nicht über den Timer angesprochen 
werden.

Wenn ich diese Zeile auskommentiert habe:

//Timer1.attachInterrupt(timerIsr);

funktioniert selbst Kanal 500 ohne Probleme und die entsprechende LED 
wird gedimmt und flackert nicht.

Das komplette Script habe ich in den Anhang gepackt.

Sobalt ich die ISR wieder aktiviere spielen die Kanäle verrückt und 
sowohl die Angeschlossene Halogenlampe als auch die LEDs vom APA102 
flackern.

Ebenfalls habe ich testweise den Timer 2 konfiguriert aber damit habe 
ich selbiges Problem.

Jetzt frage ich mich ob es überhaupt möglich ist mit dem Arduino Nano 
zwei solch Zeitkritische Aufgaben zu erledigen (Triac zünden / DMX 
Empfang)?

Oder ob ich lieber auf eine andere Hardware (NodeMCU - ESP8266) 
umsteigen sollte um diese beiden Aufgaben zu erledigen?

Oder meint Ihr es ist sinnvoller die Triac Zündung über einen seperaten 
Nano mittels Analog Inputs zu steuern?


LG Heiko

von Daniel W. (danielwohlmuth)


Lesenswert?

Heiko S. schrieb:
> die UART Interrupts doch schon ziemlich die höchste prio haben und
> eigentlich nicht blockiert werden dürften.

Nein, das gegenteil, die niedrigsten ISR Adressen haben die höchsten 
Prios soweit ich weiß (Ist schon ne Zeit lang her als ich die letzten 
ATmegas in der Hand hatte. Das deckt sich auch mit den Erfahrungen dass, 
sobald du die ISR vom Timer anschaltest der DMX Empfang wie wild 
flackert.

Heiko S. schrieb:
> Sobalt ich die ISR wieder aktiviere spielen die Kanäle verrückt und
> sowohl die Angeschlossene Halogenlampe als auch die LEDs vom APA102
> flackern.

Ja, da haste den Salat (->Race Condition) :) Die Interrupts sind 
normalerweise exklusiv, heißt: sobald du in einem drin bist ist der 
Controller für die anderen blind. Muss ja nicht zwingend immer der 
höchst priorisierte sein, da auch ein niedriger zuerst triggern kann, 
eine bestimmte Zeit zum ausführen braucht die ISR auch. da kann es 
passieren dass dein Timer IRQ dann nicht rechtzeitig genug triggert bei 
diesen zeitkritischen Operationen.

Man kann glaube ich auch nested IRQs aktivieren in dem man die globalen 
Interrupts in der ISR aktiviert. Wie genau weiß ich gerade nicht mehr, 
das ist zu lang her. Das Datenblatt des AtMegas ist da dein Freund. Es 
ist zwar lang zu lesen, aber dafür ist es ausführlich und es steht 
normal jede erdenkliche Möglichkeit drin.

Heiko S. schrieb:
> Jetzt frage ich mich ob es überhaupt möglich ist mit dem Arduino Nano
> zwei solch Zeitkritische Aufgaben zu erledigen (Triac zünden / DMX
> Empfang)?
>
> Oder ob ich lieber auf eine andere Hardware (NodeMCU - ESP8266)
> umsteigen sollte um diese beiden Aufgaben zu erledigen?

Ich kann dir sagen dass das Problem sich nicht ändern wird auf anderen 
MCU. Der ist durchaus schnell und genau genug dafür. Wir nutzen u.a. den 
ESP32 für kleinere Sachen und auch hier musst du für ein Pixel Stripe + 
DMX Empfang + WLAN schon durchaus sauber timen und auch auf 
unterschiedlichen Cores die Tasks packen dass er das sauber macht. Das 
Problem ist immer das Zusammenspiel verschiedener 
Funktionen/Timings/Tasks/ISRs.

-> Zurück zu deinem Problem:
Wie ich das sehe ist die Priorität deiner Tasks bzw. ISRs:
PWM für die Lampen: wichtig und dauerhaft nötig da sonst flackern
Pixel Timing: mittelwichtig und nur nötig bei Änderung
DMX Empfang: schon wichtig, aber wenn ein ganzer 512er Block mal 
verloren geht auch nicht so schlimm, kommt ja gleich der nächste

Daher würde ich hergehen und den niedrigsten Timer Vektor für deine PWM 
nutzen (siehe Datenblatt bzw. laut deinem Link der Timer2).

Beim DMX Empfang würde ich dann eine Art Semaphore, (damit nicht der 
Pixel IRQ dazwischen kommt) bauen -> hier muss man sehen, was der UART 
Treiber hier schon macht, evtl. puffert der ja schon was im Empfang. 
Nichts desto trotz braucht die ISR von DMXSerial doch bissl Zeit.
Währenddessen muss sie evtl(?) durch den Timer 2 unterbrochen werden 
dürfen, da sonst dein Triac nicht ordentlich angesteuert wird.
Hier evtl. mal die globalen IRQs in der RX ISR vom DMXSerial bei Beginn 
der ISR aktivieren.
-> Testen ob das simultan geht, wie man das genau macht und was man 
dabei beachten muss (denke mal sei(); und cli(); war das bei Atmel)
Jetzt ist es für deine Pixel nur nötig dass sie nach erfolgreichem DMX 
Empfang einmal die Werte bekommen, die brauchen die ja nicht ständig. 
Hier wieder mit dem Semaphore locken, damit jetzt nicht irgendwas 
anderes (DMX Empfang) stört (mit Ausnahme des Timer 2 für die PWM).

Das war alles ein bisschen ausführlich, ich weiß jedoch nicht wie tief 
du dich in der Materie auskennst, ob dir das ein bisschen weiterhilft.
Sicherlich allerdings muss du beide Libs DMXSerial und FastLed verstehen 
um am Ende alles unter einen Hut zu bekommen. Kann auch anders gehen, 
aber dann ist es Glück :)

Um da ein Gefühl für Timings zu bekommen ist ein Logicanalyser nicht das 
verkehrteste, dort siehst du wenn du alle Signale anlegst genau was sich 
wann beißt.

Evtl. auch den CPU Takt hochdrehen hilft, falls hier am Ende wirklich 
ein Engpass besteht, jedoch die Timings sauber aufdröseln muss trotzdem 
sein.

Ich hoffe ich konnte ein bisschen helfen..

von Falk B. (falk)


Lesenswert?

Heiko S. schrieb:
> Also es gibt ein Update. So wie ich das verstanden habe, sind die
> Timings von den WS2812 so eng, dass die Libary FastLED oder auch die
> Neopixel Libary während des schreibens alle Interrups blockiert und
> dadurch die Triacs während des LED Updates nicht mehr angesprochen
> werden.

So ist es. Die Mischung deiner Komponenten ist zeitkritisch!

DMX512 läuft mit 250 kBaud und 11 Bits/Byte. Das macht 44us/Byte. D.h. 
alle 44us kommt ein Interrupt, welche die Daten vom UART abholen muss. 
Die neueren AVRs können bis zu 3 BYtes im Extremfall puffern, also kann 
man ggf. bis zu ~120us "warten". Siehe Interrupt.

Die WS2812 werden in Software mit Bit-Banging angesteuert, dort dauert 1 
Bit 1,2us, die vollen 24 Bit/LED 28,8us. Für EINE LED sollte es reichen, 
ggf. 2. Danach braucht man eine Interruptfreigabe für den DMX-UART. Dann 
kommt jedoch das Problem, daß einige WS2812 LEDs schon nach 5 statt 50us 
die Daten übernehmen!

Beitrag "Re: Frage zu IR-Remote+LED-Strips an AVR"

"Sobald ich in mein Programm die WS2812 Pixels als Status-Leds einbinde
kommen die Kanäle von DMX-Serial nicht mehr sauber an"

Wieviele sind es denn? Wenn man die jeweils einzeln an ein IO-Pin klemmt 
ist es einfach. Denn dann kann man die einzeln ansteuern und dazwischen 
beliebig lange Pausen machen. Für eine handvoll Status-LEDs ist das OK.

Alles in allem ist die Mischung deiner Komponenten schon recht 
sportlich, wenn gleich machbar, wenn man sich WIRKLICH tief in das 
Timing reindenkt.

von Falk B. (falk)


Lesenswert?

Ein möglicher Lösungsansatz wäre eine schnelle TImer-ISR mit um die 
16kHz, Dort müssen dann drei Statemachine laufen

DMX512-Empfang (Polling!)
WS2812 Ansteuerung
Triac-Zündung

Bei 16 kHz hat man 62,5us Periodendauer, das macht bei 10ms 
Netzhalbwelle (Triac-Frequenz) ~ 160 Schritte Auflösung. Naja, geht so. 
Mit etwas Köpfchen und Trickserei kann man die Output-Compare-Funktion 
benutzen, um CPU-taktgenau den Triac zu zünden. Dann hat man mehr als 
genug Zeitauflösung.

von c-hater (Gast)


Lesenswert?

fop schrieb:

> Die Ansteuerung der WS2812
> wird bestimmt mangels spezialisierter Hardware komplett per Bitbanging
> in Software realisiert. In dieser Zeit geht nichts anderes.

Das stimmt so nicht. Man kann einiges nebenbei erledigen, sogar 
konkurrierende Interrupts sind in gewissem Umfang möglich. Allerdings: 
Man muss schon ganz genau wissen, was man tut. Eher nicht das Szenario, 
wo sich Arduino-Lib-Benutzer tummeln...

> Schlimmstenfalls musst Du die
> Routinen mehr oder weniger selbst schreiben, um den Überblick zu haben,
> wer wann zum Zug kommt. Dabei kannst Du natürlich aus den Librarys
> abkupfern.

Das ist auf Dauer der einzig zielführende Weg. Selber programmieren 
lernen.

von Heiko S. (heikoxxxx)


Angehängte Dateien:

Lesenswert?

Hallo zusammen,

sorry das ich mich erst jetzt melde, derzeit habe ich einfach viele 
Baustellen und Urlaub gehabt etc pp.
Ich habe es jetzt mittlerweile doch zum Laufen gebracht indem ich die 
ISR vom Triac nur noch alle 30µS durchlaufe. Ich gehe davon aus, das 
dies genug ist, da ich ja mit DMX sowieso nur 255 Dimmstufen habe.

10.000µS \ 30 = 333,33 Levels


Also augenscheinlich flackert da nichts mehr und die Kanäle reagieren 
immer auf den richtigen Kanal. Ein Oszi habe ich leider nicht zur Hand.
Eventuell hat ja jemand Lust das nachzubauen oder zu testen. Den Source 
Code hänge ich zudem an. So wie es jetzt ist bin ich jedenfalls 
zufrieden :-)

Der Code ist zwar nicht schön aber tut wie er soll ;-)

von Patrick L. (patrickloibl94)


Lesenswert?

Hallo Heiko!

Ein sehr sehr spannendes Projekt und zufällig bin ich gerade an einem 
fast identischen Aufbau dran. In meinem Fall ist es eine Leiste mit 4x 
Glühbirne die über das selbe KRIDA Electronics 4CH Dimmer Modul 
gesteuert werden sollen. Mein Testaufbau hat auch einen MAX485 Baustein 
zusammen mit einem Arduino Nano. Auch soll ein 0,96" OLED mit 3 Tasten 
zum Einsatz kommen. Ich wäre sehr froh wenn du mir kurz mehr zu deinem 
Projekt sagen könntest.

Wie sieht die Menüführung aus?
Was zeigen die WS2811 LEDs für einen Status an?
Zudem wär es super zu wissen um du nochmals Optimierungen am Code 
vorgenommen hast bzw. es bisher einwandfrei läuft?
Hast du eventuell einen Schaltplan zu deinem Aufbau?

VG

von Heiko S. (heikoxxxx)


Lesenswert?

Hallo Patrick,
es freut mich das dir dieses Projekt gefällt. Es freut mich, dass dir 
mein Projekt wie du mir in der Mail geschrieben hattest weitergeholfen 
hat. Am Code habe ich nichts mehr geändert.

Glaube der letzte  war demux5.ino aber ich muss auch dazu sagen, dass 
ich den nur hin und wieder als Strobe Controler für meine analogen 
Strobes verwendet habe, also keine Langzeittests etc pp. Auch die Triac 
Zündung habe ich nicht mit einem Oszi geprüft.

Die Menüführung sollte eigentlich aus dem Sourcecode ersichtlich sein. 
Oder einfach mal auf nem Steckbrett nachstecken und testen. Die WS2811 
Stripes geben nur den Status des Kanals aus, bzw ob ein DMX Signal 
anliegt.


Für Macros bzw Chaser wirst du mit meinem Code und nem Arduino Nano 
leider wenig Erfolg haben da der Sketch nahezu 100% des Speichers 
belegt. Da evtl Teile rausnehmen oder auf eine andere Hardware switchen.

Für die Steuerung von LED Stipes würde ich eher auf nen anderes Projekt 
Switchen. Da gibt es in google zahlreiche ES8266 Artnet Projekte die die 
Stripes ansteuern. https://github.com/mtongnz/ESP8266_ArtNetNode_v2


Für das Projeckt habe ich so keinen Schaltplan. Aber im Sourcecode 
solltes du eigentlich rauslesen können wie der Aufbau aussieht.


Buttons an Pin 15,17,16 gegen GND

Strobes/ Triacs oder Relais an Pin 6,9,10,5

OLED an A4 und A5

Max485 an RX Pin (Trennen wenn du den Sketch hochladen magst)

WS Stripes am Spi Ausgang


Hoffe das hilft dir weiter.

LG Heiko

von Lars P. (broku)


Lesenswert?

Hi,
ich hab ebenfalls ein Problem mit der DMXSerial lib.
Wenn ich das Besispiel Programm zum empfangen von DMX-Daten nutzen 
flakert die LED im Takt der TX LED auf dem Arduino.
(Meie Sender Behringer LC 2412 und DMXControll Nodle U1 sind known good 
genauso die DMX-Kabel)
Es ist nichts außer einem MAX 485 Board und der LED an dem Arduino 
angeschlossen.
Kann jemand helfen?

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.