forked from M-Labs/kirdy
Update PID Autotune Code for Driver Code
This commit is contained in:
parent
28f8c3c497
commit
82c46e04d0
|
@ -6,7 +6,7 @@ import socket
|
||||||
import json
|
import json
|
||||||
import time
|
import time
|
||||||
import signal
|
import signal
|
||||||
from driver.kirdy_async import Kirdy
|
from driver.kirdy import Kirdy, FilterConfig
|
||||||
import asyncio
|
import asyncio
|
||||||
|
|
||||||
# Based on hirshmann pid-autotune libiary
|
# Based on hirshmann pid-autotune libiary
|
||||||
|
@ -246,57 +246,43 @@ class PIDAutotune:
|
||||||
return False
|
return False
|
||||||
|
|
||||||
|
|
||||||
async def main():
|
def main():
|
||||||
"""
|
"""
|
||||||
PID Autotune Tool for Kirdy
|
PID AutoTune Tools for Kirdy
|
||||||
|
The obtained temperature works best at the target temperature specified.
|
||||||
|
Before running PID AutoTune, please
|
||||||
|
1. Secure the laser diode onto the LD adapter and copper heat sink
|
||||||
|
2. Make sure Kirdy has warmed up and reached thermal equilibrium state
|
||||||
|
|
||||||
This tool can tune the PID to be critically damped by adjusting a few parameters.
|
In case of PID Autotune Failure, you can
|
||||||
Please be advised that this tool can generate undesired PID response.
|
1. Run the PID Autotune again
|
||||||
Make sure you have set the over-temperature protection range properly to protect the laser diode.
|
2. Or increase the lookback period
|
||||||
|
3. Or increase the sampling rate
|
||||||
PID Autotune Tool Parameters:
|
|
||||||
For the operation theory and implication of each parameters, please refer to this blog post.
|
|
||||||
http://brettbeauregard.com/blog/2012/01/arduino-pid-autotune-library/
|
|
||||||
|
|
||||||
1. lookback: Reference period for local minima/maxima, seconds.
|
|
||||||
2. noiseband: Determines by how much the input value must overshoot/undershoot the setpoint(celsius).
|
|
||||||
3. output_step: Output current step size(amps).
|
|
||||||
4. target_temperature: Target Output Temperature Setpoint.
|
|
||||||
5. apply_params: Apply PID Parameters after pid autotune is successful.
|
|
||||||
|
|
||||||
Kirdy-Related Parameters:
|
|
||||||
1. Thermistor parameters.
|
|
||||||
2. Temperature monitor upper and lower limits.
|
|
||||||
3. Temperature ADC filter type and sampling rate.
|
|
||||||
|
|
||||||
Instructions:
|
|
||||||
Before running the PID Autotune Tool, please:
|
|
||||||
1. Secure the laser diode onto the LD adapter and copper heat sink with thermal paste.
|
|
||||||
2. Ensure Kirdy has warmed up and reached thermal equilibrium.
|
|
||||||
|
|
||||||
After running the PID Autotune Tool:
|
|
||||||
Test the PID parameters and evaluate the PID output behavior.
|
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
# Target temperature of the autotune routine, celsius
|
||||||
target_temperature = 20
|
target_temperature = 20
|
||||||
|
# Value by which output will be increased/decreased from zero, amps
|
||||||
output_step = 1
|
output_step = 1
|
||||||
lookback = 5.0
|
# Reference period for local minima/maxima, seconds
|
||||||
noiseband = 0.0
|
lookback = 2.0
|
||||||
# Apply parameter
|
# Determines by how much the input value must
|
||||||
apply_params = True
|
# overshoot/undershoot the setpoint, celsius
|
||||||
|
noiseband = 2.0
|
||||||
|
|
||||||
kirdy = Kirdy()
|
kirdy = Kirdy()
|
||||||
kirdy_ctrl = Kirdy()
|
kirdy.start_session(host='192.168.1.128', port=1337)
|
||||||
await kirdy.start_session(host='192.168.1.131', port=1337, timeout=0.25)
|
|
||||||
await kirdy_ctrl.start_session(host='192.168.1.131', port=1337, timeout=0.25)
|
|
||||||
|
|
||||||
await kirdy_ctrl.laser.set_power_on(False)
|
while not(kirdy.connected()):
|
||||||
await kirdy_ctrl.laser.set_i(0)
|
pass
|
||||||
|
|
||||||
await kirdy_ctrl.thermostat.set_power_on(False)
|
kirdy.laser.set_power_on(False)
|
||||||
await kirdy_ctrl.thermostat.set_constant_current_control_mode()
|
kirdy.laser.set_i(0)
|
||||||
await kirdy_ctrl.thermostat.set_tec_i_out(0)
|
|
||||||
await kirdy_ctrl.thermostat.clear_alarm()
|
kirdy.thermostat.set_power_on(False)
|
||||||
|
kirdy.thermostat.set_constant_current_control_mode()
|
||||||
|
kirdy.thermostat.set_tec_i_out(0)
|
||||||
|
kirdy.thermostat.clear_alarm()
|
||||||
|
|
||||||
class SignalHandler:
|
class SignalHandler:
|
||||||
KEEP_PROCESSING = True
|
KEEP_PROCESSING = True
|
||||||
|
@ -308,53 +294,57 @@ async def main():
|
||||||
self.KEEP_PROCESSING = False
|
self.KEEP_PROCESSING = False
|
||||||
signal_handler = SignalHandler()
|
signal_handler = SignalHandler()
|
||||||
|
|
||||||
# Configure the Thermistor Parameters
|
kirdy.device.set_active_report_mode(False)
|
||||||
await kirdy_ctrl.thermostat.set_sh_beta(3950)
|
|
||||||
await kirdy_ctrl.thermostat.set_sh_r0(10.0 * 1000)
|
|
||||||
await kirdy_ctrl.thermostat.set_sh_t0(25)
|
|
||||||
|
|
||||||
# Set a large enough temperature range so that it won't trigger over-temperature protection
|
# Configure the Thermistor Parameters
|
||||||
await kirdy_ctrl.thermostat.set_temp_mon_upper_limit(target_temperature + 20)
|
kirdy.thermostat.set_sh_beta(3950)
|
||||||
await kirdy_ctrl.thermostat.set_temp_mon_lower_limit(target_temperature - 20)
|
kirdy.thermostat.set_sh_r0(10.0 * 1000)
|
||||||
await kirdy_ctrl.thermostat.set_tec_max_cooling_i(output_step)
|
kirdy.thermostat.set_sh_t0(25)
|
||||||
await kirdy_ctrl.thermostat.set_tec_max_heating_i(output_step)
|
|
||||||
|
# Set a large enough temperature range so that it won't trigger overtemperature protection
|
||||||
|
kirdy.thermostat.set_temp_mon_upper_limit(target_temperature + 20)
|
||||||
|
kirdy.thermostat.set_temp_mon_lower_limit(target_temperature - 20)
|
||||||
|
|
||||||
|
kirdy.thermostat.set_tec_max_cooling_i(output_step)
|
||||||
|
kirdy.thermostat.set_tec_max_heating_i(output_step)
|
||||||
|
|
||||||
# The Polling Rate of Temperature Adc is equal to the PID Update Interval
|
# The Polling Rate of Temperature Adc is equal to the PID Update Interval
|
||||||
settings = await kirdy_ctrl.device.get_settings_summary()
|
kirdy.thermostat.config_temp_adc_filter(FilterConfig.Sinc5Sinc1With50hz60HzRejection.f16sps)
|
||||||
|
settings = kirdy.device.get_settings_summary()
|
||||||
sampling_rate = settings["thermostat"]["temp_adc_settings"]["rate"]
|
sampling_rate = settings["thermostat"]["temp_adc_settings"]["rate"]
|
||||||
|
|
||||||
await kirdy_ctrl.thermostat.set_power_on(True)
|
print("Settings: {0}".format(settings))
|
||||||
|
|
||||||
tuner = PIDAutotune(target_temperature, output_step,
|
tuner = PIDAutotune(target_temperature, output_step,
|
||||||
lookback, noiseband, 1/sampling_rate)
|
lookback, noiseband, 1/sampling_rate)
|
||||||
|
|
||||||
async for status_report in kirdy.report_mode():
|
kirdy.thermostat.set_power_on(True)
|
||||||
if signal_handler.KEEP_PROCESSING:
|
|
||||||
temperature = status_report["thermostat"]["temperature"]
|
|
||||||
ts = status_report['ts']
|
|
||||||
print("Ts: {0} Temperature: {1} degree".format(ts, temperature))
|
|
||||||
|
|
||||||
if (tuner.run(temperature, ts / 1000.0)):
|
while True and signal_handler.KEEP_PROCESSING:
|
||||||
print(tuner._state)
|
status_report = kirdy.device.get_status_report()
|
||||||
kirdy.stop_report_mode()
|
|
||||||
|
|
||||||
tuner_out = tuner.output()
|
temperature = status_report["thermostat"]["temperature"]
|
||||||
print("PID Autotuner Output: {0}A".format(tuner_out))
|
ts = status_report['ts']
|
||||||
await kirdy_ctrl.thermostat.set_tec_i_out(tuner_out)
|
print("Ts: {0} Current Temperature: {1} degree".format(ts, temperature))
|
||||||
else:
|
|
||||||
kirdy.stop_report_mode()
|
|
||||||
|
|
||||||
await kirdy_ctrl.thermostat.set_tec_i_out(0)
|
if (tuner.run(temperature, ts / 1000.0)):
|
||||||
await kirdy_ctrl.thermostat.set_power_on(False)
|
print(tuner._state)
|
||||||
|
break
|
||||||
|
|
||||||
if apply_params:
|
tuner_out = tuner.output()
|
||||||
kp, ki, kd = tuner.get_tec_pid()
|
kirdy.thermostat.set_tec_i_out(float(tuner_out))
|
||||||
await kirdy_ctrl.thermostat.set_pid_kp(kp)
|
|
||||||
await kirdy_ctrl.thermostat.set_pid_ki(ki)
|
|
||||||
await kirdy_ctrl.thermostat.set_pid_kd(kd)
|
|
||||||
|
|
||||||
await kirdy.end_session()
|
kirdy.thermostat.set_tec_i_out(0)
|
||||||
await kirdy_ctrl.end_session()
|
kirdy.thermostat.set_power_on(False)
|
||||||
|
|
||||||
|
pid_params = tuner.get_pid_parameters(tuning_rule="tyreus-luyben")
|
||||||
|
kirdy.thermostat.set_pid_kp(pid_params.Kp)
|
||||||
|
kirdy.thermostat.set_pid_ki(pid_params.Ki)
|
||||||
|
kirdy.thermostat.set_pid_kd(pid_params.Kd)
|
||||||
|
kirdy.thermostat.set_pid_output_max(1.0)
|
||||||
|
kirdy.thermostat.set_pid_output_min(1.0)
|
||||||
|
|
||||||
|
kirdy.end_session(block=True)
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
asyncio.run(main())
|
main()
|
||||||
|
|
Loading…
Reference in New Issue