Hey Leute ich sollte ein Prog schreiben das man auf einen Tastendruck
wartet und dann (jenachdem) welche Taste gedrückt wurde ein bestimmtes
Muster an den Led's ausgibt.. nun habe ich folgendes Problem habe
zuhause nur AVRstudio und den Simulator und es läuft einfach nicht
richtig das Programm..... ich zerbrech mir schon Tagelang den Kopf hoffe
Ihr könnt mir helfen .....
#define F_CPU 1000000
#include <avr/io.h>
#include <util/delay.h>
#define MAX_PATLEN 10
void delay_ms(unsigned int ms);
struct Pattern
{
char PatArray[MAX_PATLEN];
unsigned char patlen;
};
void putPattern(const struct Pattern* pPat, double delay);
void putSelPattern(unsigned char num);
unsigned char waitforKey();
unsigned char getKeyNum (unsigned char sw);
void initport();
int main()
{
initport();
putSelPattern(getKeyNum (waitforKey()));
while(1);
return 0;
}
void initport(void)
{
DDRD = 0x00; // PORT A als EINGANG
PORTD = 0xff; // Pull-up wird gesetzt
DDRB=0xff; // Port B auf Ausgang
PORTB=0x00; // Alle Ausg�nge auf 0
}
void putPattern(const struct Pattern* pPat, double delay)
{
int i;
for(i=0;i<pPat->patlen;i++) //Ausgabe der Bytes
{
PORTB=pPat->PatArray[i];
_delay_ms(100); //Wartezeit
}
}
void putSelPattern(unsigned char num)
{
const struct Pattern
P0={{0x00,0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80},9};
const struct Pattern P1={{0x18,0x24,0x42,0x81},4};
const struct Pattern
P2={{0xff,0x00,0xff,0x00,0xff,0x00,0xff,0x00,0xff,0x00},10};
const struct Pattern P3={{0xff,0x00,0xff},3};
const struct Pattern P4={{0xc0},1};
const struct Pattern P5={{0x03},1};
const struct Pattern P6={{0xff,0x00},2};
switch(num)
{
case 0:
putPattern(&P0,250);
break;
case 1:
putPattern (&P1,250);
break;
case 2:
putPattern (&P2,250);
break;
case 3:
putPattern (&P3,125);
break;
case 4:
putPattern (&P4,1000);
break;
case 5:
putPattern (&P5,1000);
break;
case 6:
putPattern (&P6,1000);
break;
default:
PORTB = 0xAA;
}
}
unsigned char waitforKey()
{
uint8_t Key;
Key = 0;
while(Key == 0)
{
while(PIND==0xff); // wartet bis irgendeine der 8 Tasten gedrueckt
ist
_delay_ms(100); // Prellzeit der Taste abwarten: 100ms warten
while(PIND!=0xff)
{
Key = ~PIND; // wartet bis alle Tasten wieder losgelassen sind
_delay_ms(100); // Prellzeit der Taste abwarten: 100ms warten
}
}
return Key;
}
unsigned char getKeyNum(unsigned char sw)
{
if (sw==0x01)
return 0;
else if(sw==0x02)
return 1;
else if(sw==0x04)
return 2;
else if(sw==0x08)
return 3;
else if(sw==0x10)
return 4;
else if(sw==0x20)
return 5;
else if(sw==0x40)
return 6;
else if(sw==0x80)
return 7;
else
return 255;
}
Gast
#1484181
Wichtige Regeln - erst lesen, dann posten!
* Groß- und Kleinschreibung verwenden
* Längeren Sourcecode nicht im Text einfügen, sondern als
Dateianhang
Gast
#1484184
Was funktioniert nicht? Warum nimmst du Teile deines Progamms nicht einzeln in Betrieb? z.B. Taster einlesen, Muster an LEDs ausgeben.
also das programm läuft einfach nicht rund..... zuhause hier in dem
Simulator ist es eine absolute katastrophe da er bei
"putSelPattern(getKeyNum (waitforKey()));" dieser funktion hängen
bleibt, da ich ja eine taste drücken muss was ich jedoch am simulator
nicht so hinkriege. in der fh war es so das wenn ich eine Taste gedrückt
hatte das ein muster kam jedoch hat es sich danach aufgehängt .
der prof meinte ich sollte mir das nochmal angucken
void putPattern(const struct Pattern* pPat, double delay)
{
int i;
for(i=0;i<pPat->patlen;i++) //Ausgabe der Bytes
{
PORTB=pPat->PatArray[i];
_delay_ms(100); //Wartezeit
}
}
Denis G. schrieb: > in der fh war es so das wenn ich eine Taste gedrückt > hatte das ein muster kam jedoch hat es sich danach aufgehängt . Es hat sich nicht aufgehängt, sondern es ist so geschrieben: Nach einem Tastendruck bleibt das Programm in while(1) hängen. Es tut also nur, was ihm gesagt wurde.
du solltest über deine main nochmal nachdenken... zur zeit tut das prg nicht viel... und der simulator kann auch tasten simulieren, du kannst einfach die passenden kästchen anklicken...
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
Was macht Dein Programm da? 1. Ports initialisieren 2. Auf Tastendruck warten, in Tastennummer umrechnen, Pattern ausgeben. 3. Endlosschleife <=== !!! > in der fh war es so das wenn ich eine Taste gedrückt > hatte das ein muster kam jedoch hat es sich danach aufgehängt . Also passiert genau das, was Du hier beschreibst.
ja aber bevor das prog in die whil schleife läuft muss es ja durch diese funktion putSelPattern(getKeyNum (waitforKey())); das heisst er holt sich den tastendruck , dann guckt er was zu dem tastendruck zugewiessen wurde und führt dann das muster aus UND DANN ERST GEHTS IN DIE WHILE schleife oder???? also so wars gedacht nur er kommt nicht mal zu der funktion nich mal wenn ich an der funktion ein breakpoint setzte
ich kann keine pins anklicken im simulator selbst wenn ich das Value änder passiert nix habs auch schon mit dem prog Hapsim versucht aber nix
Nach ein Punkt, der auffällt:
1 | |
2 | |
3 | |
4 | |
5 | |
Hier nimmst Du an, dass sich PIND nicht ändern kann zwischen while-Bedingung und Key-Zuweisung. Das muss nicht der Fall sein. Du kannst so durchaus ab und zu Key auf 0xff zurückbekommen (auch wenn es nicht sehr wahrscheinlich ist). Allgemein zum Programmierstil: Sauberes Einrücken ist nicht für Weicheier, sondern drückt aus, dass Du Dein Programm sauber durchdacht und strukturiert hast. Das hast Du aber doch, oder? Warum zeigt Dein Programm dann das nicht, sondern sieht aus wie Kraut und Rüben?
tja das sagt mir jeder prof nur leider hab ich es mir schon fast angewohnt so "unsauber " zu proggen vielleicht kommt hinzu das man unter zeitdruck steht .... muss es mir abgewöhnen
Denis G. schrieb: > ja aber bevor das prog in die whil schleife läuft muss es ja durch diese > funktion putSelPattern(getKeyNum (waitforKey())); > das heisst er holt sich den tastendruck , dann guckt er was zu dem > tastendruck zugewiessen wurde und führt dann das muster aus UND DANN > ERST GEHTS IN DIE WHILE schleife oder???? > also so wars gedacht nur er kommt nicht mal zu der funktion nich mal > wenn ich an der funktion ein breakpoint setzte Welche der hier beteiligten Funktionen? Das sind mehrere. Eventuell mal in getrennte Zeilen aufteilen. Einfach mal drei LEDs anschließen und diese als AUS vorbelegen. Dann in jeder der betroffenen Funktione eine der LEDs einschalten. Somit kannst Du auch ohne Debugger sehen, welche Funktion noch ausgeführt wird.
Hazeh Zimmerer schrieb: > Nach ein Punkt, der auffällt: >
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
> > Hier nimmst Du an, dass sich PIND nicht ändern kann zwischen > while-Bedingung und Key-Zuweisung. Das muss nicht der Fall sein. Du > kannst so durchaus ab und zu Key auf 0xff zurückbekommen (auch wenn es > nicht sehr wahrscheinlich ist). > > Gut aber das kann ja nicht der hauptgrund sein?!
Gast
#1484238
> ... vielleicht kommt hinzu das man unter zeitdruck steht
Die Zeit, die du da sparst, verschleuderst du später vielfach bei der
Fehlersuche.
> > Welche der hier beteiligten Funktionen? Das sind mehrere. > Eventuell mal in getrennte Zeilen aufteilen. > > Einfach mal drei LEDs anschließen und diese als AUS vorbelegen. > Dann in jeder der betroffenen Funktione eine der LEDs einschalten. > Somit kannst Du auch ohne Debugger sehen, welche Funktion noch > ausgeführt wird. also wenn ich mein debugger starte geht er in die funktion initport(); anschliessend nix mehr ..... einfach erklärt
MeinerEiner schrieb: >> ... vielleicht kommt hinzu das man unter zeitdruck steht > > Die Zeit, die du da sparst, verschleuderst du später vielfach bei der > Fehlersuche. da hast du wohl recht
> Gut aber das kann ja nicht der hauptgrund sein?!
Nein. Der Hauptgrund ist, was ich und viele andere schon schrieben:
Dein Programm ist so aufgebaut, dass es nach einem Tastendruck in eine
ewige Schleife geht. Das Verhalten, das Du als Fehler beschreibst, ist
nichts als das, was das Programm vorschreibt.
Denis G. schrieb: > tja das sagt mir jeder prof nur leider hab ich es mir schon fast > angewohnt so "unsauber " zu proggen vielleicht kommt hinzu das man unter > zeitdruck steht .... muss es mir abgewöhnen Dann solltest Du dir dringend einen anderen Programmierstil zulegen. Mit dieser Einstellung wirst Du nie ein längeres Projekt bestehen können. Was passiert wohl, wenn Du wärend eines größeren Projektes mal eine Woche Urlaub hast. Danach musst Du Dein Programm nochmal neu verstehen lernen oder nochmal komplett neu schreiben, da das einfach schneller geht. Auch solltest Du dir dringend eine ordentliche Kommentierung angewöhnen. > for(i=0;i<pPat->patlen;i++) //Ausgabe der Bytes Aha, was wird da ausgegeben? > _delay_ms(100); //Wartezeit Ach neee, hätte nicht gedacht, dass das Programm hier wartet. Du solltest nicht schreiben was passiert, sondern warum Du es gerade so gemacht hast.
so habe nun mal das probiert : putSelPattern(getKeyNum (3));//waitforKey())); da müsste er mir ja mein 3.Muster ausgeben.?!? kommt aber dann mein default muster raus also tut sich wenigstens etwas
Denis G. schrieb: > also wenn ich mein debugger starte geht er in die funktion initport(); > anschliessend nix mehr ..... einfach erklärt Aha, dann zeige uns mal die Endlosschleife in initport(). Ich würde mich als Prozessor jedenfalls nicht lange darin aufhalten.
Christian H. schrieb: > > Dann solltest Du dir dringend einen anderen Programmierstil zulegen. Mit > dieser Einstellung wirst Du nie ein längeres Projekt bestehen können. > Was passiert wohl, wenn Du wärend eines größeren Projektes mal eine > Woche Urlaub hast. Danach musst Du Dein Programm nochmal neu verstehen > lernen oder nochmal komplett neu schreiben, da das einfach schneller > geht. > > Auch solltest Du dir dringend eine ordentliche Kommentierung angewöhnen. > >> for(i=0;i<pPat->patlen;i++) //Ausgabe der Bytes > > Aha, was wird da ausgegeben? > >> _delay_ms(100); //Wartezeit > > Ach neee, hätte nicht gedacht, dass das Programm hier wartet. > > Du solltest nicht schreiben was passiert, sondern warum Du es gerade > so gemacht hast. also vielleicht nochmal zu meinen Hintergründen sollte keine entschuldigung sein hole mir gerne tipps von programieren aber ich studier energie.-elektronik.- und Umwelttechnik habe nur die Grundlagen . auch wenn mich proggen nicht wirklich überzeugt gehört es nunmal zu meinem studium dazu jedoch entschuldigt das vielleicht mein Stil !
Denis G. schrieb: > so habe nun mal das probiert : > > putSelPattern(getKeyNum (3));//waitforKey())); > > da müsste er mir ja mein 3.Muster ausgeben.?!? Nein, denn 3 wird in Deinem getKeyNum() immer mit 255 beantwortet. Das 3. Muster wäre getKeyNum(4).
>> putSelPattern(getKeyNum (4));//waitforKey())); >> Reaktion = Keine
Christian H. schrieb: > Denis G. schrieb: >> also wenn ich mein debugger starte geht er in die funktion initport(); >> anschliessend nix mehr ..... einfach erklärt > > Aha, dann zeige uns mal die Endlosschleife in initport(). > Ich würde mich als Prozessor jedenfalls nicht lange darin aufhalten. im initport() habe ich keine while schleife
putSelPattern(getKeyNum (0x20));//waitforKey())); Reaktion== LED 1 und LED 0 werden eingeschaltet das funktioniert schonmal
Gast
#1484280
>void delay_ms(unsigned int ms);
Wo findet man diese Funktion ?
_delay_ms(100); //Wartezeit
Läuft wahrscheinlich zu schnell, so dass Du die ersten Pattern nicht
siehst, sondern nur das letzte in Deiner Kette. Beim 3. Muster also
0x00.
Stimmt das mit der eingesetzten Taktfrequenz überein?
> #define F_CPU 1000000
Christian H. schrieb: > _delay_ms(100); //Wartezeit > > Läuft wahrscheinlich zu schnell, so dass Du die ersten Pattern nicht > siehst, sondern nur das letzte in Deiner Kette. Beim 3. Muster also > 0x00. > > Stimmt das mit der eingesetzten Taktfrequenz überein? >> #define F_CPU 1000000 da kannst du recht haben denn ich hab eben mal probiert LED 1 und LED 0 einmal ein und wieder aus zu schalten und siehe da ich sehe nix nur das sie aus sind wie kann ich die taktfrequenz heraus finden? in der fh haben wir diese genommen
Gast
#1484295
1 | |
2 | |
3 | |
4 | |
5 | |
Überleg mal genau, was worst-case aus diesem Stückchen rauskommen könnte Vor allem in Verbindung mit der (tschuldigung) Schrott-Fkt "getKeyNum" (Hast du mal was von "shiften" gehört ?
Gast
#1484302
Schreib das Programm komplett neu. Es ist 5 Mal länger als es sein müßte. Und versuch erstmal die Warnings (die da bestimmt auftreten) zu eliminieren. Dann erst debuggen.
krishna schrieb:
>1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
> > Überleg mal genau, was worst-case aus diesem Stückchen rauskommen könnte > Vor allem in Verbindung mit der (tschuldigung) Schrott-Fkt "getKeyNum" > (Hast du mal was von "shiften" gehört ? ja wenn die taste losgelassen ist wird der inhalt invertierend zurückgegeben das an der gedrückten taste eine 1 ist. um tastenprellen zu verhindern dann das delay sorry sollten die Fkt so machen war aufgabenstellung .
krishna schrieb: > Schreib das Programm komplett neu. > Es ist 5 Mal länger als es sein müßte. > > Und versuch erstmal die Warnings (die da bestimmt auftreten) zu > eliminieren. > > Dann erst debuggen. 0 errorrs 0 warnings
o errors 0 warnings
Gast
#1484313
was ist wenn sich zwischen > while(PIND!=0xff) und > Key = ~PIND; der Wert von PIND ändert ? Z.b. von 2 auf 255 ? Was steht dann in Key ? :-) Schreibs komplett neu. Da sind noch mehr Fehler drin, das mach keinen Spaß.
krishna schrieb: > was ist wenn sich zwischen > >> while(PIND!=0xff) > > und > >> Key = ~PIND; > > der Wert von PIND ändert ? Z.b. von 2 auf 255 ? > > Was steht dann in Key ? > > Schreibs komplett neu. Da sind noch mehr Fehler drin, das mach keinen > Spaß. wieso sollte er sich ändern
also es is absolut scheisse von dir .... ich sitzt seit 1 woche an dem prog und der prof sagt es kann nur noch ein kleiner fehler sein .... und du sagst machs neu? ich hab gedacht das is ein forum wo geholfen werden kann ?!
nochmal ne frage dazu
const struct Pattern
P0={{0x00,0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80},9};
const struct Pattern P1={{0x18,0x24,0x42,0x81},4};
const struct Pattern
P2={{0xff,0x00,0xff,0x00,0xff,0x00,0xff,0x00,0xff,0x00},10};
const struct Pattern P3={{0xff,0x00},2};
const struct Pattern P4={{0xc0,0x00},2};
const struct Pattern P5={{0x03,0x00},2};
const struct Pattern P6={{0xff,0x00},2};
0. lauflicht recht ->links
1. lauflicht von mitte nach aussen
2. alle 5mal ein und aus
3. alle einmal ein und aus
4. LED 7 und 6 einmal ein und aus
5. led 1 und 0 einmal ein und aus
6. alle ein und aus
Gast
#1484328
>wieso sollte er sich ändern Wann ändert sich der Wert von PIND denn ? :-) Du hast auch immer noch nicht verraten, wo man >void delay_ms(unsigned int ms); findet. Ok, es wird zwar nicht benutzt, aber...
krishna schrieb: >>wieso sollte er sich ändern > > Wann ändert sich der Wert von PIND denn ? :-) > > Du hast auch immer noch nicht verraten, wo man >>void delay_ms(unsigned int ms); > > findet. Ok, es wird zwar nicht benutzt, aber... er ändert sich wenn ich es drücke bzw loslasse.... mit dem delay hatte ich vorher versucht ..... bis ich bemerkt habe das ich es eigentlich nicht brauche .... guck mal bitte über meine putPattern funktion ob ich die richtig gemacht habe !?
Also dann mal reale Hilfe: - die bisherigen Tipps zumindest mal ins Auge fassen - lesbaren, vernünftig kommentierten und formatierten Quelltext präsentieren - Tipps zum Programmieren nicht einfach wegwischen mit der Begründung "mein Stil ist halt schlecht" Ein lesbarer Quelltext ist zum einen für dich eine Hilfe; aber auch wenn du darauf verzichten magst, mutest du dennoch den Leuten, die dir helfen sollen, denselben Quelltext zu. Den Quelltext ordentlich zu formatieren und (wie beim Schreiben jedes Posts hier im Forum wenige Zentimeter drüber verlangt) als C-Quelltext zu markieren, sollte man noch schaffen. Wie gesagt zumindest aus Höflichkeit den Helfern gegenüber.
also immoment ist es so das wenn ich es im code änder putSelPattern(getKeyNum (0x08));//waitforKey())); das es funktioniert . wenn ich nun aber putSelPattern(getKeyNum (waitforKey())); mache macht er nix , logisch da er auf ein Key wartet nun will ich im simulator ein bit setzen , macht er aber nicht ....
Klaus Wachtler schrieb: > Also dann mal reale Hilfe: > - die bisherigen Tipps zumindest mal ins Auge fassen > - lesbaren, vernünftig kommentierten und formatierten > Quelltext präsentieren > - Tipps zum Programmieren nicht einfach wegwischen mit der > Begründung "mein Stil ist halt schlecht" > Natürlich gebe ich dir recht . ich wisch es nicht einfach so weg ich habe gesagt ich nehme jede hilfe von programieren dankend an und versuch sie halt umzusetzen bin auch jedem dankbar der seine Zeit opfert und hilft ...
Gast
#1484346
Und drüber nachdenken, warum du diese Schleife
> while(Key == 0) {..}
gemacht hast, und ob sie überhaupt notwenig ist.
Mach zumindest die Tastenabfrage komplett neu.
Es sind vermutlich noch mehr Fehler drin, aber ich verliere grade die
Lust :-)
Btw.: In deinem Screenshot deiner Entwicklungsumgebung wird links die Geschwindigkeit 4MHz genannt. In Deinem Code aber 1MHz.
krishna schrieb: > Und drüber nachdenken, warum du diese Schleife > >> while(Key == 0) {..} > > gemacht hast, und ob sie überhaupt notwenig ist. > > Mach zumindest die Tastenabfrage komplett neu. > > Es sind vermutlich noch mehr Fehler drin, aber ich verliere grade die > Lust :-) ja kann ich mir vorstellen =) und versetzt dich mal in meine lage ich probier und probier und hab die lust schon fast am programiieren verloren obwohl ich erst damit angefangen habe =) wenn ich es neu schreiben würde , würde ich es so machen denn DAS ist meine überlegung dafür . ich initialiser mein key mit 0 und warte bis die taste gedrückt ist und invertiere den PIND damit ich eine 1 habe und wird im KEY gespeichert und zurückgegeben
also ich bin jetzt soweit das ich mir auf jedenfall denke das es am waitforKey liegt denn wenn ich es im code änder werden die muster alle ausgeführt...... wie kann ich mein wait for key am besten ändern
Gast
#1484377
> Btw.: In deinem Screenshot deiner Entwicklungsumgebung wird links die > Geschwindigkeit 4MHz genannt. In Deinem Code aber 1MHz. Ist ne Standard-"Krankheit" vom AVR-Studio. Das nimmt zu Beginn eines Debug-Ablaufes immer die 4MHz, unabhängig von dem, was man verwendet.
Rate mal, was passiert, wenn Du die Taste wärend des ersten Delay wieder loslässt? Genau, die zweite Schleife wird nicht ausgeführt, da PIND = 0xff. darauf folgt: Key = 0 => getKeyNum(0) = 255 => Defaultpattern
Gast
#1484379
1. Da Dein Programm in Main nach einmaliger Ausgabe sowieso in eine endlosschleife geht, brauchst du nichts entprellen. 2. Da du nicht entprellen musst, warte einfach nur darauf, daß eine Taste Gedrück wird... ist erstmal einfacher für dich.
MeinerEiner schrieb: >> Btw.: In deinem Screenshot deiner Entwicklungsumgebung wird links die >> Geschwindigkeit 4MHz genannt. In Deinem Code aber 1MHz. > > Ist ne Standard-"Krankheit" vom AVR-Studio. > Das nimmt zu Beginn eines Debug-Ablaufes immer die 4MHz, unabhängig von > dem, was man verwendet. ja ok macht aber immoment nix da ich hapsim benutzt und da meine muster an den leds sehe und in der uni selbst benutzten wir eclipse
Christian H. schrieb: > Rate mal, was passiert, wenn Du die Taste wärend des ersten Delay wieder > loslässt? > > Genau, die zweite Schleife wird nicht ausgeführt, da PIND = 0xff. > > darauf folgt: > Key = 0 => getKeyNum(0) = 255 => Defaultpattern ja gut aber wer kann denn innerhalb von 100ms die taste loslassen?!
Christian H. schrieb: > Rate mal, was passiert, wenn Du die Taste wärend des ersten Delay wieder > loslässt? > > Genau, die zweite Schleife wird nicht ausgeführt, da PIND = 0xff. > > darauf folgt: Sorry, hatte die äußere While-Schleife übersehen. Key = 0 => genau diese Schleife wird nicht beendet.
Denis G. schrieb:
> ja gut aber wer kann denn innerhalb von 100ms die taste loslassen?!
Das ist 1/10 Sekunde, also eine Ewigkeit.
Christian H. schrieb: > Denis G. schrieb: >> ja gut aber wer kann denn innerhalb von 100ms die taste loslassen?! > > Das ist 1/10 Sekunde, also eine Ewigkeit. das heisst?! delay kürzer machen oder weg?!
Gast
#1484397
Nochmal, du Du wartest nur auf einen einzigen Tastendruck, da brauchst du nicht zu entprellen. Danach ist das Programm (nach einigem anderem Kram) sowieso zuende.
Gast
#1484398
> ja gut aber wer kann denn innerhalb von 100ms die taste loslassen?!
Der Taster selbst... Stichwort Prellen.
Der erste Puls wird niemals 100ms erreichen.
unsigned char waitforKey() Wartet auf eine Eingabe vom Benutzer über die an PortA angeschlossenen Tasten. Dabei soll es egal sein, welche Taste bzw. ob mehr als eine Taste gedrückt wird. Gibt den invertierten Inhalt zurück, den das PIND-Register bei Tastendruck hat, so dass der Rückgabewert an der Position einer gedrückten Taste eine 1 enthält. Hinweise: Beachten Sie, dass PIND den Inhalt 0xff hat, wenn keine Taste gedrückt ist. Der Tastendruck ist erst abgeschlossen, wenn der Benutzer die Taste wieder losgelassen hat. Um eine Reaktion des Programms auf evtl. auftretendes Tastenprellen zu verhindern, sollte die Funktion mit Hilfe von delay_ms eine kurze Zeit abwarten ehe sie zurückkehrt. unsigned char getKeyNum(unsigned char sw) Wandelt den Wert, den waitforKey() liefert, in die Nummer der gedrückten Taste um, so wie sie auf dem Evaluationsboard bezeichnet sind (niederwertigstes Bit entspricht der Taste 0, höchstwertiges Bit der Taste
Denis G. schrieb: > Wartet auf eine Eingabe vom Benutzer über die an PortA angeschlossenen > Tasten. > Beachten Sie, dass PIND den Inhalt 0xff hat, wenn keine Taste gedrückt PortA != PIND
Christian H. schrieb: > Denis G. schrieb: >> Wartet auf eine Eingabe vom Benutzer über die an PortA angeschlossenen >> Tasten. > >> Beachten Sie, dass PIND den Inhalt 0xff hat, wenn keine Taste gedrückt > > PortA != PIND sorry für anfänger das heisst?
Gast
#1484413
Wenn die Taster an PortA angeschlossen sind, bringt es nichts, PinD abzufragen.
ja aber im simulator ist es ja theoretisch egal erstmal oder?!
AHh jetzt fällts mir wieder ein in der fh waren die taster aber an port D deshalb
Gast
#1484418
So wird das nie was. Machs doch gleich richtig, nimm die Ports her, wo das Zeug dranhängt. Da kommt sonst nur noch mehr Chaos rein.
SOrry hab nicht mehr dran gedacht das die Taster an PortD im Labor angeschlossen waren vielleicht hab ich auch einfach ein problem mit dem simulator umzugehen?! wenn ich ihn laufen lasse kann ich an PIND ein Bit anklicken um ihn als Taste einzuschalten?! richtig!=?
Gast
#1484424
Einfachst-Variante: //Warten auf Tastendruck: (Also solange, bis PIND != 255 ist) do ( key=~PIND } while (!key); _delay_ms(100); //"Entprellen" //Warten auf Taste Loslassen: while (PIND!=255); _delay_ms(100); //Tasten können auch beim loslassen prellen. Tippfehler darfste behalten. >Dabei soll es egal sein, >welche Taste bzw. ob mehr als eine Taste gedrückt wird. Das muss dann aber auch in getKeyNum beachtet werden. Derzeit wird es nicht beachtet.
Gast
#1484425
Achne, du gibst ja dann 255 zurück. Tschuldigung.
gut aber im simulator klappt das nicht mit taste drücken
Und noch ein Tip. Arbeite in Schritten. Wenn du Probleme mit der Tastenabfrage hast, dann mach dir ein Programm, welches erstmal nur die Tastenabfrage testet. Zb in dem das von den Tasten eingelesene Muster einfach nur auf den LED ausgegeben wird.
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
Solange das nicht zuverlässig funktioniert, hat es keinen Sinn sich da noch zusätzliche Fehlerquellen in Form von Auswertungen und Muster-Ausgaben einzubauen. Wenn es funktioniert, dann hängst du als nächstes getKeyNum ein und kontrollierst wieder anhand deiner LED, ob diese Auswertung stimmt
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
Du musst dir angewöhnen, dass ein komplettes Projekt darin besteht, dass man sich von einem Zwischenziel zum nächsten hangelt, wobei jedes der Zwischenziele getestet werden muss! Anfänger arbeiten gerne nach dem Muster: Ich programmiere erst mal trocken alles runter, so wie ich denke das es funktionieren sollte. Das Ergebnis ist dann: Sie stehen mit einem Haufen Code da, der natürlich nicht funktioniert und wissen nicht, wo sie mit der Fehlersuche anfangen sollen. Denn natürlich ist keine einzige der Teilkomponenten jemals für sich getestet worden. Im Regelfall sind solche Programme dann voll mit Fehlern, wobei man als Helfer nicht weiß wo man mit den Korrekturen anfangen soll. Da wird dann auf Teufel komm raus an einzelnen Stellen 'korrigiert' anstatt das einzig sinnvolle zu tun: Das Programm beiseite zu legen und ein neues anzufangen. In das neue Programm dann nach und nach die Einzelteile des Originalprogramms übernehmen auch wenn man sie kurzfristig etwas verändern muss um sie lauffähig zu bekommen. Aber diesmal: Jede einzelne Komponente die neu übernommen wird, wird auf Herz und Nieren getestet! Und das nächste mal arbeitest du gleich so (und achtest auch darauf, dass dein Code sauber aussieht. Formatierung und eine halbwegs übersichtliche optische Aufteilung sind kein Selbstzweck sondern vitale und wichtige Hilfsmittel im Kampf gegen Fehler. Gerade wenn man im Zeitdruck ist, nimmt ein übersichtliches Programm schon mal einen erklecklichen Anteil des Drucks aus dem Projekt heraus. Alleine das Gefühl, die Übersicht zu behalten ist schon die halbe Miete) Und ja: Auch Profis arbeiten in Schritten. Nur sind bei ihnen die Teilschritte umfangreicher. Das ist aber letztendlich nur eine Frage der Übung. Profis fangen meistens damit an, sich Gedanken über die Teilschritte zu machen, die Reihenfolge wie man die Teilschritte abarbeitet, so dass die Teile aufeinander aufbauen und auch wie man jeden Schritt testen kann. Es ist nicht ungewöhnlich, dass man in den frühen Phasen eines Projekts viel Zeit in Testcode steckt, der im Endprodukt nicht mehr auftaucht. Letztenendes kostet das aber keine Zeit. Die Zeit die man in das Testen der Einzelkomponenten investiert, bekommt man gegen Projektende hundertfach zurück. Das ist bei Profis nicht anders als bei dir.
Denis G. schrieb:
> gut aber im simulator klappt das nicht mit taste drücken
Doch. Das klappt dort genauso.
Eventuell musst du berücksichtigen, dass der Simulator wesentlich
längsamer arbeitet als die reale Hardware. Aber grundsätzlich
funktioniert das schon.
Gast
#1484535
Wenn deine Tastenroutine dann läuft (scheint sie ja, sonst gäbe es eine
Rückmeldung :-) , kannst Du hier nochmal gucken:
>in der fh war es so das wenn ich eine Taste gedrückt
hatte das ein muster kam jedoch hat es sich danach aufgehängt
Dabei inbesondere noch mal das "while(1);" in deiner main() ins Visir
nehmen.. und ein wenig drüber nachdenken.
kann vielleicht mal jemand das prog ins seinen controller reinhauen und gucken obs klappt?
Wie simulierst du? Im AVR-Simulator kannst du Änderungen an den I/O Registern nur dann vornehmen, wenn der Debugger das Programm unterbrochen hat (zumindest war das mal so). Setz dir also einen Haltepunkt auf das Einlesen des PIN Registers. Ist das Programm dort, dann ändere mit der Maus das entsprechende I/O Register und geh mit F10 einen Schritt weiter und sieh dir an, was das Programm nacht. Und bedenke auch: Jedesmal wenn du im Simulator einen F10 machst, hat dein realer Benutzer auch die Möglichkeit die Taste just in diesem Moment zu drücken oder loszulassen. Es ist daher nicht unbedingt verkehrt, die Manipulation am I/O Register nicht unbedingt bei der Abfrage des PIN Registers zu machen, sondern irgendwann davor oder danach um zu sehen, ob das Programm richtig reagiert. Es ist auch nicht verkehrt, daran zu denken, dass aus Programmsicht der Benutzer schnarchlangsam ist. So eine Abfrageschleife, wie du sie hast, dauert in der Realität hundert Millisekunden (aber auch nur wegen dem delay). Kein Mensch kann so schnell eine Taste drücken und wieder loslassen. Dein Programm wird daher diese Schleife ein paar mal abarbeiten. Auch das solltest du in Einzelschritten simulieren um zu sehen, ob deine Gedankengänge richtig sind.
also
sobald ich mein prog so starte
mit dieser main
int main()
{
initport();
putSelPattern(getKeyNum (waitforKey()));
//while(1);
return 0;
}
wird nicht mal meine ports initialisiert!!
wenn ich
int main()
{
initport();
putSelPattern(getKeyNum (0x04));
//while(1);
return 0;
}
klappts
komisch?!
Bau das ganze doch mal in Natura auf. Ich kann mir nicht vorstellen, dass eine Einrückung im Quelltext die Initialisierung der Ports durcheinander bringt.
Gast
#1484623
Was ist das für Lehrfach? Ballistische Programmierung? Gruß, Nick
Naja, sehe ich gerade, Du hast ja beim zweiten Mal noch waitForKey durch 0x04 ersetzt - trotzdem. Mir scheint, dass entweder Dein Simulator Murx ist, oder Du ihn nicht bedienen kannst. Was sagt Dir, dass die Initialisierung nicht ausgeführt wird?
Nick Müller schrieb:
> Was ist das für Lehrfach? Ballistische Programmierung?
Stochern im Nebel.
> sobald ich mein prog so starte Wie startest du? F5, also Run? Da siehst du nicht viel. Bei den ersten paar mal geht man das Programm mit F10 bzw. F11 durch. (Siehe die Menüpunkte im Debug Menü vom AVR-Studio)
Gast
#1484634
Christian H. schrieb:
> Stochern im Nebel.
Das ist die Parallelvorlesung "Fehler-orakeln". :-)
Zerleg doch mal dein Programm und bring die Teile Schritt *für*
Schritt zum laufen.
Hat doch keinen Sinn unsystematisch in der kompletten Code-Suppe
rumzustochern.
Gruß,
Nick
Der Tipp kam hier schon öfter; klarer Fall von Beratungsresistenz.
Klaus Wachtler schrieb:
> Der Tipp kam hier schon öfter; klarer Fall von Beratungsresistenz.
Eher klarer Fall von:
Ich will einfach nicht wahr haben, dass so etwas vermeintlich Simples
nicht in einem Zug gemacht werden kann und mein derzeitiges Verständnis
überfordert.
Irgendwann lernt es jeder, dass Programmieren in der Realität nicht so
einfach ist, wie einem Film und Fernsehen das immer wieder suggerieren.
doch es klappt jetzt nur immoment ist er bei meiner waitforKey funktion
und ich hab ein breakpoint gesetzt um dann ein bit zuschalten .... aber
er springt dann immer
while(PIND!=0xff)
{
Key = ~PIND; // wartet bis alle Tasten wieder losgelassen sind
_delay_ms(100); // Prellzeit der Taste abwarten: 100ms warten
}
hier hin und her
Gast
#1484670
Das erinnert mich an die Geschichte mit der Milliarde Affen, von denen dann einer in einer Million Jahren mal ein Meisterwerk verfasst. Woher bekomme ich nun für eine Million Jahre Popcorn?
Denis G. schrieb: > doch es klappt jetzt nur immoment ist er bei meiner waitforKey funktion > und ich hab ein breakpoint gesetzt um dann ein bit zuschalten .... aber > er springt dann immer > > while(PIND!=0xff) > { > Key = ~PIND; // wartet bis alle Tasten wieder losgelassen sind > _delay_ms(100); // Prellzeit der Taste abwarten: 100ms warten > } > > hier hin und her Wo springt er hin und her? Wo hast Du den Breakpoint gesetzt? Hast Du diesen Tip nicht gelesen? Beitrag "Re: Hilfe bei Parallel-IO dringend (AVR)" Wenn ja, warum hältst Du immer noch an Deinem Code fest?
Denis G. schrieb: > doch es klappt jetzt nur immoment ist er bei meiner waitforKey funktion > und ich hab ein breakpoint gesetzt um dann ein bit zuschalten .... aber > er springt dann immer > > while(PIND!=0xff) > { > Key = ~PIND; // wartet bis alle Tasten wieder losgelassen sind > _delay_ms(100); // Prellzeit der Taste abwarten: 100ms warten > } > > hier hin und her Da hier darauf gewartet wird, bis die Taste wieder losgelassen wird, musst du das im Simulator natürlich auch tun. Im I/O Fenster das Loslassen der Taste simulieren, indem du das Bit am PIND wieder wegschaltest. Denn genau darauf wartet ja while( PIND != 0xFF ) Da gehts nur dann wieder raus, wenn in PIND wieder alle simulierten Eingänge ein Häkchen haben (gefüllt sind). Du musst beim Simulieren schon auch ein wenig nachdenken, was du dem Simulator vorgaukeln musst um deine Hardware zu simulieren. Wenn dein Programm also davon ausgeht, dass "alle Bits in PIND" gesetzt bedeutet "kein Taster gedrückt", dann musst du diesen Zustand auch herstellen, indem du bei Programmstart erst mal in alle PIND Bits eine 1 reinmachst. PS: Deine Tasten sind offensichtlich Low-Aktiv. Das heißt: Der Grundzustand ist: Das entsprechende Bit im PIND ist high (im Simulator: es ist gefüllt). Der Simulator kann das nicht wissen, also musst DU diesen Zustand herstellen und die nicht gedrückten Tasten durch entsprechende High-Bits im PIND einstellen. Ein simulierter Tastendruck besteht dann darin, dass du die Füllung am entsprechenden Bit rausmachst und das Loslassen der Taste ist das Bit wieder zu füllen. Wie gesagt. Ein bischen mitdenken muss man schon auch.
Gast
#1484720
.... Du kannst noch so lange an deinem Code herumdebuggen, richtiger wird er davon nicht. Oben steht doch eine Lösung, die musst du nur rauskopieren...Hergott nochmal. Es wäre sinnvoller die Lösung von oben zu debuggen - um sie zu verstehen.
Antwort schreiben
Bitte melde dich an, um einen Beitrag zu schreiben.
