In Lesson 28 and Lesson 29 we showed how to use simple software interrupts to do quick and easy tasks like turning an LED on or off. We emphasized the importance of just doing simple tasks, and to get in and out of the interrupt function as quickly as possible. It is sometimes necessary to do more sophisticated functions. For example, the Adafruit Ultimate GPS immediately begins sending serial data on powerup. Making matters worse, it sends big bursts of data, and then waits, and then later sends bursts of data again. The data that is sent needs to not just be read, but you must parse the data to make sense of it. Hence, you end up needing to do sophisticated functions to parse the data, but at the same time you have to make sure you do not miss any of the new incoming data. This requires a more thoughtful and sophisticated interrupt strategy.
First off, we will need a better software interrupt library. You should erase the TimerOne library you installed in Lesson 28, and replace it with the one here:
https://github.com/PaulStoffregen/TimerOne
The video shows how to get the library if you are not familiar with github.
The video takes you through the code below. While this is done for the Adafruit GPS, this method should work for other sensors that spew serial data.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 | void loop(){ digitalWrite(RedLED,HIGH); delay(1000); digitalWrite(RedLED,LOW); delay(1000); if (flag==1){ Timer1.stop(); NMEA.trim(); Serial.println(NMEA); NMEA=""; flag=0; Timer1.restart(); } } void readGPS(){ if (GPSSerial.available()>0){ c=GPSSerial.read(); NMEA.concat(c); } if(c=='\r'){ flag=1; } } |
While we do this demo for the Adafruit GPS, these techniques will work for other sensors that send data over the Serial Pins.