Nano zu langsam für Display + Ultraschallsensor + Servo?

Hallo liebe Community,

ich habe ein Problem bei folgender Aufgabenstellung:

Ein Ultraschallsensor (HC-SR04) wird durch einen Servo kontinuierlich bewegt (von 0Grad bis 180Grad, und dann wieder zurück), um den vorliegenden Bereich "abzuscannen".

Die Messergebnisse werden auf einem Display (1.8" TFT) ebenfalls kontinuierlich, übereinstimmend mit der Servoposition (Winkel) angezeigt.

Das Ganze wird mit einem Arduino Nano (oder aktueller Versuch Nano Every) realisiert.

Folgender Code läuft soweit auch, nur leider sehr langsam. Dies bedeutet, der Servo benötigt ca. eine Minute um sich von 0 bis 180° zu drehen, und läuft auch nur "ruckelnd".

Meine Frage wäre nun ob der "Nano" einfach mit dieser Aufgabe überfordert ist, oder ob es möglich wäre den Code "schlanker" oder einfach intelligenter zu schreiben?

#include<Servo.h>     //Library für Servomotor
#include <SPI.h>      //Library Schnittstellen
#include <TFT.h>      //Library Display
#include "Ucglib.h"   //Library Display

#define trigPin  8    //Pin für den sendenden Ultraschallsensor
#define echoPin  9    //Pin für den empfangenden Ultraschallsensor
#define TFT_CD  6     //Pin command/data Display
#define TFT_CS  10    //Pin Chip select Display
#define TFT_RST 2     //Pin reset Display 

Servo myServo;        //Erstellung Servomotor
Ucglib_ST7735_18x128x160_HWSPI ucg(TFT_CD, TFT_CS, TFT_RST); //Zuweisung Pins von Display


int x;                //Variable x für Schleifen
int p = 5;            //Pin Servo
int distance;         //berechnete Entfernung Hindernis, Sensor schafft 65cm
int Ymax = 128;       //Bildschirmhöhe
int Xmax = 160;       //Bildschirmbreite
int pos = 8;          //Höhe des Radars auf dem Bildschirm
int deg;              //Variable Grad
int val = 200;        //Länge Linien Radar
int k;                //Variable Umwandlung x auf Display
int previous_k;       //grüne Linie mit Verzögerung löschen
long duration;        //Dauer Ultraschallmessung
float theta;          //Bogenmaß berechnen
float scaled_distance;//Verhältnis echte Entfernung zu Display
float m;              //X-Koordinate Hindernis auf Display
float n;              //Y-Koordinate Hindernis auf Display
char buffer[3];       //benötigt für korrekte Grad-Anzeige bei Rechtslauf

float ring1 = 0.30;   //Beschriftungen für Halbkreise auf Display; zeigen grobe Entfernung an
float ring2 = 0.45;
float ring3 = 0.60;

void setup(void) {
  myServo.write(0);                           //Servo startet in Position 90°
  pinMode(trigPin,OUTPUT);                    //Zuweisung Trigger als Sender
  pinMode(echoPin,INPUT);                     //Zuweisung Echo als Empfänger
  myServo.attach(p);                          //Servo auf Pin 5
  Serial.begin(19200);                         //Einstellung Baud  9600
  ucg.begin(UCG_FONT_MODE_SOLID);             //Schrift Display
  ucg.setFont(ucg_font_6x10_tr);              //Schrift Display
  ucg.clearScreen();                          //Bildschirm leeren
  ucg.setRotate270();                          //Rotation des Bildes um 90°
}

void loop(void) {
  
  fix();
  for ( x=0; x <= 180; x++){                  
    
    delay(5);                                 // 5   
    myServo.write(x);  
    distance = calculateDistance();           //Entfernung zu Hindernis durch Funktion calculateDistance()
    ucg.setPrintPos(10,0);                    //Anzeige Entfernung Hindernis
    ucg.print(distance);

    k = map(x, 0, 180, 88, 2);                //Anpassen Grad des Servos an Displaygröße
  
    if (distance < 65) {                                              //Bis max. 65cm Entfernung
      scaled_distance = distance / 65.0;                              //Verhältnis Gesamtentfernung zu Displaygröße
      theta = x * (PI / 180);                                         //Grad umrechnen in Bogenmaß
      m = (Xmax / 2) - (scaled_distance * (Xmax / 2) * -cos(theta));   //X-Koordinate des Hindernisses auf Display
      n = (scaled_distance * Ymax * sin(theta));                      //Y-Koordinate des Hindernisses auf Display
      ucg.setColor(255, 0, 0);                                        //rot
      ucg.drawPixel(m, n + pos);                                      //Zeichnet Pixel auf Display
 }
 else {
      ucg.setColor(0, 207, 0);                                        //grün
      ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * cos(radians(k * 2))), pos + (val * sin(radians(k * 2))));    //Zeichnet grüne Linie falls kein Hindernis
    }

    previous_k = map(x - 10, 0, 180, 88, 2);                          //löscht grüne Linie mit Verzögerung, Anpassung von 180° an Display
    ucg.setColor(0, 0, 0); 
    ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * cos(radians(previous_k * 2))), pos + (val * sin(radians(previous_k * 2))));


  ucg.setColor(255, 0, 0);      //Gradanzeige links unten           
  ucg.setPrintPos(160,0);
  ucg.setPrintDir(2);
  ucg.print("Deg :");
  deg = x; 
  ucg.setPrintPos(120,0);
  ucg.setPrintDir(2);
  ucg.print(deg);
   
  ucg.setColor(0, 0, 255);      //Zahlenanzeige Kreisraster
  ucg.setPrintPos(90,38);
  ucg.setPrintDir(2);
  ucg.print(ring1);
  ucg.setPrintPos(90,70);
  ucg.print(ring2);
  ucg.setPrintPos(90,110);
  ucg.print(ring3);
}

