> For the complete documentation index, see [llms.txt](https://docs.mclimate.eu/mclimate-lorawan-devices/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.mclimate.eu/mclimate-lorawan-devices/devices/mclimate-vicki-lorawan/pre-46-vicki-lorawan-device-communication-protocol/operational-modes-and-temperature-control-algorithm/algorithm-3-proportional-integral.md).

# Algorithm 3 - Proportional Integral

This algorithm is an implementation of a typical PI algorithm.

$$
ValveOpening \[%]  = Kp \* e + Ki\*\sum\_{}^{}e
$$

Both the proportional gain Kp and the integral gain Ki can be set with 5 decimal places after the comma.

The algorithm will run on 3 occasions:

&#x20;\- Periodic run (by default every 10 minutes)

&#x20;\- New target temperature is set

&#x20;\- T(measured) - T(target) > 2 degrees Celsius

$$
Integral = \sum\_{}^{}e
$$

There's a [software hysteresis](#temperature-hysteresis) in place, which prevents the movement of the motor unless the error is > Thys.

{% hint style="info" %}
The implementation does not have integral reset time - it integrates all previous errors. There's an integral anti wind-up and anti wind-down in place, which limits the integral to 0-50 degrees by default. You can change the maximum value via the command below, increasing the error limit.
{% endhint %}

## Maximum allowed Integral value

{% tabs %}
{% tab title="SET" %}

<table><thead><tr><th width="149">Byte Index</th><th>Byte value - meaning</th></tr></thead><tbody><tr><td><strong>Byte Index</strong></td><td><strong>Byte value - meaning</strong></td></tr><tr><td>0</td><td>4C - The command code</td></tr><tr><td>1</td><td>XX - I[15:8]</td></tr><tr><td>2</td><td>XX -I[7:0] </td></tr></tbody></table>

**Example command:** 0x4C012C

I\[15:0] = 012C\[HEX] = 300

Integral = I\[DEC] / 10 = 300 / 10 = 30

The error is set to its maximum allowed value of 30°C

**Default:**\
**I\[15:0] = 01F4\[HEX] = 500\[DEC] = 50°C**
{% endtab %}

{% tab title="GET" %}

<table><thead><tr><th width="135">Byte index</th><th width="157">Sent request</th><th>Response - Meaning</th></tr></thead><tbody><tr><td>0</td><td>4D – The command code.</td><td>4D – The command code.</td></tr><tr><td>1</td><td> </td><td>XX - I[15:8]</td></tr><tr><td>2</td><td></td><td>XX -I[7:0] </td></tr></tbody></table>

**Example command response:** 0x4D03E8

I\[15:0] = 03E8\[HEX] = 1000

Integral = I\[DEC] / 10 = 1000 / 10 = 100

The error is set to its maximum allowed value of 100°C

**Default:**\
**I\[15:0] = 01F4\[HEX] = 50\[DEC] = 50°C**
{% endtab %}
{% endtabs %}

## Proportional gain - Kp

{% tabs %}
{% tab title="SET" %}

<table><thead><tr><th width="149">Byte Index</th><th>Byte value - meaning</th></tr></thead><tbody><tr><td><strong>Byte Index</strong></td><td><strong>Byte value - meaning</strong></td></tr><tr><td>0</td><td>37 - The command code</td></tr><tr><td>1</td><td>XX[23:16]</td></tr><tr><td>2</td><td>XX[15:8]</td></tr><tr><td>3</td><td>XX[7:0]</td></tr><tr><td></td><td>XX[23:0] = Kp * 131072 <br><strong>Default: 0x0C0000[HEX] = 786432[DEC] -> Kp = 6</strong></td></tr></tbody></table>

**Example downlink:** Setting Kp to 2.74688: 37057E67

2.74688\*131072 = 360039 = 0x057E67
{% endtab %}

{% tab title="GET" %}

<table><thead><tr><th width="135">Byte index</th><th width="157">Sent request</th><th>Response - Meaning</th></tr></thead><tbody><tr><td>0</td><td>36 – The command code.</td><td>36 – The command code.</td></tr><tr><td>1</td><td> </td><td>A[23:16]</td></tr><tr><td>2</td><td></td><td>A[15:8]</td></tr><tr><td>3</td><td></td><td>A[7:0]</td></tr><tr><td></td><td></td><td>Kp = A[23:0]/131072</td></tr></tbody></table>

**Uplink example:** 0x36123456

A\[23:0] = 0x123456 = 1193046

Kp = 1193046 / 131072 = 9.1
{% endtab %}
{% endtabs %}

## Integral gain - Ki

{% tabs %}
{% tab title="SET" %}

<table><thead><tr><th width="136"></th><th></th></tr></thead><tbody><tr><td><strong>Byte Index</strong></td><td><strong>Byte value - meaning</strong></td></tr><tr><td>0</td><td>3E - The command code</td></tr><tr><td>1</td><td>XX[23:16]</td></tr><tr><td>2</td><td>XX[15:8]</td></tr><tr><td>3</td><td>XX[7:0]</td></tr><tr><td></td><td><p>XX[23:0] = Ki * 131072</p><p><strong>Default: 0x020000[HEX] = 131072[DEC] -> Kpi = 1</strong></p></td></tr></tbody></table>

**Example downlink:** Setting Ki to 0.412678: 3E00D34A\
0.412678\*131072 = 54090 = 0x00D34A
{% endtab %}

{% tab title="GET" %}

<table><thead><tr><th width="135">Byte index</th><th width="157">Sent request</th><th>Response - Meaning</th></tr></thead><tbody><tr><td>0</td><td>3D – The command code.</td><td>3D – The command code.</td></tr><tr><td>1</td><td> </td><td>B[23:16]</td></tr><tr><td>2</td><td></td><td>B[15:8]</td></tr><tr><td>3</td><td></td><td>B[7:0]</td></tr><tr><td></td><td></td><td>Ki = B[23:0]/131072</td></tr></tbody></table>

**Example uplink:** 0x3D112233

B\[23:0] = 0x112233 = 1122867

Ki = 1122867/131072 = 8.57
{% endtab %}
{% endtabs %}

## Get the value of the integral

<table><thead><tr><th width="135">Byte index</th><th width="157">Sent request</th><th>Response - Meaning</th></tr></thead><tbody><tr><td>0</td><td>3F – The command code.</td><td>3F – The command code.</td></tr><tr><td>1</td><td> </td><td>Integral [15:8]</td></tr><tr><td>2</td><td> </td><td>Integral [7:0]</td></tr></tbody></table>

The value of the integral is pre-multiplied by 10 by the device, so it can use 0,1 resolution.

**Example uplink:**

If the integral is 2.5, the complete command response is going to be: 0x3F0019&#x20;

Integral \[15:0] = 0x0019 = 25

Integral = 25/10 = 2.5

## PI run period

{% tabs %}
{% tab title="SET" %}

<table><thead><tr><th width="136"></th><th></th></tr></thead><tbody><tr><td><strong>Byte Index</strong></td><td><strong>Byte value - meaning</strong></td></tr><tr><td>0</td><td>41 - The command code</td></tr><tr><td>1</td><td>XX = Run period in minutes. <strong>(default value: 10 minutes)</strong></td></tr></tbody></table>

**Example downlink:**

0x410F - sets the run period to 15 minutes.
{% endtab %}

{% tab title="GET" %}

<table><thead><tr><th width="135">Byte index</th><th width="157">Sent request</th><th>Response - Meaning</th></tr></thead><tbody><tr><td>0</td><td>40 – The command code.</td><td>40 – The command code.</td></tr><tr><td>1</td><td> </td><td>XX - Run period in minutes.</td></tr></tbody></table>

**Example uplink:**

0x400B - the run period is 11 minutes
{% endtab %}
{% endtabs %}

## Temperature hysteresis (Thys)

{% tabs %}
{% tab title="SET" %}

<table><thead><tr><th width="136"></th><th></th></tr></thead><tbody><tr><td><strong>Byte Index</strong></td><td><strong>Byte value - meaning</strong></td></tr><tr><td>0</td><td>43 - The command code</td></tr><tr><td>1</td><td>XX = Temperature hysteresis value (Thys), multiplied by 10. <strong>(Default value: 0.2 deg. C)</strong></td></tr></tbody></table>

**Example downlink:**

0x4303 - sets the temperature hysteresis to 0.3 degrees Celsius.
{% endtab %}

{% tab title="GET" %}

<table><thead><tr><th width="135">Byte index</th><th width="157">Sent request</th><th>Response - Meaning</th></tr></thead><tbody><tr><td>0</td><td>42 – The command code.</td><td>42 – The command code.</td></tr><tr><td>1</td><td> </td><td>XX - Temperature hysteresis value, multiplied by 10.</td></tr></tbody></table>

**Example uplink:**

0x4210 - The temperature hysteresis is 1.6 degrees Celsius.
{% endtab %}
{% endtabs %}

{% hint style="warning" %}
The is no minimum limit for Thys (it can have a 0 value).

The maximum allowed values is 100, which corresponds to 10 degrees.
{% endhint %}


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.mclimate.eu/mclimate-lorawan-devices/devices/mclimate-vicki-lorawan/pre-46-vicki-lorawan-device-communication-protocol/operational-modes-and-temperature-control-algorithm/algorithm-3-proportional-integral.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
