Hallo Zusammen, ich habe ein Programm geschrieben, welches eine Stoppuhr in Verbindung mit dem WTV020 Sound Modul umsetzten soll. (zum Teil aus dem Internet zusammenkopiert und angepasst) Durch drücken des Start Tasters soll auf dem WTV020 eine Sounddatei abgespielt werden. Nach einer bestimmten Zeit (wenn in der Sounddatei der Startbefehl ertönt) soll die Stoppuhr wieder auf 0 gesetzt werden, da erst ab dem Zeitpunkt gezählt werden soll. Durch einen Stopptaster soll die Zeitnahme gestoppt werden. Die Zeit wird ständig über multiplexen auf einer 4x7 Segment Anzeige dargestellt. Mein Problem ist, dass die Zeitnahme, sowie das zurücksetzten nach der Zeit x und auch die Anzeige nicht immer funktionieren. Manchmal funktioniert alles. Manchmal kommt es aber auch vor, dass die angezeigte Zeit hin und her springt oder manchmal nur noch ein Ziffer auf den 4 Anzeigen zu sehen ist. Außerdem startet der Timer manchmal, ohne dass ich auf einen Taster gedrückt habe oder der Stopptaster reagiert nicht, obwohl ich vorher auf Start gedrückt habe und den Stopptaster auch lange genug gedrückt habe. Mein Programm habe ich in den Anhang gepackt. Ich hoffe mir kann irgendwer weiter helfen, da ich hier aktuell sehr am verzweifeln bin.
:
Verschoben durch User
Hallo Philipp. Das ist spannend. Du hast nur 5 Anforderungen und doch 9 beschriebene Fehler. Wo soll man da anfangen... Na vielleicht mit einem Code Review. >1) Durch drücken des Start Tasters soll Sounddatei abgespielt werden. >4) Durch einen Stoptaster soll die Zeitnahme gestoppt werden. Bei beiden Taster-Drücken (start und stop) entprellst du den Taster nicht. zeile 122: if(!(PINB & (1<<PINB2)) && lauf == 0) //Start zeile 144: if(!(PINB & (1<<PINB1)) && lauf == 1) // Stopp Das ergibt beispielhaft dieses Problem: "Außerdem (...), ohne dass ich auf einen Taster gedrückt habe." > 2) Nach einer bestimmten Zeit (wenn in der Sounddatei der Startbefehl ertönt) > soll die Stoppuhr wieder auf 0 gesetzt werden, Warum läuft die Stoppuhr überhaupt? Sie sollte bis hierher noch gar nicht gestartet sein. Sprich: Warum startest du das zählen der Stoppuhr nicht erst hier indem du den Timer2 erst hier einschaltest und wenn stopp gedrückt wurde wieder Timer2 abschaltest? Die Antwort findet sich wohl in der bestimmten Zeit; Du möchtest zwei mal zählen. (Das erste Mal bis 18800.) Später stoppst du dann den Timer2 doch. Wie wäre es zwecks Lesbarkeit zwei Funktionen zur Timer2 Stoppuhr einzuführen? Wie wäre es mit: - Timer2_Stopuhr_Start() und - Timer2_Stopuhr_Stop() Und dann noch Timer2_Stopuhr_Init() weils so schön ist. Und gleich sinnvoller Klingt als interrupt_init(). > 3) da erst ab dem Zeitpunkt gezählt werden soll. In der Timer2 ISR hast du eine korrekte Zählerlogik gebaut. (Wenn auch du zaehler[0] nicht verwendet hast.) Später rechnest du dann aber von zaehler[] auf zeiger[] für die Anzeige um, indem du die ganzen Werte einfach umkopierst. (zeiger[1]=zaehler[1]; usw.) Hier wäre es aber angebracht zwischen der Abstraktion der Darstellung für die Anzeige (zeiger[]) und der Darstellung des eigentlichen Zählens [zaehler[]) zu unterscheiden. Dann muss man auch nicht so umständlich die Zeit des startbefehls (18800) abfragen, wie du es machst: zeile 8: if(zaehler[5] >= 1 && zaehler[4] >= 8 && zaehler[3] >= 8 && sound == 1){ So sähe das doch gleich viel einfacher aus: if (zaehler >=18800) Dafür müsstest du dann zaehler passend für die Anzeige (zeiger[]) umrechnen. Kleine Hilfe: zeiger[5] = zaehler / 10000; usw. >5) Die Zeit wird ständig über multiplexen auf einer 4x7 Segment Anzeige dargestellt. Das Multiplexing sieht sauber aus. Außer: sei(), cli() mitten im Program-Lauf (start taster). Das unterbricht dein Multiplexing für eine ganze Weile, weil du dazwischen mal eben _delay_ms() aufrufst. int Nummer; Dann noch "Nummer". Diese Variable veränderst du in einer ISR. Sollte also auch volatile sein. Genau genommen benötigst du die Variable nur in der ISR. Dann kann sie auch direkt da rein. (static int Nummer = 5; Damit sie nur einmal initialisiert wird.) int adresse[6]; adresse[] wird garnicht verwendet. Hinfort damit. Sieht gleich viel aufgeräumter aus. Die editierte main.c ist im Anhang. (ungetestet) Nächste Schritte für dich: Funktion sendCommand() aufräumen, systematisch die nächsten Probleme angehen und nicht verzweifeln. ;-)
Vielen Dank für deine schnelle Antwort, ich habe deine Anpassungen mal getestet. Leider treten die Probleme immer noch auf. Ich habe mir jetzt aber mal die Hardware angeschaut. Es scheint so als ob der Quarz nicht richtig funktioniert hat. Nachdem ich den ausgetauscht habe hat alles funktioniert.
Philipp schrieb: > Vielen Dank für deine schnelle Antwort, Gerne. Nach deiner Problembeschreibung hätte ich nicht einen Fehler des Quarzes vermutet. Aber wenn es jetzt geht ist doch toll.
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.