I successfully used the code of jgustavoam! Thanks a lot. This was the only clear source on Arduino IDE and ESP32 pulse counter, which I found on the net. I was happy to understand your Portuguese with my Spanish, so that your comments plus the explanations from
https://docs.espressif.com/projects/esp ... ing-pulses added up to a lot of sense.
#include "driver/pcnt.h" worked without any additional step in Arduino IDE after having installed the
arduino-esp32-master
i.e. in my case the file was already there at the following path C:\Users\User\Documents\Arduino\hardware\arduino-esp32-master\tools\sdk\include\driver\driver\pcnt.h
when in the Arduino IDE properties the sketchbook storage location had been set to C:\Users\User\Documents\Arduino
My remaining problem for the correct pulse count are glitches. Significant overcounting improved somewhat, but not completely, after defining the pulse counter filter:
https://docs.espressif.com/projects/esp ... ing-pulses
Increasing the filter value to 1000, i.e. close to maximum, did not yet solve the problem. Any further idea would be helpful.
For the Forum find here my conversion of the code of jgustavoam to English:
Code: Select all
#include "driver/pcnt.h" // ESP32 library for pulse count
// e.g. stored in following path C:\Users\User\Documents\Arduino\hardware\arduino-esp32-master\tools\sdk\include\driver\driver\pcnt.h
// when in the Arduino IDE properties the sketchbook storage location is set to C:\Users\User\Documents\Arduino
#define PCNT_FREQ_UNIT PCNT_UNIT_0 // select ESP32 pulse counter unit 0 (out of 0 to 7 indipendent counting units)
// https://docs.espressif.com/projects/esp-idf/en/latest/esp32/api-reference/peripherals/pcnt.html
int SPEED_IR_INPUT_PIN = 15; // Input D15 = signal from IR-diode for pulse counter
bool _flag = 0; // only for testing ####################################
int16_t PulseCounter = 0; // pulse counter, max. value is 65536
int OverflowCounter = 0; // pulse counter overflow counter
int PCNT_H_LIM_VAL = 10000; // upper limit of counting max. 32767, write +1 to overflow counter, when reached
uint16_t PCNT_FILTER_VAL= 1000; // filter (damping, inertia) value for avoiding glitches in the count, max. 1023
// not in use, copy from example code ########################################
//float frequencia = 0; // Frequencia medida
//String unidade; // Unidade de medida da escala
//unsigned long tempo; // base de tempo da medida dos pulsos
//int prescaler; // frequency devider of timer
//bool conterOK = false;
pcnt_isr_handle_t user_isr_handle = NULL; // interrupt handler - not used
hw_timer_t * timer = NULL; // Instancia do timer
void IRAM_ATTR CounterOverflow(void *arg) { // Interrupt for overflow of pulse counter
OverflowCounter = OverflowCounter + 1; // increase overflow counter
PCNT.int_clr.val = BIT(PCNT_FREQ_UNIT); // clean overflow flag
pcnt_counter_clear(PCNT_FREQ_UNIT); // zero and reset of pulse counter unit
}
void initPulseCounter (){ // initialise pulse counter
pcnt_config_t pcntFreqConfig = { }; // Instance of pulse counter
pcntFreqConfig.pulse_gpio_num = SPEED_IR_INPUT_PIN; // pin assignment for pulse counter = GPIO 15
pcntFreqConfig.pos_mode = PCNT_COUNT_INC; // count rising edges (=change from low to high logical level) as pulses
pcntFreqConfig.counter_h_lim = PCNT_H_LIM_VAL; // set upper limit of counting
pcntFreqConfig.unit = PCNT_FREQ_UNIT; // select ESP32 pulse counter unit 0
pcntFreqConfig.channel = PCNT_CHANNEL_0; // select channel 0 of pulse counter unit 0
pcnt_unit_config(&pcntFreqConfig); // configur rigisters of the pulse counter
pcnt_counter_pause(PCNT_FREQ_UNIT); // pause puls counter unit
pcnt_counter_clear(PCNT_FREQ_UNIT); // zero and reset of pulse counter unit
pcnt_event_enable(PCNT_FREQ_UNIT, PCNT_EVT_H_LIM); // enable event for interrupt on reaching upper limit of counting
pcnt_isr_register(CounterOverflow, NULL, 0, &user_isr_handle); // configure register overflow interrupt handler
pcnt_intr_enable(PCNT_FREQ_UNIT); // enable overflow interrupt
pcnt_set_filter_value(PCNT_FREQ_UNIT, PCNT_FILTER_VAL); // set damping, inertia
pcnt_filter_enable(PCNT_FREQ_UNIT); // enable counter glitch filter (damping)
pcnt_counter_resume(PCNT_FREQ_UNIT); // resume counting on pulse counter unit
}
void Read_Reset_PCNT() { // function for reading pulse counter (for timer)
pcnt_get_counter_value(PCNT_FREQ_UNIT, &PulseCounter); // get pulse counter value - maximum value is 16 bits
// resetting counter as if example, delet for application in PiedPiperS
OverflowCounter = 0; // set overflow counter to zero
pcnt_counter_clear(PCNT_FREQ_UNIT); // zero and reset of pulse counter unit
//conterOK = true; // not in use, copy from example code ########################################
}
void Read_PCNT() { // function for reading pulse counter (for timer)
pcnt_get_counter_value(PCNT_FREQ_UNIT, &PulseCounter); // get pulse counter value - maximum value is 16 bits
}