Background and Motivation
While using libbulletjme to develop a relatively complex physics system (a Minecraft mod with many dynamic rigid bodies and heavily nested CompoundShape structures), we encountered the need for fine-grained control over individual contact points (ManifoldPoint), specifically at the child-shape level.
The required capabilities include:
- Selectively cancelling specific contact points
- Or ideally preventing certain contact points from being created in the first place
However, the current API only provides:
setNoContactResponse() (rigid-body level, too coarse)
onContactProcessed (post-process stage, too late in the pipeline)
This makes it difficult to implement per-child-shape collision filtering in a robust and stable manner.
Current Approach
Our current workaround relies on onContactProcessed, attempting to “neutralize” contact points by modifying their properties:
ManifoldPoints.setFlags(manifoldPointId, 0);
ManifoldPoints.setAppliedImpulse(manifoldPointId, 0);
ManifoldPoints.setAppliedImpulseLateral1(manifoldPointId, 0);
ManifoldPoints.setAppliedImpulseLateral2(manifoldPointId, 0);
ManifoldPoints.setDistance1(manifoldPointId, 500f);
// or Float.MAX_VALUE
The intention is to force the solver to ignore these contacts by making the penetration distance positive.
Observed Issues
1. Noticeable jitter with complex CompoundShape
When using more complex CompoundShape configurations (multiple child shapes):
- Even after confirming that all relevant contact points are processed and assigned positive distances
- The system still exhibits unstable jitter
- The behavior resembles “contacts not being fully cancelled”
2. Sensitivity to callback complexity and execution timing
A strong correlation was observed:
- Minimal logic (setDistance1 + immediate return) → mostly stable
- Adding simple queries (e.g., getPositionWorld, getLocalPoint, getTriangleIndex) → jitter increases significantly
- More operations / later execution → worse instability
Example:
// Stable
ManifoldPoints.setDistance1(manifoldPointId, 500f);
return;
// Unstable (only additional queries)
ManifoldPoints.getPositionWorldOnB(worldContactPoint);
ManifoldPoints.getLocalPointB(localContactPoint);
ManifoldPoints.setDistance1(manifoldPointId, 500f);
This suggests that:
Accessing ManifoldPoint data through getters may introduce side effects (e.g., native synchronization or state refresh)
3. Cannot reliably reproduce in simplified test scenarios
A particularly confusing observation:
- In a simplified test setup derived from official examples (still using complex CompoundShape and the same ManifoldPoints operations)
- The issue does not reproduce
- Behavior remains stable
However, in the actual project (more dynamic and complex scene):
- The issue appears consistently
4. Distance value behaves inconsistently
Further testing shows:
This indicates:
The issue is not simply controlled by penetration distance thresholds, but likely involves manifold lifecycle or solver-stage interactions
Requested Features / Improvements
To address this class of problems, it would be extremely helpful to have one or more of the following:
1. Contact creation hook (strongly preferred)
Expose functionality similar to Bullet’s native:
Allowing:
- Rejecting a contact point at creation time
- Preventing it from entering the manifold entirely
2. NearCallback / narrowphase hook
Allow:
- Filtering at the child-shape pair level
- Cancelling contacts before they are added to manifolds
3. API to explicitly remove or disable a ManifoldPoint
For example:
removeManifoldPoint(manifoldPointId)
- Or marking it as disabled in a solver-safe way (not just modifying distance/impulse)
Note
This issue description was translated and refined with the assistance of AI.
Background and Motivation
While using libbulletjme to develop a relatively complex physics system (a Minecraft mod with many dynamic rigid bodies and heavily nested CompoundShape structures), we encountered the need for fine-grained control over individual contact points (ManifoldPoint), specifically at the child-shape level.
The required capabilities include:
However, the current API only provides:
setNoContactResponse()(rigid-body level, too coarse)onContactProcessed(post-process stage, too late in the pipeline)This makes it difficult to implement per-child-shape collision filtering in a robust and stable manner.
Current Approach
Our current workaround relies on
onContactProcessed, attempting to “neutralize” contact points by modifying their properties:The intention is to force the solver to ignore these contacts by making the penetration distance positive.
Observed Issues
1. Noticeable jitter with complex CompoundShape
When using more complex CompoundShape configurations (multiple child shapes):
2. Sensitivity to callback complexity and execution timing
A strong correlation was observed:
Example:
This suggests that:
3. Cannot reliably reproduce in simplified test scenarios
A particularly confusing observation:
However, in the actual project (more dynamic and complex scene):
4. Distance value behaves inconsistently
Further testing shows:
For simple CompoundShape:
setDistance1(0.01f)results in behavior similar to “partially cancelled contact” (minor jitter)For complex CompoundShape:
setDistance1(Float.MAX_VALUE)does not resolve the issueThis indicates:
Requested Features / Improvements
To address this class of problems, it would be extremely helpful to have one or more of the following:
1. Contact creation hook (strongly preferred)
Expose functionality similar to Bullet’s native:
gContactAddedCallbackAllowing:
2. NearCallback / narrowphase hook
Allow:
3. API to explicitly remove or disable a ManifoldPoint
For example:
removeManifoldPoint(manifoldPointId)Note
This issue description was translated and refined with the assistance of AI.