AVCC angeschlossen?
AVCC angeschlossen?
ja hab ich , sag ja , einzeln messen von ADC1 oder ADC2 geht und wird auch richtig angezeigt, beide zusammen messen wirds Chaos.
Wenn ich Joystick Hebel nach oben bewege liegen am PC2(ADC2) 5Volt an, auf dem LCD zeigt ADC2: 1023 an, was ja richtig ist, allerdings wechselt ADC1: auch ständig von 492 auf 1023 wieder auf 492....
ADC-Eingänge der Microcontroller sind oft relativ nierderohmig, im Bereich weniger Kiloohm. Ein 50k-Poti als Quelle ist da eigentlich ungünstig.
Abhilfe ist einerseits möglich durch das bereits beschriebene Delay zwischen MUX-Umschaltung und Start der Messung, um ausreichend Samplingzeit zu gewähren.
Zum anderen kann ein Pufferkondensator pro Kanal, der sich beständig auf den aktuellen Spannungswert des Kanals auflädt, die effenktive Impedanz der Quelle merklich reduzieren, weil er binnen kurzer Zeit den internen Samplingkondensator des ADC auf (fast) gleichen Pegel bringen kann.
Ich frag mal ganz dumm:
while (ADCSRA & (1<<ADSC)) // warten bis ADC fertig
muss da nicht ein Semikolon hinter? Soll doch warten, bis ADSC zurückgesetzt ist und dann erst die folgende Codezeile zum Lesen des AD-Wertes ausführen. Ohne Semikolon wird doch die folgende Zeile oder der durch {} eingefasste folgende Block mit dem while ausgeführt, oder bin ich jetzt ganz im falschen Film?
Geändert von Holomino (22.04.2015 um 07:45 Uhr)
Du musst mal die Variablentypen gleich ziehen:
es wird ein "double" mit "int" und "unsigned long" vermischt (Fließkommazahlen mit vorzeichenbehafteten Integer mit nicht vorzeichenbehafteten Integer), da sollte der Compiler doch schon einige Warnings anzeigen.
Meines wissens ist ein "int" nicht exakt definiert, es kann je nach Compiler ein short oder sonstwas sein.
Von der Rechengenauigkeit her kommst mit "short" Variablen oder "int16_t" aus, die haben einen Zahlenbereich von −32.768 bis +32.767.
dtostrf: schaut etwas knapp aus, probier mal mehr Speicher bereitzustellen (zB char ystr[6] )
Add: AT8adc.h
*.h bedeutet einen Header Datei, da steht schon sicher mal kein Code drinnen, sondern nur zB Definitionen von Funktionen: "extern void lcd_home(void);"
erst in einer *.c Datei steht dann die genaue Funktion:
void lcd_home(void)
{
lcd_command(1<<LCD_HOME);
}
So gesehen sollte das Programm nie funktionieren, oder ist es doch unter *.c gespeichert?
LG!
alles über meinen Rasenmäherroboter (wer Tippfehler findet darf sie gedanklich ausbessern, nur für besonders kreative Fehler behalte ich mir ein Copyright vor.)
Hallo,
Dem Compiler ist das .h oder .c total egal!
Das ist nur eine Konvention und man kann als Dateiendung verwenden was das Dateisystem zu lässt.
Genau genommen werden die #include-Dateien vom Präprozessor verwaltet.
Im Prinzip macht dieser eine Art "search & replace", überall wo er #include findet löscht er dieses und kopiert die angegebene Datei rein.
Der Compiler bekommt dann diese aufgeblasene Datei gefüttert.
Früher, als der Präprozessor noch ein eigenständiges Programm war, hat man den gerne auch z.B. in der Textverarbeitung eingesetzt.
Man konnte dann einzelne Kapitel als eigene Dateien verwalten und mit den entsprechenden #includes dann das Buch zusammenstellen.
MfG Peter(TOO)
Manchmal frage ich mich, wieso meine Generation Geräte ohne Simulation entwickeln konnte?
Da rächt sich die "dumme" Angewohnheit, leere while-Schleifen in einer Zeile und ohne geschweifte Klammern zu schreiben.
da ist schlecht zu erkennen, was da abgeht, da nun auch noch der Kommentar dicht dahinter steht. Auch beim Lesen ist schlecht zu erkennen, daß es um einen Loop geht, insbesondere wenn man in ein paar Wochen an den Code noch mal ran muß. Und ohne Klammern wird da ganz schnell mal eine Semikolon reingeschrieben, obwohl die nächste Zeile eigentlich in die Schleife gehört. wenn man das grundsätzlich so schreibt:Code:ADCSRA |= (1 << ADSC); // single conversion while (ADCSRA & (1 << ADSC)) // warten bis ADC fertig ADC_result = ADCW; //ADC_result += ADCW;
passieren nicht so leicht Fehler und man kann ganz schnell noch einen Print zum Debuggen oder einen Nop für einen Breakpoint einfügen und auch wieder herauskommentieren, ohne daß die Programmstruktur kaput geht.Code:ADCSRA |= (1 << ADSC); // single conversion while (ADCSRA & (1 << ADSC)) { // warten bis ADC fertig ; } ADC_result = ADCW; //ADC_result += ADCW;
In diesem Fall wird hier während der Konvertierung dauernd das Resultat ausgelesen, ob das dem ADC gefällt, weiß ich nicht.
Es ist schon definiert, mindestens 16 Bit. Wenn aber die CPU schneller mit 64 Bit umgehen kann, kanns auch mal 64 Bit sein. Short ist da schon eher nicht definiert. Für einen Joystick reicht aber auch ein int8_t, selbst die Auflösung kann man mit den Fingern gar nicht erreichen.
MfG Klebwax
Strom fließt auch durch krumme Drähte !
Hallo erstmal und danke für die ganzen Antworten.
Muss mich aber erstmal berichtigen, denn in dem Joystick sind nicht 50kohm Potis eingebaut sondern 100kohm Potis.
Denke mal das damit auch mein Fehler sich erklären lässt, werde erstmal 2 10Kohm Potis verdrahten und diese dann messen, wenn das funktioniert ohne Propleme liegts am Joystick.
- - - Aktualisiert - - -
natürlich habe ich alles in einer Joystick.c datei gespeichert, aber da ich alles was den ADC angeht in der AT8adc.H geschrieben habe hab ich auch nur diese hier aufgelistet, kann aber gerne auch noch meine *.c vorzeigen, fals es erwünscht wird.
Warum sollte der Compiler meckern? Syntaktisch ist das Programm ja in Ordnung: wenn man keine Klammern setzt, wird die auf das while() folgende Anweisung solange ausgeführt, bis der Audruck im while() false wird. Wenn da nichts weiter passieren soll, muß dort das C-Equivalent eines NOPs stehen, nämlich das Semikolon. In deinem Code steht aber das Lesen des ADC-Resultats, und das macht er dann auch im Loop. Das ist zwar sinnloser aber gültiger Code.
Eine Hilfe ist, sich den Code automatisch von der IDE formatieren zu lassen. An der Einrückung hätte man das sofort gesehen.
MfG Klebwax
Strom fließt auch durch krumme Drähte !
Lesezeichen