|Topic was automatically imported from the old Question2Answer platform.
I’m making a 3D platforming game.
The player character is a Kinematic Body.
I used the Kinematic Body’s is_on_floor() method to determine if the player is in contact with the ground while attempting to jump, or driving the state machine for playing animations.
I am constantly checking if the player is on the ground, and if not - I apply gravitational acceleration. However for whatever reason a toggle behaviour emerged where the player would alternate between -50 and 0 Y velocity, making him jitter on the ground and also loop in a landing animation, as the state machine things he’s constantly landing from a jump. This breaks the animations, but what’s worse - it makes jumping fail half of the times (if you happen to be pressing the jump button on a frame that the is_on_floor() gives false for.
I’ve tried to workaround the is_on_foor() method by using a raycast:
If it hits anything - the player is on the ground.
If it hits something and the hit normal is (0, 1, 0) - that means the player is standing on a perfectly flat surface, so there should be no gravitational pull applied.
Without that check the player is twitching while the Kinematic Body is constantly pushing into the ground, but also - if the player walks of a ledge, he’s got immediate downward velocity which is incorrect, and makes the player fall down much too fast.
Now, making this hack causes another twitches. So it barely solves one thing and break another one.
I’ve tried to aid the whole thing by adding another Area with a collider extending around the player’s feet - to detect if he’s in contact with the ground with a bit more lee-way.
I’ve set the collision masks so the Area is ignored by the Kinematic Body -however for some reason the player can’t jump at all and gets stuck above the ground like he’s standing on that extra Area.
I can’t seem to find a solution to this basic problem of player movement in a 3D space.
This is all because is_on_floor() seems to return true or false when the player rests on the ground, without apparent reason to failure.
Are there any known solutions to this problem?