hab es unüberlegter weise in ein bereits erledigtes thema gepostet, hier , wohin es eigentlich hingehört, noch einmal zusammengefasst...
----------------------------------------------------------------------------------------------------------------------------------------------------------------

Zitat von
Rabenauge
Ich mach alles in Zeitscheiben: es läuft ein simpler Timer (nach dem Beispielprogramm BlinkWithoutDelay), der mir, beispielsweise, jede Sekunde einen Tick gibt. Diese Ticks werden gezählt, so lange, wie ich halt Aufgaben zu vergeben habe, und bei jeder Tick-Zahl wird eine Aufgabe erledigt.
Danach wird der Tick-Zähler zurückgesetzt, und der ganze Zyklus geht von vorne los.
Auf diese Weise schafft so ein kleiner Arduino erstaunlich viel.....es ist z.B. vollkommen unnötig, den Akku alle paar Millisekunden abzufragen, im XPlorer mache ich das nur alle 20 Sekunden, das genügt völlig, und ich hab 19 Sekunden, auf die ich andere Aufgaben verteilen kann.
Diesen Timer kann man beliebig langsam (oder schnell, der könnte auch Zehntelsekunden oder hundertstel) ticken lassen, so kann man z.B. auch sicherstellen, dass US-Sensoren sich nie gegenseitig in die Quere kommen (Echos abklingen lassen) usw.
Unglaublich einfach und unglaublich flexibel.
Da steht natürlich in Wirklichkeit noch bisschen Kleinkram drin (man sollte sicherstellen, dass der Arduino beim "Lies Akkustand-Tick" nicht 152x den Akku ausliest, usw. aber das Prinzip ist ganz einfach.
Hi Sly,
ich lerne neue sachen (auch simple timer
) gerne aus der kombination von beschreibung und beispiel und der "blink without delay" code ist nun ein zu simples beispiel. Würde Dir das was ausmachen hier Deinen code öffentlich zu machen? Eine PM geht natürlich auch, aber vielleicht gibt's noch andere die lernen wollen? 
wäre super, dann könnte ich endlich meine loop für den outdoor fertigschreiben ohne ständig verzweifeln zu müssen...
antwort zusammengebastelt:
-----------------------------------------
Aber gern doch.
Hier mal ein paar Auszüge aus dem Code des XPlorer1, da wird das auch so gehandhabt.
Zuerst bauen wir und nen Timner zusammen, der anhand von den millis() bei Bedarf "Ticks" erzeugt:
Code:
void timer() //***************** mehrere Sekundenticks erzeugen **********************************
{
unsigned long aktuelleMillis = millis();
if (aktuelleMillis - vergangeneMillis >= interval) // Sekunde um
{
vergangeneMillis = aktuelleMillis;
halbeTick ++; // 500ms sind um
if(halbeTick>2) // hier ist eine volle Sekunde vorbei
{
halbeTick=1; // wechselt alle halbe Sekunde
sekundenTick++; // wechselt jede volle Sekunde
gemachtFlag=0; // Aufgabe-erledigt-Flag zurücksetzen
}
if(sekundenTick==5) // mehr brauchen wir nicht
{
sekundenTick=0;
}
}
}
Der hier erzeugt jede halbe Sekunde nen Tick, und zusätzlich zählt er die Sekunden jedesmal bis fünf hoch.
Im Grunde ein umgeschriebenes "blink_without_delay"...
Im Hauptprogramm muss dieser Timer natürlich auch "hin und wieder" aufgerufen werden (immer, wenn Zeit ist), das Stück Code ist tatsächlich das _komplette_ Hauptprogramm:
Code:
void loop()
{
timer();
manageLichter();
sekundenAufgaben(); // je nachdem, was der Timer grade hat...
delay(2); // Zeit lassen für Anfragen vom NodeMCU
}
Im Unterprogramm "sekundenAufgaben" wird nun aufgedröselt, je nachdem, welchen Wert der Timer gerade hat:
Code:
void sekundenAufgaben()
{
if((sekundenTick==0)&&(gemachtFlag==0)) //wenns nicht schon erledigt wurde...
{
messeAkku();
}
if((sekundenTick==1)&&(gemachtFlag==0))
{
berechneLichtstaerke();
gemachtFlag=1;
}
}
Die gewünschten Intervalle (in denen der Timer halt "tickt") stellt man dann einfach mit passenden Konstanten ein:
Code:
unsigned long vergangeneMillis = 0; // hier der letzte Tick
const long interval = 500; // Intervall, 500 Millisekunden
Die Variable "gemachtFlag" verhindert, dass die jeweilige Aufgabe innerhalb des einen Intervalls ...zigmal erledigt wird- nur wenn die auch 0 ist, wird die Aufgabe abgearbeitet, und nachdem sie erledigt wurde, wird das Flag auf 1 gesetzt.
Im Code zum XP2 hab ich inzwischen fünf oder sechs solche Flags-der hat einiges mehr zu tun, hehe.
Der zählt aber auch die Sekunden bis 20 hoch....das Beispiel ist in alle möglichen Richtungen anpassbar, man kann den Timer schneller oder langsamer ticken lassen, man kann ihn weiter oder weniger weit hochzählen lassen, ganz wie man es gerade braucht.
Das ist natürlich keine Atomuhr- da der nur abgefragt wird, wenn keine anderen Aufgaben zu erledigen sind (hier z.B. kommt noch das manageLichter() dazwischen), geht er nicht supergenau, aber wen jucken Abweichungen von nen paar Millisekunden denn- meistens ist das Wurst.
Falls du noch Fragen dazu hast- frag einfach.
---------------------------------------------------------------------
mache ich, muss es mir erstmal genauer anschauen....
gleich die erste frage:
und das ist jetzt wirklich so, dass die in der loop aufgerufenen task's laufen, unabhängig davon, wie lange sie dauern, während die loop weiter abgearbeitet wird?
Lesezeichen