Forum: Projekte & Code ADC mit Multiplexanzeige


Announcement: there is an English version of this forum on EmbDev.net. Posts you create there will be displayed on Mikrocontroller.net and EmbDev.net.
von Peter D. (peda)


Angehängte Dateien:

Lesenswert?

Anbei ein Beispiel für eine 4-stellige Multiplexanzeige, die einen
ADC-Wert ausgibt.

Es werden insgesamt 13 IO-Pins benötigt, d.h. ein ATTiny26 reicht
vollkommen aus.

Um die Messung nicht zu beeinflussen, wird die Anzeige während der
Messung dunkelgetastet.

Als Multiplextakt wird 1Mhz  4  256 = 980Hz verwendet.

Um ein ergonomisches Ablesen zu gestatten, wird nur jede 256. Wandlung
ein neuer Wert dargestellt (4 Werte/s).

Außerdem wird der Mittelwert über 256 Messungen gebildet.

Zusammen mit der Dunkeltastung steht dadurch der Meßwert wie ne Eins.

Für ein einfacheres Platinenlayout wurden Digit 0,2 und 1,3
unterschiedlich beschaltet, deshalb werden zur Ausgabe 2
7-Segmenttabellen benutzt.

Die Digit- und Segmentzuweisungen erfolgen über Defines, lassen sich
also an beliebige Verdrahtungen anpassen.

Das ganze ist in C geschrieben.


Peter

von Tobias S. (tobias)


Lesenswert?

Hi,
waere es nicht sinnvoll, den Transistoren einen Vorwiderstand zu
bescheren? Sind ja keine FETs sondern normale bipolare Typen.


Gruss Tobias

von Benedikt (Gast)


Lesenswert?

@Tobias
Wiso Widerstände ? Die sind als Emitterfolger geschaltet und daher
fließt nur der Strom, der zum Schalten der Transistoren erforderlich
ist (Strom durch die Anzeige durch Spannunsgverstärkung des
Transistors, vermutlich wenige mA oder sogar noch weniger).

@peter dannegger
Super Projekt, wollte gerade anfangen dasselbe zu machen, aber das
brauche ich ja jetzt nichtmehr...
Gibt es dafür eigentlich ein Platinenlayout, wenn du schon schreibst
dass deshalb die Anschlussbelegung geändert wurde ?

von Tobias S. (tobias)


Lesenswert?

Benedikt:
Mein Fehler hab da garnicht drauf geachtet ...

Peter Danneggers Ehre soll nicht berührt werden :)

Gruss Tobias

von Peter D. (peda)


Lesenswert?

@Benedikt,

Das Layout kann ich leider nicht rausgeben, da ist auch viel mehr
drauf.


Peter

von cdg (Gast)


Lesenswert?

Hallo Peter,
die Widerstandsbezeichnung der Segmentwiderstände
332R soll wohl für SMD Widerstände stehen.

Das wären dann aber 3,3KOhm !!

Ich kenne die verwendeten Anzeigen HDSP-K121 zwar nicht,
aber sind 3K3 nicht ein bisschen !sehr! hoch
für eine Multiplex-Anzeige ?

Ich denke da mehr an 33Ohm (für gemultiplexte übliche 7-Seg.Anzeigen).

MfG cdg

von cdg (Gast)


Lesenswert?

Habe mir mal das Datenblatt der Anzeige angeschaut.

Danach denke ich mal, es sind 330Ohm Widerstände.

Bei 33Ohm wäre der ATMEL auch überfordert.

Ich werde die Schaltung mal aufbauen,
nur scheitert es am fehlenden ATtiny26.

Danke für die nette und nützliche Schaltung/Software.

MfG cdg

von cdg (Gast)


Lesenswert?

Meine Annahme mit 330 Ohm ist wohl richtig,
denn in der E96 Reihe gibt es den Wert 332 Ohm !!

Naja, 1% Genauigkeit für Segment-Widerstände aus der E96 Reihe,
da muss man erstmal drauf kommen.

Ich nehme dann die erwähnten 330 Ohm.

cdg

von Peter Dannegger (Gast)


Lesenswert?

Ja, 330 Ohm oder 332 Ohm ist egal.