ucg.clearScreen();
fix();

for ( x=180; x >= 0; x--){                                              
    delay(5);                                   
    myServo.write(x);                                                   //Rechtslauf durch Hochzählen von x in der Schleife
    distance = calculateDistance();                                     //Entfernung zu Hindernis durch Funktion calculateDistance()
    ucg.setPrintPos(10,0);
    ucg.print(distance);                                                //Ausgabe Entfernung

    k = map(x, 0, 180, 2, 88);                                          //Anpassen des Grad-Bereichs des Servos an Display

    if (distance < 65) {                                                //Bis max. 65cm Entfernung
      scaled_distance = distance / 65.0;                                //Verhältnis Gesamtentfernung zu Displaygröße
      theta = x * (PI / 180);                                           //Umrechnen Grad in Bogenmaß
      m = (Xmax / 2) - (scaled_distance * (Xmax / 2) * -cos(theta));     //X-Koordinate
      n = (scaled_distance * Ymax * sin(theta));                        //Y-Koordinate
      ucg.setColor(255, 0, 0);                                          //rot
      ucg.drawPixel(m, n + pos);                                        //Zeichnet Hindernis als Pixel
 }
 else {
      ucg.setColor(0, 207, 0);
      ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * -cos(radians(k * 2))), pos + (val * sin(radians(k * 2))));    //zeichnet grüne Linie, wenn kein Hindernis erkannt
    }

      previous_k = map(x + 10, 0, 180, 2, 88);
      ucg.setColor(0, 0, 0); 
      ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * -cos(radians(previous_k * 2))), pos + (val * sin(radians(previous_k * 2))));    //löscht grüne Linie mit Verzögerung

  ucg.setColor(255, 0, 0);      //Grad-Anzeige unten links
  ucg.setPrintPos(160,0);
  ucg.setPrintDir(2);
  ucg.print("Deg :"); 

  sprintf(buffer, "%03d", x);   //korrekte Anzeige, sonst 990... anstatt 99...
  
  ucg.setPrintPos(120,0);
  ucg.setPrintDir(2);  
  ucg.print(buffer);
  
  ucg.setColor(0, 0, 255);
  ucg.setPrintPos(90,38);
  ucg.setPrintDir(2);
  ucg.print(ring1);             //Zahlenanzeige Kreisraster
  ucg.setPrintPos(90,70);
  ucg.print(ring2);
  ucg.setPrintPos(90,110);
  ucg.print(ring3);
   
}
ucg.clearScreen();
}

int calculateDistance(){                      //Implementierung Funktion zur Berechnung der Entfernung mithilfe des Sensors
    digitalWrite(trigPin, HIGH);              //Sender anschalten
    delayMicroseconds(10);                    //Sendezeit 10 Mikrosekunden
    digitalWrite(trigPin, LOW);               //Sender ausschalten             
  
  duration = pulseIn(echoPin,HIGH,10000);     //Reisezeit ist der empfangene Puls am Echopin (wenn dieser HIGH ist); der Sensor wartet 10 ms
  if (duration == 0) {                        
    distance = 999;                           //wenn der Sensor nach 10 ms nichts empfangen hat setzt er die Entfernung auf 999
  } 
  else {
    distance = duration*0.034/2;}             //Berechnung der Entfernung durch die Schallgeschwindigkeit (340 m/s) durch Hin- und Rücklauf /2 , da Einzelstrecke benötigt
    if (distance > 65) {                      //wenn Entfernung größer 65cm, dann Ausgabe 999
          distance = 999;}
   return distance;
  }

void fix() {                                  //Hintergrunddesign mit Halbkreisen
  ucg.setColor(255, 0, 0);
  ucg.drawDisc(Xmax / 2, pos, 5, UCG_DRAW_LOWER_RIGHT);
  ucg.drawDisc(Xmax / 2, pos, 5, UCG_DRAW_LOWER_LEFT);

  ucg.setColor(225, 255, 50);
  ucg.drawCircle(80, pos, 115, UCG_DRAW_LOWER_RIGHT);
  ucg.drawCircle(80, pos, 115, UCG_DRAW_LOWER_LEFT);

  ucg.drawCircle(80, pos, 78, UCG_DRAW_LOWER_RIGHT);
  ucg.drawCircle(80, pos, 78, UCG_DRAW_LOWER_LEFT);

  ucg.drawCircle(80, pos, 40, UCG_DRAW_LOWER_RIGHT);
  ucg.drawCircle(80, pos, 40, UCG_DRAW_LOWER_LEFT);

  ucg.drawLine(0, pos, 160, pos);

  ucg.setColor(0, 0, 0);
  ucg.drawBox(100, 0, 30, 8);
}

Ich bin über jegliche Hilfe dankbar,
vielen herzlichen Dank!

Du machst:

  • servo 1° bewegen
  • US Abstand lesen
  • Display darstellen
  • goto 0

das dauert ewig.

Das hindert jeglichen µC und sei er noch so schnell, etwas zu tun. Verwende stattdessen millis()``, siehe IDE-Beispiel Blinken ohne delay.

Blockierende for-Schleifen sind mindestens schlechter Stil.

Die Lösung sind blockadearme "Zeitscheiben" in Zusammenhang mit Schrittketten (=finite state machine; =endlicher Automat).

Hallo zwieblum,
vielen Dank für deine Antwort!

  • den Servo kann ich auch um mehrere ° pro Schritt bewegen, das habe ich soeben versucht, es bleibt aber natürlich das "Geruckele"...

