| ||
|
Shopping Cart
|
| Home | MP3 Player | 8051 Tools | All Projects | PJRC Store | Site Map |
|
You are here:
Teensy
| Search PJRC |
|
|
Delay and Timing FunctionsSeveral functions are available to help you control the timing or speed your program performs its actions.Simple Delay: delay() & delayMicroseconds()The simplest timing function is delay(). It waits a number of milliseconds.
digitalWrite(11, HIGH); // pin 11 high delay(1000); // for 1 second digitalWrite(11, LOW); For very precise delays, you can use delayMicroseconds(), up to 16383 us. With delay(), you can wait up to 429497295 ms, or about 49.7 days. While these functions are easy, your program can not do other work during the delay. Using elapsedMillis & elapsedMicrosThese special variable types automatically increase as time elapses. It's easy to check if a certain time has elapsed, while your program performs other work or checks for user input.Responsiveness To User InputWhen using delay(), your code can not respond to user input while the delay is happening. In this example, a pushbutton has quick response, but a task is performed every 2.5 seconds.#include <Bounce.h> Bounce myButton = Bounce(2, 10); // pushbutton on pin 2 elapsedMillis sincePrint; void setup() { Serial.begin(9600); pinMode(2, INPUT_PULLUP); } void loop() { myButton.update(); if (myButton.fallingEdge()) { Serial.println("Button Press"); } if (myButton.risingEdge()) { Serial.println("Button Release"); } if (sincePrint > 2500) { // "sincePrint" auto-increases sincePrint = 0; Serial.println("Print every 2.5 seconds"); } } Repeating Multiple Tasks At Regular IntervalsYou can repeat a task at regular intervals by checking if enough time as elapsed since the task was performed last. In this example, 3 lines are printed, each at its own interval. Computing the correct delay() numbers for this sequence would be difficult!// create elapsedMillis outside loop(), to // retain its value each time loop() runs. elapsedMillis sinceTest1; elapsedMillis sinceTest2; elapsedMillis sinceTest3; void loop() { if (sinceTest1 >= 1000) { sinceTest1 = sinceTest1 - 1000; Serial.println("Test1 (1 sec)"); } if (sinceTest2 >= 2700) { sinceTest2 = sinceTest2 - 2700; Serial.println(" Test2 (2.7 sec)"); } if (sinceTest3 >= 1300) { sinceTest3 = sinceTest3 - 1300; Serial.println(" Test3 (1.3 sec)"); } }In this example, each interval is substracted from the elapsed time, which automatically adjusts for any latency. Imagine if if the Serial.println() for Test1 takes more than 4 ms, and during that time sinceTest2 increases to 2704. Because 2700 is substracted, it will start over at 4, so the next Test2 may print 4 ms early, aligned to the original schedule. If you do not care about maintaining the original schedule, or the time between events must not be less than intended, you would set the variable back to zero intead of substracting. Timeout Waiting For InputWhen waiting for input, especially data from a computer, usually it's good to give up after a "timeout". Using elapsedMillis makes this easy.
void loop() { // each time loop() runs, elapsedMillis waiting; // "waiting" starts at zero while (waiting < 1000) { if (Serial.available()) { char c = Serial.read(); Serial.print("got char = "); // do something with c Serial.println(c); waiting = 0; // reset waiting back to zero } } Serial.println("waited 1 second, no data arrived"); } When elapsedMillis is created as a local variable (inside the function), it automatically starts at zero each time the function executes. Avoid Timing PitfallsBoth elapsedMillis and elapsedMicros can increase by more than 1 count. Therefore, equality compare "==" is never a good approach. Such a program may usually work, but could fail on rare and random circumstances. Checking should always be done with ">" or "<" or ">=" or "<=".TODO: publish a library for elapsedMillis and elapsedMicros on Arduino boards. System Time: millis() & micros()You can get the total time since your program started, in milliseconds using millis(), or in microseconds using micros().These return a number between 0 to 429497295. When they reach the maximum, they roll back over to 0. For millis, that's approximately 49.7 days. For micros, that's 1 hour, 11 minutes, 34.967295 seconds. When computing time differences, care should be taken to handle the roll over case. An example can be found in File > Examples > 2.Digital > BlinkWithoutDelay. Internally, elapsedMillis and elapsedMicros use millis and micros. They handle roll over automatically, and are much easier to use. Calendar Date / TimeTODO: mention libraries.... |