Hallo Superhirn,
der Freilaufmodus ist tatsächlich interessant, wenn du nur genau einen ADC-Kanal abfragen möchtest. Sobald du aber verschiedene Kanäle benötigst, musst du laut der AVR-Doku schon etwas aufpassen. (Seite 203 in der ATmega8-Doku, die beim ASURO dabei war)
Wenn dein Hauptprogramm den ADC-Kanal über das Register ADMUX ändert, dann wird die aktuell laufende Wandlung noch weiter durchgeführt und erst danach wird der neu eingestellte Kanal 'freerunningmäßig' gewandelt.
Da das Hauptprogramm aber nun den neuen ADC-Kanal erwartet, bekommst du nun trotzdem ersteinmal noch einen Wert zum vorher eingestellten ADC-Kanal.
Falls du in deiner Hauptprogrammschleife ein Sleep hast, das länger als ZWEI Wandlerzeiten ist, kannst du direkt vor dem Sleep den ADC-Kanal wechseln, halt ein bisschen warten, und danach den Wert, der einfach in der ADC-Interruptfunktion in eine globale Variable geschrieben wurde, benutzen.
Wenn du den Kanal NICHT wechselst, dann ist der Wert tatsächlich immer aktuell.
Somit benötigst du den Sleep NUR dann, wenn du den ADC-Kanal wechseln willst.
Der code könnte ungefähr so aussehen:
Code:
unsigned int global_adc_wert;
main ()
{
char kanal_akt = 1;
char kanal_neu = 1;
unsigned int adc_wert;
while (1)
{
// Hier muss Programmcode sein, der den neuen ADC-Kanal bestimmt.
// Natürlich nur dann, wenn du es tatsächlich benötigst.
// Vielleicht ja auch nur zum testen über irgendeine Taste
if (kanal_akt != kanal_neu)
{
wechsel_den_Kanal_auf kanal_neu;
kanal_akt = kanal_neu;
Sleep (100); // Hier ein bisschen ausprobieren. DIe 100 habe ich nur geraten.
}
adc_wert = global_adc_wert; // global_adc_wert wird in der ADC-Interrupt-Funktion gefüllt.
// Hier kanst du nun beliebig auf den ADC-Wert reagieren
if (adc_wert > 100)
Lampe an;
else
Lampe aus;
}
}
P.S.: Eine Reaktion auf super_castle ist nie notwendig.
Lesezeichen