Hallo agmue,
vielen Dank für deine Antwort! Das klingt einleuchtend :slight_smile:

  • Ich denke das Thema mit den "millis()" habe ich halbwegs verstanden, ich versuche mal ob ich das in den Code eingebaut bekomme.

  • Wie das mit den blockadearmen "Zeitscheiben" funktioniert kann ich momentan nicht nach vollziehen, da muss ich mich erst einarbeiten.

Ich komme eigentlich aus einem gänzlich anderen Bereich, bitte verzeiht meine Unwissenheit!

Der "normale" Nano hat außer der Bauform mit dem Nano Every nichts gemeinsam.

Die Unwissenheit ist angeboren und niemand kann alles Wissen. Glücklicherweise können wir diesen Zustand durch Lernen verändern :smiley:

Die Vorstellungskraft ist wichtiger als Wissen, denn Wissen ist begrenzt. (Albert Einstein)

Ein µC kann immer nur genau eine Sache machen. Aber durch Verteilung der Rechenzeit auf mehrere Aufgaben kann man eine quasi Parallelverarbeitung erreichen.

Beispiel: Du drehst den Servo und wartest 5 ms. Während des Wartens könntest Du schon was auf das Display schreiben.

Laut Deinem Code bewegte er sich um 1 Grad mit einem Delay vom 5ms. D.h. bei 180 Grad sollte das weniger als 1 Sekunde dauern. Und nicht wie von Dir beschrieben 1 Minute. Da läuft was anderes schief.
Ich würde an Deiner Stelle mal ein ganz simples Programm machen, dass nur den Servo bewegt und sonst nicht macht. Vielleicht zuerst in einem grossen Schritt und falls das geht in vielen kleinen Schritten, so wie das später sein soll.

Habe gerade noch das gefunden:
https://docs.arduino.cc/learn/electronics/servo-motors/

Capacitors are recommended for powering servo motors. They help stabilize the power supply, minimize voltage drops, and reduce electrical noise. The specific capacitor values may vary based on the servo motor's requirements, but including them is good practice for better performance and reliability.

Serial.begin(19200); 

Braucht es das noch? k.A. wie viel Resourcen das ev. verbraucht. Aber so wie ich das auf die Schnelle sehe gibst Du nichts seriell aus?

Noch was zur Elektronik (obwohl ich davon sehr wenig Ahnung habe). Warum ist das TFT sowohl an 3.3 als auch an 5V angeschlossen. Muss das so? Kann der 5V Anschluss des Nano genügend Strom liefern für Servo, TFT und USensor?

Teste es mal so:

#include <Servo.h>   //Library für Servomotor
#include <SPI.h>     //Library Schnittstellen
#include <TFT.h>     //Library Display
#include "Ucglib.h"  //Library Display

#define trigPin 8  //Pin für den sendenden Ultraschallsensor
#define echoPin 9  //Pin für den empfangenden Ultraschallsensor
#define TFT_CD 6   //Pin command/data Display
#define TFT_CS 10  //Pin Chip select Display
#define TFT_RST 2  //Pin reset Display

Servo myServo;                                                //Erstellung Servomotor
Ucglib_ST7735_18x128x160_HWSPI ucg(TFT_CD, TFT_CS, TFT_RST);  //Zuweisung Pins von Display

uint8_t = x;            //Variable x für Schleifen
int p = 5;              //Pin Servo
int distance;           //berechnete Entfernung Hindernis, Sensor schafft 65cm
int Ymax = 128;         //Bildschirmhöhe
int Xmax = 160;         //Bildschirmbreite
int pos = 8;            //Höhe des Radars auf dem Bildschirm
int deg;                //Variable Grad
int val = 200;          //Länge Linien Radar
int k;                  //Variable Umwandlung x auf Display
int previous_k;         //grüne Linie mit Verzögerung löschen
long duration;          //Dauer Ultraschallmessung
float theta;            //Bogenmaß berechnen
float scaled_distance;  //Verhältnis echte Entfernung zu Display
float m;                //X-Koordinate Hindernis auf Display
float n;                //Y-Koordinate Hindernis auf Display
char buffer[3];         //benötigt für korrekte Grad-Anzeige bei Rechtslauf

