Learning Goals 3 min
By the end of this lesson you will be able to:
- Build an enemy patrol loop that walks, hits a black wall, turns 180° and walks back — no keyboard required.
- Add a lives variable and a player-side touching (Enemy v) ? check that subtracts a life and respawns the player.
- Trigger "game over" when lives hit zero with a broadcast + switch backdrop + stop [all v] chain.
Warm-Up — the maze that's too easy 7 min
You can reach the goal. You can collect the keys. The maze is a real game now — except it's too easy. Every player wins on their first try. Real games have things that try to stop you.
when flag clicked
go to x: (-200) y: (-150)
forever
if <key [right arrow v] pressed?> then
change x by (move-speed)
end
if <touching color [#000000] ?> then
set x to (last-good-x)
set y to (last-good-y)
end
if <touching color [#00ff00] ?> then
broadcast (win v)
end
end
Predict: we add a sprite that walks back and forth across one of the corridors. We don't add keyboard control to it. How does it know when to turn around?
Reveal the answer
The same way the player does — touching color [#000000] ?. The enemy walks forward, checks if it hit a wall, and turns 180° when it does. The enemy uses the exact same wall-detection pattern as the player, just with no keyboard branches.
Predict: the player touches the enemy. What's the smallest possible reaction that feels like a game (not just a notification)?
Reveal the answer
Three things in one if-then: subtract a life, snap the player back to the start position, and (optionally) pause briefly so the player can see they got hit. After a few hits, lives hit zero and the game ends. That's a real game-over loop — and it costs about eight blocks.
Today we add the danger. The maze is about to bite.
New Concept — autonomous sprites 15 min
So far every moving sprite in your game has been driven by keyboard input. Today we meet the first sprite that moves on its own. The same building blocks — forever, move, touching — but no key [] pressed? anywhere.
The minimum patrol
An enemy sprite needs three things: a way to move, a way to detect a wall, and a way to turn around. That's six blocks total.
when flag clicked
forever
move (2) steps
if <touching color [#000000] ?> then
turn cw (180) degrees
move (4) steps
end
end
The "move (4) steps after turn" matters. Without it, the enemy turns around but is still touching the wall — next frame it turns again, and again, and freezes spinning in place. The extra step pushes it clear of the wall before the next check.
Direction matters
Make sure each enemy starts pointed in the direction you want it to patrol. Click the sprite in the Stage, look at its direction in the sprite panel — 90 is right, −90 is left, 0 is up, 180 is down. Use point in direction (90) at the top of the script so the enemy starts patrol the same way every flag-click.
The player's reaction
Switch back to the player sprite. Add one more if-then inside the main forever — this one checks for touching the enemy, not a colour:
if <touching (Enemy v) ?> then
change [lives v] by (-1)
go to x: (-200) y: (-150)
wait (0.5) seconds
end
The game-over chain
Lives at zero needs its own check:
if <(lives) < (1)> then
broadcast (game-over v)
end
On the Stage, the matching receiver:
when I receive (game-over v)
switch backdrop to [Game Over v]
stop [all v]
Worked Example — one patrolling enemy 12 min
Open the L03-35 quest project. We'll add one enemy that walks a corridor, plus a lives counter, in seven steps.
Step 1 — Paint the enemy
Sprite panel → paint new sprite. Draw a small blobby creature in red (or any colour different from both the walls and the goal). Name it Enemy. Set its size to about 40 so it fits in the corridor.
Step 2 — Position and direction
Drag the Enemy in the Stage to a corridor where it can patrol back and forth without immediately getting stuck. In its scripts: when ⚑ clicked → go to x: () y: () (use the coordinates from where you placed it) → point in direction (90).
Step 3 — The patrol loop
Snap on the patrol stack from the concept section: forever containing move (2) steps, then an if <> then with touching color [#000000] ? in the diamond, with turn cw (180) degrees + move (4) steps inside.
Step 4 — Click the flag to verify
The enemy should walk back and forth across its corridor forever. If it spins in place, you forgot the extra-move-after-turn. If it walks off into a wall and freezes, your direction is wrong — re-aim it.
Step 5 — Make the lives variable
Variables → Make a Variable → lives → "For all sprites" → OK. Show it on the Stage (check the box) so the player can see how many lives they have.
Step 6 — Set lives at flag and check for enemy touch
On the player: at the top, add set [lives v] to (3) right after when ⚑ clicked. Inside the forever, add the touching-enemy if-then with life subtract + respawn + wait.
Step 7 — Game-over check + Stage receiver
Inside the same forever, add the if <(lives) < (1)> then + broadcast (game-over v). On the Stage: when I receive (game-over v) + switch backdrop to [Game Over v] + stop [all v]. (Paint a "Game Over" backdrop first.)
Click the flag. Walk into the enemy. You should lose a life and snap to the start. Do it three times — game over.
The full assembled stacks
when flag clicked
point in direction (90)
forever
move (2) steps
if <touching color [#000000] ?> then
turn cw (180) degrees
move (4) steps
end
end
when flag clicked
set [lives v] to (3)
go to x: (-200) y: (-150)
forever
if <key [right arrow v] pressed?> then
change x by (move-speed)
end
if <touching color [#000000] ?> then
set x to (last-good-x)
set y to (last-good-y)
end
if <touching (Enemy v) ?> then
change [lives v] by (-1)
go to x: (-200) y: (-150)
wait (0.5) seconds
end
if <(lives) < (1)> then
broadcast (game-over v)
end
end
What you just built: a sprite that acts on its own. The same minimum-AI pattern used in Pac-Man's ghosts, Super Mario's Goombas, and every kura-kura-shaped enemy in every platformer ever. Walk + sense + turn = patrol.
Try It Yourself — three enemy drills 15 min
Goal: Duplicate your Enemy sprite twice (right-click → duplicate). Now you have three patrols in three different corridors. Each one walks independently. Don't change the script — just position each clone in a different starting spot and point it differently.
when flag clicked
go to x: (50) y: (100)
point in direction (-90)
forever
move (2) steps
if <touching color [#000000] ?> then
turn cw (180) degrees
move (4) steps
end
end
Think: Why doesn't the player need any extra blocks to handle three enemies? Because touching (Enemy v) ? is true if the player touches any instance of the Enemy sprite (including duplicates). Duplicates inherit the same behaviour and the same name.
Goal: Make a "faster" enemy — same patrol pattern, but moves 4 steps at a time instead of 2. Position it on a long straight corridor (short corridors are unfair at this speed). Give it a different costume colour (purple, maybe) so the player can tell it apart from regular enemies.
when flag clicked
point in direction (90)
forever
move (4) steps
if <touching color [#000000] ?> then
turn cw (180) degrees
move (6) steps
end
end
Think: Why does speed-2 work with turn-step 4, but speed-4 needs turn-step 6? Because the bounce-away distance has to exceed how deep the enemy penetrated the wall on its last move. The faster you go, the deeper you embed before the check, the bigger the bounce.
Goal: Add an "alert" enemy. While it patrols normally, it checks if the player is within 100 pixels. If yes, it chases the player by pointing toward them. If not, it continues patrolling.
when flag clicked
forever
if <(distance to [Player v]) < (100)> then
point towards [Player v]
move (3) steps
if <touching color [#000000] ?> then
go to x: (50) y: (100)
end
else
move (2) steps
if <touching color [#000000] ?> then
turn cw (180) degrees
move (4) steps
end
end
end
Think: This is a 1990s arcade-style "smart enemy". The distance-check is a poor man's vision cone — real games use line-of-sight raycasting, but this approximation reads natural enough to be scary.
Mini-Challenge — the rolling Roti enemy 5 min
"Yusuf's spinning roti"
Yusuf made an enemy shaped like a roti canai that rolls across the kitchen maze. He's frustrated — the roti starts walking but freezes the moment it hits a wall, and never patrols back. He shows you this stack:
when flag clicked
point in direction (90)
forever
move (3) steps
if <touching color [#000000] ?> then
turn cw (180) degrees
end
end
Click the flag mentally. What does the roti actually do, and what one block does it need?
Reveal one valid solution
The roti walks 3 steps, hits the wall, turns 180° — but is still touching the wall, because turning doesn't move you. Next frame it checks again: still touching, turn 180° again. It spins in place forever, never escaping the wall.
The fix is one extra block: a move (5) steps right after the turn, to physically push the enemy away from the wall it just bumped into:
when flag clicked
point in direction (90)
forever
move (3) steps
if <touching color [#000000] ?> then
turn cw (180) degrees
move (5) steps
end
end
The bounce-back must be bigger than the penetration distance. If the enemy embedded 3 pixels into the wall (because the move step was 3), bouncing back 5 clears it. Detection without escape is just paralysis.
Recap 3 min
You built your first autonomous sprite — a ghost that walks the maze using the same touching color [#000000] ? pattern as the player, but with no keyboard input. The patrol is just forever + move + if <> then + turn + bounce-clear. The player gained a lives counter, a touching (Ghost v) ? check that subtracts a life and respawns, and a broadcast (game-over v) when lives hit zero. The maze is now a real game with stakes.
- Autonomous sprite
- A sprite that moves and reacts without keyboard or mouse input. Driven by its own forever loop and sensing blocks.
- Patrol
- The simplest autonomous behaviour: walk forward, hit a wall, reverse, walk back. The basis for every "guard" enemy in retro games.
- Bounce-clear step
- The extra move after a turn that physically moves the sprite away from what it just hit. Without it, the sprite gets stuck spinning at the wall.
- Lives counter
- A variable, usually visible on the Stage, that tracks how many hits the player can take. Reaches zero → game over.
- Respawn
- Teleporting the player back to a start position after losing a life. Use go to x: () y: () followed by a brief wait for invincibility.
- Game over
- The mirror of "win" — a broadcast that switches the backdrop and stops everything when the player has lost.
Homework 2 min
The Three-Enemy Maze. Make the kitchen dangerous.
- Open
HW-L3-35-Quest.sb3. Save asHW-L3-36-Patrol.sb3. - Create three enemies. Each one a duplicate of the first, positioned in a different corridor of the maze, pointed in a starting direction.
- Create a lives variable. Show it on the Stage. Set to 3 at flag.
- Add the touching-enemy check to the player: subtract a life, snap to start (go to x: (-200) y: (-150)), wait (0.5) seconds.
- Add the game-over check: if lives drop below 1, broadcast "game-over".
- Paint a "Game Over" backdrop. On the Stage, listen for "game-over" and switch + stop all.
Save and test: try to win the maze with all three enemies patrolling. Note how many lives you have left at the goal.
Bring back next class:
- The
.sb3file. - Your "best run" — finished the maze with how many lives left?
- One sentence answering: "Why does the enemy script use touching color [#000000] ? instead of if on edge, bounce?"
- One sentence answering: "What happens if you forget the wait (0.5) seconds after losing a life?"
Heads up for next class: SCR-L03-37 is the cluster project — the Top-Down Maze Game. You'll pull together the player controller, the keys-and-goal win system, and patrol enemies into one polished game with menu, levels, and a high-score record.