This automation implements a [PID](https://en.wikipedia.org/wiki/PID_controller)-T1 controller for openHAB.
A PID controller can be used for closed-loop controls. For example:
- Heating: A sensor measures the room temperature.
The PID controller calculates the heater's valve opening, so that the room temperature is kept at the setpoint.
- Lighting: A light sensor measures the room's illuminance.
The PID controller controls the dimmer of the room's lighting, so that the illuminance in the room is kept at a constant level.
- PV zero export: A meter measures the power at the grid point of the building.
The PID controller calculates the amount of power the battery storage system needs to feed-in or charge the battery, so that the building's grid power consumption is around zero,
i.e. PV generation, battery storage output power and the building's power consumption are at balance.
| `kdTimeConstant` | Decimal | D-T1: [Derivative Gain Time Constant](#derivative-time-constant-d-t1-parameter) in sec. | Y |
| `commandItem` | String | Send a String "RESET" to this item to reset the I and the D part to 0. | N |
| `loopTime` | Decimal | The interval the output value will be updated in milliseconds. Note: the output will also be updated when the input value or the setpoint changes. | Y |
If the output is the opening of a valve in %, you might want to set this parameter to a lower value (`ki=0.1` would result in 30% after 60 sec: 5\*0.1\*60=30).
## Derivative (D) Gain Parameter
Parameter: `kd`
The purpose of this parameter is to react to sudden changes (e.g. an opened window) and also to damp the regulation.
This makes the regulation more resilient against oscillations, i.e. bigger `kp` and `ki` values can be set.
A value of 0 disables the D part.
A value of 1 sets the output to the difference between the last setpoint deviation (error) and the current.
E.g. the setpoint is 25°C and the measured value is 20°C (error=5°C).
When the temperature drops to 10°C due to an opened window (error=15°C), the output is set to 15°C - 5°C = 10.
## Derivative Time Constant (D-T1) Parameter
Parameter: `kdTimeConstant`
The purpose of this parameter is to slow down the impact of the D part.
This parameter behaves like a [low-pass](https://en.wikipedia.org/wiki/Low-pass_filter) filter.
The D part will become 63% of its actual value after `kdTimeConstant` seconds and 99% after 5 times `kdTimeConstant`. E.g. `kdTimeConstant` is set to 10s, the D part will become 99% after 50s.
Higher values lead to a longer lasting impact of the D part (stretching) after a change in the setpoint deviation (error).
The "stretching" also results in a lower amplitude, i.e. if you increase this value, you might want to also increase `kd` to keep the height of the D part at the same level.
## Tuning
Tuning the `Kp`, `Ki` and `Kd` parameters can be done by applying science.
It can also be done by heuristic methods like the [Ziegler–Nichols method](https://en.wikipedia.org/wiki/Ziegler%E2%80%93Nichols_method).
But it can also be done by trial and error.
This results in quite reasonable working systems in most cases.
So, this will be described in the following.
To be able to proceed with this method, you need to visualize the input and the output value of the PID controller over time.
After you added a [Rule](https://www.openhab.org/docs/configuration/rules-dsl.html) with above trigger and action module and configured those, proceed with the following steps:
> *Notice:* A good starting point for the derivative time constant `kdTimeConstant` is the response time of the control loop.
E.g. the time it takes from opening the heater valve and seeing an effect of the measured temperature.
1. Set `kp`, `ki` and `kd` to 0
2. Increase `kp` until the system starts to oscillate (continuous over- and undershoot)
3. Decrease `kp` a bit, that the system doesn't oscillate anymore
4. Repeat the two steps for the `ki` parameter (keep `kp` set)
5. Repeat the two steps for the `kd` parameter (keep `kp` and `ki` set)
6. As the D part acts as a damper, you should now be able to increase `kp` and `ki` further without resulting in oscillations
After each modification of above parameters, test the system response by introducing a setpoint deviation (error).
This can be done either by changing the setpoint (e.g. 20°C -> 25°C) or by forcing the measured value to change (e.g. by opening a window).
This process can take some time with slow responding control loops like heating systems.
You will get faster results with constant lighting or PV zero export applications.