Control Flow

Control flow lets your game make decisions and repeat actions. Python uses indentation (4 spaces per level) to define blocks — there are no braces.

Boolean Expressions

A boolean expression is an expression that evaluates to either True or False. Comparison operators produce boolean values:

health <= 0        # True when the player is dead
score == high_score
distance > attack_range
wave_number != last_wave

Combine conditions with logical operators and, or, not:

if has_key and door_locked:
    open_door()

if not is_alive:
    respawn()

if x >= 2 and y != 0 and (x / y) > 2:   # y != 0 guards the division
    ...

Python uses short-circuit evaluation: in an and expression, if the left side is False the right side is never evaluated. This lets you write safe guards — put the cheap safety check before the potentially dangerous computation.

Conditionals

if health <= 0:
    game_over = True
elif health < 25:
    play_sound("low_health_warning")
else:
    pass   # still healthy, nothing to do

elif is “else if”. Python checks each condition in order and runs the first branch that is true. Even if several conditions are true, only the first matching branch executes.

Avoid deeply nested conditionals — they become hard to read quickly. Logical operators usually let you flatten them:

# nested (harder to read)
if x > 0:
    if y > 0:
        print("first quadrant")

# flat (clearer)
if x > 0 and y > 0:
    print("first quadrant")

try / except

When an operation might fail — converting player input to a number, opening a save file — wrap it in try/except to handle the error gracefully instead of crashing:

raw = input("Enter player speed: ")
try:
    player_speed = float(raw)
except:
    print("Invalid input, using default speed.")
    player_speed = 5.0

Python tries the try block first. If an error (exception) occurs, it jumps to the except block instead of stopping the program. If no error occurs, the except block is skipped entirely.

for Loops

Use for to iterate over a collection or a range of numbers. The loop variable changes automatically each iteration.

Iterating a list — updating every enemy each frame:

for enemy in enemies:
    enemy.update()

Iterating a range — spawning a wave:

for i in range(5):
    spawn_enemy(x=i * 10, y=0, z=0)

Iterating a dictionary’s key-value pairs:

for action, key in keybindings.items():
    print(f"{action}: {key}")

A for loop is a definite loop: it runs a known number of times (once per item in the collection).

while Loops

Use while when you do not know in advance how many iterations are needed — the loop keeps running until a condition becomes False.

# keep spawning reinforcements until the squad is full
while len(squad) < MAX_SQUAD_SIZE:
    squad.append(spawn_enemy())

The variable that changes each iteration and eventually makes the condition false is called the iteration variable. A loop without one runs forever — an infinite loop.

break exits the loop immediately. continue skips the rest of the current iteration and jumps back to the condition check:

for item in loot_table:
    if item == "legendary_sword":
        inventory.append(item)
        break       # stop as soon as we found the legendary

    if item == "junk":
        continue    # skip junk silently

Loop Patterns

Many game loops follow the same structure: initialise a variable before the loop, update it inside, use the result after.

Accumulator — running total of score or damage:

total_damage = 0
for hit in hits_this_frame:
    total_damage = total_damage + hit

Find the maximum — track the highest-scoring player:

best_score = None
for player in players:
    if best_score is None or player.score > best_score:
        best_score = player.score

Starting best_score as None means “we haven’t seen any value yet”. The first player automatically becomes the best so far, and from then on we only update when we find someone better.

The Game Loop

In Acron you will not write an explicit while True loop yourself — the engine’s run() method handles that. But the patterns above appear inside every task and event handler you register with the engine. A task is just a function that Acron calls on every frame, and it uses the same if/for/while logic you have just learned.