About PhysicsCollisionListener and PhysicsCollisionGroupListener

public void collision(PhysicsCollisionEvent event) {
	Node node = new Node();

public boolean collide(PhysicsCollisionObject nodeA, PhysicsCollisionObject nodeB) {
	Node node = new Node();
	return false;

when the collide happened, the collision() is fune, but the collide() has exception:

java.lang.IllegalStateException: Scene graph is not properly updated for rendering.
State was changed after rootNode.updateGeometricState() call.
Make sure you do not modify the scene from another thread!
Problem spatial name: Root Node
at com.jme3.scene.Spatial.checkCulling(Spatial.java:360)
at com.jme3.renderer.RenderManager.renderSubScene(RenderManager.java:717)
at com.jme3.renderer.RenderManager.renderScene(RenderManager.java:710)
at com.jme3.renderer.RenderManager.renderViewPort(RenderManager.java:1096)
at com.jme3.renderer.RenderManager.render(RenderManager.java:1158)
at com.jme3.app.SimpleApplication.update(SimpleApplication.java:253)
at com.jme3.system.lwjgl.LwjglAbstractDisplay.runLoop(LwjglAbstractDisplay.java:151)
at com.jme3.system.lwjgl.LwjglDisplay.runLoop(LwjglDisplay.java:197)
at com.jme3.system.lwjgl.LwjglAbstractDisplay.run(LwjglAbstractDisplay.java:232)
at java.lang.Thread.run(Thread.java:748)

why are they different?

1 Like

This exception means that you’re modifying the scenegraph from someplace you shouldn’t be - either from another thread, or during the render phase. Make sure all scenegraph modifications (including attach()/detach()) happen only during the update phase. In particular, I believe the collide() method should not be altering the scenegraph as it’s intended for calculating whether or not two objects collide, not for receiving and reacting to the collision event.

1 Like

I’m guessing that bullet is running in parallel mode and you are editing the scene graph (rootNode.attachChild(node);) from this thread.

use the enqueue method on the SimpleApplication. This is the way to do scene graph manipulations from another thread.

top of my head:
getApplication().enqueue(() -> rootNode.attach(node));

1 Like

thanks. how about collision()? but it has too much event, so i want use collide() to filter.
Is there any better way?

Could you explain in higher detail what you want to accomplish? What are you trying to do?

1 Like

when my bullet hits an object, i want add some effects at the collision point.

You’re on the right track then - just check the event to see if one of the colliders is your bullet before triggering the effects.

Both listeners are used for different cases.

The #collision(PhysicsCollissionEvent event) is used to notify when a collision happened. The #collide(...) method is used before a collision will happen, and depending on the returned boolean value, bullet will process the collision. In your example, you are telling bullet that it should ignore the collision.

1 Like

it dose work, thanks

1 Like

actually, i need a function like (collision(PhysicsCollissionEvent event) with PhysicsCollisionGroupListener). I’m not sure if I said correctly, but if collision() could differentiate group,
that is what i want.