Hello out there to everybody in the Moai world! My name's Andy, and I'll be creating and posting some basic game making tutorials for the Moai Platform. When Patrick asked me to create a good intro tutorial game, it took me about five minutes to come up with my concept. For simplicity's sake, I thought a game inspired by Atari's Missile Command would be the best way to showcase gameplay features like randomly spawning enemies, player input, explosions and a clear failure condition. Then at lunch that day we decided that it would be really funny if we used a lobster for the player's missile base. We were wrong about the comedy factor, but regardless, the lobster stayed.

Enter: Rocket Lobster. The game consists of enemy missiles flying down from the top of the screen towards the player’s bases at the bottom. The player is tasked with shooting defensive missiles of their own up to stop the enemy missiles from reaching their lobster.  Er, base. Note: This tutorial assumes the reader has at least a basic understanding of Lua and programming. Moai documentation can be found at http://getmoai.com/docs

as well as Moai Basics - Part 1

and Moai Basics - Part 2

. I suggest reading both of the blog posts to become more familiar with a few of the Moai classes we will use in this tutorial. In order to run the tutorial, you will need the files located here: Files for RocketLobster

. This will contain the all the image files, the font file, and the completed code (as well as a blank .lua file). Now that the introduction's out of the way, it's time to create our first game.  First thing we’ll need to do is to create our game window. Talk about this tutorial in the forums!

-- This will print “Hello Moai” on the debug screen.

print ( "hello, moai!" )

-- This opens up a window with the title of “Rocket Lobster” with

-- a width of 320 pixels and a height of 480 pixels.

MOAISim.openWindow ( "Rocket Lobster", 320, 480 )

--This will set the viewport and the layer for rendering.

viewport = MOAIViewport.new ()

viewport:setScale ( 320, 480 )

viewport:setSize ( 320, 480 )



layer = MOAILayer2D.new ()

layer:setViewport ( viewport )

MOAISim.pushRenderPass ( layer )

More in depth information on viewports and layers can be found in the Moai Basics 1

blog post. Go ahead and run the program so far and you should get:

******************** Now that we have our window set up, we’re ready to start creating and inserting our objects. Below the set up, go ahead and add in the following code.

lobsterGfx = MOAIGfxQuad2D.new ()

lobsterGfx:setTexture ( "openlobster.png" )

lobsterGfx:setRect ( -128, -128, 128, 128 )



base = MOAIProp2D.new ()

base:setDeck ( lobsterGfx )

base:setLoc ( 0, -240 )



layer:insertProp ( base )

This will create and insert our lobster base onto the game window.

-- Creates a new GfxQuad with the name of lobsterGfx

lobsterGfx = MOAIGfxQuad2D.new ()

-- Assigns the texture "openlobster.png" to that lobsterGfx Quad

lobsterGfx:setTexture ( "openlobster.png" )

-- Sets the size of the quad

lobsterGfx:setRect ( -128, -128, 128, 128 )



-- Creates a new Prop with the name of base

base = MOAIProp2D.new ()

-- Assigns the lobsterGfx textured quad to the prop "base"

base:setDeck ( lobsterGfx )

-- Sets the location of the base

base:setLoc ( 0, -240 )



-- Inserts the prop "base" into the layer so it can be seen.

layer:insertProp ( base )

Now that it’s all in there you should see the following:

******************** Now that our base is on the screen, it’s time to place a rocket.

rocketGfx = MOAIGfxQuad2D.new ()

rocketGfx:setTexture ( "rocket.png" )

rocketGfx:setRect ( -32, -32, 32, 32 )



--------------------------------



function makeRocket ()



     local rocket = MOAIProp2D.new ()

     rocket:setDeck ( rocketGfx )

     layer:insertProp ( rocket )

end



makeRocket ()

This should look fairly similar to the base making, with one major change.

function makeRocket ()



     local rocket = MOAIProp2D.new ()

     rocket:setDeck ( rocketGfx )

     layer:insertProp ( rocket )

end



makeRocket ()

Since we will eventually want to make more than one rocket (unlike our base, where one is fine), it would make more sense to create a rocket making function. Later we will come back to this function and make some changes, but for now, this will work for us. After adding in the code and running the program, you should be presented with the following:

