Kód: Vybrat vše
#include <TimeLib.h> // Time library
#include <SPI.h> // SPI library
#include <Wire.h> // Include Wire.h to control I2C
#include <LiquidCrystal_I2C.h> //Download & include the code library can be downloaded below
#include <EEPROM.h>
// Definig the relay pin
#define RELAY_IN1 32
#define RELAY_IN2 30
#define RELAY_IN3 31
#define RELAY_IN4 33
#define BUZZER 13 //buzzer pin
#define LED_R 9 //define red LED
// variables of times
int h,m,s;
int set_hours=14;
int set_minutes=25;
int set_seconds=30;
int secs=1000;
// nasledujici kod je kvuli RFID ctecky
#define MAX_BITS 100 // max number of bits
#define WEIGAND_WAIT_TIME 1 // time to wait for another weigand pulse.
unsigned char databits[MAX_BITS]; //{0,0,0,1,1,0,1,1,0,1,1,1,1,1,0,0,1,1,1,1,1,1,0,1,1}; // stores all of the data bits (obrat poslednich 22 cisel a pote pridej 3 nuly pro test)
unsigned char bitCount26; // number of bits currently captured
unsigned char flagDone; // goes low when data is currently being captured
unsigned int weigand_counter; // countdown until we assume there are no more bits
unsigned long facilityCode= 0; // decoded facility code
unsigned long cardCode=0; // decoded card code
// LCD displej
LiquidCrystal_I2C lcd(0x27,2,1,0,4,5,6,7,3, POSITIVE); // Initialize LCD Display at address 0x27
// pole pro napis schvaleno na LCD displeji a dalsi
char array1[] = " Schvaleno "; //the string to print on the LCD
int tim = 100; //the value of delay time
char array2[] = " Priloz kartu! "; //the string to print on the LCD
char array3[]=" Pocet minut: ";
// pole card pro ulozeni cisel karet v DEC soustave
unsigned long int card [216] = {1368059,3771387,2470395,1602043,1665019,3124731,4046331,3456763,3925499,3188475,303355,4089339,3710459,3522299,128507,3775227,3704571,3852539,3844347,2591995,2526203,1869051,2858491,3602939,1337851,3835387,1079803,3379963,4033019,3654651,2745595,183547,2603771,2258939,311803,236795,838395,223483,225787,113915,1042427,2652667,2614779,3323643,2734587,586235,2480635,3395835,259579,814331,2419195,1535236,2750459,3259387,3185915,1176315,903675,2403835,2323707,3789563,1366267,632315,956155,3004667,2540539,4171771,1601531,3135483,1815803,3583995,3520763,3125755,697595,1944571,692475,308475,714747,2279931,646907,3652859,2994683,243963,2212859,2750715,2524923,120571,3190523,1020923,703739,303867,693755,3395579,223995,4036859,3989499,3650043,495867,817403,2389499,456187,2726651,2137083,2533371,1799931,2800891,96251,3372795,2680315,2407419,1602555,383483,1881339,3649531,324347,4032507, 1483256, 1175478, 3881270, 198730, 52538, 1761945, 3922710, 1202086, 1432584, 1185688, 2120152, 1159240, 1905880, 1235816, 383530, 1108998, 1887016, 239926, 3547785, 3514118, 231222, 3589674, 1749097, 3882294, 3651705, 3281482,843562,3476794,526886,2577366,573686,3113754,1194570,2257318,1309226,2198152,1630792,1704073,2098057,713574,1015174,183594,1035478,92986,227354,3270970,1139544,2086280,3043336,1694166,938314,2019926,1357160,1296568,1965656,4071318,2790470,930842,770934,1146822,3470634,2472262,74810,1653784,1780728,4189210,1613480,1142568,2211814,603722,1071238,1581192,558582,3611734,1198473,1841210,211018,1164393,1236488,1061480,3761210,1938088,1141578,2561862,1562024,2887238,517910,2741802,549848,1422552,1125434,2172024,1071960,1253112,1922201,163449,2408630,1460264,3899238,3322582,866278}; //Svrcina je posledni
// pole users - ke kazdeme karte pripada urcite jmeno - momentalne jsem to odmazal
String users [216] = {};
// pole pocet - slouzi k pocitani kolikrat uzivatel provadel odber
byte pocet [216] = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}; // v poctu je jen cislo do 10
// nasledujici kody pro kontrolu a zjisteni delky pole
int length_card = sizeof(card) / sizeof(card[0]);
int length_users = sizeof(users) / sizeof(users[0]);
int length_pocet = sizeof(pocet) / sizeof(pocet[0]);
// pole z... 40 vlastne uvadi cas pristupu v danem cyklu
byte z [216] = {40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40, 40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40,40}; // time to cards
int length_z = sizeof(z) / sizeof(z[0]);
byte o = 0;
int k = 0;
int cteni = HIGH;
int q = 0;
int g = 0;
// beeper od ctecky
int BEEP_BEEP = 25;
// LED diody
int LED_RED = 53;
int LED_YELLOW = 52;
int LED_BLUE = 50;
// vyp je kvuli tlacitka, vlastne pokud je probiha cyklus a je provaden odpocet od 40 az po 1 a zmackne tlacitko treba pri 20 sekundach tak dojde k vyskoceni z cyklu a ulozeni zbytku casu prave do promenne z[i]
int vyp = 6;
// p uvadi pocet minut.. Pri 600 minutach coz se rovna 10 hodin, tak dojde vlastne k resetu navratu hodnot pole pocet na = 0 a hodnot pocet pole z na 1.. a pokud mel nekdo pristup vicekrat nez 8x tak dojde k navraceni card[i] = card[i] -10;
int p = 0; // minutes
// pro zobrazovani nactenych bitu RFID cteckou
// interrupt that happens when INTO goes low (0 bit)
void ISR_INT0() {
Serial.print("0"); // uncomment this line to display raw binary
bitCount++;
flagDone = 0;
weigand_counter = WEIGAND_WAIT_TIME;
}
// interrupt that happens when INT1 goes low (1 bit)
void ISR_INT1() {
Serial.print("1"); // uncomment this line to display raw binary
databits[bitCount] = 1;
bitCount++;
flagDone = 0;
weigand_counter = WEIGAND_WAIT_TIME;
}
void setup() {
//rele
pinMode(RELAY_IN1, OUTPUT); // Initialization of the relay
pinMode(RELAY_IN2, OUTPUT); // Initialization of the relay
pinMode(RELAY_IN3, OUTPUT); // Initialization of the relay
pinMode(RELAY_IN4, OUTPUT); // Initialization of the relay
digitalWrite(RELAY_IN1, HIGH);
digitalWrite(RELAY_IN2, HIGH);
digitalWrite(RELAY_IN3, HIGH);
digitalWrite(RELAY_IN4, HIGH);
pinMode(LED_RED, OUTPUT);
pinMode(LED_BLUE, OUTPUT);
pinMode (LED_YELLOW, OUTPUT);
pinMode (vyp, INPUT);
pinMode(BEEP_BEEP, OUTPUT);
lcd.begin (16,2);
digitalWrite(BEEP_BEEP, HIGH); // High = off
pinMode(2, INPUT); // DATA0 (INT0)
pinMode(3, INPUT); // DATA1 (INT1)
Serial.begin(9600);
Serial.println("RFID Readers");
// binds the ISR functions to the falling edge of INTO and INT1
attachInterrupt(0, ISR_INT0, FALLING);
attachInterrupt(1, ISR_INT1, FALLING);
weigand_counter = WEIGAND_WAIT_TIME;
}
void printChar()
{
// cas (ktery se zobrazuje na LCD displeji
Serial.print(h/10);
Serial.print(h%10);
Serial.print(":");
Serial.print(m/10);
Serial.print(m%10);
Serial.print(":");
Serial.print(s/10);
Serial.print(s%10);
Serial.println ();
}
void loop()
{
// kontrola
Serial.print ("Pocet karet: ");
Serial.println (length_card);
Serial.print ("Pocet uzivatelu: ");
Serial.println (length_users);
Serial.print ("Pocet pocet: ");
Serial.println (length_pocet);
Serial.print ("Pocet z: ");
Serial.println (length_z);
/* if (o == 0) {
z [i] = 40;
o++;
}} */
for(h=set_hours;h<24;h++) //hOURS
{
for(m=set_minutes;m<60;m++) //mINUTES
{
// navyseni p - pocet minut o +1 vlastne kazdou novou minut
p++;
Serial.print ("P po navyseni: ");
Serial.println (p);
// nulovaní
if (p == 600){
lcd.setCursor (0, 1);
lcd.print(" ");
p = 0;
for (int i = 0; i != length_card; i++) {
if (pocet [i] == 1 || pocet [i] == 2 || pocet [i] == 3 || pocet [i] == 4 || pocet [i] == 5 || pocet [i] == 6 || pocet [i] == 7 || pocet [i] == 8){
pocet [i] = 0;
z [i] = 40;
}
if (pocet [i] == 8) {
card [i] = card [i] - 10;
Serial.print ("card [i] po nulovani: ");
Serial.println (card [i]);
}
Serial.print ("pocet [i] po nulovani: ");
Serial.println (pocet [i]);
Serial.print ("Vraceni z [i] zpet na 40: ");
Serial.println (z [i]);
}
Serial.print ("p po nulovani: ");
Serial.println (p);
}
for(s=set_seconds;s<60;s++) //Seconds
{
printChar();
digitalWrite (LED_YELLOW, HIGH);
delay(secs-(millis()%1000));
digitalWrite (LED_YELLOW, LOW);
// At this point use NO lcd.clear() otherwise the LCD flackers
lcd.setCursor(0, 0);
lcd.print("SIRUP"); // e.g. you can change it to: Please show your ID.
lcd.setCursor(0, 1);
lcd.print("Pocet minut: "); // e.g. you can change it to: Please show your ID.
lcd.setCursor(13, 1);
lcd.print (p);
lcd.setCursor (8, 0);
lcd.print(h/10);
lcd.print(h%10);
lcd.print(":");
lcd.print(m/10);
lcd.print(m%10);
lcd.print(":");
lcd.print(s/10);
lcd.print(s%10);
/*lcd.setCursor(0, 1);
for (int positionCounter2 = 0; positionCounter2 < 14; positionCounter2++)
{
lcd.print(array2[positionCounter2]); // Print a message to the LCD.
delay(tim); //wait for 250 microseconds
} */
// kvuli ctecky, pouzivam nyni 26 bitu, ale ctu poslednich 22, zbytek doplnim nulami
// This waits to make sure that there have been no more data pulses before processing data
if (!flagDone) {
if (--weigand_counter == 0)
flagDone = 1;
}
// if we have bits and we the weigand counter went out
if (bitCount > 0 && flagDone) {
unsigned char i;
Serial.print("Read ");
Serial.println(bitCount);
Serial.print(" bits. ");
if (bitCount == 35) {
// 35 bit HID Corporate 1000 format
// facility code = bits 2 to 14
for (i=2; i<14; i++) {
facilityCode <<=1;
facilityCode |= databits[i];
}
Serial.println (facilityCode);
// card code = bits 15 to 34
for (i=14; i<34; i++) {
cardCode <<=1;
cardCode |= databits[i];
}
h = 1;
printBits();
}
else if (bitCount == 26) {
// standard 26 bit format
// facility code = bits 2 to 9
for (i=1; i<9; i++) {
facilityCode <<=1;
facilityCode |= databits[i];
}
Serial.println (facilityCode);
// card code = bits 10 to 23
for (i=3; i<25; i++) {
Serial.print ("I: ");
Serial.println (i);
Serial.print ("Databits: ");
Serial.println (databits [i]);
Serial.print ("CARDCODE: ");
Serial.println (cardCode);
cardCode <<=1;
cardCode |= databits[i];
}
printBits();
}
else {
// you can add other formats if you want!
// Serial.println("Unable to decode.");
}
// cleanup and get ready for the next card
bitCount = 0;
facilityCode = 0;
cardCode = 0;
for (i=0; i<MAX_BITS; i++)
{
databits[i] = 0;
}
}
}
set_seconds=00;
}
set_minutes=00;
}
set_hours=00;
}
void printBits() {
Serial.print("FC = ");
Serial.print(facilityCode);
Serial.print(", CC = ");
Serial.println(cardCode);
int a = 0;
int b = 0;
Serial.print ("Pocet karet: ");
Serial.println (length_card);
// cyklus pro hledani nacteneho cisla v poli card [a]
for (a; a != length_card; a++) {
if (cardCode == card [a]){
Serial.println("Autorizace OK");
Serial.println();
q = 1; // kvuli dopoctu casu na hodinach, jestli ano nebo ne (protoze se jedna o sekvenci kodu) - tzn. pokud se provadi odber (cyklus) tak je cas zastaven - dopocitavam
Serial.print ("Pocet [a] před, ma byt nula: ");
// pri prvnim nacteni karty se pocet ma zvysit o +1 kod viz dale
Serial.println (pocet [a]);
Serial.print ("Cislo z je: ");
// ma byt 40 pri prvnim nacteni karty
Serial.println (z [a]);
if (z[a] == 1){
pocet [a] = 8;
lcd.clear();
lcd.setCursor (0, 0);
lcd.print ("Prekrocen denni");
Serial.println ("Prekrocen denni limit");
lcd.setCursor (0, 1);
lcd.print ("limit.");
delay (1500);
break;
}
else
pocet [a]++;
Serial.print ("Pocet [a] po, ma byt o jedno vice");
Serial.println (pocet [a]);
// promenna b vlastne urcuje cas cyklu (vlastne to, jak dlouho budou sepnuty ty dane relatka)... takze pokud pristupoval poprve, tak ma cas 40 s. Dale pokud pristupoval podruhe tak viz podminky. Vim ze zde mam problem, ktery bych mel
// doladit ovsem nemel by byt problem to, ze pokud pri nulovani hodnot se stane to, co se stane nekterym uzviatelum a to, ze se jim na LCD zobrazi schvaleno a pak ihned zamitnuto
if (pocet [a] == 1)
{
b = 40;
}
if (pocet [a] == 2 && z [a] > 35)
{
b = 35;
}
if (pocet [a] == 3 && z [a] > 30)
{
b = 30;
}
if (pocet [a] == 4 && z [a] > 25)
{
b = 25;
}
if (pocet [a] == 5 && z [a] > 20)
{
b = 20;
}
if (pocet [a] == 6 && z [a] > 15)
{
b = 15;
}
if (pocet [a] == 7 && z [a] > 10)
{
b = 10;
}
if (pocet [a] == 8 && z [a] > 5)
{
b = 5;
}
// pokud dany uzivatel pristupoval 8x tak se mu timto karta zablokuje (odblokuje se pri nulovani)
if (pocet [a] == 8)
{
card [a] = card [a] + 10;
Serial.print ("Card [a]");
Serial.println (card [a]);
}
// Output on LCD (e.g. for employees)
lcd.clear();
lcd.setCursor(0, 0);
//cyklus pro napsani schvaleno na displeji a rozsviceni modre led pro kontrolu sepnuti relatek
for (int positionCounter1 = 0; positionCounter1 < 16; positionCounter1++)
{
digitalWrite (LED_BLUE, HIGH);
lcd.print(array1[positionCounter1]); // Print a message to the LCD.
delay(tim); //wait for 250 microseconds
}
// zde na displeji se zobrazi napis cepuj a pod nim jmeno daneho uzivatele
lcd.setCursor(0, 1);
lcd.print(F("Cepuj: "));
Serial.println ("Cepuj: ");
lcd.setCursor(0, 0);
lcd.print (" ");
lcd.setCursor(0, 0);
lcd.print(users [a]);
Serial.println (users [a]);
// do promenne i se priradi vlastne cas co byl v b... tzn kazdy poprve ma mit v promenne i prirazeno 40 s... i po nulovani hodnot.
for (int i = b; i > 0; i = i - 1) {
// Unlock the door and lock it after 5 seconds
digitalWrite(RELAY_IN1, LOW);
digitalWrite(RELAY_IN2, LOW);
digitalWrite(RELAY_IN3, LOW);
digitalWrite(RELAY_IN4, LOW);
digitalWrite (LED_BLUE, HIGH);
/* Serial.println ("Aaaaaaaaaaaa");
Serial.println (a);
Serial.println ("IIIIIIIIII");
Serial.println (i); */
// pokud dojde cas k 1 tak se do z[a] = 1 a na zaklade opetovneho nacteni karty se mu v podmince diky z [i] == 1 priradi do pocet [a] = 8 a tim se mu zablokuje karta i kdyz pristupoval pouze jednou
if (i == 1)
z [a] = 1;
Serial.println (i);
g++;
// nasledujici slouzi k nacteni impulzu po zmacknuti tlacitka z duvodu vyskoceni z cyklu
cteni = digitalRead (vyp);
Serial.println (cteni);
Serial.println (vyp);
if (cteni == LOW)
{
lcd.setCursor (0,0);
lcd.print (" ");
lcd.setCursor(3, 0);
lcd.print("!Ukonceno!");
Serial.println ("Ukonceno zmacnutim tlacitka");
digitalWrite (LED_YELLOW, HIGH);
delay(300);
digitalWrite (LED_RED, HIGH);
delay(300);
digitalWrite (LED_BLUE, HIGH);
delay(300);
digitalWrite (LED_YELLOW, LOW);
delay(300);
digitalWrite (LED_RED, LOW);
delay(300);
digitalWrite (LED_BLUE, LOW);
delay(300);
// Zde jsem to ponechal v poznamce to z[a] = i... coz by byt nemelo.. zapomnel jsem na to.. tudiz jsou problemy s prirazovanim casu (kazdopadne toto poresim)
// ovsem stale by to nemel byt ten problem ze pri nulovani hodnot mu to napise schvaleno a ihned zamitnuto... jako by v promenne b byla 0
// z [a] = i;
break;
}
// tyto podminky slouzi jen kvuli zobrazovani udaju na LCD displeji... protoze pokud je cas < 10 tak jsem mel na displeji treba 70 s (skutecne 7 s)
if (i < 10) {
lcd.setCursor (0,1);
lcd.print (" ");
lcd.setCursor(0, 1);
lcd.print(F("Cepuj: "));
lcd.setCursor (8, 1);
lcd.print (i);
}
else
{
lcd.setCursor (7, 1);
lcd.print(i);
}
delay (1000);
}
// nasledujici slouzi jen k dopocitani casu na LCD displeji (ktery se zobrazuje) aby cas sedel.. to znamena pokud nekdo Cepuje 40 sekund, tak by byl cas o 40 pozadu.
int l = 0;
int f = 0;
f = s + g + 20;
if (f > 60)
{
l = 1;
s = (f - 60);
m = m + l;
}
else if (f < 60)
{
s = f;
}
l = 0;
g = 0;
digitalWrite(RELAY_IN1, HIGH);
digitalWrite(RELAY_IN2, HIGH);
digitalWrite(RELAY_IN3, HIGH);
digitalWrite(RELAY_IN4, HIGH);
digitalWrite (LED_BLUE, LOW);
lcd.setCursor(0, 1);
lcd.print("Nashledanou");
// 1,5 Sekunden warten, damit LCD nicht "flackert" und dann LCD-Anzeige loeschen
// Wait for 1,5 seconds to prevent a LCD flackering and then clear the LCD display
delay(1500);
lcd.clear();
// dodal jsem
}
}
if (q == 0)
{
lcd.setCursor (0,1);
lcd.print ("Nacepuj si vodu.");
int l = 0;
int f = 0;
f = s + 20;
if (f > 60)
{
l = 1;
s = (f - 60);
m = m + l;
}
else if (f < 60)
{
s = f;
}
l = 0;
g = 0;
}
q = 0;
lcd.setCursor (0,0);
lcd.print (" ");
lcd.setCursor(2, 0);
lcd.print("!Zamitnuto!");
delay (2000);
lcd.setCursor (0,0);
lcd.print (" ");
lcd.setCursor(2, 0);
lcd.print(cardCode);
Serial.print ("Cardcode za zamitnuto: ");
Serial.println (cardCode);
for (int i = 0; i != length_card;i++)
{
if (z [a] == 1)
{
lcd.setCursor (0,1);
lcd.print (" ");
}
}
digitalWrite(LED_RED, HIGH);
// Lets be annoying and beep more
digitalWrite(BEEP_BEEP, LOW);
delay(200);
digitalWrite(BEEP_BEEP, HIGH);
delay(200);
digitalWrite(BEEP_BEEP, LOW);
delay(200);
digitalWrite(BEEP_BEEP, HIGH);
delay(200);
digitalWrite(BEEP_BEEP, LOW);
delay(200);
digitalWrite(BEEP_BEEP, HIGH);
delay(15000);
digitalWrite(LED_RED, LOW);
lcd.clear();
}