Hallo Leute, ich bin gerade dabei, mir ein Programm für einen Zähler zu schreiben. Mit Hilfe eines Drehimpulsgebers sollen 3 7.Segmentanzeigen hoch/runtergezählt werden. Soweit so gut - bis hier hin funktioniert auch alles wunderbar. Die Zahlen lassen sich in 1'er Schritten hochzählen. Der Drehgeber wird über einen Timer ausgelesen, wie hier in der Codesammlung schon geschildert wurde. Nun möchte ich mein Programm aber so ändern, dass sich der Erhöhungsschritt in Abhängigkeit der Drehgeschwindigkeit ändert. Bsp.: langsames Drehen ermöglicht Feineinstellung im 1'er-Schritttakt; je schneller man nun am Drehimpulsgeber dreht, desto größer sind die Schritte. Also, langsam drehen = feineinstellung, schnell drehen = Grobeinstellung. Bis jetzt feht mir zur Umsetzung aber die Idee, wie man an so eine Sache heran geht. Hat evtl. jemand eine Idee oder Vorschlag bzw. hat sowas schon einmal programmiert?
>Bsp.: langsames Drehen ermöglicht Feineinstellung im 1'er-Schritttakt; >je schneller man nun am Drehimpulsgeber dreht, desto größer sind die >Schritte. Also, langsam drehen = feineinstellung, schnell drehen = >Grobeinstellung. Du müsstest mit einem zweiten Zähler prüfen, wie viele Impulse inerhalb einer gewissen Zeitspanne reingekommen sind und daraus ableiten, ob schnell oder langsam gedreht wurde.
@ Thomas (Gast) >Nun möchte ich mein Programm aber so ändern, dass sich der >Erhöhungsschritt in Abhängigkeit der Drehgeschwindigkeit ändert. Das ist aber nicht das Gleiche wie dein Betreff ! >Bsp.: langsames Drehen ermöglicht Feineinstellung im 1'er-Schritttakt; >je schneller man nun am Drehimpulsgeber dreht, desto größer sind die >Schritte. Also, langsam drehen = feineinstellung, schnell drehen = >Grobeinstellung. Sowas wird auch in Mausbeschleunigern benutzt. >Bis jetzt feht mir zur Umsetzung aber die Idee, wie man an so eine Sache >heran geht. Hat evtl. jemand eine Idee oder Vorschlag Du musst messen/speichern, wann die letzte Änderung des Drehgebers stattgefunden hat. Das ist einfach, das machst du direkt nach der Auswertung im Timerinterrupt. Wenn dieser Wert mehrfach eine bestimmte Schwelle unterschreitet (schnell drehen) wird dein Positionszähler dann ebem um beispielsweise 5 und nicht nur 1 erhöht. MFG Falk
Du mißt die Zeit zwischen zwei Flanken Deines Drehgebers. Ist die Zeit < 0,5s addierst/subtrahierst Du 10, ist die Zeit >= 0,5s addierst/subtrahierst Du 1. Die Zeitwerte sind hier frei gewählt, solltest Du dann ausprobieren. Viel Spaß und Erfolg
kann man den Drehgeber auch drücken? Ich habe das für einen Timer so gelöst das gedrückt halten + drehen die Minuten einstellt, einfaches drehen die Sekunden.
>kann man den Drehgeber auch drücken? Ich habe das für einen Timer so >gelöst das gedrückt halten + drehen die Minuten einstellt, einfaches >drehen die Sekunden. Pass aber auf, dass du dir dabei nicht die Finger brichst! Die Verrenkungen will ich gar nicht sehen.
@ sechshochdrei (Gast) >Pass aber auf, dass du dir dabei nicht die Finger brichst! Die >Verrenkungen will ich gar nicht sehen. Statt Drücken + Drehen kann man auch Umschalten. Kurz Drücken schaltet zwischen verschiedenen Geschwindigkeiten/Parametern um. Gedreht wird dann ohne drücken. MfG Falk
@Falk:
>Statt Drücken + Drehen kann man auch Umschalten.
Ja, hast schon Recht. Der Beitragschreiber wollte aber so einen
"Mausbeschleuniger" haben (welcher meiner Meinung nach unter Win2k
irgendwie umgänglicher ist als bei WinXP)
Der Drehgeber hat auch eine Tastfunktion, die jedoch schon für etwas Anderes reserviert ist. Aber sonnst keine schlechte Idee. Die Frage ist aber, wie misst man am Besten die Zeit zwischen 2 Flanken des Drehgebers? Ich möchte dazu keinen weiteren Timer ver(sch)wenden. @Falk Brunner: Ich glaube auch schon zu wissen, wie ich deinen Vorschlag unsetzen könnte. Muss ich heut Nachmittag mal ausprobieren, ob das so funktioniert, wie ich es mir denke. Ich programmiere das Ganze übrigens in C.
Das Ganze soll einfach zum Voreinstellen einer bestimmten Zeit sein, die über 3 7 Seg. Anzeigen ausgegeben wird. Es wäre ja unsinnig, wenn man z.B. x-mal am Drehgeber drehen müsste, um z.B. 5 Minuten auf der Anzeige einstellen zu können.
>Pass aber auf, dass du dir dabei nicht die Finger brichst! Die >Verrenkungen will ich gar nicht sehen. das klappt sehr gut sogar, kommt sicher auch auf den Drehknopf an. Ich nutze das für einen Belichtungstimer und komme da mit dem einen Drehknopf aus: Drücken < 0,5s : gespeicherte Zeit laden Drücken 0,5..3s : Timer Starten oder Stoppen wenn er läuft Drücken > 3s : eingestellte Zeit speichern Aber da gibt es viele Möglichkeiten, sollte ja auch nur eine Anregung sein.
JojoS (Gast) schrieb: >Drücken < 0,5s : gespeicherte Zeit laden >Drücken 0,5..3s : Timer Starten oder Stoppen wenn er läuft >Drücken > 3s : eingestellte Zeit speichern und JojoS (Gast) schrieb: >kann man den Drehgeber auch drücken? Ich habe das für einen Timer so >gelöst das gedrückt halten + drehen die Minuten einstellt, einfaches >drehen die Sekunden. Sind aber zwei Paar Schuhe!
es ist ein Drehgeber, es ging ja darum : >Der Drehgeber hat auch eine Tastfunktion, die jedoch schon für etwas >Anderes reserviert ist. das es eben trotzdem möglich ist mehrere Tast-Funktionen zu haben und auch Drücken+Drehen geht. Die Funktionen werden erst ausgelöst wenn der Drehgebertaster losgelassen wird.
@ Thomas (Gast) >Die Frage ist aber, wie misst man am Besten die Zeit zwischen 2 Flanken >des Drehgebers? Ich möchte dazu keinen weiteren Timer ver(sch)wenden. Hab ich doch schon geschrieben. "Du musst messen/speichern, wann die letzte Änderung des Drehgebers stattgefunden hat. Das ist einfach, das machst du direkt nach der Auswertung im Timerinterrupt." >Ich programmiere das Ganze übrigens in C. Kein Problem. MfG Falk
Ja, schon, aber mir fehlt trotzdem noch ein gewisser Leitfaden. Leider hab ich den Quelltext gerade nicht zur Verfügung, aber im Prinzip ist das mit der Tasterabfrage und der darauf zu erfolgenden Reaktion folgendermaßen: _uint8 d; //Variable zum Erhöhen/verringern des 7-Seg Zählers void TimerISR { If(TasterDrehRehts) { d++; ### } If(TasterDrehLinks) { d--; ### } } So, nun sagst du, dass an der Stelle, wo sich das ### befindet, gemessen und gespeichert werden soll. Aber irgendwie muss ich ja auch zählen, wie viel Zeit seit dem letzten Impuls vergangen ist. Und wie mach ich das, ohne noch einen weiteren Timer zu nutzen?
@ Thomas (Gast) >So, nun sagst du, dass an der Stelle, wo sich das ### befindet, gemessen >und gespeichert werden soll. Aber irgendwie muss ich ja auch zählen, wie >viel Zeit seit dem letzten Impuls vergangen ist. Und wie mach ich das, >ohne noch einen weiteren Timer zu nutzen? Mit einer Variable? Dein Timer wird beispielsweise alle 5ms aufgerufen (200Hz).
1 | uint8 d; //Variable zum Erhöhen/verringern des 7-Seg Zählers |
2 | |
3 | void TimerISR |
4 | {
|
5 | static uint8 cnt_aktion; // Zählerstand seit letzter Links/Rechts Aktion |
6 | |
7 | if (cnt_aktion!=255) cnt_aktion++; // Erhöhen ohne Overflow |
8 | |
9 | If(TasterDrehRehts) |
10 | {
|
11 | if (cnt_aktion>100) |
12 | d++; |
13 | else
|
14 | d+=5; |
15 | cnt_aktion=0; |
16 | }
|
17 | If(TasterDrehLinks) |
18 | {
|
19 | if (cnt_aktion>100) |
20 | d--; |
21 | else
|
22 | d-=5; |
23 | cnt_aktion=0; |
24 | }
|
25 | }
|
Wenn mans noch etwas schöner/intuitiver mache will nimmt man einen weiteren Zähler, welcher X mal erfasst, ob die Drehabstände eine kritische Schwelle unterschritten haben und dieser steuert dann d++ bzw d+=5; So kann man beispielsweise dreimal relativ schnell in Einerschritten drehen und erst dan wird der Turbo eingeschaltet.
1 | uint8 d; //Variable zum Erhöhen/verringern des 7-Seg Zählers |
2 | |
3 | void TimerISR |
4 | {
|
5 | static uint8 cnt_aktion; // Zählerstand seit letzter Links/Rechts Aktion |
6 | static uint8 cnt_turbo; // Anzahl schneller Drehpulse |
7 | |
8 | if (cnt_aktion!=255) cnt_aktion++; // Erhöhen ohne Overflow |
9 | |
10 | If(TasterDrehRehts || TasterDrehLinks) { |
11 | if (cnt_aktion<100) |
12 | if (cnt_turbo!=255) cnt_turbo++; |
13 | else
|
14 | cnt_turbo=0; |
15 | cnt_aktion=0; |
16 | }
|
17 | |
18 | If(TasterDrehRehts) |
19 | {
|
20 | if (cnt_turbo>3) |
21 | d+=5; // schnell drehen |
22 | else
|
23 | d++; // langsam drehen |
24 | }
|
25 | |
26 | If(TasterDrehLinks) |
27 | {
|
28 | if (cnt_turbo>3) |
29 | d-=5; // schnell drehen |
30 | else
|
31 | d--; // langsam drehen |
32 | }
|
33 | }
|
MFG Falk
Uups, noch ein kleiner Fehler drin.
1 | uint8 d; //Variable zum Erhöhen/verringern des 7-Seg Zählers |
2 | |
3 | void TimerISR |
4 | {
|
5 | static uint8 cnt_aktion; // Zählerstand seit letzter Links/Rechts Aktion |
6 | static uint8 cnt_turbo; // Anzahl schneller Drehpulse |
7 | |
8 | if (cnt_aktion!=255) cnt_aktion++; // Erhöhen ohne Overflow |
9 | |
10 | if(TasterDrehRehts || TasterDrehLinks) { |
11 | if (cnt_aktion<100) { |
12 | if (cnt_turbo!=255) cnt_turbo++; |
13 | }
|
14 | else
|
15 | cnt_turbo=0; |
16 | cnt_aktion=0; |
17 | }
|
18 | |
19 | if(TasterDrehRehts) |
20 | {
|
21 | if (cnt_turbo>3) |
22 | d+=5; // schnell drehen |
23 | else
|
24 | d++; // langsam drehen |
25 | }
|
26 | |
27 | if(TasterDrehLinks) |
28 | {
|
29 | if (cnt_turbo>3) |
30 | d-=5; // schnell drehen |
31 | else
|
32 | d--; // langsam drehen |
33 | }
|
34 | }
|
MFG Falk
Wirklich sehr clever. Vielen Dank für die Codezeilen, die mich echt weiter bringen. Grüße Thomas!
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.