Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

Resolved How to properly store all values to a compute buffer?

Discussion in 'Shaders' started by GodblessUnity, May 9, 2023.

  1. GodblessUnity

    GodblessUnity

    Joined:
    Sep 7, 2022
    Posts:
    2
    Hi,

    I have followed the three eyed raytracer guide to ray tracing with the aim to trace the propagation of the rays. I therefore want to store the data of each ray. I am new to shaders and therefore my knowledge is lacking.

    The problem I have is that I am unsure on how to store ALL my data into a RWStructuredBuffer. Should I use the SV_GroupIndex with the DispatchId somehow? The current solution is something I randomly found, it seems to work fine as I now can see the data of more rays than before (than by just using id.x or id.y), but I am unsure what I am actually doing here,
     uint index = id.x + id.y * 64;
    . How should one go about this problem? As far as I have seen there are no 2D arrays in HLSL and moreover arrays cannot be sent via compute buffer as it is not a blittable type?

    Edit: All I had to do was to multiply above with the amount the width specified in the dispatch call to get a correct result.

    Code (HLSL):
    1. [numthreads(64,1,1)]
    2. void CSMain(uint3 id : SV_DispatchThreadID, int id2 : SV_GroupIndex)
    3. {
    4.     _Pixel = id.xy;
    5.  
    6.     uint index = id.x + id.y * 64;
    7.  
    8.     // Get the dimensions of the RenderTexture
    9.     uint width, height;
    10.     Result.GetDimensions(width, height);
    11.  
    12.     // Transform pixel to [-1,1] range
    13.     float2 uv = float2((id.xy + _PixelOffset) / float2(width, height) * 2.0f - 1.0f);
    14.  
    15.     // Get a ray for the UVs
    16.     Ray ray = CreateCameraRay(uv);
    17.  
    18.     RayData rayData;
    19.     // Trace and shade the ray
    20.     float3 result = float3(0, 0, 0);
    21.     for (int i = 0; i < 8; i++)
    22.     {
    23.         RayHit hit = Trace(ray);
    24.         result += ray.energy * Shade(ray, hit);
    25.              
    26.         if (!any(ray.energy))
    27.             break;
    28.      
    29.         rayData.direction = ray.direction;
    30.         rayData.energy = ray.energy;
    31.         // we want total distance of one ray
    32.         rayData.origin = ray.origin;
    33.         rayData.distance += hit.distance;
    34.      }
    35.  
    36.     _Rays[index] = rayData;
    37.  
    38.     Result[id.xy] = float4(result, 1);
    39. }
    Code (CSharp):
    1.         // Set the target and dispatch the compute shader
    2.         RayTracingShader.SetTexture(0, "Result", _target);
    3.         int threadGroupsX = Mathf.CeilToInt(Screen.width / 64.0f);
    4.         int threadGroupsY = Mathf.CeilToInt(Screen.height ); /// 8.0f
    5.         RayTracingShader.Dispatch(0, threadGroupsX, threadGroupsY, 1);
    Thanks in advance!
     
    Last edited: May 9, 2023