******** Счетчики ******** Счетчики используются для подсчета событий. .. _ctu-counter: CTU — Инкрементный счетчик ========================== Увеличивает значение счетчика при каждом переднем фронте на входе CU. **Входные параметры:** - ``CU`` (BOOL) — вход увеличения (реагирует на передний фронт) - ``RESET`` (BOOL) — сброс счетчика в 0 - ``PV`` (WORD) — предельное значение **Выходные параметры:** - ``Q`` (BOOL) — TRUE, когда ``CV >= PV`` - ``CV`` (WORD) — текущее значение счетчика **Описание работы:** Блок CTU увеличивает внутреннее значение счетчика на 1 при каждом обнаружении переднего фронта на входе CU. Если вход RESET активен (TRUE), счетчик сбрасывается в 0. Выход Q становится TRUE, когда текущее значение счетчика достигает или превышает предельное значение PV. При этом счетчик продолжает увеличиваться, и Q остается TRUE. **Пример использования:** .. code-table:: PROGRAM Example VAR ctu1 : CTU; count_up : BOOL; reset_count : BOOL; counter_value : WORD; reached_limit : BOOL; END_VAR ctu1(CU := count_up, RESET := reset_count, PV := 10); counter_value := ctu1.CV; reached_limit := ctu1.Q; END_PROGRAM **Внутренняя реализация:** Исходный код блока: .. code-table:: FUNCTION_BLOCK CTU VAR_INPUT CU : BOOL; RESET : BOOL; PV : WORD; END_VAR VAR_OUTPUT Q : BOOL; CV : WORD; END_VAR VAR rt : R_TRIG; V : WORD; END_VAR rt(CLK := CU); IF RESET THEN V := 0; ELSE IF rt.Q THEN V := V + 1; END_IF; END_IF; Q := V >= PV; CV := V; END_FUNCTION_BLOCK .. _ctd-counter: CTD — Декрементный счетчик ========================== Уменьшает значение счетчика при каждом переднем фронте на входе CD. **Входные параметры:** - ``CD`` (BOOL) — вход уменьшения (реагирует на передний фронт) - ``LOAD`` (BOOL) — загрузка начального значения из PV - ``PV`` (WORD) — начальное значение **Выходные параметры:** - ``Q`` (BOOL) — TRUE, когда ``CV = 0`` - ``CV`` (WORD) — текущее значение счетчика **Описание работы:** Блок CTD уменьшает внутреннее значение счетчика на 1 при каждом обнаружении переднего фронта на входе CD, но только если текущее значение больше 0. Если вход LOAD активен (TRUE), в счетчик загружается начальное значение из PV. Выход Q становится TRUE, когда текущее значение счетчика равно 0. При достижении 0 дальнейшее уменьшение не происходит. **Пример использования:** .. code-table:: PROGRAM Example VAR ctd1 : CTD; count_down : BOOL; load_count : BOOL; counter_value : WORD; reached_zero : BOOL; END_VAR ctd1(CD := count_down, LOAD := load_count, PV := 10); counter_value := ctd1.CV; reached_zero := ctd1.Q; END_PROGRAM **Внутренняя реализация:** Исходный код блока: .. code-table:: FUNCTION_BLOCK CTD VAR_INPUT CD : BOOL; LOAD : BOOL; PV : WORD; END_VAR VAR_OUTPUT Q : BOOL; CV : WORD; END_VAR VAR rt : R_TRIG; V : WORD; END_VAR rt(CLK := CD); IF LOAD THEN V := PV; ELSE IF rt.Q AND V > 0 THEN V := V - 1; END_IF; END_IF; Q := V = 0; CV := V; END_FUNCTION_BLOCK .. _ctud-counter: CTUD — Реверсивный счетчик ========================== Может увеличивать и уменьшать значение счетчика. **Входные параметры:** - ``CU`` (BOOL) — вход увеличения (реагирует на передний фронт) - ``CD`` (BOOL) — вход уменьшения (реагирует на передний фронт) - ``RESET`` (BOOL) — сброс счетчика в 0 - ``LOAD`` (BOOL) — загрузка начального значения из PV - ``PV`` (WORD) — начальное значение / предельное значение **Выходные параметры:** - ``QU`` (BOOL) — TRUE, когда ``CV >= PV`` - ``QD`` (BOOL) — TRUE, когда ``CV = 0`` - ``CV`` (WORD) — текущее значение счетчика **Описание работы:** Блок CTUD объединяет функции инкрементного и декрементного счетчиков. При каждом переднем фронте на входе CU значение увеличивается на 1. При каждом переднем фронте на входе CD значение уменьшается на 1 (если V > 0). Вход LOAD загружает начальное значение из PV. Вход RESET имеет приоритет над LOAD и сбрасывает счетчик в 0. Выход QU становится TRUE, когда CV >= PV. Выход QD становится TRUE, когда CV = 0. **Пример использования:** .. code-table:: PROGRAM Example VAR ctud1 : CTUD; count_up : BOOL; count_down : BOOL; reset_count : BOOL; load_count : BOOL; counter_value : WORD; up_reached : BOOL; down_reached : BOOL; END_VAR ctud1(CU := count_up, CD := count_down, RESET := reset_count, LOAD := load_count, PV := 10); counter_value := ctud1.CV; up_reached := ctud1.QU; down_reached := ctud1.QD; END_PROGRAM **Внутренняя реализация:** Исходный код блока: .. code-table:: FUNCTION_BLOCK CTUD VAR_INPUT CU : BOOL; CD : BOOL; RESET : BOOL; LOAD : BOOL; PV : WORD; END_VAR VAR_OUTPUT QU : BOOL; QD : BOOL; CV : WORD; END_VAR VAR rt_UP : R_TRIG; rt_DOWN : R_TRIG; V : WORD; END_VAR rt_UP(CLK := CU); rt_DOWN(CLK := CD); IF LOAD THEN V := PV; ELSE IF rt_DOWN.Q AND V > 0 THEN V := V - 1; END_IF; END_IF; IF RESET THEN V := 0; ELSE IF rt_UP.Q THEN V := V + 1; END_IF; END_IF; QU := V >= PV; QD := V = 0; CV := V; END_FUNCTION_BLOCK .. seealso:: * :doc:`data_types` - для информации о числовых типах данных. * :doc:`edge_detection` - для детекторов фронтов.