Phaser3 SceneTransition(シーンの遷移)

phaser

Phaser3 SceneTransition(シーンの遷移)

versiont: 3.52.0

Phaser3のSceneにはシーンの遷移、つまりあるシーンから別のシーンに移り変わる(遷移)ときに利用できる Transition という機能が付いている。

例えば村のマップからアイテムショップに入る時、現在プレイヤーが存在するマップ(村)を徐々に透明にし、次に侵入するマップ(アイテムショップ)の透明度を徐々に下げていくようにしてシーンが切り替わる演出を作りたいなどの時に使える(伝わるかな?)

Transitionの使用方法

Transitionを使用してシーンの切り替えを行う時は scene.start を使わずに scene.transition を使用する。引数は Phaser.Types.Scenes.SceneTransitionConfig である。

this.scene.transition({
  // 遷移先のシーン
  target: 'gameOver',
  // 遷移先のシーンのinitの引数として渡したいデータ
  data: {data: 100},
  // 遷移にかける時間
  duration: 2000,
  // 遷移中に毎フレーム繰り返す処理
  onUpdate: (progress: number) => {

  },
});

これを使う。最初は遷移中に遷移元のシーン、遷移先のシーンに何が起きているのかわからないと思うので、以下の処理をシーンのイベントに仕込んで観察してみることをおすすめする。

// 遷移元のシ遷移先ーン
class From extends Phaser.Scene {
  init (): void {
    this.events.on(Phaser.Scenes.Events.TRANSITION_INIT, () => {
      console.log('遷移元: transition init');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_START, () => {
      console.log('遷移元: transition: transition start');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_WAKE, () => {
      console.log('遷移元: transition: transition wake');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_OUT, () => {
      console.log('遷移元: transition: transition out');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_COMPLETE, () => {
      console.log('遷移元: transition: transition complete');
    });
  }
}

// 遷移先のシーン
class To extends Phaser.Scene {
  init (): void {
    this.events.on(Phaser.Scenes.Events.TRANSITION_INIT, () => {
      console.log('遷移先: transition init');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_START, () => {
      console.log('遷移先: transition: transition start');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_WAKE, () => {
      console.log('遷移先: transition: transition wake');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_OUT, () => {
      console.log('遷移先: transition: transition out');
    });
    this.events.on(Phaser.Scenes.Events.TRANSITION_COMPLETE, () => {
      console.log('遷移先: transition: transition complete');
    });
  }
}

あとは、両シーンの init, create, update, shutdown にも出力を入れてあげれば何が起きているか分かると思う。

遷移について

先述の方法で自分でログの出力をみて自分で確認するほうが納得できると思うが、シーンの遷移は以下の図ようになっている。(あくまで一例)

draw1

要するに、遷移が開始すると config.duration で指定した時間は遷移元、遷移先の両シーンが立ち上がった状態になり、それぞれ必要なタイミングでTransition用のイベントが発火する、ということである。

Transition使用時の注意

まず注意すべきなのは、イベントが発火する以外は両シーンが普通に動いている状態であることに注意しないといけない。例えば遷移が始まってから完了するまでの間、プレイヤーの入力を受け付けたくなければ、遷移元は TRANSITION_OUT に、遷移先は TRANSITION_COMPLETE に、入力の許可、拒否をするイベントを登録しないといけない。

次に、ここまでで説明して分かるとおりTransitionは基本的にイベントの登録によって構築しないといけないが、このイベントはシーンのshutdown時にすべて消えるようになっている。そのため、毎回必要になるタイミング、またはシーンの initcreate 呼び出し時にイベントを登録する必要がある。

最後に、これは多分バグだと思うが、これを書いている時点で “Transition終了のタイミングで遷移元のシーンがshutdownした後、一度だけupdateが呼び出される” という挙動をする。shutdown状態のシーンがupdateされてしまうのでバグっぽいが、とりあえず直るまでは注意しておいてほしい。