J'ai créé ce code sur Arduino où l'objectif est que l'utilisateur saisisse un temps de retard dans le moniteur série, puis la LED doit clignoter avec ce temps de retard. Par exemple, si je tape 1000, la LED doit être allumée pendant 1 seconde puis éteinte pendant 1 seconde, puis répétez.
Mon problème est que lorsque le code a fini de s'exécuter une fois, il attend une nouvelle entrée d'utilisateur, au lieu de continuer à clignoter. Je pense que je dois retirer le Serial.parseInt
de la boucle, mais je ne sais pas comment, car chaque fois que j'ai essayé de le mettre ailleurs, la LED s'allume en permanence.
Voici le code:
int ledPin = 13; void setup() { // put your setup code here, to run once: pinMode(ledPin, OUTPUT); Serial.begin(9600); Serial.print(" Enter delay time: "); while (!Serial.available()); } void loop() { // put your main code here, to run repeatedly int delayTime = Serial.parseInt(); digitalWrite(ledPin, HIGH); delay(delayTime); digitalWrite(ledPin, LOW); delay(delayTime); }
3 Réponses :
Lisez simplement le temps de retard dans votre setup
avant d'entrer dans la boucle
int ledPin = 13; int delayTime = 0; void setup() { // put your setup code here, to run once: pinMode(ledPin, OUTPUT); Serial.begin(9600); Serial.print(" Enter delay time: "); while (!Serial.available()); delayTime = Serial.parseInt(); } void loop() { // put your main code here, to run repeatedly digitalWrite(ledPin, HIGH); delay(delayTime); digitalWrite(ledPin, LOW); delay(delayTime); }
Serial.parseInt
est une fonction de blocage. Cela signifie qu'il attend une entrée série valide jusqu'à ce qu'il expire. Pour cette raison, toute autre action de la boucle
doit également attendre. Cependant, la lecture de l'entrée utilisateur dans setup
ne fonctionne qu'une seule fois, donc elle ne demande plus jamais à l'utilisateur de saisir une nouvelle fois.
Pour éviter cela, vous devrez vérifier le tampon série, puis lire chaque octet individuellement , tout en faisant clignoter la LED dans la boucle principale.
Une autre chose à éviter maintenant, est l'utilisation de la fonction delay
, car elle bloque également toute la boucle principale les lectures en série) pour le temps de paramètre donné. Vous pouvez toujours faire clignoter la LED en utilisant des intervalles d'horodatage.
Pour un bel exemple de lecture série non bloquante, nous pouvons utiliser cet exemple de la documentation Arduino . De plus, pour un autre bel exemple d'esquisse clignotant par LED sans utiliser delay
, nous pouvons utiliser le Exemple BlinkWithoutDelay de la documentation Arduino également.
String inString = ""; unsigned long previousMillis = 0; int delayTime = 0; int ledState = LOW; int ledPin = 13; void nonBlockingSerialReadDelayTime() { while (Serial.available() > 0) { int inChar = Serial.read(); if (isDigit(inChar)) { // convert the incoming byte to a char and add it to the string inString += (char)inChar; } // if you get a newline (user pressed ENTER on the serial console) if (inChar == '\n') { // set our new delay time delayTime = inString.toInt(); // clear the string for new input inString = ""; // ask user again Serial.print(" Enter delay time: "); } } } void blinkLED() { unsigned long currentMillis = millis(); if (currentMillis - previousMillis >= delayTime) { // save the last time you blinked the LED previousMillis = currentMillis; // if the LED is off turn it on and vice-versa if (ledState == LOW) { ledState = HIGH; } else { ledState = LOW; } // set the LED with the ledState of the variable digitalWrite(ledPin, ledState); } } void setup() { pinMode(ledPin, OUTPUT); Serial.begin(9600); while (!Serial.available()); Serial.print(" Enter delay time: "); } void loop() { nonBlockingSerialReadDelayTime(); blinkLED(); }
Bien sûr que Serial.parseInt () bloque, mais vous pouvez le combiner avec Serial.available ()
const int ledPin = 13; int delayTime = 1000; void setup() { pinMode(ledPin, OUTPUT); Serial.begin(9600); Serial.print(" Enter delay time: "); } void loop() { digitalWrite(ledPin, HIGH); delay(delayTime); digitalWrite(ledPin, LOW); delay(delayTime); if (Serial.available()) { int temp = Serial.parseInt(); if (temp > 0) delayTime = temp; Serial.print(" Enter delay time: "); } }
Bien sûr, cette approche ne permet pas de faire un cycle de clignotement très lent immédiatement , mais c'est un problème différent.