PIN Pad mit HM-MOD-EM-8Bit

User stellen ihre Haussteuerung vor

Moderator: Co-Administratoren

Sven_A
Beiträge: 4155
Registriert: 26.01.2016, 08:14
System: Alternative CCU (auf Basis OCCU)
Wohnort: Renningen
Hat sich bedankt: 348 Mal
Danksagung erhalten: 284 Mal

PIN Pad mit HM-MOD-EM-8Bit

Beitrag von Sven_A » 12.10.2020, 15:44

Hallo,

angeregt durch diesen Thread hab ich mich mal hin gesetzt und ein PIN Pad /Codetastatur für die Homematic gebastelt.
Die Auswertung der Eingabe findet in der CCU statt, kann also nicht durch Manipulation am PinPad übergangen werden. Was natürlich am Pin Pad im Aussenbereich geht wäre einen Keylogger anzuschließen.
Das ursprüngliche Arduinoprogramm ist NICHT auf Stromsparen ausgelegt, ein Batteriebetrieb daher NICHT möglich. Es wird eine Spannungsversorgung per USB oder 5 bis 12V an VIN / GND benötigt.

Erweiterung: Jerome hat dankenswerterweise den Sketch erweitert. Nach installation der LowPower Bibliothek kann ein Arduino Pro Mini (3,3v, 8MHz, wie bei den AskSin Projekten auch) verwendet werden, das ganze ist dann Batterietauglich. Versorgung über z.B. 2xAA Batterie. Bitte auch die Hinweise hier beachten:
https://asksinpp.de/Grundlagen/01_hardw ... versorgung

DISCLAIMER:
Der HM Funk ist als NICHT SICHER zu betrachten, dessen sollte sich jeder bewusst sein der damit seine Haustüre oder das Garagentor öffnen will. Verwendung auf eigene Verantwortung!

Mit einer 3x4 Matrix Tastatur ist es in Kombination mit dem HM-MOD-EM-8Bit möglich die Auswertung der Tasten in die CCU zu legen.
Benötigt werden:
- 3x4 Matrix Tastatur
- Arduino (hier: Nano, oder Pro Mini 3,3v 8MHz)
- HM-MOD-EM-8Bit
- Gehäuse
- optional: LED rot und grün (oder DuoLED)
- Für Batteriebetrieb: zusätzlichen Taster, weitere LED um Wachzustand anzuzeigen

Verkabelung:
IMG_20201012_144656_867.jpg

Einstellungen des HM-MOD-EM-8bit auf der CCU:
Das Modul muss auf "Modus 2" gestellt werden damit es mit meinem Skript zusammen arbeitet.
Ebenfalls sollte die Übertragung auf gesichert gestellt werden, um zumindest eine einfache Replay-Attacke zu erschweren.

Sketch für den Arduino (Quick und Dirty):

Code: Alles auswählen

#include <Keypad.h>
//Hier wird die größe des Keypads definiert
const byte COLS = 3; //3 Spalten
const byte ROWS = 4; //4 Zeilen
//Die Ziffern/Zeichen:
char hexaKeys[ROWS][COLS]={
{'#','0','*'},
{'9','8','7'},
{'6','5','4'},
{'3','2','1'}
};

byte colPins[COLS] = { 8, 7, 6 }; //Definition der Pins für die 3 Spalten
byte rowPins[ROWS] = { 5, 4, 3, 2 };//Definition der Pins für die 4 Zeilen
char Taste; //pressedKey entspricht in Zukunft den gedrückten Tasten
byte dataPins[] = {9, 10, 11, 12};
byte dataAccept = 13;

Keypad Tastenfeld = Keypad(makeKeymap(hexaKeys), rowPins, colPins, ROWS, COLS); //Das Keypad kann absofort mit myKeypad angesprochen werden
void setup() {
Serial.begin(9600);

for (int i=0; i<=3; i++) {
  pinMode(dataPins[i],OUTPUT);
}

pinMode(dataAccept,OUTPUT);

}

