Peter Dannegers Tastenenptrellung - Modifikation Problem

Gast #1644975
Lesenswert?
• ▲
▼
Moin zusammen,

ich beschäftige mich momentan wieder mit dem leidigen Thema der 
Tastenentprellung und benutze als Grundlage Peter Dannegers Code, doch 
muss ich diesen modifizieren, um ihn für meine Anwendung nutzbar zu 
machen.

Hintergrund der Modifikation ist, dass ich nicht einen Timer Overflow 
benutze, sondern einen Capture, da ich einen Atmega169 im 
Energiesparmodus betreibe. Hier ist nur noch Timer2 verfügbar (wird 
separat über den TOSC Pin getaktet). Der Overflow wird bereits durch 
eine RTC benutzt.

Soweit so gut.
Peter Dannegers Code läuft soweit ohne Probleme mit dem Capture, doch 
wird hier dauerhaft alle 10ms der Port-Eingang abegefragt.
Dies muss ich aufgrund meiner Stromsparoption ändern:

Da die 2 Taster einen PinChange auslösen, aktiviere ich im PCINT das 
Capture Interrupt - das läuft ohne Probleme. Doch muss dieses dann auch 
wieder abgeschaltet werden. Hierzu fügte ich eine zweite Variable ein, 
die einfach zählt wie oft das Capture Interrupt ausgelöst wurde. Wenn 
diese eine gewisse Zahl erreicht, so wird das Capture-Interrupt 
abgeschaltet. Das geht auch ohne Probs. :)

Doch hat einer meiner Taster (S1) eine Repeat-Funktion, sprich wenn 
diese Taste 5Sekunden lang gedrückt wird, so wird die FLAG S1_LONG 
gesetzt.

Wenn ich Taste2 (hier geht nur einfaches Drücken) betätige, so läuft die 
Modifikation, sprich das Capture-Interrupt wird gleich abgeschaltet.

Wenn ich jedoch Taste1 kurz drücke, so bleibt der Capture-Interrupt ca. 
7Sekunden an?! - Wo ist mein Fehler?
Danke im Vorraus

Hier mein Code:

> ISR(TIMER2_COMP_vect )
> {
> static uint8_t ct0, ct1,rpt, counter;
> uint8_t i;
>
> OCR2A = TCNT2 + 5; //20ms
> i = key_state ^ ( (~PINE) & FLAG_CODE_TASTER);    // key changed ?
> ct0 = ~( ct0 & i );      // reset or count ct0
> ct1 = ct0 ^ (ct1 & i);    // reset or count ct1
> i &= ct0 & ct1;      // count until roll over ?
> key_state ^= i;      // then toggle debounced state
> FLAG1_LOC |= key_state & i;    // 0->1: key press detect
>
> if( (key_state & (1<<FLAG_S1_PRESSED) ) == 0 )  // check repeat function
> {
>   rpt = 40;    // start delay
> }
>
>
> if(++counter == 5) //Interrupt wurde 5mal aufgerufen
> {
>   if( (PINE & (1<<FLAG_S1_PRESSED) ) ) //Ist Taster1 nicht gedrückt
>   {
>     TIMSK2 &= ~(1<<OCIE2A); //Stoppe Capture-Interrupt
>     counter = 0;
>   }
>
>   else //Taster1 ist gedrückt
>   {
>     OCR2A = TCNT2 + 51; //200ms - Erst wieder in 200ms abfragen, da ja
>                                   5Sekunden gedrückt sein könnte
>   }
> }
> if( --rpt == 0 )
> {
>   //rpt = REPEAT_NEXT;      // repeat delay
>   FLAG1_LOC |= (1<<FLAG_S1_LONG); //Setze Flag Taste lange gedrückt
>   TIMSK2 &= ~(1<<OCIE2A); //Stoppe Capture-Interrupt
> }
>}

Antwort schreiben

Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt. Bitte hier nur auf die ursprüngliche Frage antworten, für neue Fragen einen neuen Beitrag erstellen.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.