For the contains
method on the Phaser.Geom.Triangle
class, this method only seems to check if the provided point is contained within the triangle and excludes if the point is on one of the triangle edges. I am not sure why this is the case, but from the docs, it links to this article with more information on the math that is used for this check: Point in triangle test.
Based on this, you could modify the logic in the processCallback
function to include checks for the edges. A partial example:
if (triangle.x2 === triangle.x3 && triangle.x2 === player.getTopRight().x) {
return true;
}
const topLeft = triangle.contains(player.getTopLeft().x, player.getTopLeft().y);
const topRight = triangle.contains(player.getTopRight().x, player.getTopRight().y);
If you add that, to your fiddle
, then when you try to move the box directly up, the movement should be blocked.
For doing a full collision with the triangle, this becomes a little more complicated since the collider is using the default box collider. What happens normally with the Arcade Physics collision is, when you provide a processCallback
function, Phaser will run that function and if the return value is true
, Phaser will try to separate the two Arcade Physics Bodies. In the example above, and in your 2nd fiddle, we see that this works when the two objects have an initial collision, and Phaser will push the object away from the triangle
In the cases were the processCallback
function returns false
, Phaser will not attempt to separate the two bodies, which is why the player
is able to move over the part of the tile
that is not the triangle
. Once this happens, the original box collider of the tile
and player
is overlapping, and once this happens, Phaser is not able to separate the two Physics bodies, which is why the player
can now move through the triangle
shape.
To handle this, you could add custom logic to the collideCallback
to separate the game objects, since the collideCallback
will only be invoked when your processCallback
function returns true
.
A basic example:
this.physics.add.collider(
tile,
player,
() => {
player.x -= 5;
player.y += 5;
},
(tile, player) => {
// your existing code for the processCallback function
}
);