Hi, ich wollte einen kleinen nützlichen Codeblock einbauen aber ich weiß nicht genau wie ich es schreibe: Wenn ich 3mal angenommen auf einen bestimmten Schalter gedrückt habe soll eine LED angehen. Habt ihr eine Idee? Gruß und Danke
Simon Name schrieb: > Habt ihr eine Idee? Kannst du bis 3 zählen? Dann bring deinem Controller bei, das auch zu tun. Und dann überlegst du dir, was er machen soll, wenn er damit fertig ist. mfg.
Natürlich kann ich bis drei zählen aber es nicht meinem Arduino bei bringen weil bei diesem Thema stehe ich auf dem Schlauch: muss ich while einsetzen oder for??? Da ich von diesen Befehlen nur die grobe Ahnung wie sie funktionieren und was sie bedeuten aber ich kann sie nicht genau anwenden. So, zufrieden?
In C vielleicht so, unter der annahme, dass ein drücken einen interrupt hervorruft:
1 | // ....
|
2 | volatile unsigned int counter = 0; |
3 | // ....
|
4 | |
5 | |
6 | ISR(PCINT0_vect) { |
7 | counter++; |
8 | if(counter==3) { |
9 | PORTB ^= (1<<PB0); //toggle PB0 |
10 | counter=0; |
11 | }
|
12 | }
|
oder kürzer:
1 | // ....
|
2 | volatile unsigned int counter = 0; |
3 | // ....
|
4 | |
5 | |
6 | ISR(PCINT0_vect) { |
7 | if(++counter==3) { |
8 | PORTB ^= (1<<PB0); //toggle PB0 |
9 | counter=0; |
10 | }
|
11 | }
|
Simon Name schrieb: > Natürlich kann ich bis drei zählen aber es nicht meinem Arduino bei > bringen weil bei diesem Thema stehe ich auf dem Schlauch: muss ich while > einsetzen oder for??? > Da ich von diesen Befehlen nur die grobe Ahnung wie sie funktionieren > und was sie bedeuten aber ich kann sie nicht genau anwenden. Ich würde einen Zähler nehmen, auf neudeutsch "counter". Gruss Harald
Simon Name schrieb: > Da ich von diesen Befehlen nur die grobe Ahnung wie sie funktionieren > und was sie bedeuten aber ich kann sie nicht genau anwenden. Dann wird es Zeit für den Klassiker (KHB wo bist du?): Kernighan & Ritchie, Programmieren in C, 2. Edition Adrian Figueroa schrieb: > volatile unsigned int counter = 0; Wenn die Variable nur im Interrupt verwendet wird ist das volatile überflüssig. Simon Name schrieb: > Was bedeutet "ISR (PCINT0_vect)"??? GCC-Syntax für Interrupts. Keine Ahnung wie das beim Arduino geht.
Simon Name schrieb: > Hi, > ich wollte einen kleinen nützlichen Codeblock einbauen aber ich weiß > nicht genau wie ich es schreibe: Du hast so ziemlich ALLES vergessen was notwendig ist: Was genau ist dein Problem? Die Programmiersprache? Erlerne Sie zunächst, bevor du konkrete Eigenaufgaben angehen willst Die Hardware? Die ist nur dir Bekannt, offensichtlich weißt du darüber aber auch nichts, geschweige denn kannst du sie ansteuern. Nimm einen Counter (74xx4059) und ein paar Und-Gatter und beschalte sie entsprechend. Da benötigt es keinen Code (denn davon hast du keine Ahnung) MFG
Mal nebenbei bemerkt, bei der Version von Adrian Figueroa fehlt jede Art von Entprellung...
Ich sollte vielleicht noch hinzufügen dass ich es mit dem Arduino vorhabe.
die "ISR" ist eine Funktion, die aufgerufen wird, wenn ein Interrupt ausgelöst wird (etwa durch die Reaktion auf die Änderung eines PINs oder von einem Timer), wobei "PCINT0_vect" für eine Zustandsänderung der zuvor als "überwacht" festgelegten PINs steht. Dabei ist PCINT0 nicht etwa ein einzelner Pin, sondern die Zusammenfassung all derer, die du vorher zum Abfragen eingeschaltet hast. Die von mir vorgegebene Funktion schaltet bei jedem Ändern des Zustandes am Eingangspin, deswegen ist sie für dich gerade nicht geeignet, sie zählt auch das loslassen des schalters mit (und ein schwingen des schalters (--> http://arduino.cc/en/Tutorial/Debounce ): Dass du mit Arduino arbeitest, hatte ich nicht gesehen, dazu gibt es was leichteres: http://arduino.cc/en/Reference/AttachInterrupt
Simon Name schrieb: > Da ich von diesen Befehlen nur die grobe Ahnung wie sie funktionieren > und was sie bedeuten aber ich kann sie nicht genau anwenden. Hmm... In diesem Falle: Wie wäre es damit, sich mit der Bedeutung dieser Befehle vertraut zu machen, sprich: Zu lernen, was diese bedeuten? Ich denke nicht, dass die Sprache C so komplex ist, dass man das nur mit Habilitation begreifen kann... Zu meiner Zeit gab es so zusammengetüddeltes Papier mit schwarzen Hieroglyphen drauf - nannte sich wohl Buch bzw. Bücher. Aber heutzutage sollte eine einfache Google-Suche reichen, um ein C-Tutorial bzw. eine -Referenz zu finden...
Simon Name schrieb: > Natürlich kann ich bis drei zählen aber es nicht meinem Arduino bei > bringen weil bei diesem Thema stehe ich auf dem Schlauch: muss ich while > einsetzen oder for??? Man nehme eine Variable, ein +1 und ein if.
void setup () { Serial.begin(9600); pinMode(2, INPUT); pinMode(13, OUTPUT); } void loop() { int Schalter; Schalter=digitalRead(2); Serial.println(Schalter, DEC); int zeahler=0; if(digitalRead(Schalter)==HIGH){ zeahler++; } if(zeahler==3){ digitalWrite(13, HIGH); delay(300); digitalWrite(13, LOW); } } Mein Code aber er funktioniert nicht.
Da fehlt die Hälfte. Wie/Wo wird loop aufgerufen? Wenn das ganze mehrfach funktionieren soll muss noch eine Schleife drum. Und wenns in einer Extrafunktion ist die ständig aufgerufen wird muss die Variable static sein...
Ich möchte nicht unhöfflich sein aber ich komme nicht ganz mit. Bitte vielleicht einbisschen genauer.
doch doch, der funktioniert, die schleife läuft aber auf deinem 16Mhz prozessor ziemlich schnell! wenn du den schalter gedrückt hälst, zählt der zähler hoch und ist nur sehr kurz bei "3". du kannst ja noch einen delay einbauen: du brauchst nicht zweimal den taster abzufragen.
1 | void setup () { |
2 | Serial.begin(9600); |
3 | pinMode(2, INPUT); |
4 | pinMode(13, OUTPUT); |
5 | |
6 | }
|
7 | |
8 | void loop() { |
9 | int Schalter=digitalRead(2); |
10 | Serial.println(Schalter, DEC); |
11 | int zeahler=0; |
12 | |
13 | if(Schalter==HIGH){ |
14 | zeahler++; |
15 | }
|
16 | if(zeahler==3){ |
17 | digitalWrite(13, HIGH); |
18 | delay(300); |
19 | digitalWrite(13, LOW); |
20 | }
|
21 | delay(200); |
22 | }
|
Lese mal das Buch Kernighan & Ritchie, Programmieren in C
@Simon: Fehlt da nicht generell etwas drumherum was zunächst setup() und dann in einer Endlosschleife loop() aufruft? Oder nimmt das der Arduino einem ab? Ich kenne mich leider nur mit echtem C aus...
Es gibt ja einmal einen Void Setup und dann einen Void Loop
Simon Name schrieb: > So, zufrieden? Nein. Wie willst du programmieren, wenn du nicht einmal weisst, wie man eine Variable hochzählt und dass Ergebnis abfragt? Deshalb hörst du erstmal auf deinen Lehrer: while(!Ahnung) { dein Lehrer schrieb: > Lese mal das Buch } mfg.
Ja was while ist weiß ich schon aber sorry wenn ich es doch nicht so genau anwenden kann
entschuldige, ich habe einen fehler übersehen. du setzt in dem code bei jedem durchlauf den counter auf 0. setz die initialisierung nach setup.
1 | int zeahler=0; |
2 | |
3 | void setup () { |
4 | Serial.begin(9600); |
5 | pinMode(2, INPUT); |
6 | pinMode(13, OUTPUT); |
7 | }
|
8 | |
9 | void loop() { |
10 | int Schalter=digitalRead(2); |
11 | |
12 | if(Schalter==1){ |
13 | zeahler++; |
14 | delay(200); |
15 | }
|
16 | if(zeahler==3){ |
17 | digitalWrite(13, HIGH); |
18 | delay(300); |
19 | digitalWrite(13, LOW); |
20 | }
|
21 | }
|
Simon Name schrieb: > Ja was while ist weiß ich schon aber sorry wenn ich es doch nicht so > genau anwenden kann Wenn du in ein paar Jahren mal den Führerschein machen willst, wirst du doch auch nicht in der ersten Minute losfahren dürfen, weil du schon weißt, wie man die Hupe betätigt. Du mußt vorher lernen, wozu das Lenkrad und die drei Pedale gut sind.
Hör mal vielleicht habe ich in Arduinosprache bzw. C noch nciht so eine Große Ahnung aber in anderen vielleicht schon und wenn ich mal nicht weiter weiß darf ich doch in einem Forum fragen und nicht gleich runtergeputzt werden
> unter der annahme, dass ein drücken einen interrupt hervorruft:
Bitte liebe Kinder macht das nicht, denn Taster prellen und ein uC macht
daraufhin dutzende von Interrupts. Man erfasst Tster NIEMALS mit
Interrupts.
Ausserdem: Wie lange dürfen denn die 3 Tastendrücke auseinanderliegen ?
Jeden Tag einer ? Nicht vielleicht in 10 Sekunden alle 3 ?
1 | #define TASTER 2
|
2 | main() |
3 | {
|
4 | char taster; |
5 | int dauer; |
6 | char letzter=digitalRead(TASTER); |
7 | while(1) |
8 | {
|
9 | char dieser=digitalRead(TASTER); |
10 | if(dieser&&!letzter) |
11 | {
|
12 | taster++; |
13 | if(taster==3) |
14 | {
|
15 | // mach das was du bei 3 Tastendrücken willst
|
16 | taster=0; |
17 | dauer=0; |
18 | }
|
19 | }
|
20 | letzter=dieser; |
21 | delay(10); // länger als die Prellzeit |
22 | if(taster>0) |
23 | {
|
24 | dauer++; |
25 | if(dauer>1000) /7 1000 x 10msec = 10 sec |
26 | {
|
27 | taster=0; |
28 | dauer=0; |
29 | }
|
30 | }
|
31 | }
|
32 | }
|
Wieso? was ist daran so schlimm? Geht da mein Computer bzw. Arduino kaputt 0_o :)
> Man erfasst Tster NIEMALS mit Interrupts.
ich kann doch nicht die ganze zeit meine taster abfragen, während etwas
anderes gemacht wird, der taster aber trotzdem eine funktion haben
soll...
Adrian Figueroa schrieb: > ich kann doch nicht die ganze zeit meine taster abfragen, während etwas > anderes gemacht wird, der taster aber trotzdem eine funktion haben > soll... Deswegen macht man das nebenbei in einem Timer Interrupt. Interrupts und Taster sind idr. nur sinnvoll um einen Controller aufzuwecken.
> Deswegen macht man das nebenbei in einem Timer Interrupt.
Der Timer interrupt ist ja sehr kurz, dann muss ich ja so kleine
abtastabstände nehmen, dass die "drückzeit" des schalters höher ist
(100ms vielleicht).. da kommt ja auch eine menge zusammen
Adrian Figueroa schrieb: > Der Timer interrupt ist ja sehr kurz, dann muss ich ja so kleine > abtastabstände nehmen, dass die "drückzeit" des schalters höher ist > (100ms vielleicht).. da kommt ja auch eine menge zusammen Nein, da kommt keine Menge zusammen. Man nimmt z.b. einen Timer interrupt alle 50 ms, wenn der Taster in diesem Interrupt 3 mal hintereinander gedrückt ist kann man davon ausgehen, dass er auch wirklich gedrückt ist und nicht prellt. Dann setzt du ein Flag das du dann in deinem Hauptprogramm auswertest. Das alles frisst vielleicht 0.5% der Rechenzeit deines Controllers. Wohl eher noch weniger. Das tolle daran ist auch, dass man (fast) beliebig viele Taster verwenden kann.
> ich kann doch nicht die ganze zeit meine taster abfragen Du vielleicht nicht, gute Programmierer aber schon. Timer ist zwar eine Methode aber nicht die einzige. > dann muss ich ja so kleine abtastabstände nehmen, > dass die "drückzeit" des schalters höher ist Natürlich. Für einen uC ein Klacks. Lernt programmieren.
Es gibt hier C-Tutorials über Entprellung, das ist ganu das was Du brauchst. Mit den Arduino-Bibliotheken kenne ich mich nicht aus, aber die "loop" dürfte der Endlosschleife im main entsprechen. http://www.mikrocontroller.net/articles/Entprellung#Warteschleifen-Verfahren Das Prinzip ist einfach, der Timer läuft vor sich hin und wenn eine Taste länger als eine vorgegebene Zeit High-Wert hat wird sie in einer volatilen globalen Variable gespeichert. In Deiner loop() wertest Du un diese globale Variable aus und zählst eine lokale variable hoch und prüfst ob sie dreimal, viernal usw. erhöht wurde.
Adrian Figueroa schrieb: > Der Timer interrupt ist ja sehr kurz, dann muss ich ja so kleine > abtastabstände nehmen, dass die "drückzeit" des schalters höher ist > (100ms vielleicht).. da kommt ja auch eine menge zusammen Taster werden 1000 Mal pro Sekunde abgefragt. Wenn sich ein Tastzustand geändert hat, lässt man ihn für ein paar Millisekunden in Ruhe. Das nennt man Entprellen. Und der arme µC macht das klaglos mit. Im Gegenteil. Der freut sich sogar. Sonst würden ihm nämlich irgendwann vor lauter Langeweile die Pins abfaulen. Und nur dadurch bekommt er wirklich jeden Tastendruck mit. Denn die reine Abfrage eines Tasters dauert nur einen Prozessortakt. Egal wie oft oder selten man das macht. Mit Delays und Interrupts schafft man sich erst richtige Probleme. Der einzige Einsatzzweck eines Tasters mit Interrupt ist das Aufwecken aus dem Sleepmode. Aber auch nur dafür. Der erste Befehl nach dem Sleep lautet dann PCICR = 0. Und dann geht es mit der ganz normalen Entprellung weiter. mfg.
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.