Search Unity

CollisionWorld.CastRay 10x slower than Physics.Raycast.

Discussion in 'Physics for ECS' started by MNNoxMortem, Mar 1, 2022.

  1. MNNoxMortem

    MNNoxMortem

    Joined:
    Sep 11, 2016
    Posts:
    723
    I have two examples scenes, which both load the same Mesh Collider, once as a GameObject, once as a Unity.Physics.Collider. Then I perform a simple raycast on click. It looks like CollisionWorld.CastRay is 10x as slow as Physics.CastRay.

    I have enabled burst, disabled Safety Checks and Native Debug Mode Compilation.
    upload_2022-3-1_16-3-10.png
    upload_2022-3-1_16-3-52.png
    Tried it with and without burst.

    CollisionWorld.CastRay is using the example code from Unity.Physics https://docs.unity3d.com/Packages/com.unity.physics@0.6/manual/collision_queries.html

    Code (CSharp):
    1.  
    2. // Physics.CastRay
    3. // bool result = Physics.Raycast(ray, out var hit);
    4. Hit (-15,3, -1,0, -93,2) after 0 ms or 63 ticks
    5. Hit (-15,3, -1,0, -93,2) after 0 ms or 54 ticks
    6.  
    Code (CSharp):
    1.  
    2. // CollisionWorld.CastRay
    3. Hit float3(-15,33019f, 0,474617f, -73,96638f) after 0 ms or 755 ticks
    4. Hit float3(-15,33019f, 0,474617f, -73,96638f) after 0 ms or 747 ticks
    5.  
    And while it becomes faster in an IL2CPP Release build compared to the editor, it is still much slower. I am wondering why it is so much slower and what differences could influence this. I would have expected it to be pretty much the same.

    Code (CSharp):
    1. // IL2CPP Release Physics.Raycast
    2. Hit (3,4, -0,6, -4,6) after 0 ms or 36 ticks
    Code (CSharp):
    1. // IL2CPP Release CollisionWorld.CastRay
    2. Hit float3(0,8347985f, 2,100365f, -58,24535f) after 0 ms or 254 ticks
    I am wondering if this is because of the general degradation noticed here https://forum.unity.com/threads/unity-physics-performance-degraded-since-2020-3-16.1207051/

    I am using Unity 2020.3.27f1 with the following packages
    Code (csharp):
    1. "com.havok.physics": "0.6.0-preview.3",
    2. "com.unity.jobs": "0.8.0-preview.23",
    3. "com.unity.mathematics": "1.2.5",
    4. "com.unity.entities": "0.17.0-preview.42",
    5. "com.unity.rendering.hybrid": "0.11.0-preview.43",
    6. "com.unity.collections": "0.15.0-preview.21",
    7. "com.unity.platforms": "0.5.0-preview.6",
    8. "com.unity.platforms.windows": "0.10.0-preview.10",
    9.  
     
    Last edited: Mar 1, 2022
  2. tertle

    tertle

    Joined:
    Jan 25, 2011
    Posts:
    3,759
    Are you doing this on main thread? Because yes it's going to be reasonably slow then. Try it with burst.
     
    Last edited: Mar 4, 2022
    MNNoxMortem likes this.
  3. MNNoxMortem

    MNNoxMortem

    Joined:
    Sep 11, 2016
    Posts:
    723
    @tertle as written I have tried it with burst.
    Yes, both cases are called from the main thread from a MonoBehaviour.Update, as Physics.CastRay is a sync call as well and completes within the same frame. Otherwise it would not be that easy to compare both, wouldn't it be ;)?

    Code (csharp):
    1.  
    2. private void Update(){
    3.   if (Input.GetKeyDown(KeyCode.Mouse0) && Input.GetKey(KeyCode.LeftAlt))
    4.     ...
    5.     bool result = Physics.Raycast(ray, out var hit);
    6.     ...
    7.  
    Code (csharp):
    1.  
    2. private void Update(){
    3.   if (Input.GetKeyDown(KeyCode.Mouse0) && Input.GetKey(KeyCode.LeftAlt))
    4.     ...
    5.     var physicsWorldSystem =
    6. World.DefaultGameObjectInjectionWorld.GetOrCreateSystem<Unity.Physics.Systems.BuildPhysicsWorld>();
    7.     CollisionWorld collisionWorld = physicsWorldSystem.PhysicsWorld.CollisionWorld;
    8.     var input = new RaycastInput
    9.     {
    10.       Start = RayFrom,
    11.       End   = RayTo,
    12.       Filter = new CollisionFilter
    13.       {
    14.         BelongsTo    = ~0u,
    15.         CollidesWith = ~0u, // all 1s, so all layers, collide with everything
    16.         GroupIndex   = 0
    17.       }
    18.     };
    19.     bool haveHit = collisionWorld.CastRay(input, out hit);
    20.     ...
    21.  
     
    Last edited: Mar 4, 2022
  4. lclemens

    lclemens

    Joined:
    Feb 15, 2020
    Posts:
    761
    Hmmm that is odd. Do you have your benchmark in a repo that we could run?