Forum: Mikrocontroller und Digitale Elektronik Drehzahlregelung für DC-Motor


von Rudolf G. (Gast)


Lesenswert?

Hi Leute,
ich befasse mich gerade mit folgendem Problem:

Ich habe hier einen kleinen 12V DC-Motor.
Den steuere ich mit einem Mikrocontroller über eine H-Brücke an, sodass 
er in beide Richtungen drehen kann. Mittels einer PWM kann ich auch die 
Drehzahl einstellen.
Bisher habe ich das jetzt so gemacht, dass ich die Spannung am Abgriff 
eines Potis AD-gewandelt habe, und dann diesen Wert als Vorgabe für die 
PWM genommen habe. Das geht natürlich; der Motor lässt sich von 0% bis 
100% in der Drehzahl einstellen.
Das dumme ist nur, dass wenn der belastet wird, die Drehzahl natürlich 
sinkt!
Ich habe mir jetzt überlegt, ob man das nicht irgendwie regeln kann. An 
dem Motor ist ein Encoder angebracht, der liefert rechteckige Impulse 
(um 90° verschoben). Damit lässt sich die Drehrichtung und die Drehzahl 
bestimmen.
Also, ich habe mir überlegt: man schaut sich irgendwie das 
Ausgangssignal vom Encoder an, bestimmt daraus die Drehzahl, und 
vergrössert oder verkleinert danach den Tastgrad der PWM so, dass die 
Drehzahl ihren Sollwert erreicht. Geht das? Könnt ihr mir einen Tipp 
geben, wie ich das am besten anfange?
Ich verwende einen 8051 Controller, genauer einen AT89C4051.

Gruss

von C. H. (_ch_)


Lesenswert?

Rudolf G. schrieb:
> Also, ich habe mir überlegt: man schaut sich irgendwie das
> Ausgangssignal vom Encoder an, bestimmt daraus die Drehzahl, und
> vergrössert oder verkleinert danach den Tastgrad der PWM so, dass die
> Drehzahl ihren Sollwert erreicht. Geht das?
ja, ganz genau so wird das gemacht

>Könnt ihr mir einen Tipp geben, wie ich das am besten anfange?
> Ich verwende einen 8051 Controller, genauer einen AT89C4051.
entweder Impulse pro Zeit messen, oder die Impulsbreite und danach auf 
die Drehzahl hochrechnen

Gruß
Christian

von Rudolf G. (Gast)


Lesenswert?

Hallo Christian,

