Problem beim löschen von einer Eingabe auf einem i2C Display

Hallo Forengemeinde,

wollte mich kurz vorstellen, hab jedoch keinen eigenen Bereich dafür gefunden (oder übersehen?). Mein Name ist Michael und zähle nun knapp 50 Lenze. Vor ein par Wochen habe ich angefangen, mittels eines Set´s von Elegoo in die Welt von Arduino einzutauchen. Jedoch bin ich gerade mal so weit, dass ich es geschafft habe, etwas auf dem seriellen Monitor auszugeben .... mit anderen Worten: also noch blutiger Anfänger.

Nun habe ich versucht, einen Sketch (von dem ich noch meilenweit entfernt bin, diesen selber zu schreiben!) umzuschreiben, was mir auch teilweise gelungen ist. Diesen habe ich zur freien Verfügung im Netz gefunden. Jedoch habe ich ein Problemchen, bei denen ich mit meinem bisherigen Wissen nicht weiter komme. Hier hoffe ich nun auf Eure Hilfe.

Es geht um eine Drehachse mit Nema17, angesteuert über eine TB6560 Endstufe, für meine Portalfräse. Eingabe des Winkels erfolgt über ein 4x4 Keypad, Ausgabe kommt über ein Nokia Display. Das ganze läuft auf einen Mega2560.

Diesen Sketch wollte ich nun umschreiben, so dass ich ein 20x4 I2C Display verwenden kann.Und ich musste die Formel für die Berechnung der Schritte des Schrittmotors anpassen.

Die Eingabe des Winkels erfolgt in ganzen Grad über das Keypad, wird im Display angezeigt und mittels Raute bestätigt. Sollte man sich vertippt haben, kann man mittels Sterntaste die Eingabe Stelle für Stelle löschen.

Was funktioniert:

ich habe es geschafft, das I2C Display einzubinden. Ich kann den Winkel eingeben, dieser wird auch im Display angezeigt. Wenn ich die Raute Taste betätige, fährt der Motor auf die angegebene Position und der Eingabebereich für den winkel wird gelöscht. Soweit so gut.

Was funktioniert nicht:

Ab Zeile 195 wird das Löschen mit der Sterntaste definiert. Im original Sketch mit dem Nokia Display funktioniert es einwandfrei. Jedoch mit dem LCD nicht. Ich habe auch schon versucht, dass ich die entsprechenden Stellen im Display mit Leerzeichen überschreibe, leider ohne Erfolg. Im Moment habe ich keine Idee, wie ich das lösen kann.

Ich habe die Programmteile, die für das Nokiadisplay notwendig waren, im Skech behalten und nur auskommentiert, so dass man den originalen Sketch nach verfolgen kann. Sollte das ganze etwas durcheinander wirken, bitte ich das zu entschuldigen .... bin halt noch Anfänger

Danke im Voraus und LG
Michael

Drehachse_mit_LCD_Test_4.ino (8.68 KB)

Hab nun den Sketch eben umgeschrieben, so dass man auch eine Uno R3 Board verwenden kann. Durch die Verwendung von einem I2C Display werden weniger Anschlüsse benötigt, also warum einen Mega verwenden.

Bezüglich des oben beschriebenen Problems ist mir aufgefallen, dass wohl das Löschen der Eingabe funktioniert. Gibt man z.B. einen Winkel von 255 Grad ein, betätigt dann dreimal die Sterntaste, kann man z.B. 360 eingeben. Die Zahlen im Display werden ersetzt.

Das Problem ist, dass mit betätigen der Sterntaste das Programm dies erkennt, jedoch die falsche Zahl am Display nicht gelöscht wird.

LG
Michael

Soweit ich weiss behält ein LCD Display immer das letzte Zeichen in der Anzeige bis ein neues Zeichen in den Platz geschrieben wird...

Versuche nochmal bei löschen des Zeichens, ein Leerzeichen an seinen Platz zu schreiben...

LG

@ Skipper_Do

danke für den Hinweis. Das war der Wink, den ich gebraucht habe.

Ich habe zuerst versucht, wie von die vorgeschlagen, ein Leerzeichen an den Platz zu schreiben. Jedoch wurde es "eingefügt, so dass sich die vorhandenen Zeichen nach rechts verschoben haben.

Nun habe ich es einfach so gelöst, dass ich beim Drücken der Sterntaste einfach das LCD lösche und neu aufbauen lasse.