float ring1 = 0.30;  //Beschriftungen für Halbkreise auf Display; zeigen grobe Entfernung an
float ring2 = 0.45;
float ring3 = 0.60;

void setup(void) {
  myServo.write(0);                //Servo startet in Position 90°
  pinMode(trigPin, OUTPUT);        //Zuweisung Trigger als Sender
  pinMode(echoPin, INPUT);         //Zuweisung Echo als Empfänger
  myServo.attach(p);               //Servo auf Pin 5
  Serial.begin(19200);             //Einstellung Baud  9600
  ucg.begin(UCG_FONT_MODE_SOLID);  //Schrift Display
  ucg.setFont(ucg_font_6x10_tr);   //Schrift Display
  ucg.clearScreen();               //Bildschirm leeren
  ucg.setRotate270();              //Rotation des Bildes um 90°
}

void loop(void) {
  fix();
  for (x = 0; x <= 180; x++) {
    myServo.write(x);
    distance = calculateDistance();  //Entfernung zu Hindernis durch Funktion calculateDistance()
    ucg.setPrintPos(10, 0);          //Anzeige Entfernung Hindernis
    ucg.print(distance);
    if (distance < 65) {                                              //Bis max. 65cm Entfernung
      scaled_distance = distance / 65.0;                              //Verhältnis Gesamtentfernung zu Displaygröße
      theta = x * (PI / 180);                                         //Grad umrechnen in Bogenmaß
      m = (Xmax / 2) - (scaled_distance * (Xmax / 2) * -cos(theta));  //X-Koordinate des Hindernisses auf Display
      n = (scaled_distance * Ymax * sin(theta));                      //Y-Koordinate des Hindernisses auf Display
      ucg.setColor(255, 0, 0);                                        //rot
      ucg.drawPixel(m, n + pos);                                      //Zeichnet Pixel auf Display
    } else {
      k = map(x, 0, 180, 88, 2);  //Anpassen Grad des Servos an Displaygröße
      ucg.setColor(0, 207, 0);                                                                                      //grün
      ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * cos(radians(k * 2))), pos + (val * sin(radians(k * 2))));  //Zeichnet grüne Linie falls kein Hindernis
    }

    previous_k = map(x - 10, 0, 180, 88, 2);  //löscht grüne Linie mit Verzögerung, Anpassung von 180° an Display
    ucg.setColor(0, 0, 0);
    ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * cos(radians(previous_k * 2))), pos + (val * sin(radians(previous_k * 2))));

    ucg.setColor(255, 0, 0);  //Gradanzeige links unten
    ucg.setPrintPos(160, 0);
    ucg.setPrintDir(2);
    ucg.print("Deg :");
    ucg.setPrintPos(120, 0);
    ucg.print(x);
    ucg.setColor(0, 0, 255);  //Zahlenanzeige Kreisraster
    ucg.setPrintPos(90, 38);
    ucg.print(ring1);
    ucg.setPrintPos(90, 70);
    ucg.print(ring2);
    ucg.setPrintPos(90, 110);
    ucg.print(ring3);
  }

  ucg.clearScreen();
  fix();

  for (x = 180; x >= 0; x--) {
    delay(5);
    myServo.write(x);                //Rechtslauf durch Hochzählen von x in der Schleife
    distance = calculateDistance();  //Entfernung zu Hindernis durch Funktion calculateDistance()
    ucg.setPrintPos(10, 0);
    ucg.print(distance);  //Ausgabe Entfernung

    k = map(x, 0, 180, 2, 88);  //Anpassen des Grad-Bereichs des Servos an Display

    if (distance < 65) {                                              //Bis max. 65cm Entfernung
      scaled_distance = distance / 65.0;                              //Verhältnis Gesamtentfernung zu Displaygröße
      theta = x * (PI / 180);                                         //Umrechnen Grad in Bogenmaß
      m = (Xmax / 2) - (scaled_distance * (Xmax / 2) * -cos(theta));  //X-Koordinate
      n = (scaled_distance * Ymax * sin(theta));                      //Y-Koordinate
      ucg.setColor(255, 0, 0);                                        //rot
      ucg.drawPixel(m, n + pos);                                      //Zeichnet Hindernis als Pixel
    } else {
      ucg.setColor(0, 207, 0);
      ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * -cos(radians(k * 2))), pos + (val * sin(radians(k * 2))));  //zeichnet grüne Linie, wenn kein Hindernis erkannt
    }

    previous_k = map(x + 10, 0, 180, 2, 88);
    ucg.setColor(0, 0, 0);
    ucg.drawLine(Xmax / 2, pos + 3, Xmax / 2 + (-val * -cos(radians(previous_k * 2))), pos + (val * sin(radians(previous_k * 2))));  //löscht grüne Linie mit Verzögerung

    ucg.setColor(255, 0, 0);  //Grad-Anzeige unten links
    ucg.setPrintPos(160, 0);
    ucg.setPrintDir(2);
    ucg.print("Deg :");

    sprintf(buffer, "%03d", x);  //korrekte Anzeige, sonst 990... anstatt 99...

    ucg.setPrintPos(120, 0);
    ucg.setPrintDir(2);
    ucg.print(buffer);

    ucg.setColor(0, 0, 255);
    ucg.setPrintPos(90, 38);
    ucg.setPrintDir(2);
    ucg.print(ring1);  //Zahlenanzeige Kreisraster
    ucg.setPrintPos(90, 70);
    ucg.print(ring2);
    ucg.setPrintPos(90, 110);
    ucg.print(ring3);
  }
  ucg.clearScreen();
}

