This
article outlines the steps in creating a simple Ping Pong game in Director. The
first step is the creation of a 3D cast member. Click on Windows in the Main
Menu and select Shockwave 3D, a 3D cast would be created in the cast Window,
rename the cast member as “3D World” and place it on sprite1. And then you can
start adding script to the 3D cast.
The beginSprite method is mainly used for initializing the 3D environment such as, model
creation, positioning the model in the 3D environment, adding skin to the
model, adding collision modifiers to the model etc.
-- Initializing the 3D cast member
mySprite = sprite(me.spriteNum)
tMember = mySprite.member
tMember.resetWorld()
-- Create a ball model
ballResource = tMember.newModelResource("Ball", #sphere)
ballResource.radius = 7
ballModel = tMember.newModel("Ball", ballResource)
-- positioning the ball model
ballModel.transform.identity()
ballModel.transform.translate(0,-75,0)
-- add new shader and texture to the
ball model
tMember.newTexture("Texture02",#fromImageObject,member("Image1").image)
newShader01
= tMember.newShader("newPainter",#standard)
newShader01.texture = tMember.texture("Texture02")
ballModel.shader = newShader01
-- Add collision modifier
.addModifier(#collision) -- enabled by default
ballModel.collision.mode = #sphere
ballModel.collision.resolve = FALSE -- resolved on an individual basis
ballModel.collision.setCollisionCallback(#ballCollide, me)
Any
number of models can be created from a modelResource.
The model is the actual object that is visible in the 3D World. A model can be
repositioned, cloned and made to respond to user event.
In
order to give a realistic appearance to the Model, Shader is added to the Model. A Shader is the
"skin" which is wrapped around the model resource used by the model.
The visible component of a shader is created with up
to eight layers of textures. These eight texture layers are either created from
bitmap cast members or image objects within Director or imported with models
from 3D modeling programs. A texture can be used by any number of shaders. Changes to a texture will appear in all shaders which use that texture.
The
collision modifier is added to the Model, it allows the model to detect and
respond to collision. The setCollisionCallback() method is used to
register a method, that is called when the collision is detected. In a game, we
require the ball to bounce of the wall except when it collides against the bottom
wall. Hence, we set the collision enabled property to TRUE and set the resolve property to FALSE since the
collision is not resolved on an individual basis, but according to the rules of
the game.
on ballCollide me, collisionData
case collisionData.modelB of
leftwallModel:
xDirection = 1
otherwise:
.
.
.
.
end case
end
The collisionData object has four properties, modelA and modelB are the models involved in the collision, pointOfContact is the world position of the collision and collisionNormal is the direction of the collision.
The code is
broken as follows.
To stimulate
the motion of the ball, we use the enterframe method
to reposition the object in each frame.
on enterframe
LocX = ballModel.transform.position.x +
(3 * xDirection)
LocY = ballModel.transform.position.y +
(3 * yDirection)
ballModel.transform.position = vector(LocX, LocY,0)
end
To
move the pinpong bat, we use the keyDown method, the keyPressed method tests whether the last key
that was pressed on the keyboard is equal to the given keycode.
on keyDown()
--123: Left
--126: up
--125: down
--124: Right
.
.
.
if _key.keyPressed(123) and gameOver<>1 then -- left button clicked
LocX = max (LocX-20,-70)
batModel.transform.position = vector(LocX,-65,0)
end if
.
.
.
end
To
create text in the 3D world, create a text cast member and edit it using the
text editor. Create a TextModelResource using the
Text Member. Inorder to apply shader to the Text, the shaderList (The number of entries in
this list equals the number of meshes in the model resource used by the model.
Each mesh can be shaded by only one shader) of the
Text must be initialized to the new shader.
-- create a
text
textResource = member("normal_text").extrude3d(tMember)
textResource.tunnelDepth = 18
textResource.smoothness = 50
textModel = tMember.newModel("3DText",textResource)
textModel.transform.position = vector(-95,-20,0)
textModel.visibility = #none
-- add texture
to text
tMember.newTexture("Texture03",#fromImageObject,member("Image2").image)
newShader02 = tMember.newShader("newPainter01",#standard)
newShader02.texture = tMember.texture("Texture03")
count_shader = tMember.model("3DText").shaderList.count
i = 0
repeat while i < count_shader
i = i + 1
tMember.model("3DText").shaderlist[i] =
newShader02
end repeat
I have used the Particle
system to draw a line across the screen. You can play around with the particle
system to get a wide variety of effects like smoke, fire etc.
-- create a particle model
particleResource = tMember.newModelResource("particle01", #particle,#both)
particleResource.colorRange.start=rgb(255,0,0)
particleResource.colorRange.end=rgb(0,0,255)
particleResource.sizeRange.start= 2
particleResource.sizeRange.end= 0
particleResource.blendRange.start=100.0
particleResource.blendRange.end=0.0
particleResource.emitter.numParticles=1000
particleResource.emitter.minSpeed=30
particleResource.emitter.maxSpeed=50
particleResource.emitter.angle=3
particleModel = tMember.newModel("particle01", particleResource)
particleModel.visibility = #none
particleModel.transform.position = vector(-95,-15,0)
The code for the complete
ping pong game is as follows. You can play around with the code and add buttons
to restart the game and more.
Create a field member and
label it “score_field” to enter score, import two
images to the cast library and name it “Image1” and “Image2” to create the
textures for the objects. Create a Text member and name it “normal_text” , open the text editor and type “Game Over”.
----------
Define the property and global variables
property mySprite
property tMember
property leftwallModel
property rightwallModel
property bottomwallModel
property topwallModel
property batModel
property ballModel
property textModel
property brickModel
property particleModel
property brickResource
property newShader03
property Texture01
global xDirection
global yDirection
global gameOver
global gScore
global seti
-----------------------------------------------------------------------
on beginSprite(me)
mySprite = sprite(me.spriteNum)
tMember = mySprite.member
tMember.resetWorld()
cameraModel = mySprite.camera
gameOver = 0
xDirection = 1
yDirection = 1
brickModel = [40]
gScore = 0
seti = 1
member("score_field").text = gScore & " "
-- Create the batModel model
batResource = tMember.newModelResource("Bat", #box)
batResource.height = 4
batResource.width = 30
batResource.length = 5
batModel = tMember.newModel("Bat", batResource)
batModel.transform.identity()
batModel.transform.translate(0,-65,0)
-- Add collision
modifier
batModel.addModifier(#collision)
batModel.collision.mode = #box
batModel.collision.resolve = FALSE
-- Create the
left wall model
lwallResource = tMember.newModelResource("lwall", #box)
lwallResource.height = 140
lwallResource.width = 3
lwallResource.length = 5
leftwallModel = tMember.newModel("lwall", lwallResource)
leftwallModel.transform.identity()
leftwallModel.transform.translate(-90,0,0)
-- Add collision
modifier
leftwallModel.addModifier(#collision)
leftwallModel.collision.mode = #box
leftwallModel.collision.resolve = FALSE
-- Create the
right wall model
rwallResource = tMember.newModelResource("rwall", #box)
rwallResource.height = 140
rwallResource.width = 3
rwallResource.length = 5
rightwallModel = tMember.newModel("rwall", rwallResource)
rightwallModel.transform.identity()
rightwallModel.transform.translate(90,0,0)
-- Add collision
modifier
rightwallModel.addModifier(#collision)
rightwallModel.collision.mode = #box
rightwallModel.collision.resolve = FALSE
-- Create the top
wall model
twallResource = tMember.newModelResource("twall", #box)
twallResource.height = 3
twallResource.width = 180
twallResource.length = 5
topwallModel = tMember.newModel("twall", twallResource)
topwallModel.transform.identity()
topwallModel.transform.translate(0,70,0)
-- Add collision
modifier
topwallModel.addModifier(#collision)
topwallModel.collision.mode = #box
topwallModel.collision.resolve = FALSE
-- Create the
bottom wall model
bwallResource = tMember.newModelResource("bwall", #box)
bwallResource.height = 3
bwallResource.width = 180
bwallResource.length = 5
bottomwallModel = tMember.newModel("bwall", twallResource)
bottomwallModel.transform.identity()
bottomwallModel.transform.translate(0,-75,0)
-- Add collision
modifier
bottomwallModel.addModifier(#collision)
bottomwallModel.collision.mode = #box
bottomwallModel.collision.resolve = FALSE
-- Add texture to
the wall and the bat
tMember.newTexture("Texture01",#fromImageObject,member("Image2").image)
tMember.model("Bat").shader.texture=tMember.texture("Texture01")
-- Create a ball
model
ballResource = tMember.newModelResource("Ball", #sphere)
ballResource.radius = 7
ballModel = tMember.newModel("Ball", ballResource)
-- Add collision
modifier
ballModel.addModifier(#collision) -- enabled by default
ballModel.collision.mode = #sphere
ballModel.collision.resolve = FALSE --
resolved on an individual basis
ballModel.collision.setCollisionCallback(#ballCollide, me)
-- add new shader and texture to the ball model
tMember.newTexture("Texture02",#fromImageObject,member("Image1").image)
newShader01 = tMember.newShader("newPainter",#standard)
newShader01.texture = tMember.texture("Texture02")
ballModel.shader = newShader01
-- add new shader and texture to the brick model
tMember.newTexture("Texture04",#fromImageObject,member("Image1").image)
newShader03 = tMember.newShader("newPainter02",#standard)
newShader03.texture = tMember.texture("Texture04")
-- Create a brick
brickResource = tMember.newModelResource("Brick", #box)
brickResource.height = 10
brickResource.width = 10
brickResource.length = 5
i=0
k=0
j=0
x = -80
y = 60
repeat while i<2
repeat while j<17
j=j+1
k = k+1
brick_model_label = "Brick" & k
brickModel[k] = tMember.newModel(brick_model_label,brickResource)
brickModel[k].transform.position = vector (x,y,0)
x = x + 10
brickModel[k].shader = newShader03
-- add collision modifier
brickModel[k].addModifier(#collision) -- enabled by default
brickModel[k].collision.mode = #box
brickModel[k].collision.resolve = FALSE
end repeat
i=i+1
j=0
y = y - 10
x = -80
end repeat
-- create a text
textResource = member("normal_text").extrude3d(tMember)
textResource.tunnelDepth = 18
textResource.smoothness = 50
textModel = tMember.newModel("3DText",textResource)
textModel.transform.position = vector(-95,-20,0)
textModel.visibility = #none
-- add texture to
text
tMember.newTexture("Texture03",#fromImageObject,member("Image2").image)
newShader02 = tMember.newShader("newPainter01",#standard)
newShader02.texture = tMember.texture("Texture03")
count_shader = tMember.model("3DText").shaderList.count
i = 0
repeat while i < count_shader
i = i + 1
tMember.model("3DText").shaderlist[i] = newShader02
end repeat
-- create a
particle model
particleResource = tMember.newModelResource("particle01", #particle,#both)
particleResource.colorRange.start=rgb(255,0,0)
particleResource.colorRange.end=rgb(0,0,255)
particleResource.sizeRange.start= 2
particleResource.sizeRange.end= 0
particleResource.blendRange.start=100.0
particleResource.blendRange.end=0.0
particleResource.emitter.numParticles=1000
particleResource.emitter.minSpeed=30
particleResource.emitter.maxSpeed=50
particleResource.emitter.angle=3
particleModel = tMember.newModel("particle01", particleResource)
particleModel.visibility = #none
particleModel.transform.position = vector(-95,-15,0)
end beginSprite
----------------------------------------------------------------------
on keyDown()
--123: Left
|