Readme
/*
INSTRUCTION: PID Controller
1) Purpose
- This module computes the control output in the range outMin…outMax (typically 0…100).
- Works for a valve, damper, VFD, etc.
2) Signals
- setpoint (SP) : setpoint
- input (PV) : measurement (controlled variable)
- feedbackValue : actual/previous device output (important for incremental form)
- output : controller output (command to the device)
Why feedbackValue:
- The module computes u(t)=u(t-h)+du(t).
- If feedbackValue is wired to the real device output, the module handles manual overrides,
external limits, and saturation more stably (less integrator “windup”).
3) Action direction
- reverseAction=false (Direct): e = SP - PV
- reverseAction=true (Reverse): e = PV - SP
4) PID algorithm
- Incremental form (velocity form)
- D term based on PV (to avoid spikes on SP steps)
- Dead zone deadZone: if |e| < deadZone, the module holds feedbackValue (or lastU/outMin)
5) enable=false behavior via disableMode
- Min : outputs outMin
- Max : outputs outMax
- Zero : outputs 0
- Hold : holds a safe value (feedbackValue -> lastU -> outMin -> 0)
6) Status protection
- If any critical input has a non-ok status, the module does NOT write null.
It holds a safe value (Hold) and sets output with fault status.
7) Autotune (autotuneEnable)
7.1) tuningMode = Relay
- output toggles between outMin and outMax:
- when PV crosses SP, or
- by timer relayPeriod
- autotuneState shows Relay: High / Relay: Low
- This mode does NOT compute kp/ki/kd. It is used to “excite” the plant and observe the response.
relayPeriod recommendations (seconds):
- fast loops (pressure/flow/speed/RPM): 5…10
- slow loops (temperature): 15…30
7.2) tuningMode = Ziegler
Important: in this version Ku is taken from the current kp.
That means:
- you set kp yourself so that PV oscillates around SP (with SP crossings).
- the module computes Tu from SP crossings (error sign change = half-period).
- after 10 half-periods (5 periods) and after zieglerMinTime it writes new kp/ki/kd by Ziegler–Nichols:
Kp = 0.6*Ku
Ki = 1.2*Ku/Tu
Kd = 0.075KuTu
- then autotuneEnable turns off automatically, autotuneState becomes "Done: Tu=..."
zieglerMinTime recommendations (seconds):
- fast loops: 60…120
- temperature: 300…600
How to tell Ziegler is running:
- autotuneState: "ZN: half=0/10" -> "ZN: half=10/10"
- the half counter increases only when PV crosses SP back and forth
8) Wiring in Wire Sheet (required)
- Feed input (PV) from the sensor
- Feed setpoint (SP) from the setpoint source
- Feed feedbackValue from the actual device output (if unavailable — leave empty, the module uses lastU/outMin)
- Connect output to the device command
9) Startup flags (Execute On Change)
To make onExecute run automatically:
- set "x" on: enable, disableMode, setpoint, input, feedbackValue,
kp,ki,kd, dt, deadZone, outMin,outMax, reverseAction,
autotuneEnable, tuningMode, relayPeriod, zieglerMinTime
- do NOT set "x" on: output, autotuneState
10) Common “doesn’t work” causes
- output doesn’t change: onExecute is not called (missing x on inputs)
- Relay doesn’t toggle: outMin/outMax not ok or equal
- ZN half doesn’t increase: PV doesn’t cross SP (kp too small / wrong reverseAction / plant not responding)
*/