|
To really get you started with 3D development using Mascot Capsule Micro3D v3, here are ten small example MIDlets that step-by-step introduce the basic techniques you have to master. All examples are based on the same core code that displays a simple 3D model. The examples add the following aspects to this basic structure:
Example 1 Simply shows the 3D model Example 2 Moves the model left/right and up/down using the keys 2, 8, 4 and 6 Example 3 Scales the 3D model using keys 7 and 9 (Note: Scale the model, don't move it on the Z axis) Example 4 Adds light to the 3D scene by the pressing the "Light" soft button Example 5 Switches between parallel and perspective projection by pressing the "Perspective" soft button Example 6 Rotates the 3D model using the phone's joystick Example 7 Adds an animation to the 3D model Example 8 Adds two animations, press 1 to switch between them Example 9 Shows multiple 3D models Example 10 Shows how to draw primitives on the screen
All example MIDlets can be downloaded below and installed as one MIDlet suite.
Download Micro3D v3 basic MIDlet suite>>
Note: The MIDlets are meant as examples of useful Mico3D techniques, not good MIDlet coding practices in general. For example, there is no appropriate code for handling the interruption of a MIDlet in he case of a call or even a proper exit soft button. To exit each MIDlet, press and keep pressing the "back" hard button.
Most of the code should be easy to understand without further explanations, but some important points are discussed below.
Example 1: Show the 3D model The basic 3D model and texture are imported and set up with the lines:
figure = new Figure("http://localhost/example/DemoMIDP/test_model_robo.mbac"); mainTexture = new Texture("http://localhost/example/DemoMIDP/tex_001.bmp", true); figure.setTexture(mainTexture);
The 3D world is rendered on the Canvas like this:
private Graphics3D g3 = new Graphics3D(); … protected void paint(Graphics g) { ... g3.bind(g); g3.renderFigure(figure, 0, 0, layout, effect); //Flush to screen g3.flush(); //Release the Graphics 3D object g3.release(g);
}
Example 2: Move the model The AffineTrans class is used for all transformations, i.e. moving and rotating. The MIDlet moves the 3D model on the X and Y axis by changing two elements in the AffineTrans matrix.
affineTrans.m03 += moveX; affineTrans.m13 += moveY;
Example 3: Scale the model The 3D model can be scaled by creating a matrix with the scaling factors and multiplying this matrix with the AffineTrans matrix. Note that this scales the model and doesn't move it on the z axis (which in this particular case might have looked the same).
AffineTrans scaleTrans = new AffineTrans(); scaleTrans.set(scaleX,0,0,0,0,scaleY,0,0,0,0,scaleZ,0); // Scaling the model affineTrans.mul(scaleTrans);
Example 4: Add light Light is very easy to set up. A direction vector and an intensity value is all that's needed.
private Vector3D dir = new Vector3D(-3511, 731, 878); // Light vector private final int dirIntensity = 4096; // Light intensity private final int ambIntensity = 1755; // Ambient light intensity
...
light = new Light(dir,dirIntensity,ambIntensity); effect = new Effect3D( light, Effect3D.NORMAL_SHADING, true, null); ... g3.renderFigure(figure, 0, 0, layout, effect); ...
Example 5: Projections You can use either perspective or parallel projection on the 3D model. Switch between the two with simple calls.
// Camera distance private final static int persNear = 1; // Minimum distance to the camera private final static int persFar = 4096; // Maximum distance to the camera private final static int persAngle = 682; // Angle
...
//Setting the projection method if(persEnabled){ layout.setPerspective(persNear, persFar, persAngle); }else{ layout.setParallelSize(800, 800); }
Example 6: Rotate the model To rotate the 3D model you use the same technique as you use to scale the model in example 3. You create an AffineTrans object that holds your rotation data and then multiply its matrix with the model's main AffineTrans.
// Rotation value public final static int SPIN_X_PLUS = 100; // Increase or decrease value of the rotation around X axis public final static int SPIN_Y_PLUS = 100; // Increase or decrease value of the rotation around Y axis private static int spinX = 0; // X axis rotation value private static int spinY = 0; // Y axis rotation value
...
kc = getGameAction(kc); switch (kc) { case Canvas.UP: // roll up setSpinX(-SPIN_X_PLUS); break; case Canvas.DOWN: // roll down setSpinX(SPIN_X_PLUS); break; case Canvas.LEFT: // roll left setSpinY(-SPIN_Y_PLUS); break; case Canvas.RIGHT: // roll right setSpinY(SPIN_Y_PLUS); break; default: break; }
...
AffineTrans rotTrans = new AffineTrans();
//X roll rotTrans.setIdentity(); rotTrans.setRotationX(spinX); affineTrans.mul(rotTrans);
//Y roll rotTrans.setIdentity(); rotTrans setRotationY(spinY); affineTrans.mul(rotTrans);
Example 7: Animate the model This example shows how animation data can be imported as .mtra files and used to animate your 3D model.
action = new ActionTable("http://localhost/example/DemoMIDP/action_01.mtra"); ... frame += action.getNumFrames(0)/10; if( frame >= action.getNumFrames(0) ){ frame = 0; } figure.setPosture(action, 0, frame); g3.renderFigure(figure, 0, 0, layout, effect);
Example 8: Animate with multiple animation files Using two different animation files isn't much harder than using just one. Just import the two files and choose which one to use each time the 3D model is rendered.
action[0] = new ActionTable("http://localhost/example/DemoMIDP/action_01.mtra"); action[1] = new ActionTable("/example/DemoMIDP/action_02.mtra"); ... case Canvas.KEY_NUM1: // action actNo = 1; frame = 0; break; ...
frame += action[actNo].getNumFrames(0)/10; if( frame >= action[actNo].getNumFrames(0) ){ frame = 0; actNo = 0; }
figure.setPosture(action[actNo], 0, frame); g3.renderFigure(figure, 0, 0, layout, effect);
Example 9: Show multiple 3D models Using multiple 3D models is just as easy as using multiple animation files on a single model. All you have to do is create a new figure instance from the new 3D model .mbac file and use it just as you did with the first one.
// One Figure created from a mbac file... figure = new Figure("http://localhost/example/DemoMIDP/test_model_robo.mbac"); mainTexture = new Texture("http://localhost/example/DemoMIDP/tex_001.bmp", true); figure.setTexture(mainTexture);
//... And another Figure created from another mbac file. figureBg = new Figure("http://localhost/example/DemoMIDP/test_model_haikei.mbac");
Example 10: Draw with primitives Even if Micro3D v3 is primarily used with models pre-built using a 3D modeling program, you can make it draw 3D graphics directly from primitives using an array of commands:
// Use this array of commands to show a triangle with texture.... static int[] command = { Graphics3D.COMMAND_LIST_VERSION_1_0, Graphics3D.PRIMITVE_TRIANGLES | Graphics3D.PDATA_NORMAL_PER_FACE | Graphics3D.PDATA_TEXURE_COORD | Graphics3D.PATTR_LIGHTING | Graphics3D.PATTR_SPHERE_MAP | Graphics3D.PATTR_BLEND_HALF | (1<<16), // Nbr of primitives, in this case just one triangle 0, 0, 0, // The triangle's ccordinates 200, 0, 0, 0, 200, 0, 0, 0, 4096, // The Normal 0,255,255,255, 0, 0, // The coordinates for the texture Graphics3D.COMMAND_END, }; ...
protected void paint(Graphics g) { ... g3.drawCommandList( mainTexture, 0, 0, layout, effect, command); ... }
|