Welcome! Log In Create A New Profile

Advanced

Hot end temperature control

Posted by dc42 
Hot end temperature control
February 08, 2014 07:21PM
In my latest fIrmware version (0.57m-dc42) I've added support for the M301 command to set the PID parameters. I've also changed the default PID parameters and made minor changed to the PID code to improve PID performance. Here are before and after pics of the hot end temperature graph when it is commanded to 200C from room temperature:



Before the changes, the hot end would never settle at 200C, it was always a degree or two cooler because the limit on the integral term was set too low.

I've attempted to choose parameters that reach typical hot end temperatures quickly from room temperature, while not overshooting by more than 2C. I was unable to find any good advice for tuning the PID parameters. I tried variations on Ziegler-Nichols, but it turns out that this and other classical PID tuning techniques are optimized for response to disturbances and give lousy command response. In the end I found that a much smaller Ki coefficient than Z-N is required to avoid overshoot. The ideal seems to be to choose Ki so that it gradually builds up to the required value.

The old firmware considered that being within 5C of the requested temperatures was good enough to start printing. I've reduced thus to 2C in this build.

The new binary is at [github.com] (follow that link and press the Raw button to download). I'd be interested in hearing how well the temperature setting works for others, since Ormerods may differ slightly, and in any alternative PID parameters that are found to work well.

Edited 1 time(s). Last edit at 02/10/2014 12:42PM by dc42.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].

Re: Hot end temperature control
February 09, 2014 04:35AM
Looks great dc I'll give it a go later, hopefully this will stop the bouncing/oscillating temp I have been experiencing while cool printing around 175

Matt


Limited Edition Red RS Ormerod 1 #144 of 200 - RRP 1.09fw
iamburnys Ormerod Upgrades Github
Follow me on ThingiVerse My Designs
Re: Hot end temperature control
February 09, 2014 06:35AM

dc42
That works great as you can see from the before and after
Thanks
John
Re: Hot end temperature control
February 09, 2014 03:42PM
Thanks John, good to hear that it doesn't only work for me.

I've been thinking some more about this. One of the reasons that Ziegler-Nichols tuning gives such terrible results for this PID is that the PID is extremely non-linear. The PID is set to operate when the temperature is within 150C of the target, however when the temperature is more than about 12C from target, the P term alone is sufficient to turn the heater full on or off. So the output is clipped. This means that heating takes far longer than it would in an ideal PID, and the I term accumulates for far longer. That is why I had to reduce Ki so much to get acceptable overshoot.

I think a better approach might be:

1. Do a calculation to find the approximate PID output needed to maintain the requested temperature, based on a one-time measurement, or on a learning algorithm with results stored in EEPROM. Ideally, this would take account of the ambient temperature.

2. Set the initial I-term to that value.

3. As long as the PID output causes the heater to be full on or full off, keep the I-term constant at that initial value.

4. When the PID output gives a result that is not full on or full off, allow the I-term to change.

5. The PID will now be operating in linear mode, so Ziegler-Nichols or another tuning mechanism can be used to tune it.

Does anyone with experience of PIDs have any comments on this approach? I don't plan to implement it yet, since the existing approach with my tweaks seems to work well enough.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 10, 2014 12:25PM
Another very useful feature DC42 - note that the Gcode is M301 (not M503 as presumably typoed in your starting post). I still get an overshoot of approximately 6 degrees with the new defaults ( P=20, I=0.027,D100), but it damps out with marginal ringing within a minute.

Trying some tuning tips from around the web I can't get much better (but can get a lot worsesmiling smiley) response , maybe the implementation is a little "non standard"?

Ray
Re: Hot end temperature control
February 10, 2014 12:44PM
Ray, thanks for pointing out the typo, I've now corrected it. See my post just prior to yours for why I think the standard tuning techniques don't work with this PID. What is your ambient temperature, and what temperature did you set when you got the overshoot? To reduce the overshoot, try decreasing the I term a little, leaving the P and D terms alone.

