🔷 My First Unity Game · Episode 3 of 8 · See All Episodes
🧱 Episode 3 · Beginner+ · Prefabs & Events

Prefab Power!
Unity Breakout

Breakout is Unity’s perfect prefab lesson: build one brick, stamp out fifty from code, wire up physics bounces, particle bursts and a proper game-state manager with restart.

👶 Ages 12+ ⏱️ ~2 Hours 🔷 Unity & C# ✓ Free
📦 Prefabs 🌀 Instantiate loops 🏓 Mouse paddle 💥 OnCollisionEnter2D Particle bursts 🔁 Scene reload
0 XP
Level 1
🔥0
Your Progress 0 / 6 steps
1
🏓
Court, Paddle & Mouse
New 2D project with a mouse-driven paddle
Active
🎯
Goal for this step

Set up the arena and a paddle that tracks the mouse.

  • 1New 2D project Breakout. Walls: three thin sprites with BoxCollider2D (left, right, top).
  • 2Paddle: square sprite scaled (1.6, 0.25), collider, and the script below.
  • 3Camera.main.ScreenToWorldPoint converts pixel mouse coordinates into world space, the conversion every engine needs (remember getBoundingClientRect in JS?).
  • 4Clamp x to the court and lock y. Play, silky mouse control.
PaddleMouse.cs
using UnityEngine;

public class PaddleMouse : MonoBehaviour
{
    void Update()
    {
        Vector3 world = Camera.main.ScreenToWorldPoint(Input.mousePosition);
        transform.position = new Vector3(
            Mathf.Clamp(world.x, -7f, 7f),
            -4.2f,
            0f);
    }
}
✏️
Fill in the Blanks
+15 XP
Pixel coordinates become world coordinates via Camera.main.. The paddle’s y is locked at while x follows the mouse.
🧠
Knowledge Check
+15 XP
Why must mouse input be converted before use?
AMice are analog
BInput.mousePosition is in SCREEN pixels; the game lives in world units, two different coordinate spaces
CC# requires Vector3
2
📦
The Brick Prefab
Build one brick, save it as a reusable asset
Locked
🎯
Goal for this step

Create a brick GameObject and turn it into a prefab.

  • 1Build ONE brick: sprite (scale 1.2×0.45), BoxCollider2D, and a Brick.cs script holding a points value and a colour setter.
  • 2Now the Unity superpower: drag the brick from the Hierarchy into the Project panel, it becomes a Prefab (blue icon), a saved template.
  • 3Delete the scene copy. The template lives on as an asset.
  • 4Edit the prefab → every future copy updates. One source of truth for every brick in every level.
Brick.cs
using UnityEngine;

public class Brick : MonoBehaviour
{
    public int points = 10;

    public void SetRow(int row, Color color)
    {
        points = (5 - row) * 10;
        GetComponent<SpriteRenderer>().color = color;
    }
}
✏️
Fill in the Blanks
+15 XP
A saved GameObject template is a , created by dragging from the Hierarchy into the panel. Editing the prefab updates copy.
🧠
Knowledge Check
+15 XP
Prefabs are Unity’s answer to which pattern from your earlier series?
AThe game loop
BThe object blueprint (GameMaker objects, C++ classes), define once, instantiate many
CScreen shake
3
🌀
Instantiate the Wall
Spawn 50 bricks from a loop at runtime
Locked
🎯
Goal for this step

Generate the whole wall from code using the prefab.

  • 1A WallBuilder script on an empty GameObject: nested loops calling Instantiate(brickPrefab, position, rotation).
  • 2Drag the prefab asset into the script’s public field, code meets assets.
  • 3Colour by row from a public Color array (editable in the Inspector, your palette is designer-tweakable).
  • 4Position maths: x from column, y from row, exactly like every wall you have built.
WallBuilder.cs
using UnityEngine;

public class WallBuilder : MonoBehaviour
{
    public Brick brickPrefab;
    public Color[] rowColors = new Color[5];

    void Start()
    {
        for (int row = 0; row < 5; row++)
        {
            for (int col = 0; col < 10; col++)
            {
                Vector3 pos = new Vector3(-6.75f + col * 1.5f,
                                           4f - row * 0.6f, 0f);
                Brick b = Instantiate(brickPrefab, pos, Quaternion.identity);
                b.SetRow(row, rowColors[row]);
                b.transform.parent = transform;   // tidy hierarchy
            }
        }
    }
}
⌨️
Code Challenge
+20 XP
Spawn one configured brick:
WallBuilder.cs
Brick b = (brickPrefab, pos, Quaternion.identity);
b.(row, rowColors[row]);
💡 Hint: Unity’s spawn function clones the prefab at a position; then the brick configures itself from its row.
🧠
Knowledge Check
+15 XP
b.transform.parent = transform; exists purely to…
AMake bricks bounce
BNest spawned bricks under the builder in the Hierarchy, organisation, not behaviour
CDouble the points
4
💥
Ball, Bounce & Brick Death
Physics ball plus OnCollisionEnter2D destruction
Locked
🎯
Goal for this step

