Menu
CoddyTech

Flächenschaden

Lektion 20 von 25 im Kurs Unity-Spiel: Tower Defense von Coddy.

Die Granate der Kanone explodiert dort, wo sie landet, und fügt jedem Gegner in der Nähe der Explosion Schaden zu, nicht nur ihrem Ziel. Physics.OverlapSphere(center, radius) gibt jeden Collider innerhalb von radius um center zurück: Gegner, aber auch den Boden und den Weg. Jeder Collider, der über ein IDamageable verfügt, erleidet den Schaden. Das Ziel ist eines davon, da die Granate auf ihm landet, also darf es nicht zusätzlich ein zweites Mal getroffen werden. Eine Bombe, die jede Kiste in ihrer Umgebung zurückstößt:

void Explode()
{
    foreach (Collider other in Physics.OverlapSphere(transform.position, blastRadius))
    {
        if (other.TryGetComponent(out Rigidbody body))
        {
            Vector3 away = (body.position - transform.position).normalized;
            body.AddForce(away * push, ForceMode.Impulse);
        }
    }
}

Der Explosionsradius ist Teil der Daten der Kanone, daher braucht ein Projektil jetzt mehr als nur eine Schadenszahl: Launch erhält auch die TowerData des Turms. Der Explosionsradius eines Pfeils beträgt 0, sodass seine Schüsse weiterhin nur ihr Ziel treffen. Der Schaden bleibt ein separates Argument, da er von der Stufe des Turms abhängt.

Eine Explosion zeigt dem Spieler, wo die Granate detoniert ist: eine durchsichtige Kugel, so breit wie der Explosionsradius, die nach einer Viertelsekunde verschwindet. Destroy(blast, 0.25f) zerstört sie nach dieser Verzögerung, ganz ohne eigenen Timer.

challenge icon

Aufgabe

Mittel

Kanonenkugeln explodieren und verletzen jeden Gegner in der Nähe.

  1. Füge in TowerData public float splashRadius; hinzu (CannonData legt den Wert auf 1.5 fest). Launch erhält ein drittes Argument, TowerData data, das der Turm übergibt.
  2. Bei der Ankunft erleidet jedes IDamageable in Physics.OverlapSphere(transform.position, data.splashRadius) einmal Schaden, wenn data.splashRadius > 0; andernfalls nur das Ziel.
  3. Zeige dann dort ein serialisiertes blastPrefab an, skaliert mit Vector3.one * data.splashRadius * 2f, und rufe Destroy(blast, 0.25f) auf.

Drücke „Spielen“: Eine Kanonenexplosion verletzt dicht gedrängte Grunts. Drücke dann „Prüfen“.

Probier es selbst

using UnityEngine;

public class Projectile : MonoBehaviour
{
    [SerializeField] private float speed = 12f;

    private Transform target;
    private int damage;

    public void Launch(Transform target, int damage)
    {
        this.target = target;
        this.damage = damage;
    }

    void Update()
    {
        if (target == null)
        {
            Destroy(gameObject);
            return;
        }

        transform.position = Vector3.MoveTowards(transform.position, target.position, speed * Time.deltaTime);
        if (transform.position == target.position)
        {
            if (target.TryGetComponent(out IDamageable damageable))
            {
                damageable.TakeDamage(damage);
            }
            Destroy(gameObject);
        }
    }
}

Alle Lektionen in Unity-Spiel: Tower Defense

Übe selbstständig: Unity-Playground