Repository navigation
Description
Summary
The runtime physics simulation steps JoltScene (Scene::OnPhysics3DUpdate → m_JoltScene->Simulate(), Scene.cpp:1491), but JoltScene consumes only 3 of the ~20 PhysicsSettings fields. Gravity, fixed timestep, velocity/position solver iterations, Baumgarte, penetration slop, speculative-contact distance, restitution threshold, sleep thresholds, and the determinism / warm-start / manifold-reduction flags are silently ignored by the live simulation. They are applied only to Physics3DSystem::m_PhysicsSystem, a separate JPH::PhysicsSystem that is never stepped for the scene (Physics3DSystem::Update has no caller).
Net effect: a project that authors non-Earth gravity or tunes the solver gets the hardcoded defaults with no warning.
Evidence
JoltScene::InitializeJoltreads onlym_MaxBodies/m_MaxBodyPairs/m_MaxContactConstraintsfromPhysics3DSystem::GetSettings()(JoltScene.cpp:2521-2559), then hardcodes gravitym_JoltSystem->SetGravity(JPH::Vec3(0.0f, -9.81f, 0.0f))(JoltScene.cpp:2566) and never callsSetPhysicsSettings(...).JoltScene::m_FixedTimeStep = 1.0f / 60.0fis a hardcoded member (JoltScene.h:443), not read fromsettings.m_FixedTimestep.JoltScene::SetGravity(...)exists (JoltScene.cpp:262) but has no caller anywhere in the live path.Physics3DSystem::UpdatePhysicsSystemSettings()correctly applies gravity + all solver/sleep settings viam_PhysicsSystem->SetGravity(...)/m_PhysicsSystem->SetPhysicsSettings(...)(Physics3DSystem.cpp:486, 513) — but toPhysics3DSystem::m_PhysicsSystem, which the scene never simulates (Physics3DSystem::Update, Physics3DSystem.cpp:328, has no caller).
Reproduction
- Set
m_Gravity = {0, -3.71, 0}(Mars) in the project physics settings (persisted byProjectSerializer). - Press Play with any dynamic body.
- Bodies fall at 9.81 m/s², not 3.71. Likewise raising the velocity-solver iterations, lowering
m_PenetrationSlop, orm_AllowSleeping=falsehas zero effect on the live sim. Only the three buffer limits are honoured (which is exactly whatContactConstraintLimitsHonouredTestchecks — it never asserts gravity/solver).
Fix direction
In JoltScene::InitializeJolt, after m_JoltSystem->Init(...), apply the full PhysicsSettings: SetGravity(ToJolt(settings.m_Gravity)), SetPhysicsSettings(...) (mirror Physics3DSystem::UpdatePhysicsSystemSettings), and seed m_FixedTimeStep from settings.m_FixedTimestep. Then either retire the never-stepped Physics3DSystem::m_PhysicsSystem or document its role. Add a test asserting authored gravity/solver settings reach the live JoltScene (the current test only covers the 3 buffer limits).
Score
capability: 5
craft: 3
stability: 5
decay: 1
effort: 2
confidence: 1.0
learning: 2
fun: 3
kano: table-stakes
blocked_by: []
blocks: []
Rated per issue-scoring · score = confidence × (capability + craft + stability + decay) / effort, derived by the picker.
Activity
coderabbitai commentedon Jul 4, 2026
🔗 Related PRs
#78 - Feature/physics integration [closed]
#323 - feat(physics): springy (soft) hinge/slider joint limits via SpringSet… [merged]
#468 - feat(physics): wire Jolt HeightFieldShape into terrain collision (
#428) [merged]#484 - Feature/deterministic fixed timestep [merged]
#539 - fix(physics3d): route JoltScene through PhysicsSettings, fix contact-… [merged]
🧪 Issue enrichment is currently in open beta.
To disable automatic issue enrichment, add the following to your
.coderabbit.yaml:💬 Have feedback or questions? Drop into our discord!
drsnuggles8 commentedon Jul 4, 2026
PR opened: #556 —
JoltScene::InitializeJoltnow applies gravity, the full solver/sleepJPH::PhysicsSettingsblock, and the fixed timestep to the liveJoltScene::m_JoltSysteminstead of only reaching the never-steppedPhysics3DSystem::m_PhysicsSystem.Extended
ContactConstraintLimitsHonouredTest(rather than adding a new test file) with a settings-plumbing check and a runtime-behavior check (lunar vs. Earth gravity actually changes fall distance). Full physics test sweep (127 tests) passes with no regressions.Will auto-close on merge via "Fixes #540" in the PR description.