1

My game has multiple screens, like side-by-side rooms and I'm trying to allow user to drag between them, like presentation slides.

So I'm doing it by each room as a different scene, just for organizing the map in different files.

import Phaser from 'phaser';
import BaseScene from './../base';

export default class scene1 extends BaseScene {

  parent;

  constructor(handle, parent) {
    super(handle);
    this.parent = parent;
  }

  preload() {
  }

  create() {
    this.cameras.main.setViewport(this.parent.x, this.parent.y, 200, 200);
    this.add.text(10, 10, 'scene1').setOrigin(0);
  }

  refresh ()
  {
    this.cameras.main.setPosition(this.parent.x, this.parent.y);
    this.scene.bringToTop();
  }

}

After that, I'm adding all those scenes in the map, by loading it's class and positioning it's X side-by-side. It's working fine.

Also, the code below allows me to drag each scene at once.

async attachScene(number){

  let sceneKey = 'cena' + number;
  let sceneImport = await import("./../../scenes/" + number);
  let sceneX = number * this.scale.width;

  var win = this.add.zone(sceneX, 0, 200, 200).setInteractive().setOrigin(0);
  this.input.setDraggable(win);
  var c = new sceneImport.default(sceneKey, win);

  win.on('drag', function (pointer, dragX, dragY) {
    this.x = dragX;
    c.refresh();
  });
  this.scene.add(sceneKey, c, true);

}

The problem is that I don't know the best way to drag all those scenes at once.

How can I do it? Maybe Camera class? Containers? Zones?

anderlaini
  • 1,593
  • 2
  • 24
  • 39

1 Answers1

1

I'm not sure im swtiching the scenes togehter is a good idea, because of performance and so.
That said, you can simply move all the scenes, if you create a "drag vector" and apply it after the drag ended, to all rooms. I would use the pointerup and pointerdown events of the main scene, so that the coordinates work right and because the scene doesn't have Drag-Events.

Here a short demo showcasing this:
It is abit long,but needed for the demo to work.
(the part after the comment // EVENT HANDLING, is the most relevant)

document.body.style = 'margin:0;';

class BaseClass extends Phaser.Scene  {
    constructor(key){
        super(key);
    }
    
    create(data){
        this.parent = data;
        this.cameras.main.setViewport(data.x, data.y, data.width, data.height);
    }
    
    refresh() {
      this.cameras.main.setPosition(this.parent.x, this.parent.y);
    }
}

class Scene1 extends BaseClass {
    constructor(){
        super('scene1');
    }
    
    create(data){
        super.create(data);
        this.add.text(10, 10, 'Scene1').setOrigin(0).setDepth(100);
        this.add.rectangle(0, 0, this.parent.width, this.parent.height, 0xff0000 ).setOrigin(0);
    }
}

class Scene2 extends BaseClass {
    constructor(){
        super('scene2')
    }
    
    create(data){
        super.create(data);
        this.add.text(10, 10, 'Scene2').setOrigin(0).setDepth(100);
        this.add.rectangle(0, 0, this.parent.width, this.parent.height, 0xffff00 ).setOrigin(0);
    }
}



class Main extends Phaser.Scene {
    constructor(){
        super('main')
    }
    
    create(){
    
        let layout = [
            { key: 'scene1' },
            { key: 'scene2' },
        ];
        this.openScenes(layout);
        
        // EVENT HANDLING
        this.input.on('pointerdown', (pointer) => {
            this.dragStartPosition= { x:pointer.x , y:pointer.y };
        }); 
            
        this.input.on('pointermove', this.updatePosition, this);
            
        this.input.on('pointerup', this.updatePosition, this);
    }
    
    updatePosition(pointer){
        console.info(pointer.buttons)
        if(this.dragStartPosition){
            let vector = { 
                x: pointer.x - this.dragStartPosition.x,
                y: pointer.y - this.dragStartPosition.y
            };
            this.scene.manager.scenes.forEach((scene) => {
                if(scene.refresh){ // is a room scene
                    scene.parent.x += vector.x;
                    scene.parent.y += vector.y;
                    scene.refresh();
                }
            });
            this.dragStartPosition = pointer.buttons == 0 ? null : { x:pointer.x , y:pointer.y };
        }
    }

    openScenes(scenes){
        let roomWidth = config.width/2;
        let roomHeight = config.height/2;
        for (let idx = 0; idx < scenes.length; idx++){
            let room = this.add.zone(idx * roomWidth, 50, roomWidth, roomHeight)
                .setOrigin(0);
            this.scene.run(scenes[idx].key, room );  
        }
    }
}

var config = {
    type: Phaser.AUTO,
    width: 536,
    height: 183,
    scene: [Main, Scene1, Scene2, ],
    banner: false
}; 

new Phaser.Game(config);
console.clear();
<script src="//cdn.jsdelivr.net/npm/phaser/dist/phaser.min.js"></script>

Updated demo:
I added the event pointermove so, that the dragging is not so janky.

winner_joiner
  • 12,173
  • 4
  • 36
  • 61