Probleme mit Programmcode für Türschloßprojekt

Mich wundert, dass der Code überhaupt häuft.

 char myKey = myOwnKeyPad.readKey();

du definierst myKey als einzelnen char obwohl deine Funktion eine Zeichenkette liefert (KEY_X). Ich würde MyAnalogKeyPad.h so ändern, dass mir die Lib auch nur einen char zurückgibt.

obwohl deine Funktion eine Zeichenkette liefert (KEY_X).

Und welche Library verwendest du ?
Tobias' in
#include <MyAnalogKeyPad.h>
verwendete scheint immerhin zu kompilieren, auch wenn er nicht verrät was er da nimmt...

Und dass eine Funktion namens keyPressed() einen Buchstaben zurückliefert, ist doch recht sinnvoll, oder.

Ich verwende meine eigene Subroutine die liefert ein byte zurück:

0 -> 0
...
9 -> 9

  • -> 10

-> 11

nichts -> 12
Fehler -> 13

Ich vermute durch die Zuweisung gibt es einen Überlauf und in myKey wird nur das letzte Zeichen des Strings gespeichert. Das Funktioniert auch bei Key_0 bis Key_9. Nur bei # = KEY_hash steht dann in myKey ein h und bei * = KEY_star ein r. Dann funktioniert die Funktion atoi() aber nicht mehr. Das ganze ist keine saubere Lösung und dass es funktioniert ist ehr ein Zufall.

Nur bei # = KEY_hash steht dann in myKey ein h und bei * = KEY_star ein r.

???
Ich weiss nicht wo bei
[b]#define KEY_hash '#'  [/b]
der Buchstabe 'h' ( 0x68 ) vorkommt
???


Da es bei Tobias schon ziemlich funktionert, ist mir klar, dass sein keyPressed() bei der Taste 0 ein '0' liefert, usw.
Eingabe[4] bleibt immer 0, damit geht dann auch atoi(Eingabe). sobald man genau 4 Ziffern eingetippt hat.

Ich weiss nicht wo bei
[b]#define KEY_hash '#'  [/b]
der Buchstabe 'h' ( 0x68 ) vorkommt
???

Da es bei Tobias schon ziemlich funktionert, ist mir klar, dass sein keyPressed() bei der Taste 0 ein '0' liefert, usw.
Eingabe[4] bleibt immer 0, damit geht dann auch atoi(Eingabe). sobald man genau 4 Ziffern eingetippt hat.

ich weiß jetzt nicht wo du dass #define KEY_hash '#' her hast. Tobias93 hat das ganze so beschrieben: Taste - Rückgabewert

Die Library für das Keypad liefert mir folgende Werte zurück je nachdem welche Taste gedrückt ist:

nichts gedrückt - KEY_NOT_PRESSED
0 - KEY_0
1 - KEY_1
2 - KEY_2
3 - KEY_3
4 - KEY_4
5 - KEY_5
6 - KEY_6
7 - KEY_7
8 - KEY_8
9 - KEY_9

- KEY_hash

    • KEY_star

Ich persönlich versuche alles was mit strings zu tun hat in C zu vermeiden. Strings brauchen viel speicher und lassen sich unkomfortabel verarbeiten. Z.B hat Eingabe im Sketch eine Größe von 5 * 8 bit = 40 bit für 5 stellen. Mit einem long mit 32 bit kannst du einen 9-stelligen code eingeben.

Ich persönlich versuche alles was mit strings zu tun hat in C zu vermeiden

Genau, ich auch.

Daher war ich gar nicht auf die Idee gekommen, dass

...
9 - KEY_9

- KEY_hash

    • KEY_star

irgendwas mit Strings zu tun haben könnte. Hat's ja auch nicht :wink:

ich weiß jetzt nicht wo du das
#define KEY_hash '#'
her hast.

Geraten.
Ist auch eigentlich egal, jedenfalls im Beispielcode dieses Threads.
"KEY_hash" als string ist auf jeden Fall Unsinn. Und sicher nicht der Rückgabewert von keyPressed().

