public void Init(SteeringAgent agent, SteeringController steering, RigidbodyMovementController physicsController) { this.agent = agent; this.steering = steering; this.physicsController = physicsController; pathManager = PathManager.Instance; TargetPosition = agent.transform.position + agent.transform.forward; racingLineProgress = pathManager.RacingLinePath.path.GetClosestProgressOnPath(agent.transform.position); }
private Vector3 GetAccelerationForPlayerAvoidance(ICollection <RigidbodyMovementController> targets) { Vector3 acceleration = Vector3.zero; // 1. Find the target that the character will collide with first // The first collision time float shortestTime = float.PositiveInfinity; // The first target that will collide and other data that we will need and can avoid recalculating RigidbodyMovementController firstTarget = null; float firstMinSeparation = 0; float firstDistance = 0; float firstRadius = 0; Vector3 firstRelativePos = Vector3.zero; Vector3 firstRelativeVel = Vector3.zero; foreach (RigidbodyMovementController target in targets) { // Calculate the time to collision Vector3 relativePos = controller.ColliderPosition - target.ColliderPosition; Vector3 relativeVel = controller.RealVelocity - target.RealVelocity; float distance = relativePos.magnitude; float relativeSpeed = relativeVel.magnitude; if (relativeSpeed == 0) { continue; } float timeToCollision = -1 * Vector3.Dot(relativePos, relativeVel) / (relativeSpeed * relativeSpeed); // Check if they will collide at all Vector3 separation = relativePos + relativeVel * timeToCollision; float minSeparation = separation.magnitude; if (minSeparation > controller.ColliderRadius + target.ColliderRadius + collisionDistanceOffset) { continue; } // Check if its the shortest if (timeToCollision > 0 && timeToCollision < shortestTime) { shortestTime = timeToCollision; firstTarget = target; firstMinSeparation = minSeparation; firstDistance = distance; firstRelativePos = relativePos; firstRelativeVel = relativeVel; firstRadius = target.ColliderRadius; } } // 2. Calculate the steering // If we have no target then exit if (firstTarget == null) { return(acceleration); } // If we are going to collide with no separation or if we are already colliding then steer based on current position if (firstMinSeparation <= 0 || firstDistance < controller.ColliderRadius + firstRadius + collisionDistanceOffset) { acceleration = controller.ColliderPosition - firstTarget.ColliderPosition; } // Else calculate the future relative position else { acceleration = firstRelativePos + firstRelativeVel * shortestTime; } // Avoid the target acceleration = controller.ConvertVector(acceleration); acceleration.Normalize(); acceleration *= steering.maxAcceleration; return(acceleration); }
public void Init(SteeringAgent agent, SteeringController steering, RigidbodyMovementController controller) { this.agent = agent; this.steering = steering; this.controller = controller; }
private void OnValidate() { physicsController = GetComponent <RigidbodyMovementController>(); }