Hello ! I used the HelloPicking example to make the following: I left click a spatial attached to a specific node to select it and then i right click anywhere on the terrain to place it there. It works fine with a cube but when i do this on the Oto model ,it doesnt work properly. It doesnt place the model where i want, but somewhere else. My code :
[java]package main;
import java.util.List;
import com.jme3.animation.AnimChannel;
import com.jme3.animation.AnimControl;
import com.jme3.animation.AnimEventListener;
import com.jme3.app.SimpleApplication;
import com.jme3.bullet.BulletAppState;
import com.jme3.bullet.collision.shapes.CapsuleCollisionShape;
import com.jme3.bullet.collision.shapes.CollisionShape;
import com.jme3.bullet.control.CharacterControl;
import com.jme3.bullet.control.RigidBodyControl;
import com.jme3.bullet.util.CollisionShapeFactory;
import com.jme3.collision.CollisionResults;
import com.jme3.font.BitmapText;
import com.jme3.input.ChaseCamera;
import com.jme3.input.KeyInput;
import com.jme3.input.controls.ActionListener;
import com.jme3.input.controls.KeyTrigger;
import com.jme3.input.controls.MouseButtonTrigger;
import com.jme3.light.AmbientLight;
import com.jme3.light.DirectionalLight;
import com.jme3.material.Material;
import com.jme3.math.ColorRGBA;
import com.jme3.math.Ray;
import com.jme3.math.Vector2f;
import com.jme3.math.Vector3f;
import com.jme3.scene.Geometry;
import com.jme3.scene.Node;
import com.jme3.scene.Spatial;
import com.jme3.scene.shape.Box;
public class Collision extends SimpleApplication
implements ActionListener, AnimEventListener{
AnimChannel shootingChannel;
AnimControl animationControl;
AnimChannel animationChannel;
float airTime = 0;
Spatial target;
private Spatial sceneModel;
Spatial servant1;
private BulletAppState bulletAppState;
private RigidBodyControl landscape;
private CharacterControl player3;
// private Vector3f walkDirection = new Vector3f();
private Node servants= new Node("servants");
private boolean left = false, right = false, up = false, down = false;
Node player;
public static void main(String[] args) {
Collision app = new Collision();
app.start();
}
public void simpleInitApp() {
/PLAYER*/
player = (Node) assetManager.loadModel("Models/Oto/Oto.mesh.xml");
player.setLocalScale(0.5f);
player.setLocalTranslation(1, 0, -10);
rootNode.attachChild(player);
//CAMERA*////////
this.getCamera().setLocation(new Vector3f(0, 256, 0));
this.flyCam.setMoveSpeed(100f);
this.viewPort.setBackgroundColor(new ColorRGBA(0.7f, 0.8f, 1f, 1f));
ChaseCamera chaseCam = new ChaseCamera(cam, player, inputManager);
chaseCam.setDefaultDistance(40);
chaseCam.setMinDistance(40);
viewPort.setBackgroundColor(new ColorRGBA(0.7f,0.8f,1f,1f));
flyCam.setEnabled(false);
flyCam.setDragToRotate(true);
/SERVANTS////
rootNode.attachChild(servants);
servants.attachChild(makeCube("a Dragon", -2f, 0f, 1f));
servant1 = assetManager.loadModel("Models/Oto/Oto.mesh.xml");
//ninja.scale(0.05f, 0.05f, 0.05f);
//servant1.rotate(0.0f, -3.0f, 0.0f);
// servant1.setLocalTranslation(6f, 0, -22.0f);
servant1.setLocalScale(0.5f);
servants.attachChild(servant1);
/ Set up Physics /
bulletAppState = new BulletAppState();
stateManager.attach(bulletAppState);
// We re-use the flyby camera control for rotation, while positioning is handled by physics
// initCrossHairs();
setUpKeys();
setUpLight();
setupAnimationController();
sceneModel = assetManager.loadModel("Models/terrain/terrain.obj");
sceneModel.setLocalTranslation(-10,-1,10);
CollisionShape sceneShape =
CollisionShapeFactory.createMeshShape((Node) sceneModel);
landscape = new RigidBodyControl(sceneShape, 0);
sceneModel.addControl(landscape);
CapsuleCollisionShape capsuleShape = new CapsuleCollisionShape(0.5f, 4.2f, 1);
player3 = new CharacterControl(capsuleShape, 0.05f);
player3.setJumpSpeed(20);
player3.setFallSpeed(50);
player3.setGravity(50);
player3.setPhysicsLocation(new Vector3f(10, 10, -10));
rootNode.attachChild(sceneModel);
bulletAppState.getPhysicsSpace().add(landscape);
bulletAppState.getPhysicsSpace().add(player3);
player.addControl(this.player3);
}
public void onAnimChange(AnimControl control, AnimChannel channel, String animName) {
}
public void onAnimCycleDone(AnimControl control, AnimChannel channel, String animName) {
if (channel == shootingChannel) {
channel.setAnim("stand");
}
}
private void setUpLight() {
// We add light so we see the scene
AmbientLight ambLight = new AmbientLight();
ambLight.setColor(ColorRGBA.White);
rootNode.addLight(ambLight);
DirectionalLight dl = new DirectionalLight();
dl.setColor(ColorRGBA.White);
dl.setDirection(new Vector3f(2.8f, -2.8f, -2.8f).normalizeLocal());
rootNode.addLight(dl);
}
/* We over-write some navigational key mappings here, so we can
- add physics-controlled walking and jumping: /
private void setUpKeys() {
inputManager.addMapping("Shoot", new MouseButtonTrigger(0)); // trigger 2: left-button click
inputManager.addMapping("GoTo", new MouseButtonTrigger(1));
inputManager.addListener(this, "Shoot");
inputManager.addListener(this, "GoTo");
inputManager.addMapping("Lefts", new KeyTrigger(KeyInput.KEY_A));
inputManager.addMapping("Rights", new KeyTrigger(KeyInput.KEY_D));
inputManager.addMapping("Ups", new KeyTrigger(KeyInput.KEY_W));
inputManager.addMapping("Downs", new KeyTrigger(KeyInput.KEY_S));
inputManager.addMapping("Jumps", new KeyTrigger(KeyInput.KEY_J));
inputManager.addListener(this, "Lefts");
inputManager.addListener(this, "Rights");
inputManager.addListener(this, "Ups");
inputManager.addListener(this, "Downs");
inputManager.addListener(this, "Jumps");
}
/* These are our custom actions triggered by key presses.
- We do not walk yet, we just keep track of the direction the user pressed. /
public void onAction(String binding, boolean keyPressed, float tpf) {
Vector3f camDir = cam.getDirection().clone().multLocal(0.2f);
Vector3f camLeft = cam.getLeft().clone().multLocal(0.2f);
camDir.y = 0;
camLeft.y = 0;
//THE PROBLEM I THINK ITS HERE**********///
if (binding.equals("GoTo") && !keyPressed && target!=null) {
Vector3f origin = cam.getWorldCoordinates(inputManager.getCursorPosition(),0.0f);
Vector3f direction = cam.getWorldCoordinates(inputManager.getCursorPosition(), 0.3f);
direction.subtractLocal(origin).normalizeLocal();
Ray mouseRay = new Ray(origin, direction);
CollisionResults results = new CollisionResults();
rootNode.collideWith(mouseRay, results);
if (results.size()>0){
Vector3f pt = results.getCollision(0).getContactPoint();
String hit = results.getCollision(0).getGeometry().getName();
System.out.println(pt+hit);
target.setLocalTranslation(pt);
target=null;
System.out.println(pt);
}else{
System.out.println("qq0");}
}
if (binding.equals("Shoot") && !keyPressed) {
Vector3f origin = cam.getWorldCoordinates(inputManager.getCursorPosition(), 0.0f);
Vector3f direction = cam.getWorldCoordinates(inputManager.getCursorPosition(), 0.3f);
direction.subtractLocal(origin).normalizeLocal();
Ray mouseRay = new Ray(origin, direction);
CollisionResults results = new CollisionResults();
servants.collideWith(mouseRay, results);
// 4. Print the results.
if (results.size()>0){
Vector3f pt = results.getCollision(0).getContactPoint();
target = results.getCollision(0).getGeometry();
System.out.println(pt);
//target=hit;
}else{
System.out.println("qq0");}
}
if (binding.equals("Lefts")) {
left = keyPressed;
} else if (binding.equals("Rights")) {
right = keyPressed;
} else if (binding.equals("Ups")) {
up = keyPressed;
} else if (binding.equals("Downs")) {
down = keyPressed;
} else if (binding.equals("Jumps")) {
player3.jump();
}
}
/**
- This is the main event loop–walking happens here.
- We check in which direction the player is walking by interpreting
- the camera direction forward (camDir) and to the side (camLeft).
- The setWalkDirection() command is what lets a physics-controlled player walk.
- We also make sure here that the camera moves with player.
*/
private final Vector3f walkDirection = new Vector3f();
private void setupAnimationController() {
animationControl = player.getControl(AnimControl.class);
animationControl.addListener(this);
animationChannel = animationControl.createChannel();
shootingChannel = animationControl.createChannel();
shootingChannel.addBone(animationControl.getSkeleton().getBone("uparm.right"));
shootingChannel.addBone(animationControl.getSkeleton().getBone("arm.right"));
shootingChannel.addBone(animationControl.getSkeleton().getBone("hand.right"));
}
@Override
public void simpleUpdate(float tpf) {
// System.out.println(player.getPhysicsLocation());
Vector3f camDir = cam.getDirection().clone().multLocal(0.2f);
Vector3f camLeft = cam.getLeft().clone().multLocal(0.2f);
camDir.y = 0;
camLeft.y = 0;
walkDirection.set(0, 0, 0);
if (left) {
walkDirection.addLocal(camLeft);
// servant1.lookAt(player.getLocalTranslation(),new Vector3f(1,1,1));
// servant1.setLocalTranslation(player.getLocalTranslation().x-2,1,player.getLocalTranslation().z-2);
}
if (right) {
walkDirection.addLocal(camLeft.negate());
}
if (up) {
walkDirection.addLocal(camDir);
}
if (down) {
walkDirection.addLocal(camDir.negate());
}
if (!this.player3.onGround()) {
airTime = airTime + tpf;
} else {
airTime = 0;
}
if (walkDirection.length() == 0) {
if (!"stand".equals(animationChannel.getAnimationName())) {
animationChannel.setAnim("stand", 1f);
}
} else {
this.player3.setViewDirection(walkDirection);
if (airTime > .3f) {
if (!"stand".equals(animationChannel.getAnimationName())) {
animationChannel.setAnim("stand");
}
} else if (!"Walk".equals(animationChannel.getAnimationName())) {
animationChannel.setAnim("Walk", 0.7f);
}
}
this.player3.setWalkDirection(walkDirection);
}
protected Geometry makeCube(String name, float x, float y, float z) {
Box box = new Box(new Vector3f(x, y, z), 1, 1, 1);
Geometry cube = new Geometry(name, box);
Material mat1 = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");
mat1.setColor("Color", ColorRGBA.randomColor());
cube.setMaterial(mat1);
return cube;
}
}[/java]
Am i doing something wrong?or is there a problem with the spesific model?