- 12V Akku mit 280 Ah bauen         
Ergebnis 1 bis 10 von 25

Thema: YACCBOA - YetAnotherCameraControlerBasedOnArduino

Hybrid-Darstellung

Vorheriger Beitrag Vorheriger Beitrag   Nächster Beitrag Nächster Beitrag
  1. #1
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    12.04.2008
    Alter
    40
    Beiträge
    557
    Tja......

    Ich sitze hier grade vor meinem Aufbau und bin ziemlich ernüchtert. Es tun sich immer neue Baustellen auf....


    Die Hardware funktioniert im Prinzip. Die Ventile öffnen, die Blitze blitzen und die Kamera nimmt Bilder auf. ABER! Aber..... aber -_-

    Zwei Blitze unterschiedlicher Hersteller haben unterschiedliche Verzögerungen. Daher habe ich zur Zeit noch Doppelbelichtungen. Dies würde sich recht einfach beheben lassen, wenn nicht das zweite, gravierendere Problem wäre.

    Die Bibliotheken, die ich für das Menü, LCD oder mein eigener Code haben die blöde Eigenschaft, die Vorgänge nicht im Millisekundenbereich aufeinander abzustimmen. Ich habe den Tropfen immer ein paar Millimeter über der Wasseroberfläche, gar nicht im Bild oder schon die letzten Kräusel auf der Oberfläche. Aber ich schaffe es nicht, das Bild zwischen diesen Momenten zu schießen. Ich vermute, dass irgend ein Teil des Codes die Abläufe so verzögert, dass ich z.B. nur in 10ms-Sekunden springen kann.

    Ich vermute, dass es an meinem eigenen Code liegt, da in den Funktionen für den Ablauf (Kamera, Tropfen, Blitz) weder das LCD noch das Menü arbeitet. Ich zähle die Millisekunden per
    Code:
    millis_aktuell = millis() - millis_start;
    und lasse die entsprechenden Aktionen ausführen wenn eine if-Abfrage erkennt, dass genug ms vergangen sind.

    Verwendet wird ein Arduino Pro Mini 16MHz.

    Kann mir jemand nen Tipp geben, wie ich Vorgänge auf die Millisekunde genau timen kann?
    Alles ist möglich. Unmögliches dauert nur etwas länger!

  2. #2
    Erfahrener Benutzer Fleißiges Mitglied
    Registriert seit
    07.04.2010
    Ort
    Im Städtedreieck Köln-Bonn-Aachen
    Alter
    37
    Beiträge
    106
    Das Arduino Pro Mini hat den ATmega328 als µC verbaut. Dieser hat 3 Timerbausteine (2x 8Bit und 1x 16Bit).
    Ich würde es damit versuchen.

    Entweder du liest das/die Register TCNTx per Hand aus, oder du stellst einen Timer so ein, dass er alle 1ms einen Überlauf hat und einen Interrupt auslöst.

  3. #3
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    12.04.2008
    Alter
    40
    Beiträge
    557
    Ich bin mir nicht sicher wo das Problem liegt. Ich habe heute Vormittag den Durchlauf der Funktion mal per
    Code:
    micros_durchlauf_start = micros();
    .....
    jede menge Code
    .....
    micros_durchlauf = micros() - micros_durchlauf_start;
    Serial.println(micros_durchlauf);
    gemessen. Dabei werden mir pro Durchlauf 20-28 Microsekunden ausgegeben. Was mich aber stutzig macht ist ein Wert nach ca. 100 Durchläufen aus der Reihe schlägt und mit rund -15500µs angegeben wird. Es ist bei jeden Aufruf der Funktion nur ein einzelner Wert nach ca 100 Durchläufen.


    Ich bin mir nicht sicher, ob ein Timer-Interrupt mein Problem lösen wird. Die Funktion scheint ja (meistens) schnell genug zu sein, um sogar mehrmals pro Millisekunde auf ein evtl. auszuführendes Event zu überprüfen. Die ISR müsste ja ähnlich aussehen wie meine bisher verwendete (nachfolgende) Funktion.
    Code:
    void ausloesen(void)
    {
      int millis_start = millis();
      int millis_aktuell = millis();
      int status_ventil_open[3] = {0,0,0};
      int status_ventil_closed[3] = {0,0,0};
      int status_blitz = 0;
      int status_sva = 0;
      int status_trigger = 0;
      int timer_blitz = 500;
      int kamera_delay = 82;
      int micros_durchlauf = 0;
      int micros_durchlauf_start = 0;
      
    
    
      
      lcd.clear();
      lcd.home();
      lcd.print(valve_delay[1]);
      sva();
      
      
      while(tmp == 0)
      {
        millis_aktuell = millis() - millis_start;
        micros_durchlauf_start = micros();
        
         
    //    lcd.setCursor(0,2);
    //    lcd.print(millis_aktuell);
        
        // Ventile öffnen
        for(int i = 0; i<valve_amount;i++)
        {    
          if((millis_aktuell > valve_delay[i]) && (status_ventil_open[i] == 0) && (valve_active[i] == 1))
          {
            digitalWrite(+i,HIGH);
            status_ventil_open[i] = 1;
          }
        }
        
        // Ventile schließen
        for(int i=0;i<valve_amount;i++)
        {
          if((millis_aktuell > (valve_delay[i]+valve_size[i])) && status_ventil_closed[i] == 0)
          {
            digitalWrite(+i,LOW);
            status_ventil_closed[i] = 1;
          }
        }
        
        // Kamera auslösen
        if((millis_aktuell > (timer_blitz - kamera_delay) && (status_trigger == 0)))
        {
          digitalWrite(13,HIGH);
          status_trigger = 1;
        }
        
        // Blitze auslösen
        if((millis_aktuell > timer_blitz) && (status_blitz == 0))
        {
          trigger_blitze();
          status_blitz = 1;
        }
        
        micros_durchlauf = micros() - micros_durchlauf_start;
        Serial.println(micros_durchlauf);
        if(millis_aktuell > 2000)
        {
          tmp=1;
          digitalWrite(13,LOW);
          display_setup_valve_delay();
        }
      }
    }
    Alles ist möglich. Unmögliches dauert nur etwas länger!

  4. #4
    Erfahrener Benutzer Fleißiges Mitglied
    Registriert seit
    07.04.2010
    Ort
    Im Städtedreieck Köln-Bonn-Aachen
    Alter
    37
    Beiträge
    106
    Okay... ich habe min. 10 mal die Antwort hier verworfen.

    Was mich stört, ist das eine menge Lib. aufgerufen werden, die für mich scheinbar der Plattform Arduino als Entwicklungsumgebung abhängig sind.
    Korregiere mich, wenn das nicht stimmt.

    Ich würde immer noch einfach den 16Bit Timer im Hintergrund mitlaufen lassen und ihn als Zeitgeber nehmen.
    Aber ich weiß jetzt nicht, ob Arduino einen so tief in die Hardware des µC rein läst. Sprich ob du einfach das CS11-Bit im TCCR1B Register auf High setzten kannst und das TCNT1 Register einfach auslesen kann, ohne eine aufwendige Funktion zu benutzen.

    Sprich so:
    Code:
    unsigned int auslesen;
    TCCR1B|=(1<<CS11);
    auslesen=TCNT1;
    Die Anweisungen dauern jeweils meine ich max. 4 Takte.

    Daher meine Grundlegende Frage: Kannst du direkt, ohne irgendwelche Funktionen, auf die Register zugreifen?

  5. #5
    Erfahrener Benutzer Roboter Genie Avatar von m.a.r.v.i.n
    Registriert seit
    24.07.2005
    Ort
    Berlin
    Beiträge
    1.247
    Hallo,

    schickes Gerät, gefällt mir sehr gut. Wollte auf deine PM antworten, aber dein Postfach ist voll.

    @Jimmybot Beim Arduino läuft bereits der Timer im Hintergrund im Interrupt als Zeitgeber. Da würde ich nicht dran herum schrauben.

    Das Problem liegt vermutlich eher an den Variablen Typen. Millis() und micros() geben 'unsigned long' zurück, du verwendest 'int' (das sind beim Arduino 16Bit Werte). Das kann zu Überläufen und ungeahnten Problemen führen.

    Bei meinen Tests habe ich nur schnöde delay() Aufrufe verwendet, will aber auch später millis() verwenden. Brauche ich aber erst wenn ich mehrere Ventile verwende.
    Kann meinen Code aber gerne hier posten, falls gewünscht.

    LG Peter

  6. #6
    Erfahrener Benutzer Fleißiges Mitglied
    Registriert seit
    07.04.2010
    Ort
    Im Städtedreieck Köln-Bonn-Aachen
    Alter
    37
    Beiträge
    106
    Zitat Zitat von m.a.r.v.i.n Beitrag anzeigen

    @Jimmybot Beim Arduino läuft bereits der Timer im Hintergrund im Interrupt als Zeitgeber. Da würde ich nicht dran herum schrauben.
    Wieder was dazu gelernt. Danke für den Hinweis.

  7. #7
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    12.04.2008
    Alter
    40
    Beiträge
    557
    Danke für die Antwort. Timer sind, wie schon erwähnt, durch die Arduino IDE zum Teil belegt. Gibt Wege diese freizulegen und zu nutzen. Aber da bin ich noch nicht fit genug für.

    Der Hinweis mit den Datentypen ist berechtigt. Hab ich ganz vergessen. Werde ich mir morgen mal Gedanken drüber machen.

    PS: Postfach ist wieder frei
    Alles ist möglich. Unmögliches dauert nur etwas länger!

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

12V Akku bauen