void loop() {
  
Taste = Tastenfeld.getKey(); //pressedKey entspricht der gedrückten Taste

if (Taste) {
  switch (Taste) {
    case '0': 
    digitalWrite(dataPins[0], HIGH);
    digitalWrite(dataPins[1], HIGH);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '1': 
    digitalWrite(dataPins[0], LOW);
    digitalWrite(dataPins[1], HIGH);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;
    
    case '2': 
    digitalWrite(dataPins[0], HIGH);
    digitalWrite(dataPins[1], LOW);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '3': 
    digitalWrite(dataPins[0], LOW);
    digitalWrite(dataPins[1], LOW);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '4': 
    digitalWrite(dataPins[0], HIGH);
    digitalWrite(dataPins[1], HIGH);
    digitalWrite(dataPins[2], LOW);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '5': 
    digitalWrite(dataPins[0], LOW);
    digitalWrite(dataPins[1], HIGH);
    digitalWrite(dataPins[2], LOW);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '6': 
    digitalWrite(dataPins[0], HIGH);
    digitalWrite(dataPins[1], LOW);
    digitalWrite(dataPins[2], LOW);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '7': 
    digitalWrite(dataPins[0], LOW);
    digitalWrite(dataPins[1], LOW);
    digitalWrite(dataPins[2], LOW);
    digitalWrite(dataPins[3], HIGH);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '8': 
    digitalWrite(dataPins[0], HIGH);
    digitalWrite(dataPins[1], HIGH);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], LOW);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '9': 
    digitalWrite(dataPins[0], LOW);
    digitalWrite(dataPins[1], HIGH);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], LOW);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '*': 
    digitalWrite(dataPins[0], HIGH);
    digitalWrite(dataPins[1], LOW);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], LOW);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    case '#': 
    digitalWrite(dataPins[0], LOW);
    digitalWrite(dataPins[1], LOW);
    digitalWrite(dataPins[2], HIGH);
    digitalWrite(dataPins[3], LOW);
    delay(200); 
    digitalWrite(dataAccept, HIGH);
    delay(200); 
    digitalWrite(dataAccept, LOW);
    Serial.print("Die Taste ");
    Serial.print(Taste);
    Serial.print("wurde gedrueckt");
    Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
    break;

    default:
    break;

  }
}
}


Und hier der Sketch mit LowPower, für Batteriebetrieb geeignet. Vielen Dank an jp112sdl für die Erweiterung!
ACHTUNG: Alle Pins um eins verschoben, auf Pin 2 wird ein zusätzlicher Taster gegen GND verwendet um den Arduino aus dem Tiefschlaf zu holen. PIN14 ist A0. PIN15 ist A1.

Auf PIN15 kann eine LED (mit Vorwiderstand, ich hatte gerade eine einfache grüne 3mm LED mit 220Ohm benutzt) angeschlossen werden um zu zeigen wenn der Arduino wach ist und eingaben auf der Tastatur möglich sind.

Code: Alles auswählen

#include <Keypad.h>
#include <LowPower.h>

#define WAKEUP_PIN          2
#define POWER_LED          15
#define SLEEP_TIMEOUT_MS 5000

//Hier wird die größe des Keypads definiert
const byte COLS = 3; //3 Spalten
const byte ROWS = 4; //4 Zeilen
//Die Ziffern/Zeichen:
char hexaKeys[ROWS][COLS] = {
  {'#', '0', '*'},
  {'9', '8', '7'},
  {'6', '5', '4'},
  {'3', '2', '1'}
};

byte colPins[COLS] = { 9, 8, 7 }; //Definition der Pins für die 3 Spalten
byte rowPins[ROWS] = { 6, 5, 4, 3 };//Definition der Pins für die 4 Zeilen
char Taste; //pressedKey entspricht in Zukunft den gedrückten Tasten
byte dataPins[] = {10, 11, 12, 13};
byte dataAccept = 14;

unsigned long timerStartMillis = 0;
volatile bool wkup = false;

Keypad Tastenfeld = Keypad(makeKeymap(hexaKeys), rowPins, colPins, ROWS, COLS); //Das Keypad kann absofort mit myKeypad angesprochen werden
void setup() {
  Serial.begin(9600);

  for (int i = 0; i <= 3; i++) {
    pinMode(dataPins[i], OUTPUT);
  }

  pinMode(dataAccept, OUTPUT);
  pinMode(POWER_LED, OUTPUT);
  pinMode(WAKEUP_PIN, INPUT_PULLUP);
}

void resetTimer() {
  wkup = false;
  timerStartMillis = millis();
}

void processKeyPad() {
  Taste = Tastenfeld.getKey(); //pressedKey entspricht der gedrückten Taste

  if (Taste) {
    resetTimer();
    switch (Taste) {
      case '0':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '1':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '2':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '3':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '4':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '5':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '6':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '7':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '8':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '9':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '*':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '#':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      default:
        break;
    }
  }
}

