godotengine / godot

Godot Engine – Multi-platform 2D and 3D game engine
https://godotengine.org
MIT License
91.52k stars 21.26k forks source link

RigidBody gets stuck on collision boundaries #46712

Open bluecorn745 opened 3 years ago

bluecorn745 commented 3 years ago

Godot version:

3.2.2-stable, 3.2.3-stable, 3.2.4rc3 (GodotPhysics), 4-4de0768cd (GodotPhysics3D and Bullet)

OS/device including version: Windows 10 20H2, Kubuntu 20.10

Issue description: When moving a RigidBody in character mode across a flat surface composed of one or more static collision bodies, it will frequently get stuck at the edges of triangles, convex hulls, and collision primitives, as if running into a wall at these points. Exactly which edges will be collided with in this way is difficult to predict, but the RigidBody still gets stuck very consistently. This issue occurs instead of #46596 if using GodotPhysics in the same scenario in 3.2, and happens with either physics engine in 4 (as of this morning).

Steps to reproduce:

  1. Create a RigidBody in character mode that can be moved around by the user
  2. Create a flat, static terrain with any type of collision shapes side-by-side (I used a GridMap)
  3. (In 3.2) Switch to GodotPhysics
  4. Enable "Visible Collision Shapes" option in the editor
  5. Run the scene, attempt to move your RigidBody around, and enjoy the glitch

Minimal reproduction project:

For 3.2: 3.2_godotphysics_sticky.zip For 4: StickyRigid_4_4de0768cd.zip (Arrow keys/space to jump move the RigidBody. Orange terrain is trimesh planes, red is trimesh cubes, yellow is convex cubes, green is BoxShapes. There are a couple different scenes with different sizes of character RigidBody)

e344fde6bf commented 3 years ago

This is probably happening because rigid bodies can phase through trimesh collision shapes.

https://user-images.githubusercontent.com/79001820/111020432-7c522200-8411-11eb-9c94-7b261bb2892f.mp4

The distance that they clip through the mesh gets worse as you increase the strength of gravity, this video was taken with gravity_scale=10. It still happens with gravity_scale=1 and default gravity values, it's just less severe.

Leakbang commented 2 years ago

This issue is still present in Godot 4 (v4.0.dev.calinou [e31138958]). The issue becomes very apparent with the box and cylinder collision shapes.

Gastronok commented 2 years ago

Oof. Had an idea for a very simple 3D game with voxel-based terrain. Thought a GridMap would be a great way to go about easily designing different areas. Can't even move across the floor.

Is Godot just not a good fit for simple voxel games?

bluecorn745 commented 2 years ago

@Gastronok that was basically what I was attempting to do when I first discovered this issue, and I've moved away from using Godot for that (and any project that requires marginally accurate physics, which is 99.9% of my projects)... so I agree with that assessment.

That being said, GridMap is actually a really cool/useful concept, and if the physics simulation was better it would be ideal for a voxel game.

On Thu, Jul 7, 2022, 9:40 PM Gastronok @.***> wrote:

Oof. Had an idea for a very simple 3D game with voxel-based terrain. Thought a GridMap would be a great way to go about easily designing different areas. Can't even move across the floor.

Is Godot just not a good fit for simple voxel games?

— Reply to this email directly, view it on GitHub https://github.com/godotengine/godot/issues/46712#issuecomment-1178542420, or unsubscribe https://github.com/notifications/unsubscribe-auth/ATB2M26NVRIIS4FSLJZXVTLVS6WMJANCNFSM4YWBZNLA . You are receiving this because you authored the thread.Message ID: @.***>

Calinou commented 2 years ago

Remember that for a voxel game (or a 2D pixel art game), writing your own physics from scratch in GDScript or C# is often an option. You typically only have to worry about AABB-style collisions, with no slopes or rigidbody-like behavior. This gives you perfectly stable physics behavior which will never be affected by physics bugs or regressions in the engine.

This kind of custom physics can even be done with fixed-point math to ensure determinism across machines (which is useful for rollback multiplayer).

As for the original issue, it can sometimes be worked around by setting the object's gravity scale to 0 when a collision with the floor is detected (e.g. using a raycast). This is what Quake 2 and onwards did to prevent sliding down slopes when not moving. See also Shifty's character movement manifesto.

StoreBoughtRocketGames commented 2 years ago

This is happening to me with Godot 4 Beta 5 using CharacterBody3D with trimesh objects. The only way I can get the character to not get stuck with trimesh collisions is to use a planar mesh. I tried a sort of hacky version of the raycast with a slight positive gravity when the character gets stuck, but there are still instances where the character can get stuck completely within the trimesh.

Has there been any movement on this, or any kind of workaround? With this issue, it's kind of a show stopper for my game. Means I can't use any kind of landscape with rolling hills, mountains, etc. Is that a correct statement? Thanks!

Gamepro5 commented 2 years ago

I'm fairly sure improper collision detection at trimesh edges cause this issue too. It can sometime cause a shape to clip straight through the trimesh. https://github.com/godotengine/godot/issues/69137

Gegbee commented 1 year ago

Can confirm that this is still happening in Godot 4 as of March 2nd, 2023.

Stinger8991 commented 1 year ago

Had this issue, though I can confirm this happened when normals are facing inside the model. Once the faces normals of the model being used to generate the collisions are flipped, issue resolved.

idchlife commented 1 year ago

Had this issue, though I can confirm this happened when normals are facing inside the model. Once the faces normals of the model being used to generate the collisions are flipped, issue resolved.

I'm having the cave-like structure. Did not help my case. Inverted trimesh doesn't allow even slightest movement from inside. Just pushes outside the whole trimesh. It seems ok in editor, though. Like it looks even similar to usual trimesh from flipped normals.

FeralBytes commented 1 year ago

I suspect that Godot is flipping the import from Blender. But I could be wrong. Anyways I over came this issue by choosing the collision shape and turning on back-face collisions. At that point the Tri-mesh collision worked as expected.

upost commented 5 months ago

I did some experiments for many hours when I ran into this issue and for me I got best results with: Godot 4.2 Jolt Physics GridMap cell size 4x4x4 In Physics settings, set maximum allowed penetration to 0.001 and default contact bias to 0.08 In the meshlib, for each meshInstance3d (created with Blender, imported from glb): create static trimesh body, delete the created collision object, then "create single convex collision neighbour" and make it child of the StaticBody3D. In some collision objects, I changed the margin to 0.01m. I avoided creating concave objects, but for them I used the "create multiple convex collision children" option. Note that you always need to make the collision objects childs of the staticBody3D. For the player, I use a CapsuleShape3D for collisions with margin set to 0.05.