Ich nehme immer 1%/50ppm Metallschicht, weil das einfacher ist, als für
jeden Wert 1% und 5% zu kaufen. Und der Preisunterschied ist ja nicht so
groß.

In Schaltplänen ist es üblich, R für Ohm zu schreiben.
Für 3,32kOhm hätte ich geschrieben 3k32.


Wenn man keine high efficiency Anzeigen nimmt, kann man die Widerstände
auch noch verringern.


Peter

von Norbert Lukoski (Gast)


Angehängte Dateien:

Lesenswert?

Hallo. Hab ein kleines Problem. Arbeite zum ersten mal mit dem AVR
Atmega8 und möchte über den ADC0 Eingang eine Spannung einlesen und
über 7-SegmentAnzeige ausgeben lassen. Spannung kommt am Eingang an und
ich denke das der ADC im frei laufenden Betrrieb läuft, aber er spuckt
komische Zahlen auf der Anzeige aus. Meine MEinung ist, dass es an der
Ergebnisroutine liegt. Wenn wir in meine VAriable "value" einen Wert
definieren rechnet er den entsprechenden Wert aus und gitb ihn auch
richtig auf der Anzeige aus. Aber wenn er sich die Werte über den
Eingang ADC0 holen soll und diese dann in ADCL und ADCH reinschreibt
kommt nur Null raus. Kannst du mir vielleicht helfen?

von peter dannegger (Gast)


Lesenswert?

@Norbert

"Aber wenn er sich die Werte über den Eingang ADC0 holen soll und
diese dann in ADCL und ADCH reinschreibt kommt nur Null raus."


Was aus dem ADC rauskommt, schmeißt Du weg.

Du setzt value3 einmalig auf 0 und gibst es aus.

Es ist also voll korrekt, daß nur 0 angezeigt wird.


Peter


P.S.:
Du hast Dir meinen Code überhaupt kein bischen angesehen, stimmts ?

von Norbert Lukoski (Gast)


Angehängte Dateien:

Lesenswert?

Sory hatter die falsche Version vom Quellcode. Da muss ich dir recht
geben das hat man auf dem ersten Blick gesehen das da Null raus kommt.
Ichhab jetzt eine andre Methode angewendet. Könntest du mal bitte
darauf schauen. Aber eine Frage stellt sich mir, warum schaut der ADC
nicht die ganze Zeit (frei laufender Modus ist aktiviert) die Werte auf
der BCD Anzeige aus. Eigentlich sollte er wie eine Multimeter arbeiten
ud die Spanung ausgeebn die im ADC reinkommt. Ich habe die Messmethode
ja in der while bzw. for Schleife drin so dass er eigentlich dauernd
arbeiten muss.Ach noch eine andre Frage, wir hatten schon mal mit nem
andren Microkontroller gearbeitet und das war etwas einfahcer da man
dort ein Ergebnisregister hatte und es einfach in ne andere Variable
schreiben konnte. Des Weiteren hatte wir dort mit Interruprroutinen
gearbeitet und mit Timern. Kann ich das so wie es im ANhang zu sehen
ist machen und einfach über Methoden starten? Würde mich auf eine
baldige Antwort von DIr sehr freuen. Bis dann

von Norbert Lukoski (Gast)


Lesenswert?

So ich hab jetzt nochmal getest und es liegt an der Routine um das
Ergebnis aus den beiden Registern ADCL und ADCH zu bekommen. Meine
Routine ist laut dem Programm ICC AVR Wizzard:

 float value2=0;
 value=ADCL;            //Read 8 low bits first (important)
 value|=ADCH << 8; //read 2 high bits and shift into top byte
 //value=200;
 value2=((5*value)/20.46);
 value=((int)value2);
 hunderstel=((value*10)%10);
 einer=(value%10);

Du siehst das ich zum testen value mal auf 200 stelle und schmweißt das
richtige aus. Das PRoblem ist ja das ich ne 16Bit Zahl habe und nun aus
dieser Zahl die Spanungswerte rausfiltern muss. Kannst du mir beim
herausfiltern der jeweils 8-Bit Werte helfen. Weil anscheinend meine
vom Wizzard eigentlich falsch ist?

