Hey guys -
Steven, Sergey and Michal - just awesome. I learned a lot, so a big THANK YOU to you all. For example, I didn't know there were ready-to-use schedulers for Lua. Another point: I knew that coroutines were implemented using setjmp/longjmp. Since my university times, it's been somehow ingrained in my consciousness that setjmp/longjmp were a kind of magic only the gurus could use and their usage shoud be at least minimized, if not avoided completely. And for this reason, I would use yield/resume sparingly, and never dreamt of invoking it from a timer callback. Now I'm only surprised how straightfoward the coroutine-based implemetation of sleep() is.
I agree with Michal (see his love2d link) the best way (at least much better than my rabbit example) to talk about coroutines is using turtle graphics. Now, we have the user, who's written some Lua code. She is thinking in terms of going forward, turning, slowing down or waiting. His code could be as simple as following:
-- draw a square
for i = 1, 4 do
On the other side of the Lua/C wall we have a C/C++ programmer, who's thinking in low-level terms - frames, timing, callbacks, etc. As it turns out, my biggest problem was to understand how this gap between two programming paradigms is bridged - I knew only that coroutines were the recommended way. With my current understanding (I didn't have the time to study all the projects you guys linked to yet) I believe the magic is hidden in the way the 'forward' and 'turnRight' procedures are implemented. Using Sergey's sleep() example, I would implement forward as
for i = 1, steps do
moveTurtle(1) -- move the turtle 1 pixel in the given direction, let's ignore the details
coroutine.yield(.....) -- leaving out the parameters to keep it simple
and I'd bind 'coroutine.resume()' either to a timer which fires every tick, or connect it somehow to the engine's 'update()' function.
Did I get it right? Again, my biggest problem was to imagine how to bridge the user's code (they just don't care about coroutines and other low-level stuff) with the drawing engine which updates the screen in a loop independently of user's actions/scripts.
Again, thanks for the great examples.