Skip to content

Counter function blocks

Counters accumulate rising edges on their count inputs. The base types count with INT; typed variants (_INT, _DINT, _LINT, _UDINT, _ULINT) widen the preset PV and current value CV to the named integer type.

Counts rising edges on CU. Q is TRUE when the count reaches the preset PV. R resets the count to zero. Typed variants: CTU_INT, CTU_DINT, CTU_LINT, CTU_UDINT, CTU_ULINT.

DirectionNameTypeMeaning
InputCUBOOLCount-up trigger (rising edge)
InputRBOOLReset
InputPVINT¹Preset value
OutputQBOOLTRUE when CV ≥ PV
OutputCVINT¹Current count

¹ PV/CV follow the typed variant: DINT for CTU_DINT, LINT for CTU_LINT, UDINT for CTU_UDINT, ULINT for CTU_ULINT.

FUNCTION_BLOCK CTU
VAR_INPUT
CU : BOOL;
R : BOOL;
PV : INT;
END_VAR
VAR_OUTPUT
Q : BOOL;
CV : INT;
END_VAR
END_FUNCTION_BLOCK
VAR
counter : CTU;
END_VAR
counter(CU := partDetected, R := resetBtn, PV := 10);
batchFull := counter.Q; // TRUE once 10 parts counted
count := counter.CV;

Counts rising edges on CD downward from the preset value. LD loads PV into CV. Q is TRUE when CV reaches zero. Typed variants: CTD_INT, CTD_DINT, CTD_LINT, CTD_UDINT, CTD_ULINT.

DirectionNameTypeMeaning
InputCDBOOLCount-down trigger (rising edge)
InputLDBOOLLoad preset into CV
InputPVINT¹Preset value
OutputQBOOLTRUE when CV ≤ 0
OutputCVINT¹Current count

¹ Width follows the typed variant, as for CTU.

FUNCTION_BLOCK CTD
VAR_INPUT
CD : BOOL;
LD : BOOL;
PV : INT;
END_VAR
VAR_OUTPUT
Q : BOOL;
CV : INT;
END_VAR
END_FUNCTION_BLOCK
VAR
remaining : CTD;
END_VAR
remaining(CD := itemShipped, LD := reload, PV := 20);
empty := remaining.Q; // TRUE once CV counts down to 0
left := remaining.CV;

Combined up/down counter. Typed variants: CTUD_INT, CTUD_DINT, CTUD_LINT, CTUD_UDINT, CTUD_ULINT.

DirectionNameTypeMeaning
InputCUBOOLCount-up trigger (rising edge)
InputCDBOOLCount-down trigger (rising edge)
InputRBOOLReset CV to 0
InputLDBOOLLoad PV into CV
InputPVINT¹Preset value
OutputQUBOOLTRUE when CV ≥ PV
OutputQDBOOLTRUE when CV ≤ 0
OutputCVINT¹Current count

¹ Width follows the typed variant, as for CTU.

FUNCTION_BLOCK CTUD
VAR_INPUT
CU : BOOL;
CD : BOOL;
R : BOOL;
LD : BOOL;
PV : INT;
END_VAR
VAR_OUTPUT
QU : BOOL;
QD : BOOL;
CV : INT;
END_VAR
END_FUNCTION_BLOCK
VAR
stock : CTUD;
END_VAR
stock(CU := incoming, CD := outgoing, R := FALSE, LD := FALSE, PV := 100);
level := stock.CV;