biglebowsky19
biglebowsky19

Reputation: 33

How to create mask for a whole container in Phaser 3?

I am trying to create a planet with a background, sphere shadow and a mask, it was pretty straightforward to implement this in Phaser 2, but now it has a bunch of tricky parts for me

Once I update the mask property of my container, nothing is displayed at all. I have already tried several Masks groups, but couldn't succeeded...

In other words: I need to "put" the rectangle background inside of a sphere by using a circle mask

What am I doing wrong? Is there any other better way to do this maybe?

so here is the method I use:

init({ x, y, size, sprite, id }) {
    const container = this.scene.add.container(x, y);

    const width = (1200 / 300) * 200;
    const height = 200;

    const earthBMD = this.scene.textures.createCanvas(`earthBMD${id}`, width, height);
    earthBMD.draw(0, 0, this.scene.textures.get(`map-${size}-${sprite}`).getSourceImage());
    const planet = this.scene.add.sprite(0, 0, earthBMD).setOrigin(0.5).setAngle(-15);

    const shadow = this.scene.add.sprite(0, 0, 'sphere').setOrigin(0.5, 0.5).setScale(0.5);

    const mask = this.scene.make.graphics(0, 0).fillStyle(1000000, 0.5).fillCircle(0, 0, 150);

    container.add([planet, mask, shadow]);
    container.mask = new Phaser.Display.Masks.GeometryMask(this.scene, mask);

    return container;
}

Upvotes: 2

Views: 1672

Answers (1)

winner_joiner
winner_joiner

Reputation: 14845

Should be pretty easy to create the desired effect (atleast with this basic GameObjects). I'm not sure where your init function is inside. If it is in a Scene, you just have to remove the scene from this.scene...., than it should work. (and that would be the underlining issue)

p.s.: don't add the mask to the container, like in this line container.add([planet, mask, shadow]); except you want the mask Image/Shape to be rendered on the canvas.

here a stripped down example:

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

var config = {
    type: Phaser.CANVAS,
    width: 536,
    height: 183,
    scene: {
        create
    },
    banner: false
}; 

function create () {

    const container = this.add.container(0, 0);

    const width = config.width;
    const height = config.height;

    let g = this.make.graphics({add:false});
    
    g.fillStyle(0xffff00)
    g.fillRect(10,10, 150, 150);
    
    g.generateTexture('map', 150, 150);

  
    const planet = this.add.sprite(50, 10, 'map')
      .setOrigin(0)

    const mask = this.make.graphics({add:false})
      .fillStyle(1000000, 0.5)
      .fillCircle(0, 0, 200);
    

    container.add([planet]);

    container.mask = new Phaser.Display.Masks.GeometryMask(this, mask);

}

new Phaser.Game(config);
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/phaser.js"></script>

P.s.: the officials examples are pretty good. Checkout these examples

Upvotes: 2

Related Questions