void dummyISR() {
  wkup = true;
}

void loop() {

  if (wkup) resetTimer();
  
  processKeyPad();
  
  attachInterrupt(0, dummyISR, LOW);

  if (millis() - timerStartMillis > SLEEP_TIMEOUT_MS) {
    digitalWrite(POWER_LED, LOW);
    LowPower.powerDown(SLEEP_FOREVER, ADC_OFF, BOD_OFF);
  } else {
    digitalWrite(POWER_LED, HIGH);
  }

  detachInterrupt(0);
}

Systemvariablen auf der CCU:
Auf der CCU werden 3 Variablen benötigt:
SVs.png


Programme auf der CCU:
Auf der CCU werden 3 Programme benötigt.

Mein "Auswerteprogramm" verschickt im Moment bei korrekter Codeeingabe (1234 oder 4567) lediglich eine Pushovernachricht per Skript mit dem Code als Inhalt. Das Skript kann man gegen die gewünschte Aktion austauschen, also z.B. Garage öffnen, Keymatic öffnen, ...

Mit * wird der aktuelle Inhalt der Eingabevariable gelöscht, damit kann also eine Eingabe abgebrochen und neu gestartet werden.
Eine Eingabe MUSS mit # abgeschlossen werden, erst dann startet die Auswertung.
Ein Code kann nicht mit 0 beginnen, sondern nur mit den Ziffern 1 bis 9.

Nach der dritten Falscheingabe wird das PinPad für 5 Minuten gesperrt.
Nach der vierten Falscheingabe wird das PinPad für 1 Stunde gesperrt.
Nach der fünften Falscheigabe wird endgültig gesperrt.
Bei korrekter Eingabe wird der Fehlerzähler auf 0 gesetzt.

Ich empfehle dringend die optionalen LEDs zu verbauen, und alle die das Teil bedienen darauf zu Impfen das nach jedem Tastendruck das aufleuchten der grünen LED abzuwarten ist. Sonst könnt ihr euch sicher sein das dass ganze schief geht.

PRG_PinPad_lesen_v2.1.png
PRG_PinPad_auswerten.jpg
Pin Pad Code auswerten
PRG_PinPad_sperren.jpg
Pin Pad im Fehlerfall sperren

Jetzt fehlt nur noch ein schönes Gehäuse aus dem 3 Drucker, dann könnte das ganze Montiert werden.

Gruß,
Sven
Zuletzt geändert von Sven_A am 12.11.2020, 14:10, insgesamt 4-mal geändert.

smotomike
Beiträge: 19
Registriert: 13.12.2017, 20:41
Hat sich bedankt: 3 Mal

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von smotomike » 12.10.2020, 22:36

Hey, danke für die Arbeit :-)

Wäre es denn möglich das ganze als Batteriebetrieb zu betreiben? Bzw was müsste denn dafür geändert werden?

Der Sketch sollte doch auch auf einem Arduino mini pro laufen, oder? kombiniert mit dem Low Power Mode sollte das ganze doch auch per Batterie laufen.

Oder?

Sven_A
Beiträge: 4155
Registriert: 26.01.2016, 08:14
System: Alternative CCU (auf Basis OCCU)
Wohnort: Renningen
Hat sich bedankt: 348 Mal
Danksagung erhalten: 284 Mal

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von Sven_A » 13.10.2020, 08:09

Ja, sollte schon gehen. Ich hab nur noch nie irgendwas mit Low Power gemacht, daher hab ich einfach keine Ahnung von.
Wenn da jemand drüber schauen kann der weiß wie das geht wäre ich sehr dankbar.

jp112sdl
Beiträge: 12108
Registriert: 20.11.2016, 20:01
Hat sich bedankt: 848 Mal
Danksagung erhalten: 2148 Mal
Kontaktdaten:

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von jp112sdl » 13.10.2020, 08:32

Die Low-Power Lib von Rocketscream könnte das erledigen.
Funktioniert zumindest (bei den AskSinPP Projekten) zuverlässig und gut.

Ich würde hier das Beispiel "powerDownWakeExternalInterrupt" heranziehen und noch einen extra "Aufwecktaster" einbauen.

So kann der AVR dauerhaft schlafen, bis er durch den Taster geweckt wird (könnte zusätzlich noch durch eine LED angezeigt werden).
Dann wacht er auf, so dass eine Pin-Eingabe erfolgen kann.
Nach jedem Tastendruck wird immer noch so 5 Sekunden (neu) gewartet (für Langsamtipper ^^), bis er wieder in den Sleep geht.

VG,
Jérôme ☕️

---
Support for my Homebrew-Devices: Download JP-HB-Devices Addon

Sven_A
Beiträge: 4155
Registriert: 26.01.2016, 08:14
System: Alternative CCU (auf Basis OCCU)
Wohnort: Renningen
Hat sich bedankt: 348 Mal
Danksagung erhalten: 284 Mal

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von Sven_A » 13.10.2020, 08:47

Gerade mal geschaut, ich hab sogar noch nen passenden Pro Mini hier liegen.

Einfach nur pro Loop für Zeit x schlafen legen und hoffen das der Tastendruck länger anliegt wird vermutlich nicht so zielführend sein, oder?
Eine zusätzliche Taste zum Aufwachen.... ja... unschön wenn die Tastatur so aus einem Guss ist und dann ein zusätzlicher Knopf da ist....

=== Nachtrag ===

Könnte natürlich die Sterntaste umwidmen, dann muss die Eingabe immer mit * beginnen, das wäre ja in Ordnung.... ich glaub ich teste das mal.

jp112sdl
Beiträge: 12108
Registriert: 20.11.2016, 20:01
Hat sich bedankt: 848 Mal
Danksagung erhalten: 2148 Mal
Kontaktdaten:

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von jp112sdl » 13.10.2020, 08:50

Wäre mal schnell zusammengezimmert. Kann es mangels Hardware nicht testen.
Die Pins sind alle eins weiter gerutscht, da ich den HW INT Pin 2 zum Aufwecken brauchte ^^

Code: Alles auswählen

#include <Keypad.h>
#include <LowPower.h>

#define WAKEUP_PIN          2
#define POWER_LED          15
#define SLEEP_TIMEOUT_MS 5000

//Hier wird die größe des Keypads definiert
const byte COLS = 3; //3 Spalten
const byte ROWS = 4; //4 Zeilen
//Die Ziffern/Zeichen:
char hexaKeys[ROWS][COLS] = {
  {'#', '0', '*'},
  {'9', '8', '7'},
  {'6', '5', '4'},
  {'3', '2', '1'}
};

byte colPins[COLS] = { 9, 8, 7 }; //Definition der Pins für die 3 Spalten
byte rowPins[ROWS] = { 6, 5, 4, 3 };//Definition der Pins für die 4 Zeilen
char Taste; //pressedKey entspricht in Zukunft den gedrückten Tasten
byte dataPins[] = {10, 11, 12, 13};
byte dataAccept = 14;

unsigned long timerStartMillis = 0;
volatile bool wkup = false;

Keypad Tastenfeld = Keypad(makeKeymap(hexaKeys), rowPins, colPins, ROWS, COLS); //Das Keypad kann absofort mit myKeypad angesprochen werden
void setup() {
  Serial.begin(9600);

  for (int i = 0; i <= 3; i++) {
    pinMode(dataPins[i], OUTPUT);
  }

  pinMode(dataAccept, OUTPUT);
  pinMode(POWER_LED, OUTPUT);
  pinMode(WAKEUP_PIN, INPUT);
}

void resetTimer() {
  wkup = false;
  timerStartMillis = millis();
}

void processKeyPad() {
  Taste = Tastenfeld.getKey(); //pressedKey entspricht der gedrückten Taste

  if (Taste) {
    resetTimer();
    switch (Taste) {
      case '0':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '1':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '2':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '3':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '4':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '5':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '6':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '7':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], LOW);
        digitalWrite(dataPins[3], HIGH);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '8':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '9':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], HIGH);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '*':
        digitalWrite(dataPins[0], HIGH);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      case '#':
        digitalWrite(dataPins[0], LOW);
        digitalWrite(dataPins[1], LOW);
        digitalWrite(dataPins[2], HIGH);
        digitalWrite(dataPins[3], LOW);
        delay(200);
        digitalWrite(dataAccept, HIGH);
        delay(200);
        digitalWrite(dataAccept, LOW);
        Serial.print("Die Taste ");
        Serial.print(Taste);
        Serial.print("wurde gedrueckt");
        Serial.println(); //Teile uns am Serial Monitor die gedrückte Taste mit
        break;

      default:
        break;
    }
  }
}

void dummyISR() {
  wkup = true;
}