int calculateDistance() {       //Implementierung Funktion zur Berechnung der Entfernung mithilfe des Sensors
  digitalWrite(trigPin, HIGH);  //Sender anschalten
  delayMicroseconds(10);        //Sendezeit 10 Mikrosekunden
  digitalWrite(trigPin, LOW);   //Sender ausschalten

  duration = pulseIn(echoPin, HIGH, 10000);  //Reisezeit ist der empfangene Puls am Echopin (wenn dieser HIGH ist); der Sensor wartet 10 ms
  if (duration == 0) {
    distance = 999;  //wenn der Sensor nach 10 ms nichts empfangen hat setzt er die Entfernung auf 999
  } else {
    distance = duration * 0.034 / 2;
  }                     //Berechnung der Entfernung durch die Schallgeschwindigkeit (340 m/s) durch Hin- und Rücklauf /2 , da Einzelstrecke benötigt
  if (distance > 65) {  //wenn Entfernung größer 65cm, dann Ausgabe 999
    distance = 999;
  }
  return distance;
}

void fix() {  //Hintergrunddesign mit Halbkreisen
  ucg.setColor(255, 0, 0);
  ucg.drawDisc(Xmax / 2, pos, 5, UCG_DRAW_LOWER_RIGHT);
  ucg.drawDisc(Xmax / 2, pos, 5, UCG_DRAW_LOWER_LEFT);

  ucg.setColor(225, 255, 50);
  ucg.drawCircle(80, pos, 115, UCG_DRAW_LOWER_RIGHT);
  ucg.drawCircle(80, pos, 115, UCG_DRAW_LOWER_LEFT);

  ucg.drawCircle(80, pos, 78, UCG_DRAW_LOWER_RIGHT);
  ucg.drawCircle(80, pos, 78, UCG_DRAW_LOWER_LEFT);

  ucg.drawCircle(80, pos, 40, UCG_DRAW_LOWER_RIGHT);
  ucg.drawCircle(80, pos, 40, UCG_DRAW_LOWER_LEFT);

  ucg.drawLine(0, pos, 160, pos);

  ucg.setColor(0, 0, 0);
  ucg.drawBox(100, 0, 30, 8);
}