Wire the ball’s physics and destroy bricks on contact.

  • 1Ball setup from Episode 1: Rigidbody2D (gravity 0, continuous), bouncy material, launched downward at start.
  • 2Ball script’s OnCollisionEnter2D: if we hit a Brick component, add its points and Destroy(brick.gameObject).
  • 3Paddle steering: on paddle contact, override the x velocity based on hit offset (the eternal spin), keeping overall speed constant with normalized * speed.
  • 4A speed clamp in FixedUpdate keeps physics honest (min 5, max 9).
Ball.cs
using UnityEngine;

public class Ball : MonoBehaviour
{
    public float speed = 6f;
    Rigidbody2D rb;

    void OnCollisionEnter2D(Collision2D hit)
    {
        Brick brick = hit.gameObject.GetComponent<Brick>();
        if (brick != null)
        {
            GameManager.Instance.AddScore(brick.points);
            Destroy(brick.gameObject);
        }

        if (hit.gameObject.CompareTag("Paddle"))
        {
            float offset = transform.position.x - hit.transform.position.x;
            Vector2 dir = new Vector2(offset * 1.2f, 1f).normalized;
            rb.linearVelocity = dir * speed;
        }
    }
}
✏️
Fill in the Blanks
+15 XP
Checking WHAT was hit uses <Brick>() and a null test. Removing the brick from the world is (brick.gameObject).
🧠
Knowledge Check
+15 XP
GetComponent<Brick>() returning null means…
AA bug
BThe thing we hit has no Brick component, it was a wall or paddle. Null IS the answer "not a brick"
CThe brick is empty
5
Particles & Juice
A ParticleSystem prefab bursts on every brick
Locked
🎯
Goal for this step

Add Unity’s particle system for brick-break explosions.

  • 1GameObject → Effects → Particle System. Configure a burst: Duration 0.3, Looping OFF, Start Speed 4, Start Size 0.12, Emission → Bursts → one burst of 15, Shape → Sphere.
  • 2Stop Action: Destroy, the effect cleans itself up. No manual lifetime code!
  • 3Prefab it, then Instantiate at the brick’s position on death (one line in the ball script).
  • 4Tint via the main module’s Start Color, pass the brick’s colour through.
  • 5Compare: JS particles = 40 lines of manual physics; Unity = a component you configure. Both worth knowing.
Ball.cs (addition)
public ParticleSystem burstPrefab;

// inside the brick-hit branch:
ParticleSystem burst = Instantiate(
    burstPrefab,
    brick.transform.position,
    Quaternion.identity);
var main = burst.main;
main.startColor = brick.GetComponent<SpriteRenderer>().color;
✏️
Fill in the Blanks
+15 XP
The particle system cleans itself up via Stop Action: . A one-off explosion uses a in the Emission module rather than continuous emission.
🧠
Knowledge Check
+15 XP
Configuring particles in the Inspector vs coding them by hand (your JS version) trades…
AQuality for speed
BFine control for speed and power, engines give you a Ferrari, hand-coding taught you how engines work
CNothing, they are identical
6
🔁
Game Manager & Scene Reload
Singleton scoring, lives, and one-line restart
Locked
🎯
Goal for this step

Finish with lives, win/lose states and a restart that just works.

  • 1GameManager with the singleton pattern (Instance) so any script reaches it without wiring, used sparingly, it is the community-standard manager pattern.
  • 2A bottom trigger zone costs a life and respawns the ball; zero lives → game over UI.
  • 3Win when no Brick components remain: FindObjectsByType<Brick>().Length == 0 (checked when bricks die).
  • 4Restart is gloriously lazy in Unity: SceneManager.LoadScene(SceneManager.GetActiveScene().name), the entire scene rebuilds itself, wall included (Start() runs again!).
GameManager.cs
using UnityEngine;
using UnityEngine.SceneManagement;

public class GameManager : MonoBehaviour
{
    public static GameManager Instance;
    void Awake() { Instance = this; }

    public void Restart()
    {
        Time.timeScale = 1f;
        SceneManager.LoadScene(
            SceneManager.GetActiveScene().name);
    }
}
⌨️
Code Challenge
+20 XP
Reload the current scene to restart everything:
GameManager.cs
SceneManager.(
    SceneManager.().name);
💡 Hint: One function loads a scene by name; the other asks which scene is currently running.
🧠
Knowledge Check
+15 XP
Reloading the scene restarts the game perfectly because…
AUnity saves your progress
BEverything respawns fresh and every Start() re-runs, including the wall builder. State reset for free
CIt clears the disk
🎉🏆🎮✨🎉
Workshop Complete!
Prefabs, Instantiate, particles and scene management, the core Unity production loop. Onwards to Episode 4: the top-down shooter!
0
Total XP
1
Level
0
Best Streak
0%
Accuracy
▶ Episode 4: Top-Down Shooter →
⭐ View My Progress & Certificates

This workshop was free and took many hours to build. If it helped you learn something new, consider supporting the project.

☕ Support on Ko-fi