ok. Wie ich oben ganz am Anfang geschrieben habe: Ich bin Anfänger auf dem Gebiet, dass heißt so ziemlich 50% der letzten Posts sind für mich Böhmsche Dörfer :frowning:
Ich versuchs mal zu erklären. Der Sketch und die dafür benötigten Librarys habe ich mittels des Lehrbuchs: "Die elektronische Welt mit Arduino entdecken" geschrieben, dass heißt was da steht hab ich eingetippt und die Sktech Erklärung dazu habe ich versucht zu verstehen.

Ich versuche jetzt mal mein Problem genau wie möglich in Worte zu fassen:

Die Header Datei die für das Projekt angelegt wurde:

#ifndef MYKEYPAD_H
#define MYKEYPAD_H

#if ARDUINO < 100
#include <WProgram.h>
#else
#include <Arduino.h>
#endif

#define KEY_NOT_PRESSED '-'
#define KEY_1 '1'
#define KEY_2 '2'
#define KEY_3 '3'
#define KEY_4 '4'
#define KEY_5 '5'
#define KEY_6 '6'
#define KEY_7 '7'
#define KEY_8 '8'
#define KEY_9 '9'
#define KEY_0 '0'
#define KEY_star 'stern'
#define KEY_hash 'raute'

class MyAnalogKeyPad{
public:
MyAnalogKeyPad (byte analogPin); // Parametrisierter Konstruktor
void setDebounceTime(unsigned int debounceTime); // setzen der Prellzeit
void setThresholdValue(byte tv); // setzen der Threshold (Grenzwert)
char readKey(); // Ermitteln des gedrückten Tasters auf Keypad
private:
byte analogPin; // analoger Pin zur Messwertaufnahme
unsigned long debounceTime; // private Variable für die Prellzeit
long lastValue; // letzte Zeit der millis-Funktion
byte threshold; // Toleranzwert
};
#endif

nun poste ich die cpp Datei:

#include "MyAnalogKeyPad.h" // Parametrisierter Konstruktor

MyAnalogKeyPad::MyAnalogKeyPad(byte ap){
analogPin = ap; // Analog Pin für Messwertaufnahme
debounceTime= 300; // Initialwert für DebounceTime festlegen
threshold = 5; // Toleranzwert festlegen
}

void MyAnalogKeyPad::setDebounceTime(unsigned int time){ // Methode zum Setzen der Prellzeit
debounceTime = time;
}

void MyAnalogKeyPad::setThresholdValue(byte tv){ // Methode zum Setzen der Tolleranz
threshold = tv;
}

char MyAnalogKeyPad::readKey(){ // Methode zum Ermitteln des gedrückten Tasters auf dem Keypad
char key = KEY_NOT_PRESSED; // Initialwert von key ist "KEY_NOT_PRESSED" (nichts ist gedrückt)
byte aValue = analogRead(analogPin);
if((aValue > 0)&&(millis()- lastValue >= debounceTime)){
if((aValue > (176 - threshold))&&(aValue < (176 + threshold)))
key = KEY_1;
if((aValue > (163 - threshold))&&(aValue < (163 + threshold)))
key = KEY_2;
if((aValue > (149 - threshold))&&(aValue < (149 + threshold)))
key = KEY_3;
if((aValue > (136 - threshold))&&(aValue < (136 + threshold)))
key = KEY_4;
if((aValue > (122 - threshold))&&(aValue < (122 + threshold)))
key = KEY_5;
if((aValue > (108 - threshold))&&(aValue < (108 + threshold)))
key = KEY_6;
if((aValue > (94 - threshold))&&(aValue < (94 + threshold)))
key = KEY_7;
if((aValue > (79 - threshold))&&(aValue < (79 + threshold)))
key = KEY_8;
if((aValue > (64 - threshold))&&(aValue < (64 + threshold)))
key = KEY_9;
if((aValue > (48 - threshold))&&(aValue < (48 + threshold)))
key = KEY_star;
if((aValue > (32 - threshold))&&(aValue < (32 + threshold)))
key = KEY_0;
if((aValue > (15 - threshold))&&(aValue < (15 + threshold)))
key = KEY_hash;

lastValue = millis();
}
return key;
}