Hallo wwerner,

Danke für den Code, da kommt dann folgende Fehlermeldung

"error: expected unqualified-id before '=' token
uint8_t = x; //Variable x für Schleifen"

Hallo Gehatsle,

vielen Dank für deine Antwort.

  • Mit einem simplen Programm lässt sich der Servo ganz "normal" bewegen.

  • Ich habe zum Testen das Delay mal komplett ausgeblendet. Da ändert sich nichts (funktioniert gleich wie zuvor) da es offensichtlich wo anders hängt.

  • Serial.begin(19200) habe ich ebenfalls mal ausgeblendet, hierbei ändert sich ebenfalls nichts.

  • Das Display benötigt die 3.3 und die 5V, siehe Bild.

Vielen Dank aber für die vielen Inputs,
ich benötige erst mal ne Weile um das alles auszuchecken! :slight_smile:

1 Like

Mach mal das = weg

uint8_t  x = 0; 

Damit solte tun.

Wenn auf LED darf nur 3,3V ist es ein 3.3V Display.
Auch bei AZ gekauft? Dan darfst in kurzer zeit neuen bestellen, es ist nicht 5V tolerant.

Gerne!
Aber vieleicht habe ich den Ausdruck "ruckeln" missverstanden. Wenn der Servo zB in 20 Grad Schritten bewegt würde (statt 1 Grad): Bewegt er sich dann innerhalb dieser 20 Grad normal und fährt regelmässig? Und hält dazwischen einfach immer an? Dann wäre wohl wirklich einfach etwas am Code langsam oder falsch.

@fony
... so stehts auf der Beschreibung..

Ja, geht, aber läuft gleich langsam wie zuvor.

Also der Servo läuft "normal". Wenn ich z.B. in 10° Schritten fahre, wird jeweils um 10° "sauber" gefahren, und dann hält der Servo an. Nachdem dann die "Berechnungen" durchlaufen sind (ca. 500ms) fährt der Servo wieder um 10° weiter....

Habe soeben mal die Komponenten mit einem Labornetzteil versorgt. Damit läuft es minimal schneller, aber nur weil sich der Servo nun nen Ticken schneller bewegt. Die "Wartezeiten" sind nach wie vor da...

Stromaufnahme lt. Labornetzgerät für alles zusammen (Arduino, Sensor, Servo, TFT-Display) 90mA.

An der Stromversorgung liegt es wohl eher nicht..

  • Mir ist noch etwas eingefallen. Momentan fährt der Servo immer mit "Vollgas" auf die nächste Position und "wartet" dann. Ich würde gerne die Geschwindigkeit mit der sich der Servo von Punkt zu Punkt bewegt reduzieren, um so das Ruckeln etwas zu dämpfen.

Mir ist klar dass dies das eigentliche Problem nicht löst. Sollte es aber lösbar sein, dann wäre der ganze Ablauf vermutlich zu schnell, und ich müsste eh wieder bremsen.

Dann weisst du doch schon, wo die Zeit bleibt. Sind es die Berechungen oder das Display schreiben? Du musst jetzt beginnen ein Profiling zu machen. Stichworte: millis und serial.Print

Das kann im Problemfall 10 ms dauern.
Woher die 500 ms je Schritt kommen, ist aber noch unklar. Am Nano an sich liegts aber nicht.
Mehr Serielle Ausgaben als die Baudrate hergibt sollte man vermeiden.

  • Nur Stepper in 180 1° Schritten
  • Mit US-Messung ohne Display
  • Mit Display

Hallo nochmals,

vielen Dank für die vielen Tipps! Ich benötige da noch etwas Zeit, da ich momentan wohl noch zu blöd bin das schnell mal so hinzubasteln... :slight_smile: