-
-
Notifications
You must be signed in to change notification settings - Fork 52
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Suggestion: Option to trigger repeating timer immediately #57
Comments
Instead of complicating the interface, would it be just as easy to call the task directly the first time (as soon as the processor is initialized enough to handle it)? For example:
|
It's a workaround but is somewhat clumsy, and in some cases other work might also need to be duplicated in setup() or the timer action might need to be triggered the first time in loop(), with an associated boolean, to ensure correct ordering of operations. Simply having support for both leading and falling edge triggers would be more expressive, simplifying application code, reducing possible bugs (such as accidental deletion of the initial trigger), and keeping the timer callback triggers exclusively the responsibility of the timer infrastructure. There is also another take on this which is to recognise that having a timer expire either immediately or after a full cycle are just special cases of the more general concept of allowing the starting timer value to be specified. If the timer start point can be specified, a timer could expire first after say 5 seconds and thereafter every 60 seconds, which could also be nice in some cases. |
I would like to remind you that most languages have the do-while structure. |
Your original suggestion was for an immediate (on first tick) and repeating triggers. What about scheduling timer.in(0, myTask); // run myTask once on next tick
timer.every(myInterval, myTask); // run myTask periodically |
Thanks, and yes that can be done as a compromise. It would be more expressive and neater though to have the right tool for the job, Kind of like a manufacturer who makes push buttons that only activate on release, and to someone who wants one that activates on press, saying to just press it really quickly; it might work, but would simply be better to have one that behaved as needed. |
I like @skrobinson's suggestion. Here is a helper function which has the requested feature:
While it works, I do not like the function name I chose. It is not nearly as intuitive/elegant as the built-in method names Since choosing a good name is important for a good library, I wouldn't want to make clients use this hack as it is. (It's OK for personal use, as there are fewer places to change once I find a better name.) If you would like to experiment with a "show and tell" example and perhaps find a better function name, here's my sketch:
|
Good suggestion. Thinking about it more this morning, the more general form would be a fire_and_repeat operation, with both the interval before the first firing specifiable (i.e. a delay), the repeat interval and a count; instant firing would then be a special case of the more general form. Given that, you have possibilities such as: Fire immediately: Fire once after/in 10 units: Fire every 10 units until cancelled: Fire after 1 unit and then every 10 units up to 5 times: etc. Convenience methods such as firing once after a delay, repeated firing every number of units etc. are specialisations. |
These are synonyms for
Would this call the function at On a meta-related note... Would a |
I'd implement every 10 seconds with the first after 1 second as 1,10,20,, as that is the more likely use case, but 1, 11, 21 might be useful too so having that as an option could have merit. The thing to recognise is that there's fundamentally only one type of timer, and what we might think of as different types of timers can all be expressed in terms of the generic timer. |
@skrobinson I just added my example to @nickion I agree I would (personally) prefer to just use and maintain the Sometimes interfaces must get more complicated than basic primitives. I'm not sure that is the case here (maybe this use case is too specific for general interest). I would rather avoid growing the interface if possible, as doing so creates more testing and support issues. Regardless, sometimes a developer needs something more complicated than what a library provides. It keeps development interesting. Helper functions (like this) can help you make a simple library more powerful, even when they are not built in. If it turns out that many/most clients are using a helper, then maybe it is important enough it should be added to the base library. In the meantime others can add the example helper to their code. |
It would be useful to have a signature that specified whether a timer should start already expired so that it fires on the first timer tick via loop() rather than only after the specified interval. In this way an initial action can be performed without the need to explicitly trigger the callbacks.
The text was updated successfully, but these errors were encountered: