We are running a survey to help us improve the experience for all of our members. If you see the survey appear, please take the time to tell us about your experience if you can.
I'm using 4 x 4 keypad to send the output to 2 7-segment LED.
problem: key de bouncing problem
Summary problem: when I press key, it shows both digit on the left and right. For example, if I first press 1, it should show 1 on the right and blank on the left. If I press 3 next, it should show 1 on the left and 3 on the right. Right now, it I press 1 it shows 1 on the left and 1 on the right. I think this relate to key debouncing. Please check my code.
void read(void) {
char left_val = 'n';
char right_val = 'n';
char next_val = readKeyPad();
while(1){
next_val = readKeyPad();
if (right_val == next_val || next_val == 'n'){
printChar(left_val, Left);
delay(FRAME_PERIOD);
printChar(right_val, Right);
}
else {
left_val = right_val;
right_val = next_val;
} }
Hey,
There are plenty of denouncing strategies defined in textbooks, with solutions in hardware, digital logic, and software.
I suggest you scope the signal, and see a typical period of noise. This would make your solution inherently empirical, so I wouldn't feel the need to make beautiful code.
Simply assert stability a certain number of iterations. If you have an RTOS, poll it with a task. If you don't want to consume so much resources polling it, your option is applying a period of time where the result is unstable, and effectively, "dont care" 'X' in DLD :).
Example for a polling code:
//Uvision calls compiler with compiler defines. E.g. "C166.exe DEFINE(TDD)" #include <stdint.h> //XintY_t #include <stdbool.h> //bool #include <stdlib.h> //rand bool eg_mySwitch(void) { #ifdef TDD //Returns psuedo 1 or 0 return ((rand() >> 1) >= (32767 >> 1)); #else //Your hardware abstraction #endif } //Hardware abstraction layer #define FILTER_WINDOW_LEN 10 //length of my window for the debouncer, find experimentally #define FILTER_MAX_ITERATIONS 10000 // Arbitrary exit condition... #define FILTER_X_GETSTATE eg_mySwitch //callback function that returns 1 or 0 bool poll_switch(bool endState) { static uint8_t s_vals[FILTER_WINDOW_LEN]; static uint8_t s_index; static uint8_t s_total; //Start polling while(s_index != FILTER_WINDOW_LEN) { s_vals[s_index] = FILTER_X_GETSTATE(); if(s_vals[s_index] == endState) s_index++; else s_index = 0; if(s_total++ == FILTER_MAX_ITERATIONS) return !endState; } //done return endState; }
I have always done keys in a (typically 10ms) "debounce time" timer ISR. two identical reads and you are OK. It just works and is dead simple