Personalize
Lição 18 de 18 do curso Jogo de Unity: Defesa de Torres da Coddy.
O jogo precisa de um final. Você perde quando as vidas chegam a 0 e vence quando todas as ondas tiverem sido enviadas e não houver mais nenhum inimigo no tabuleiro. O spawner sabe quando a última onda foi enviada, e Enemy.All sabe quantos inimigos restam, então o spawner espera o tabuleiro ficar vazio e, em seguida, dispara um evento ao qual o GameManager está inscrito. Uma coroutine espera por uma condição usando WaitUntil, que verifica uma lambda uma vez por frame. Uma sala de quebra-cabeça que abre sua saída quando todos os interruptores estão ligados:
yield return new WaitUntil(() => switchesOn == switches.Length);
exit.SetActive(true);Qualquer um dos finais mostra o EndPanel com uma mensagem e para o jogo com Time.timeScale = 0. As vidas nunca ficam abaixo de 0: um Tank que recebe 2 de dano quando resta 1 vida passaria direto por uma verificação de exatamente 0, então Mathf.Max mantém o valor em 0 ou mais.
Jogar Novamente carrega a cena outra vez. Time.timeScale não faz parte da cena e mantém seu valor após o carregamento, então um jogo parado em 0 começaria congelado outra vez: defina-o como 1 antes de carregar.
Agora, deixe o jogo com a sua cara. Tudo o que afeta o equilíbrio está no Inspector:
- GameManager do jogo:
startMoney(150) estartLives(20). - As
wavesdo Spawner, oito linhas com o tipo de inimigo, a quantidade e o espaçamento, etimeBetweenWaves(8). - Os assets EnemyData: velocidade, vida, recompensa e quantas vidas cada tipo consome. O Boss tem 450 de vida e consome 10.
- Os assets TowerData: custo, dano, alcance, cadência de tiro, os valores das melhorias, o dano em área do Cannon e a lentidão da torre Frost.
É possível vencer usando os valores padrão com uma defesa mista nas curvas do caminho, melhorada conforme o dinheiro chega; algumas torres de um só tipo não serão suficientes. Mude um número de cada vez e jogue para perceber o efeito.
Desafio
Difícil- Em
WaveSpawner, adicionepublic event Action AllWavesCleared. Depois que a última onda for enviada, aguarde até queEnemy.Allesteja vazio e, em seguida, dispare o evento. - Em
GameManager, adicione os campos serializadosendPanel(um GameObject) eendText(um TMP_Text). As vidas nunca ficam abaixo de 0 e, quando chegam a 0, o jogo termina comGame Over. Quando todas as ondas forem concluídas e ainda houver vidas, o jogo termina comYou Win!. Ao terminar, exiba o painel com a mensagem e definaTime.timeScalecomo 0. - Escreva
public void PlayAgain(), que será chamado pelo botão do painel: restaure o tempo ao normal e carregue novamente a cena ativa.
Pressione Play e defenda a base durante as oito ondas; depois, clique em Check. Em seguida, ajuste o jogo no Inspector e jogue do seu jeito.
Experimente você mesmo
using UnityEngine;
using TMPro;
public class GameManager : MonoBehaviour
{
[SerializeField] private int startMoney = 100;
[SerializeField] private int startLives = 20;
[SerializeField] private WaveSpawner spawner;
[SerializeField] private TMP_Text moneyText;
[SerializeField] private TMP_Text livesText;
[SerializeField] private TMP_Text waveText;
private int money;
private int lives;
void OnEnable()
{
Enemy.ReachedBase += OnReachedBase;
Enemy.Killed += OnKilled;
spawner.WaveStarted += ShowWave;
}
void OnDisable()
{
Enemy.ReachedBase -= OnReachedBase;
Enemy.Killed -= OnKilled;
spawner.WaveStarted -= ShowWave;
}
void Start()
{
money = startMoney;
lives = startLives;
ShowMoney();
ShowLives();
}
public bool TrySpend(int amount)
{
if (amount > money)
{
return false;
}
money -= amount;
ShowMoney();
return true;
}
public void Earn(int amount)
{
money += amount;
ShowMoney();
}
void OnKilled(Enemy enemy)
{
Earn(enemy.data.reward);
}
void OnReachedBase(Enemy enemy)
{
lives -= enemy.data.damage;
ShowLives();
}
void ShowMoney()
{
moneyText.text = "Money: " + money;
}
void ShowLives()
{
livesText.text = "Lives: " + lives;
}
void ShowWave(int wave, int total)
{
waveText.text = "Wave " + wave + "/" + total;
}
}
Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.