How to make rigidbody gameobjects block each other without being able to be pushed by others

Hello,
so this is a question I came up with few days ago. It is not specific to any of the lectures but this could easily be part of one of the later 3D games that were developed during the Unity 3D course. I also asked this in the official Unity help room but did not get any answer so far. (https://answers.unity.com/questions/1571683/how-to-make-objects-block-each-other-without-being.html).
Its mostly about unitys physics engine, colliders and rigidbodies.

Lets pretend I want to develop a game that has these different types of gameobjects.

  • Player Characters (multiple)
  • Enemies
  • Static Objects (World)
  • And some gameplay objects that the player can pick up and move around

The physics interaction of these objects should be as follows:

  • Some kind of gravity for Players, gameplay objects and enemies
  • Enemies, Players and Gameplay objects should block each other
    • This means that if a player or enemy (called gameobject A) moves against a player/enemy/gameplay object (gameobject B), those objects should collide with eath other but B should not move as a result of the collision with A. So a player/enemy should not be able to push other players, enemies or gameplay objects around. (These kind of interactions should be like collisions between rigidbodies and static colliders, as if they would move against a wall).

Now to the problem or (for me) confusing part:
As we know in Unity its recommended to add a rigidbody (RB) component to any gameobject that has a collider and moves. This is due to performance reasons and to have these kind of objects not being treated as static colliders. In this example this means that players, enemies and gameplay objects all need to have a rigidbody component. With an RB attached they can now detect collisions with other colliders and do not simply ignore collisions and fall through the ground, etc. So thats good. But the problem now is that all of these objects can be pushed by each other through physics. For example when a player moves against another player or gameplay object as a result that object is moved by the moving player because of the collision and the resulting force being applied to these gameobjects. This is what i do not want. I just want them to collide (meaning that they cannot move through each other) but they should not be pushed by other gameobjects.

There are some “solutions” that i was experimenting with but did not achieve what i wanted. Like making (some of) them kinematic, which makes them not being pushed by rigidbodies (which is good) but they will no longer interact with each other because kinemaitc -> kinematic wont collide, so they just move through each other. Gravity also do not affect those objects anymore.
Another approach was using the constraints and locking the RB rotation and tranlation. This works half way. The good part is that the objects block each other and are also not pushed by others. But in Unity it is suggested to move an rigidbody object using his rb. By either using rb.moveposition or rb.addforce / rb.velocity = someVec3. But if the RB translation is locked the gameobjects wont be able to move. You would need to move them via the Transform component which is considered a no go for RB objects.This can also lead to wrong colliision detection as far as i undestood.
(Sidenote: And what if i simply want to move them using addforce because the movement should behave like that?)
So this cant be the right solution either.

I hope you understand what my question is about. I really dont understand what the default approach should look like for this kind of problem in unity. I also do not think that this is a very specific problem because this can affect a lot of games. So there must be solutions to this in unity. There are plenty of games that have different moving objects (in unity these should be RBs). And if those objects collide with eath other they do not move through each other and they also do not push each other around. They just behave like they would move against a “wall”.

I’m extremely new to Unity and C# having just less than a week in. But when I wanted to make a windmill obstacle for boost on my own I had a similar issue. The rocket was able to collide with and push the windmills in reverse. After thinking about it I realized the issue was mass. They both had a mass of 1. I scaled the windmill mass up to 10 so 10 times that of the rocket. It did the trick. Just had to remember to adjust the rotation force on the windmill to account for the new mass. Now my rocket doesn’t stand a chance against them. lol. Since I’m new this may be a temp/terrible fix, but it did work for my case.

Did not check the date on this post. lol. My bad.

Adjusting the mass does not fix my problem. The thing is mass works only relative. So this might work for a player <-> enemy interaction. If player has mass of 1 and enemy 10 then player wont be able to push enemy. But enemy can push player. There is also another problem. Lets say there are 2 enemies. One of them is just standing, the other one is moving towards you. The enemies just have a simple ai so he will move a straight line to you. The enemy who is just standing is between you and the enemy chasing you. Now both enemies have the same mass. This means that the enemy moving towards you will push the enemy who is just standing because their masses are the same.

I think the problem is because unity expects you to use rigidbodies for every object that has a collider and moves. Thats because of performance reasons. If an object with an collider does not have a rb it is treated as a static collider. If a static collider moves. The static collider cache must be reevaluated. I dont know if this is actually still a thing with the newer unity versions or just in the older versions. But there are still official tutorials that suggest to put rb on those objects and also the docs point this out. And attaching a rb to an object enables physics. You can deactivate physics by marking the object kinematic but then no collision detection is performed. This allows then every moving kinematic object to move thorugh other kinematic / static objects.
So if a player is rb non kinematic and every thing else that moves is kinematic, this works for interactions between player and those kinematic objects. But they will still be able to push the player. But the worse part is that the kinematic objects wont have any collision with each other. And if you dont just have enemies but other objects as kinematic like some items that you as a player can carry around, the enemys can just move through them.

You need a stopping distance for the player and the enemies.
The reason for this is because they are trying to get to the origin point, I believe we hint at a solution in where we stop Ethan our temporary placeholder from running into objects because the destination is at the origin so he never reached it.

The same can probably be reversed to place on the enemies and detected when they are a set distance from the player stop and attack rather than keep pushing into the enemy whilst attacking.

Hope this helps and if you havent got the RPG course i think this might help with a lot of the things here :slight_smile:

This topic was automatically closed 24 hours after the last reply. New replies are no longer allowed.

Privacy & Terms