Pause a sketch to wait until any key is pressed

Hi

I wish for a sketch to loop once and halt, wait for any key to be pressed then loop again using the very simple while(!Serial.available()) { }.

I have tried to get this to work with the simple example below, but my efforts are only half successful.

What happens is that the code either waits for a keypress then loops and loops ad-infinitum, or just runs once then never again - and I just cannot get my head around my very basic error :o

void setup()
{
   Serial.begin(9600);
}


void loop()
{

  while(!Serial.available()) { }  // if here: code will not run until keypress, then will not stop!

  int MyArray[10];

  FillArray(MyArray, 10);

  for(int i = 0; i< 10; i++){
     Serial.println(MyArray[i]);
      

       
   }


   //while(!Serial.available()) { } // If here: code runs once then just will not go again 
    
}


void FillArray(int TheArray[], int n)
{
   for(int i = 0; i < n; i++){
       TheArray[i] = 10 * i;
   }
}

It will never stop because you never call Serial.read() to remove the character and it stays available in the buffer.

AAh - knew I was daft!

Thanks. Got it.

Here’s a working solution :slight_smile:

void setup()
{
   Serial.begin(9600);
}


void loop(){
  
  waitForSerial();  // Here we go
  
  int MyArray[10];
  FillArray(MyArray, 10);

  for(int i = 0; i< 10; i++){
    Serial.println(MyArray[i]);
  }
}


void FillArray(int TheArray[], int n)
{
   for(int i = 0; i < n; i++){
       TheArray[i] = 10 * i;
   }
}

/*
 * Here's a little function to wait for a keypress and 
 * then kill the data received.
 */
void waitForSerial(){
  while (!Serial.available()) {
  }
  Serial.println(Serial.read());
}

Here's a working solution

What if there is already a byte or bytes in the input buffer when you call the function ?

UKHeliBob:
What if there is already a byte or bytes in the input buffer when you call the function ?

Hmmm…

I should probably run the line <Serial.println(Serial.read());> before the call as well as after it?

You shouldn't be thinking in terms of pausing or delaying in your code, just about checking
for events that require a response. The default state of a microcontroller is running around
like crazy in loop() checking for any change in inputs or a new time-out. Constant vigilance.

If you start using delays or blocking while loops you'll create code that cannot be combined
with other code to make more complex sketches.

Typically anything more than very simple behaviour will require the coding up of a state-machine.

I should probably run the line <Serial.println(Serial.read());> before the call as well as after it?

And if there were several bytes in the input buffer, then what ?

MarkT:
You shouldn't be thinking in terms of pausing or delaying in your code

I can see, and fully acknowledge, that it is not ideal programming technique as it locks up the MCU doing absolutely nothing.
For me, however, in this instance where I'm in the course of developing a quite (for me :confused: ) complicated sketch, I need to halt the output to the serial monitor so that I can study the changing outputs after certain steps, something that was proving nigh on impossible without killing the loop altogether.
It was a simple solution to a simple problem that I sought.

UKHeliBob:
And if there were several bytes in the input buffer, then what ?

Good point, which didn't raise any issues for me as I was fully in control at the keyboard :stuck_out_tongue:
How about another while before the existing one?

  /*
 * Here's a little function to empty the buffer, 
 * wait for a keypress and then kill the data received.
 */
void waitForSerial(){
  while(Serial.available()){Serial.read();}
  while (!Serial.available()) { }
  Serial.println(Serial.read());
}