EDIT: A combination of Patrick Hughes' and teodron's answers solved the velocity problem (I think), thanks a lot! This is the new code:
I decided to use a separate recursion method now too since I don't want to recalculate the acceleration in each recursion.
public override void Update(double fixedTimeStep)
{
Acceleration.Zero();// = CalculateAcceleration(fixedTimeStep);
PreviousState = new MovingEntityState(CurrentState.Position, CurrentState.Velocity);
CurrentState = SlidingCollision(CurrentState, fixedTimeStep);
Heading = Vector2.NormalizeRet(CurrentState.Velocity);
}
private MovingEntityState SlidingCollision(MovingEntityState state, double timeStep)
{
bool collisionFound = false;
/* Calculate the next position given no detected collision. */
Vector2 futurePosition = state.Position + state.Velocity * timeStep;
Vector2 intersectionPoint = new Vector2();
Vector2 intersectionPointNormal = new Vector2();
/* I did not include the collision detection code, if a collision is detected the intersection point and normal in that point is returned. */
/* If no collision was detected it is safe to move to the future position. */
if (!collisionFound)
return new MovingEntityState(futurePosition, state.Velocity);
/* Set new position to the intersection point (slightly before). */
Vector2 newPosition = intersectionPoint;
/* Project the new velocity along the intersection normal. */
Vector2 newVelocity = state.Velocity - 1.90 * intersectionPointNormal * state.Velocity.DotProduct(intersectionPointNormal);
/* Calculate the time of collision. */
double timeOfCollision = Math.Sqrt((newPosition - state.Position).LengthSq() / (futurePosition - state.Position).LengthSq());
/* Calculate new time step, remaining time of full step after the collision * current time step. */
double newTimeStep = timeStep * (1 - timeOfCollision);
return SlidingCollision(new MovingEntityState(newPosition, newVelocity), newTimeStep);
}
Even though the code above seems to slide the puck correctly please have a look at it.
I have a few questions, if I don't multiply by 1.90 in the newVelocity calculation it doesn't work (I get a stack overflow when the puck enters the corner because the timeStep decreases very slowly -> a collision is found early in every recursion), why is that? what does 1.90 really do and why 1.90?
Also I have a new problem, the puck does not move parallell to the short side after exiting the curve; to be more exact it moves outside the rink (I am not checking for any collisions with the short side at the moment). When I perform the collision detection I first check that the puck is in the correct quadrant. For example bottom-right corner is quadrant four i.e. circleCenter.X < puck.X && circleCenter.Y > puck.Y is this a problem? or should the short side of the rink be the one to make the puck go parallell to it and not the last collision in the corner?