public void Update(DX11Game _game) { var game = TW.Graphics; if (movementDisabled) { frameMovement = Vector3.Zero; } if (velocity.LengthSquared() < 0.001f) { velocity = Vector3.Zero; } // Calculate component in the direction of the velocity if (frameMovement.LengthSquared() > 0.00001f) { var dot = Vector3.Dot(Vector3.Normalize(frameMovement), Vector3.Normalize(velocity)); if (dot < 0) { velocity -= velocity * 0.1f * -dot; frameMovement -= Vector3.Normalize(velocity) * Vector3.Dot(frameMovement, Vector3.Normalize(velocity)); } } if (velocity.LengthSquared() > 0.001f) { while (controllerHitReport.HitQueue.Count > 0) { var hit = controllerHitReport.HitQueue.Dequeue(); var frictionDot = Vector3.Dot(velocity, hit.WorldNormal); if (frictionDot > 0) { continue; // moving away from surface } var tangentVelocity = velocity - hit.WorldNormal * frictionDot; if (tangentVelocity.LengthSquared() < (1f * 1f)) { //Static friction velocity -= tangentVelocity; } else { //Dynamic friction velocity -= tangentVelocity * game.Elapsed; // this integrates the friction force. } } } controllerHitReport.HitQueue.Clear(); // This is bad practice ( 2-way dependancy ) (no clue what this means) player.Position = controller.Position.dx(); //Gravity var gravity = Vector3.Down * 10; if (!DisableGravity) { velocity += gravity * game.Elapsed; } frameMovement += velocity * game.Elapsed; var oldPos = controller.Position; controller.ReportSceneChanged(); // Apply fake gravity. Downward speed is constant. controller.Move(frameMovement); frameMovement = Vector3.Zero; // Clamp to 0 for now Vector3 position = controller.Position; if (position.Y < controller.Height + GroundHeight) { controller.Position = position + Vector3.UnitY * (controller.Height - position.Y + GroundHeight); } if (Math.Abs((controller.Position - oldPos).Y) < 0.001) { velocity.Y = 0; } player.Position = controller.Position.dx(); //Console.WriteLine(velocity); if (DisableGravity) { velocity = Vector3.Zero; // Apply infinite friction } }