sehr schön. Danke für deine schnelle Antwort!
Wenn ich jetzt die Impulsbreite kenne, wie kann ich dann daraus auf den 
PWM-Tastgrad hochrechnen? Muss ich dazu die Kennlinie vom Motor 
aufnehmen Tastgrad vs. Drehzahl und das dann in einer Tabelle ablegen? 
Oder gibt es eine elegantere Methode`?

von Stefan M. (Gast)


Lesenswert?

Du solltest Dich mit Regelungstechnik beschäftigen. Als Ansatz:

Deine Sollgröße ist die gewünschte Drehzahl, die Stellgröße die PWM und 
die Führungsgröße ist die gemessene Drehzahl. Du kannst auch die 
Drehzahl einfach durch die Pulsbreite ersetzen, dann gibst Du die 
Pulsbreite vor. Für die Regelung der Drehzahl kannst Du einen 
PID-Regler nehmen. Sourcecode findest Du ziemlich viel im Netz. Die 
Reglerparameter (P, I und D) kannst Du nach der Methode nach 
Ziegler-Nichols bestimmen.

Zur Vereinfachung habe ich Dir die Suchbegriffe für eine Suchmaschine 
Deiner Wahl unterstrichen.

mfg, Stefan.

von C. H. (_ch_)


Lesenswert?

Hallo Rudolf,

'auf den PWM-Tastgrad hochrechnen' macht deine Drehzahlregelung.
Für den Istwert der Regelung musst du nur die Auflösung deines 
Impulsgebers wissen, damit du auf die Drehzahl hochrechnen kannst.

Das mit deiner Tabelle würde theoretisch auch funktionieren, ist aber 
viel zu aufwändig und funktioniert bei weitem nicht so gut wie eine 
richtige Regelung.
Gerade wenn du schon einen Sensor hast bietet sich eine Regelung nahezu 
an!

von Rudolf G. (Gast)


Lesenswert?

@Stefan
Vielen Dank. Ich suche mal hier im Forum nach den PID-Reglern.
Ich muss allerdings sagen, dass ich während meiner Ausbildung die 
Regelungstechnik nur gestreift habe; wir haben lediglich kurz 
angeschaut, wie man mit OpAmps Regler baut, und was die für Kennlinien 
haben.
Aber ich denke, ihr könnt mir sicher Hilfestellung geben, beim bauen 
eines digitalen Reglers auf einem Mikrocontroller, oder?

@Christian
Ja, wie bereits Stefan angedeutet hat, wird dann wohl eine PID-Regelung 
die bessere Wahl sein. Die werde ich auch versuchen, zu imlementieren!

von C. H. (_ch_)


Lesenswert?

Rudolf G. schrieb:
> Ja, wie bereits Stefan angedeutet hat, wird dann wohl eine PID-Regelung
> die bessere Wahl sein. Die werde ich auch versuchen, zu imlementieren!
Du kannst dir ja das Leben auch leicht machen und den Regler 
schrittweise entwerfen.
Zuerst P-Regler, dann PI-Regler, wenn's immer noch genügt dann noch den 
D-Anteil dazu.
Die Frage ist nur ob dein Antrieb wirklich so dynamisch sein muss, dass 
du gleich einen PID-Regler brauchst.

Viel Erfolg und Spaß :-)

Gruß
Christian

von Rudolf G. (Gast)


Lesenswert?

@Christian
jaa, der Antrieb sollte schon einigermassen dynamisch sein. Ich will 
halt ne einigermassen exakte, und vor allem konstante, einstellbare 
Drehzahl. Und wenn die Last sich ändert, dann darf die Drehzahl nicht 
allzu viel überschwingen.

Hast du vielleicht einen kleinen Code, wo ich ansatzweise mal sehen 
kann, wie sowas implementiert wird?
Hier finde ich nur komplette PID-Regler, die mir auf den ersten Blick 
schon etwas kompliziert ausschauen.

von Olaf (Gast)


Lesenswert?

> Hier finde ich nur komplette PID-Regler, die mir auf
> den ersten Blick schon etwas kompliziert ausschauen.

Also ich finde ja das ein PID Regler sehr einfach aussieht.
Das schwierige ist gerade das was man nicht sieht, also die
Bestimmung der Koeffizienten. Und ganz besonder wenn sich deine
Regelstrecke noch aendert.
Es ist daher leider absolut unumgaenglich das du dich ernsthaft mit
Regelungstechnik auseinandersetzt wenn du soetwas fuer dein System
implementieren willst und abschreiben ist bei Reglern normalerweise
nicht zielfuehrend.

Olaf

von Rudolf G. (Gast)


Lesenswert?

Hey, ich hab hier einen Thread gefunden, wo jemand das mit den Reglern 
ein bisschne erklärt hat:

> P-Regler: Nimm den Temperaturfehler, multipliziere ihn mit dem
> "P-Anteil" und gib das zum Ausgang.
> I-Regler: Nimm den Temperaturfehler, integriere ihn über die Zeit (also
> aufsummieren), multipliziere das mit dem "I-Anteil" und gib das zum
> Ausgang.
> D-Regler: Nimm den Temperaturfehler, differentiere ihn (also jeweils den
> Unterschied zweier aufeinanderfolgender Samples berechnen),
> multipliziere das mit dem "D-Anteil" und gib das zum Ausgang.

Das kommt mir irgendwo her ja bekannt vor!
Also, hab ich kurz mein Visual Studio gestartet, und mir vorerst mal für 
den PC eine Konsolenanwendung gebastelt, die das macht. Der Code sieht 
wie folgt aus:


  int drehzahl_ist = 0;
  int drehzahl_soll = 20;
  int regler_ausgang = 0;

  int e;
  int ealt = 0;
  int esum = 0;

  int p_ant = 1;
  int i_ant = 1;
  int d_ant = 1;

  int p;
  int i;
  int d;
  while(1)
  {
      e = drehzahl_soll - drehzahl_ist;
      p = e * p_ant;
      esum = esum + e;
      i = esum * i_ant;
      d = d_ant * (e - ealt);
      ealt = e;
      regler_ausgang = p + i + d;
  }

und nun die Frage:
ist das korrekt so`? Wenn ich das auf den Mikrocontroller portiere, 
werde ich dann natürlich in die Variable "drehzahl_ist" die mittels 
Sensor ermittelte Drehzahl reinschreiben. In "drehzahl_soll" kommt ein 
mittels Poti und ADC einstellbarer Wert. Und "regler_ausgang" ist 
natürlich dann der Tastgrad meiner PWM.

