@Override
	public void run() {

		// Get some ship variables (must be final)
		final float mass = movableEntity.getMass();
		final Vect3D pos = new Vect3D(movableEntity.getPos());
		final Vect3D speed = new Vect3D(movableEntity.getSpeed());

		targetOffset.copy(target).substract(pos);

		if (targetOffset.modulus() == 0) {
			// TODO If we do not return there is a division by 0 somewhere below this point.
			// However, that's not clean.
			return;
		}

		normalizedTargetOffset.copy(targetOffset).normalize(1);
		speedOpposition.copy(normalizedTargetOffset).rotate(90).mult(speed.prodVectOnZ(normalizedTargetOffset));

		float cosSpeedToTO = 1;
		if (speed.modulus() != 0) {
			cosSpeedToTO = Math.abs(new Vect3D(speed).normalize(1).prodScal(normalizedTargetOffset));
		}

		// distance = length (target_offset)
		float distance = targetOffset.modulus();

		// Optimal slowing distance when cruising at MAX_SPEED before entering the slowing radius
		// Optimal slowing distance is computed for debugging purposes only
		slowingDistance = 0.00001f + (float) (Math.pow(speed.modulus(), 2) / (2 * movableEntity.getMaxSteeringForce() / mass * cosSpeedToTO));

		// Ramped speed is the optimal target speed modulus
		float rampedSpeed = (float) Math.sqrt(2 * movableEntity.getMaxSteeringForce() / mass * distance);
		// clipped_speed clips the speed to max speed
		float clippedSpeed = Math.min(rampedSpeed, movableEntity.getMaxSpeed());
		// desired_velocity would be the optimal speed vector if we had unlimited thrust
		desiredVelocity.copy(targetOffset).add(speedOpposition).mult(clippedSpeed / distance);

		steeringForce.copy(desiredVelocity).substract(speed).mult(mass);
		float factor = 1.35f;
		float sdmin = slowingDistance / factor;
		float sdmax = slowingDistance;
		float overdrive = 1.0f + speed.modulus() / rampedSpeed;
		if (distance > sdmax) {
			steeringForce.truncate(movableEntity.getMaxSteeringForce()); // / mass
		} else if (distance > sdmin) {
			float stModulus = steeringForce.modulus();
			steeringForce.normalize((distance - sdmin) / (sdmax - sdmin) * stModulus + (sdmax - distance)
					/ (sdmax - sdmin) * movableEntity.getMaxSteeringForce() * overdrive); // / mass
		} else {
			steeringForce.normalize(movableEntity.getMaxSteeringForce() * overdrive); // / mass
		}

		// stop condition
		if (new Vect3D(target).substract(pos).modulus() < 5 && speed.modulus() < 1 && movableEntity instanceof Ship) {
			movableEntity.removeBehavior(this);
		}
	}