Nasal Loops: Difference between revisions

Jump to navigation Jump to search
m
Update {{func link}} form
(Template usage)
m (Update {{func link}} form)
Line 5: Line 5:
A polling loop is akin to somebody permanently running to a room to check if the lights are on - a listener is like somebody being INSIDE the room SLEEPING and only WAKING up once the lights are turned on.
A polling loop is akin to somebody permanently running to a room to check if the lights are on - a listener is like somebody being INSIDE the room SLEEPING and only WAKING up once the lights are turned on.


The {{func link|setlistener}} API is intended to catch rare events. Avoid complex loops if you don't have to.
The {{func link|setlistener()}} API is intended to catch rare events. Avoid complex loops if you don't have to.


In general, "loops" are not bad or expensive, it really depends on what you're doing inside the loop.
In general, "loops" are not bad or expensive, it really depends on what you're doing inside the loop.
Line 13: Line 13:
timers or listeners are only really preferable over loops when it comes to checking for some condition, because polling is called "busy-waiting", i.e. more expensive, see my previous analogy.
timers or listeners are only really preferable over loops when it comes to checking for some condition, because polling is called "busy-waiting", i.e. more expensive, see my previous analogy.
A listener or timer "waiting" is not resource-hungry, it's not even busy - it's not doing anything until it is "fired".
A listener or timer "waiting" is not resource-hungry, it's not even busy - it's not doing anything until it is "fired".
Regarding {{func link|setprop}}/{{func link|getprop}} - they're not as bad as we used to think - in fact, Thorsten has shown that they're preferable over most [[Nasal library/props|props.nas APIs}}, this may however change once the whole thing is replaced with cppbind bindings.
Regarding {{func link|setprop()}}/{{func link|getprop()}} - they're not as bad as we used to think - in fact, Thorsten has shown that they're preferable over most [[Nasal library/props|props.nas APIs}}, this may however change once the whole thing is replaced with cppbind bindings.


Well loops aren't bad necessarily: they can be used in a less-than-optimal manner, but there are often times where they make a lot of sense. Some pros and cons of both:
Well loops aren't bad necessarily: they can be used in a less-than-optimal manner, but there are often times where they make a lot of sense. Some pros and cons of both:
Line 35: Line 35:
{{Note|Need to discuss split-frame-loops here!}}
{{Note|Need to discuss split-frame-loops here!}}


To optimize things in Nasal space, you need to understand where things really ARE slow - for starters, you can use "debug.benchmark()" for this - which is wrapper for two {{func link|systime}} calls to capture the overhead of the callback.
To optimize things in Nasal space, you need to understand where things really ARE slow - for starters, you can use "debug.benchmark()" for this - which is wrapper for two {{func link|systime()}} calls to capture the overhead of the callback.


Philosopher has some more sophisticated stuff doing this sort of thing, but it's more difficult to set up and not yet ready for "prime-time" - overall, discussions like these make it obvious that we could greatly benefit from having support for runtime benchmarking/profiling and debugging of Nasal code running within the FG main loop.
Philosopher has some more sophisticated stuff doing this sort of thing, but it's more difficult to set up and not yet ready for "prime-time" - overall, discussions like these make it obvious that we could greatly benefit from having support for runtime benchmarking/profiling and debugging of Nasal code running within the FG main loop.
Line 156: Line 156:
</syntaxhighlight>
</syntaxhighlight>


Note that the {{func link|settimer}} function expects a ''function object'' (<tt>loop</tt>), not a function call (<tt>loop()</tt>) (though it is possible to make a function call return a function object--an advanced functional programming technique that you won't need to worry about if you're just getting started with Nasal).  
Note that the {{func link|settimer()}} function expects a ''function object'' (<tt>loop</tt>), not a function call (<tt>loop()</tt>) (though it is possible to make a function call return a function object--an advanced functional programming technique that you won't need to worry about if you're just getting started with Nasal).  


The fewer code FlightGear has to execute, the better, so it is desirable to run loops only when they are needed. But how does one stop a loop? A once triggered timer function can't be revoked. But one can let the loop function check an outside variable and refuse calling itself, which makes the loop chain die off:
The fewer code FlightGear has to execute, the better, so it is desirable to run loops only when they are needed. But how does one stop a loop? A once triggered timer function can't be revoked. But one can let the loop function check an outside variable and refuse calling itself, which makes the loop chain die off:
Line 195: Line 195:
</syntaxhighlight>
</syntaxhighlight>


Beginning with FlightGear 2.11+ you should consider using the {{func link|maketimer}} API instead.
Beginning with FlightGear 2.11+ you should consider using the {{func link|maketimer()}} API instead.


See also {{func link|settimer}}
See also {{func link|settimer()}}

Navigation menu