Der passende Sketch wurde ja schon zu Anfang gepostet.

Nun beschreibe ich euch mal meinen aktuellen Standpunkt:

Das Programm funktioniert in sofern das ich wenn die Zahlen 9200, also der in CODE gespeicherte Wert eingegeben wird ein I/O Port geschaltet wird... Tür geht auf.
Wenn die Falschen Zahlen eingegeben werden geht die Tür nicht auf. Die beiden Zeichen will ich mal rauslassen weil da läuft´s nicht so richtig wenn die eingetippt werden spielt der Sketch irgendwie die Reise nach Jerusalem :slight_smile:

Ok hab ich mir gedacht dann überbrückst du die beiden Schalter halt und dann hat sichs. Nun möchte ich aber das man mit der Kombination #100 oder *100 oder irgend einer Kombination mit den Zeichen in eine Menüeebene kommt um da z.B. das Kennwort zu ändern. Jetzt steh ich vor dem Problem das die Sonderzeichen ja nicht funktionieren... das is ja schonmal schlecht. Hab ich mir gedacht, komm egal, nimmste als Kombination die dich ins Menü bringt eben 0000, dann fällt die Kombination eben als mögliche Kennwortkombination weg.... bleiben ja immer noch genug.

Jetzt geb ich also 0000 ein und komme in das Menü - bis dahin klappts.
Nun lasse ich am Display anzeigen :
Auswahl:
1 = Code aendern

Jetzt will ich das ich wenn ich eine 1 eintippe (nur eine 1 nicht 0001) das ich dann in die Ebene zum Menü ändern komme. Tippe ich nun 1 ein, passiert nichts... Da bin ich aber glaube ich selbst auf das Problem gestoßen. Ich müsste ein Array anlegen was nur eine Zahl speichert und nicht [5] oder ? Whatever gebe ich nun halt 0001 ein bekomme ich angezeigt Coder verweigert und er springt wider an den Anfang. Das heißt er scheint nicht zu verstehen das er nun eine Ebene höher ist und die Eingaben hier nicht mit den Vorgaben der Ebene für die Codeeingabe verglichen werden sollen.

Könnt ihr mir hier eine Tipp geben wie man das Problem lösen kann, vielleicht auch mit Begründung, damit ich es verstehe?

Schonmal vielen Dank,

Tobias

Mach dir als erstes ein Struktogramm/PAP und überleg wie dein Programm funktionieren soll. Wenn du das geschafft hast kannst du dir über die Programmierung Gedanken machen. Das ist dann eine rein technische Frage. Dabei solltest du die Konventionen von C kennen und beachten. Ließ ein Tutorial und beschäftige dich nochmal damit was Datentypen sind. Dann überlegst du, ob du unbedingt mit char arbeiten möchtest, oder ob du einfach byte bzw. int Variablen benutzt. Mit letzteren kann man rechnen und Bitopperationen durchführen. Dann könnte man seinen code auch so einlesen:

myKey = myOwnKeyPad.readKey(); // Abfragen des gedrückten Tasters
if (myKey != X){ // X ist eine Zahl die kommt, wenn keine Taste gedrückt wurde
Eingabe = Eingabe*10+myKey;
}

... was Datentypen sind. Dann überlegst du, ob du unbedingt mit char arbeiten möchtest, oder ob du einfach byte bzw. int Variablen benutzt. Mit letzteren kann man rechnen und Bitopperationen durchführen

circuit99 hat Recht, nur oben erwähnter Satz ist evtl. missverständlich.
byte und char ist fast dasselbe, bis auf das Vorzeichen. Du meinst sicher den Unterschied zwischen

#define KEY_0 '0' // 0x30
#define KEY_0 0 // 0x00

Beides kann sowohl in byte wie auch in char Variablen verwendet werden.

Ersteres kann gleich angezeigt werden, das zweite ist leichter zum Rechnen. Der Unterschied ist aber minimal ( '0' dazuaddieren bzw. abziehen, oder auch bitweise ein/ausblenden)

int brauchst du nur für mehrstellige codes ( long wenns über 4 Stellen sein können ). Ein 8 bit Arduino arbeitet lieber mit bytes.


#define KEY_star 'stern'
#define KEY_hash 'raute'

ist sehr verwirrend. Schade, dass der Compiler das überhaupt zulässt.

#define KEY_star '*'    // ist übrigens kleiner als '0'

oder

#define KEY_star 10  // oder irgendein Wert > 9

Muss in jedem Fall bei der Berechnung abgefangen werden ( was z.Zt. fehlt und zu Tobias' "Reise nach Jerusalem" führt )

Es gibt 2 Punkte die ich nicht verstehe / bzw. nicht hinbekomme.

  1. Wie funktioniert das Einlesen. Wie speichere ich am besten die Eingabe ab, damit ich mit ihr dann auch weiter rechnen und arbeiten kann? Besonders im Bezug auf die Zeichen * und #

  2. Wie kann ich das Einlesen der Codes für die einzelnen Ebenen anpassen. Das heißt das er in der Startebene wo er auffordert den Code einzulesen, soll er ja nur bei Eingabe = CODE den Code akzeptieren. Gibt man z.B. #100 ein soll man in die Menüebene kommen. Alle anderen Eingaben werden als falsch erkannt. Ist man nun in der Menüebene und soll auch wider für irgendwelche Funktionen was eingeben soll er ja nun wider etwas einlesen, allerdings das nicht mit den Parametern aus der Startebene vergleichen. Das macht er aktuell. Gibt man z.B. 1000 für Code ändern ein zeigt er an CODE verweigert, das was er aber nur in der Startebene machen soll.

Ich finde zu den beiden Punkten keine Lösung bzw. bekomme es nicht hin.
Ich wäre dankbar für Lösungsvorschläge.
Gruß
Tobias93

Hallo,
ich kämpfe mich gerade durch ein ähnliche Problem (siehe String abfragen ?). In meinem Sketch habe dann auch 'atoi' ausprobiert, es wurde mir hier dann der Wert 35 (ascii für #) bzw. 42 (ascii für *) ausgegeben, also "421000" für "*1000", allerdings hat mich das ganze nicht richtig weitergebracht. :disappointed_relieved:

Versuchen wir mal, es einfach zu machen :wink:

Mit jedem Tastendruck liefert readKey() ein Zeichen zurück und hat sich schon um Prellen und kurze/lange Tastendrücke gekümmert, oder liefert bei Abfrage den Wert KEY_NOT_PRESSED, wenn kein neuer Tastendruck da war. Das ist doch schon das Schwierigste.

Für mich das zweitschwierigste war:

#define KEY_star 'stern'

und tatsächlich, Kinder, wenn euch meine Erklärung verwirrt, oder es zu grausam ist, macht schnell die Augen zu

(ich hab meinen Arduino geopfert und es ausprobiert):

#define KEY_STAR 'stern' // kein Syntaxfehler, ist ja nur der Präprozessor
  byte testkey = KEY_STAR;  // kein Syntaxfehler
  static char teststring[]= "---";
  teststring[1] = testkey;
  Serial.println(teststring);  // erzeugt  "-n-"

Genauso erzeugt
#define KEY_hash 'raute' im Endeffekt ein 'e'

Das ist jetzt wohl nur Tobias' Problem.


wie Arduinokiller einmal einen Stern als 42 kriegen kann ist mir klar. Merkwürdig ist mir, wie er aber aus "10" eine "4210" (statt z.B. "424948" , weil eine '1' hat den ASCII-wert 49 (0x31) genauso wie '' den Wert 42 hat.


Tobias kann natürlich die Library anpassen, da hatten wir schon 2 Varianten, eine zum einfach Rechnen, eine zum einfach Anzeigen.
Ab jetzt nehm ich mal an, wir bleiben beim Einfach Anzeigen und die Stern-Taste würde als '' im Display erscheinen, wenns ein 'n' ist wissen wir ja, warum. Rechnen (einen als Zahl agespeicherten CODE ermitteln und vergleichen) kann man mit '' genauso schlecht wie mit 'n'.
Ihr könnt die Augen wieder aufmachen

Ein Sclüsselcode bestht also nur aus Ziffern, die # und * Tasten sind was besonderes. Was, das kann man sich frei wählen.
Für's einfache Verständnis lassen wir so wie es jetzt ist: Schlüsselcode sind 4 Ziffern, nicht mehr und nicht weniger.

Wir wollen ausser einer Code-Eingabe auch in einen Funktions-Menü-Modus springen:
Nehmen wir doch dazu das * Zeichen.
Dann definieren wir noch das # Zeichen als Anfang einer Code Eingabe, das hilft auch, wenn man sich vertippt hat.
Bei variabel langen Schlüsseln brauchen wir noch ein Ende-Zeichen ( zB. den Stern ) aber lassen wir das erstmal.

#define EINGABE 0
#define MENU 1
byte mode = EINGABE;  // Voreinstellung

byte stelle = 0;
unsigned int CODE = 9367;
unsigned int Eingabe = 0; // gleich als Zahl umgerechnet

void loop(){
  char myKey = myOwnKeyPad.readKey();                    // Abfragen des gedrückten Tasters
  if (myKey != KEY_NOT_PRESSED){                         // Abfragen ob irgendein Taster gedrückt ist
     lcd.print(myKey);                                      // Taste im LCD anzeigen
     if ( mode == EINGABE)
       switch (myKey)  {
       case KEY_STAR:
         mode = MENU;
         break;
      case KEY_HASH:
         delay(200); // damit man das # Zeichen noch kurz sieht
         stelle = 0;    // alles auf Anfang
         Eingabe = 0;
         lcd.clear(); // ...
         break;
      default:  // alle anderen Tasten
         Eingabe = Eingabe*10 + myKey-'0' ;  // setzt voraus, dass diese
         stelle++;
         if ( stelle == 4) {
           if (Eingabe == CODE) {
               // usw. ( richtiger Code )
           } else {
               // falscher Code
           }
         }
         break;
     } // Ende switch
     else {   // Menu - Zweig
         if ( myKey == ...
         // wie kommen wir wieder zur Code - eingabe ???
     }
  }
}

hy,
ich möchte nochmal ganz kurz auf den Code von mir zu sprechen kommen und nicht auf deinen neuen, weil er mir kompliziert vorkommt und ich ihn nicht richtig verstehe. Bei meinem Code ist es ja so das die Eingabe die vom Keypad zurück kommt in einem Array gespeichert wird:

Eingabe[stelle] = myKey;

Entschieden ob man bzw. was man in das Array speichern soll geschieht mit der if - Abfrage:

if (myKey != KEY_NOT_PRESSED)

Kann man nun auch in der Library den Rückgabewert für z.B. # auf 10 setzen und * auf 11 und dann in einer if Abfrage sagen das wenn

myKey!= KEY_NOT_PRESSED && myKEY!= 10 && myKEY!= 11 ist das er dann ganz normal in das Array Eingabe speichern soll. Ist die Eingabe jedoch 11 oder 10 dann soll er diesen Wert in ein anderes Array was diese beiden Zahlen aufnehmen kann speichern und diesen Wert dann in int umwandeln um damit zu arbeiten? Wäre das vielleicht einfacher? Ich versuche das Problem schon eine ganze Weile auf diese Art zu lösen weil ich die vielen Lösungsvorschläge hier nur sehr bedingt (wenn überhaupt) verstehe. Ich suche ja nicht die high end Lösung sondern auch eine die ich verstehe.
Können wir vielleicht an dem Lösungsvorschlag von mir weiterarbeiten und deinen Vorschlag michael_x erstmal rauslassen?

Vielen Dank für eure Unterstützung,
Tobi

Klar, das mit dem switch und der Zusatz-Variable, ob gerade Daten-Eingabe erfolgt oder nicht, kannst du gerne weglassen.
Auch, ob du die gesamte Zahlencode-Eingabe gleich als Zahl, oder erstmal als char[] speicherst um hinterher atoi aufzurufen, ist Geschmackssache.

Das Haupt-Problem ist, dass # und * nicht in der Variable Eingabe landen, da hast du Recht und vermeidest es ja auch.

if (myKey!= KEY_NOT_PRESSED && myKEY!= KEY_STAR && myKEY!= KEY_HASH)

ist auch nur eine Schönheitsfrage, die aussen vor lässt, wie die drei #defines nun tatsächlich definiert sind.

Frage ist also, was willst du im else-Zweig dieses if machen ...

 -> KEY_NOT_PRESSED : gar nichts
    KEY_STAR        : ?
    KEY_HASH        : ?

wie Arduinokiller einmal einen Stern als 42 kriegen kann ist mir klar. Merkwürdig ist mir, wie er aber aus "10" eine "4210" (statt z.B. "424948" , weil eine '1' hat den ASCII-wert 49 (0x31) genauso wie '' den Wert 42 hat.

Sorry, der Sketch hat mir einmal "42100035" (*1000#) angezeigt, warum auch immer. Bei weitern Versuchen und Änderungen im Sketch bekam ich meisten eine Summe angezeigt z.B. "270" (egal ob ich *1000# oder *0001# eingegeben habe).

Bei weitern Versuchen und Änderungen im Sketch bekam ich meisten eine Summe angezeigt z.B. "270" (egal ob ich *1000# oder *0001# eingegeben habe).

Um einen Text mit atoi() in eine Zahl umwandeln zu können, dürfen natürlich keine nicht-Ziffern ( # * ) drin sein. Das hat der Original-Sketch, den Tobias anfangs gepostet hat, aber gemacht. Diese Zeichen gleich abzufangen und nach Bedarf darauf zu reagieren, ist wohl z.Zt. die Aufgabe.

Bzw. genau zu definieren, was bei * oder # passieren soll.
Als beliebig mögliche Teile des Schlüssels würde ich sie nicht zulassen, eher als fest definierte Anfangs- und Endezeichen

Tobias:
Ist die Eingabe jedoch 11 oder 10 dann soll er diesen Wert in ein anderes Array was diese beiden Zahlen aufnehmen kann speichern und diesen Wert dann in int umwandeln um damit zu arbeiten? Wäre das vielleicht einfacher?

Das klingt mir eher kompliziert: - Warum erst in ein anderes Array speichern? Warum in eine Zahl wandeln? ( In welche ? ) Wenn der zu überprüfende Schlüssel eine Zahl ist, warum dann diese Zahl nicht mit den Zifferntasten eingeben?

Evtl. zur Verwirrung: Wenn der gesuchte Schlüssel z.B. #12*#098 sein soll, dann würde ich das ganze Umwandeln in eine Zahl lassen, den hinterlegten CODE als char[] definieren und so prüfen. Der Benutzer hat dann aber keine Möglichkeit einen Versuch abzubrechen und neu anzufangen. Man müsste also solange tippen bis "Falsche Eingabe" kommt und ab dann seinen neuen Versuch starten.
Wie wird dann ein neuer Code definiert? Verstehe ich deinen alten Vorschlag jetzt erst?
Das Ergebnis einer Schlüsselprüfung soll statt nur ( richtig / falsch ) besser ( richtig / Menü:ändern / falsch ) sein ?

Evtl. zu weiteren Verwirrung : statt die Tasten als entweder Dezimalzahl oder als KeineZahl zu unterscheiden, könnte man sie auch als HexadezimalZiffern interpretieren . Der gesuchte Schlüssel z.B. #12*#098 wäre dann alslong CODE = 0xA12BA098;gespeichert.
Auch eine schöne Zahl.

circuit's Umrechnung ginge dann fast genauso, mit
Eingabe = Eingabe*16+myKey;

Kann sein, dass ich dich die ganze Zeit nicht verstanden hab (verstehen wollte), weil mir das " # ist Sonderfall " so fest im Hirn saß.

schön das wir uns jetzt alle verstehen.
Eine konkrete Frage:
kann mir jemand meinen Code, sowohl Library als auch Sketch so umschreiben das man mit den Zahlen von 0 bis 9 und auch mit den Zeichen * und # weiter arbeiten kann ? Aktuell habe ich den Sketch so geändert das ich als Rückgabewerte für * und # 10 und 11 verwende. Dennoch klappt es nicht einfach zu sagen:

If (myKey = 10)
{
...
}

ich weiß nicht woran es liegt, vermute aber das es immernoch mit der Umwandlung von char in int zusammenhängt. Und das ist der Teil den ich nicht verstehe.

Danke für eure Hilfe,

Tobi

if (myKey == 10)
{
...
}

siehst du die 2 Gleichheitszeichen ? Manchmal ist es sowas. Wenn das alle deine Probleme schon löst, prima.


Wenn nicht:
Und, da ich ja offensichtlich der letzte war, der gedacht hat, * und # sei keine Zahl,
bin ich jetzt derjenige, der sagt, da brauchst du gar kein extra ' if ' ?!?

wenn die 0 - Taste die Zahl 0, nicht das Zeichen '0' liefert, usw, und * und # die Zahlen 10 ( 0x0a ) und 11 ( 0x0b ) liefern,
dann ist der einzige Sonderfall z.B. #define KEY_NOT_PRESSED 0xFF 
Dann kannst du doch - so hab ich das jetzt verstanden - den eingegebenen Code incl. + und # direkt als Hex-Zahl speichern.

Die Umwandlung einer Zahl in ein darstellbares Zeichen geht am elegantesten per array: ( s. displaycode im Beispiel )

const long CODE = 0xB1034A; // = "  #1034*  "

const char displaycode[] = "0123456789*#";    // displaycode[3] ist das Zeichen '3' , usw.

byte stelle;                    // 0 .. 5 ( bei 6 ist die Eingabe komplett)
unsigned long Eingabe; // geht bis 8 Zeichen incl * und #
 
void loop() {
  byte key = myOwnKeyPad.readKey();  // liefert eine Zahl zwischen 0 und 12 
  if (key != KEY_NOT_PRESSED) {                         // Abfragen ob irgendein Taster gedrückt ist
     lcd.print(displaycode[myKey]);                    // Taste im LCD anzeigen
     Eingabe = Eingabe*16+key;                            // Gesamt-Eingabe sammeln
     stelle++; 
     if (stelle == 6) {
        // Eingabe prüfen
        // ... 
        // und alles wieder initialisieren
        Eingabe = 0;
        stelle = 0;
        lcd.clear();
        lcd.print("Neue Eingabe");
        lcd.setCursor(2,0); 
        
     }
}

hallo,

der Sketch funktioniert nun. Menüebene ist auch realisiert worden. Danke an alle für die gute Unterstützung.
Bei Interesse, hier ist der Sketch (PS: Der Sketch ist in mehrere Tabs aufgeteilt diese habe ich einzeln unten angehängt):

#include <MyAnalogKeyPad.h>
#include <LiquidCrystal.h>
#define analogPinKeyPad 0 // Definition des analogen Pins
#define RS 12 // Register Select
#define E 11 // Enable
#define D4 5 // Datenleitung 4
#define D5 4 // Datenleitung 5
#define D6 3 // Datenleitung 6
#define D7 2 // Datenleitung 7
#define COLS 16 // Anzahl der Spalten
#define ROWS 2 // Anzahl der Zeilen
char CODE[5] = "9200";
char MENUECODE[5] = "#100";
char Eingabe[5]; // max. 5 stellige Zahl generieren
char Menueauswahl[2];
char aktuellercodea[5];
char neuercodea[5];
byte stelle;
byte stellezwei;
byte stelledrei = 0;
byte stellevier = 0;
byte stellefuenf;
byte stellesechs;
int ende = 0;
int endezwei = 0;
int endedrei = 0;
int endevier = 0;

MyAnalogKeyPad myOwnKeyPad (analogPinKeyPad); // KeyPad Instanziieren
LiquidCrystal lcd ( RS,E,D4,D5,D6,D7); // LCD Instanziieren

void setup(){
Eingabe[4]= 0;
Menueauswahl[4] = 0;
MENUECODE[4]=0;
aktuellercodea[4]=0;
neuercodea[4] = 0;
CODE[4] = 0;
myOwnKeyPad.setDebounceTime(200);
lcd.begin(COLS, ROWS);
Willkommensbildschirm();
}
void loop(){
ende = 0;
endezwei = 0;
char myKey = myOwnKeyPad.readKey();
if (myKey != KEY_NOT_PRESSED){
Eingabe[stelle] = myKey;
stelle++;
lcd.print("*");
}
if (stelle == 4){
if (strcmp(CODE,Eingabe)== 0){
delay(500);
Tuer_oeffnen();
}
if (strcmp(MENUECODE,Eingabe)== 0){
delay(500);
Menue_oeffnen();
}
else if (strcmp(CODE,Eingabe)!= 0){
delay(500);
Fehlermeldung();
}
}
}

void Fehlermeldung(){
lcd.clear();
stelle = 0;
lcd.print("CODE VERWEIGERT!");
delay(2000);
lcd.clear();
stelle = 0;
lcd.print(" CODE EINGABE:");
lcd.setCursor(6,1);
}

void Menue_oeffnen(){

lcd.clear();
stelle = 0;
lcd.print("Menue oeffnen...");
delay(2000);
lcd.clear();
lcd.print("Code aendern?");
lcd.setCursor(0,1);
lcd.print("1= ja / 2= nein");

while ( ende != 1){
char Menueeingabe = myOwnKeyPad.readKey();
if (Menueeingabe != KEY_NOT_PRESSED){ // Abfragen ob irgendein Taster gedrückt ist
Menueauswahl[stellezwei] = Menueeingabe;
stellezwei++;
if (stellezwei == 1){
int b = atoi(Menueauswahl);
if (b == 2){
lcd.clear();
lcd.print("Abbrechen...");
delay(2000);
lcd.clear();
stellezwei = 0;
ende = 1;
Willkommensbildschirm();
}
if ( b == 1){
lcd.clear();
lcd.print("Code aendern");
delay(2000);
lcd.clear();
stellezwei = 0;
ende = 1;
code_aendern();
}

if (b != 1 && b!= 2){
ende = 1;
stellezwei = 0;
Willkommensbildschirm();
}
}
}
}
}

void Tuer_oeffnen(){
lcd.clear();
stelle = 0;
lcd.print("Tuer oeffnen");
delay(2000);
lcd.clear();
stelle = 0;
delay(20);
Willkommensbildschirm();
}

void Willkommensbildschirm(){
lcd.clear(); // Display Anzeige löschen
lcd.print(" AUSBILDUNG");
delay(2000); // 4 Sekunden warten
lcd.clear();
lcd.print(" CODE EINGABE:");
lcd.setCursor(6,1);

}

void code_aendern(){
endezwei = 0;
endedrei = 0;
stelle = 0;
stellezwei = 0;
stelledrei = 0;
stellevier = 0;
lcd.clear();
lcd.print("aktueller CODE:");
lcd.setCursor(0,1);

while ( endezwei != 1){
char aktuellercode = myOwnKeyPad.readKey();
if (aktuellercode != KEY_NOT_PRESSED){
aktuellercodea[stelledrei] = aktuellercode;
stelledrei++;
lcd.print("*");
}
if (stelledrei == 4){
if (strcmp(CODE,aktuellercodea)== 0){
lcd.clear();
lcd.print("neuer Code:");
lcd.setCursor(0,1);
endezwei = 1;

while ( endedrei != 1){
char neuercode = myOwnKeyPad.readKey();
if (neuercode != KEY_NOT_PRESSED){
neuercodea[stellevier] = neuercode;
stellevier++;
lcd.print(neuercode);
}
if (stellevier == 4){
strcpy (CODE,neuercodea);
lcd.clear();
endedrei = 1;
Willkommensbildschirm();

}
else if (strcmp(CODE,aktuellercodea)!= 0){
endezwei = 1;
lcd.clear();
lcd.print("CODE VERWEIGERT!");
delay(2000);
lcd.clear();
Willkommensbildschirm();
}
}
}
}
}
}