Na, klappt's so?

von Rudolf G. (Gast)


Lesenswert?

Ach ja, ich muss hier noch anmerken, dass ich dann natürlich die 
Konstanten "p_ant", "i_ant" und "d_ant" entsprechend auf den Motor 
anpassen muss. Die legen ja den jeweiligen Anteil fest.

von Olaf (Gast)


Lesenswert?

Im Prinzip ist das so richtig. Ich wuerde dir also empfehlen
einfach mal anzufagen und Erfahrungen zu sammeln. :-)

Es gibt noch ein paar Dinge du du bedenken solltest:

Notwendige Abtastfrequenz deines Eingangs damit keine Information
verloren geht.

Notwendige Frequenz mit der dein Regler laeuft. Die kannst du nicht
einfach so aendern weil das auch ein Regelparameter ist.

Maximalwerte fuer I-anteil.

Ueberlege dir vorher GENAU wie gross deine Eingangs und Ausgangsgroessen 
werden und welche Zwischenwerte bei den Berechnungen des Reglers so 
rauskommen. Du wirst dann uebrigens feststellen das man so einen Regler 
zwar durchaus in einem 8Bit-Controller bauen kann, aber es doch eine 
sehr dankbare Aufgabe fuer 16bit-Controller ist.

Und danach kannst du dich dann Sonderfaellen hingeben. Zum Beispiel der 
Verwendung unterschiedlicher Reglerparameter bei bestimmten Drehzahlen 
oder Lastsituationen.

Und es koennte auch einfacher sein erst einen I-Regler fuer den 
Motorstrom zu bauen und dem dein Drehzahlregler zu ueberlagern. Oder du 
linearisiert die Regelstrecke ueber ein Array falls du genug Platz im 
Flashrom hast.

Und dann kommt als Zusatzboni so sachen wir Losbrechmoment beim 
anfahren, Spiel in einem Getriebe, schwingungen im Antrieb wenn du 
federnde Elemente in deiner Mechanik hast, Alterung, usw....

Regelungstechnik ist interessant, aber nicht einfach.

Olaf

von Rudolf G. (Gast)


Lesenswert?

Hallo Olaf,
danke für deine Ausführungen!
sehr interessant, die ganze Thematik.
Gibt es eine Faustregel, nach der ich die notwendige, minimale 
Abtastfrequenz bestimmen kann?

Und:
Was ich noch feststelle ist, wenn ich für die P- I- und D-Anteile ganze 
Zahlen grösser 1 verwemde, dann wird mein regler_ausgang sehr schnell 
sehr gross. Aber die ganzen Variablen möchte ich eigentlich höchstens in 
int-Werten speichern, und die haben bei meinem 8051 halt 16 Bits (und 
nicht wie auf dem PC 32). Kann ich das ganze irgendwie sinnvoll 
skalieren?

Weiter habe ich noch das Problem, dass mein Sollwert, den ich vorgebe, 
eine Zahl zwischen 0 und 1023 ist (10 Bit ADC). Die PWM wird aber nur 
über einen Wert zwischen 0 und 255 bestimmt! Auch die Drehzahl hat 
wieder einen anderen Zahlenbereich. Wie kann ich denn das ganze 
skalieren, dass am regler_ausgang nie mehr als 255 raus kommt? kann ich 
das dem Regler irgendwie "sagen", sodass er "weiss", dass er gar nie 
über 255 raus kommen kann?

von Stefan M. (Gast)


Lesenswert?

Den Tip mit dem Schrittweisen entwickeln fand ich gut. Mach doch erst 
mal einen P-Regler. Der ist sehr einfach.

1) Rechne die Differenz zwischen der Soll-Drehzahl und der Ist-Drehzahl 
aus
2) der neue PWM-Wert ist die Differenz Mal einer Konstante (P)