Edited 2 time(s). Last edit at 02/10/2014 12:45PM by dc42.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 10, 2014 01:09PM
Quote
dc42
I've also changed the default PID parameters and made minor changed to the PID code to improve PID performance.

dc do you mean you have improved on M303?


# 500
Re: Hot end temperature control
February 10, 2014 01:20PM
No, neither the original firmware nor my modified version implements M303. I guess it would be quite easy to do a simplified version of M303 that just tweaks the I-term. I think the current PID is too nonlinear to do much better than that.

Edited 2 time(s). Last edit at 02/10/2014 01:24PM by dc42.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 10, 2014 01:43PM
Ambient is around 22°C, target temperature is 200°C: Dropping the I term to 0.022 reduced the overshoot, but left a little more ringing and finally settled slightly below the target (200°C) - I increased to I= 0.021 and increased P to 22 (after a couple of trials), now the overshoot is around 2 degrees, and it settles at 199.7+/- 0.2 within around 10 seconds...

or so I thought until I did repeat - it looks as though there's a long-term effect on the final output based on the initial error - the attached graph shows the temperatures (sampled once per second) for P=22, I=0.021 and D=100. The first run started with a measured temperature around 35, overshot then had dampened ringing centered around 201°C, I then turned off the heater, let it cool to around 100°C then turned it on again - this time there's less overshoot and the ringing is pretty much fully damped and centered bang on 200 (note the purple line shows the target temperature). Turning the heater off again and starting up around 155°C, the "overshoot" barely scrapes past 200, but the plateau is at around 198. I left it to cool to around 30 and ran it again, and it behaves as it did for the first run (it's now 10 minutes past the point shown and it has settled at 200.3 +0.2/-0.3).



I'm not sure what conclusions to draw from this, other than when tuning one would have to be careful to let the nozzle cool to ambient.

Nonetheless - a 10 second overshoot of 2K is a pretty damn good percentage error and the long term average of +/- 0.3K is very stable - more importantly, extruding 100mm @10mm/min did very little (the temperature initially dropped by around 0.5 then recovered after 5 seconds or so), contacting the bed didn't noticably change the nozzle temperature at all, so all in all it works well.

Ray

btw Before updating, my nozzle temperature was fairly persistently below the set point by around 3-5K

Edited 1 time(s). Last edit at 02/10/2014 01:44PM by rayhicks.
Re: Hot end temperature control
February 10, 2014 03:22PM
I haven't done PID tuning recently but did do lots of this in the past for temperature control and gas mixing control e.g. controlling O2 level in an O2+N mixture. Great fun, but very time consuming.
I even developed and optimised my own controller methods, but found that these had been invented many years before me!

The real pain that you are I believe identifying is you are wanting different PID terms based on different error/start conditions. My own view is that when the error between the target temperature and set point is large you need to disable the I term or you can get huge overshoot as the I error term just gets larger and larger until the setpoint is reached and then you get a large overshoot to compensate! Traditionally most people set the I term small to avoid this start up error, but then you don't get the benefit of the I term when you are at/near the target temperature.

My 'best' solution for many situations was use a PI control (not control the rate), I then defined two zones as 'ramp up' and 'home in', during the 'ramp up' the integral term was zero, so it was a pure proportional control, but once at the 'homing in' stage the integral term was enabled and reduced the setpoint errors quickly. (The other thing I remember trying without success, but I can't recall why!, is to have the I term related to the inverse of the error, but that was probably down to our methods)

This type of control only works when you can accept the slew rates of the system, which in the Ormerod you can as we just want to heat up quickly.

As said I haven't done this in years now, but from memory the above worked well once set up, however, I see the results you are already getting as excellent!


Ormerod #007 (shaken but not stirred!)
KP
Re: Hot end temperature control
February 10, 2014 04:24PM
I haven't downloaded any firmware yet, much less dug into the code. Does the controller not do any clamping of the I term to prevent integral windup? That definitely would be an area for future development.

KeV.
Re: Hot end temperature control
February 10, 2014 05:19PM
Yes the controller does clamp the I term. However, the I term was being clamped at far too low a value, so that if the commanded temperature was greater than about 100C, it would never be held, because a substantial P term was needed to keep the controller in the steady state. The controller was effectively a PD controller except at low temperatures.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 11, 2014 04:09AM
Looks great! Hours of fun to be had here with different algorithms . Alternative to PID might be to look up a desired trajectory based on temperature error and adjust PWM duty cycle based on trajectory error (Think its a "higher order " algorithm). Dont know the proper name but I used to call it IPD - Integral of proportional and differential. but that was servo motors not 2D printer heaters!

More fun to be had with a fuzzy logic algorithm too smiling smiley

I best shut up. Im certainly no expert... Fantastic work dc42 smiling smiley


regards
Andy


Ormerod #318
www.zoomworks.org - Free and Open Source Stuff smiling smiley
Re: Hot end temperature control
February 11, 2014 04:22AM
Quote
rayhicks
Ambient is around 22°C, target temperature is 200°C: Dropping the I term to 0.022 reduced the overshoot, but left a little more ringing and finally settled slightly below the target (200°C) - I increased to I= 0.021 and increased P to 22 (after a couple of trials), now the overshoot is around 2 degrees, and it settles at 199.7+/- 0.2 within around 10 seconds...

or so I thought until I did repeat - it looks as though there's a long-term effect on the final output based on the initial error -
...

btw Before updating, my nozzle temperature was fairly persistently below the set point by around 3-5K

If the ringing is too high then you should decrease the P-term. If your starting temperature is high then expect the temperature to settle a few degrees low initially, because the I-term will not have time to reach the required value during the heating phase. But it will slowly climb to the set temperature. Your earlier problem with the nozzle being persistently below the set point was caused by the I term being sampled at too low a value in the old firmware.

One thing I may try is using two different values of Ki: a low one initially, then a much higher one when the temperature gets close to target and the PID is operating in its linear range. This would mean that if the temperature does initially settle a few degrees off target, it would revert to target faster.

Edited 2 time(s). Last edit at 02/11/2014 04:23AM by dc42.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 11, 2014 05:49AM
Quote
dc42

If the ringing is too high then you should decrease the P-term. If your starting temperature is high then expect the temperature to settle a few degrees low initially, because the I-term will not have time to reach the required value during the heating phase. But it will slowly climb to the set temperature. Your earlier problem with the nozzle being persistently below the set point was caused by the I term being sampled at too low a value in the old firmware.

One thing I may try is using two different values of Ki: a low one initially, then a much higher one when the temperature gets close to target and the PID is operating in its linear range. This would mean that if the temperature does initially settle a few degrees off target, it would revert to target faster.

Indeed I tried a range of values for each term (starting with P only then adding I and eventually D) to address the ringing and overshoot, including using a higher I once the temperature was around the target (which behaved as predicted), seemingly with improvements - then I realised I wasn't necessarily seeing improvements, but dependency on initial conditions - hence the cautionary tale. I initially used an approach outlined here [newton.ex.ac.uk] out of interest (then reverted to your original terms for comparison- they actually worked better, then I tweaked those a little).

I'm not sure that there's much to be improved now that the temperature actually does get to target within much less than a minute with totally insignificant overshoot (only 2° past the 200° target for less than 5 seconds I think), then settles like a rock on the target not being disturbed by losing heat to filament or bed as far as the limited testing I did yesterday showed - the offset of <= 5°C that the previous settings had was more of a niggle than a practical concern, and your refinements mean that the hotend is now doing exactly what it should (in my mind) and the temperature control is now is "very good/excellent" rather than "satisfactory/good enough" as it had been.

Cheers

Ray
Re: Hot end temperature control
February 11, 2014 06:49AM
Thanks Ray, in that case I'll leave the PID alone, at least until I get bored.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 11, 2014 01:49PM
Hello dc42,
I'm facing with the same problem but amplified: the PID let the temperatureunder the set point for aout 15°c any set of PID parameter I send through the M301 command.
I want to try to modify the configuration firmware with your proposal but I'm new on the use of Arduino software. How can I transfer the binary you stored in the GThub to the firmware configuration file for my Melzi?
Thank you for your help!
Re: Hot end temperature control
February 11, 2014 01:59PM
Hi Proclea,

The firmware I have been modifying is the Duet firmware for the Ormerod. The Melzi uses a different processor and so different firmware. So my binary is unfortunately of no use to you unless you upgrade your electronics to Duet.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 13, 2014 07:06AM
Hi Dc,

I'm having a problem with the head heater that seems reproducible, if the head has only cooled a little when you start another print it doesn't get to temperature again.

This is the process I've noticed a few times.

- Start a direct print job from web interface.
- head heats up to temp (~195C).
- printing starts.
- something goes wrong with print, ahhh!
- [Pause] the print job.
- move head out of the way when buffered commands have finished.
- clear bed of duff print job.
- (at this point bed and head are still holding at temp).
- [Reset] the interface, (this switches off both heaters).
- after interface has reset I start web printing another G file (head temp has dropped to ~190 by now).
- head starts to heat up but doesn't get above 191-192C
- printing doesn't start.

Matt


Limited Edition Red RS Ormerod 1 #144 of 200 - RRP 1.09fw
iamburnys Ormerod Upgrades Github
Follow me on ThingiVerse My Designs
Re: Hot end temperature control
February 13, 2014 07:48AM
Hi Matt,

Yes that is an unfortunate side-effect of the way the PID controller works. When you reset the board with the head hot, the I term and the head temperature are no longer in step, because the I term has been reset to zero but the head has not cooled. The head will eventually reach the commanded temperature, but will take a long time. There are a couple of things I can try to alleviate this:

- The first time the head temp is commanded after a reset, look at the starting head temp and preset the I term to a value that is approximately what is needed to maintain that temperature. This will reduce the initial error. Ideally, the controller would learn what I term is needed, storing the learned profile in EEPROM.

- Use two different values of Ki, the present (small) one when the controller is operating out of the linear region, and a much larger one when it is operating in the linear region. This will cause the error to be corrected more quickly.

I'll take a look at this when I get time. In the meantime, when this happens to you, try using M301 Ixxx to temporarily increase the I-term once the head is within about 10C of the desired temperature. The default value is 0.027. I suggest you try values between about 0.1 and 2. Too high a value will cause oscillations. Let me know what works well. Don't forget to reset the I-term (or reset the printer) before you heat the head up from cold again.

Edited 1 time(s). Last edit at 02/13/2014 07:49AM by dc42.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
February 13, 2014 09:04AM
Matt, when I tried out the PID the other day I noticed this effect (see above [forums.reprap.org]), but I'd let the head cool a little longer - if you look at the graphs you can see that when it cooled for a minute or so it got to 100°C, when it was next switched on it pretty much went straight back (second peak), when I then let it cool a lot less (to around 155°C) there was a small but noticeable dip - so maybe the easiest method (probably as quick as adjusting the I term) is just wait another minute before turning on the heater after a reset, or indeed turn off the heater immediately after you hit pause and before you clean up the bedsmiling smiley it should have dropped to 100 or less and the PID settings should cope.

Cheers

Ray
Re: Hot end temperature control
February 16, 2014 12:33PM
@ treth, hi I just spotted your post regarding this, I have applications using pid where an overshoot will cause a mechanical failure similar to a head crash on a hard drive, in those instances the integral term error has to be removed when the target value is achieved to prevent damage, PID is normally about averaging speed control over time where overshoot to catch up isn't a problem.

Best regards

Mike
Re: Hot end temperature control
March 05, 2014 04:51PM
Quote
dc42
Yes the controller does clamp the I term. However, the I term was being clamped at far too low a value, so that if the commanded temperature was greater than about 100C, it would never be held, because a substantial P term was needed to keep the controller in the steady state. The controller was effectively a PD controller except at low temperatures.

It clamps the I term poorly. The I term should indeed be big enough so that Ki*temp_iState can to supply the proper output at at steady state at the setpoint (e=0 and d=0) but the I term should be more dynamically constrained so that Ki*temp_iState + Kp*error-temp_dState it within limits. If your heater can do 200C at half power, then the limit should be (with one-second sampling) at least 128/0.021=6095 C*s

If the the limits were large enough, and I'm interpreting the graph correctly: There was a positive offset in the first pulse in the graph above because temp_iState accumulated too much (maybe 60s*160C/2=4800Cs by the area of a triangle?) on the way up from 20C and couldn't start decreasing until it exceeded the setpoint, The second pulse looked better because temp_iState may have not grown too big in the time from 100C to 200C (30s?) (30s*100C/2=1500Cs in temp_iState?) The third pulse was low because there wasn't enough time to accumulate temp_iState (15s*45C/2=300Cs?) to match the process. At 198C, temp_iState probably would have increased at 2Cs/s with exponential decay until the temp_iState*.021 supplies the appropriate heater output for 200C.

With a P=22 and I=0.021, the integrator reset time constant is 22/0.021=1047 time units (9 minutes at 0.5s sampling?). It will take on the order of that time for the I term to dump excessive windup or balance out an offset.

Constraining the temp_iState like [www.controlguru.com] (See Solution 1 step 5) around [github.com] would let you have a bigger Ki that approaches the setpoint faster and avoids excessive integrator windup. For example, you could drop the line 171-172 code and put in stuff like [github.com]

Edit: dc42's code at [github.com] is smarter in that the temp_iState is maintained and limited in output units rather than C*s units, which makes the limit term insensitive to changes in Ki. Then at around line 180 and 181, you could adjust temp_iState by the amount it exceeds the limits to dynamically eliminate the excess windup.

Edited 3 time(s). Last edit at 03/05/2014 05:03PM by DaveX.
Re: Hot end temperature control
March 05, 2014 05:12PM
DaveX, in the more recent firmware versions (057r and 057t), I've used a much larger I-term - hence reducing the integrator reset time constant - but enabled the PID controller only when the temperature is within 20C of target. This allows the I-accumulator to change more rapidly, at the expense of some initial overshoot (or occasionally undershoot) - especially when the temperature is reduced by more than 20C (which however is not a common scenario for 3D printers). Let me know what you think.

Ideally, the code would have some prior or learned knowledge of the approximate power needed to maintain a given temperature, so that when switching from PID to non-PID mode, the I-accumulator could be preset to that value.



Large delta printer [miscsolutions.wordpress.com], E3D tool changer, Robotdigg SCARA printer, Crane Quad and Ormerod

Disclosure: I design Duet electronics and work on RepRapFirmware, [duet3d.com].
Re: Hot end temperature control
March 06, 2014 04:27AM
kP/kI =Ti gives time constants of 9/(.2/.5)= 22.5 time units versus 20/0.027=370 time units so the I should be a lot more responsive. (You may want to double-check the unit conversions in [github.com] -- If you sum the error 2 times/second into temp_iState, the units of "error" would be C*hs where hs is a half-second, and you want your kI to convert that into counts, so it is applied as counts/(C*hs). So to get a value that means 0.2 counts/(Cs) you might need to use 0.1 counts/(Chs) or to do 0.2*HEAT_SAMPLE_TIME. IOW: If you double the sampling frequency, you'll double the errors summing into temp_iState, so you'd need to halve the kI. Or you could move the HEAT_SAMPLE_TIME conversion out of the config file and put it into Heat.cpp code line 175. I'm not certain I've got it all right here, but it seems like it could be backwards.)

One way commercial PIDs apply the prior knowledge idea is by having "bumpless" switching between manual and PID modes. When you switch from PID to manual mode, it would hold the output value constant at whatever it is. For example, if you had a manual power setting gcode like M301 X0 it could turn of the PID and leave the output as-is. Or a M301 X0 S0.75 that sets a flag to disable the PIDand calls SetHeater(0,.75) could manually set a particular power level. Then switching from manual to PID control (M301 X1 ???) could set the target temperature to the measured temperature, initialize the integral term based on the current output value, and clear the flag. For example, given an output of 0.75, calculate temp_iState[0]=output*255/pidKi[0] and activeTemperature[0]=platform->GetTemperature[0]. If the system was at steady state, it should stay where it is "bumpless"-ly, but if it was in transition, the temp_iState would not be unreasonable. You could supply the prior knowledge in G-code with M305 X1 S0.75 to reset the i term to 75% power. Since you are maintaining I state in output units, changes in Ki don't bump your process like they would if you were keeping state in C*hs units.

[brettbeauregard.com] does a good job of illustrating some of this.

With a Kp of 20, the proportional term will drive the PID to full scale when the process is below setpoint-12.5C From Ray's graphs, it looks like it changes about 3C per second at full power, so if it's summing every half-second starting from setpoint-20, the process should accumulate about 20C*6s/2*2=120Cs/2 of integrated error on the way up. With a kI of .4 counts/(C*s/2), that makes an I contribution of about 48 counts by the time it gets to the setpoint. If 48/255 is more power than you need to hold the setpoint temperature, the overshoot would be due to the I term.

If the overshoot is due to an excessive temp_iState term, constraining it further by pidKp*error would trim the temp_iState to zero below setpoint-12.5C, accumulating maybe 12.5*4/2*2*.4=20 counts of power


Ack -- when your config is doing the setpoint-20 cutoff thing, it's using the Kp=9 setting, not 20, so it would drop from full to 180/255=70% full power at setpoint-20, and Ray's setup might slow to about 2C/s until the I term catches up.

If you are looking for smooth behavior and minimal overshoot with your current code, I'd try widening the setpoint+/-20 band to +/- 28.3C to match the Kp=9 @ fullpower temperature so the PID starting transition is smooth. Or you could try modifing the code to do the "bumpless" thing at setpoint-20, and try to set temp_iState at 255-kP*error=75 so you don't get the output drop at the transition. Still, limiting I-forced overshoot would depend on the P term contribution dropping faster than the I term accumulates.

I've been experimenting with Teacup's PID (and Marlin's) on some of these issues and saw you were doing interesting work on controlling integrator windup.

Edited 1 time(s). Last edit at 03/06/2014 04:39AM by DaveX.
Re: Hot end temperature control
March 06, 2014 05:09AM
I did some stuff with compensator algorithms many years ago. I remember then finding that classic PID didnt work if the load was unknown... You always had problems with integrator wind up! IIRC we moved to a scheme where we looked up a desired velocity based on difference between required and actual position (in this case substitute rate of change of temperature rather than velocity)) . The Output was then the integral of the error between desired and actual velocity - integral of rate of change of that error. You tune with two constants for KP and Kd. ( I believe there was a simplifying relation based on the equations of motion and neglecting higher order terms e.g Kd = -2 * Kp but cant remember the maths now!) In this scheme the output settles at a particular value to counteract a large range of loads with no requirement for an integral term. To find the desired rate of change of temperature, draw a graph of the required rate of change of temperature against temperature error and then put it in a lookup table.

The conclusion was that In an age of cheap calculation with microcontrollers PID is outdated smiling smiley

regards
Andy


Ormerod #318
www.zoomworks.org - Free and Open Source Stuff smiling smiley
Sorry, only registered users may post in this forum.

Click here to login