From 3a3a5de8c94dbf6cb8d8ecf555db4c7690678fc7 Mon Sep 17 00:00:00 2001 From: "roo..li" Date: Sat, 6 Aug 2011 09:42:51 +0000 Subject: [PATCH] Added javadoc, fixed tiny typo, reformatted sample a bit. git-svn-id: https://jmonkeyengine.googlecode.com/svn/trunk@7982 75d07b2b-3a1a-0410-a2c5-0572b91ccdca --- .../test/jme3test/input/TestCameraNode.java | 247 +++++++++--------- .../test/jme3test/input/TestChaseCamera.java | 192 +++++++------- 2 files changed, 216 insertions(+), 223 deletions(-) diff --git a/engine/src/test/jme3test/input/TestCameraNode.java b/engine/src/test/jme3test/input/TestCameraNode.java index 5ac72aa05..59a9360fc 100644 --- a/engine/src/test/jme3test/input/TestCameraNode.java +++ b/engine/src/test/jme3test/input/TestCameraNode.java @@ -1,39 +1,35 @@ /* - * Copyright (c) 2009-2010 jMonkeyEngine - * All rights reserved. - * + * Copyright (c) 2009-2010 jMonkeyEngine All rights reserved. + *

* Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are - * met: - * - * * Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * + * modification, are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + *

* * Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + *

* * Neither the name of 'jMonkeyEngine' nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED - * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, - * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, - * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR - * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF - * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING - * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + *

+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. */ package jme3test.input; -import com.jme3.app.SettingsDialog; import com.jme3.app.SimpleApplication; -import com.jme3.input.ChaseCamera; import com.jme3.input.KeyInput; import com.jme3.input.MouseInput; import com.jme3.input.controls.ActionListener; @@ -51,111 +47,112 @@ import com.jme3.scene.Node; import com.jme3.scene.control.CameraControl.ControlDirection; import com.jme3.scene.shape.Quad; import com.jme3.system.AppSettings; -import java.awt.event.KeyEvent; +/** + * A 3rd-person camera node follows a target (teapot). Follow the teapot with + * WASD keys, rotate by dragging the mouse. + */ public class TestCameraNode extends SimpleApplication implements AnalogListener, ActionListener { - private Geometry teaGeom; - private Node teaNode; - CameraNode camNode; - - public static void main(String[] args) { - TestCameraNode app = new TestCameraNode(); - AppSettings s = new AppSettings(true); - s.setFrameRate(100); - app.setSettings(s); - app.start(); + private Geometry teaGeom; + private Node teaNode; + CameraNode camNode; + boolean rotate = false; + Vector3f direction = new Vector3f(); + + public static void main(String[] args) { + TestCameraNode app = new TestCameraNode(); + AppSettings s = new AppSettings(true); + s.setFrameRate(100); + app.setSettings(s); + app.start(); + } + + public void simpleInitApp() { + // load a teapot model + teaGeom = (Geometry) assetManager.loadModel("Models/Teapot/Teapot.obj"); + Material mat = new Material(assetManager, "Common/MatDefs/Misc/ShowNormals.j3md"); + teaGeom.setMaterial(mat); + //create a node to attach the geometry and the camera node + teaNode = new Node("teaNode"); + teaNode.attachChild(teaGeom); + rootNode.attachChild(teaNode); + // create a floor + mat = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md"); + mat.setTexture("ColorMap", assetManager.loadTexture("Interface/Logo/Monkey.jpg")); + Geometry ground = new Geometry("ground", new Quad(50, 50)); + ground.setLocalRotation(new Quaternion().fromAngleAxis(-FastMath.HALF_PI, Vector3f.UNIT_X)); + ground.setLocalTranslation(-25, -1, 25); + ground.setMaterial(mat); + rootNode.attachChild(ground); + + //creating the camera Node + camNode = new CameraNode("CamNode", cam); + //Setting the direction to Spatial to camera, this means the camera will copy the movements of the Node + camNode.setControlDir(ControlDirection.SpatialToCamera); + //attaching the camNode to the teaNode + teaNode.attachChild(camNode); + //setting the local translation of the cam node to move it away from the teanNode a bit + camNode.setLocalTranslation(new Vector3f(-10, 0, 0)); + //setting the camNode to look at the teaNode + camNode.lookAt(teaNode.getLocalTranslation(), Vector3f.UNIT_Y); + + //disable the default 1st-person flyCam (don't forget this!!) + flyCam.setEnabled(false); + + registerInput(); + } + + public void registerInput() { + inputManager.addMapping("moveForward", new KeyTrigger(keyInput.KEY_UP), new KeyTrigger(keyInput.KEY_W)); + inputManager.addMapping("moveBackward", new KeyTrigger(keyInput.KEY_DOWN), new KeyTrigger(keyInput.KEY_S)); + inputManager.addMapping("moveRight", new KeyTrigger(keyInput.KEY_RIGHT), new KeyTrigger(keyInput.KEY_D)); + inputManager.addMapping("moveLeft", new KeyTrigger(keyInput.KEY_LEFT), new KeyTrigger(keyInput.KEY_A)); + inputManager.addMapping("toggleRotate", new MouseButtonTrigger(MouseInput.BUTTON_LEFT)); + inputManager.addMapping("rotateRight", new MouseAxisTrigger(MouseInput.AXIS_X, true)); + inputManager.addMapping("rotateLeft", new MouseAxisTrigger(MouseInput.AXIS_X, false)); + inputManager.addListener(this, "moveForward", "moveBackward", "moveRight", "moveLeft"); + inputManager.addListener(this, "rotateRight", "rotateLeft", "toggleRotate"); + } + + public void onAnalog(String name, float value, float tpf) { + //computing the normalized direction of the cam to move the teaNode + direction.set(cam.getDirection()).normalizeLocal(); + if (name.equals("moveForward")) { + direction.multLocal(5 * tpf); + teaNode.move(direction); } - - public void simpleInitApp() { - // Load a teapot model - teaGeom = (Geometry) assetManager.loadModel("Models/Teapot/Teapot.obj"); - - Material mat = new Material(assetManager, "Common/MatDefs/Misc/ShowNormals.j3md"); - teaGeom.setMaterial(mat); - //creating a node to attach the geometry and the camera node - teaNode = new Node("teaNode"); - teaNode.attachChild(teaGeom); - mat = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md"); - mat.setTexture("ColorMap", assetManager.loadTexture("Interface/Logo/Monkey.jpg")); - Geometry ground = new Geometry("ground", new Quad(50, 50)); - ground.setLocalRotation(new Quaternion().fromAngleAxis(-FastMath.HALF_PI, Vector3f.UNIT_X)); - ground.setLocalTranslation(-25, -1, 25); - ground.setMaterial(mat); - rootNode.attachChild(ground); - rootNode.attachChild(teaNode); - - - //creating the camera Node - camNode = new CameraNode("CamNode", cam); - //Setting the direction to Spatial to camera, this means the camera will copy the movements of the Node - camNode.setControlDir(ControlDirection.SpatialToCamera); - //attaching the camNode to the teaNode - teaNode.attachChild(camNode); - //setting the local translation of the cam node to move it away from the teanNode a bit - camNode.setLocalTranslation(new Vector3f(-10, 0, 0)); - //setting the camNode to look at the teaNode - camNode.lookAt(teaNode.getLocalTranslation(), Vector3f.UNIT_Y); - - - //disabling the flyCam (don't forget that!!) - flyCam.setEnabled(false); - - regsiterInput(); + if (name.equals("moveBackward")) { + direction.multLocal(-5 * tpf); + teaNode.move(direction); } - - public void regsiterInput() { - inputManager.addMapping("moveForward", new KeyTrigger(KeyInput.KEY_W)); - inputManager.addMapping("moveBackward", new KeyTrigger(KeyInput.KEY_S)); - inputManager.addMapping("moveRight", new KeyTrigger(KeyInput.KEY_D)); - inputManager.addMapping("moveLeft", new KeyTrigger(KeyInput.KEY_A)); - inputManager.addMapping("toggleRotate", new MouseButtonTrigger(MouseInput.BUTTON_LEFT)); - inputManager.addMapping("rotateRight", new MouseAxisTrigger(MouseInput.AXIS_X, true)); - inputManager.addMapping("rotateLeft", new MouseAxisTrigger(MouseInput.AXIS_X, false)); - inputManager.addListener(this, "moveForward", "moveBackward", "moveRight", "moveLeft"); - inputManager.addListener(this, "rotateRight", "rotateLeft", "toggleRotate"); + if (name.equals("moveRight")) { + direction.crossLocal(Vector3f.UNIT_Y).multLocal(5 * tpf); + teaNode.move(direction); } - boolean rotate = false; - Vector3f direction = new Vector3f(); - - public void onAnalog(String name, float value, float tpf) { - //computing the normalized direction of the cam to move the teaNode - direction.set(cam.getDirection()).normalizeLocal(); - if (name.equals("moveForward")) { - direction.multLocal(5 * tpf); - teaNode.move(direction); - } - if (name.equals("moveBackward")) { - direction.multLocal(-5 * tpf); - teaNode.move(direction); - } - if (name.equals("moveRight")) { - direction.crossLocal(Vector3f.UNIT_Y).multLocal(5 * tpf); - teaNode.move(direction); - } - if (name.equals("moveLeft")) { - direction.crossLocal(Vector3f.UNIT_Y).multLocal(-5 * tpf); - teaNode.move(direction); - } - if (name.equals("rotateRight") && rotate) { - teaNode.rotate(0, 5 * tpf, 0); - } - if (name.equals("rotateLeft") && rotate) { - teaNode.rotate(0, -5 * tpf, 0); - } - + if (name.equals("moveLeft")) { + direction.crossLocal(Vector3f.UNIT_Y).multLocal(-5 * tpf); + teaNode.move(direction); + } + if (name.equals("rotateRight") && rotate) { + teaNode.rotate(0, 5 * tpf, 0); + } + if (name.equals("rotateLeft") && rotate) { + teaNode.rotate(0, -5 * tpf, 0); } - public void onAction(String name, boolean keyPressed, float tpf) { - //toggling rotation on or off - if (name.equals("toggleRotate") && keyPressed) { - rotate = true; - inputManager.setCursorVisible(false); - } - if (name.equals("toggleRotate") && !keyPressed) { - rotate = false; - inputManager.setCursorVisible(true); - } + } + public void onAction(String name, boolean keyPressed, float tpf) { + //toggling rotation on or off + if (name.equals("toggleRotate") && keyPressed) { + rotate = true; + inputManager.setCursorVisible(false); } + if (name.equals("toggleRotate") && !keyPressed) { + rotate = false; + inputManager.setCursorVisible(true); + } + + } } diff --git a/engine/src/test/jme3test/input/TestChaseCamera.java b/engine/src/test/jme3test/input/TestChaseCamera.java index 459b74547..04b528f7e 100644 --- a/engine/src/test/jme3test/input/TestChaseCamera.java +++ b/engine/src/test/jme3test/input/TestChaseCamera.java @@ -5,7 +5,7 @@ * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are * met: - * + * * * Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * @@ -33,125 +33,121 @@ package jme3test.input; import com.jme3.app.SimpleApplication; import com.jme3.input.ChaseCamera; -import com.jme3.input.KeyInput; -import com.jme3.input.MouseInput; import com.jme3.input.controls.ActionListener; import com.jme3.input.controls.AnalogListener; import com.jme3.input.controls.KeyTrigger; -import com.jme3.input.controls.MouseButtonTrigger; import com.jme3.material.Material; import com.jme3.math.FastMath; import com.jme3.math.Quaternion; import com.jme3.math.Vector3f; import com.jme3.scene.Geometry; -import com.jme3.scene.Node; import com.jme3.scene.shape.Quad; -import java.awt.event.KeyEvent; +/** A 3rd-person chase camera orbits a target (teapot). + * Follow the teapot with WASD keys, rotate by dragging the mouse. */ public class TestChaseCamera extends SimpleApplication implements AnalogListener, ActionListener { - private Geometry teaGeom; - private ChaseCamera chaseCam; - private Node pivot; - - public static void main(String[] args) { - TestChaseCamera app = new TestChaseCamera(); - app.start(); + private Geometry teaGeom; + private ChaseCamera chaseCam; + + public static void main(String[] args) { + TestChaseCamera app = new TestChaseCamera(); + app.start(); + } + + public void simpleInitApp() { + // Load a teapot model + teaGeom = (Geometry) assetManager.loadModel("Models/Teapot/Teapot.obj"); + Material mat_tea = new Material(assetManager, "Common/MatDefs/Misc/ShowNormals.j3md"); + teaGeom.setMaterial(mat_tea); + rootNode.attachChild(teaGeom); + + // Load a floor model + Material mat_ground = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md"); + mat_ground.setTexture("ColorMap", assetManager.loadTexture("Interface/Logo/Monkey.jpg")); + Geometry ground = new Geometry("ground", new Quad(50, 50)); + ground.setLocalRotation(new Quaternion().fromAngleAxis(-FastMath.HALF_PI, Vector3f.UNIT_X)); + ground.setLocalTranslation(-25, -1, 25); + ground.setMaterial(mat_ground); + rootNode.attachChild(ground); + + // Disable the default first-person cam! + flyCam.setEnabled(false); + + // Enable a chase cam + chaseCam = new ChaseCamera(cam, teaGeom, inputManager); + + //Uncomment this to invert the camera's vertical rotation Axis + //chaseCam.setInvertVerticalAxis(true); + + //Uncomment this to invert the camera's horizontal rotation Axis + //chaseCam.setInvertHorizontalAxis(true); + + //Comment this to disable smooth camera motion + chaseCam.setSmoothMotion(true); + + //Uncomment this to disable trailing of the camera + //WARNING, trailing only works with smooth motion enabled. It is true by default. + //chaseCam.setTrailingEnabled(false); + + //Uncomment this to look 3 world units above the target + //chaseCam.setLookAtOffset(Vector3f.UNIT_Y.mult(3)); + + //Uncomment this to enable rotation when the middle mouse button is pressed (like Blender) + //WARNING : setting this trigger disable the rotation on right and left mouse button click + //chaseCam.setToggleRotationTrigger(new MouseButtonTrigger(MouseInput.BUTTON_MIDDLE)); + + //Uncomment this to set mutiple triggers to enable rotation of the cam + //Here spade bar and middle mouse button + //chaseCam.setToggleRotationTrigger(new MouseButtonTrigger(MouseInput.BUTTON_MIDDLE),new KeyTrigger(KeyInput.KEY_SPACE)); + + //registering inputs for target's movement + registerInput(); + + } + + public void registerInput() { + inputManager.addMapping("moveForward", new KeyTrigger(keyInput.KEY_UP), new KeyTrigger(keyInput.KEY_W)); + inputManager.addMapping("moveBackward", new KeyTrigger(keyInput.KEY_DOWN), new KeyTrigger(keyInput.KEY_S)); + inputManager.addMapping("moveRight", new KeyTrigger(keyInput.KEY_RIGHT), new KeyTrigger(keyInput.KEY_D)); + inputManager.addMapping("moveLeft", new KeyTrigger(keyInput.KEY_LEFT), new KeyTrigger(keyInput.KEY_A)); + inputManager.addMapping("displayPosition", new KeyTrigger(keyInput.KEY_P)); + inputManager.addListener(this, "moveForward", "moveBackward", "moveRight", "moveLeft"); + inputManager.addListener(this, "displayPosition"); + } + + public void onAnalog(String name, float value, float tpf) { + if (name.equals("moveForward")) { + teaGeom.move(0, 0, -5 * tpf); } - - public void simpleInitApp() { - // Load a teapot model - teaGeom = (Geometry) assetManager.loadModel("Models/Teapot/Teapot.obj"); - pivot = new Node("pivot"); - Material mat = new Material(assetManager, "Common/MatDefs/Misc/ShowNormals.j3md"); - teaGeom.setMaterial(mat); - pivot.attachChild(teaGeom); - mat = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md"); - mat.setTexture("ColorMap", assetManager.loadTexture("Interface/Logo/Monkey.jpg")); - Geometry ground = new Geometry("ground", new Quad(50, 50)); - ground.setLocalRotation(new Quaternion().fromAngleAxis(-FastMath.HALF_PI, Vector3f.UNIT_X)); - ground.setLocalTranslation(-25, -1, 25); - ground.setMaterial(mat); - pivot.attachChild(ground); - - // Disable the flyby cam - flyCam.setEnabled(false); - - // Enable a chase cam - chaseCam = new ChaseCamera(cam, teaGeom, inputManager); - - //Uncomment this to invert the camera's vertical rotation Axis - //chaseCam.setInvertVerticalAxis(true); - - //Uncomment this to invert the camera's horizontal rotation Axis - //chaseCam.setInvertHorizontalAxis(true); - - //Comment this to disable smooth camera motion - chaseCam.setSmoothMotion(true); - - //Uncomment this to disable trailing of the camera - //WARNING, trailing only works with smooth motion enabled and is the default behavior - //chaseCam.setTrailingEnabled(false); - - //Uncomment this to look 3 world units above the target - //chaseCam.setLookAtOffset(Vector3f.UNIT_Y.mult(3)); - - //Uncomment this to enable rotation when the middle mouse button is pressed (like Blender) - //WARNING : setting this trigger disable the rotation on right and left mouse button click - //chaseCam.setToggleRotationTrigger(new MouseButtonTrigger(MouseInput.BUTTON_MIDDLE)); - - //Uncomment this to set mutiple triggers to enable rotation of the cam - //Here spade bar and middle mouse button - //chaseCam.setToggleRotationTrigger(new MouseButtonTrigger(MouseInput.BUTTON_MIDDLE),new KeyTrigger(KeyInput.KEY_SPACE)); - - //registering inputs for target's movement - regsiterInput(); - - rootNode.attachChild(pivot); + if (name.equals("moveBackward")) { + teaGeom.move(0, 0, 5 * tpf); } - - public void regsiterInput() { - inputManager.addMapping("moveForward", new KeyTrigger(keyInput.KEY_UP)); - inputManager.addMapping("moveBackward", new KeyTrigger(keyInput.KEY_DOWN)); - inputManager.addMapping("moveRight", new KeyTrigger(keyInput.KEY_RIGHT)); - inputManager.addMapping("moveLeft", new KeyTrigger(keyInput.KEY_LEFT)); - inputManager.addMapping("displayPosition", new KeyTrigger(keyInput.KEY_P)); - inputManager.addListener(this, "moveForward", "moveBackward", "moveRight", "moveLeft"); - inputManager.addListener(this, "displayPosition"); + if (name.equals("moveRight")) { + teaGeom.move(5 * tpf, 0, 0); } - - public void onAnalog(String name, float value, float tpf) { - if (name.equals("moveForward")) { - teaGeom.move(0, 0, -5 * tpf); - } - if (name.equals("moveBackward")) { - teaGeom.move(0, 0, 5 * tpf); - } - if (name.equals("moveRight")) { - teaGeom.move(5 * tpf, 0, 0); - } - if (name.equals("moveLeft")) { - teaGeom.move(-5 * tpf, 0, 0); - - } + if (name.equals("moveLeft")) { + teaGeom.move(-5 * tpf, 0, 0); } - public void onAction(String name, boolean keyPressed, float tpf) { - if (name.equals("displayPosition") && keyPressed) { - teaGeom.move(10, 10, 10); + } + + public void onAction(String name, boolean keyPressed, float tpf) { + if (name.equals("displayPosition") && keyPressed) { + teaGeom.move(10, 10, 10); - } } + } - @Override - public void simpleUpdate(float tpf) { - super.simpleUpdate(tpf); + @Override + public void simpleUpdate(float tpf) { + super.simpleUpdate(tpf); - // teaGeom.move(new Vector3f(0.001f, 0, 0)); - // pivot.rotate(0, 0.00001f, 0); - // rootNode.updateGeometricState(); - } + // teaGeom.move(new Vector3f(0.001f, 0, 0)); + // pivot.rotate(0, 0.00001f, 0); + // rootNode.updateGeometricState(); + } // public void update() { // super.update(); //// render the viewports