Nun klapp es. Ob es letztendlich genau so funktioniert, wie ich mir das vorstelle, kann ich erst sagen, wenn ich die Steuerung samt Drehachse auf der Portalfräse ausprobiert habe. Bin da aber guter Hoffnung :slight_smile:

Danke nochmals und LG

Michael

Hi

Nicht die schönste Lösung - aber das Problem ist damit erst Mal hinterm Pflug.
Selber hatte ich Mal versuche, eine Menüstruktur zur Auswahl der Spindel oder eines zweier Laser-Module mit der Fräse zu verheiraten.
Ganz nebenbei wollte ich das Drehzahl-Signal der Steuerung (LinuxCNC) abgreifen und für den PWM-Laser (6000mW, Blau) benutzen.
An der Fräse habe ich aber so viele Störungen, daß zumindest der Breadboard-Aufbau keine 10 Sekunden am Stück überlebte, laufender Reset, spätestens, wenn die Spindel mit im Spiel war.
Das könnte auch auf Dich zukommen :wink:
Wäre nicht uninteressiert, wenn Du Deinen Aufbau am Rennen hast!

Was möchtest Du mit der 4.ten Achse bearbeiten? Fräse - was für Eine? Selber eine britische CNC3020-T per LinuxCNC, EstlCAM und LibreCAD. (Ist eine Chinesin, aber damals der günstigste Verkäufer kam aus UK) Mittlerweile bei Spindel 5 (Original DC 190V, Dremel, Geradschleifer, 500W PWM-Spindel, 1500W FU-Spindel)

MfG

Hi postmaster-ino,

na ich hoffe doch, dass die "Schönheit" mit der Erfahrung kommt :smiley: . Vorerst denke ich mir, lieber ein häßliches Auto als zu Fuß gehen....

Störungen an der Fräße können durchaus zu einem sehr ärgerllichen Problem werden, zumal man sich bei solchen Problemen oftmals dumm und dämlich sucht, bis man etwas gefunden hat. Da ich aber bei Fräse und Steuerung schon etwas auf die EMV geachtet habe (z.B. geschirrmte Schleppkettenleitungen, Schirmm auf Masse, Netzfilter in der Steuerung usw.), hoffe ich auch hier mal, dass es funktioniert. Aber wie schon erwähnt, werde ich das wohl erst sehen, wenn das ganze Brimborium montiert und in Betrieb ist. Ich hoffe mal, dass ich nächstes WE, oder bis Mitte nächter Woche schlauer bin.

Die 4. Achse benötige ich als Teilkopf. Also z.B. Bohrungen geleichmäßig auf einem Rundkörper zu verteilen. Ich muss natürlich erwähnen, dass die 4. Achse unabhängig von der CNC Steuerung läuft! Meine Fräse kann nur 2,5D. Bisher war es ausreichend. Ein Umbau auf 3D wäre erheblich teurer geworden, da ich ein anderes BOB sowie andere Software benötigt hätte. Da war die Lösung mit Arduino erstmal einfacher, zumal ich 3D bisher nicht wirklich vermisst habe

