Menu
CoddyTech

One Script Runs the Game

Part of the Building Real Games section of Coddy's Unity journey. Lesson 12 of 60.

Put the score in the player's script, the lives in a health script and the game-over check in a third, and every script needs the others' numbers, so each new rule touches several files. Unity games usually give those numbers to one script, the GameManager, on an empty GameObject of its own. It owns the score, the lives and the rule that ends the game. Other scripts only report what happened, by calling its public methods. In this penalty shootout the net reports each goal:

public class GameManager : MonoBehaviour
{
    private int goals;
    private int shotsLeft = 5;

    public void ShotTaken(bool scored)
    {
        if (shotsLeft == 0) return;
        shotsLeft--;
        if (scored) goals++;
        Debug.Log("Goals: " + goals + ", shots left: " + shotsLeft);
        if (shotsLeft == 0) Debug.Log("Full time: " + goals + " goals");
    }
}
// Net.cs, on the goal's trigger
public GameManager game;

void OnTriggerEnter(Collider other)
{
    if (other.CompareTag("Ball")) game.ShotTaken(true);
}

The net does not know how many shots are left or when the game ends. It reports a goal, and the manager decides what that means; the keeper's script reports a save with game.ShotTaken(false). For a shootout of 3 shots you change one number in one script. The check at the top of ShotTaken stops a ball that rolls in after full time from counting.

You fill the game field in the Inspector by dragging the GameManager object onto it, and Unity finds the GameManager script on that object. The manager is also the place for the HUD: when it holds the score text and the game-over panel, the screen changes in the same method that changes the numbers, and no other script touches the UI.

challenge icon

Challenge

Easy

Let the GameManager keep score and lives.

  1. AddScore(int points): unless gameOver, add to score and show Score: 6 in scoreText.
  2. LoseLife(): take 1 off lives and show Lives: 2; at 0, set gameOver, show gameOverPanel, set player.enabled = false.
  3. In Gem and Bomb, when other.CompareTag("Player"), call game.AddScore(points) or game.LoseLife(), then Destroy(gameObject).

Press Play and hit three bombs. Then Check.

Try it yourself

using UnityEngine;
using TMPro;

public class GameManager : MonoBehaviour
{
    public TMP_Text scoreText;
    public TMP_Text livesText;
    public GameObject gameOverPanel;
    public Player player;
    private int score;
    private int lives = 3;
    private bool gameOver;

    public void AddScore(int points)
    {
        // add the points and show the new score, unless the game is over
    }

    public void LoseLife()
    {
        // take one life and show it; at 0 lives the game is over
    }
}

All lessons in Building Real Games

Practice on your own: Unity playground