3

I have this really simple sketch where I blink a led light. If I send another value threw the serial monitor then first there is always a brief second where the light doesn't blink anymore. Why is that, and how can I get rid of that?

int the_delay = 300;

void setup() {
  Serial.begin(115200);
  pinMode(12, OUTPUT);
}

void loop() {
  digitalWrite(12, HIGH);   
  delay(the_delay);            
  digitalWrite(12, LOW);    
  delay(the_delay);            
}


void serialEvent() {

  if (Serial.available()) {   
    the_delay = Serial.parseInt();
    Serial.println(the_delay);
  }
}

In case it helps, eventually I would like to send values with 60fps.

3

It's because you're using Serial.parseInt(). It uses a timeout to find the end of the data on the serial port, and while it's waiting for that timeout it can do nothing else.

You would be better off manually reading the serial data a character at a time to build up an input string (C-string, not Arduino String) with a proper line terminator (line-feed, \n) and then convert that into an integer with atoi().

| improve this answer | |
2

Try typing a non-digit character after the delay value; even Enter should work if your terminal is configured to send any kind of end-of-line. Serial.parseInt() waits the full timeout (default: 1000 ms) after each digit, for the next one. A non-digit will end the input value immediately.

| improve this answer | |
1

See How to process incoming serial data without blocking. An interim solution is to get the Serial Monitor to send a newline automatically when you press Send.

Here is example code that processes input without blocking:

// Example of processing incoming serial data without blocking.

// how much serial data we expect before a newline
const unsigned int MAX_INPUT = 50;

void setup ()
  {
  Serial.begin (115200);
  } // end of setup

// here to process incoming serial data after a terminator received
void process_data (const char * data)
  {
  // for now just display it
  // (but you could compare it to some value, convert to an integer, etc.)
  Serial.println (data);
  }  // end of process_data

void processIncomingByte (const byte inByte)
  {
  static char input_line [MAX_INPUT];
  static unsigned int input_pos = 0;

  switch (inByte)
    {

    case '\n':   // end of text
      input_line [input_pos] = 0;  // terminating null byte

      // terminator reached! process input_line here ...
      process_data (input_line);

      // reset buffer for next time
      input_pos = 0;  
      break;

    case '\r':   // discard carriage return
      break;

    default:
      // keep adding if not full ... allow for terminating null byte
      if (input_pos < (MAX_INPUT - 1))
        input_line [input_pos++] = inByte;
      break;

    }  // end of switch

  } // end of processIncomingByte  

void loop()
  {
  // if serial data available, process it
  while (Serial.available () > 0)
    processIncomingByte (Serial.read ());

  // do other stuff here like testing digital input (button presses) ...

  }  // end of loop
| improve this answer | |

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.