von Simon K. (simon) Benutzerseite


Lesenswert?

Hm?

1. Muss man nicht zuerst ADCH auslesen?
2. Geht in deinem "ICC Wizard" (?) nicht einfach 16bitvariable = ADC
statt aufwendigem zusammenführen?
3. / 20.46? Wofür ins das?

4. für integer nach ascii (einer/zehner/hunderter) umwandlung gibts
auch itoa(...);

von Uwe (Gast)


Lesenswert?

Hallo Peter!
>Um die Messung nicht zu beeinflussen, wird die Anzeige während der
>Messung dunkelgetastet.

Ist da nicht ein leichtes flackern zu sehen?
Habe soetwas vor kurzem auch gemacht und die Anzeige bei Wandlung
angehalten(weniger Spannungssprünge) aber die Anzeige flackert leider
etwas.

MFG Uwe

von peter dannegger (Gast)


Lesenswert?

@Uwe,

die Bildfrequenz (Zeitdauer für alle 4 Digits) ist etwa 200Hz, da
flackert nichts mehr.


Peter

von Uwe (Gast)


Lesenswert?

@Peter,
Die Bildfrequenz spielt da keine Rolle, ausschlggebend ist ja wie oft
du Wandelst. Wenn die Wandlung fast synchron mit der Anzeige ist, wird
fast an der selben Stelle ausgesetzt. Diese Aussetzer werden dann
sichtbar. Habe gerade überlegt ob ich nicht ein 5.Scheindigit
einfügen sollte und da die Wandlungen laufen lasse.

Schönen Tag noch, Uwe

von peter dannegger (Gast)


Lesenswert?

@Uwe,

probier meinen Code doch mal aus, da flackert nichts.

Und daß die Wandlung synchron zur Anzeige sein muß, habe ich doch
erklärt.

Ob nun ein extra Zyklus oder bei jedem Digit ist egal, Hauptsache
schneller als 100Hz, damits nicht flackert.



Peter

von Marcel (Gast)


Lesenswert?

Sorry fürs ausgraben, aber ich habe folgendes Problem:

Digits 0 und 2 zeigen Bullshit an (irgendwelche Segmente, aber keine 
sinnvollen Zahlen), die Dezimalpunkte werden nicht korrekt angezeigt. 
Aufbau ist genau nach Schaltung, Source das originale Codebeispiel.

Ich weiß nicht mehr weiter...vielleicht hat jemand einen Tip für mich?

Marcel

von Marcel (Gast)


Lesenswert?

Äh, nee, is ja peinlich - wer lesen kann ist glatt im Vorteil ! Die 
beiden Anzeigen sind ja tatsächlich anders layoutet ...

Problem gelöst.

Marcel

von 65432 (Gast)


Lesenswert?

Peter, mit welchem Programm hast du den Schaltplan erstellt? Sieht 
sauber aus! Gibt es das kostenlos?

von Peter D. (peda)


Lesenswert?

65432 wrote:
> Peter, mit welchem Programm hast du den Schaltplan erstellt? Sieht
> sauber aus! Gibt es das kostenlos?

Ne, das hatte mal richtig Geld gekostet.
Ist Protel 99SE.
Die Bauteile definiere ich mir meistens selber.


Peter

von Andreas L. (andreasl)


Lesenswert?

Hallo, ist richtig interessant dieser Thread. Nun bin ich noch nicht 
Sattelfest mit uPC, möchte Euch aber gerne ein paar Fragen stellen:

1. Wäre es möglich das ich als Anfänger es hinbekomme statt des Tiny26 
einen Mega88 zu verwenden und den Rest der Schaltung so zu lassen wie 
sie jetzt ist? Ich müßte doch die richtige defination Datei einbinden 
(io.h) und mir die richtigen PORT´s aus den Datasheet raussuchen?

2. Ist es möglich eine LCD Anzeige zu verwenden? Ich habe hier in der 
Codesammlung irgendwo ein LCD.h gesehen. Aber da  stoße ich 
wahrscheinlich an meine Grenzen.

3. Wie, oder kann man das erweitern auf 4 Messwert anzeigen?

von Jan (Gast)


