How to Interface 4x4 Keypad in Embedded C: Simple Guide
To interface a
4x4 keypad in Embedded C, connect its rows and columns to microcontroller pins, configure rows as outputs and columns as inputs with pull-ups, then scan by setting rows low one by one and reading columns to detect pressed keys. Use a nested loop to check each key and map the row-column pair to the corresponding character.Syntax
Interfacing a 4x4 keypad involves setting microcontroller pins connected to rows as outputs and columns as inputs. You then scan keys by driving each row low and reading the column inputs to detect which key is pressed.
The main steps are:
- Initialize row pins as outputs and set them high.
- Initialize column pins as inputs with pull-up resistors.
- Scan each row by setting it low and checking columns for a low signal.
- Map the detected row and column to the corresponding key value.
c
void keypad_init(void) { // Set row pins as output and set high // Set column pins as input with pull-ups } char keypad_get_key(void) { for (int row = 0; row < 4; row++) { // Set current row low // Read columns // If column low, return mapped key // Set row high again } return '\0'; // No key pressed }
Example
This example shows how to scan a 4x4 keypad connected to PORTB pins of an 8-bit microcontroller. Rows are connected to pins RB0-RB3 and columns to RB4-RB7.
c
#include <xc.h> #define ROWS 4 #define COLS 4 // Key map for 4x4 keypad const char keys[ROWS][COLS] = { {'1', '2', '3', 'A'}, {'4', '5', '6', 'B'}, {'7', '8', '9', 'C'}, {'*', '0', '#', 'D'} }; // Initialize keypad pins void keypad_init(void) { TRISB = 0xF0; // RB0-RB3 output (rows), RB4-RB7 input (columns) PORTB = 0x0F; // Set rows high (RB0-RB3), columns high (RB4-RB7) pull-ups enabled } // Scan keypad and return pressed key or '\0' if none char keypad_get_key(void) { for (int row = 0; row < ROWS; row++) { PORTB = ~(1 << row) & 0x0F; // Drive one row low, keep columns high __delay_ms(5); // Small delay for signal to settle unsigned char col_val = PORTB & 0xF0; // Read columns for (int col = 0; col < COLS; col++) { if (!(col_val & (1 << (col + 4)))) { // Active low while (!(PORTB & (1 << (col + 4)))); // Wait for key release return keys[row][col]; } } } return '\0'; } int main(void) { keypad_init(); char key; while (1) { key = keypad_get_key(); if (key != '\0') { // Use the key value (e.g., display or process) } } return 0; }
Output
No direct output; returns pressed key character when a key is pressed.
Common Pitfalls
Common mistakes when interfacing a 4x4 keypad include:
- Not configuring rows as outputs and columns as inputs properly.
- Failing to enable pull-up resistors on column inputs, causing floating inputs and false readings.
- Not adding a small delay after setting a row low before reading columns, leading to unstable readings.
- Not waiting for key release, causing multiple detections of a single press.
c
/* Wrong way: No pull-ups and no delay */ void keypad_init_wrong(void) { TRISB = 0xF0; // Rows output, columns input PORTB = 0x00; // Rows low, no pull-ups } /* Right way: Pull-ups enabled and delay added */ void keypad_init_right(void) { TRISB = 0xF0; // Rows output, columns input PORTB = 0x0F; // Rows high, pull-ups enabled } char keypad_get_key_right(void) { for (int row = 0; row < 4; row++) { PORTB = ~(1 << row) & 0x0F; // Drive one row low, keep columns high __delay_ms(5); // Delay for stable reading // Read columns and detect key PORTB = 0x0F; // Reset rows high } return '\0'; }
Quick Reference
Summary tips for 4x4 keypad interfacing:
- Rows: Output pins, start high, drive low one at a time.
- Columns: Input pins with pull-up resistors enabled.
- Scan: Drive each row low, read columns for low signal.
- Debounce: Add small delay and wait for key release.
- Map row-column to key character using a 2D array.
Key Takeaways
Configure keypad rows as outputs and columns as inputs with pull-ups.
Scan keys by driving rows low one at a time and reading columns for pressed keys.
Add delays and wait for key release to avoid false or repeated detections.
Use a 2D array to map row-column pairs to keypad characters.
Test hardware connections and pin configurations carefully to avoid floating inputs.