// Include the required Arduino libraries:
#include <LedControl.h>
#include <EEPROM.h>
//define pin outputs for LedMatrix
int DIN = 11; //data input
int CS = 12; //control system input
int CLK = 13; //clock input
//byte map for checkmark display
byte checkmark [8] = {
B10000000,B01000000,B00100000,B00010000,B00001000,B00000101,B00000010,B00000000
};
//byte map for cross display
byte cross [8] = {
B10000001,B01000010,B00100100,B00011000,B00011000,B00100100,B01000010,B10000001
};
//byte map for circle display
byte circle [8] = {
B00111100,B01000010,B10000001,B10000001,B10000001,B10000001,B01000010,B00111100
};
//byte map for square display
byte sqr [8] = {
B00000000,B01111110,B01000010,B01000010,B01000010,B01000010,B01111110,B00000000
};
//byte map for target display
byte target [8] = {
B00111100,B01000010,B10011001,B10100101,B10100101,B10011001,B01000010,B00111100
};
//define pins used for LedMatrix as well as number of devices in chain
LedControl lc=LedControl(DIN, CLK, CS,0); // 0 means 1 device in chain
const int numRows = 4; //number of keypad rows
const int numCols = 4; //number of keypad columns
const int debounceTime = 20; //number of ms for debounce
const int maxChars = 9; //maximum characters for passcodes
//list of access codes
const String defaultPassCodes[4] = {"EEE20003","100997445","103182927","101957275"};
// keymap defines character returned when corresponding key is pressed
const char keymap[numRows][numCols] = {
{'1','2','3','A'},
{'4','5','6','B'},
{'7','8','9','C'},
{'*','0','#','D'}
};
//determining pins for rows and columns
const int rowPins[numRows] = {9,8,7,6};
const int colPins[numCols] = {5,4,3,2};
/*-----------------------SETUP-----------------------*/
void setup() {
Serial.begin(9600); //start up serial monitor
lc.shutdown(0,false); //turn on ledcontrol system
lc.setIntensity(0,15); // set led intensity
lc.clearDisplay(0); //clear led display
for (int row = 0; row < numRows; row++){
pinMode(rowPins[row],INPUT); //set row pins as input
digitalWrite(rowPins[row], HIGH); //turn on Pull-ups
}
for (int column = 0; column < numCols; column++){
pinMode(colPins[column],OUTPUT); //set column pins as output for writing
digitalWrite(colPins[column], HIGH); //deactivate columns
}
}
/*-----------------------LOOP-----------------------*/
void loop() {
delay(500);
Serial.println("\n-------- Welcome to the Access Control System -------\n");
/*---Keypad Entry---*/
delay(500);
Serial.println("------------ Keypad Online -----------");
keypad();
/*---Menu Options---*/
Serial.println("\n--------Welcome to the Access Control System-------\n");
Serial.println("Menu Options: ");
Serial.println(" 1 : Change Passcodes");
Serial.println(" 2 : Retrieve Temperature Data");
Serial.println(" 3 : Access Keypad");
while(Serial.available() > 0) Serial.read();
int select = menuSelect();
switch (select) {
case 1:
/*---Passcode Change---*/
Serial.println("--------Passcode Change Placeholder-------");
break;
case 2:
/*---Sensor Data---*/
Serial.println("--------Retrieve Temperature Data-------");
Serial.println(getTemperature());
break;
case 3:
/*---Keypad Entry---*/
Serial.println("------------Keypad-----------");
keypad();
}
delay(500);
}
//function to access system via default passcode in serial monitor
bool serialPass() {
String input = "";
Serial.println("Enter passcode in Serial Monitor to unlock Keypad: ");
Serial.println("Hint: it's EEE20003");
while (true) {
delay(100);
if (Serial.available() > 0) {
input = Serial.readString();
input.trim();
}
while(Serial.available() > 0) {Serial.read();}
if (input != "") {
Serial.println(input);
if (input == readFromEEPROM(0)){
Serial.println("\nKeypad Unlocked.\n");
return true;
}
else {
Serial.println("Invalid passcode. Try again :");
input = "";
}
}
}
}
//function to display main menu
int menuSelect(){
while (true){
if (Serial.available() > 0) {
char input = Serial.read();
if (input == '1'){
Serial.println("\n1");
return 1;
}
else if (input == '2'){
Serial.println("\n2");
return 2;
}
else if (input == '3') {
Serial.println("\n3");
return 3;
}
else {
Serial.println("\nUnknown Input");
}
}
while(Serial.available() > 0) Serial.read();
delay(500);
}
}
//function to use keypad
void keypad() {
String passEnter = "";
int count = 0;
String passCheck = "";
Serial.println("Select User");
if (Serial.available() > 0){
int UserCheck = Serial.read();
passCheck = defaultPassCodes[UserCheck];
}
while (true) {
Serial.println("Enter passcode on Keypad: ");
while (count < 9){
char key = getKey();
if (key != 0){ //checks for not 0
Serial.print(key);
if (key == passCheck.charAt(count)){
passEnter = passEnter + key;
count += 1;
}
else if (key != passCheck.charAt(count)){
ledDisplay(cross,5000);
break;
}
}
}
/*---Check Keypad Entry---*/
if (checkPasscode(passEnter)) {
break;
}
else {
passEnter = "";
count = 0;
}
}
}
//function to return the pressed key, or '0' if no key is pressed
char getKey() {
char key = 0; //sets 0 as no key pressed
for (int column = 0; column < numCols; column++){
digitalWrite(colPins[column], LOW); //activates current column
for (int row = 0; row < numRows; row++){ //scan rows for key press
if(digitalRead(rowPins[row]) == LOW){
delay(debounceTime);
while (digitalRead(rowPins[row]) == LOW)
; //wait for key to be released
key = keymap[row][column];
}
}
digitalWrite(colPins[column], HIGH); //deactivate current column
}
return key; //returns character of key press, or 0
}
//function to read temperature from sensor
String getTemperature() {
float BETA = 3950;
bool metricCelsius;
String temp;
Serial.println("Choose metric to read temperature: ");
Serial.println("1 : Celsius");
Serial.println("2 : Fahrenheit");
Serial.println();
while (true){
if (Serial.available() > 0) {
char selection = Serial.read();
if (selection == '1'){
metricCelsius = true;
break;
}
else if (selection == '2'){
metricCelsius = false;
break;
}
else {
Serial.println("Please enter value '1' (Celsius) or '2' (Fahrenheit).\n");
}
}
while(Serial.available() > 0) {Serial.read();}
delay(500);
}
int analogValue = analogRead(A0);
float celsius = 1 / (log(1 / (1023. / analogValue - 1)) / BETA + 1.0 / 298.15) - 273.15;
float fahren = celsius * 1.8 + 32;
if (metricCelsius) {
temp = "Temperature: "+String(celsius)+" C";
}
else {
temp = "Temperature "+String(fahren)+" F";
}
return temp;
}
//function to write passcode to EEPROM
void writeToEEPROM(String passcode, int passIndex) {
char passcodeArray[maxChars];
passcode.toCharArray(passcodeArray,maxChars+1);
for (int i = 0; i < maxChars+1; i++){
EEPROM.write((passIndex*(maxChars+1))+i, passcodeArray[i]);
}
}
//function to read passcode from EEPROM
String readFromEEPROM(int passIndex) {
String passRead = "";
for (int i = 0; i < maxChars; i++){
char digit = EEPROM.read((10*passIndex)+i);
if (isAlphaNumeric(digit)) {
passRead = passRead + digit;
}
}
return passRead;
}
//function to compare keypad entry to list of stored passcodes
bool checkPasscode(String passEnter) {
bool access = false;
for (int codeNum = 0; codeNum < sizeof(defaultPassCodes)/sizeof(defaultPassCodes[0]); codeNum++){
if (passEnter == defaultPassCodes[codeNum]){
access = true;
break;
}
}
if (access == true){
Serial.println("\n\n**** Access Granted. ****");
//display positive access response
for (int i=0;i<8;i++){
lc.setRow(0,i,checkmark[i]);
}
delay(2000);
lc.clearDisplay(0);
//series of if statements to identify and display
//specific bitmap to individual passcodes
if (passEnter == defaultPassCodes[1]){
for (int i=0;i<8;i++){
lc.setRow(0,i,circle[i]);
}
delay(3000);
lc.clearDisplay(0);
}
if (passEnter == defaultPassCodes[2]){
for (int i=0;i<8;i++){
lc.setRow(0,i,sqr[i]);
}
delay(3000);
lc.clearDisplay(0);
}
if (passEnter == defaultPassCodes[3]){
for (int i=0;i<8;i++){
lc.setRow(0,i,target[i]);
}
delay(3000);
lc.clearDisplay(0);
}
}
else {
Serial.println("\n\n**** Access Denied. ****");
//display negative access response
for (int i=0;i<8;i++){
lc.setRow(0,i,cross[i]);
}
delay(3000);
lc.clearDisplay(0);
}
return access;
}