Meine Fräse ist eine Karla mit AMB1050 Fräsmotor mit Portalsteuerung (HF Spindel traue ich mich nicht, wegen der alten Elektrik in dem Miethaus, wo ich wohne ....( und ich bezahle dem Vermieter keinen Allstromsensitiven FI!). Antriebe Nema23 mit 1,9Nm, gesteuert über 3 Endstufen Leadshine DM542 und Versorgt mit 45V. Software nutze ich komplett Estlcam, Board ist die Mega2560 Variante von Arduinoclub.

Und was die 4. Achse angeht, so gebe ich die Hoffnung nicht auf, dass sich Christian doch noch dazu hinreißen läßt, eine 4. Achse in Estlcam zu programmieren :grinning:

LG

Immer das ganze Display löschen ist halt langsam und flackert. Auch Zeilen löschen und neu schreiben flackert. Normal formatiert man seine Ausgaben immer auf eine konstante Breite. Dann wird Text direkt überschrieben und der Rest mit Leerzeichen aufgefüllt

Hallo Serenifly,

Meinst du mit "formatieren, dass immer der gleiche Test an der gleichen Stelle erscheint? das hab ich im Prinzip so gemacht. Beim Neuaufbau des Displays werden die Zeichen immer an die gleiche Stelle gesetzt. Es geht um 3 Stellen in Zeile 2, die ich irgendwie gelöscht bekommen muss. Und da ja das LCD (vermutlich über einen eigenen kleinen speicher) die letzten Zeichen behält, werden diese Zeichen nicht gelöscht, da ja durch das Betätigen der Stern Taste keine Eingabe im eigentlichen Sinne gemacht wird. Ich habe mir mal die Commands vom Display angesehen, jedoch nichts gefunden, dass man einzelne Zeichen oder eine Zeile löschen kann.

LG

Nein. Das hat nichts mit der Position zu tun. Sondern dass du immer die gleiche Anzahl an Zeichen schreibst.

z.B. 1 wird zu "001" und 20 wird zu "020", bzw. führende Leerzeichen statt Nullen. Aber immer 3 Zeichen.
Das gleiche mit reinem Text. Erst den neuen Text schreiben und dann hinten mit Leerzeichen aufüllen

Ich habe mir mal die Commands vom Display angesehen, jedoch nichts gefunden, dass man einzelne Zeichen oder eine Zeile löschen kann

Genau deswegen habe ich das doch gesagt. Wenn man es richtig macht braucht man das nicht.
Löschen = Leerzeichen schreiben. Die Displays sind halt etwas langsam. Daher sieht es nicht gut aus wenn man erst eine Zeile löscht und dann neu schreibt

Hi

Wenn Du mit Leerzeichen löschen willst - schreibe testweise Bindestriche - dann siehst Du, Wo Du löscht.

Das Problem bekommen wir aber hin, wenn der Rest läuft ... zwei Wochen kann ich doch glatt noch auf Deine Erfolgsmeldung warten :slight_smile:

Was Christian (Knüll) angeht: Die zwei Mal, Die ich Ihn angeschrieben hatte, waren die BugFixes meist am gleichen Tag schon draußen.
Bin sehr angetan von Seinem Programm und schon einige Versionen dabei (v5 ??).

MfG

Hallo Leute,

hat nun doch etwas länger gedauert, als gedacht. Zum einen hat mich eine schöne Erkältung erwischt und zum anderen war das Gehäuse für die Steuerung doch aufwändiger, als ich erwartet habe. Jedenfalls ist die ganze Elektronik nun schön in einem Gehäuse verbaut und der Testaufbau auf dem Schreibtisch funktioniert.
Zum Testen an der Fräse zieht es mich im Moment nicht wirklich in den Keller, da ich noch nicht wirklich auf der Höhe bin.

Und als ich so auf dem Sofa lag, kam mir nach dem 15. Päckchen Tempos die Idee, dass es doch nützlich sein könnte, wenn man das Spannfutter permanent drehen lassen könnte (z. B. um den Rundlauf eines Bauteils im Spannfutter mittels Puppytaster zu prüfen und auszurichten).

Also hab ich die Taste A auf dem Keypad zum Starten des Motors definiert, die Taste B zum Stoppen. Leider konnte ich den Motor aber noch nicht dazu bewegen, dass es sich überhaupt dreht .... da muss ich noch etwas probieren.
Dabei ist mir aber ein Problem aufgefallen, für das ich bisher keine Idee habe:

Während der Motor sich dreht, sollte das Keypad "gesperrt" sein, damit man nicht versehentlich etwas eingeben kann. Erst nachdem man die Taste B gedrückt hat, um den Motor zu stoppen, sollte nach einer kurzen Wartezeit die Eingabe über das Keypad wieder funktionieren. Wenn also jemand eine Idee dazu hat, nur her damit :smiley:

LG
Michael

Hi

Einlesen, Was Da gedrückt wird, machst Du ja eh - wartest ja auf das 'B'.
WENN Du also die Funktion Dauerdrehen aktiv hast, wird Alles, was kein 'B' ist, verworfen.

MfG

Schönen Abend zusammen,

so .... wegen ausgefallener Kellerexperimente aufgrund heftiger Rüsselsucht hab ich mich mal etwas mit meinem Sketch befasst.

Scheinbar hab ich das mit dem LCD kapiert. Es werden nun nur noch die Bereiche neu geschrieben, in denen etwas geändert wird. Somit flackert das Display nicht mehr und der Sketch wird auch etwas schlanker.

Auch habe ich es nun endlich geschafft, dass sich mein Motor dreht. Aaaaber .... ums verrecken kann ich ihn nicht stoppen.

Ich habe die Tasten vom Keypad folgendermaßen definiert:

case 'A': //defines key to turn motor permanently
turnmotor();
break;

case 'B': //defines key to stop motor
stopmotor();
break;

und dann mittels void folgender maßen ausgeführt:

void turnmotor(){

int steps=1;
stepper.setMaxSpeed(300);

do{
int turn=(steps++);
stepper.moveTo(turn);
stepper.run();
}while(stopmotor);

}

void stopmotor(){

stepper.setCurrentPosition(0);
stepper.stop();
}

wenn ich nun die TAste A drücke, dreht sich der Motor permanent. Soweit so gut! Wenn ich jedoch dann Taste B drücke, läuft der Motor munter weiter. Man kann nur noch ausschalten. Also bleibe ich in der do while Schleife hängen.
Nun frage ich mich: habe ich beim Argument bei "while" etwas falsches eingetragen oder ist "stopmotor" falsch definiert?

LG
Michael

Gib uns bitte den vollständigen Sketch.
stopmotor hast Du als Funktion angelegt, deswegen ist die verwendung des reinen Namens die Aufrufadresse der Funktion.

Da geht einiges schief, das kann man aber an dem Fragment nicht genau definieren.

Setze Deinen Code bitte in Codetags (</>-Button oben links im Forumseditor oder [code] davor und [/code] dahinter ohne *).
Dann ist er auch auf mobilen Geräten besser lesbar.
Das kannst Du auch noch nachträglich ändern.

Gruß Tommy

Hi

Eine WHILE-Schleife wird so lange ausgeführt, wie die Bedingung wahr ist.
stopmotor ist NUR die Adrese der Funktion void stopmoter(void);.
DAS hätte Dir der Kompiler auch als Warnung gesagt, wenn Du Ihn Das hättest anzeigen lassen.
Da die Adresse ungleich Null ist, ist die WHILE IMMER wahr - somit kommst Du aus dieser While nie wieder raus.

Warum nicht beim Druck auf 'A' eine Variable 'dauerlauf' auf true setzen?
Warum nicht bei Druck auf 'B' die Variable 'dauerlauf' wieder auf false setzen?
Warum nicht bei jedem anderen Druck prüfen, ob 'dauerlauf' ungleich true ist, sonst die Eingabe verwerfen?
Warum nicht, wenn 'dauerlauf' true ist, den Motor weiter drehen lassen?

ABER: Das ALLES nicht in einer while - Das musst Du bei JEDEM Durchlauf prüfen und entsprechend verzweigen.

MfG

Die Petition zum Sketch in Code-Tags unterstütze ich ebenfalls.

sorry Tommy56 & postmaster-ino, hier mal der vollständige Sketch

#include "AccelStepper.h" // AccelStepper Library
#include <Keypad.h>  // Keypad Library
#include <Wire.h> // I2C Bus Library
#include <LiquidCrystal_I2C.h> // LCD Library
LiquidCrystal_I2C lcd(0x27,20,4); // Adress for LCD

// Variables to hold entered number on Keypad
volatile int firstnumber=99;  // used to tell how many numbers were entered on keypad
volatile int secondnumber=99;
volatile int thirdnumber=99;

// Variables to hold Distance and CurrentPosition
int keyfullnumber=0;  // used to store the final calculated distance value
String currentposition = "";  // Used for display on LCD


// Keypad Setup
const byte ROWS = 4; // Four Rows
const byte COLS = 4; // Four Columns
char keys[ROWS][COLS] = {
  {'1','2','3','A'},
  {'4','5','6','B'},
  {'7','8','9','C'},
  {'*','0','#','D'}
};
byte rowPins[ROWS] = {2,3,4,5}; // Arduino pins connected to the row pins of the keypad
byte colPins[COLS] = {8,9,10,11}; // Arduino pins connected to the column pins of the keypad
Keypad keypad = Keypad( makeKeymap(keys), rowPins, colPins, ROWS, COLS );  // Keypad Library definition
                                                                  
// AccelStepper Setup
AccelStepper stepper(1, A0, A1);  // 1 = Easy Driver interface
                                  // Arduino A0 connected to STEP pin of Easy Driver
                                  // Arduino A1 connected to DIR pin of Easy Driver

void setup(void) {
    {
      lcd.init(); // initiate LCD
      lcd.begin(20,4); // start LCD
      lcd.backlight(); // turn LCD backlight on
    }
  
    
  //  AccelStepper speed and acceleration setup
  stepper.setMaxSpeed(1200);  // Not to fast or you will have missed steps
  stepper.setAcceleration(600);  //  Same here
  
  // Draw starting screen on LCD
   {

    lcd.clear();
    lcd.setCursor(4,0);
    lcd.print("NC Drehachse");
    lcd.setCursor(0,1);
    lcd.print("--------------------");
    lcd.setCursor(1,2);
    lcd.print("Indexer Ver. 1.12"); // only shown at power on
    delay(2000);
    lcd.setCursor(1,2);
    lcd.print("                 ");
    lcd.setCursor(0,2);
    lcd.print("Winkeleingabe:");
    lcd.setCursor(19,2);
    lcd.write(0xDF);
    lcd.setCursor(1,3);
    lcd.print("Aktuelle Pos:");
    lcd.setCursor(19,3);
    lcd.write(0xDF);
    
  }
  
}

void loop(){
  
  char keypressed = keypad.getKey();  // Get value of keypad button if pressed
  if (keypressed != NO_KEY){  // If keypad button pressed check which key it was
    switch (keypressed) {
      
      case '1':
        checknumber(1);
      break;
        
      case '2':
        checknumber(2);
      break;

      case '3':
        checknumber(3);
      break;

      case '4':
        checknumber(4);
      break;

      case '5':
        checknumber(5);
      break;

      case '6':
        checknumber(6);
      break;

      case '7':
        checknumber(7);
      break;

      case '8':
        checknumber(8);
      break;

      case '9':
        checknumber(9);
      break;

      case '0':
        checknumber(0);
      break;

      case '*':
        deletenumber();
      break;

      case '#':
        calculatedistance();
      break;

      case 'A':         //defines key to turn motor permanently
        turnmotor();
      break;

      case 'B':         //defines key to stop motor
        stopmotor();   
      break;
    }
  }

}

void checknumber(int x){
  if (firstnumber == 99) { // Check if this is the first number entered
    firstnumber=x;
    String displayvalue = String(firstnumber);  //  Transform int to a string for display
    lcd.setCursor(16,2);
    lcd.print(displayvalue);
  } else {
    if (secondnumber == 99) {  // Check if it's the second number entered
      secondnumber=x;
      String displayvalue = (String(firstnumber) + String(secondnumber));
      lcd.setCursor(16,2);
      lcd.print(displayvalue);
  } else {  // It must be the 3rd number entered
      thirdnumber=x;
      String displayvalue = (String(firstnumber) + String(secondnumber) + String(thirdnumber));
      lcd.setCursor(16,2);
      lcd.print(displayvalue);
    }
  }
}

 
void deletenumber() {  // Used to backspace entered numbers
  if (thirdnumber !=99) {
      String displayvalue = (String(firstnumber) + String(secondnumber));
        
          lcd.setCursor(15,2);
          lcd.print("    "); // clears LCD area for new displayvalue / delete third number
          lcd.setCursor(16,2);
          lcd.print(displayvalue);
        thirdnumber=99;
  } 
  else {
    if (secondnumber !=99) {
      String displayvalue = String(firstnumber);
     
          lcd.setCursor(15,2);
          lcd.print("    "); // clears LCD area for new displayvalue / delete second number
          lcd.setCursor(16,2);
          lcd.print(displayvalue);
      secondnumber=99;
   } 
   else {
     if (firstnumber !=99) {
       String displayvalue = "";
     
          lcd.setCursor(15,2);
          lcd.print("    ");  // clears LCD area for new displayvalue / delete first number
          lcd.setCursor(16,2);
          lcd.print(displayvalue);
       firstnumber=99;
      }
    }
  }
}
  
void calculatedistance() {  // Used to create a full number from entered numbers

    if (thirdnumber == 99 && secondnumber == 99 && firstnumber != 99) {
      keyfullnumber=firstnumber;
      movestepper(keyfullnumber);
    }
    
    if (secondnumber != 99 && thirdnumber == 99) {
      keyfullnumber=(firstnumber*10)+secondnumber;
      movestepper(keyfullnumber);
    }
    
    if (thirdnumber != 99) {
      keyfullnumber=(firstnumber*100)+(secondnumber*10)+thirdnumber;
      movestepper(keyfullnumber);
    }
    
    resetnumbers(); // Reset numbers to get ready for new entry
  } 

void movestepper(float z) {  //  Move the stepper
  
  float calculatedmove=((z*1600*4)/360); // Calkulate Steps/°(z * 1600 Microsteps * Gear ratio)/ 360° ...
  stepper.runToNewPosition(calculatedmove);
  currentposition = int(z); // change z into an int to display on LCD an even Number, 
 
  {

    lcd.setCursor(15,2);
    lcd.print("    "); // clears LCD area to reset numbers for next entry
    lcd.setCursor(14,3);
    lcd.print("     "); // clears LCD area to display next current position
    lcd.setCursor(16,3);
    lcd.print(currentposition);
    
}
  
}
                
void resetnumbers() {  // Reset numbers for next entry
  firstnumber=99;
  secondnumber=99;
  thirdnumber=99;
} 

void turnmotor(){

  int steps=1;
  stepper.setMaxSpeed(300);
  
    do{
      int turn=(steps++);
      stepper.moveTo(turn);
      stepper.run();
    }while(stopmotor);

}

void stopmotor(){

     stepper.setCurrentPosition(0);
     stepper.stop();
}

Ich hoffe, so ist es richtig mit dem Code....

@postmaster-ino

eigentlich lasse ich mir die Fehler schon anzeigen. Hat mir schon des öfteren geholfen, ein vergessenes Semikolon oder eine vergessene Klammer zu setzen. Bei diesem Sketch hat der Compiler nicht gemeckert. Da dachte ich .... nun gut, dann mal hoch auf den Uno damit.

Wie schon erwähnt, funktioniert soweit alles bis auf das Stoppen des Motors

LG
Michael

Wie schon geschrieben stopmotor ist die Adresse der Funktion stopmotor() und damit nie false.

Gruß Tommy

Hallo Zusammen,

so, da ist er wieder ....

nachdem ich nun einige Möglichkeiten versucht habe, mein "STOP" Problem innerhalb von loop zu lösen, muss ich mir doch eingestehen, dass ich noch blutiger Anfänger bin, der noch vieles zu lernen hat.

Also bin ich dazu zurück, dass ich drehen und stoppen des Motors über eine Funktion mache. Und was soll ich sagen .... habs soweit hinbekommen.

Lediglich ein Problem habe ich noch, bei dem ich auf keine Lösung komme:

Wenn der Uno neu gestartet wird (z.B. Reset, einschalten oder nach hochladen des Sketch) und dann mittels Taste A die Funktion "turnmotor" aufgerufen wird, muss man die Taste A zweimal drücken. Beim ersten mal zuckt der Motor nur ganz kurz. Beim zweiten Druck auf A funktioniert es dann genau so, wie ich es mir vorstelle. Wenn ich mir das LCD ansehe, sieht es so aus, als würde nach einem Neustart vom Uno beim Druck auf A die Funktion "turnmotor" zwar aufgerufen, aber das Programm rennt einfach durch die Funktion durch und ignoriert (außer die LCD Anzeigen) die Anweisungen innerhalb der Funktion.
Aber wie beschrieben, passiert das nur nach einem Neustart vom Board. Solange das Board dann läuft, kann ich munter Winkel eingeben, anfahren, den Motor drehen lasen und auch stoppen .... genau so, wie ich mir das eben vorstelle.

--> Sketch im nächsten Beitrag, da mir gesagt wird, meine Nachricht ist zu lang .....

LG
Michael

so, hier der Sketch:

#include "AccelStepper.h" // AccelStepper Library
#include <Keypad.h>  // Keypad Library
#include <Wire.h> // I2C Bus Library
#include <LiquidCrystal_I2C.h> // LCD Library
LiquidCrystal_I2C lcd(0x27,20,4); // Adress for LCD

// Variables to hold entered number on Keypad
volatile int firstnumber=99;  // used to tell how many numbers were entered on keypad
volatile int secondnumber=99;
volatile int thirdnumber=99;

// Variables to hold Distance and CurrentPosition
int keyfullnumber=0;  // used to store the final calculated distance value
String currentposition = "";  // Used for display on LCD

// Keypad Setup
const byte ROWS = 4; // Four Rows
const byte COLS = 4; // Four Columns
char keys[ROWS][COLS] = {
  {'1','2','3','A'},
  {'4','5','6','B'},
  {'7','8','9','C'},
  {'*','0','#','D'}
};
byte rowPins[ROWS] = {2,3,4,5}; // Arduino pins connected to the row pins of the keypad
byte colPins[COLS] = {8,9,10,11}; // Arduino pins connected to the column pins of the keypad
Keypad keypad = Keypad( makeKeymap(keys), rowPins, colPins, ROWS, COLS );  // Keypad Library definition
                                                                  
// AccelStepper Setup
AccelStepper stepper(1, A0, A1);  // 1 = Easy Driver interface
                                  // Arduino A0 connected to STEP pin of Easy Driver
                                  // Arduino A1 connected to DIR pin of Easy Driver

bool stopmotor=false;   // Variable to stop permanent turning Motor in funktion "void turnmotor()"
char stopm;             // Variable for keypad input in funktion "void turnmotor()"
volatile long total=1;  // Variable for counting in funktion "void turnmotor()"
volatile long go;       // Variable for moving motor in funktion "void turnmotor()"

void setup(void) {
    {
      lcd.init(); // initiate LCD
      lcd.begin(20,4); // start LCD
      lcd.backlight(); // turn LCD backlight on
    }
     
  //  AccelStepper speed and acceleration setup
  stepper.setMaxSpeed(1000);  // Not to fast or you will have missed steps
  stepper.setAcceleration(700);  //  Same here
  
  // Draw starting screen on LCD
   {

    lcd.clear();
    lcd.setCursor(4,0);
    lcd.print("NC Drehachse");
    lcd.setCursor(0,1);
    lcd.print("--------------------");
    lcd.setCursor(1,2);
    lcd.print("Indexer Ver. 1.21"); // only shown at power on
    delay(2000);
    lcd.setCursor(1,2);
    lcd.print("                 ");
    lcd.setCursor(0,2);
    lcd.print("Winkeleingabe:");
    lcd.setCursor(19,2);
    lcd.write(0xDF);
    lcd.setCursor(1,3);
    lcd.print("Aktuelle Pos:");
    lcd.setCursor(19,3);
    lcd.write(0xDF);
    
  }
  
}

void loop(){
  
  char keypressed = keypad.getKey();  // Get value of keypad button if pressed
  if (keypressed != NO_KEY){  // If keypad button pressed check which key it was
    switch (keypressed) {
      
      case '1':
        checknumber(1);
      break;
        
      case '2':
        checknumber(2);
      break;

      case '3':
        checknumber(3);
      break;

      case '4':
        checknumber(4);
      break;

      case '5':
        checknumber(5);
      break;

      case '6':
        checknumber(6);
      break;

      case '7':
        checknumber(7);
      break;

      case '8':
        checknumber(8);
      break;

      case '9':
        checknumber(9);
      break;

      case '0':
        checknumber(0);
      break;

      case '*':
        deletenumber();
      break;

      case '#':
        calculatedistance();
      break;

      case 'A':         //defines button for funktion to turn motor permanently
        turnmotor();
      break;

    }
  }

}

void checknumber(int x){
  if (firstnumber == 99) { // Check if this is the first number entered
    firstnumber=x;
    String displayvalue = String(firstnumber);  //  Transform int to a string for display
    lcd.setCursor(16,2);
    lcd.print(displayvalue);
  } else {
    if (secondnumber == 99) {  // Check if it's the second number entered
      secondnumber=x;
      String displayvalue = (String(firstnumber) + String(secondnumber));
      lcd.setCursor(16,2);
      lcd.print(displayvalue);
  } else {  // It must be the 3rd number entered
      thirdnumber=x;
      String displayvalue = (String(firstnumber) + String(secondnumber) + String(thirdnumber));
      lcd.setCursor(16,2);
      lcd.print(displayvalue);
    }
  }
}

 
void deletenumber() {  // Used to backspace entered numbers
  if (thirdnumber !=99) {
      String displayvalue = (String(firstnumber) + String(secondnumber));
        
          lcd.setCursor(15,2);
          lcd.print("    "); // clears LCD area for new displayvalue / delete third number
          lcd.setCursor(16,2);
          lcd.print(displayvalue);
        thirdnumber=99;
  } 
  else {
    if (secondnumber !=99) {
      String displayvalue = String(firstnumber);
     
          lcd.setCursor(15,2);
          lcd.print("    "); // clears LCD area for new displayvalue / delete second number
          lcd.setCursor(16,2);
          lcd.print(displayvalue);
      secondnumber=99;
   } 
   else {
     if (firstnumber !=99) {
       String displayvalue = "";
     
          lcd.setCursor(15,2);
          lcd.print("    ");  // clears LCD area for new displayvalue / delete first number
          lcd.setCursor(16,2);
          lcd.print(displayvalue);
       firstnumber=99;
      }
    }
  }
}
  
void calculatedistance() {  // Used to create a full number from entered numbers

    if (thirdnumber == 99 && secondnumber == 99 && firstnumber != 99) {
      keyfullnumber=firstnumber;
      movestepper(keyfullnumber);
    }
    
    if (secondnumber != 99 && thirdnumber == 99) {
      keyfullnumber=(firstnumber*10)+secondnumber;
      movestepper(keyfullnumber);
    }
    
    if (thirdnumber != 99) {
      keyfullnumber=(firstnumber*100)+(secondnumber*10)+thirdnumber;
      movestepper(keyfullnumber);
    }
    
    resetnumbers(); // Reset numbers to get ready for new entry
  } 

void movestepper(float z) {  //  Move the stepper
  
  float calculatedmove=((z*1600*4)/360); // Calkulate Steps/°(z * 1600 Microsteps * Gear ratio)/ 360° ...
  stepper.runToNewPosition(calculatedmove);
  currentposition = int(z); // change z into an int to display on LCD an even Number, 
 
  {

    lcd.setCursor(15,2);
    lcd.print("    "); // clear LCD area to reset numbers for next entry
    lcd.setCursor(14,3);
    lcd.print("     "); // clear LCD area to display next current position
    lcd.setCursor(16,3);
    lcd.print(currentposition);
    
  }
  
}
                
void resetnumbers() {  // Reset numbers for next entry
  firstnumber=99;
  secondnumber=99;
  thirdnumber=99;
} 

void turnmotor(){               // funktion to turn Motor permanently
  
  stepper.setMaxSpeed(300);     // set motorspeed to 300 steps/min
  
      lcd.setCursor(0,2);
      lcd.print("    Motor dreht     ");
      lcd.setCursor(0,3);
      lcd.print("                    ");
      
  do {
    stopm=keypad.getKey();      
        if(stopm=='B'){            // if keypad input = B ....
        stopmotor=!stopmotor;      // toogle stopmotor into true
        } 
    go=(total++);                  // count steps for motor
    stepper.moveTo(go);            
    stepper.run();
    

      
  } while (stopmotor==true);
  stepper.setCurrentPosition(0);  // stop motor and set position to 0

    lcd.setCursor(3,2);
    lcd.print(" Motor STOP   ");

    delay(1500);

    lcd.setCursor(0,2);
    lcd.print("Winkeleingabe:");
    lcd.setCursor(19,2);
    lcd.write(0xDF);
    lcd.setCursor(1,3);
    lcd.print("Aktuelle Pos:");
    lcd.setCursor(19,3);
    lcd.write(0xDF);
  
  stepper.setMaxSpeed(1000);      // set motorspeed back to 1000 steps/min
  stopmotor=!stopmotor;           // toggle stopmotor back to false
  
 }

LG

Hi

Nocj nicht zu Deinem Problem, aber Du solltest Abstand von String nehmen.
Ab Zeile 142

    String displayvalue = String(firstnumber);  //  Transform int to a string for display
    lcd.setCursor(16,2);
    lcd.print(displayvalue);
    lcd.setCursor(16,2);
    lcd.print(firstnumber);

Ab Zeile 249:

  do {
    stopm=keypad.getKey();     
        if(stopm=='B'){            // if keypad input = B ....
        stopmotor=!stopmotor;      // toogle stopmotor into true
        }
    go=(total++);                  // count steps for motor
    stepper.moveTo(go);           
    stepper.run();
  } while (stopmotor==true);

Blöd, daß Du beim Start in Zeile 34

bool stopmotor=false;   // Variable to stop permanent turning Motor in funktion "void turnmotor()"

stopmotor auf false setzt - vor der DO-WHILE-Schleife ändert NIEMAND diesen Wert, somit ist der Wert FALSE und die DO-WHILE wird direkt nach dem ersten Schritt abgebrochen.

Ändere die Zeile 34 Mal auf true.

Und bitte reduziere die Leerzeilen - Das sind keine Rudeltiere!

MfG