void loop() {

  if (wkup) resetTimer();
  
  processKeyPad();
  
  attachInterrupt(0, dummyISR, LOW);

  if (millis() - timerStartMillis > SLEEP_TIMEOUT_MS) {
    digitalWrite(POWER_LED, LOW);
    LowPower.powerDown(SLEEP_FOREVER, ADC_OFF, BOD_OFF);
  } else {
    digitalWrite(POWER_LED, HIGH);
  }

  detachInterrupt(0);
}
Sven_A hat geschrieben:
13.10.2020, 08:47
Einfach nur pro Loop für Zeit x schlafen legen und hoffen das der Tastendruck länger anliegt wird vermutlich nicht so zielführend sein, oder?
Da müsste man zu oft Aufwachen
Sven_A hat geschrieben:
13.10.2020, 08:47
Eine zusätzliche Taste zum Aufwachen.... ja... unschön wenn die Tastatur so aus einem Guss ist und dann ein zusätzlicher Knopf da ist....
Wäre aber vielleicht ein Kompromiss für die Batterie-Variante...

VG,
Jérôme ☕️

---
Support for my Homebrew-Devices: Download JP-HB-Devices Addon

Sven_A
Beiträge: 4155
Registriert: 26.01.2016, 08:14
System: Alternative CCU (auf Basis OCCU)
Wohnort: Renningen
Hat sich bedankt: 348 Mal
Danksagung erhalten: 284 Mal

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von Sven_A » 13.10.2020, 08:55

jp112sdl hat geschrieben:
13.10.2020, 08:50
Wäre mal schnell zusammengezimmert. Kann es mangels Hardware nicht testen.
Die Pins sind alle eins weiter gerutscht, da ich den HW INT Pin 2 zum Aufwecken brauchte ^^
Danke!
Leider hat der Pro Mini keinen Pin 14...
Also doch die * Taste des Pads zum aufwecken missbrauchen. Das dabei noch ein zweiter Pin zuckt (Matrixtastatur) sollte ja egal sein, oder?

jp112sdl
Beiträge: 12108
Registriert: 20.11.2016, 20:01
Hat sich bedankt: 848 Mal
Danksagung erhalten: 2148 Mal
Kontaktdaten:

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von jp112sdl » 13.10.2020, 08:56

Sven_A hat geschrieben:
13.10.2020, 08:55
jp112sdl hat geschrieben:
13.10.2020, 08:50
Wäre mal schnell zusammengezimmert. Kann es mangels Hardware nicht testen.
Die Pins sind alle eins weiter gerutscht, da ich den HW INT Pin 2 zum Aufwecken brauchte ^^
Leider hat der Pro Mini keinen Pin 14...
14 = A0 :wink:
15 = A1
usw.

VG,
Jérôme ☕️

---
Support for my Homebrew-Devices: Download JP-HB-Devices Addon

Sven_A
Beiträge: 4155
Registriert: 26.01.2016, 08:14
System: Alternative CCU (auf Basis OCCU)
Wohnort: Renningen
Hat sich bedankt: 348 Mal
Danksagung erhalten: 284 Mal

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von Sven_A » 13.10.2020, 08:58

jp112sdl hat geschrieben:
13.10.2020, 08:56
14 = A0 :wink:
15 = A1
usw.
Echt jetzt? Cool, danke dir! Dann teste ich das mal!

jp112sdl
Beiträge: 12108
Registriert: 20.11.2016, 20:01
Hat sich bedankt: 848 Mal
Danksagung erhalten: 2148 Mal
Kontaktdaten:

Re: PIN Pad mit HM-MOD-EM-8Bit

Beitrag von jp112sdl » 13.10.2020, 08:59

Sven_A hat geschrieben:
13.10.2020, 08:55
Das dabei noch ein zweiter Pin zuckt (Matrixtastatur) sollte ja egal sein, oder?
Der Pin zuckt in dem Sinne nicht... die Pins haben erstmal alle HIGH oder LOW Level und werden von der KeyPad.h nacheinander auf den jeweils anderen Reihen- oder Zeilen-Pegel gezogen (kenne die Lib nicht, beides wäre möglich) um dann zu schauen, was die gegenüberliegenden Zeilen- oder Reihen-Pins für nen Pegel in dem Moment haben. Daraus lässt sich dann rausfinden, welche Taste gerade gedrückt wurde.

Deshalb wird auch das Wecken mit einer Matrix nicht (oder nur zufällig) funktionieren.

VG,
Jérôme ☕️

---
Support for my Homebrew-Devices: Download JP-HB-Devices Addon

Antworten

Zurück zu „Projektvorstellungen“