phaser
phaser copied to clipboard
Input.alwaysEnabled does not work when a interactive game object is below it
Version
- Phaser Version: 3.52 only
Description
interactive object that are invisible and has a interactive object behind it, do not receive input events even if it has "input.alwaysEnabled = true"
Example Test Code
var config = {
type: Phaser.WEBGL,
parent: 'phaser-example',
width: 800,
height: 600,
scene: {
create: create
}
};
var game = new Phaser.Game(config);
function create()
{
var invisibleRect = this.add.rectangle(400, 300, 256, 256, 0x00ff00);
var rect = this.add.rectangle(400, 300, 256, 256, 0x0000ff).setDepth(-1);
var text = this.add.text(128, 128, "0").setFontSize(28);
var count = 0;
invisibleRect.setInteractive();
invisibleRect.input.alwaysEnabled = true;
invisibleRect.on('pointerdown', function () {
count++;
text.text = count.toString();
});
rect.setInteractive();
invisibleRect.alpha = 0;
}
Additional Information
Did some testing a i begin to get the bug after the commit "616566c - Renamed sortGameObjects
to sortDropZones
and then repurposed the old method for the new render list sorting technique."
Thank you for submitting this issue. We have fixed this and the fix has been pushed to the master
branch. It will be part of the next release. If you get time to build and test it for yourself we would appreciate that.
I test it in my project it did not fix the issue. The problem is that invisible game objects with "input.alwaysEnabled = true" it is always put behind visible game object when it come to input even when the depth of the invisible game object is higher.
for the project i am working on we did fixed it by using a sort function like this in inputPlugin:
sortGameObjects: function (gameObjects, pointer)
{
if (gameObjects.length < 2 || !pointer.camera)
{
return gameObjects;
}
var list = pointer.camera.renderList;
var _this = this;
return gameObjects.sort(function (childA, childB)
{
var ia = list.indexOf(childA);
var ib = list.indexOf(childB);
if (ia === -1 || ib === -1)
{
if ((childA.input && childA.input.alwaysEnabled) ||
(childB.input && childB.input.alwaysEnabled))
{
return _this.sortDropZoneHandler(childA, childB);
}
}
return ib - ia;
});
}
But i am not confident that it is good fix for the problem but it works in our case
Using your test passes with a fresh build of Beta 4: http://labs.phaser.io/view.html?src=src%5Cbugs%5C5507%20always%20enabled.js&v=dev
My test is not great it only has one object that is below the invisible one and because both the visible and invisible is at sorted as if they have a index of 0 in the renderList. It appears that work, but if you add one more object it fails.
var config = {
type: Phaser.AUTO,
parent: 'phaser-example',
width: 800,
height: 600,
scene: {
create: create
}
};
var game = new Phaser.Game(config);
function create()
{
var invisibleRect = this.add.rectangle(400, 300, 300, 300, 0x00ff00);
var rect = this.add.rectangle(400, 300, 256, 256, 0x0000ff).setAlpha(0.5);
var rect2 = this.add.rectangle(350, 300, 256, 256, 0xff0000).setAlpha(0.5);
var text = this.add.text(128, 128, "0").setFontSize(28);
var count = 0;
invisibleRect.name = 'invis';
invisibleRect.setInteractive();
invisibleRect.input.alwaysEnabled = true;
invisibleRect.on('pointerdown', function () {
count++;
text.text = count.toString();
});
rect.name = 'rect';
rect.setInteractive();
rect2.name = "rect2"
rect2.setInteractive();
invisibleRect.alpha = 0;
//invisibleRect.alpha = 0.3;
invisibleRect.setDepth(1);
rect.setDepth(-2);
rect2.setDepth(-1);
}
https://user-images.githubusercontent.com/3351370/145205086-a74959c6-ef86-437b-83c6-e356bcbabaad.mp4
Looking at this further, the issue is this line of code within sortGameObjects
: var list = pointer.camera.renderList;
because the invisible rectangle won't be on this list, so won't get an index. Swapping this to use the Display List instead fixes this issue. Finally!