Phaser: Multiple scenes

By

Learn how to use multiple scenes in Phaser by extending Phaser.Scene in separate files, passing them as an array, and switching with this.scene.start.

~~~

This post is part of a Phaser series. Click here to see the first post of the series.

To use multiple scenes in Phaser, you create each scene as a class extending Phaser.Scene, pass the classes as an array to the scene property, and switch between them with this.scene.start().

In the previous examples we saw how to create a scene, by passing an object with functions references to the scene property of the Phaser.Game() options object:

function preload() {}

function create() {}

new Phaser.Game({
  width: 450,
  height: 600,
  scene: {
    preload,
    create
  }
})

This is a simple scenario, and it works fine for a demo.

But a real game usually has multiple scenes: a loading screen, a menu, the game itself, a game over screen. Each one has its own logic and its own lifecycle methods.

Creating scenes as classes

You can create each scene in its separate file, and pass them to the scene property, but this time as an array.

In this case scenes are created extending the Phaser.Scene object.

I create a Welcome scene in a separate Welcome.js file:

export default class Scene1 extends Phaser.Scene {
  constructor() {
    super('welcome')
  }

  create() {
    this.add.text(20, 20, 'Loading..')

    setTimeout(() => {
      this.scene.start('game')
    }, 2000)
  }
}

The string we pass to super() is the scene key. It’s the name we use to reference this scene from other scenes.

Then I create a Game scene in Game.js:

export default class Scene2 extends Phaser.Scene {
  constructor() {
    super('game')
  }

  create() {
    this.add.text(20, 20, 'Playing game!')
  }
}

Note that we have the create() method here. We can also have preload() and update() like we did previously.

And we import them and pass them to the scene property into our main game file:

import Phaser from 'phaser'
import Welcome from './Welcome'
import Game from './Game'

const config = {
  width: 800,
  height: 600,
  backgroundColor: 0x000000,
  scene: [Welcome, Game]
}

const game = new Phaser.Game(config)

The first scene listed in the array (Welcome) starts automatically. The others sit there until something starts them.

Switching scenes

In the Welcome scene we call this.scene.start('game') to move to the Game scene after 2 seconds. start() shuts down the current scene and starts the one matching the key.

Instead of setTimeout(), you can use Phaser’s own clock: this.time.delayedCall(2000, () => this.scene.start('game')). It behaves the same here, but it’s tied to the game loop, so it pauses when the game pauses.

You can also pass data to the scene you’re starting:

this.scene.start('game', { level: 1 })

The Game scene receives it as an argument in its init(data) or create(data) method.

One pitfall to watch out for: the key is a plain string, so a typo won’t be caught by your editor. If you write this.scene.start('Game') but the key is 'game', the switch won’t happen. When starting a scene does nothing, check the key first.

Tagged: Phaser · All topics
~~~

Related posts about phaser: