-
Notifications
You must be signed in to change notification settings - Fork 21
C3D 05 Adding Physics
Following on in the same pattern, this tutorial is as similar to the 2D equivalent as possible in order to demonstrate the similarities and differences in implementation.
For this example, create a new class named CadetHelloPhysics
in the default package, set it to be the default application and copy and paste the code below into it.
package
{
import flash.display.Sprite;
import flash.events.Event;
import cadet.core.CadetScene;
import cadet3D.components.cameras.CameraComponent;
import cadet3D.components.core.MeshComponent;
import cadet3D.components.debug.TridentComponent;
import cadet3D.components.geom.CubeGeometryComponent;
import cadet3D.components.geom.PlaneGeometryComponent;
import cadet3D.components.lights.DirectionalLightComponent;
import cadet3D.components.materials.ColorMaterialComponent;
import cadet3D.components.renderers.Renderer3D;
import cadet3DPhysics.components.behaviours.RigidBodyBehaviour;
import cadet3DPhysics.components.processes.PhysicsProcess;
[SWF( width="700", height="400", backgroundColor="0x002135", frameRate="60" )]
public class CadetHelloPhysics extends Sprite
{
private var cadetScene:CadetScene;
private var defaultMaterial:ColorMaterialComponent;
public function CadetHelloPhysics()
{
cadetScene = new CadetScene();
// Add Renderer
var renderer:Renderer3D = new Renderer3D();
renderer.viewportWidth = stage.stageWidth;
renderer.viewportHeight = stage.stageHeight;
cadetScene.children.addItem(renderer);
renderer.enable(this);
// Add Trident
var trident:TridentComponent = new TridentComponent();
cadetScene.children.addItem(trident);
// Add Camera
var camera:CameraComponent = new CameraComponent();
camera.rotationX = -145;
camera.rotationY = -45;
camera.rotationZ = -180;
camera.x = 1000;
camera.y = 1000;
camera.z = 1000;
cadetScene.children.addItem(camera);
// Add Light source
var dirLight:DirectionalLightComponent = new DirectionalLightComponent();
dirLight.ambient = 0.3;
dirLight.diffuse = 1;
dirLight.rotationX = 65;
dirLight.rotationY = -90;
cadetScene.children.addItem(dirLight);
// Add Physics Process
cadetScene.children.addItem(new PhysicsProcess());
// Add default Material
defaultMaterial = new ColorMaterialComponent();
cadetScene.children.addItem(defaultMaterial);
// Create floor
var planeGeometry:PlaneGeometryComponent = new PlaneGeometryComponent(6000, 6000);
var planeEntity:MeshComponent = new MeshComponent();
planeEntity.materialComponent = defaultMaterial;
planeEntity.geometryComponent = planeGeometry;
planeEntity.children.addItem(planeGeometry);
planeEntity.children.addItem(new RigidBodyBehaviour());
cadetScene.children.addItem(planeEntity);
// Create cubes
var sceneWidth:uint = 2000;
var sceneHeight:uint = 6000;
var sceneDepth:uint = 2000;
var cubeSize:uint = 80;
var variation:uint = 20;
for ( var i:int = 0; i < 150; i++ )
{
var x:Number = Math.random() * sceneWidth - sceneWidth/2;
var y:Number = Math.random() * sceneHeight;
var z:Number = Math.random() * sceneDepth - sceneDepth/2;
var width:Number = cubeSize + Math.random() * variation;
var height:Number = cubeSize + Math.random() * variation;
var depth:Number = cubeSize + Math.random() * variation;
addCubeEntity( x, y, z, width, height, depth );
}
addEventListener( Event.ENTER_FRAME, enterFrameHandler );
}
private function addCubeEntity( x:Number, y:Number, z:Number, width:Number, height:Number, depth:Number ):MeshComponent
{
var cubeGeometry:CubeGeometryComponent = new CubeGeometryComponent(width, height, depth);
var cubeEntity:MeshComponent = new MeshComponent();
cubeEntity.x = x;
cubeEntity.y = y;
cubeEntity.z = z;
cubeEntity.materialComponent = defaultMaterial;
cubeEntity.geometryComponent = cubeGeometry;
cubeEntity.children.addItem(cubeGeometry);
cubeEntity.children.addItem(new RigidBodyBehaviour());
cadetScene.children.addItem(cubeEntity);
return cubeEntity;
}
private function enterFrameHandler( event:Event ):void
{
cadetScene.step();
}
}
}
The first part of the CadetHelloPhysics
constructor, designated by the following comments should be familiar from the previous tutorial:
//Add Renderer
//Add Trident
//Add Camera
//Add Light source
The first new bit of code is:
// Add Physics Process
cadetScene.children.addItem(new PhysicsProcess());
Note how the implementation is identical to the 2D equivalent, except PhysicsProcess
in this instance refers to cadet3DPhysics.components.processes.PhysicsProcess
, rather than cadet2DBox2D.components.processes.PhysicsProcess
.
For our next trick we create a default material:
// Add default Material
defaultMaterial = new ColorMaterialComponent();
cadetScene.children.addItem(defaultMaterial);
This is the grey material shared between all the boxes, which we need only create one instance of.
Next up is the floor:
// Create floor
var planeGeometry:PlaneGeometryComponent = new PlaneGeometryComponent(6000, 6000);
var planeEntity:MeshComponent = new MeshComponent();
planeEntity.materialComponent = defaultMaterial;
planeEntity.geometryComponent = planeGeometry;
planeEntity.children.addItem(planeGeometry);
planeEntity.children.addItem(new RigidBodyBehaviour());
cadetScene.children.addItem(planeEntity);
For this we create a large PlaneGeometryComponent
, then add references to it and the defaultMaterial
to a new MeshComponent
named planeEntity
. In order to make the floor solid, we add a RigidBodyBehaviour
as a child of the planeEntity
too. On being added to its parent, the RigidBodyBehaviour
checks to see if it has a sibling Geometry; if so, it creates the relevant AwayPhysics equivalent object in order to give it a presence in the physics scene.
Finally, we add some cubes by creating a for loop which calls the addCubeEntity
method, passing in some randomised values. Note how a RigidBodyBehaviour
is also added to each cubeEntity
, ensuring that each has a presence in the physics scene.
Build and run to watch the boxes fall!