// Update is called once per frame void Update() { // TODO 1: Agents much separate from each other: // 1- Find other agents in the vicinity (use a layer for all agents) // 2- For each of them calculate a escape vector using the AnimationCurve // 3- Sum up all vectors and trim down to maximum acceleration Collider[] colliders = Physics.OverlapSphere(transform.position, search_radius, mask); Vector3 escapeVectorsSum = Vector3.zero; foreach (Collider col in colliders) { Debug.Log("Collision!"); Vector3 escapeVector = transform.position - col.transform.position; escapeVectorsSum += escapeVector; } escapeVectorsSum.y = 0; if (colliders.Length > 1) { escapeVectorsSum /= colliders.Length; } float t = escapeVectorsSum.magnitude / search_radius; float escapeForce = falloff.Evaluate(t); escapeVectorsSum.Normalize(); escapeVectorsSum *= escapeForce; if (escapeVectorsSum.magnitude > move.max_mov_acceleration) { escapeVectorsSum.Normalize(); escapeVectorsSum *= move.max_mov_acceleration; } if (escapeVectorsSum.magnitude > 0) { move.AccelerateMovement(escapeVectorsSum); } }
// Update is called once per frame void Update() { if (target_move) { // Create a vector that describes the ideal velocity Vector3 ideal_movement = transform.forward * target_move.movement.magnitude; // Calculate acceleration needed to match that velocity Vector3 acceleration = ideal_movement - move.movement; acceleration /= time_to_target; // Cap acceleration if (acceleration.magnitude > move.max_mov_acceleration) { acceleration.Normalize(); acceleration *= move.max_mov_acceleration; } move.AccelerateMovement(acceleration, priority); } }
// Update is called once per frame void Update() { // TODO 1: Agents much separate from each other: // 1- Find other agents in the vicinity (use a layer for all agents) Collider[] colliders = Physics.OverlapSphere(move.transform.position, search_radius, mask); // 2- For each of them calculate a escape vector using the AnimationCurve Vector3 TotalSum = Vector3.zero; foreach (Collider col in colliders) { Vector3 escape = (move.transform.position - col.transform.position); float distance = escape.magnitude; float factor = distance / search_radius; TotalSum += escape.normalized * move.max_mov_velocity * (1 - falloff.Evaluate(factor)); } // 3- Sum up all vectors and trim down to maximum acceleration move.AccelerateMovement(TotalSum); }
void Update() { if (target_move) { // TODO 5: First come up with your ideal velocity // then accelerate to it. Vector3 targetVel = target_move.movement; Vector3 newAcceleration = targetVel - move.movement; newAcceleration /= time_to_target; if (newAcceleration.magnitude > move.max_mov_acceleration) { newAcceleration.Normalize(); newAcceleration *= move.max_mov_acceleration; } move.AccelerateMovement(newAcceleration); } }
// Update is called once per frame void Update() { if (target_move) { // TODO 8: First come up with your ideal velocity // then accelerate to it. //similar to steeringArrive Vector3 ideal_velocity = target_move.movement; Vector3 accel = ideal_velocity - move.movement; accel = accel / time_to_accel; if (accel.magnitude > move.max_mov_acceleration) { accel = accel.normalized * move.max_mov_acceleration; } move.AccelerateMovement(accel); } }
// Update is called once per frame void Update() { Collider[] colliders = Physics.OverlapSphere(transform.position, search_radius, mask); Vector3 final = Vector3.zero; foreach (Collider col in colliders) { if (col.gameObject != this.gameObject) { GameObject go = col.gameObject; if (go == gameObject) { continue; } Vector3 diff = transform.position - go.transform.position; float distance = diff.magnitude; //float acceleration = (1.0f - falloff.Evaluate(distance / search_radius)) * move.max_mov_acceleration; float acceleration = (1 - distance / search_radius) * -move.max_mov_acceleration; if (acceleration < 0) { acceleration *= -move.max_mov_acceleration; } final += diff.normalized * acceleration; } float final_strength = final.magnitude; if (final_strength > 0.0f) { if (final_strength > move.max_mov_acceleration) { final = final.normalized * move.max_mov_acceleration; } final.y = 0; move.AccelerateMovement(final, priority); } } }
public void Steer(Vector3 target) { if (!move) { move = GetComponent <Move>(); } // TODO 3: Find the acceleration to achieve the desired velocity // If we are close enough to the target just stop moving and do nothing else // Calculate the desired acceleration using the velocity we want to achieve and the one we already have // Use time_to_target as the time to transition from the current velocity to the desired velocity // Clamp the desired acceleration and call move.AccelerateMovement() Vector3 diff = move.target.transform.position - transform.position; if (diff.magnitude < min_distance) { move.SetMovementVelocity(Vector3.zero); } else { float speedfactor = diff.magnitude / slow_distance; diff = (diff.normalized * move.max_mov_speed) * speedfactor; Vector3 current = move.movement; Vector3 accel = (diff - current) / time_to_accel; if (accel.magnitude > move.max_mov_acceleration) { accel = accel.normalized * move.max_mov_acceleration; } move.AccelerateMovement(accel); } //TODO 4: Add a slow factor to reach the target // Start slowing down when we get closer to the target // Calculate a slow factor (0 to 1 multiplier to desired velocity) // Once inside the slow radius, the further we are from it, the slower we go }
// Update is called once per frame void Update() { if (!move) { move = GetComponent <Move>(); } else { float angle = Mathf.Atan2(move.current_velocity.x, move.current_velocity.z); Quaternion q = Quaternion.AngleAxis(Mathf.Rad2Deg * angle, Vector3.up); foreach (my_ray ray in rays) { RaycastHit hit; if (Physics.Raycast(new Vector3(transform.position.x, transform.position.y + 1, transform.position.z), q * ray.direction.normalized, out hit, ray.length, mask) == true) { move.AccelerateMovement(new Vector3(transform.position.x, 0, transform.position.z) + hit.normal * avoid_distance, priority); } } } }
public void Steer(Vector3 target) { if (!move) { move = GetComponent <Move>(); } Vector3 direction = target - transform.position; //If the distance to the target is less than min_distance just stop moving if (direction.magnitude < min_distance) { move.SetMovementVelocity(Vector3.zero, priority); return; } //Find desired acceleration Vector3 desired_velocity = direction.normalized * move.max_mov_velocity; //Calculating the slow factor if (direction.magnitude < slow_distance) { desired_velocity *= (direction.magnitude / slow_distance); } Vector3 desired_accel = desired_velocity - move.movement[priority]; desired_accel /= time_to_target; //Clamp desired acceleration if (desired_accel.magnitude > move.max_mov_acceleration) { desired_accel = desired_accel.normalized * move.max_mov_acceleration; } move.AccelerateMovement(desired_accel, priority); }
public void Steer(Vector3 target) { if (!move) { move = GetComponent <Move>(); } // TODO 3: Create a vector to calculate our ideal velocity // then calculate the acceleration needed to match that velocity // before sending it to move.AccelerateMovement() clamp it to // move.max_mov_acceleration Vector3 currVel = target - transform.position; float distanceToTarget = currVel.magnitude; currVel.Normalize(); currVel *= move.max_mov_acceleration; Vector3 newAcceleration = currVel; if (distanceToTarget < slow_distance) { Vector3 idealVel = currVel.normalized * distanceToTarget * time_to_target; if (distanceToTarget < min_distance) { idealVel = Vector3.zero; } newAcceleration = idealVel - move.movement; } newAcceleration.y = 0; move.AccelerateMovement(newAcceleration); }
// Update is called once per frame void Update() { Collider[] colliders = Physics.OverlapSphere(transform.position, search_radius, mask); // collision data GameObject target = null; float target_shortest_time = float.PositiveInfinity; float target_min_separation = 0.0f; float target_distance = 0.0f; Vector3 target_relative_pos = Vector3.zero; Vector3 target_relative_vel = Vector3.zero; foreach (Collider col in colliders) { GameObject go = col.gameObject; if (go == gameObject) { continue; } Move target_move = go.GetComponent <Move>(); if (target_move == null) { continue; } // calculate time to collision Vector3 relative_pos = go.transform.position - transform.position; Vector3 relative_vel = target_move.current_velocity - move.current_velocity; float relative_speed = relative_vel.magnitude; float time_to_collision = Vector3.Dot(relative_pos, relative_vel) / relative_speed * relative_speed; // make sure there is a collision at all float distance = relative_pos.magnitude; float min_separation = distance - relative_speed * time_to_collision; if (min_separation > 2.0f * search_radius) { continue; } if (time_to_collision > target_shortest_time) { continue; } Debug.Log("Avoiding " + go.name); target = go; target_shortest_time = time_to_collision; target_min_separation = min_separation; target_distance = distance; target_relative_pos = relative_pos; target_relative_vel = relative_vel; } //if we have a target, avoid collision if (target != null) { Vector3 escape_pos; if (target_min_separation <= 0.0f || target_distance < search_radius * 2.0f) { escape_pos = target.transform.position - transform.position; } else { escape_pos = target_relative_pos + target_relative_vel * target_shortest_time; } move.AccelerateMovement(-(escape_pos.normalized * move.max_mov_acceleration)); } }