Load assets dynamically in the runtime multiple time in the same scene

Hello! I’m facing some issue with the loading process.

At the moment I’m able to load all of my assets on the runtime (outside the preload method) which is exactly what I desired at the time.

However, I would like to load other assets later on in the same scene. When I try to do it, it seems like the loader is not starting even if I’m calling it. The debug message ‘loading started’ is only trigger once.

My questions is : why is the loader only starting once? Thanks

export default class AssetLoader {
  private scene: Phaser.Scene

  constructor(scene: Phaser.Scene) {
    this.scene = scene

    // Load assets on start
    this.scene.load.on('start', () => {
      this.loadCommunAssets()
      this.loadThemeAssets()
      console.log("loading started")
    })
 
    // Load assets on events
    EventDispatcher.getInstance().on('onTransition', this.onLoadSceneAssets)
  }

  // Callback to load new assets
  private readonly onLoadSceneAssets = (targetKey: string): void => {
    this.loadGameAssets(targetKey)
    this.scene.load.start()
  }

  // Load game assets
  private loadGameAssets(targetKey: string): void {
    // [...]
  }
}

:wave:

Is one AssetLoader supposed to load 1 batch or 2 batches? I only see 1 load.start(), and it’s not in the constructor.

Here don’t you want to queue those assets before starting the loader?

1 Like

Oh! Thanks for the precision. Basically, I would simply have to move the loadCommunAssets and loadThemeAsset methods outside the start callback in the constructor to queue those before starting the loader… I had some confusion there.

Hello, I changed the code a bit according to your saying and I still have the same issue.

Basically, when the game starts, only the game assets related to ‘shed’ are loading (which is OK). However, when the player interacts with some elements, I would like to load new assets but nothing seems to load. Why?

Thanks!

import EventDispatcher from '../eventDispatcher'
import Phaser from 'phaser'

export default class AssetLoader {
  private scene: Phaser.Scene
  private locationData: any
  private itemData: any
  private characterData: any
  private puzzleData: any

  constructor(scene: Phaser.Scene) {
    this.scene = scene
    this.locationData = this.scene.cache.json.get('locationData')
    this.itemData = this.scene.cache.json.get('itemData')
    this.characterData = this.scene.cache.json.get('characterData')
    this.puzzleData = this.scene.cache.json.get('puzzleData')

    this.loadCommunAssets()
    this.loadThemeAssets()
    this.loadGameAssets('shed')
    this.scene.load.start()

    EventDispatcher.getInstance().on('onLoadScene', this.onLoadScene)
  }

  private readonly onLoadScene = (targetKey: string): void => {
    this.loadGameAssets(targetKey)
  }

  /**
   * Load commun assets
   */
  private loadCommunAssets(): void {
      // [...]
  }

  /**
   * Load theme assets
   */
  private loadThemeAssets(): void {
    // [...]
  }

  /**
   * Load game assets
   */
  private loadGameAssets(targetKey: string): void {
    // [...]
  }

I don’t know if this is the best approach but this seems to fix my issue

 private readonly onLoadScene = (targetKey: string): void => {
  this.scene.load.reset()
  this.loadGameAssets(targetKey)
  this.scene.load.start()
}

Did you confirm that onLoadScene() ever gets called?

If you want to troubleshoot more, try phaser-plugin-loader.

I might try to simplify this by getting rid of the class altogether.

Yes! The method is being called. Everything seems to work perfectly now.

As I mentionned, I don’t know if this.scene.load.reset() could cause some drawbacks but its working fine.

Might have to look a that in the future.