0
\$\begingroup\$

I'm using Unity to create a 2D platformer game. I ran into an issue I was hoping someone could help me with. I'm using OnCollisionEnter2D() to detect when the player gameobject touches the ground, which is a tilemap. At the most basic implementation, it looks like this:

private void OnCollisionEnter2D(Collision2D collision) {

    Debug.Log("Tile collision");

    var map = collision.collider.GetComponent<Tilemap>();
    var grid = map.layoutGrid;

    // Find the coordinates of the tile we hit.
    var contact = collision.GetContact(0);
    Vector3 contactPoint = contact.point - 0.05f * contact.normal;
    Vector3 gridPosition = grid.transform.InverseTransformPoint(contactPoint);
    Vector3Int cell = grid.LocalToCell(gridPosition);

    // Extract the tile asset at that location.
    var tile = map.GetTile(cell);

    if(tile == null)
        return; // No valid tile! Abort!

    // Do something when a new tile is hit
    // TODO: Place function here

}

When I run my game, the console displays "tile collision" whenever I jump and then touch a tilemap surface. The console message will not display again until I leave whatever surface I'm on and touch it again. Although this is close to what I want, it's not exactly what I'm trying to achieve.

I'd like to be able to display the message every time the player touches another tile, even if its the same tile the player was previously touching. I'm not entirely sure how to implement this, though. Does anyone have any pointers that might help me achieve my desired outcome?

\$\endgroup\$
6
  • 1
    \$\begingroup\$ Are you looking for OnCollisionStay2D? Also, there's no engine called "Unity2D" — it's just Unity, no matter what mix of dimensions you're using. \$\endgroup\$
    – DMGregory
    Oct 22, 2021 at 19:30
  • \$\begingroup\$ This sentence: "I'd like to be able to display the message every time the player touches another tile, even if its the same tile the player was previously touching." doesn't really make any sense. Touching "another tile" can't possibly be "the same tile." Which do you mean? \$\endgroup\$ Oct 22, 2021 at 21:03
  • \$\begingroup\$ @DMGregory, I was specifying Unity 2D, since I'm working on a 2D project. I've never made a 3D project, but I'd imagine that things work differently with an additional dimension. I am well aware that there isn't an engine with that name, lol. But yes, I think this is the function I should be using instead. Thanks! \$\endgroup\$
    – Mav
    Oct 22, 2021 at 21:48
  • \$\begingroup\$ @AcmeNerdGames That's my bad, I didn't proofread before posting. What I meant was that I'd like the message to display when the player steps off of one tile and onto another, even if the two tiles are of the same variety. \$\endgroup\$
    – Mav
    Oct 22, 2021 at 21:48
  • 1
    \$\begingroup\$ That makes more sense. I feel like we still need a little more info though. What sort of collider is attached to the player? For instance, are there discreet colliders on his feet that come in contact with the tile map? Can you show us a diagram or screenshot of your game scene so we can understand how the player is supposed to be interacting with the ground plane? A picture might be worth a 1000 words here. \$\endgroup\$ Oct 22, 2021 at 22:15

1 Answer 1

1
\$\begingroup\$

As DMGregory noted in his comment, it sounds like you need to check OnCollisionStay2D to check that the player continues to be grounded to the tile. Alternatively, you could check OnCollisionExit2D to learn when the player has become ungrounded.

\$\endgroup\$
1
  • \$\begingroup\$ This worked. Where OnCollisionEnter2D was only checking the current tile whenever a collision occurred and only triggered again after jumping and coming back in contact with the tile, OnCollisionStay2D check continuously, which is precisely what I was looking for. Thanks so much :) \$\endgroup\$
    – Mav
    Oct 27, 2021 at 15:20

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .