etqw-sdk/base/renderprogs/stuff.rprog

250 lines
8.0 KiB
Plaintext
Raw Permalink Normal View History

2008-05-29 00:00:00 +00:00
renderBinding grass_times { vector { 0 } }
/*
* The grass shader used by the stuff system, does sine wave wind and grass positioning
*/
renderProgram stuff/grass {
program vertex arb { <%
# This is not position invariant!
TEMP r0, r1, r2, r3, r4, r5, r7, r9, vert, scale, normal, normalMod;
PARAM mat[4] = { state.matrix.mvp };
PARAM taylor = { -0.16666666666666666666666666666667, 0.0083333333333333333333333333333333, -0.0001984126984126984126984126984127,
2.7557319223985890652557319223986e-6 };
PARAM waveDistortx = { 30, 20.0, 0.0, 0.0 };
PARAM waveDistortz = { 0.0, 0.0, 0.0, 0.0 };
PARAM waveDistorty = { 0.0, -10.0, 0.0, 0.0 };
PARAM waveDirx = { 0.001, 0.0, 0, 0 };
PARAM waveDiry = { 0.001,-0.001, 0, 0 };
PARAM waveSpeed = { 0.3, 0.6, 0.7, 1.4 };
PARAM piVector = {4.0, 1.5707963267948966192313216916398, 3.1415926535897932384626433832795, 6.283185307179586476925286766559 };
PARAM lightingWaveScale = { 0.35, 0.10, 0.10, 0.03 };
PARAM lightingScaleBias = { 0.6, 0.7, 0.2, 0.0 };
# Put the stuff on it's final spot
MOV vert, $positionAttrib;
# Calculate arguments for the sines
MUL r0, waveDirx, vert; # use vertex pos x as inputs to sinusoidal warp
MAD r0, waveDiry, vert, r0; # use vertex pos y as inputs to sinusoidal warp
ADD r0, $grass_times.x, r0; # add time to animate them
FRC r0, r0; # wrap to 0-1 interval
SUB r0, r0, 0.5; # subtract 0.5
MUL r1, r0, piVector.w; # *=2pi, means coords now range from(-pi to pi)
# Calculate powers
MUL r2, r1, r1; # (wave vec)^2
MUL r3, r2, r1; # (wave vec)^3
MUL r5, r3, r2; # (wave vec)^5
MUL r7, r5, r2; # (wave vec)^7
#MUL r9, r7, r2; # (wave vec)^9
# Approx sin with taylor coeffs
MAD r0, r3, taylor.x, r1; #(wave vec) - ((wave vec)^3)/3!
MAD r0, r5, taylor.y, r0; # + ((wave vec)^5)/5!
MAD r0, r7, taylor.z, r0; # - ((wave vec)^7)/7!
#MAD r0, r9, taylor.w, r0; # - ((wave vec)^9)/9!
# Every componenst of r0 contains the sin of a different argument
# sum them together to get the final offset value
DP4 r3.x, r0, waveDistortx;
DP4 r3.y, r0, waveDistorty;
# Calculate the amount of warping
MUL r4.xy, r3, $colorAttrib.w;
MOV r4.z, 0;
# Displace the vertex
MOV r2.w, 1;
ADD r2.xyz, r4, vert;# add sinusoidal warping to grass position
MAD normal, r3, $grass_times.w, $normalAttrib;
DP3 normal.w, normal, normal;
RSQ normal.w, normal.w;
MUL normal, normal, normal.w;
# do atmosphereing
#seTemplate atmosphere_ARB< r2, r1 >
#MUL scale, scale, r1.x;
#MUL scale, scale, r1.x; ##boost fog fade a bit
# Put it in projection space
DP4 result.position.x, r2, mat[0];
DP4 result.position.y, r2, mat[1];
DP4 result.position.z, r2, mat[2];
DP4 result.position.w, r2, mat[3];
# Output texcoords & light contribution
MOV result.texcoord[0], $texCoordAttrib;
MOV result.texcoord[1], normal; # normal map for ambient cubemap lookup
DP3 r2, normal, $sunDirection; # dot normal,sun
MAD r2, r2, 0.5, 0.5;
MUL result.color.xyz, r2, $sunColor; # multiply with sunlight color (WARNING: if the lightscale is to high this will get clamped to 0..1!)
MOV result.color.secondary, $colorAttrib; # vertex color
SUB r0, $positionAttrib, $viewOrigin;
DP3 scale, r0, r0;
MUL scale, scale, $stuffParameters.w;
RSQ scale.x, scale.x;
RCP scale.x, scale.x;
SLT r0, $foliageHackDistance.x, scale.x;
MAD scale.x, scale.x, $stuffParameters.y, -$stuffParameters.z;
SUB scale.x, 1, scale.x;
MUL result.color.w, scale.x, r0.x; # for fading
TEMP R1,R2;
SUB R2, $positionAttrib, $viewOrigin;
DP3 R1.x, R2, R2;
RSQ R1.y, R1.x;
MUL R1.x, R1.y, R1.x;
MAD result.texcoord[2].x, R1.x, $fogDepths.z, $fogDepths.w;
%> }
program fragment arb { <%
OPTION ARB_precision_hint_fastest;
TEMP r0, r1;
TEX r0, fragment.texcoord[0], $diffuseMap, 2D;
# use kill instead of alpha testing, this should theoretically be faster but also
# it means we can blend using a different alpha than the alpha we test against...
#
# Acutal benchmarks reveal kill is actually a very big bottleneck in this shader
# but alpha testing has a similar cost, it's probably early z-culling or whatever
# related stuff that causes this.
# Optimizing other parts of the shader seems useless only the kill and the
# dependencies seem to change the render time, hiding the kill dependencies
# between other instructions (to hide pipeline latency) seems to make no
# noticeable difference
SUB r1.a, r0, 0.5;
KIL r1.a;
TEX r1, fragment.texcoord[1], $ambientCubeMap, CUBE;
MUL r1, r1, $ambientBrightness;
MUL r0.rgb, r0, fragment.color.secondary; # diffuse color
ADD r1, r1, fragment.color; # add ambient and sun
MUL result.color, r0, r1; # final color
MUL result.color.a, r0.a, fragment.color.a; # distance scaled alpha
%> }
}
renderProgram stuff/grass_alphatestarb {
program vertex reference stuff/grass
program fragment arb { <%
OPTION ARB_precision_hint_fastest;
TEMP r0, r1;
TEMP r3;
MUL r3, fragment.position, 0.0625;
TEX r1, fragment.texcoord[1], $ambientCubeMap, CUBE;
TEMP noise;
TEX noise, r3, $noiseMap, 2D;
SLT noise.w, noise.w, fragment.color.a;
#KIL -noise.w; #alphaout.a;
TEX r0, fragment.texcoord[0], $diffuseMap, 2D;
MUL r1.w, noise.w, r0.w;
# use kill instead of alpha testing, this should theoretically be faster but also
# it means we can blend using a different alpha than the alpha we test against...
#
# Acutal benchmarks reveal kill is actually a very big bottleneck in this shader
# but alpha testing has a similar cost, it's probably early z-culling or whatever
# related stuff that causes this.
# Optimizing other parts of the shader seems useless only the kill and the
# dependencies seem to change the render time, hiding the kill dependencies
# between other instructions (to hide pipeline latency) seems to make no
# noticeable difference
SUB r3, r1, 0.4;
KIL r3.a;
MUL r1, r1, $ambientBrightness;
MUL r0.rgb, r0, fragment.color.secondary; # diffuse color
ADD r1, r1, fragment.color; # add ambient and sun
MUL result.color, r0, r1; # final color
MUL result.color.a, r0.a, 1.15;
#MOV result.color.rgb, noise.w; # distance scaled alpha
%> }
}
renderProgram stuff/grass_alphatestcg {
program vertex cg {
<%
struct VsInputs {
float3 norm : $normalAttrib;
float2 diff : $texCoordAttrib;
};
struct VsOutputs {
float2 diff : TEXCOORD0;
float3 norm : TEXCOORD1;
float4 color0 : COLOR;
float4 color1 : COLOR1;
};
VsOutputs vertex( VsInputs indata ) {
VsOutputs o;
$if r_32ByteVtx
indata.diff *= 1.f/4096.f;
$endif
o.color0 = 1;
o.color1 = 1;
o.norm = indata.norm;
o.diff = indata.diff;
return o;
}
%>
}
program fragment cg {
<%
struct VsOutputs {
float2 pos : WPOS;
float2 diff : TEXCOORD0;
float3 norm : TEXCOORD1;
float fog : TEXCOORD2;
float4 color0 : COLOR;
float4 color1 : COLOR1;
};
samplerCUBE ambientMap : $ambientCubeMap;
sampler2D noiseMap : $noiseMap;
sampler2D diffuseMap : $diffuseMap;
float4 ambientBrightness : $ambientBrightness;
float4 fogColor : $fogColor;
float4 fragment(VsOutputs indata) : COLOR {
float4 noise = tex2D( noiseMap, indata.diff * 3 );
if ( indata.color0.w < noise.w ) {
discard;
}
float4 diff = tex2D( diffuseMap, indata.diff );
if ( diff.w < 0.4 ) {
discard;
}
float3 amb = texCUBE( ambientMap, indata.norm ).rgb * ambientBrightness.rgb + indata.color0.rgb;
diff.rgb *= indata.color1.rgb;
diff.rgb *= amb;
diff.a *= 1.15f;
return float4( lerp( diff.rgb, fogColor.rgb, indata.fog ), diff.a );
}
%>
}
}
renderProgram stuff/grass_alphatest {
program vertex reference stuff/grass
program fragment reference stuff/grass_alphatestcg
}