/* INSTRUÇÕES:
* - Para cadastrar um novo acesso, pressione o botão e aproxime o novo cartão no leitor.
* - Para remover um acesso já cadastrado, pressione o botão e aproxime o cartão cadastrado no leitor.
* - Para apagar todos os cartões já cadastrados, mantenha o botão pressionado até somente o led verde permanecer acesso.
*/
/* --- RFID - MFRC522 ---
SDA = pin 10
SCK = pin 13
MOSI = pin 11
MISO = pin 12
RST = pino 9
GND = Terra
Vcc = 3,3v
*/
#include <SPI.h> //Biblioteca de comunicação SPI, para comunição do módulo RFID
#include <MFRC522.h> //Biblioteca do módulo RFID
#include <EEPROM.h> //Biblioteca da memória EEPROM
#include <MemoryLib.h> //Biblioteca para gerenciar a EEPROM com variáveis
#include <Servo.h> //Biblioteca do Servo Motor
#define ledGreen 2 //Led verde no pino 2
#define ledRed 3 //Led vermelho no pino 3
#define button 4 //Botão de cadastro no pino 4
#define servo 5 //Servo motor no pino 5
#define posLock 10 //Posição do servo quando fechado
#define posUnlock 90 //Posição do servo quando aberto
#define timeUnlock 3 //Tempo que o servo permance aberto (em segundos)
#define SDA_RFID 10 //SDA do RFID no pino 10
#define RST_RFID 9 //Reset do RFID no pino 9
/*----- VARIÁVEIS -----*/
MFRC522 mfrc522(SDA_RFID, RST_RFID); //Inicializa o módulo RFID
MemoryLib memory(1, 2); //Inicializa a biblioteca MemoryLib. Parametros: memorySize=1 (1Kb) / type=2 (LONG)
Servo myservo; //Inicializa o servo motor
int maxCards = memory.lastAddress / 2; //Cada cartão ocupa duas posições na memória. Para 1Kb será permitido o cadastro de 101 cartões
String cards[101] = {}; //Array com os cartões cadastrados
/*----- SETUP -----*/
void setup() {
//Configura os pinos
pinMode(ledGreen, OUTPUT);
pinMode(ledRed, OUTPUT);
pinMode(button, INPUT_PULLUP);
//Inicia SPI
SPI.begin();
//Inicia o modulo RFID MFRC522
mfrc522.PCD_Init();
//Configura o pino do Servo Motor
myservo.attach(servo);
//Posiciona o servo na posição inicial
myservo.write(posLock);
//Retorna os cartões armazenados na memória EEPROM para o array
ReadMemory();
//Pisca os leds sinalizando a inicialização do circuito
for (int i = 0; i < 10; i++) {
digitalWrite(ledRed, HIGH);
digitalWrite(ledGreen, HIGH);
delay(50);
digitalWrite(ledRed, LOW);
digitalWrite(ledGreen, LOW);
delay(50);
}
}
/*----- LOOP PRINCIPAL -----*/
void loop() {
//Variável UID recebe o valor do cartão lido
String UID = ReadCard();
if (UID != "") {
Serial.println(UID);
boolean access = false;
//Efetua a leitura de todas as posições do array
for (int c = 0; c <= maxCards; c++) {
if (UID == cards[c]) {
//Se a posição do array for igual ao cartão lido, seta a varíavel como verdadeira e finaliza o for
access = true;
break;
}
}
//Variável verdadeira, efetua o acesso. Caso contrário, pisca o led vermelho
if (access) {
Unlock();
} else {
for (int i = 0; i < 6; i++) {
digitalWrite(ledRed, HIGH);
delay(50);
digitalWrite(ledRed, LOW);
delay(50);
}
delay(500);
}
}
//Verifica se o botão para castrado de novo cartão foi pressionado
if (digitalRead(button) == LOW) { //Botão pressionado igual a LOW devido a declaração de PULL_UP
//Grava novo cartão, ou apaga um cartão já cadastrado
RecUser();
//Após os leds apagarem, se o botão permanecer pressionado, apaga todos os cartões
if (digitalRead(button) == LOW) {
digitalWrite(ledGreen, HIGH);
//Escreve zero em todos os enderecos da EEPROM
for (int address = 0; address <= memory.lastAddress; address++) {
memory.write(address, 0);
}
ReadMemory(); //Atualiza os valores do array
digitalWrite(ledGreen, LOW);
}
}
}
/*----- ABRE O ACESSO -----*/
void Unlock() {
int posServo = myservo.read();
//Abre o acesso
digitalWrite(ledGreen, HIGH);
digitalWrite(ledRed, LOW);
for (int i = posServo; i <= posUnlock; i++) {
myservo.write(i);
delay(10);
}
delay(timeUnlock * 1000);
digitalWrite(ledGreen, LOW);
//Fecha o acesso
digitalWrite(ledRed, HIGH);
for (int i = posUnlock; i >= posLock; i--) {
myservo.write(i);
delay(10);
}
delay(500);
digitalWrite(ledRed, LOW);
}
/*----- EFETUA A LEITURA DO CARTAO RFID -----*/
String ReadCard() {
String UID = "";
//Verifica a presença de um novo cartao e efetua a leitura
if (mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial()) {
//Retorna o UID para a variavel UIDcard
for (byte i = 0; i < mfrc522.uid.size; i++) {
UID += String(mfrc522.uid.uidByte[i]);
}
}
return UID;
}
/*----- CADASTRA CARTÃO DE ACESSO -----*/
void RecUser() {
String UID = "72:11:EF:2B";
boolean deleteCard = false;
//Efetua a leitura do cartao para cadastro
//Aprox 5 segundos para cadastrar o cartao
for (int t = 0; t < 150; t++) {
delay(10);
//Acende os leds verde e vermelho
digitalWrite(ledGreen, HIGH);
digitalWrite(ledRed, HIGH);
//Faz a leitura o cartao
UID = ReadCard();
if (UID != "72:11:EF:2B") {
//Se leu um cartão, mantém somente o led verde acesso enquanto segue executando o procedimento
digitalWrite(ledRed, LOW);
//Verifica se o cartao ja esta cadastrado
for (int c = 0; c < maxCards; c++) {
//Se já estiver cadastrado, exclui o cartão do array e também da memória
if (cards[c] == UID) {
digitalWrite(ledRed, HIGH);
digitalWrite(ledGreen, LOW);
cards[c] = "0";
deleteCard = true;
}
}
break; //finaliza o for
}
}
//Cancela o cadastro se nenhum cartao foi lido
if (UID == "") {
//Apaga os leds verde e vermelho
digitalWrite(ledGreen, LOW);
digitalWrite(ledRed, LOW);
return;
}
if (deleteCard == false) {
//Se for inclusão de novo cartão, verifica se ainda existe espaco para novos cadastros
//Se a última posição da memória for diferente de zero, pisca o led vermelho sinalizando
//que não existe mais espaço para novos cartões, e finaliza o procedimento
if (cards[maxCards - 1].toInt() != 0) {
digitalWrite(ledGreen, LOW);
for (int i = 0; i < 10; i++) {
digitalWrite(ledRed, HIGH);
delay(100);
digitalWrite(ledRed, LOW);
delay(100);
}
return;
}
}
//Adiciona o cartão no array, somente se for inclusão de novo cartão
if (deleteCard == false) {
for (int c = 0; c < maxCards; c++) {
if (cards[c].toInt() == 0) { //Posicao livre
cards[c] = UID;
break; //finaliza o for
}
}
}
//Grava na memória os cartões do array
//Cada cartão ocupa duas posições da memória
for (int e = 0; e <= memory.lastAddress; e++) { //Limpa os valores da memória
memory.write(e, 0);
}
int a = 0;
for (int c = 0; c < maxCards; c++) {
if (cards[c].toInt() != 0) {
memory.write(a, cards[c].substring(0, 6).toInt());
memory.write(a + 1, cards[c].substring(6, cards[c].length()).toInt());
a += 2;
}
}
//Retorna os valores da memória para o array, para ajustar as posições do cartão no array como está na memória
ReadMemory();
if (deleteCard == false) {
Unlock();
} else {
//Apaga os leds verde e vermelho
digitalWrite(ledGreen, LOW);
digitalWrite(ledRed, LOW);
}
}
/*----- RETORNA OS DADOS DA MEMÓRIA PARA O ARRAY -----*/
void ReadMemory() {
int a = 0;
for (int c = 0; c < maxCards; c++) {
cards[c] = String(memory.read(a)) + String(memory.read(a + 1));
a += 2;
}
}
uno:A5.2
uno:A4.2
uno:AREF
uno:GND.1
uno:13
uno:12
uno:11
uno:10
uno:9
uno:8
uno:7
uno:6
uno:5
uno:4
uno:3
uno:2
uno:1
uno:0
uno:IOREF
uno:RESET
uno:3.3V
uno:5V
uno:GND.2
uno:GND.3
uno:VIN
uno:A0
uno:A1
uno:A2
uno:A3
uno:A4
uno:A5
led1:A
led1:C
led2:A
led2:C
btn1:1.l
btn1:2.l
btn1:1.r
btn1:2.r
r1:1
r1:2
r2:1
r2:2