#include <stdio.h>
#include "pico/stdlib.h"
#include <string.h>
#define SET 1
#define RESET 0
#define COMP 4
char password1[COMP+1] = {0};
// Define os pinos GPIO para as linhas e para as colunas
const uint8_t Linha[] = {2, 3, 4, 5};
const uint8_t Coluna[] = {6, 7, 8, 9};
// Define os pinos GPIO para os LEDs e o display de 7 segmentos
const uint8_t LED_VERDE = 10;
const uint8_t LED_VERMELHO = 11;
const uint8_t Display[] = {12, 13, 14, 15, 16, 17, 18}; // Pinos para os segmentos do display de 7 segmentos
const uint8_t mux_display_pins[] = {19, 20, 21, 22}; // Pinos para controle dos displays
// Mapeamento das teclas em uma matriz 4x4
char teclas[4][4] = {
{'1', '2', '3', 'A'},
{'4', '5', '6', 'B'},
{'7', '8', '9', 'C'},
{'*', '0', '#', 'D'}
};
// Mapeamento dos segmentos do display para cada dígito de 0 a 9
const uint8_t segmentos[10][7] = {
{RESET, RESET, RESET, RESET, RESET, RESET, SET}, // 0
{SET, RESET, RESET, SET, SET, SET, SET}, // 1
{RESET, RESET, SET, RESET, RESET, SET, RESET}, // 2
{RESET, RESET, RESET, RESET, SET, SET, RESET}, // 3
{SET, RESET, RESET, SET, SET, RESET, RESET}, // 4
{RESET, SET, RESET, RESET, SET, RESET, RESET}, // 5
{RESET, SET, RESET, RESET, RESET, RESET, RESET}, // 6
{RESET, RESET, RESET, SET, SET, SET, SET}, // 7
{RESET, RESET, RESET, RESET, RESET, RESET, RESET}, // 8
{RESET, RESET, RESET, SET, SET, RESET, RESET} // 9
};
// Inicializando os pinos de GPIO e os LEDs
void init_teclado() {
for (int i = 0; i < 4; i++) {
// Configuração das linhas como saídas
gpio_init(Linha[i]);
gpio_set_dir(Linha[i], GPIO_OUT);
gpio_put(Linha[i], RESET);
// Configuração das colunas como entradas
gpio_init(Coluna[i]);
gpio_set_dir(Coluna[i], GPIO_IN);
gpio_pull_down(Coluna[i]); // força as colunas para zero.
}
// Inicialização dos pinos dos LEDs
gpio_init(LED_VERDE);
gpio_set_dir(LED_VERDE, GPIO_OUT);
gpio_put(LED_VERDE, RESET);
gpio_init(LED_VERMELHO);
gpio_set_dir(LED_VERMELHO, GPIO_OUT);
gpio_put(LED_VERMELHO, RESET);
// Inicialização dos pinos do display de 7 segmentos
for (int i = 0; i < 7; i++) {
gpio_init(Display[i]);
gpio_set_dir(Display[i], GPIO_OUT);
gpio_put(Display[i], RESET);
}
// Inicialização dos pinos de controle dos displays
for (int i = 0; i < 4; i++) {
gpio_init(mux_display_pins[i]);
gpio_set_dir(mux_display_pins[i], GPIO_OUT);
gpio_put(mux_display_pins[i], 1); // Desativa os displays inicialmente
}
}
// Varredura do teclado e retorno da tecla pressionada
char leitura_teclado() {
for (int row = 0; row < 4; row++) {
// Coloca a linha atual em nível alto
gpio_put(Linha[row], SET);
for (int col = 0; col < 4; col++) {
if (gpio_get(Coluna[col])) {
// Espera um tempo para estabilização da tecla pressionada
sleep_ms(100);
while (gpio_get(Coluna[col])); // Espera até a tecla ser liberada
gpio_put(Linha[row], RESET); // Reseta a linha atual
return teclas[row][col];
}
}
// Coloca a linha atual novamente para nível baixo
gpio_put(Linha[row], RESET);
}
return 0;
}
// Função para mostrar um dígito em um dos displays selecionados
void show_digit(uint8_t digits, uint8_t digit) {
// Desativa todos os displays
for (int i = 0; i < 4; i++) {
gpio_put(mux_display_pins[i], 1);
}
// Ativa os segmentos referentes ao dígito
for (int i = 0; i < 7; i++) {
gpio_put(Display[i], segmentos[digit][i]);
}
// Ativa o display especificado
gpio_put(mux_display_pins[digits], 0);
}
// Função para pegar a senha digitada
void get_senha(char *senha, int tam) {
int index = 0;
while (index < tam) {
char key = leitura_teclado();
if (key != 0) {
Serial1.printf("%c", key); // Usar Serial1.printf para imprimir no Serial Monitor
senha[index] = key;
if (key >= '0' && key <= '9') {
uint8_t digit = key - '0';
for (int i = 0; i < 100; i++) { // Multiplexação rápida
for (int j = 0; j < 4; j++) { // Mostrar em todos os displays
show_digit(j, digit);
sleep_ms(5);
}
}
}
index++;
sleep_ms(100);
}
}
senha[tam] = '\0';
}
// Função para comparar duas senhas
bool compare_senhas(const char *password1, const char *password2) {
return strcmp(password1, password2) == 0;
}
void setup() {
Serial1.begin(115200); // Iniciar a comunicação serial corretamente
init_teclado();
Serial1.println("Cadastro da senha do cofre com 4 digitos!");
get_senha(password1, COMP);
Serial1.println("\nSenha gravada!");
}
void loop() {
static int cont = 0;
static bool acesso = true;
if (acesso) {
Serial1.println("Digite a senha do cofre de 4 digitos!");
char input[COMP+1] = {0};
get_senha(input, COMP);
if (compare_senhas(input, password1)) {
Serial1.println("\nSenha Correta: Acesso ao cofre!");
gpio_put(LED_VERDE, SET);
sleep_ms(2000);
gpio_put(LED_VERDE, RESET);
acesso = false;
} else {
Serial1.println("\nSenha Incorreta: Acesso ao cofre negado!");
gpio_put(LED_VERMELHO, SET);
sleep_ms(1000);
gpio_put(LED_VERMELHO, RESET);
cont++;
}
sleep_ms(50); // estabilização
if (cont > 2) {
Serial1.println("\n Três tentativas bloqueadas por 5 segundos!");
sleep_ms(5000);
cont = 0;
}
}
}