LearnGML

Conditionals & Loops

Now we know how to use variables and perform some basic operations on those variables, but we are still missing some crucial ingredients for controlling our games. The next step is to learn how to execute certain sections of code based on whether certain conditions are met, and to execute code in loops.

Conditionals

Quite often, you will want to only execute some code under specific circumstances. For example, we want the player to lose when their health reaches 0. We can do this with an if statement. An if statement will check whether a condition is True or False (in Boolean terms), and if it is True then the following code block will run, otherwise it will be skipped.


if (health <= 0)
{
    dead = true;
}

You can also choose to run code given the condition isn’t met using the else keyword, for example:


if (health <= 0)
{
    dead = true;
}
else
{
    dead = false;
}

Furthermore, you can chain together different conditions using else if:


if (keyboard_check_pressed(vk_right))
{
    hspeed = 4;
}
else if (keyboard_check_pressed(vk_left))
{
    hspeed = -4;
}
else
{
    hspeed = 0;
}

What if you want to check multiple conditions at once? Although you can write each condition one after the other, it is much more elegant to combine these conditions into a single check, like so:


// Use && (or "and") to check if both conditions are true (the ! in front of
// the second condition inverts the result, ie. it is checking if vk_left is
// *not* pressed
if (keyboard_check_pressed(vk_right) && !keyboard_check_pressed(vk_left))
{
    hspeed = 4;
}

// Use || (or "or") to check if either or both conditions are true
if (keyboard_check_pressed(vk_right) || keyboard_check_pressed(vk_left))
{
    state = "walking";
}

// Use ^^ (or "xor") to check if exactly one of the conditions is true
if (keyboard_check_pressed(vk_right) ^^ keyboard_check_pressed(vk_left))
{
    walking_horizontally = true;
}

Finally, if / else statements can be compressed into something called a ternary operation. This syntax sacrifices readability for compactness, and for that reason is not overly recommended, and is mainly included for familiarity and comprehension.


// Dead is true if hp is less than or equal to 0, otherwise it is false
dead = (hp <= 0) ? true : false;

Loops

Loops are another crucial tool for programmers, allowing you to repeatedly execute code without having to type it over and over again. Furthermore, you can utilize different values in each iteration of a loop in order to execute more advanced code, which will be detailed below.

For Loops

For loops are very commonly used across all programming languages. They are most useful when you want to repeat a section of code and also keep track of the iterator, ie. the counter for determining whether the code should repeat or not.


// A For Loop that prints out every number from 1 to 10
for (var i = 1; i <= 10; i++)
{
    show_debug_message(i);
}

What is inside the brackets of the for loop can be broken down into 3 sections, with semicolons ( ; ) in between.

  • The declaration of the iterator. This runs once at the start of the loop. Note the use of a local variable here, as generally the iterator variable does not need to be accessed outside of the loop, although YMMV.
  • The expression against which the iterator is tested. This runs each cycle of the loop, and determines whether to continue looping or to stop and move to the next section of code.
  • The operation performed on the iterator. After each iteration of the loop has been executed, this operation is performed on the iterator

For more details on the specifics of for loops, please consult the manual .

While Loops

While loops are also extremely common in the programming world, and the key difference between them and for loops is that a while loop does not keep track of an iterator. Therefore if you wish to repeat a section of code until a condition is met, and the number of iterations per se does not matter, then a while loop is likely what you will want to use.


// A While Loop that increments x by 5 until it is greater than or equal to 100
while (x < 100)
{
    x += 5;
}

WARNING: it is extremely easy to accidentally make an infinite while loop where the expression will always be true, causing your game to become unresponsive until you force close it. Use caution.

// A While Loop that will loop infinitely as x will never equal 10
x = 3;
while (x != 10)
{
    x += 2;
}

Repeat

Repeat is a simple, covenient keyword for when you just want to repeat a section of code a specific number of times.


// This Repeat Loop will square x 10 times
x = 2;
repeat (10)
{
    x = power(x, 2);
}

A note on With

The with keyword is a particularly interesting and powerful tool that is rather unique to GML. The primary function of with is to change the scope of your code to that of another instance (or struct, more on structs later), however if you use with on an object rather than a specific instance of an object, it will act like a loop and repeat the following section of code in each active instance of that object type. This might seem overwhelming at the moment, but we shall cover some examples of how this can be used later, which will hopefully demonstrate how powerful with can be.

Break and Continue

Break and continue are two keywords that let you prematurely end loops. Although the specifics of how these two keywords vary depending on where they are used (in a for loop, while loop, with statement etc.), break generally immediately exits the loop while continue ends the current iteration of the loop, but does not exist the loop itself.


// Break
total = 0;
maximum = irandom_range(20, 40);

for (var i = 0; i < maximum; i++)
{
    if (i > 30)
    {
        break;
    }
    total += i;
}

// Continue
total = 0;
maximum = irandom_range(20, 40);

for (var i = 0; i < maximum; i++)
{
    if (i % 2 == 0)
    {
        continue;
    }
    total += i;
}