******************** Now that we’ve got the rocket, it’s time to make it move. With this step, things are going to get a bit more complicated; we will be introducing threads as well as functions within functions, but we’ll take it piece by piece. The next section will take the previous code and add a new function into the makeRocket function, and we also change the coordinates of the base to a constant. For organization's sake, we will be placing our constants at the top of the code, right above the window initialization.

BASE_X = 0

BASE_Y = -240

Now that our constants are in, we need to change the base creation to match.

base = MOAIProp2D.new ()

base:setDeck ( lobsterGfx )

base:setLoc ( BASE_X, BASE_Y ) -- New base coordinates



layer:insertProp ( base )

Here we just changed the way that the base gets its location. For clarity later on, we will just use BASE_X and BASE_Y. Now to make the rocket move!

function makeRocket ()



     local rocket = MOAIProp2D.new ()

     rocket:setDeck ( rocketGfx )

     layer:insertProp ( rocket )



----------------

     function rocket:main ()



          MOAIThread.blockOnAction ( self:seekLoc ( BASE_X, BASE_Y, 3.0, MOAIEaseType.LINEAR ))

     end



     rocket.thread = MOAIThread.new ()

     rocket.thread:run ( rocket.main, rocket )

end



makeRocket ()

The main thing that we are adding in is the rocket:main function.

function rocket:main ()



     MOAIThread.blockOnAction ( self:seekLoc ( BASE_X, BASE_Y, 3.0, MOAIEaseType.LINEAR ))

end



rocket.thread = MOAIThread.new ()

rocket.thread:run ( rocket.main, rocket )

In our rocket:main function, we create MOAIThread.blockOnAction and inside that we’re starting the movement. self:seekLoc ( BASE_X, BASE_Y, 3.0, MOAIEaseType.LINEAR)) will make self (our rocket) seek the location (seekLoc) of BASE_X (for x coords), BASE_Y (for y coords) with a timer of 3.0 (3 seconds from start to finish), and an ease type of linear (meaning the speed goes at a constant speed.)  After we created the rocket:main function, we will run it in a thread.

makeRocket ()  -- Make our rocket

Now after all those are in, running the game will get you this:

******************** Now that we have our rocket flying towards our base with reckless abandon, it’s time to make it actually do something. I think exploding is a good idea. In order to do this, we will first need to create the explosion and then call it when the rocket hits its target. This step is two in one. First step is to create the explosion. This will have to be inserted above the rocket creation, since the rocket will call the explosion.

explosionGfx = MOAIGfxQuad2D.new ()

explosionGfx:setTexture ( "fire.png" )

explosionGfx:setRect ( -32, -32, 32, 32 )



--------------------------------



function makeExplosion ( x, y, size )



     local explosion = MOAIProp2D.new ()

     explosion:setDeck ( explosionGfx )

     explosion:setLoc ( x, y )

     explosion.size = size

     layer:insertProp ( explosion )



----------------



     function explosion:main ()



          for i = 1, 128 do

               self:setFrame ( -i, -i, i, i )

               coroutine.yield ()

          end



          layer:removeProp ( explosion )

     end



     explosion.thread = MOAIThread.new ()

     explosion.thread:run ( explosion.main, explosion )

end

This should look very similar to the rocket. We’re still creating the explosionGfx outside everything, and then inside a function calling that graphic onto the newly created prop, but now we have the explosion:main function. Let’s look at that for a moment.

function explosion:main ()



     for i = 1, 128 do

          self:setFrame ( -i, -i, i, i )

          coroutine.yield ()

     end



     layer:removeProp ( explosion )

end



explosion.thread = MOAIThread.new ()

explosion.thread:run ( explosion.main, explosion )

In our for loop, the goal here is to set the size of the explosion and slowly make it grow from a size of ( -1, -1, 1, 1 ) to a size of ( -128, -128, 128, 128) and to cycle through that until it is finished, then it will remove itself from the game.  (layer:removeProp ( explosion ) ) Now that the explosion has been created, it’s time to add the explosion to the rocket. This bit of code will be added inside the rocket:makeRocket function after "layer:insertProp." Here is the newly updated rocket.

function rocket:explode ( size )



     local x, y = self:getLoc ()

     local explosion = makeExplosion ( x, y, size )

     self.thread:stop ()

end



----------------



function rocket:main ()



     MOAIThread.blockOnAction ( self:seekLoc ( BASE_X, BASE_Y, 3.0, MOAIEaseType.LINEAR ))

     self:explode ( 128 )

     layer:removeProp ( self )

     layer:removeProp ( base )

end

First we’ll have to create a rocket:explode function.

-- start a function by taking in a size

function rocket:explode ( size )



     -- get the location of the rocket

     local x, y = self:getLoc ()

     -- create an explosion with the rocket's loc and the new size

     local explosion = makeExplosion ( x, y, size )



     self.thread:stop ()

end

After creating our rocket:explode function, we can plug that into rocket:main

function rocket:main ()



     MOAIThread.blockOnAction ( self:seekLoc ( BASE_X, BASE_Y, 3.0, MOAIEaseType.LINEAR ))

     -- when the rocket finishes its path, it will explode with this size

     self:explode ( 128 )



     layer:removeProp ( self ) -- removes the rocket from the game

     layer:removeProp ( base ) -- removes the base from the game

end

Running that, you should see:

******************** Now that we’ve got our rocket to explode and blow up our base, we’re going to need a way to defend ourselves. Here comes the ally rocket. This step will be very involved, and we will have to do many things. Create our game loop, create an ally rocket and an enemy rocket type, assign a target for our rockets, create player input, change the direction the rocket points in, launch multiple enemy rockets, change the size of the explosion depending on if it hits the base or not. So let’s jump into it! First things first we’re going to declare a few math utility functions. Nothing special here. They do, however, have to be declared above everything else, since we will be using them in other functions, so we'll just put them right below the setup constants.

--------------------------------



function angle ( x1, y1, x2, y2 )



     return math.atan2 ( y2 - y1, x2 - x1 ) * ( 180 / math.pi )

end



--------------------------------



function distance ( x1, y1, x2, y2 )



     return math.sqrt ((( x2 - x1 ) ^ 2 ) + (( y2 - y1 ) ^ 2 ))

end

--------------------------------

Next we’ll change the size of the explosion. OLD:

function explosion:main ()



     for i = 1, 128 do

NEW:

function explosion:main (  )



     for i = 1, self.size do

We’re now going to be plugging in a size variable into the explode function, and using that to determine the size of our explosion. Later on we will declare that size variable depending on which type of rocket we launch. Now we need to add a considerable chunk to our rocket making function. First, however, we'll need a few more constants; these ones will be used to determine rocket speed . Again, declare these with the other constants at the top of the code.

MIN_ENEMY_SPEED = 200

MAX_ENEMY_SPEED = 300



ALLY_SPEED = 300

Here’s the new one in its entirety.

function makeRocket ( isAlly, startX, startY, targetX, targetY, speed )



     local travelDist = distance ( startX, startY, targetX, targetY )

     local travelTime = travelDist / speed

     local rocket = MOAIProp2D.new ()



     rocket:setDeck ( rocketGfx )

     layer:insertProp ( rocket )

     rocket:setLoc ( startX, startY )

     rocket:setRot ( angle ( startX, startY, targetX, targetY ) + 90 )

     rocket.isAlly = isAlly               -- declare



----------------



     function rocket:explode ( size )



          local x, y = self:getLoc ()

          local explosion = makeExplosion ( x, y, size )

          layer:removeProp ( self )



          self.thread:stop ()

     end



----------------



     function rocket:main ()



          MOAIThread.blockOnAction ( self:seekLoc ( targetX, targetY, travelTime, MOAIEaseType.LINEAR ))



          if self.isAlly then

               self:explode ( 64 )

          else

               self:explode ( 128 )

               layer:removeProp ( base )

          end

     end



----------------



     rocket.thread = MOAIThread.new ()

     rocket.thread:run ( rocket.main, rocket )

end



------------------------



function launchEnemyRocket ( startX, startY )



     makeRocket ( false, startX, startY, BASE_X, BASE_Y, math.random ( MIN_ENEMY_SPEED, MAX_ENEMY_SPEED ))

end



--------------------------------



function launchAllyRocket ( targetX, targetY )



     makeRocket ( true, BASE_X, BASE_Y, targetX, targetY, ALLY_SPEED )

end

First thing you will notice is that we are now using travelTime instead of using 3.0 for our rocket speed. Make sure you don't miss adding it to MOAIThread.blockOnAction. Another major change to the makeRocket function is the “isAlly” variable.  This will determine if the rocket is one of the friendly rockets, or an enemy rocket. We will pass this thorough when we create the rocket and it will determine the spawn location. First, we’ll go ahead and set up two different types of rockets.

function launchEnemyRocket ( startX, startY )



     makeRocket ( false, startX, startY, BASE_X, BASE_Y, math.random ( MIN_ENEMY_SPEED, MAX_ENEMY_SPEED ))

end

When the launchEnemyRocket function is called, a start location is run through it; it then plugs that into the makeRocket function, and also declares that isAlly = false. Finally, a rocket speed is determined with math.random and the constants we declared earlier.

function launchAllyRocket ( targetX, targetY )



     makeRocket ( true, BASE_X, BASE_Y, targetX, targetY, ALLY_SPEED )

end

Similar to the launchEnemyRocket, we plug the variables in, except this time we declare isAlly = true. Now that we have our new rocket launching functions, it’s time to create a game loop so that we can run them more than once!

mainThread = MOAIThread.new ()

mainThread:run (



     function ()



          local frames = 0

          while true do

               coroutine.yield ()

               frames = frames + 1

               if frames >= 90 then

                    frames = 0

                    launchEnemyRocket ( math.random ( -160, 160 ), 300 )

               end

          if MOAIInputMgr.device.mouseLeft:down () then

               launchAllyRocket ( layer:wndToWorld ( MOAIInputMgr.device.pointer:getLoc () ))

          end

     end

end

)

So here it is, the game loop. Pretty small, pretty simple, but powerful. Let’s go through the sections of it. First we declare our main thread ( mainThread = MOAIThread.new () ) and then we run that thread with our function inside. In that function, we first declare frames = 0, and then yield. During that yield, we add 1 to frame every cycle. Finally, when the frame count hits 90, we reset it to 0 and then run launchEnemyRocket with a Y value of 300 and an X value of (math.random ( -160, 160 ), allowing us to spawn it at any spot along that line, to add some randomness to the rockets. As well as spawning in our enemy rockets, we will now take in player input. "MOAIInputMgr.device.mouseLeft:down" means that when the mouseLeft button has been pressed, then the game will launchAllyRocket with the coordinates taken from ( layer:wndToWorld  (MOAIInputMgr.device.pointer:getLoc ()) meaning that wherever the mouse pointer is at the moment of the button press, that location will be translated into coordinates that the game will use as the target location. And here's what our game looks like at this point:

******************** Now that we finally can launch our own rockets and they will explode, it’s time to make those explosions actually do something. We’re rounding the bases and are almost finished with our game. This step, we will introduce hit detection on the explosions, and rearrange a few of our previous functions. Without further talking, it’s time to start adding things in for our hit detection. First, we will need to create a table of enemy rockets that we will use to check if the explosion hit the rocket or not. We can go ahead and make that table right after we create our rocketGfx.

rocketGfx = MOAIGfxQuad2D.new ()

rocketGfx:setTexture ( "rocket.png" )

rocketGfx:setRect ( -32, -32, 32, 32 )



enemyRockets = {}

Now that we have our enemyRockets table, it’s time to start plugging our enemy rockets into the table. We’ll do this by editing our makeRocket function and placing the following code right after “rocket.isAlly = isAlly”

rocket:setLoc ( startX, startY )

rocket:setRot ( angle ( startX, startY, targetX, targetY ) + 90 )

rocket.isAlly = isAlly



if not isAlly then

     enemyRockets [ rocket ] = rocket

end

And now our enemy rockets have been placed into a table! Now we need to create a hit detection function to our explosion. This will need to be placed inside the explosion:makeExplosion function, but above the explosion:main function.

function explosion:checkHit ( prop )



     local x1, y1 = self:getLoc ()

     local x2, y2 = prop:getLoc ()

     return distance ( x1, y1, x2, y2 ) <= self.size

end

This one looks small, but there’s a lot going on. The function itself takes in a prop (one of our enemy rockets) and compares the location of our explosion against the location of the prop. It then returns distance and if the location is less than or equal to the size of the prop, it will explode. Now we have to change the rocket:explode function to handle what happens when the rocket is told to explode. We do that by adding enemyRockets [ self] = nil to the function.

function rocket:explode ( size )



     local x, y = self:getLoc ()

     local explosion = makeExplosion ( x, y, size )

     layer:removeProp ( self )



     enemyRockets [ self ] = nil

     self.thread:stop ()

end

After that, we have to edit the explosion:main function to run the checkHit function we just made.

     function explosion:main ()



          for i = 1, self.size do

               self:setFrame ( -i, -i, i, i )

               for rocket in pairs ( enemyRockets ) do

                    if self:checkHit ( rocket ) then

                         rocket:explode ( 64 )

                    end

               end

          coroutine.yield ()

     end

     layer:removeProp ( self )

end

And there we go, we are all finished with hit detection. An ally rocket that explodes will look like:

******************** Now we’re in the home stretch. We have our game loop going, we have rockets flying in all directions, explosions that can blow up other things, a base that goes away when it gets hit. The final thing we’re missing is some sort of game over system. We’ll need to stop all rockets from launching after our base has been blown up, and also to create a game over message. Let’s get to it! First, we’ll need to create a game over bool. We can just declare this right above the enemyRockets table.

gameOver = false

enemyRockets = {}

That’s easy enough. Now we’ll need the game to end once the base has been blown up and removed. That’s as easy as putting gameOver = true into the rocket:main thread, like so

-- hide the base

layer:removeProp ( base )

-- set the game over flag

gameOver = true

Now when our base gets blown up, gameOver will be set to true. But now what do we do? Simple, we’ll just stop running the main game loop. OLD:

function ()



     local frames = 0

     while true do

          coroutine.yield ()

          frames = frames + 1

NEW:

function ()



     local frames = 0

          -- Once gameOver = true, the main thread stops running.

          while not gameOver do

               coroutine.yield ()

               frames = frames + 1

And now, for our final step: placing a game over message onto the screen after the game ends. Right after the while loop ends, we can create a text box. Here is what that looks like

-- This creates a font and loads up the arialbd.tff file for that font.

local font = MOAIFont.new ()

font:loadFromTTF ( "arialbd.ttf", "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789,.?!", 12, 163 )



local textbox = MOAITextBox.new ()

textbox:setFont ( font )

textbox:setTextSize ( font:getScale ())

textbox:setRect ( -160, -80, 160, 80 )

textbox:setAlignment ( MOAITextBox.CENTER_JUSTIFY )

textbox:setYFlip ( true )

textbox:setString ( "You are dead!" ) --- All of these set the parameters of the textbox.

layer:insertProp ( textbox )

textbox:spool () --- And finally, this places the textbox into the layer, spooling it along one letter at a time.

And that’s it! We finally have finished Rocket Lobster.

******************** In case you were interested, here is what our final code looks like.

--==============================================================

-- Copyright (c) 2010-2011 Zipline Games, Inc.

-- All Rights Reserved.

-- http://getmoai.com

--==============================================================

--==============================================================

-- set up

--==============================================================



print ( "hello, moai!" )

SCREEN_UNITS_X = 320

SCREEN_UNITS_Y = 480

SCREEN_WIDTH = SCREEN_UNITS_X

SCREEN_HEIGHT = SCREEN_UNITS_Y



BASE_X = 0

BASE_Y = -240

MIN_ENEMY_SPEED = 200

MAX_ENEMY_SPEED = 300

ALLY_SPEED = 300



MOAISim.openWindow ( "Rocket Lobster", SCREEN_WIDTH, SCREEN_HEIGHT )

viewport = MOAIViewport.new ()

viewport:setScale ( SCREEN_UNITS_X, SCREEN_UNITS_Y )

viewport:setSize ( SCREEN_WIDTH, SCREEN_HEIGHT )



layer = MOAILayer2D.new ()

layer:setViewport ( viewport )

MOAISim.pushRenderPass ( layer )



--==============================================================

-- utility functions

--==============================================================



--------------------------------

function angle ( x1, y1, x2, y2 )



     return math.atan2 ( y2 - y1, x2 - x1 ) * ( 180 / math.pi )

end

--------------------------------

function distance ( x1, y1, x2, y2 )



     return math.sqrt ((( x2 - x1 ) ^ 2 ) + (( y2 - y1 ) ^ 2 ))

end

--==============================================================

-- base

--==============================================================



lobsterGfx = MOAIGfxQuad2D.new ()

lobsterGfx:setTexture ( "openlobster.png" )

lobsterGfx:setRect ( -128, -128, 128, 128 )



base = MOAIProp2D.new ()

base:setDeck ( lobsterGfx )

base:setLoc ( BASE_X, BASE_Y )



layer:insertProp ( base )

--==============================================================

-- explosion rig

--==============================================================



explosionGfx = MOAIGfxQuad2D.new ()

explosionGfx:setTexture ( "fire.png" )

explosionGfx:setRect ( -32, -32, 32, 32 )



--------------------------------



function makeExplosion ( x, y, size )



     local explosion = MOAIProp2D.new ()

     explosion:setDeck ( explosionGfx )

     explosion:setLoc ( x, y )

     explosion.size = size

     layer:insertProp ( explosion )



 ----------------



     function explosion:checkHit ( prop )



          local x1, y1 = self:getLoc ()

          local x2, y2 = prop:getLoc ()

          return distance ( x1, y1, x2, y2 ) <= self.size

     end



 ----------------



     function explosion:main ()



          for i = 1, self.size do

               self:setFrame ( -i, -i, i, i )

               for rocket in pairs ( enemyRockets ) do

                    if self:checkHit ( rocket ) then

                         rocket:explode ( 64 )

                    end

               end

               coroutine.yield ()

          end

          layer:removeProp ( self )

     end



     explosion.thread = MOAIThread.new ()

     explosion.thread:run ( explosion.main, explosion )

end



--==============================================================

-- rocket

--==============================================================



rocketGfx = MOAIGfxQuad2D.new ()

rocketGfx:setTexture ( "rocket.png" )

rocketGfx:setRect ( -32, -32, 32, 32 )



gameOver = false

enemyRockets = {}



--------------------------------



function makeRocket ( isAlly, startX, startY, targetX, targetY, speed )



     local travelDist = distance ( startX, startY, targetX, targetY )

     local travelTime = travelDist / speed

     local rocket = MOAIProp2D.new ()



     rocket:setDeck ( rocketGfx )

     layer:insertProp ( rocket )

     rocket:setLoc ( startX, startY )

     rocket:setRot ( angle ( startX, startY, targetX, targetY ) + 90 )



     rocket.isAlly = isAlly

     if not isAlly then

          enemyRockets [ rocket ] = rocket

     end



 ----------------



     function rocket:explode ( size )



          local x, y = self:getLoc ()

          local explosion = makeExplosion ( x, y, size )

          layer:removeProp ( self )

          enemyRockets [ self ] = nil

          self.thread:stop ()

     end



 ----------------



     function rocket:main ()



          MOAIThread.blockOnAction ( self:seekLoc ( targetX, targetY, travelTime, MOAIEaseType.LINEAR ))

          if self.isAlly then

               self:explode ( 64 )

          else

               self:explode ( 128 )

               gameOver = true

               layer:removeProp ( base )

          end

     end

     rocket.thread = MOAIThread.new ()

     rocket.thread:run ( rocket.main, rocket )

end



--------------------------------



function launchEnemyRocket ( startX, startY )



     makeRocket ( false, startX, startY, BASE_X, BASE_Y, math.random ( MIN_ENEMY_SPEED, MAX_ENEMY_SPEED ))

end



--------------------------------



function launchAllyRocket ( targetX, targetY )



     makeRocket ( true, BASE_X, BASE_Y, targetX, targetY, ALLY_SPEED )

end



--==============================================================

-- game loop

--==============================================================



mainThread = MOAIThread.new ()

mainThread:run (



     function ()



          local frames = 0

          while not gameOver do

                coroutine.yield ()

                frames = frames + 1

                if frames &gt;= 90 then

                     frames = 0

                     launchEnemyRocket ( math.random ( -160, 160 ), 300 )

                end

                if MOAIInputMgr.device.mouseLeft:down () then

                     launchAllyRocket ( layer:wndToWorld ( MOAIInputMgr.device.pointer:getLoc () ))

                end

          end



          local font = MOAIFont.new ()

          font:loadFromTTF ( "arialbd.ttf", "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789,.?!", 12, 163 )



          local textbox = MOAITextBox.new ()

          textbox:setFont ( font )

          textbox:setTextSize ( font:getScale ())

          textbox:setRect ( -160, -80, 160, 80 )

          textbox:setAlignment ( MOAITextBox.CENTER_JUSTIFY )

          textbox:setYFlip ( true )

          textbox:setString ( "You are dead!" )

          layer:insertProp ( textbox )

          textbox:spool ()

     end

)