Getting Started with Sprite Timers

August 9, 2020 garrison tutorial, ims213, game development 4 minutes, 54 seconds

Sprite Timers

A "sprite timer" is just a way of saying that we're going to create some code that will be dedicated to making one decision for us: Is it time to show a different sprite, or should we continue showing the same one we've been showing? It is easy to get confused by the word "timer" -- it makes it sound as if there is something especially clock-like or time-specific to this function. It does end up working like a super-simple countdown timer, I suppose, but only in a really generic way. Think of it like this: Get rid of the word "timer" and substitute the word "clicker."

This code makes significant use of the new concept (covered 16 September 2020) of "sprite timers" and "movement timers."


function _init()

 --using 'frame' in the same
 --way we've used 'counter'

 frame=1

 -- keep track of the
 -- starting and ending
 -- sprites for our character

 startcel=1
 finalcel=4

 -- TIMER SECTION --

 -- Timers can be used to do ANYTHING.  
 -- We'll use them a LOT.

 -- how often should we update
 -- the current cel?  Here, I
 -- set it at 5.  Which means
 -- update once every 5 frames...

 celtimer=5

 -- If the computer updates our
 -- screen at 30 frames/second,
 -- then celtimer 5 means
 -- an update to our animated character
 -- happens 6x a second (1 out of every
 -- 5 frames)... so what if we celtimer to 15?
 -- This character's animation would be
 -- updated 2x per second (1 out of
 -- every 15 frames).

 movetimer=3

 -- our second timer (celtimer is the
 -- first); we use this one to control
 -- rate at which our sprite changes
 -- its x position. 

 -- Positional variables --
 -- starting position
 startx=-7

 -- ending position
 finalx=128+1

 -- our horizontal speed
 xinc=2

 ypos=64 -- it will stay static

 -- STARTUP Variables
 -- our first position and first sprite...
 xpos=startx
 nowcel=startcel

function _update()

 -- as always, we need to keep track of time
 -- as it ticks by in our code.

 frame=frame+1

 -- we're outsourcing!  instead of junking
 -- up our _update with stuff that we
 -- will eventually forget about, we're
 -- going to put it into a custom function

 roboupdate()

end

function _draw()

 -- Remember how we used to 
 -- do lots of maths and stuff
 -- in _draw()?  All of it
 -- is happening in roboupdate().
 -- Yes, a sprite is still being
 -- drawn with every new frame.
 -- But _draw() no longer has anything
 -- to do with figuring out which sprite
 -- or where.  That's an important
 -- improvement.

 cls(1)

  --draw a horizon line for effect
  line(0,64+5,128,64+5)

  -- now draw current sprite @ current x,y
  spr(nowcel, xpos, ypos)

  -- (Note that all 3 variables are all
  -- global!  Not good.  We'll address
  -- that later -- for now its ok, tho.)

end

function roboupdate()
 -- the heavy-lifting now happens
 -- here!  Everything will be
 -- easier to understand and
 -- repair because of that.
 -- Compartmentalizing like this
 -- can be called "abstraction."

-- is it time for a new cel?
 if (frame % celtimer==0) then
     nowcel = nowcel + 1
     -- did we go past the last cel?
     -- then go back to first cel.
     if (nowcel>finalcel) then
        nowcel=startcel
     end
 end

-- is it time to move our guy?
 if (frame % movetimer==0) then
    xpos=xpos+xinc
    -- did we move him past the
    -- edge of the screen?  then
    -- wrap him around to start!
    if (xpos>finalx) then
        xpos=startx
    end
 end

end