320 likes | 423 Views
Intro to J2ME. Prog. 240- 571 , Semester 2, 200 6 -200 7. Objective s: to introduce M3G; to start talking about "M3G Chapter 2. An Animated Model" leave the floor, penguin, and animation details until next time. M3G. Part 1. 1. Features. M3G: the Mobile 3D Graphics API
E N D
Intro to J2ME. Prog. 240-571, Semester 2, 2006-2007 • Objectives: • to introduce M3G; • to start talking about "M3G Chapter 2. An Animated Model" • leave the floor, penguin, and animation details until next time M3G. Part 1
1. Features • M3G: the Mobile 3D Graphics API • developed as JSR-184 • present in WTK 2.2 and later • a combination of high-level and low-level features • retained and immediate modes • combined with J2ME via the Canvas or GameCanvas classes
No callbacks • No separate rendering thread • so you must code your own animation loop using a timer or a thread • Requires CLDC 1.1. for floats • make sure to select it in the WTK
Two Modes • Retained Mode (high-level API) • build a 3D scene by building a scene graph • the scene graph is rendered automatically • similar to Java 3D, but a much smaller API • and a few extras • Immediate Mode (low-level API) • based on OpenGL ES • no scene graph data structure
Scene Graph Example a World object is the top node World Group Camera Light Light Mesh Group Mesh Sprite
Mesh: a 3D model • subclasses: morphing mesh, skinned mesh • Sprite: a 2D image • A Group is a useful way of grouping objects so they can be transformed with a single operation. • Typical transformations: • scaling, rotation, translation • animation based on key frames
Mesh Details Appearance Mesh VertexBuffer Material composed of composed of IndexBuffer 1 or more PolygonMode Appearance 1 or more CompositingMode VertexBuffer positions VertexArray Fog composed of normals VertexArray Image2D 0 or 1 Texture2D 1 or more colours VertexArray 0 or 1 tex. coords. VertexArray 0 or more
2. WTK 2.2 Examples • Life3D • the Game of Life in 3D • PogoRoo • a kangaroo bouncing on a pogo stick • retainedmode • animates a skateboarder model • a M3D file
Hello World public class Test extends MIDlet { private MyCanvas c = new MyCanvas(); protected void startApp() {Display.getDisplay(this).setCurrent(c);} protected void pauseApp() {} protected void destroyApp() {} }
public class MyCanvas extends Canvas { private Graphics3D iG3D; // for rendering private World scene; // for the scene graph public MyCanvas() { iG3D = Graphics3D.create(); scene = (World)Loader.load(”/w.m3d”)[0]; } protected void paint(Graphics g) { iG3D.bindTarget(g); iG3D.render( scene ); iG3D.releaseTarget();// flush } }
Animated World public class Test extends MIDlet { MyCanvas c = new MyCanvas(); MyTimer updater = new MyTimer(); . . . private class MyTimer extends TimerTask { public MyTimer() {new Timer().schedule(this,0,40);} // 40ms public void run() { c.repaint(); } } }
public class MyCanvas extends Canvas { int time = 0; . . . protected void paint(Graphics g) { iG3D.bindTarget(g); scene.animate(time+=40);// 25 fps iG3D.render( scene ); iG3D.releaseTarget(); } }
3. M3G Chapter 2. An Animated Model • Make a penguin walk in circles http://fivedots.coe.psu.ac.th/~ad/jg/m3g2/
3.1. Features • Uses retained mode. • The scene includes a single directional light, a textured floor, a light blue background • or an image background • Mixes M3G rendering and MIDP's drawString() • Penguin model is an animated Mesh • it translates and rotates
AnimM3G Class Diagrams TimerTask MIDlet Canvas CommandListener
Scene Graph scene World scene graph children Background Light Camera Group animated Mesh transRotGroup floorMesh Mesh model built by the Floor class built by the AnimModel class
3.2. AnimCanvas Constructor private World scene; // global variable public AnimCanvas(...) { // ... other code scene = new World();buildScene(); // ... other code }
private void buildScene() // add nodes to the scene graph { addCamera(); addLight(); addBackground(); animModel = new AnimModel(); scene.addChild( animModel.getModelGroup() ); // add the model addFloor(); } // end of buildScene()
3.3. Adding the Camera private void addCamera() { Camera cam = new Camera(); float aspectRatio = ((float) getWidth()) / ((float) getHeight()); cam.setPerspective(70.0f, aspectRatio, 0.1f, 50.0f); cam.setTranslation(0.0f, 0.5f, 2.0f); // up and back // cam.setOrientation(-10.0f, 1.0f, 0, 0); // angle downwards slightly scene.addChild(cam); scene.setActiveCamera(cam); }
AnimM3G Viewed from Above cam.setTranslation(0.0f, 5.0f, 0.0f); cam.setOrientation(-90.0f, 1.0f, 0, 0);
3.4. Adding a Light private void addLight() { Light light = new Light(); // default white, directional light light.setIntensity(1.25f); // make it a bit brighter light.setOrientation(-45.0f, 1.0f, 0, 0); // down and into scene scene.addChild(light); }
3.5. Adding a Background private void addBackground() { Background backGnd = new Background(); backGnd.setColor(0x00bffe); // a light blue background scene.setBackground(backGnd); }
A Background Image private void addBackground() { Background backGnd = new Background(); Image2D backIm = loadImage("/clouds.gif"); // cloudy blue sky if (backIm != null) { backGnd.setImage(backIm); backGnd.setImageMode(Background.REPEAT, Background.REPEAT); } else backGnd.setColor(0x00bffe); // a light blue background scene.setBackground(backGnd); }
private Image2D loadImage(String fn) { Image2D im = null; try { im = (Image2D) Loader.load(fn)[0]; } catch (Exception e) { System.out.println( "Cannot make image from " + fn); } return im; } // end of loadImage()
3.6. Adding the Floor private void addFloor() { Image2D floorIm = loadImage("/bigGrid.gif"); // large, so slow to load Floor f = new Floor( floorIm, 8); //8 by 8 sz // Image2D floorIm = loadImage("/grass.gif"); // or try "/floor.png" // Floor f = new Floor( floorIm, 6);// 6 by 6 scene.addChild( f.getFloorMesh() ); }
3.7. Adding the Penguin // global for translating and rotating the model private Group transRotGroup; public AnimModel() { // other code ... Mesh model = makeModel(); // reposition the model's start position and size model.setTranslation(0.25f, 0.25f, 0.25f); // so at center model.scale(0.5f, 0.5f, 0.5f); // translation/rotation group for the model transRotGroup = new Group(); transRotGroup.addChild(model); // other code ... }
Changing the Penguin's Position Mesh model = makeModel(); // reposition the model's start position and size model.setTranslation(0.25f, 0.25f, 0.25f); // so at center model.scale(0.5f, 0.5f, 0.5f);
3.8. Updating the Application paint(){ // render the 3D scene // draw 2D info. string } AnimCanvas KVM repaintrequest update(){ // increment world time // call animate() on world // call repaint() } AnimCanvas update thecanvas AnimTimer (in AnimM3G) run(){ animCanvas.update(); } call run() everyPERIOD ms timer
AnimCanvas // global timing information private int appTime = 0; private int nextTimeToAnimate; public AnimCanvas(AnimM3G top) { // other code... // start the animation nextTimeToAnimate = scene.animate(appTime); } public void update() // called by TimerTask every PERIOD (50) ms { appTime++; if (appTime >= nextTimeToAnimate) { nextTimeToAnimate = scene.animate(appTime) + appTime; repaint(); } }
Rendering the Scene private Graphics3D iG3D; // global public AnimCanvas(AnimM3G top) { // other code... iG3D = Graphics3D.getInstance(); } protected void paint(Graphics g) { iG3D.bindTarget(g); try { iG3D.render(scene); } catch(Exception e) { e.printStackTrace(); } finally { iG3D.releaseTarget(); } // show the model's coordinates in MIDP g.drawString( animModel.getPosition(), 5,5, Graphics.TOP|Graphics.LEFT); } safer coding style