Jump to content
  • Advertisement
Sign in to follow this  
pnt1614

Perspective divison without the clipping in stochastic rasterization

This topic is 804 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I am trying to implement the stochastic rasterization based on the paper: "Real-Time Stochastic Rasterization on Conventional  GPU Architectures" and provided pseudo code. But I do not understand how they address a problem as a triangle moves to/from a position behind the camera ("crossing z=0" in the paper) in the geometry shader. To handle the "crossing z = 0" problem, they generate a 2D AABB to contain all vertices behind the camera then find an intersection between an edge and the near plane and use this intersection point to update the 2D AABB. As generating a 2D AABB to contain all vertices behind the camera, they perform perspective divison without clipping and I think this yield a incorrect result.

 

I have implemented the following shader code in the geometry shader using DirectX 11 and HLSL 5.0

void intersectNear(float3 start, float3 end, inout float2 minXY, inout float2 maxXY)
{
    float denom = end.z - start.z;
    if (abs(denom) > 0.0001)
    {
        float a = (nearPlaneZ - start.z) / denom;
        if ((a >= 0.0) && (a < 1.0))
        {
   	     // Intersection point in camera space
	     float3 cs = float3(lerp(start.xy, end.xy, a), nearPlaneZ);

	     // Intersection point in screen space
	     float2 ss = project42(mul(float4(cs, 1.0), g_mProj));
	     minXY = min(minXY, ss);
	     maxXY = max(maxXY, ss);
        }
    }
}

void ST_GS(triangle VS_OUTPUT input[3] : SV_POSITION, inout TriangleStream<GS_OUTPUT_ST> output)
{
        ......

        float4 ssP0A = input[0].Prev_hPos; // A0 in the clip space
	float4 ssP0B = input[1].Prev_hPos; // B0 in the clip space
	float4 ssP0C = input[2].Prev_hPos; // C0 in the clip space

	float4 ssP1A = input[0].Curr_hPos; // A1 in the clip space
	float4 ssP1B = input[1].Curr_hPos; // B1 in the clip space
	float4 ssP1C = input[2].Curr_hPos; // C1 in the clip space


        // scaled depth values in the view space
        float minDepth = min6(input[0].Prev_vPos.z, input[1].Prev_vPos.z, input[2].Prev_vPos.z,
				input[0].Curr_vPos.z, input[1].Curr_vPos.z, input[2].Curr_vPos.z)  / far_plane;
				
        float maxDepth = max6(input[0].Prev_vPos.z, input[1].Prev_vPos.z, input[2].Prev_vPos.z,
				input[0].Curr_vPos.z, input[1].Curr_vPos.z, input[2].Curr_vPos.z) / far_plane;


       
        if (maxDepth < near_plane || minDepth > 1.0f)
        {
            return; // Out of view frustrum
        }		
	else if (minDepth < 0.0f)
	{
   	    float2 clipMin = float2(-1.0f, -1.0f);
	    float2 clipMax = float2(1.0f, 1.0f);

	    // Make 2D AABB
	    // Grow the 2D AABB to contain all points with z < z_near
	    if (input[0].Prev_vPos.z < nearPlaneZ)
	    {
		float2 v = project42(ssP0A);
		clipMin = min(clipMin, v);
		clipMax = max(clipMax, v);
			}
	    if (input[1].Prev_vPos.z < nearPlaneZ)
	    {
		float2 v = project42(ssP0B);
		clipMin = min(clipMin, v);
		clipMax = max(clipMax, v);
	    }

	    if (input[2].Prev_vPos.z < nearPlaneZ)
     	    {
		float2 v = project42(ssP0C);
		clipMin = min(clipMin, v);
		clipMax = max(clipMax, v);
	    }


	    if (input[0].Curr_vPos.z < nearPlaneZ)
	    {
		float2 v = project42(ssP1A);
		clipMin = min(clipMin, v);
		clipMax = max(clipMax, v);
	    }
		
  	    if (input[1].Curr_vPos.z < nearPlaneZ)
	    {
		float2 v = project42(ssP1B);
		clipMin = min(clipMin, v);
		clipMax = max(clipMax, v);
	    }

   	    if (input[2].Curr_vPos.z < nearPlaneZ)
	    {
		float2 v = project42(ssP1C);
		clipMin = min(clipMin, v);
		clipMax = max(clipMax, v);
	    }


	    // Viewport clips the generated 2D AABB
	    intersectNear(input[0].Prev_vPos.xyz, input[1].Prev_vPos.xyz, clipMin, clipMax);
	    intersectNear(input[1].Prev_vPos.xyz, input[2].Prev_vPos.xyz, clipMin, clipMax);
	    intersectNear(input[2].Prev_vPos.xyz, input[0].Prev_vPos.xyz, clipMin, clipMax);

	    intersectNear(input[0].Curr_vPos.xyz, input[1].Curr_vPos.xyz, clipMin, clipMax);
	    intersectNear(input[1].Curr_vPos.xyz, input[2].Curr_vPos.xyz, clipMin, clipMax);
	    intersectNear(input[2].Curr_vPos.xyz, input[0].Curr_vPos.xyz, clipMin, clipMax);

	    intersectNear(input[0].Prev_vPos.xyz, input[0].Curr_vPos.xyz, clipMin, clipMax);
	    intersectNear(input[1].Prev_vPos.xyz, input[1].Curr_vPos.xyz, clipMin, clipMax);
	    intersectNear(input[2].Prev_vPos.xyz, input[2].Curr_vPos.xyz, clipMin, clipMax);


	    // Output a quad
	    points[0].posH = float4(clipMax.x, clipMin.y, nearPlaneDepth, 1.0);
	    points[1].posH = float4(clipMax.x, clipMax.y, nearPlaneDepth, 1.0);
	    points[2].posH = float4(clipMin.x, clipMin.y, nearPlaneDepth, 1.0);
	    points[3].posH = float4(clipMin.x, clipMax.y, nearPlaneDepth, 1.0);
					
	
	    output.Append(points[0]);
	    output.Append(points[1]);
	    output.Append(points[2]);
	    output.Append(points[3]);
	    output.RestartStrip();

	    return;
}

I am not sure that this is the limitation of this paper or I do not understand this stage. Is there anyone understood this paper or this stage? Please help me. Thanks in advance.

Share this post


Link to post
Share on other sites
Advertisement
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

GameDev.net is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!