What happens to controls after GeometryBatchFactory.optimize() called on parent?

Hi,

Can anybody explain what happens to RigidBodyControls added to spatials after calling GeometryBatchFactory.optimize() on their parent node?

They’re still in action after calling GeometryBatchFactory.optimize(), I mean they still behave exactly like if I never called GeometryBatchFactory.optimize() and I see them when I activate the mesh-like debugging material but I can’t get their object reference anymore from the rootNode tree, since all their attached spatials are now destroyed and replaced by a single geometry (the batched geometry).

I have a situation where I want to add RigidBodyControls to spatials that will be batched at some point, but I want to be able to destroy or move the RigidBodyControls, now they stay there forever because I don’t have any handle to interact with them anymore.

I’m guessing at the moment that one solution could be to make an ArrayList and put their object references there so that I can interact with them later on after calling GeometryBatchFactory.optimize() but what do you guys think? Anybody knows if and where they go in the rootNode tree after calling GeometryBatchFactory.optimize() on their parent node?

Those RigidBodies won’t work anymore though once all objects are batched. Either you should add a rigid body control to the merged object after batching, but it will act as a whole, either you should use the BatchNode. BatchNode allows the use of controls on individual geometries (see TestBatchNodeTower in the test repo).

RigidBodies are in the PhysicSpace, I guess you can get them from it (BulletAppState.getPhysicsSpace().getRigidBodyList()). The GeometryBatchFactory works at the mesh level and doesn’t manage the controls attached to geometries it’s batching.

1 Like
@nehon said: RigidBodies are in the PhysicSpace, I guess you can get them from it (BulletAppState.getPhysicsSpace().getRigidBodyList()).

That’s interesting, but how am I supposed to retrieve them if they have no name? (compared to spatials which do)

Am I right about making an array or a ConcurrentHashMap to store all those controls which will be batched at some point, so that I keep the handles to manipulate them?

EDIT: I remember trying BatchNode on a previous project and remember liking it. I will give it a try too! It may just be what I need after all.

BatchNode still allows you to manipulate objects and move them. It detects this and automatically updates its internal mesh to represent the moved objects. When a BatchNode is requested to render itself, it doesn’t actually render its children but instead the aforementioned batched mesh. This creates the illusion of individual objects rendered when in reality it is all one object.

Another alternative to BatchNode is the newly added jME3.1 InstancedNode which works similarly but instead uses special GPU functions to render the same object multiple times with different transforms. If supported by the GPU, InstancedNode is much more effective when there’s a large number of complex objects with constantly changing transforms (such as in the case of physics).

Oh yeah, InstancedNode shall be perfect for particles and such! :smiley: Looking forward to that feature too.

@.Ben. said: Oh yeah, InstancedNode shall be perfect for particles and such! :D Looking forward to that feature too.

Only if the particles have lots of triangles.

Instancing works well when you have bigger objects that you want to have lots of. But for smaller objects, batching is still better. With instancing, even though we are only submitting one draw call, the driver is internally still doing multiple draw calls. It’s faster than if we did it but still slower than batching when the objects are small.

@nehon said: Those RigidBodies won't work anymore though once all objects are batched. Either you should add a rigid body control to the merged object after batching, but it will act as a whole, either you should use the BatchNode. BatchNode allows the use of controls on individual geometries (see TestBatchNodeTower in the test repo).

RigidBodies are in the PhysicSpace, I guess you can get them from it (BulletAppState.getPhysicsSpace().getRigidBodyList()). The GeometryBatchFactory works at the mesh level and doesn’t manage the controls attached to geometries it’s batching.

They (the RigidBodyControls) still worked as expected once the objects were batched, but the problem was to keep track of them; it was a mess and I tried to go the route of making a ConcurrentHashMap but then I had other threads puting stuff in it as well and it ended up working not that great. I finally decided to go with BatchNode since the implementation is F*** ridiculous. All I had to do to was to rename Node n = new Node(“My node”); to BatchNode n = new BatchNode(“My node”); and later do n.batch(); and it keeps all the geometries culled so that all their RigidBodyControls are perfectly retrievable from the rootNode tree as expected under their original tree location, everything is as expected. I just wonder: would this system still be efficient if there were thousands of those culled geometries left behind by BatchNode, but since they’re culled, all it does is use a little bit of RAM. This will not be the case in this project anyways… at maximum 200 batched geometries at any given time, that’s it. Thanks Rémy. +1’ed you as this solved my issue. Thx everybody for participating.

Well batchNode has its tradeoffs though.
All the geometries are kept in the scene graph, that’s convenient for many things, but all the mesh data are doubled. Because you still have the original geometries in memory, along with the batched geometry. So basically you’ll consume more memory.

And as you underlined, batchNode makes culling inefficient if you batch an entire scene. Which can be worst than not batching and having culling. Usually you want to have some paging system, only batch subparts of the scene to have some macro culling still going on…

Anyway, glad it solved your issue :wink: