Nagrody
Lekcja 10 z 18 w kursie Gra Unity: Obrona wieżowa w Coddy.
Każdy wróg pokonany przez wieżę zapewnia nagrodę w postaci reward. Enemy zgłasza zabicie tak samo jak dotarcie do bazy: za pomocą zdarzenia statycznego Killed, a GameManager nasłuchuje go i dodaje pieniądze.
Zabicie musi być nagradzane tylko raz. Destroy nie usuwa obiektu od razu: następuje to na końcu klatki, a do tego czasu obiekt nadal jest w grze. Dwa strzały mogą trafić w tej samej klatce, a drugi trafia wroga z 0 punktów zdrowia, który nadal tam jest. Jeśli TakeDamage zgłasza zabicie za każdym razem, gdy zdrowie wynosi 0 lub mniej, drugi strzał przyznaje nagrodę ponownie. Gra w balony z lotkami ma tę samą pułapkę, którą można wyeliminować za pomocą bool:
public void Pop()
{
if (popped)
{
return;
}
popped = true;
Popped?.Invoke(this);
Destroy(gameObject);
}Wróg nie potrzebuje dodatkowego bool, ponieważ jego zdrowie już wskazuje, czy jest martwy: TakeDamage, które stwierdza, że zdrowie wynosi 0 lub mniej, nie ma już nic do zrobienia.
Wyzwanie
Średni- W
Enemyzadeklaruj publiczne statyczne zdarzenieKilled(Action<Enemy>). Wywołaj je, przekazując wroga, gdy TakeDamage zmniejszy jego zdrowie do 0 lub poniżej, tuż przed jego zniszczeniem. - Za zabicie przyznawana jest nagroda tylko raz: gdy TakeDamage zostanie wywołane dla wroga, którego zdrowie wynosi już 0 lub mniej, nic się nie dzieje.
- W
GameManagerdodajpublic void Earn(int amount), które zwiększa ilość pieniędzy i wyświetla ją. ZasubskrybujEnemy.Killedobok ReachedBase i przyznaj nagrodę za zabitego wroga w postaci jegoreward.
Naciśnij Graj i obserwuj, jak ilość pieniędzy rośnie, gdy wieże działają, a następnie naciśnij Sprawdź.
Spróbuj swoich sił
using System;
using System.Collections.Generic;
using UnityEngine;
public class Enemy : MonoBehaviour, IDamageable
{
public static readonly List<Enemy> All = new List<Enemy>();
public static event Action<Enemy> ReachedBase;
public EnemyData data;
public Transform[] waypoints;
private int next = 1;
private int health;
void Awake()
{
health = data.maxHealth;
}
void OnEnable()
{
All.Add(this);
}
void OnDisable()
{
All.Remove(this);
}
void Update()
{
Vector3 target = waypoints[next].position;
transform.position = Vector3.MoveTowards(transform.position, target, data.speed * Time.deltaTime);
if (transform.position == target)
{
next++;
if (next == waypoints.Length)
{
ReachedBase?.Invoke(this);
Destroy(gameObject);
}
}
}
public void TakeDamage(int amount)
{
health -= amount;
if (health <= 0)
{
Destroy(gameObject);
}
}
}
Ta lekcja zawiera krótki quiz. Zacznij lekcję, żeby na niego odpowiedzieć i śledzić swoje postępy.