Hi!
Ausgangslage:
-Mega8 Controller
-200kOhm Poti an PC4 (Wiper/Schieber an ADC, ein Ende an GND, andere
Ende an 5V+)
Problem:
Trotz Tutorial-Studium Verständnisprobleme - da Anfänger. Das Poti soll
im Controller eine Zahl zwischen 0 und 350 regeln. Die am Poti
eingestellte Spannung muss also in eine Zahl gewandelt werden. Und ich
weiß nicht, welche Teile der vielen Beispiele im Internet für meine
Anwendung gebraucht werden.
Die Abfrage muss permanent laufen, darum darf der ADC glaube ich nicht
abgeschaltet werden nach der Abfrage.
Als Grudgerüst habe ich das hier stehen:
1
uint16_tReadChannel(uint8_tmux)
2
{
3
uint8_ti;
4
uint16_tresult;
5
ADCSRA=(1<<ADEN)|(1<<ADPS1)|(1<<ADPS0);
6
7
ADMUX=mux;
8
ADMUX|=(1<<REFS1)|(1<<REFS0);
9
ADCSRA|=(1<<ADSC);
10
while(ADCSRA&(1<<ADSC)){
11
;
12
}
13
result=ADCW;
14
15
result=0;
16
for(i=0;i<4;i++)
17
{
18
ADCSRA|=(1<<ADSC);
19
while(ADCSRA&(1<<ADSC)){
20
;
21
}
22
result+=ADCW;
23
}
24
ADCSRA&=~(1<<ADEN);
25
result/=4;
26
returnresult;
27
}
Wo muss ich den Eingangsport angeben, also PC4??? Und wie muss die
Umrechnung aussehen, damit ich auf eine Zahl zwischen 0 und 350 komme???
Danke!!!
Die Umrechnungsfunktion ist eine Geradenfunktion der Bauart
y = ax + b
Die Gerade schneidet den Nullpunkt, also ist (0, 0) auf der Geraden und
das b in der Geradengleichung ist 0.
Damit ist bereits ein Punkt bekannt und du brauchst nur noch einen
zweiten Punkt, um die Zweipunkteform der Geradengleichung aufzustellen.
Vom zweiten Punkt ist ist bekannt, daß y 350 ist. Du brauchst also nur
noch den x-Wert - in diesem Fall den Ausgabewert des ADC - und du kannst
die Geradengleichung aufstellen.
http://de.wikipedia.org/wiki/Geradengleichung
Plausibel...danke!
Weißt Du auch, wie ich zu dem Punkt komme, an dem man die Formel im Code
berechnen kann?
Taster abfragen habe ich schon geschafft. Poti noch nicht, da ich im
Beispielcode keine Anpassungsmöglichkeiten finde. Poti ist korrekt an
PC4 verschaltet.
@kiara
Die Referenzspannung habe ich so gesetzt wie Du es geschrieben hast. Mit
den anderen Teilen komm ich aber nicht klar weil ich nicht weiß, wo ich
diese Zeilen positionieren soll.
Und bei
wert = ReadChannel(4); // PC4 als Channel ausgewählt
wird ja nur die Nummer gewählt und nicht die Bank oder? Weil das könnte
ja auch PD4 sein...
So sieht es jetzt aus:
1
uint16_tReadChannel(uint8_tmux)
2
{
3
uint8_ti;
4
uint16_tresult;
5
ADCSRA=(1<<ADEN)|(1<<ADPS1)|(1<<ADPS0);
6
ADMUX=mux;
7
ADMUX|=(1<<REFS0);
8
9
ADCSRA|=(1<<ADSC);
10
while(ADCSRA&(1<<ADSC)){
11
;
12
}
13
result=ADCW;
14
result=0;
15
for(i=0;i<4;i++)
16
{
17
ADCSRA|=(1<<ADSC);
18
while(ADCSRA&(1<<ADSC)){
19
;
20
}
21
result+=ADCW;
22
}
23
ADCSRA&=~(1<<ADEN);
24
result*=2;
25
returnresult;
26
}
@Peter, kiara und alle:
Mein Ziel ist eine Zahl die in einer Variable gespeichert wird damit ich
damit später weiterlernen/-arbeiten kann. Der Code ist aber für mich
nicht ganz nachvollziehbar. Kann mir jemand aus obigen Informationen es
so zusammenkopieren, damit es am Ende stimmt - also als gesamtes?
> Mein Ziel ist eine Zahl die in einer Variable gespeichert wird damit ich> damit später weiterlernen/-arbeiten kann. Der Code ist aber für mich> nicht ganz nachvollziehbar. Kann mir jemand aus obigen Informationen es> so zusammenkopieren, damit es am Ende stimmt - also als gesamtes?
Selten so gelacht...
Wie wärs denn, wenn du dir einfach mal die Beschreibung des ADC
vornimmst und nachsiehst, was die einzelnen Bits in den Controlregistern
bedeuten?
Das macht zwar ein bischen Arbeit, führt aber doch erstaunlich schnell
zu netten Aha-Effekten.
Das habe ich gemacht. Es tauchen aber keine Sachen auf, die ich wieder
erkenne. Den Syntax von C verstehe ich, aber bei Potis gibt es mehr als
high oder low und nach 4 Stunden Google-Suche darf ich doch vorsichtig
fragen, woran es scheitert?!
ReadChannel(4); - meiner hat aber mehrere Bänke...
Ich mach das nunmal nicht beruflich und ich bin nur auf Probleme mit
Code-Wirrwar gestoßen. Ein kleines und kompaktes Beispiel, in dem am
Ende eine regelbare Zahl rauskommt, gabs bei meinen Suchbegriffen nicht.
Entweder etwas, was nicht funktionierte oder nur eine allgemeine
Erkärung der Register. Oder undokumentierter Code, mit dem ich als
Einsteiger nichts anfangen kann.
wert = ReadChannel(4) bedeutet, dass ADC4 als Ananlogeingang ausgewählt
wird und das ist der Pin PC4 (Datenblatt). Wenn du die Funktion so
verwendest wie oben darfst du halt nicht vergessen, dass sie den 8fachen
Analog-wert zurückgibt...
Da ist der code von peda besser, !! result muss hier am Ende von
ReadChannel durch 4 geteilt werden!!
Also ich würds dann so machen:
@kiara
So muss es also aussehen. Ich teste es so schnell wie möglich. Mit dem
ADC war es dann ein Missverständnis, ich habe nämlich soeine kostenlose
Eagle-Version installiert und dort weicht die Portbeschreibung vom
Datenblatt ab.
Danke für die Hilfe und ich melde mich mit dem Ergebnis!
Ist ist auch nicht peinlich, wenn man
uint16_t wert = (uint16_t)((ReadChannel(4) * 22422UL) >> 16);
rechnet, also einen long für erhöhte Genauigkeit konsultiert.