2D Collision Reponses

Started by
4 comments, last by flyslasher 10 years, 3 months ago

Hi,

I understand without problem when 2 rectangles are colliding, (I'm talking here of a really basic collision system, with one static object and one dynamic) my problem is more about what do we do once we know there is collision.

I know basically that we cancel a part of the movement to bring the dynamic object the closest to the static object.

Here is an image to illustrate my question:

collis10.png

How do we know if we should bounce the dynamic object vertically or horizontally to correct the movement (e.g Falling on a platform, running the feet against a small wall)

I've been able to do algorithm that worked but they were to specific to special case and velocity.

I've read that we can check what is the shortest way to move the dynamic object out of collision, but what if we have a very small vertically velocity and a high horizontal velocity....

I hope I made the explanation of my problem clear.

Advertisement

There are different ways to solve this, but my suggestion is to use the simplest method.

Move your object on a single axis 1st, then check for collision (for example, y-axis 1st). If collision, then you know it happened because of vertical movement, and you can perform your response using only the y-axis (either it stops, or it bounces if it has elasticity).

Then you move the object in the x-axis and check for collisions and do the same.

This handles many general problems in platform games, like a player jumping and hitting a wall. You don't want your player to stop moving up and down when it hits a wall, but only stop moving on the x-axis.

Good luck and have fun!

My Gamedev Journal: 2D Game Making, the Easy Way

---(Old Blog, still has good info): 2dGameMaking
-----
"No one ever posts on that message board; it's too crowded." - Yoga Berra (sorta)

Separation y-axis and x-axis for checking collision... why I didn't think of that, I'll try that!

thanks!

It works great, thanks again for the help, sometime I don't think directly about the simplest solution to implement...

The problem with that approach is that it doesn't really take into account on which axis the collision happened first, meaning the player can be pushed out of a platform sideways instead of landing on top, depending if you check the X or Y axis first.

You probably won't notice it most of the time, except when you move diagonally onto a corner.

A way to fix this is to calculate the overlap first, then divide that by the objects velocity to find out which axis collided first, and then push it out in that direction.


float timeOfImpactX = std::numeric_limits<float>::infinity();
float timeOfImpactY = std::numeric_limits<float>::infinity();

if(dynamicBody.velocity.x != 0.0f) timeOfImpactX = GetRECTOverlapX(staticBodyRect, dynamicBodyRect) / dynamicBody.velocity.x;
if(dynamicBody.velocity.y != 0.0f) timeOfImpactY = GetRECTOverlapY(staticBodyRect, dynamicBodyRect) / dynamicBody.velocity.y;
if(timeOfImpactX < timeOfImpactY)
{
    // Solve X first
}
else
{
    // Solve Y
}

Something like that. I'm not sure myself if this is the best way but it's something to think about when your collision resolution feels weird when trying to land on the edge of a platform/tile.

This is just a thought, but it should do what you need to do if the math in my mind isn't hazed over from last night.

Using vectors you can calculate the distance from object 1 to object 2 and subtract the two distances from the origins of the objects to their respective edges. If it's less than 0, it means you are colliding and then use the overlapping vector components to calculate where you need to push the object away.

This topic is closed to new replies.

Advertisement