Nelze vybrat více než 25 témat Téma musí začínat písmenem nebo číslem, může obsahovat pomlčky („-“) a může být dlouhé až 35 znaků.

main.ino 5.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229
  1. #include <Arduino.h>
  2. #include <Keypad/Keypad.h>
  3. #include <LiquidCrystal.h>
  4. #define KP_ROWS 4
  5. #define KP_COLS 4
  6. char keys[KP_ROWS][KP_COLS] = {
  7. {'1','2','3','A'},
  8. {'4','5','6','B'},
  9. {'7','8','9','C'},
  10. {'*','0','#','.'}
  11. };
  12. byte rowPins[KP_ROWS] = {A3, A2, A0, A1};
  13. byte colPins[KP_COLS] = {8, 9, 10, 11};
  14. Keypad keypad = Keypad(makeKeymap(keys), rowPins, colPins, KP_ROWS, KP_COLS);
  15. #define LCD_ROWS 2
  16. #define LCD_COLS 16
  17. LiquidCrystal lcd(2, 3, 4, 5, 6, 7);
  18. #define SELF_TEST_LABEL "Self testing..."
  19. #define SELF_TEST_ERROR_LABEL "Error: "
  20. #define UID_LABEL "UID:"
  21. #define PWD_LABEL "PWD:"
  22. #define LOGIN_IN_PROGRESS "Login..."
  23. #define LOGIN_FAILED "Login failed"
  24. #define LOGIN_SUCCESS "Access granted"
  25. #define UID_MAX_LEN 12
  26. #define PWD_MAX_LEN 12
  27. String uid;
  28. String password;
  29. enum Status {
  30. Uid,
  31. Password,
  32. SelfTest,
  33. LoginInProgress,
  34. LoginFailed,
  35. LoginSuccess
  36. };
  37. Status status = Uid;
  38. #define MAX_IDLE_TIME 20
  39. unsigned long lastActivity = 0;
  40. #define LOGIN_FAILED_TIME 2
  41. #define SELF_TEST_INTERVAL 60
  42. #define SELF_TEST_ERROR_INTERVAL 2
  43. #define MAX_SELF_TEST_TIME 5
  44. unsigned long lastSelfTest = 0;
  45. #define SELF_TEST_NO_ERROR '0'
  46. int lastSelfTestResult = SELF_TEST_NO_ERROR;
  47. void setup() {
  48. Serial.begin(9600);
  49. Serial.println("Starting...");
  50. lcd.begin(LCD_COLS, LCD_ROWS);
  51. lcd.blink();
  52. lcd.noAutoscroll();
  53. selfTest();
  54. }
  55. String makeChars(char c, int count) {
  56. char str[count + 1];
  57. memset(str, c, count);
  58. str[count] = 0;
  59. return String(str);
  60. }
  61. bool handleUidPassword(String& str, int maxLength, char key) {
  62. int len = str.length();
  63. if (key >= '0' && key <= '9') {
  64. if (len < maxLength) {
  65. str += key;
  66. return true;
  67. }
  68. }
  69. else if (key == 'C' || key == '*') {
  70. if (len > 0) {
  71. str = str.substring(0, len - 1);
  72. return true;
  73. }
  74. else if (status == Password) {
  75. status = Uid;
  76. return true;
  77. }
  78. }
  79. return false;
  80. }
  81. void loop() {
  82. unsigned long secs = millis() / 1000;
  83. if (handleKeyPad()) {
  84. lastActivity = secs;
  85. updateLcd();
  86. }
  87. if ((uid.length() != 0 || password.length() != 0) && secs - lastActivity >= MAX_IDLE_TIME) {
  88. askUidPassword();
  89. }
  90. if (uid.length() == 0 && password.length() == 0 && secs - lastSelfTest >= SELF_TEST_INTERVAL) {
  91. selfTest();
  92. }
  93. }
  94. bool handleKeyPad()
  95. {
  96. char key = keypad.getKey();
  97. if (key != NO_KEY) {
  98. if (status == Uid) {
  99. if (key == '#') {
  100. if (uid.length() != 0) {
  101. status = Password;
  102. return true;
  103. }
  104. }
  105. else {
  106. return handleUidPassword(uid, UID_MAX_LEN, key);
  107. }
  108. }
  109. else if (status == Password) {
  110. if (key == '#') {
  111. if (password.length() != 0) {
  112. login(uid, password);
  113. return true;
  114. }
  115. }
  116. else {
  117. return handleUidPassword(password, PWD_MAX_LEN, key);
  118. }
  119. }
  120. }
  121. return false;
  122. }
  123. void updateLcd()
  124. {
  125. Serial.println("Update LCD");
  126. lcd.clear();
  127. if (status == Uid || status == Password)
  128. {
  129. lcd.setCursor(0, 0);
  130. lcd.print(UID_LABEL);
  131. lcd.print(uid);
  132. lcd.setCursor(0, 1);
  133. lcd.print(PWD_LABEL);
  134. lcd.print(makeChars('*', password.length()));
  135. if (status == Uid) {
  136. lcd.setCursor(strlen(UID_LABEL) + uid.length(), 0);
  137. }
  138. else {
  139. lcd.setCursor(strlen(PWD_LABEL) + password.length(), 1);
  140. }
  141. }
  142. else if (status == SelfTest) {
  143. lcd.print(SELF_TEST_LABEL);
  144. if (lastSelfTestResult != SELF_TEST_NO_ERROR) {
  145. lcd.setCursor(0, 1);
  146. lcd.print(SELF_TEST_ERROR_LABEL);
  147. lcd.print(lastSelfTestResult);
  148. }
  149. }
  150. else if (status == LoginInProgress) {
  151. lcd.print(LOGIN_IN_PROGRESS);
  152. }
  153. else if (status == LoginFailed) {
  154. lcd.print(LOGIN_FAILED);
  155. }
  156. else if (status == LoginSuccess) {
  157. lcd.print(LOGIN_SUCCESS);
  158. }
  159. }
  160. void askUidPassword()
  161. {
  162. status = Uid;
  163. uid = "";
  164. password = "";
  165. updateLcd();
  166. }
  167. void login(String uid, String password)
  168. {
  169. status = LoginInProgress;
  170. updateLcd();
  171. delay(LOGIN_FAILED_TIME * 1000);
  172. Serial.println(uid);
  173. Serial.println(password);
  174. status = LoginSuccess;
  175. updateLcd();
  176. delay(LOGIN_FAILED_TIME * 1000);
  177. askUidPassword();
  178. }
  179. void selfTest()
  180. {
  181. lastSelfTest = SELF_TEST_NO_ERROR;
  182. status = SelfTest;
  183. updateLcd();
  184. bool test = true;
  185. while (test) {
  186. unsigned long secs = millis() / 1000;
  187. Serial.println("Self Testing");
  188. while (Serial.available() == 0 && (millis() / 1000) - secs < MAX_SELF_TEST_TIME);
  189. if (Serial.available() > 0) {
  190. lastSelfTestResult = Serial.read();
  191. if (lastSelfTestResult == SELF_TEST_NO_ERROR) {
  192. test = false;
  193. }
  194. else {
  195. updateLcd();
  196. delay(SELF_TEST_ERROR_INTERVAL * 1000);
  197. }
  198. }
  199. }
  200. lastSelfTest = millis() / 1000;
  201. askUidPassword();
  202. }