Die Abtastfrequenz mußt Du möglichst konstant machen. Für einen Motor 
würde ich zunächst mal 1kHz nehmen. Das sollte Dein 8051 locker 
schaffen. Damit hast Du schonmal die Hälfte von einer verünftigen 
Regelung. Beim P-Regler brauchst Du Dir auch keine Gedanken machen, daß 
Wertebereiche überschritten werden. Es ist eben nur eine einfache 
Multiplikation.


Du mußt Dich jetzt auch nicht mit den Grundlagen der Regelungstechnik 
befassen, das ist verschwendete Zeit. Zumal die Mathematik ziemlich 
abschreckend sein kann. Für einen PID-Regler kann man ziemlich einfach 
die gute Regelparameter finden, mit Ziegler-Nichols.

mfg, Stefan.

von avr (Gast)


Lesenswert?

Für Reglerfragen empfehle ich gerne diese Erklärung:

http://www.rn-wissen.de/index.php/Regelungstechnik

Bei einem Motor ist die Einstellung über die Erprobung
meist ausreichend.

Mein Tip: mach dir noch einen F/U-Wandler als Testgerät, dann
kannst du die Drehzahl als Spannung auf dem Oskar darstellen.
Damit sieht man das Regelverhalten wie in den Darstellungen.

gruß avr

von Rudolf G. (Gast)


Lesenswert?

Hallo,
vielen Dank für den interessanten Link. Und auch für deine Ausführungen, 
Stefan.
Ich versuche das jetzt mal umzusetzen.
Allerdings taucht bei mir grade ne Frage auf.
Und zwar:
nehmen wir an, ich regle die Drehzahl auf 100 U/min.
Jetzt wird der Motor stark belastet; der Regler regelt das natürlich 
aus, und alles ist okay. Nun verschwindet aber die Belastung wieder; der 
Motor dreht jetzt halt ein bisschen schneller, sagen wir mit 150 U/min. 
Jetzt will der Regler das ja auch ausregeln, aber dazu müsste er den 
Motor noch bremsen können! Wie implementiere ich eine solche bremse am 
besten?
Mir ist klar, dass ich den Motor bremsen kann, wenn ich beide Lowside- 
oder Highside Mosfet einschalte. Aber wie detektiere ich einen solchen 
Fall?
Da stehe ich momentan noch auf dem Schlauch. Ansonsten denke ich, habe 
ich soweit begriffen, wie das ganze funktioniert.

von avr (Gast)


Lesenswert?

Normalerweise braucht man keine Bremse.
Wenn man den Motor nicht mehr ansteuert wird die
Drehzahl automatisch durch die Mechanik kleiner.
Es wird ja etwas angetrieben und da entstehen Verluste.

von Gast (Gast)


Lesenswert?

>Den steuere ich mit einem Mikrocontroller über eine H-Brücke an, sodass
>er in beide Richtungen drehen kann.

Damit hast Du auch eine Bremsfunktion. PWM -> 0: Motor steht!

von Klaus F. (kfalser)


Lesenswert?

> Mir ist klar, dass ich den Motor bremsen kann, wenn ich beide Lowside-
> oder Highside Mosfet einschalte. Aber wie detektiere ich einen solchen
> Fall?

Dazu solltest Du wirklich dich ein bischen mit Regelungstechnik 
gefassen.
Das, was Du vorgibst (in deinem Fall den Wert für die PWM), nennt man 
Stellgröße.
Wenn der Regler sagt, dass die Stellgröße negativ ist, dann heißt das in 
Deinem Fall: "bremsen". Nicht alle Endstufen können diesen 
Betriebsmodus, man  nennt soetwas 4 Quadranten Regler.

Der Rest ist Regelungstechnik, d.h. dreht der Motor zu langsam oder zu 
schnell dann kann der Regler ihn erst mit einer gewissen Verzögerung auf 
die Soll-Drehzahl zurückregeln. Dies nennt man Einschwingverhalten und 
hängt unter anderen von der Dämpfung und Motorlast ab.
Der Motor selbst kann ja auch nicht sofort von einer Drehzahl zur 
anderen springen, sondern ändert seine Drehzahl kontinuierlich zur Last.

von Gast (Gast)


Lesenswert?

>Der Motor selbst kann ja auch nicht sofort von einer Drehzahl zur
>anderen springen, sondern ändert seine Drehzahl kontinuierlich zur Last.

