Hallo, ich möchte gerne ein Projekt realisieren und weiß nicht genau wie ich anfangen soll.Ich möchte gerne mit dem Mega8 einen Computerlüfter Steuern und ein Relais.Das Relais soll eine Wärmeplatte ein/ausschalten.Die Temperatur soll mit einen Sensor kontrolliert werden.Der Lüfter soll Drehzahlgesteuert sein.Das ganze möchte ich mit 2 Potis steuern und die eingestellten Werte sollen auf einen LCD ausgegeben werden. Also ich schaffe Werte auf einen LCD auszugeben.Potis mit dem ADC auszulesen und den Sensor in Betrieb zu nehmen.Mit der Drehzahlregelung weiß ich es jetzt noch nicht,aber das wird wohl mein kleinstes Problem sein. Problem ist jetzt folgendes der ADC so wie ich Ihn bis jetzt erst benutzt habe gibt mir Werte von 0-255 (Terminal Programm).Ich möchte jetzt aber z.B. meine Wärmeplatte nur von 0-100° einstellen können.Wie schaffe ich jetzt das ich nur ein ADC Ergebniss von 0-100 in meinem Programm erhalte.Weil dieses möchte ich dann einfach mit dem Ist-Wert vom Sensor vergleichen und ein/ausschalten. Dann wie funktioniert das mit der Drehzahlsteuerung habe so einen Lüfter mit dem dritten Kabel dran. Ich möchte jetzt keinen fertigen Code oder so ich wollte jetzt einfach mal eine kleine Starthilfe. MfG Sebastian
Ok, das klingt doch alles schonmal nicht schlecht. Daß du Werte auf dem LCD dargestellt bekommst ist sehr hilfrech. Das erleichtert das Debugging ungemein. Du siehst im Terminal Werte von 0-255. Das kann entweder bedeuten, daß du nur das untere Byte deines 10-bit-Ergebnisses ausgiebst (bei rechtsbündiger Anordnung, verlierst du beiden obersten Bits) oder eben nur das obere Byte bei linksbündiger Anordnung (verlierst du beiden untersten Bits). Der ADC könnte dir ja eigentlich Werte von 0-1023 liefern. Da du ja recht lernbereit zu sein scheinst (sehr löblich) überlasse ich es erstmal dir, wie du das handhabst/hinkriegst. Jetzt willst du einen Zahlenbereich von 0-100 darstellen. Wenn das ohne Kommastellen ablaufen soll, dann ist das ja ganz einfach: dein ADC gibt Werte raus von 0 bis xxx. Wenn xxx als 1023 angenommen wird, dann mußt du also 100 auf 1023 aufteilen. Wie das geht? 1023 / 100 = 10,23! Was du mit dem Wert jetzt anzustellen hast überlasse ich erstmal wieder dir =) . Zu deinem Lüfter: unterscheide zwischen Steuerung und Regelung. Bei einer Steuerung gibst du stumpf einen "Sollwert" vor. Ob dein Lüfter jetzt aber wirklich damit läuft weißt du nicht und interessiert dich auch nicht. Bei einer Regelung hast du einen Sollwert, und erhältst über eine Messung den Istwert (Drehzahl). Mit den beiden Werten mußt du einen Regelalgorithmus füttern (für Anfänger oft nicht ganz einfach). Darum solltest du erstmal mit dem "Steuern" der Drehzahl anfangen. Der Rest ist wieder nur eine Frage der Skalierung. Du weißt z.B.: der Lüfter darf maximal 12V. Jetzt kannst du sagen: bei 0°C soll der Lüfter stehen, und bei 100°C mit Nenndrehzahl laufen (die Drehzahl bei 12V). Also mußt du den Spannungsanstieg pro °C hinkriegen: 12V / 100°C = 0,12 V/°C. das ist dann aber eine Steuerung, keine Regelung. Und wenn du das hingekriegt hast, dann reden wir über die Regelung :) ... Gruß
Nachtrag: wie findet eigentlich deine Temperaturmessung statt? Und willst du wirklich eine "Temperaturregelung" haben? Wenn ja, dann brauchst du eine Temperaturregelung, der dann noch eine Drehzahlregelung des Lüfters unterlagert ist. Da wird es dann schon "interessant". Falls du es hinkriegst die Werte 0-1023 aus dem ADC zu kitzeln: meinst du nicht es wäre sinnvoller, wenigstens in 0,1°C-Schritten zu arbeiten? Dann ginge dein Wertebereich von 0-102,3°C in 0,1 Grad-Schritten...
Also ich habe gestern noch bis 4 Uhr am Computer gehangen.Und selbst herausgefunden das ich den ADC Wert ganz einfach Teilen kann.Ich habe den ADC vorher auf 8bit eingestellt gehabt,deswegen waren es nur 0-255 jetzt läuft er auf 10bit und wird dann geteilt.Ich kann jetzt auch schon beide Potis einlesen und den Wert auf den LCD ausgeben.Weil ich jetzt noch keinen Sensor hier rumliegen habe,ist ein Sollwert im Programm um zu testen ob das Relais schaltet das funktioniert auch.Also ist dieser Teil kein Problem mehr für mich.Jetzt hatte ich vor genau wie Du geagt hast den Lüfter zu intigrieren.Da bin ich aber noch etwas überfragt wie ich das anstelle,weil er ja 12V braucht.Würde er nur 5V brauchen hätte ich den irgendwie über PWM gesteuert.Ich brauche zwar eigentlich nur etwa die hälfte der möglichen Drehzahl des Lüfters,aber zum anlaufen braucht er die 12V danach kann dann sofort runtergeregelt werden.Was kann ich jetzt zwischen Lüfter und Mega8 schalten,das Dimmbar ist? Wenn ich dann diese Hürde gemeistert habe,wollte ich irgendwie das Signal für die Drehzahl über den Timer(Counter) zählen und dann weiterverarbeiten.Bin ich auf dem richtigen Weg?Oder kann man das besser lösen? Um zu erläutern warum ich den Temparatur Sensor und die Drehzahlsteuerung benötige erkläre ich am besten was ich vor habe. Ich möchte ein Magnetrührer selber bauen,da anständige Modelle sehr teuer sind.Und wirklich viel Elektronik ist da nicht drin.Es wird eine alte Warmeplatte benutzt um die Chemiekalien zu erhitzen,der Sensor soll eine genaue Gradzahl einstellung ermöglichen.Der Lüfter dreht eigentlich nur 2 Magnete.Der Drehzahlbereich sollte zwischen 100-1000rpm liegen.Das war es schon. MfG Sebastian
Ich habe gerade wahrscheinlich mal den ganz klassischen Anfänger Fehler gemacht.Und zwar wollte ich für die Drehzahlen eine art sagen wir mal Tabelle machen um die verschiedenen PWM Signale zu erzeugen. Das klapte auch aber ich wollte stufenlos Regeln. Ich habe jetzt noch mal mein kleines Spatzenhirn angestrengt und den Wert vom ADC als Wert für den Timer genommen das klapt auch. So einfach kann es sein! Jetzt müßte ich nur wissen wie genau die 3 Leitung vom Lüfter funktioniert was kommt da für ein Signal raus? Kommt ein Signal für eine Umdrehung? MfG Sebastian
Moin, Sebastian schrieb: > Da bin ich aber noch etwas überfragt wie > ich das anstelle,weil er ja 12V braucht.Würde er nur 5V brauchen hätte > ich den irgendwie über PWM gesteuert.Ich brauche zwar eigentlich nur > etwa die hälfte der möglichen Drehzahl des Lüfters,aber zum anlaufen > braucht er die 12V danach kann dann sofort runtergeregelt werden. Es klingt ja ein bißchen so, als ob dir die Hardware ansich etwas Probleme bereitet. Um von den 5V aus deinem Controller auf 12V zu kommen gibt es ein besonderes Teil: den Transistor :) ! Wie du das Ding dann zu verbauen hast steht (nicht nur) hier auf der Seite ganz gut erklärt. Sebastian schrieb: > Wenn > ich dann diese Hürde gemeistert habe,wollte ich irgendwie das Signal für > die Drehzahl über den Timer(Counter) zählen und dann > weiterverarbeiten.Bin ich auf dem richtigen Weg? Ich finde ja :) Sebastian schrieb: > Ich möchte ein Magnetrührer selber bauen, Das check ich nicht. Wie soll den der Lüfter, der die Magnete antreibt, die Temperatur beeinflussen? Das ist alles etwas durcheinander. Ich dachte die Beeinflussung der Temperatur geschieht über an- und- ausschalten der Heizplatte?! Dann wird die Temperatur aber nie "genau" sein (Stichwort Zweipunktregler, Hysterese). Bei den drei Lüfterleitungen kann man so pauschal erstmal nichts sagen. Erstmal müßte man wissen, was das genau für ein Lüfter ist. Bei drei Leitungen ist es wohl ein ganz normaler/älterer. Die Modernen haben ja z.T. vier Leitungen. Versorgung+, Masse, Drehzahlsignal vom Lüfter (Ist-Wert) und PWM-Eingang (Sollwert). Wenn du nur drei Leitungen hast entfällt der PWM-Eingang. Mit dem Tachosignal ist das wieder so eine Sache. Das ist bei diesen Lüftern nicht wirklich einheitlich. Ich hatte mal einen, der gab alle 180° einen Puls aus. Aber der Pegel war alles andere als sauber. Wenn du das genau wissen willst hilft nur ein Scope. Also, du hast zwei Sollwerte: 1. Drehzahl der Rührers (hat erstmal mit der Temperatur nichts zu tun!) 2. Soll-Temperatur Temperaturregler sollte kein Problem sein: PLatte an, Platte aus (Hysterese). Bei der Drehzahl: willst du die wirklich "regeln"? Reicht es nicht die Drehzahl von 0-100% einstelbar zu machen? Wenn Regelung: ein langsamer I-Regler sollte reichen...
Kann mir einer sagen wie ich am besten jetzt die Signale von Lüfter auswerten kann?Es kommen ja pro Umdrehung 2 Signale also muss ich schonmal auf jeden fall durch 2 teilen.Aber wie rechnet man am besten die Umdrehung pro Minute aus weil eine Minute will ich ja nicht warten
Also das ist ja nun mal alles andere als schwierig! Du kennst doch einen Dreisatz, oder? Du mußt doch einfach nur einen Timer laufen lassen. Durch die Prozessorfrequenz weißt du doch, wie lange der Timer braucht, um um 1 erhöht zu werden. Also, Zeit zwischen den Impulsen stoppen und einfach auf die Minute hochrechnen! Arbeite dich mal hier durch: http://www.mikrocontroller.net/articles/AVR-GCC-Tutorial/Die_Timer_und_Z%C3%A4hler_des_AVR und hier: http://www.mikrocontroller.net/articles/Festkommaarithmetik Gruß
Also ich habe den Lüfter mit den 3 Kabeln der gibt alle 180° ein Signal. Natürlich könnte ich den Lüfter auch einfach von 0-100% einstellen das würde auch funktionieren,aber ich möchte ja mit meinen Projekten dazulernen.Ich Programmiere ja mit Bascom,weil es relativ leicht ist mit den Bascom Funktionen schnelle Ergebnisse zu bekommen.Wenn mein Programm dann läuft schreib ich es komplett um (Rufe alle Register usw. manuell auf).Ich möchte irgendwann wenn ich Bascom behersche auf C umsteigen.Ich habe auch ganz wenig C Kenntnisse weil ich damit angefangen habe,aber ich fand es für den Einstieg zu schwer.Ich mache das ganze noch nicht so lange.Und bis jetzt kann ich nur die Grundfunktionen.Ich werde mich mal durch die Links lesen und das wird mir bestimmt weiter helfen.Also wie ich einen Transistor anschließe ist mir schon bekannt, da ich aber nicht soviel Ahnung von Elektronik habe dachte ich eigentlich das ein Transistor einfach nur die 12V durchleiten kann.Das dieser auch den Strom regeln kann ist mir neu (außer irgendwelche IC's).Dreisatz ist mir noch bekannt:) Also werde mich dann jetzt ans lesen machen.Sollten danach noch immer Fragen offen sein,darf ich mich bestimmt ja nochmal melden oder??
Also ich habe mich jetzt mal ein wenig da durchgelesen und wollte mal fragen ob ich das jetzt richtig gerechnet habe. Aufgabe möchte 1 Sek. errechnen. Also Takt 8Mhz/Prescaler (1024)= 781,25Khz 1/781,25=128us 1/128 =7812,5 Zählerschritte Timer1 16bit =65535 65535-7812,5= 57722,5 ab/aufrunden = 57723 Dann den Timer1 mit TCNT1=57723 vorladen. Ist das so richtig?
Jo, ich glaub das passt so. Aber das find ich sehr umständlich. Da hat ja jeder seinen eigenen Geschmack, aber ich würd es anders lösen. Es gibt ja grundsätzlich zwei Lösungsansätze, um auf deinen Drehzahl/Frequenz zu kommen. 1. eine definierte Zeit warten und Pulse zählen. Vorteil: du hast direkt die Drehzahl/Zeiteinheit vorliegen. Nachteil: du mußt immer deine Zeiteinheit abwarten. 2. du stoppst die Zeit, zwischen zwei Pulsen. Klarer Vorteil: du mußt nicht immer erst deinen Messzeitraum von 1. abwarten, sondern kannst mit jedem neuen Puls die Drehzahl errechnen. Das ist auch der "Nachteil": Mit der gestoppten Zeit mußt du das ganze dann auf die genaue Drehzahl/Zeiteinheit umrechnen. Das sollte aber kein Problem sein (hoff ich). Der Timer1 kann im CTC-Mode betrieben werden, der ist hier dein Freund. Dann sparst du dir das Vorladen :) . Und ich würd mir eine "einfachere" Zeiteinteilung einfallen lassen. Wenn du z.B. bei 8MHz den Vorteiler 8 benutzt weißt du ja schon, daß er alle 1 µs +1 macht. Da kommst du dann aber sehr schnell auf sehr große Zahlenwerte (bei niedrigen Drehzahlen). Jetzt stell dir mal vor, daß dein Timer immer bei 250 überläuft. Ein Interrupt tritt also alls 250 µs oder alls 0,25 ms auf. Jetzt Zähl doch einfach mal die Interrupts zwischen zwei Pulsen. Durch die geschicke Zeiteinteilung sind die Werte dann auch leichter zu verstehen. Jetzt hast du z.B. 234 Interrupts zwischen den Pulsen. Also sind 234 * 0,25 ms vergangen, alse 58,5 ms. Und so oft, wie die Zahl jetzt in 1s reinpasst, daß ist deine Drehzahl/Sekunde :) . Klar soweit?! Übrigens: http://www.google.de/search?hl=de&safe=off&client=firefox-a&hs=eXT&rls=org.mozilla:de:official&q=danke+sagen&revid=401858695&sa=X&ei=q_MyTduWJdCOswaTrOT4CQ&ved=0CCUQ4QIoAQ Gruß
Also so einiger maßen verstehe ich das schon aber nicht so richtig. Ich würde schon die Variante bevorzugen die Zeit zu stoppen zwischen den 2 Impulsen. Aber wär vielleicht jemand so nett mir das genauer zu erklären.Ich steh irgendwie total auf dem Schlauch. MfG Basti
Würde es eventuell auch so gehen? Wenn ich den Timer auf Prescale 8 stelle würde ja bei 8Mhz der Takt 1us sein.Dann in der Routine den Timer auf 0 stellen Und anfangen zu zählen dann im Programm die Variable Zahlstand aufrufen und umrechnen auf eine Minute 'Timer1----------------------------------------------------------------- ----------- Config Timer1 = Counter , Prescale = 8 , Edge = Falling On Timer1 Enable Timer1 Start Timer1 Timerroutine: Timer1 = 0 Zahlstand = Timer1
Also ehrich, ich hab dir die Formel doch schon auf dem Silbertablett serviert! Annahme: Controller läuft bei 8 MHz, Vorteiler des Timers 8(NUR BEISPIEL, weil einfach zu rechnen!) Über das Format der Zahlen mußt du dir selbst Gedanken machen... -> Timer zählt mit 1 MHz (1 µs pro Zählschritt). Erstes Signal kommt, Timer starten. Timer-Vergleichswert bei 249 -> 250 Zählschritte bis ISR-Aufruf (bitte korrigieren falls falsch). Es dauert also 250 * 1 µs ( In der ISR zählst du jetzt in einer Variablen die Aufrufe des Interrupts. Jetzt kommt irgendwann das nächste Signal -> Timer stoppen. Jetzt steht in der Variablen z.B. 234 drin. 234 mal sind also 250 µs verstrichen -> 234 * 250 = 58500 µs = 58,5 ms. Jetzt steht aber ja noch ein Rest im Timer. Der hat ja immer hochgezählt. Auch wenn er keinen Interrupt ausgelöst hat, dann beinhaltet er aber ja noch einen Zählwert, bei dem dann durch das zweite Signal gestoppt wurde. Der Restwert sei 120. Durch unseren Vorteiler wissen wir, daß dieser Wert direkt eine Zeit in µs repräsentiert. Diesen Wert mit berücksichtigen: 58500 + 120 = 58620 µs = 58,62 ms. Und jetzt: siehe oben!!! Wie kriegt man raus, wie oft eine Zahl, in eine Andere reinpasst? Division! Denkweise: für eine Umdrehung brauch das Ding 58,62 ms (oder auch 0,05862 s). Das heißt ich schaffe in 1s... ähm... 1 / 0,05862 = 17,06 Umdrehungen! Pro Minute sind das also... ähm... 17,06 * 60 = 1023,5 Umdrehungen! Und wenn wir berücksichtigen, daß pro Umdrehung 2 Signale kommen teilen wir nochmal durch 2 und sind dann bei 511,77. Das ist doch echt mal kein Stoff aus dem Mathe-LK :) . http://www.google.de/search?q=danke+sagen&ie=utf-8&oe=utf-8&aq=t&rls=org.mozilla:de:official&client=firefox-a Gruß
Nur eine Frage habe ich noch wie Lese ich die Werte jetzt am besten ein? Das ist eigentlich mein einziges Problem den rest verstehe ich. MfG Sebastian Und PS vielen dank für die Hilfe
Konkretisiere deine Fragen bitte. Mit der Frage
> wie Lese ich die Werte jetzt am besten ein?
kann keiner was anfangen. Wie ein Signal (ich vermute, daß du das
meinst) eingelesen werden muß hängt nur davon ab, wie das Signal
aussieht. Wenn du nicht weißt, was du messen willst brauchst du gar
nicht erst mit dem Messen anzufangen. Zu fast allen Hardware-Fragen im
Bezug darauf, wie ein Signal auszusehen hat, gibt das Datenblatt
Auskunft.
Die Zauberformel hier im Forum lautet fast immer "Konkrete Frage,
konkrete Antwort", und Eigeninitiative. Ist nicht bös gemeint, aber
versuch nochmal selbst dahinter zu kommen...
Gruß
Ich habe jetzt noch eine Lösung gefunden.Womit ich aber Probleme habe ist zu wissen wo das Programm wieviel Zeit braucht.Klar mit dem Timer ist mir das klar.Aber wenn ich jetzt z.B. den Timer overflow auf 1us stelle.Dann aber die Werte z.B. mit ICP oder Int auslese haben ja die eine eigende Routine und mit meiner Timer Routine nichts zu tun.Und da bin ich am verzweifeln.Woher weiß ich jetzt wann der Interrupt auftritt?Ich habe darüber auch nicht wirklich was in meinem Buch stehen oder irgendwo eine vernünftige erklärung gefunden.Was ich auch nicht wirklich verstehe ist wenn ich den Timer wieder auf 1us stelle und dann den Timer auf 0 setze Timer starte Wert auslese und Timer wieder stoppe dann mißt doch der Timer garnicht mehr genau auf 1us,oder nicht? Na ja mein Code sieht jetzt auf jeden fall so aus,das einzige was jetzt noch nicht gemacht ist,ist die Umrechnung auf RPM/min. $regfile = "m8def.dat" $crystal = 8000000 Declare Function Lopulse() As Word Dim Value As Word Config Lcd = 16 * 2 Config Lcdbus = 4 Config Lcdpin = Pin , Db4 = Portd.4 , Db5 = Portd.5 , Db6 = Portd.6 , Db7 = Portd.7 , E = Portd.3 , Rs = Portd.2 Cursor Of Config Pinb.0 = Input Set Portb.0.0 Inputpin Alias Pinb.0 Config Timer1 = Timer , Prescale = 8, On Timer1 Overflow_isr Nosave Enable Timer1 Enable Interrupts Do Value = Lopulse() Cls Locate 1 , 1 Lcd Value ; "Wert" Waitms 20 Loop End Function Lopulse() As Word While Inputpin <> 0 : Wend Tcnt1 = 0 Start Timer1 While Inputpin = 0 : Wend Stop Timer1 Lopulse = Tcnt1 End Function Lopulse() Overflow_isr: !push r24 Stop Timer1 Tcnt1 = 0 !pop r24 Return
Sebastian schrieb: > Ich habe jetzt noch eine Lösung gefunden.Womit ich aber Probleme habe > ist zu wissen wo das Programm wieviel Zeit braucht. Im Idealfall brauchst du das gar nicht wissen. > Klar mit dem Timer > ist mir das klar. Na dann passt es doch. Das ist die einzige Zeit, die du wirklich wissen musst. > Aber wenn ich jetzt z.B. den Timer overflow auf 1us > stelle.Dann aber die Werte z.B. mit ICP oder Int auslese haben ja die > eine eigende Routine und mit meiner Timer Routine nichts zu tun. Macht ja nichts. > Und da > bin ich am verzweifeln.Woher weiß ich jetzt wann der Interrupt > auftritt? Musst du nicht wissen. Genau dazu gibt es den Interrupt Capture. Der erledigt das wegspeichern des Timer-Wertes in Hardware. Du brauchst dir nur noch die Zählerwerte von der Capture Einheit zu holen. Bei denen hast du die Gewissheit, dass sich genau im Moment des Pulses weggespeichert wurden. Selbst wenn du dir diese Ergebnis in paar µs später abholst. > Ich habe darüber auch nicht wirklich was in meinem Buch stehen > oder irgendwo eine vernünftige erklärung gefunden.Was ich auch nicht > wirklich verstehe ist wenn ich den Timer wieder auf 1us stelle und dann > den Timer auf 0 setze Im Idealfall lässt du den Timer durchlaufen. Stell es dir wie eine Uhr vor: Dein Kumpel schreit 'Jetzt'. Du schaust auf deine Uhr und siehst, dass der Sekundenzeiger auf 18 steht. Das merkst du dir. Nach einer gewissen Zeit schreit den Kumpel wieder 'Jetzt'. Blick auf die Uhr: Der Sekundenzeiger steht auf 42. Wieviele Sekunden sind also zwischen den beiden 'Jetzt' vergangen? 42 - 18 = 24 Zu keinem Zeitpunkt musstest du die Uhr anhalten oder auf 0 stellen und trotzdem hast du die Information die du willst. Das einzige worauf du aufpassen musst, ist wenn der Sekundenzeiger 1 oder mehrere male über die 60 drüberkommt. Dann musst du dein Ergebnis entsprechend korrigieren. Ist aber nicht wirklich schwer. > Timer starte Wert auslese und Timer wieder stoppe > dann mißt doch der Timer garnicht mehr genau auf 1us,oder nicht? Und wozu brauchst du so eine Genauigkeit? Bei einem Rührermotor? Meiner Meinung nach werden viel zu viele Probleme damit angegeangen, dass Timer unnötigerweise auf viel zu tiefer Ebene vorgeladen, 0-gesetzt, gestartet-gestoppt oder händisch ausgelesen werden. Alles Dinge, die man beim Einsatz der eingebauten Hardware und dafür lesen des Datenblatts und benutzen der kleinen grauen Zellen gar nicht braucht.
Also würdest Du einfach den Timer einstellen als timer und laufen lassen dann eine Interroupt Routine Int0 schreiben wo dann drin steht startwert=timer1 Hi low flanke abwarten endwert=timer1 startwert-entwert=value value*?=rpmmin (das dann im Hauptprogramm) return Richtig? MfG Sebastian
Sebastian schrieb: > Also würdest Du einfach den Timer einstellen als timer und laufen lassen > dann eine Interroupt Routine Int0 schreiben wo dann drin steht > > startwert=timer1 > Hi low flanke abwarten nein In dem Moment, in dem du in einer Interrupt Routine das Wörtchen 'warten' gebrauchst (ausser bei wirklich kleinen Zeiten, aber den Fall hast du nicht), bist du schon auf dem Holzweg. Du kriegst doch 2 Interrupts hintereinander, für jede halbe Umdrehung einen. In jedem Interrupt brauchst du nur nachsehen, wie sich der jetzige Timerwert in Bezug auf den Timerwert im letzten Interrupt verhält. Drum hat auch in meinem Realwert-Beispiel dein Kumpel "jetzt" gerufen. Ich hab da nicht geschrieben, dass du ab dem ersten Ruf an seinen Lippen klebst und nur auf den 2.ten Ruf wartest. Kumpel ruft und du siehst auf die Uhr. Das ist das Pendant zum Interrupt Aufruf mit Timer auslesen. Und ja. Es gibt Variablen, in denen man sich Werte solange aufheben kann, bis man sie dann tatsächlich braucht.
Ah ich glaube ich hab es verstanden.Da Int0 ja bei jeden feststellen einer Änderung am Pin ins Unterprogramm geht brauche ich ja garnicht auf ein Signal warten sondern nur den Timerwert speichern.Diesen dann als sagen wir mal wertneu und wertalt speichern und vergleichen.
Sebastian schrieb: > Ah ich glaube ich hab es verstanden.Da Int0 ja bei jeden feststellen > einer Änderung am Pin ins Unterprogramm geht brauche ich ja garnicht auf > ein Signal warten sondern nur den Timerwert speichern.Diesen dann als > sagen wir mal wertneu und wertalt speichern und vergleichen. Im Prinzip. Und wenn du jetzt noch die Forderung mit dazu nimmst, dass das Auslesen des Timers möglichst zeitnah mit dem tatsächlichen Auftreten des Signals passieren soll und daher von der Hardware gemacht werden soll, dann hast du den Input Capture Interrupt des Timers entdeckt. Anstelle das du dir einen Int0 auslösen lässt und selbst danach irgendwann den Timer ausliest, erledigt die Hardware beides in einem Aufwasch: Die Signaländerung wird detektiert UND gleichzeitig wird der aktuelle Timerwert in Hardware weggespeichert UND ein entsprechender Interrupt wird generiert. Und weil das so ist, braucht man die tatsächliche Programm-Laufzeit vom Auftreten des Signals bis dann der Timer in der ISR ausgewertet wird, gar nicht mehr wissen. Allerdings muss man auch sagen, dass die Programmlaufzeit vom Auftreten des Signals bis du dann den Timer ausliest im Grunde uninteressant ist. Deine Forderung nach 1µs braucht nämlich kein Mensch. Damit könntest du die Drehzahl auf 1 Millionstel Umdrehungen PRO SEKUNDE feststellen. Ich bezweifle, dass dein Rührwerk überhaupt so gleichmässig dreht, dass das Sinn macht. Wenn überhaupt, wird sich bei dir das meiste im Millisekundenbereich abspielen. Und 1 Millisekunde ist für einen µC eine laaaange Zeit.
Kannst Du mir noch vielleicht sagen in welchen register start endwert gespeichert wird.Dann hätte ich alles was ich brauche. Vielen dank für deine hilfe
Sebastian schrieb: > Kannst Du mir noch vielleicht sagen in welchen register start endwert > gespeichert wird.Dann hätte ich alles was ich brauche. Sei mir nicht böse. Aber das wichtigste was du brauchst, ist das Datenblatt zu deinem Prozessor. Denn da steht das alles drinnen. Und deswegen möchte ich die Frage hier nicht beantworten. Denn der Glaube: Ich brauch das Datenblatt nicht, weil ich eh in BASCOM arbeite ... das ist ein Irrglaube.
Kein Problem bin dir nicht böse.Ich habe es jetzt so gelöst Oncapture: Wcapture = Capure1 Wzaehler = Wcapture - wcapturealt Wcapturealt = Wcapture Return
So habe es jetzt nochmal geändert mein ganzes Programm sieht bis jetzt so aus.Jetzt muss ich noch ein PWM Signal erzeugen für den Motor und natürlich den Sensor für die Temperatur einfügen.Außerdem noch die Umrechnung in die Drehzahl.PWM kann ja mit timer1 und 2 erzeugt werden könnte ich jetzt noch diese mit timer1 machen oder ist es sinnvoll timer2 zu benutzen. $regfile = "m8def.dat" $crystal = 8000000 $baud = 9600 Dim 1count As Long At &H60 Dim Wcountlo As Word At &H60 Overlay Dim wcounthi as word at &h62 overlay Dim Grad As Word Dim Rpm As Word On Icp1 Oncapture On Ovf1 Onoverflow 'Display Einstellungen----------------------------------------------------------- ------------------------------- Config Lcd = 16 * 2 Config Lcdbus = 4 Config Lcdpin = Pin , Db4 = Portd.4 , Db5 = Portd.5 , Db6 = Portd.6 , Db7 = Portd.7 , E = Portd.3 , Rs = Portd.2 Cursor Off 'ports einstellungen----------------------------------------------------------- --------------------------------- Config Portb.1 = Output 'Test Output Motor Config Portc.0 = Input 'ADC0 Input Config Portc.1 = Input 'ADC1 Input Config Portb.3 = Output 'Outpu Relais Wärmeplatte Config Portb.0 = Input Portb.0 = 1 'Timer1----------------------------------------------------------------- --------------------------------------- Config Timer1 = Timer , Prescale = 1024 , Capture Edge = Falling , Noise Cancel = 1 Enable Timer1 Enable Icp1 Enable Interrupts 'ADC-------------------------------------------------------------------- --------------------------------------- Config Adc = Free , Prescaler = 4 , Reference = Internal Start Adc '----------------------------------------------------------------------- --------------------------------------- 'Hauptprogramm Do Disable Interrupts Cls Locate 1 , 7 'Nur zum test Lcd 1count ; "Wert" wcounthi=0 Enable Interrupts Grad = Getadc(0) / 6 'ADC0 Einlesen Locate 1 , 1 Lcd Grad ; "ß" Rpm = Getadc(1) 'ADC1 Einlesen Locate 2 , 1 Lcd Rpm ; "Rpm" Waitms 30 If Grad < 60 Then Portb.3 = 1 Else Portb.3 = 0 End If Loop '------------------------------------------------------------------ Oncapture: Timer1 = Timer1 - capture1 Wcountlo = Capture1 Return Onoverflow: Incr Wcounthi Return MfG Sebastian
Habe da mal eine frage zum PWM. Ich benutzte jetzt den Timer2 so eingestellt Config Timer2 = Pwm , Prescale = 8 , Compare Pwm = Clear Up , Pwm = On Enable Timer2 Start Timer2 im Programm habe ich dann Motorpwm = Rpm / 4 Ocr2 = Motorpwm Jetzt habe ich aber das Problem das wenn ich ungefähr bei einen Drittel bin (Poti) das der Strom wieder fällt dann aber wieder ansteigt.Woran kann das liegen?
Kann mir jemand sagen wie ich 0,000128 in eine VARIABLE kriege? Weil ich rechne jetzt 1x Umdrehung = Takte Timer*0.000128s >(dauert ein Takt) UmdrehungMin.= Minute(60)/Umdrehung ist doch richtig so oder?
Sebastian schrieb: > Kann mir jemand sagen wie ich 0,000128 in eine VARIABLE kriege? Wenn es irgendwie geht, willst du das gar nicht. Man kann zb mit 0.75 multiplizieren, indem man zuerst mit 3 multiplizert und dann durch 4 dividiert. Man muss nur aufpassen, dass kein Zwischenergebnis entsteht, welches für den Datentyp zu gross ist. > Weil ich rechne jetzt > > 1x Umdrehung = Takte Timer*0.000128s >(dauert ein Takt) > UmdrehungMin.= Minute(60)/Umdrehung Forme die Umrechnung um. Das kann man auch anders berechnen.
Moin, darum hab ich oben weiter (glaub ich) auch schon auf den Artikel zur Festkommaarithmetik verwiesen. Du kriegst die Zahl 0,000128 nicht SO in eine Variable, die für den Controller angenehm zu verarbeiten ist. ABER: wer schreibt dir denn vor, daß du in "Sekunden" rechnen mußt? Wenn du alles z.B. in Microsekunden rechnest hast du auf einmal 128 da stehen :) . Kein Komma, nur die Tatsache, daß eine Sekunde aus 1000000 µs besteht. Mit einem ähnlichen beispiel steht es hier auch irgendwo, wie man eine eingelesene Spannung am ADC in einen Wert in Volt umwandelt. Du rechnest einfach in Millivolt, und schon verschwinden die Kommas. Und für die Ausgabe: kein Problem! Dann machst du (bei den Millivolt) erst "durch 1000", dann kommt z.B. "3" heraus, dann gibst du ein Komma aus (einfach so) und dann gibst du deine "Millivolts % 1000" aus. Alles wird gut...
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.