Die ADC-Klassen

Ups, das letzte Thema, dann noch das kleine Projekt, kurz mal mit anderen Controllern spielen und ein bisschen UML-Show … das war es dann auch. Also dann frisch zum Endspurt.

Für Mikrocontrollerlösungen ist das Erfassen und die Verarbeitung analoger Daten oft essentiell. Mit den ADC-Klassen des AVR C++ Framework lassen sich eine Vielzahl von Aufgabenstellungen rings um den Analog-Digital-Converter mit wenigen Handgriffen erledigen. Das folgende Bild zeigt die UML-Darstellung ausgewählter ADC-Klassen.

Analoge Daten verarbeiten

Wahrscheinlich sind die meisten Problemstellungen, bei denen ein Analogwert erfasst, verarbeitet und daraufhin etwas, was auch immer, getan werden soll, mit einer Auflösung von 8 Bit absolut hinreichend zu lösen. Somit soll im ersten Beispiel ein 8 Bit Wert erfasst und per Uart an das Controlcenter gesendet werden. Der Charm dabei ist, dass 8 Bit Werte sich auch sehr reibungslos per Uart übertragen lassen. Nun denn - der Entwurf:

/////////////////////////////////////////////////////
// ENTWURF Beispiel Analog 1
/////////////////////////////////////////////////////
class Application : public Controller
{
    // Attribute für den Analogwert, den Lichtsensor und die Uart anlegen
 
    public: void onStart()
    {
        // Lichtsensor und Uart initialisieren
    }
 
    public: void onWork()
    {
	// kann leer bleiben oder gleich löschen
    }
 
    public: void onTimer10ms()
    {
        // Helligkeitswert erfassen
        // den Wert an das Controlcenter senden
    }    
 
} app; 

Es sollen die Sensorwerte vom Lichtsensor erfasst und an das Control Center gesendet werden. Verbinden Sie den Lichtsensor mit dem Analogkanal 0. Dieser liegt in Zweitbelegung an Port C Bit 0.

Der ADC des AVR sampelt grundsätzlich mit 10 Bit. Man kann aber das Ergebnis der Digitalisierung so im ADC Register ausrichten, dass sich ein 8 Bit Ergebnis in Assembler leichter abholen lässt. Aber, ist es in C noch wichtig sich um derartige Details zu kümmern? Die Klasse AnalogDevice besitzt jeweils eine Operation, die den 10 bzw. 8 Bit Wert der Wandlung liefert. Und hier setzen wir mit dem folgenden Beisiel an:

/////////////////////////////////////////////////////
// Beispiel Analog 1
/////////////////////////////////////////////////////
class Application : public Controller
{
    protected: uint8 helligkeit;
    protected: AnalogDevice lichtsensor;
    protected: Uart konsole;
 
    public: void onStart()
    {
        lichtsensor.config(0);
        konsole.config(9600);
    }
 
    public: void onWork()
    {
	// leer    
    }
 
    public: void onTimer10ms()
    {
        helligkeit=lichtsensor.getValue8();
        konsole.sendByte(helligkeit);
    }    
 
} app; 

Bilden, übertragen und testen Sie das Programm. Beachten Sie die Einstellungen des COM-Ports im Controlcenter.

<flashplayer width=„600“ height=„450“ position=„0“>file=http://youtu.be/eKqLqUJUB14</flashplayer>

Das was wir als nächstes programmieren wollen, notieren wir als Konzept im Quellcode. Sie kennen das Spiel ja. In dieser Übung soll die Formatierung und Ausgabe von Zeichenketten mit der Erfassung von Analogwerten mit einer 10 Bit Auflösung kombiniert werden. Ganz nebenbei muss auch noch etwas gerechnet werden. Wir möchten die tatsächliche Spannung in Millivolt und auch in Volt, mit eins, zwei oder auch drei Nachkommastellen ermitteln.

///////////////////////////////////////////////////////
// KONZEPT Beispiel Ausgabe der Spannung in Millivolt
///////////////////////////////////////////////////////
class Application : public Controller
{
    // Attribute für die Analogwerte und Berechnung anlegen
    // Instanzen für den Analogeingan und die Konsole anlegen
    // ein Attribut vom Typ String für die Formatierung anlegen
 
    public: void onStart()
    {
       // Initialisierung des Analogeingangs und der Uart
    }
 
    public: void onWork()
    {
        // 10 Bit Analogwert erfassen
        // in "reale" Spannung umrechnen
        // Ausgabestring formatieren
        // Ergebnis per Uart senden
        // ein paar Millisekunden auf die Bremse treten
    }      
} app; 

Die Realisierung soll in zwei Varianten erfolgen. Zunächst mit der Ausgabe in Millivolt und danach die Erweiterung auf die Ausgabe mit einer Stelle nach dem Komma.

// Ausgabe der Spannung in Millivolt
class Application : public Controller
{
    protected: uint32 analogwert, spannung;
    protected: AnalogDevice analogEingang;
    protected: Uart konsole;
    protected: String text;
 
    public: void onStart()
    {
        analogEingang.config(0);
        konsole.config(9600);
    }
 
    public: void onWork()
    {
        analogwert=analogEingang.getValue10();
        spannung=analogwert*5000/1024;
        text.format("U = %lu mV \n",spannung);
        konsole.sendString(text);
        waitMs(500);
    }      
} app; 

Diesmal soll das Potentiometer 1 als Quelle für unsere Analogwerte dienen. Schließen Sie das Potentiometer an den Analogkanal 0 an (PortC.0).

Erstellen, übertragen und testen Sie das Programm. Beachten Sie die Einstellungen für den Com-Port und den Zeilenumbruch im Controlcenter. Das Ergebnis sollte wie folgt aussehen:

Nachdem die Umrechnung und Ausgabe in Millivolt funktioniert, geben wir die Werte formatiert mit einer Genauigkeit von einer Stelle nach dem Komma aus.

// Ausgabe der Spannung in Volt, Genauigkeit eine Stelle hinter dem Komma
class Application : public Controller
{
    protected: uint16 analogwert, spannung;
    protected: AnalogDevice analogEingang;
    protected: Uart konsole;
    protected: String text;
 
    public: void onStart()
    {
        analogEingang.config(0);
        konsole.config(9600);
    }
 
    public: void onWork()
    {
        analogwert=analogEingang.getValue10();
        //Volt=analogwert*VRef/Maximalwert
        //deziVolt=analogwert*deziVoltRef/1024
        spannung=analogwert*50/1024; 
      	text.format("Spannung = %u,%u Volt \n",spannung/10,spannung%10);
	konsole.sendString(text);
     	waitMs(500);
    } 
} app;

Erstellen, übertragen und testen Sie das Programm. Beachten Sie die Einstellungen für den Com-Port und den Zeilenumbruch im Controlcenter. Das Ergebnis sollte dem folgendem Bildschirmauszug entsprechen.

Videozusammenfassung

Nächstes Thema