Window Mode Switching in Godot

Window Mode Switching in Godot

“How do I launch a Godot game in fullscreen mode?” A simple question that probably every (desktop) game developer has to ask. The right answer is a bit more complicated than what I would have hoped for, but only a little bit.

I’m using this approach in Godot 4.3.

Step 1: Set Window Mode to Fullscreen

Go to Project → Project settings → Display → Window → Mode and change it to Fullscreen.

Fullscreen mode in Project Settings

This might be enough for development purposes or if you only need fullscreen mode for your game. However, sooner or later, you may find yourself, like me, wanting to give players the ability to change the window mode in-game.

Step 2: Change Window Mode Through Code

Create a button or keyboard shortcut (or both) that executes the following code to toggle between fullscreen and windowed modes:

func toggle_fullscreen():
    var current_mode = DisplayServer.window_get_mode()
    if current_mode == DisplayServer.WINDOW_MODE_FULLSCREEN:
        DisplayServer.window_set_mode(DisplayServer.WINDOW_MODE_WINDOWED)
    else:
        DisplayServer.window_set_mode(DisplayServer.WINDOW_MODE_FULLSCREEN)

Now, the game starts in fullscreen mode, and the player can switch to windowed mode later. However, I want the player to choose the window mode only once and have that mode automatically restored when the game restarts.

This is where it gets tricky. It’s easy to save the window mode to a file, load it during startup, and set the mode accordingly. The problem is that once the game is exported, the initial window mode will always be set to fullscreen. So, the game will always start in fullscreen mode and then, a few milliseconds later, switch to windowed mode once the settings file is loaded. This quick switch is visible to the player, which is distracting and creates a poor user experience. I definitely don’t want that in my game, and I’m guessing neither do you.

Step 3: Persist Window Mode

The Godot engine doesn’t allow us to execute custom code before the window is initialized, so there’s no way to load the window mode from a custom settings file and apply it before the window is displayed. Fortunately, there’s a built-in settings file we can use: Project Settings Override. In the screenshot below, I’ve specified the location of this file as user://custom_overrides.cfg.

Project Settings Override

Settings from this file are loaded during startup and override the project settings. We just need to save the window mode there:

func save_window_mode(is_fullscreen: bool):
    var overrides_file_path = ProjectSettings.get_setting("application/config/project_settings_override")
    if overrides_file_path:
        var config := ConfigFile.new()
        var mode := DisplayServer.WINDOW_MODE_FULLSCREEN if is_fullscreen else DisplayServer.WINDOW_MODE_WINDOWED
        config.set_value("display", "window/size/mode", mode)
        var result = config.save(overrides_file_path)
        if result != OK:
            printerr("Failed to save project settings override file '%s', error code: %d" % [overrides_file_path, result])
    else:
        print("No project settings override file defined.")

The user://custom_overrides.cfg looks like this. It is an ini-style format that Godot uses internally:

[display]

window/size/mode=0

Now, when the game starts, the window is initialized directly in fullscreen or windowed mode, without any visible glitches. Hurray!