Angehängte Dateien:

Lesenswert?

Hallo,

habe mal auf Anregung eines Kollegen versucht dieses nette Projekt auf 
Wechselspannungsmessung aufzubohren, aber einige Problemchen damit. Vor 
den MC habe ich einen Vorteiler auf URef/2 und kopple dann die 
Wechselspannung ein. Vorberechnet sollte das eigentlich funktionieren. 
Im Code habe ich eine Peak2Peak- Erkennung ergänzt, welche nach meiner 
Meinung eigentlich funktionieren sollte:




SIGNAL( SIG_ADC )
{
   static u32 adc_sum;
   static u32 MIN;
   static u32 MAX;
   static u32 TEMP_ADC;

   static u8 count;
   u8 i;

   TEMP_ADC= ADC;
   adc_sum += ADC;

if( TEMP_ADC > MAX ){

   MAX=TEMP_ADC;
   }

if( TEMP_ADC < MIN ){

   MIN=TEMP_ADC;
   }


   count++;

   if( count == 0 ){      // 4 values/s
     adc_val = adc_sum >> 8;    // average über 256 samples
     adc_sum = 0;
     Peak2Peak= MAX-MIN;


  MIN =512;
  MAX =512;

   }


sowie in der Anzeige dann:

 dec_out( (Peak2Peak * SCALE) >> 16 );


Aber irgendwie tut das nicht so wie es soll. Zeigt nicht das an was es 
soll (zu wenig). Hat jemand Verbesserungsvorschläge? Ist die Peak- 
Erkennung doch zu langsam (zu wenige Abtastungen)? Irgend ein anderer 
Fehler?

Jan

von Alexej (Gast)


Lesenswert?

Hallo, Peter!
Ich heiße Alexej. Ich bin aus Ukraine.
Ich will das Voltmeter machen, das Sie hier beschrieben haben. Aber Ich 
cann nicht *.hex die Datei machen.
Können Sie mir helfen? Und welche fuse bits muß ich aufstellen?

Danke im Voraus für Ihnen.
---
Mit freundlichen Grüßen,
Alexej.

von Kreativlücke (Gast)


Lesenswert?

Hallo Peter,

dein Projekt gefällt mir sehr gut. Hat sich die Schaltung bewährt oder 
würdest du heute etwas anders machen?

> Um ein ergonomisches Ablesen zu gestatten, wird nur jede 256. Wandlung
> ein neuer Wert dargestellt (4 Werte/s).

Kann man diese Rate erhöhen oder wären da tief gehende Änderungen 
notwendig?
Sind 20 Werte / Sekunde denkbar ohne die 256. Wandlungen herabzusetzen?

von Ratzjo Mittelbau (Gast)


Lesenswert?

Kreativlücke schrieb:
> Hat sich die Schaltung bewährt oder
> würdest du heute etwas anders machen?

Er hat 2008 schon nicht auf die gestellten Fragen geantwortet, dann wird 
er es heute wohl auch nicht tun.

von Kreativlücke (Gast)


Lesenswert?

> Er hat 2008 schon nicht auf die gestellten Fragen geantwortet, dann wird
> er es heute wohl auch nicht tun.

Vielleicht hat er die letzte nicht gesehen. Ich weiß jedenfalls, dass 
Peter noch ab und zu hier unterwegs ist.

Aber es sei dir natürlich frei gestellt die Fragen zu beantworten :)

von Kreativlücke (Gast)


Lesenswert?

Wäre es möglich einfach eine höhere Taktfrequenz als 1 Mhz einzustellen?
Würde dann nicht auch alles x mal schneller ausgeführt werden und 
dadurch auch mehr Werte / s angezeigt werden? :)

von Peter D. (peda)


Lesenswert?

Kreativlücke schrieb:
> Wäre es möglich einfach eine höhere Taktfrequenz als 1 Mhz einzustellen?

Ja natürlich. Man muß dann den ADC-Vorteiler anpassen, um im Bereich 
50..200kHz zu bleiben.

Die Meßwertrate ergibt sich bei mir aus:
1MHz / 4 / 256 / 256 = 3,8Hz
Man kann an jedem dieser Parameter drehen.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.