Das ist genau der Punkt an dem man etwas aufpassen sollte. Wenn der 
Motor etwas größer ist(so ab 20W reicht schon), und man dann eine 
direkte Drehrichtungsumkehr vorgibt können in abhängigkeit von der 
Spannungsquelle schon ganz beachtliche Ströme fließen. Bei 12V und 20W 
Motor könenn das schon mal leicht 60A werden. Damit hab ich mir schon n 
paar Mosfets zerstört. Verhindern kann man das ua. mit einer 
unterlagerten Stromregelung. Dann gibt der Drehzahlregler nicht direkt 
die PWM für die Mosfets vor sondern den Sollwert für den Stromregler. 
Und der Stromregler stellt dann die PWM. Das hat neben den 
Sicherheitsfunktionen auch noch Regeleungstechnisch große Vorteile, da 
man damit das dynamischere System direkt regeln kann und nicht erst den 
Umweg über die Drehzahl machen muss.

von Rudolf G. (Gast)


Lesenswert?

Hmm, das mit der Bremse werde ich vorerst noch weg lassen.
Zuerst soll mein PID-Regler funktionieren! Das versuche ich grade zu 
programmieren. Es geht so halbwegs.... ;-)
Ich meld' mich dann wieder.

von Albert D. (albert32)


Lesenswert?

Hallo, ist zwar in Basic...

Bascom Beispiel von "ELEKTOR"
Ein Permanent-Magnet soll mittels eines Elektromagneten genau so stark 
angezogen werden, dass er in der Schwebe verharrt.
Die Stellgröße soll hier je nach System gedämpft wirken. Das Verhalten 
des Reglers wird durch Differenzalgleichungen beschrieben.
Der  P-Anteil ändert seine Größe proportional zur Regelabweichung 
(Sollwert-Istwert). Dies wirkt nur auf die KP Verstärkung.
Das D-Glied eines Reglers ist ein Differenzierer, welcher immer mit dem 
P-Anteil oder (I-Anteil) gemeinsam auftreten muss. Der D-Anteil entsteht 
durch die Regelabweichung über die Zeit und wird mit der Nachstellzeit 
multipliziert. Er ist nicht von der Regelabweichung abhängig, sondern 
nur von der Änderungsgeschwindigkeit. Große Nachstellzeiten bewirken 
große Änderungen der Stellgröße und bringen damit oft Unruhe in die 
Regelung.
Ein Integralanteil wird dann verwendet, wenn die Regelabweichung 
möglichst genau auf Null gebracht werden soll. Er wird hier nicht 
verwendet, weil immer mit einer Regelabweichung gearbeitet wird und nur 
die Regelverstärkung verändert wird.
'
'z.B. mega88
'Pin19  AD6 Sensor Eingng
'Pin10  PD6 Ausgang
'----------------------------------------------------------------------- 
------------
' PD REGLER
'----------------------------------------------------------------------- 
------------
' S1 At Pb3 = Up
' S2 At Pb4 = Down

$regfile = "mxxdef.dat"
$crystal = xxxxx

Dim N As Byte
Dim X As Integer
Dim Y As Single
Dim Z As Single
Dim Xold As Single
Dim Xp As Single
Dim Xi As Single
Dim Xd As Single


Dim P As Single
Dim I As Single
Dim D As Single
Config Adc = Single , Prescaler = 32 , Reference = Off      ' AD-Wandler 
starten
Start Adc
Config Timer0 = Pwm , Prescale = 1 , Compare A Pwm = Clear Down , 
Compare B Pwm = Clear Down

P = 0.1
D = 60

Do

 If Pinb.3 = 0 Then P = P + 0.0002  'Taster SW1
 If Pinb.4 = 0 Then P = P - 0.0002  'Taster SW2

 X = 0
 For N = 1 To 8
   X = X + Getadc(6)
 Next X
 X = X / 8
 If X < 512 Then X = 512  ' hier im Beispiel - nur der Bereich 512 bis 
1023 ist für den Regler verwendbar

 Xp = X - 512
 Xp = Xp * P

 Xd = X - Xold
 Xold = X
 Xd = Xd * D

 Y = Xp + Xd
 Y = Y / 2
 If Y > 255 Then Y = 255
 If Y < 0 Then Y = 0

 Pwm0a = Int(y)      'Ausgang PWM



Loop

mfg

albert

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.