A number that counts down limits a power-up, and the event checks it first, so it never goes below zero.
Ammo, fuel, a shield that flickers out: the best power-ups run out. Behind each one is a number counting down.
A power-up that runs out needs a number: shots left, seconds left. Each use takes 1 away. The ship says how many shots are left after each one.
Make your prediction first. Help opens once you've locked it in.

let shot: Sprite = null
let rock: Sprite = null
let ammo = 3
scene.setBackgroundColor(15)
let ship = sprites.create(img`
8 8 . . . . . .
8 9 9 9 9 . . .
8 9 1 1 9 9 9 9
8 9 9 9 9 . . .
8 8 . . . . . .
`, SpriteKind.Player)
ship.setPosition(20, 60)
controller.moveSprite(ship, 0, 100)
ship.setStayInScreen(true)
controller.A.onEvent(ControllerButtonEvent.Pressed, function () {
shot = sprites.createProjectileFromSprite(img`
4 4 4
`, ship, 100, 0)
ammo += -1
ship.sayText(ammo)
})
game.onUpdateInterval(1000, function () {
rock = sprites.create(img`
. e e e .
e e d e e
e d e e e
. e e e .
`, SpriteKind.Enemy)
rock.setPosition(160, randint(10, 110))
rock.vx = -50
})
sprites.onOverlap(SpriteKind.Projectile, SpriteKind.Enemy, function (sprite, otherSprite) {
sprite.destroy()
otherSprite.destroy()
info.changeScoreBy(1)
})
Look at the on A pressed block. Does anything ask whether there is ammo left?
Press A (space) again and again. Watch what the ship says.

let shot: Sprite = null
let rock: Sprite = null
let ammo = 3
scene.setBackgroundColor(15)
let ship = sprites.create(img`
8 8 . . . . . .
8 9 9 9 9 . . .
8 9 1 1 9 9 9 9
8 9 9 9 9 . . .
8 8 . . . . . .
`, SpriteKind.Player)
ship.setPosition(20, 60)
controller.moveSprite(ship, 0, 100)
ship.setStayInScreen(true)
controller.A.onEvent(ControllerButtonEvent.Pressed, function () {
shot = sprites.createProjectileFromSprite(img`
4 4 4
`, ship, 100, 0)
ammo += -1
ship.sayText(ammo)
})
game.onUpdateInterval(1000, function () {
rock = sprites.create(img`
. e e e .
e e d e e
e d e e e
. e e e .
`, SpriteKind.Enemy)
rock.setPosition(160, randint(10, 110))
rock.vx = -50
})
sprites.onOverlap(SpriteKind.Projectile, SpriteKind.Enemy, function (sprite, otherSprite) {
sprite.destroy()
otherSprite.destroy()
info.changeScoreBy(1)
})
This version checks first. Try to fire a fourth shot.

let star: Sprite = null
let shot: Sprite = null
let rock: Sprite = null
let ammo = 3
scene.setBackgroundColor(15)
let ship = sprites.create(img`
8 8 . . . . . .
8 9 9 9 9 . . .
8 9 1 1 9 9 9 9
8 9 9 9 9 . . .
8 8 . . . . . .
`, SpriteKind.Player)
ship.setPosition(20, 60)
controller.moveSprite(ship, 0, 100)
ship.setStayInScreen(true)
controller.A.onEvent(ControllerButtonEvent.Pressed, function () {
if (ammo > 0) {
shot = sprites.createProjectileFromSprite(img`
4 4 4
`, ship, 100, 0)
ammo += -1
}
ship.sayText(ammo)
})
game.onUpdateInterval(1000, function () {
rock = sprites.create(img`
. e e e .
e e d e e
e d e e e
. e e e .
`, SpriteKind.Enemy)
rock.setPosition(160, randint(10, 110))
rock.vx = -50
})
game.onUpdateInterval(5000, function () {
star = sprites.create(img`
. . 5 . .
5 5 5 5 5
. 5 5 5 .
. 5 . 5 .
`, SpriteKind.Food)
star.setPosition(160, randint(10, 110))
star.vx = -30
})
sprites.onOverlap(SpriteKind.Projectile, SpriteKind.Enemy, function (sprite, otherSprite) {
sprite.destroy()
otherSprite.destroy()
info.changeScoreBy(1)
})
sprites.onOverlap(SpriteKind.Player, SpriteKind.Food, function (sprite, otherSprite) {
otherSprite.destroy()
})
This version fires only if ammo > 0. Fill in each press of A.
| ammo before | a shot? | ammo after |
|---|---|---|
| 3 | yes | 2 |
| 1 | ||
| 0 |
A star refills the ammo to 5.
A star floats past every 5 seconds. Its overlap only destroys it.
Add set ammo to 5 in the Player–Food overlap.
Now a star adds 3 to what you have. Which is better for a player with 4 shots left?
Use change ammo by 3 in place of set.
A star refills the ammo to 5.
This ticks by itself when your blocks do what is asked.
A star adds 3 shots to what you have left.
This ticks by itself when your blocks do what is asked.
The shield from last lesson. A new variable, shieldTime, is set to 5 when you catch a star.
shieldTime.shieldTime reaches 0, set shield to false and put the black background back.Catching a star already sets shieldTime to 5. In the timer that runs every 1000 ms, add: if shield, change shieldTime by -1.
Inside that if, add another: if shieldTime = 0, set shield to false and set the background back to 15 (black).
The shield switches off by itself after 5 seconds.
This ticks by itself when your blocks do what is asked.
A runner with a sprint boost on B (enter on the keyboard): 3 seconds of extra speed, then back to normal. Make it fair: only 3 boosts for the whole game, counted down.
Students limit a blaster with a number that counts down, check it first so it never goes below zero, refill it with a star, and make a shield run out after 5 seconds. About 45 minutes.
Open the teacher guide: answers, solutions, slides and a worksheet.
A power-up that runs out is a number counting down. For ammo, the A event asks if ammo > 0 first, then fires and changes ammo by -1. Without the check, ammo goes below zero and the shots never stop (the misconception). With ≥ 0 there is one shot too many.
For time, a timer every 1000 ms counts shieldTime down while the shield is on, and at 0 sets the shield back to false: an if inside an if. Set (refill to 5) and change (add 3) are different, which Modify brings out.
Checking before using. When the count goes below zero, ask what the event asks first.
Stretch: Show the shield time with the ship's say block, every second.
Support: Give students the if shield in the timer, so they add only the countdown and the switch-off.
Next: the Power-ups challenge, with less help. Skillmap: Save the Galaxy (arcade.makecode.com/skillmaps).