einmalige loop zum Start

Hallo!

ich würde gerne einen ATMEGA8535 mit einem längeren Sketch programmieren.

Unter anderm würde ich gerne eine Hochfahrfrequenz simulieren, die nur einmal durchlaufen soll.
Bei Tests war ich auch erfolgreich gewesen. (Zumindest habe ich das sehr stark in Erinnerung)

Jetzt wollte ich den Sketch zusammen nehmen, hab ihn auf den Microcontroller geladen und es will nicht mehr so, wie ich es will:

Der Plan war einen Lautsprecher und LEDs anzusprechen, 5 Sekunden nachdem das Board mit der Spannungsquelle versorgt wurden und ein einmaliges durchlaufen dieser.
Gedacht war es folgendermaßen:

...
void loop()
{

 if(millis() == 360); //nach 5 Sekunden (beim ATMEGA8535 entsprechen 360ms 5s)
    {
      digitalWrite(LEDs, HIGH)
etc.
}

Der Controller wird mit Strom versorgt, beginnt millis() zu zählen und nach der angegeben Zeit setzt die Schleife ein.
Da der millis() Wert nicht mehr erreicht werden kann, wird auch diese Schleife nicht mehr durchlaufen.

Allerdings läuft diese Schleife bei mir ständig von Beginn der Stromzufuhr an durch.
Gerade nochmal an einem ATTINY13 probiert, hier klappt auch nichts ...

Ich hoffe ihr habt meine Idee verstanden und könnt mir helfen :slight_smile:

Ein einmaliger loop() heißt setup()

Wenn der Sketch nichts anderes machen muß:

setup()
 {
 delay(5000);
 andere Kode;
 }
loop(){}

Bedenke aber auch, daß der Bootloader einige Zeit braucht, bis der Sketch aufgerufen wird.

Grüße Uwe

Wenn du nicht den Weg über Setup und delay gehen willst, dann mußt du dir eine Variable setzen, die dir den erstmaligen Aufruf anzeigt:

void loop()
{
.....
  static boolean init = true;
  if(millis() == 360 && init); //nach 5 Sekunden (beim ATMEGA8535 entsprechen 360ms 5s)
    {
      init = false;
      digitalWrite(LEDs, HIGH)
etc.
}

erklär mir mal bitte warum 360ms 5 s sein sollen.
Das verstehe ich nicht.
1000ms sind eine Sekunde und das ist wohl immer so.
gruß

das ist wohl immer so

Nur wenn man's richtig macht :wink:

Wenn das übliche
#define F_CPU 16000000UL
nicht zur verwendeten Hardware passt, kann man das natürlich auch durch einen Kommentar "ausgleichen".
Wobei die 360 schon seltsam ist (bei echten 1 MHz (statt angenommener 16MHz) wäre es eher 312 für 5 Sekunden).

Die empfohlene Anpassung ist natürlich ein passender Eintrag in boards.txt :wink:

lassen wir mal bitte die Zeit in Sekunden außen vor, ok?

Rein zum Verständnis:
Warum reicht ein

if(millis() == time

nicht aus?

Die Spannungsquelle wird angeschlossen, der Controller beginnt zu zählen und wenn die Zeit seit Start (millis()) abgelaufen ist, dann wird die Schleife ausgeführt. Danach wird sie nicht mehr ausgeführt, weil millis() == time schon verstrichen ist. Dennoch läuft die Schleife wieder und wieder.
Kann mir das bitte jemand näherbringen?

Es könnte ausreichen, wenn du sicherstellst, dass die loop() schnell genug durchlaufen wird.

Beim Arduino, bei dem millis() echte millisekunden ausspuckt heißt das: kürzer als 1ms.
Sonst kann es passieren, das bei einem Durchlauf millis() 359 bringt, beim nächsten schon 361. Und schon hast du deine Bedingung if millis() == 360 verpasst.

Hallo,
Deine "if-Schleife" läuft Dir durch. If 5000 dann

ist 4998
if 5000 dann
ist 4999

Sketch

ist 5001
if 5000 dann
bumm!

Startmillis = millis()
Ich würde mir die Startmillis merken, dann 5000 dazuzählen
dann
if millis() >= Startmillis plus 5000 dann

so ähnlich sollte das laufen. Aber das Forum ist voll von milliZählerei
Gruß und Spaß
Andreas

Ich werfe mal noch eine Lösung in den Ring. Viele Wege führen ja bekanntlich nach Rom.

   while(millis() <= 5000){ // oder 360 oder was auch immer
    // ---- hier deine Startsequnez
  }

  while(1){
 
    // Hier der Rest
    
  }

So hätte ich das Problem gelöst.
Zur Not die Millisekunden noch so versorgen, dass die Arduino Startzeit für Bootloader und Co berücksichtigt wird
Grüße,

Sven

Und so würde ich es mir vorstellen, wenn man die Startzeit noch mit ein bezieht.

void setup() {

}

void loop()
{
 unigned long StartTime = millis() + 5000; // oder 360 oder was auch immer
   while(millis() <= StartTime){ 
    // ---- hier deine Startsequnez
  }

  while(1){
 
    // Hier der Rest
    
  }
}