Bin zum ersten mal hier. Habe bereits von euch vieles gelesen und gelernt und darf an dieser Stelle ein grosses Lob schicken, da ich finde dass hier ein sehr guter Umgang gepflegt wird.
Nun brauche ich spezielle Hilfe. Im Forum hab ich nichts gefunden. Ich bin nicht ganz neu in der Arduinowelt. Praxisnahe Hobbyanwendung geht mal gerade so, Systemverständnis also was im Prozessor abläuft eher rudimentär. Bin halt Maschinenbauer und kein Elektroniker...
Aber nun zu meinem Code Problem.
Ich stelle gerade einen Drehzahlmesser (Messscheibe - schwarz/weiß) zusammen mit Phototransistor, Interruptroutine, kleine und hohe Drehzahlen, Anzeige auf OLED. Das funktioniert alles. Nun möchte ich noch zwei Taster zufügen, mit denen ich die Anzahl der Messfelder im Code verändern kann. Die Messscheibe wird vom Phototransistor abgetastet. Hierzu habe ich eine Tasterabfrage mit entprellen und short/long press. Funktioniert stand alone. Füge ich dieses aber als Funktion dem Programm bei (egal ob im Setup (weil ja nur einmal abgefragt wird) oder im loop bleibt der Setup hängen. Programm kompiliert fehlerfrei und lädt hoch. Ich verwende Arduino IDE 1.89 und UNO Rev 3.
Hier der Code.
Ich hoffe
- alles in tags richtig dargestellt,
- lesbar und verständlich. (Habe den Code gekürzt zum besseren lesen
- falls alles gebraucht wird kann ich das natürlich posten
- hoffe ich konnte das Problem ausführlich genug schildern
- hoffe auf Hilfe
- wenn nix geht, läuft der Code auch ohne Taster ... ich möchte aber gern was lernen...
```
/*
V03.1 Taster zur Auswahl Messteilung zugefuegt. -- bleibt im Setup haengen. Funktion stand alone ok.
*/
//***** OLED 0.96" Display *****
#include <Adafruit_GFX.h> // Include core graphics library for the display.
#include <Adafruit_SSD1306.h> // Include Adafruit_SSD1306 library to drive the display.
Adafruit_SSD1306 display(128, 64); // Create display.
#include <string.h> // Inkludiere die string.h-Bibliothek
#include <Fonts/FreeMonoBold18pt7b.h> // Add a custom font.
//***** INTERRUPT *****
int motordrzPin1 = 7;
int motordrzPin = 2; // INT0; interruptPin 2 - obstacle avoidance sensor interface
volatile unsigned long zeitGemessen = 0;
volatile unsigned long letzteMessung = 0;
volatile float drehzahlMotor = 0;
volatile float drehzahldurchschnitt = 0;
unsigned long anzahl = 0;
unsigned long anzahlAlt = 0;
unsigned long drehzahlMotorSumme = 0;
unsigned long drehzahlMotorSummeAlt = 0;
//***** KLEINE DREHZAHLEN *****
unsigned long messZeit = millis();
unsigned long zeitProUmdrehung = 0;
bool motorPin = true;
bool status_motorPin = true;
//bool status_Impuls = true;
float abwDrz = 2;
float faktor_Durchschnitt = 1.0;
float faktor_drz = 0.0;
char stabilitaet[20];
unsigned int zaehler = 0;
//***** TASTER *****
const int button1Pin = 5; // Pin für Taster 1
const int button2Pin = 6; // Pin für Taster 2
int button1State = HIGH; // Aktueller Zustand von Taster 1
int button2State = HIGH; // Aktueller Zustand von Taster 2
int button1PreviousState = HIGH; // Vorheriger Zustand von Taster 1
int button2PreviousState = HIGH; // Vorheriger Zustand von Taster 2
unsigned long button1PressStartTime = 0; // Startzeit des Taster-Drucks von Taster 1
unsigned long button2PressStartTime = 0; // Startzeit des Taster-Drucks von Taster 2
const unsigned long debounceDelay = 50; // Entprellungsverzögerung (in Millisekunden)
const unsigned long longPressDelay = 1000; // Zeit für langen Tasterdruck (in Millisekunden)
bool button2LongPressDetected = false; // Flag für erkannten Long-Press von Taster 2
int counter = 1; // Variable zum Hoch- und Herunterzählen
int teilung = 1; //Messscheibe , Angabe fuer Impulse pro Umdrehung
int freigabe = true;
void setup() {
Serial.begin(115200);
pinMode(button1Pin, INPUT_PULLUP); // Taster 1 als Eingang mit Pull-Up-Widerstand
pinMode(button2Pin, INPUT_PULLUP); // Taster 2 als Eingang mit Pull-Up-Widerstand
pinMode(motordrzPin, INPUT); // Define obstacle avoidance sensor as
// OLED 0.96" Display:
display.begin(SSD1306_SWITCHCAPVCC, 0x3C); // Initialize display with the I2C address of 0x3C.
delay(1000); //OLED Vorbereitung
display.clearDisplay(); // Clear the buffer.
display.setTextColor(WHITE); // Set color of the text to white.
display.setRotation(0); // Set orientation. Goes from 0, 1, 2 or 3.
display.setTextWrap(false); // By default, long lines of text are set to automatically “wrap” back to the leftmost column.
display.dim(0); // Set brightness (0 is maximum and 1 is a little dim).
display.clearDisplay(); // Clear the display so we can refresh.
display.setTextSize(2); // OLED Darstellung Version
display.setCursor(10, 0);
display.println("Drehzahl-");
display.println(" messer");
display.setTextSize(1);
display.setCursor(0, 38);
display.println(" Vers. V0.4");
display.setCursor(0, 52);
display.println(" v 26.06.2023");
display.display();
delay (5000);
display.clearDisplay();
display.setTextSize(1); // OLED Darstellung Auswahl Messteilung soll spaeter in den Tasteraufruf
display.setCursor(18, 5);
display.println("Messteilung");
display.setCursor(24, 20);
display.println ("FIX 1-Teilung");
display.setCursor(10, 35);
display.println ("Start Messung");
display.setCursor(10, 50);
display.println ("press Taster");
display.display();
delay (3000);
Serial.println("Initalisierung"); //das ist das einzige was noch im Serial zu sehen ist
/* Tasteraufruf nur bsp, beinhaltet in einer funktionierenden Version 2 Taster, short/long press
// Problemcode im Setup wenn auskommentiert bleibt Setup haengen
while (freigabe == true) {
int button2Reading = digitalRead(button2Pin);
if (button2Reading == LOW) {
freigabe = false;
Serial.print("Start Messung "); Serial.println (freigabe);
}
}
*/
attachInterrupt(digitalPinToInterrupt(motordrzPin), drehzahl, RISING);
}
void loop() {
/* alternativer code im loop, wenn auskommentiert bleibt Setup haengen
if (freigabe == true) {
taster();
}
*/
rpm_Anzeige (); //wird normal ausgefuehrt obwohl auch Funktion
while (drehzahlMotor <= 200) { //wird normal ausgefuehrt, obwohl auch While Schleife
motorPin = digitalRead (motordrzPin); //Umdrehungsberechnung, hier soll ohne Interrupt nur der Pin ausgelesen werden
if (motorPin != status_motorPin) { //aendert Status nach LOW / HIGH
status_motorPin = motorPin;
if (motorPin == HIGH) { //ausgefuehrt,wenn PIN HIGH, LOW passiert (egal wie lange) nichts.
zeitProUmdrehung = millis() - messZeit; //alte Startzeit verwenden
drehzahlMotor = 60000.0 / (zeitProUmdrehung * teilung); //Berechnung der Umdrehungszeit
messZeit = millis(); //neue Startzeit festlegen
abwDrz = drehzahlMotor - drehzahldurchschnitt;
// .......code gekuerzt hier steht nur etwas zur Messwertabweichung
drehzahldurchschnitt = faktor_Durchschnitt * drehzahldurchschnitt + faktor_drz * drehzahlMotor;
//... code gekuerzt, hier sind nur OLED befehle
}
}
}
if (drehzahlMotor >= 200) //Berechnung Motordrehzahl groesser 200 Umin und Anzeige
{
drehzahlMotor = (drehzahlMotorSumme - drehzahlMotorSummeAlt) / (anzahl - anzahlAlt);
//... code gekuerzt nur OLED und Serial befehle
anzahlAlt = anzahl;
drehzahlMotorSummeAlt = drehzahlMotorSumme;
}
}
void drehzahl() //Interruprroutine
{
anzahl++;
zeitGemessen = micros() - letzteMessung;
letzteMessung = micros();
drehzahlMotor = 60000000 / zeitGemessen;
drehzahlMotorSumme += drehzahlMotor;
drehzahldurchschnitt = 0.9 * drehzahldurchschnitt + 0.1 * drehzahlMotor;
}
void rpm_Anzeige () { // OLED Anzeige statisch RPM oberste Zeile, funktioniert
display.clearDisplay();
display.setTextSize(2);
display.setCursor(0, 0); // (x,y).
display.println("RPM:"); // Text or value to print.
display.display();
}
/*
Aufruf dieser Funktion erfolgt nicht wg Setup Problem
void taster() {
while (freigabe == true) {
int button2Reading = digitalRead(button2Pin);
if (button2Reading == LOW) {
freigabe = false;
Serial.print("Start Messung "); Serial.println (freigabe);
}
}
}
*/
```