68 pcnt_unit_config_t unit_config = {
69 .low_limit = INT16_MIN,
70 .high_limit = INT16_MAX,
71 .flags = {.accum_count =
true},
73 esp_err_t error = pcnt_new_unit(&unit_config, &this->
pcnt_unit);
74 if (error != ESP_OK) {
75 ESP_LOGE(TAG,
"Creating PCNT unit failed: %s", esp_err_to_name(error));
79 pcnt_chan_config_t chan_config = {
80 .edge_gpio_num =
static_cast<gpio_num_t
>(this->pin->
get_pin()),
81 .level_gpio_num = GPIO_NUM_NC,
84 if (error != ESP_OK) {
85 ESP_LOGE(TAG,
"Creating PCNT channel failed: %s", esp_err_to_name(error));
89 pcnt_channel_edge_action_t rising = PCNT_CHANNEL_EDGE_ACTION_HOLD;
90 pcnt_channel_edge_action_t falling = PCNT_CHANNEL_EDGE_ACTION_HOLD;
93 rising = PCNT_CHANNEL_EDGE_ACTION_HOLD;
96 rising = PCNT_CHANNEL_EDGE_ACTION_INCREASE;
99 rising = PCNT_CHANNEL_EDGE_ACTION_DECREASE;
104 falling = PCNT_CHANNEL_EDGE_ACTION_HOLD;
107 falling = PCNT_CHANNEL_EDGE_ACTION_INCREASE;
110 falling = PCNT_CHANNEL_EDGE_ACTION_DECREASE;
114 error = pcnt_channel_set_edge_action(this->
pcnt_channel, rising, falling);
115 if (error != ESP_OK) {
116 ESP_LOGE(TAG,
"Setting PCNT edge action failed: %s", esp_err_to_name(error));
121 uint32_t max_glitch_ns = PCNT_LL_MAX_GLITCH_WIDTH * 1000u / ((
uint32_t) esp_clk_apb_freq() / 1000000u);
122 pcnt_glitch_filter_config_t filter_config = {
123 .max_glitch_ns = std::min(this->
filter_us * 1000u, max_glitch_ns),
125 error = pcnt_unit_set_glitch_filter(this->
pcnt_unit, &filter_config);
126 if (error != ESP_OK) {
127 ESP_LOGE(TAG,
"Setting PCNT glitch filter failed: %s", esp_err_to_name(error));
132 error = pcnt_unit_add_watch_point(this->
pcnt_unit, INT16_MIN);
133 if (error != ESP_OK) {
134 ESP_LOGE(TAG,
"Adding PCNT low limit watch point failed: %s", esp_err_to_name(error));
137 error = pcnt_unit_add_watch_point(this->
pcnt_unit, INT16_MAX);
138 if (error != ESP_OK) {
139 ESP_LOGE(TAG,
"Adding PCNT high limit watch point failed: %s", esp_err_to_name(error));
143 error = pcnt_unit_enable(this->
pcnt_unit);
144 if (error != ESP_OK) {
145 ESP_LOGE(TAG,
"Enabling PCNT unit failed: %s", esp_err_to_name(error));
148 error = pcnt_unit_clear_count(this->
pcnt_unit);
149 if (error != ESP_OK) {
150 ESP_LOGE(TAG,
"Clearing PCNT unit failed: %s", esp_err_to_name(error));
153 error = pcnt_unit_start(this->
pcnt_unit);
154 if (error != ESP_OK) {
155 ESP_LOGE(TAG,
"Starting PCNT unit failed: %s", esp_err_to_name(error));