Bounce

Once collision has happened, it is common to bounce off from the obstacle. It might be not too obvious when your head hits the wall (I dont recommend trying it, you only get headache), but looking at the things like ball it is quite easy to notice how the ball rarely continues moving through the obstacle or stops right near it.

Lets see how to find new movement vector after the collision has happened.

In the picture red line is movement vector, green is the wall (vector), black is normal of the wall and blue is new movement vector after the collision. Thick lines are projections of movement vector on the wall and on the walls normal.

Its quite obvious how original movement vector and new movement vector differ. Cant see it? Well, look at their projections. The projection on the wall is exactly same, but projection on the walls normal has opposite direction. From this we can easily create system for moving object to bounce off from the wall:
* find intersection point
* find projections of movement vector
* reverse projection on the normal
* add up projections

If you forgot what is projection or how to find it, look it up in the chapter3.

v1 is our movement vector. v2 is the wall (obstacle) vector. Left hand normal of v2:

v2.lx = v2.vy;
v2.ly = -v2.vx;

Dot product between v1 and v2:

dp1 = v1.vx*v2.vx + v1.vy*v2.vy;

projection of movement vector on the v2:

proj1.vx=dp1*v2.dx;
proj1.vy=dp1*v2.dy;

Dot product between v1 and v2 normal:

dp2 = v1.vx*v2.lx + v1.vy*v2.ly;

projection of movement vector on the v2 (notice how we need to divide left hand normal with length to use unit size vector):

proj2.vx=dp*(v2.lx/v2.len);
proj2.vy=dp*(v2.ly/v2.len);

reversing projection on the normal:

proj2.vx*=-1;
proj2.vy*=-1;

finding new movement vector by adding up projections:

v1.vx=proj1.vx+proj2.vx;
v1.vy=proj1.vy+proj2.vy;

In this example try to drag points and see how movement vector changes:

You can download the source fla.

Real bounce and friction

Same way as in real life no object can move forever because of friction and loss of energy, the bounce is not perfect in reality either. Perfect bounce happens when length of movement vector after the collision is exactly same as before the collision. We can take into account loss of energy in the bounce by assigning 2 variables to each object: "bounciness" and "friction":

ob.b=0.99;
ob.f=0.99;

When finding new movement vector we can now multiply each projection with the b and f of both objects. Bounciness affects the projection on the wall normal vector, friction affects the projection on the wall vector.

v1.vx=v1.f*v2.f*proj1.vx+v1.b*v2.b*proj2.vx;
v1.vy=v1.f*v2.f*proj1.vy+v1.b*v2.b*proj2.vy;

What if both objects have b and f equal to 1? Then we have perfect bounce - nothing is lost in the collision and movement continues with same strength. If for example the moving object or the wall have no bounce (b=0) then after the collision movement vector is parallel to the wall and object gets stick to the wall. Imagine the ball flying into tar or glue.

Of course you can also have bounce bigger then 1, in which case the collision would speed up movement. Good example of this might be bumpers in the pinball, when hit they give the ball extra speed.

In this example the point is moving in the stage with gravity and many walls. You can drag the endpoints of the walls.

Moving point loops through all the walls and checks if it will hit any of them in time that was passed since last check. If it would hit multiple walls, then the wall with closest intersection point is picked. Then the end point of object is set to intersection point and new movement vector is calculated. End point is then moved from intersection point to the direction of new vector substracting the value it took to get from original starting point to intersection point.

You can improve the system further with at least two ways:
1. Because object is drawn last time on screen at starting point p0 and next time at ending point p1 then human eye doesnt see it never go near the wall at intersection point ip. It might result to see object moving straight from p0 to p1. While not correct, sometimes the object is placed at the intersection point and whole screen is updated so the eye can see it hitting the wall.
2. It is possible for object to hit another wall after first wall. Currently only closest wall is bounced from. To be sure, you could start checking of collision with every wall over after new vector is found. Then you should only check for new vector from intersection point to p1 (blue in the picture).

You can download the source fla.

Next: Ball vs line.

Top