Get Collision

Is there any way to check if an object collides with another? I tried using something from the help but I didn’t manage.

https://wiki.jmonkeyengine.org/legacy/doku.php/jme3:advanced:physics_listeners

Thanks wezrule. Didn’t think it was advanced :stuck_out_tongue:

OK, I created an empty .java file and put the following in:

[java]/*

  • To change this template, choose Tools | Templates
  • and open the template in the editor.

    */

    package Platform;



    import com.jme3.bullet.collision.PhysicsCollisionEvent;

    import com.jme3.bullet.collision.PhysicsCollisionListener;

    import com.jme3.bullet.control.RigidBodyControl;

    import com.jme3.scene.Spatial;



    public class MyCustomControl extends RigidBodyControl implements PhysicsCollisionListener {



    public void collision(PhysicsCollisionEvent event) {

    if (event.getNodeA().getName().equals(“player”)) {

    final Spatial node = event.getNodeA();

    System.out.println(“true”);

    } else if (event.getNodeB().getName().equals(“player”)) {

    final Spatial node = event.getNodeB();

    System.out.println(“true”);

    }

    }



    }

    [/java]



    After that, I called the following in the Main file



    [java]MyCustomControl x2 = new MyCustomControl();[/java]



    But now I am lost, as I can’t see anything in the tutorial about how to get the result if ObjectA collides with ObjectB. Any help please?

you also need to add the collisionListener to the physics space.

[java] bulletAppState.getPhysicsSpace().addCollisionListener(collisionlistener);[/java]

I added that, and I had to create the following field:

[java]private PhysicsCollisionListener collisionlistener;[/java]

When I run, the program closes immediately.



ERROR:





SEVERE: Uncaught exception thrown in Thread[LWJGL Renderer Thread,5,main]

java.lang.NullPointerException

at com.jme3.bullet.PhysicsSpace.distributeEvents(PhysicsSpace.java:350)

at com.jme3.bullet.BulletAppState.update(BulletAppState.java:177)

at com.jme3.app.state.AppStateManager.update(AppStateManager.java:143)

at com.jme3.app.SimpleApplication.update(SimpleApplication.java:238)

at com.jme3.system.lwjgl.LwjglAbstractDisplay.runLoop(LwjglAbstractDisplay.java:158)

at com.jme3.system.lwjgl.LwjglDisplay.runLoop(LwjglDisplay.java:203)

at com.jme3.system.lwjgl.LwjglAbstractDisplay.run(LwjglAbstractDisplay.java:221)

at java.lang.Thread.run(Thread.java:662)

BUILD SUCCESSFUL (total time: 4 seconds)

Well one way is to pass the bulletAppState reference as a constructor argument



[java]public MyCustomControl(BulletAppState bulletAppState) {

bulletAppState.getPhysicsSpace().addCollisionListener(this);

}[/java]

Is that regarding the error?

i guess

I put the code into the .java file and the following error came up.



SEVERE: Uncaught exception thrown in Thread[LWJGL Renderer Thread,5,main]

java.lang.NoSuchMethodError: Platform.MyCustomControl: method ()V not found

at Platform.Main.simpleInitApp(Main.java:75)

at com.jme3.app.SimpleApplication.initialize(SimpleApplication.java:218)

at com.jme3.system.lwjgl.LwjglAbstractDisplay.initInThread(LwjglAbstractDisplay.java:138)

at com.jme3.system.lwjgl.LwjglAbstractDisplay.run(LwjglAbstractDisplay.java:206)

at java.lang.Thread.run(Thread.java:662)



Could you tell me where to put each code, because I really think I put them in the wrong files? Thanks for your patience.

start here first:

java.lang.NoSuchMethodError: Platform.MyCustomControl: method ()V not found

OK, I solved that. I didn’t put bulletAppState in the brackets of Main.



Now I have this problem:



SEVERE: Uncaught exception thrown in Thread[LWJGL Renderer Thread,5,main]

java.lang.NullPointerException

at Platform.MyCustomControl.collision(MyCustomControl.java:20)

at com.jme3.bullet.PhysicsSpace.distributeEvents(PhysicsSpace.java:350)

at com.jme3.bullet.BulletAppState.update(BulletAppState.java:177)

at com.jme3.app.state.AppStateManager.update(AppStateManager.java:143)

at com.jme3.app.SimpleApplication.update(SimpleApplication.java:238)

at com.jme3.system.lwjgl.LwjglAbstractDisplay.runLoop(LwjglAbstractDisplay.java:158)

at com.jme3.system.lwjgl.LwjglDisplay.runLoop(LwjglDisplay.java:203)

at com.jme3.system.lwjgl.LwjglAbstractDisplay.run(LwjglAbstractDisplay.java:221)

at java.lang.Thread.run(Thread.java:662)



I’ll try to see where it went wrong.

well a java.lang.NullPointerException, means you are trying to use an object’s variables/methods, but it has not been initialized yet (it is null). A good thing to do is to use the debugger and set a breakpoint on the line where the error occurred if there are multiple object references there, so you can find out which one is null and work from there.

The collisionlistener I added above is null. What values can I give it? Could this be the problem?

Gave up trying to see what is wrong with it. I think the problem is with the variable collisionlistener because it is null. However, I don’t know what value to give it. If anyone can help me, I’d appreciate it.

[java]package Platform;

import com.jme3.bullet.BulletAppState;

import com.jme3.bullet.collision.PhysicsCollisionEvent;

import com.jme3.bullet.collision.PhysicsCollisionListener;

import com.jme3.bullet.control.RigidBodyControl;

import com.jme3.scene.Spatial;

/**

*

  • @author Mamo

    */

    public class MyCustomControl extends RigidBodyControl implements PhysicsCollisionListener{

    public void collision(PhysicsCollisionEvent event) {

    if (event.getNodeA().getName().equals("player")) {

    final Spatial node = event.getNodeA();

    System.out.println("true");

    } else if (event.getNodeB().getName().equals("player")) {

    final Spatial node = event.getNodeB();

    System.out.println("true");

    } else {

    System.out.println("false");

    }

    }

    public MyCustomControl(BulletAppState bulletAppState) {

    bulletAppState.getPhysicsSpace().addCollisionListener(this);

    }

    }

    [/java]

    [java]/**

    *@author Nicholas Mamo
  • Last Update: 8/9/11
  • Updates: Creation, Using SimpleLevel.java, Perfectionized collision, Added settings

    */

    package Platform;

    import com.jme3.app.SimpleApplication;

    import com.jme3.bullet.BulletAppState;

    import com.jme3.bullet.collision.PhysicsCollisionListener;

    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.CollisionResult;

    import com.jme3.collision.CollisionResults;

    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.light.AmbientLight;

    import com.jme3.light.DirectionalLight;

    import com.jme3.material.Material;

    import com.jme3.math.ColorRGBA;

    import com.jme3.math.Vector3f;

    import com.jme3.scene.Geometry;

    import com.jme3.scene.shape.Box;

    import com.jme3.system.AppSettings;

    public class Main extends SimpleApplication

    implements ActionListener {

    private Geometry green;

    private BulletAppState bulletAppState;

    private RigidBodyControl f;

    private PhysicsCollisionListener collisionlistener;

    private CharacterControl player;

    private Vector3f walkDirection = new Vector3f();

    private boolean left = false, right = false;

    private SimpleLevel l = new SimpleLevel();

    public static void main(String[] args){

    AppSettings settings=new AppSettings(true);

    settings.put("Width", 640);

    settings.put("Height", 480);

    settings.put("Title", "Platform");

    settings.put("VSync", true);

    settings.put("Samples", 4);

    Main app = new Main();

    app.setSettings(settings);

    app.setShowSettings(false);

    app.start();

    }

    public void simpleInitApp() {

    viewPort.setBackgroundColor(new ColorRGBA(0.7f,0.8f,1f,1f));

    bulletAppState = new BulletAppState();

    stateManager.attach(bulletAppState);

    flyCam.setEnabled(false);

    setUpKeys();

    CapsuleCollisionShape capsuleShape = new CapsuleCollisionShape(1f, 0f, 1);

    player = new CharacterControl(capsuleShape, 0.2f);

    player.setJumpSpeed(30);

    player.setFallSpeed(40);

    player.setGravity(30);

    player.setPhysicsLocation(new Vector3f(2, 10, 0));

    Box box2 = new Box( new Vector3f(0,0,0), 1f,1f,1f);

    green = new Geometry("Box", box2);

    Material mat2 = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");

    mat2.setColor("Color", ColorRGBA.Green);

    green.setMaterial(assetManager.loadMaterial( "Materials/Ground.j3m"));

    rootNode.attachChild(green);

    bulletAppState.getPhysicsSpace().add(player);

    bulletAppState.getPhysicsSpace().enableDebug(assetManager);

    PhysicsCollisionListener listen;

    bulletAppState.getPhysicsSpace().addCollisionListener(collisionlistener);

    MyCustomControl x2 = new MyCustomControl(bulletAppState);

    BlockCount bc = new BlockCount();

    int block;

    block = l.blocknumber;

    for (int i = 1; i < block; i++){

    float x = (l.b.xExtent);

    float y = (l.b.yExtent);

    float z = (l.b.zExtent);

    bc.Count(i, x, y, z);

    l.geom.setMaterial(assetManager.loadMaterial( "Materials/Ground.j3m"));

    CollisionShape sceneShape2 = CollisionShapeFactory.createMeshShape( l.geom);

    f = new RigidBodyControl(sceneShape2, 0);

    l.geom.addControl(f);

    rootNode.attachChild(l.geom);

    f.setCollisionGroup(2);

    bulletAppState.getPhysicsSpace().add(f);

    }

    DirectionalLight light = new DirectionalLight();

    light.setDirection(new Vector3f( -1f, -1f, -1f));

    light.setColor(ColorRGBA.White.mult(0.5f));

    rootNode.addLight( light );

    AmbientLight amb = new AmbientLight();

    amb.setColor(ColorRGBA.White.mult(1f));

    rootNode.addLight(amb);

    }

    private void setUpKeys() {

    inputManager.addMapping("Lefts", new KeyTrigger(KeyInput.KEY_A));

    inputManager.addMapping("Rights", new KeyTrigger(KeyInput.KEY_D));

    inputManager.addMapping("Jumps", new KeyTrigger(KeyInput.KEY_SPACE));

    inputManager.addListener(this, "Lefts");

    inputManager.addListener(this, "Rights");

    inputManager.addListener(this, "Jumps");

    }

    public void onAction(String binding, boolean value, float tpf) {

    if (binding.equals("Lefts")) {

    left = value;

    } else if (binding.equals("Rights")) {

    right = value;

    } else if (binding.equals("Jumps")){

    player.jump();

    }

    }

    @Override

    public void simpleUpdate(float tpf) {

    //System.out.println(player.getCollisionGroup());

    //player.addCollideWithGroup(2);

    Vector3f camLeft = cam.getLeft().clone().multLocal(0.5f);

    Vector3f pos = new Vector3f(player.getPhysicsLocation());

    walkDirection.set(0, 0, 0);

    camLeft.z = 0;

    ChaseCamera chasecam = new ChaseCamera(cam, green);

    chasecam.setDefaultHorizontalRotation(1.565f);

    chasecam.setDefaultVerticalRotation(0f);

    chasecam.setLookAtOffset(new Vector3f(0, 0, 0));

    chasecam.setChasingSensitivity(0f);

    chasecam.setDefaultDistance(50);

    green.addControl(chasecam);

    green.setLocalTranslation(player.getPhysicsLocation());

    if (left) {

    walkDirection.addLocal(camLeft);

    }

    if (right) {

    walkDirection.addLocal(camLeft.negate());

    }

    walkDirection.setZ(0f);

    player.setWalkDirection(walkDirection);

    if ((pos.z < -0.1f) || (pos.z >0.1f)){

    player.setPhysicsLocation(new Vector3f(pos.x, pos.y, 0));

    }

    if (pos.y < 0){

    player.setPhysicsLocation(new Vector3f(2, 2, 0));

    }

    if ((pos.y > 0) && (pos.y < 0.5)){

    player.setPhysicsLocation(new Vector3f(pos.x, 1, 0));

    }

    if ((pos.y < 0) && !(player.onGround())){

    player.setPhysicsLocation(new Vector3f(2, 1, 0));

    }

    }

    }[/java]

first of all remove:

[java]bulletAppState.getPhysicsSpace().addCollisionListener(collisionlistener);[/java]



you declared collisionlistener, but never assigned it a value, so its going to be null, and possibly interfere with the one you’ve already added in your customControl.



I really recommend you go back to learning java basics and then re-read all of the JME tutorials. Things are only going to get harder

1 Like

Using the try-catch for the exception, the error comes whenever the player collides.

On further debugging, the player is null :confused:

Finally solved the problem. I attached the Geometry (“green”) that is attached to the player with a Collision Shape. But there was still one problem; player had no name. Therefore, I used the following code:



[java]try{

System.out.println(event.getNodeB().getName());

System.out.println(event.getNodeA().getName());

} catch (NullPointerException e){

System.out.println(“Green”);

}[/java]



The only object that can move is “Green” (with player). Green updates its position after player, and thus player collides first. Therefore, when player collides, I output “Green” to know that player collided and thus the geometry. Thanks a lot @wezrule for providing me with that useful link.