Ignore collision with all enemies without checking their tags

OK, so this is a bit of a quandary for my player class…

Right now, I am looping through a string array of enemy tags, and then for each enemy tag in that array, I run Physics2D.IgnoreCollision()

This is in FixedUpdate() inside my player’s class. And yes, this is probably a terrible idea. It does work, but… yeah.

Is there a way I can use Physics2D.IgnoreCollision() without having to check for every enemy tag?

Just to clarify things -

I am using Physics2D.IgnoreCollision() so that I can keep the player from bumping into the enemies, but also still do damage to them. I implemented an interface in a health base class that all enemies and the player derive from, so I was able to set up an IDamageable interface and just call the Damage() function within that interface, which means I don’t have to use CompareTag() inside the OnTriggerEnter2D() function.

It’s incredibly efficient, and I was just curious if something like this were possible with Physics2D.IgnoreCollision().

As it turns out, I was doing this all wrong. Live and learn, I guess…

I have a Physics2D.IgnoreCollision() set up in the start of my enemy base class, and it just checks for the player tag on start, so as it turns out, I don’t need anything fancy for this.

Look into layers and layer-based collision detection.

Yeah, that is an option, but wouldn’t that turn off collision completely, in that I wouldn’t be able to detect collision at all between the unchecked layers?

Physics2D.IgnoreCollision() at least allows me a bit more control, as I can just return false if I need collision detection again. Plus, at least from my testing, Physics2D.IgnoreCollision() only ignores the first collider on a game object, so I can still detect a collider on that game object if it’s checked as a trigger, as long as that collider is not the first collider in the stack (inspector hierarchy).

I honestly don’t follow what you’re asking for here. It seems you’re not explaining something important because you either want a callback or you don’t and layers would do that. Is there some different layer/tags etc.

Ugh… the problem has been solved.

“Today is a good day to smile!” - Gowron, Tellytubbies.

Sorry, it seems I annoyed you? You replied but your reply wasn’t correct so I was trying to understand so I could suggest an alternative but I needed to understand first.

This part is incorrect. Ignore collision does what the docs say, ignores collisions between two colliders. It doesn’t matter the order of colliders on a GameObject which has nothing to do with physics which wouldn’t even know about that order.

Does it only ignore colliders that are not set as a “trigger”? The reason I’m confused here is because I had a collider that was 2nd in the game object’s inspector hierarchy. First was set as a trigger, and the second was not. I used Physics2D.IgnoreCollision(), and it would not ignore collision. I moved the “trigger” collider below the non-trigger collider, and it worked successfully. It ignored collision. This could have been a fluke, or confirmation bias, and I just hadn’t realized it at that point, but if you say it doesn’t work that way, then it doesn’t work that way.

No. If that were the case then it’d state that in the docs. Triggers are not special colliders; that option just tells the physics engine what do when a “contact” happens i.e. should it create contacts and calculate a collision response or not. This is after the ignore check because a “contact” has happened.

Ignore this order because the physics engine has no concept of GameObjects or even Unity Colliders. The physics engine runs at a low-level with physics shapes and bodies. Something like the ordering of components is another universe to it. It has no effect. Nada. :slight_smile:

Don’t worry about it, I get asked all sorts of questions, most of which are assuming that the physics engine “is” Unity and that it understands GameObjects, Colliders etc. Unity acts as an authoring system where components create low-level physics objects. It’s these physics objects that the physics engine uses and understands. Move a Unity component up in the GameObject list via the inspector; nothing whatsoever in physics will be affected by it as you do it.

The ignore collision thing just puts this collider pair into a hash-table. When the physics engine encounters something that may come into contact (broadphase) it performs a callback. At this point Unity is hooked into this callback and decides a yes/no if it can happen. One of the things checked here is whether the two physics shapes are part of a Unity Collider which is designated as ignoring each other.

In C++ code terms in the engine, there’s code like this callback from Box2D that returns false to indicate these two should never collide if it’s in the hash-map.

    virtual bool ShouldCollide(b2Fixture* fixtureA, b2Fixture* fixtureB) const
    {
        Collider2D* colliderA = reinterpret_cast<Collider2D*>(fixtureA->GetUserData());
        Collider2D* colliderB = reinterpret_cast<Collider2D*>(fixtureB->GetUserData());

        // Check if these colliders are set to ignore each other.
        if (m_PhysicsScene->GetIgnoreCollision(colliderA, colliderB))
            return false;

Yeah, it’s essentially a case of correlation does not equal causation.

As far as what’s happening behind the scenes here, that’s always good info, thanks.

Always remember, there’s nothing scarier than Gowron’s eyeballs.

1 Like

A fair point, well made. :slight_smile: