More Related Content Similar to [shaderx5] 3.2 Selective Supersampling Similar to [shaderx5] 3.2 Selective Supersampling (20) [shaderx5] 3.2 Selective Supersampling1. SHADERX5
shader study http://cafe.naver.com/shader.cafe
ohyecloudy http://ohyecloudy.com
2010.03.22
6. No selective-supersampling selective-supersampling
• high-frequency component가 문제
– specular highlight가 어른거리게 만든다
– 밉맵mip-map을 사용하는 이유와 같다.
8. multisampling
supersampling
• hybrid solution
– edge : multisampling
– aliasing 문제가 있는 부분 : supersampling
10. float4 vfSum = 0.0;
for (int i = 0; i < SAMPLE_COUNT; i++)
{
vfSum += OriginalShader(sampleCoordinate[i]);
}
return vfSum / SAMPLE_COUNT;
좀 더 정확하게 근사하자.
ddx와 ddy를 사용
11. A
ddx
ddy
texture
projection
OR A’s ddx != B’s ddx
A’s ddy != B’s ddy
B
ddx
ddx
ddy
Returns the partial derivative of the specified value with respect to
the screen-space x-coordinate.
ddy
Returns the partial derivative of the specified value with respect to
the screen-space y-coordinate.
12. const float2 fSamples[SAMPLE_COUNT] =
{
// using a rotated grid
float2( 0.125, 0.375),
float2( 0.375, -0.125),
float2(-0.125, -0.375),
float2(-0.375, 0.125),
};
// compute gradients
float2 fDX = ddx(texCoord);
float2 fDY = ddy(texCoord);
float4 vfSum = 0.0;
for (int i = 0; i < SAMPLE_COUNT; ++i)
{
float2 vfSampleCoord =
texCoord + fSamples[i].x * fDX + fSamples[i].y * fDY;
vfSum += OriginalShader(vfSampleCoord);
}
return vfSum / SAMPLE_COUNT;
14. float4 main(
float2 texCoord : TEXCOORD0,
float3 vnLight : TEXCOORD1) : COLOR
{
// compute the gradients of the texture coordinates
float2 fDX = ddx(texCoord);
float2 fDY = ddy(texCoord);
// Compute lighting
라이팅은 그냥 수행
float3 vBase = tex2D(tBase, texCoord).rgb;
float3 vBump = tex2D(tBump, texCoord).xyz;
float3 vNormal = normalize(vBump*2.0 – 1.0); // [0,1] -> [-1,1]
float3 cAmbient = 0.15 * vBase;
float fDiffuse = saturate(dot(vLight, vNormal));
float fSpecular = specular만 selective supersampling
(SPECULAR(vNormal) +
SPECULAR(SAMPLENORMAL( 0.25, 0.75)) +
SPECULAR(SAMPLENORMAL(-0.25,-0.75)) +
SPECULAR(SAMPLENORMAL(-0.75, 0.25)) +
SPECULAR(SAMPLENORMAL( 0.75,-0.25))) / 5.0;
return float4(cAmbient + fDiffuse * vBase + fSpecular, 0);
}
#define SAMPLENORMAL(x, y)
normalize(tex2D(tBump, texCoord + (0.5*x) * fDX + (0.5*y) * fDY).xyz * 2.0 – 1.0)
15. // Center sample
float fSpecular = SPECULAR(vNormal);
// Compute specular gradients
float2 ds = float2(ddx(fSpecular), ddy(fSpecular));
// If it’s above the threshold, then take the other four samples too
if (dot(ds, ds) > 0.0002)
{
fSpecular += SPECULAR(SAMPLENORMAL( 0.25, 0.75));
fSpecular += SPECULAR(SAMPLENORMAL(-0.25,-0.75));
fSpecular += SPECULAR(SAMPLENORMAL(-0.75, 0.25));
fSpecular += SPECULAR(SAMPLENORMAL( 0.75,-0.25));
fSpecular /= 5.0;
}
dynamic branch
threshold를 둬서 넘으면 supersampling
17. • 성능을 위해 multisampling을 쓰는 경우
internal aliasing 문제가 발생할 수 있다.
• 발생하는 부분만 supersampling을 사용해서
문제를 해결할 수 있다.
– 전체 supersampling보다는 퍼포먼스