|
|
(15 intermediate revisions by one user not shown) |
Line 1: |
Line 1: |
− | ##############################################################
| + | define TransparentMirrorReflection() |
− | # Pool Water
| + | material |
− | #
| + | if (viewerRenderType = $kRenderTypeShadow) |
− | | + | create StandardShaderShadow() |
− | seti poolWaterLayer 5
| + | else |
− | | + | if (viewerRenderType = $kRenderTypeThumbnail) |
− | | + | create TransparentBlankMirrorMaterial($kRenderTypeThumbnail) |
− | ##############################################################
| + | else |
− | # Simple water material
| + | if (not $mirrorReflectionsEnabled) |
− | #
| + | set currentType (viewerRenderType) |
− | # This material modulates the vertices by two sin waves --
| + | create TransparentBlankMirrorMaterial($currentType) |
− | # one in X and one in Y. It then produces reflection and
| + | |
− | # refraction direction texture coordinates suitable for a
| + | |
− | # cubic environment map.
| + | |
− | | + | |
− | | + | |
− | #beginshader PoolWaterMaterialTwoWave
| + | |
− | #description Pool water with X/Y waves
| + | |
− | | + | |
− | #BeginStdAttrBlock
| + | |
− | | + | |
− | | + | |
− | setf wmTransparency 0.5
| + | |
− | #attrdescription Water transparency
| + | |
− | | + | |
− | setf wmXSpeed 3 # min:0 max:100
| + | |
− | #attrdescription Lookup texture for diffuse intensity.
| + | |
− | setf wmXRepeat 1 # min:0 max:100
| + | |
− | #attrdescription Lookup texture for diffuse intensity.
| + | |
− | setf wmXWaveHeight 0.1 # min:0 max:100
| + | |
− | #attrdescription Lookup texture for diffuse intensity.
| + | |
− | | + | |
− | setf wmYSpeed 5 # min:0 max:100
| + | |
− | #attrdescription Lookup texture for diffuse intensity.
| + | |
− | setf wmYRepeat 1.8 # min:0 max:100
| + | |
− | #attrdescription Lookup texture for diffuse intensity.
| + | |
− | setf wmYWaveHeight 0.2 # min:0 max:100
| + | |
− | #attrdescription Lookup texture for diffuse intensity.
| + | |
− | | + | |
− | set wmReflectionTexture reflectionoutdoorwater-envcube
| + | |
− | #attrdescription Environment cube map texture for reflection
| + | |
− | | + | |
− | setb wmRefractionEnabled false
| + | |
− | #attrdescription Whether refraction is enabled
| + | |
− | | + | |
− | set wmRefractionTexture reflectionoutdoorwater-envcube
| + | |
− | #attrdescription Environment cube map texture for refraction
| + | |
− | | + | |
− | | + | |
− | #EndStdAttrBlock
| + | |
− | | + | |
− | define PoolWaterSurfaceMaterial() | + | |
− | material | + | |
− | shader -layer $poolWaterLayer | + | |
− | validateRenderShaderContext -vertexFormat position 0 required
| + | |
− |
| + | |
− | create DetermineHardwareSupport() | + | |
− |
| + | |
− | if ($useSWVertexShaderPath or $useFixedFunctionPath) | + | |
− | # The vertex shader to ripple the water surface is deemed too expensive for SWVS. | + | |
− | # Note that because on some low-end cards shaders are turned off, DetermineHardwareSupport()
| + | |
− | # will set $useFixedFunctionPath to true and $useSWVertexShaderPath to false; however,
| + | |
− | # since the device is in swvp mode, the RegularWavesHLSL shader would validate anyway, which
| + | |
− | # we don't want. Therefore here we do the simplified water surface if using either SWVS or FFP.
| + | |
− | create SimplifiedWaterSurface()
| + | |
− | else | + | |
− | if ($useHWShader2Path) | + | |
− | create HighEndWaterSurface() | + | |
| else | | else |
− | create RegularWavesHLSL() | + | create TransparentMirrorReflectionMaterial() |
− | endif | + | endif |
− | endif | + | endif |
− |
| + | endif |
− | end #end shader | + | |
− |
| + | |
− | # basic fallback.
| + | |
− | shader -layer $poolWaterLayer
| + | |
− | create SimplifiedWaterSurface()
| + | |
− | end #end shader
| + | |
− |
| + | |
− | end #end material
| + | |
− | enddef
| + | |
− | | + | |
− | define SimplifiedWaterSurface()
| + | |
− | pass -fixedFunction
| + | |
− | alphaBlend srcFactor(srcAlpha) add dstFactor(invSrcAlpha)
| + | |
− | depthTest true -enableDepthWrite false
| + | |
− | colorScalar (0.2,0.3,1.0) 0.4
| + | |
− | stage
| + | |
− | textureBlend select(colorScalar) select(colorScalar)
| + | |
− | end
| + | |
| end | | end |
| enddef | | enddef |
| | | |
− | | + | define TransparentBlankMirrorMaterial(renderType) |
− | define RegularWavesHLSL() | + | shader |
− |
| + | validateRenderShaderContext -viewerRenderType &renderType |
− | #DRIVERBUG
| + | |
− | # The -clipAlways flag is needed to work around what appears to be a driver bug.
| + | |
− | # On NVIDIA GF2 class HW, the presence of the cube map texture in the pass below
| + | |
− | # leads to a large performance drop whenever the pass is rendered with clipping disabled.
| + | |
− | # Rendering this pass with clipping enabled avoids the performance drop. In addition,
| + | |
− | # substituting a 2D texture for the cube map texture, or rendering this pass in HW
| + | |
− | # using fixed function vertex processing also avoids the performance drop (but would obviously
| + | |
− | # not have the desired visual result).
| + | |
− | # The cause of this is unknown. This was observed on a GF4GO, driver version 42.58.
| + | |
− | pass -clipAlways -modifiedEachFrameHint
| + | |
− | #fillmode wireframe
| + | |
− | alphaBlend srcFactor(one) add dstFactor(one)
| + | |
− | seti textureLights (numLightsOfType(environmentCube)) | + | |
− |
| + | |
− | shaderProgram -target vertexProgram -method compile -version 1_1
| + | |
− | | + | |
− | bindConstants 0 -bindingID geomToClip -constantCount 4
| + | |
− | bindConstants 4 -bindingID geomToCamera -constantCount 3
| + | |
− | | + | |
− | bindConstants 7 -bindingID frameInfo
| + | |
− | | + | |
− | bindConstants 11 -bindingID immediateData -data ($wmXRepeat, 0, $wmXWaveHeight, $wmXSpeed)
| + | |
− | bindConstants 12 -bindingID immediateData -data (0, $wmYRepeat, $wmYWaveHeight, $wmYSpeed)
| + | |
− | | + | |
− | # pre-evaluate these
| + | |
− | setf xscale (-$wmXRepeat * $wmXWaveHeight)
| + | |
− | setf yscale (-$wmYRepeat * $wmYWaveHeight)
| + | |
− | bindConstants 13 -bindingID immediateData -data ($xscale,$yscale, 1,0)
| + | |
− | bindConstants 14 -bindingID allStandardLightData -constantCount 4 -constantType float
| + | |
− | bindConstants 18 -bindingID cameraToGlobal -constantCount 3
| + | |
| | | |
− | if (tsIsDay) | + | pass |
− | bindConstants 25 -bindingID immediateData -data (0.75, 0.75, 0.75, 1) | + | shaderProgram -target vertexProgram -method assemble |
− | else
| + | bindConstants 0 -bindingID geomToClip -constantCount 4 |
− | bindConstants 25 -bindingID immediateData -data (0.2, 0.2, 0.2, 1)
| + | shaderSource |
− | endif
| + | vs_1_1 |
− | | + | dcl_position v0 |
− | shaderSource
| + | m4x4 oPos, v0, c0 |
− | | + | endShaderSource |
− | float4 frameInfo : register(c7);
| + | end |
− | float4 waveDataX : register(c11);
| + | |
− | float4 waveDataY : register(c12);
| + | |
− | float4 waveDataHelper : register(c13);
| + | |
− | float4x4 clipSpaceMatrix : register(c0);
| + | |
− | float4x3 cameraSpaceMatrix : register(c4);
| + | |
− | float4x3 cameraToGlobalMatrix : register(c18);
| + | |
− |
| + | |
− | float4 nightColor: register(c25); | + | |
| | | |
− | float4 lightDirection : register(c14);
| + | colorScalar (0,0,0) 0.5 |
− | float4 lightColor : register(c15);
| + | stage |
− | const static float4 refractionWeights={1,1,2,0};
| + | textureBlend select(colorScalar) select(colorScalar) |
− |
| + | end |
− | const static float4 layerBlue={0.3, 0.7, 1.0, 1};
| + | end |
− |
| + | end |
− | struct InputVertex
| + | |
− | {
| + | |
− | float3 position: POSITION0;
| + | |
− | float3 normal : NORMAL0;
| + | |
− | };
| + | |
− |
| + | |
− | struct OutputVertex
| + | |
− | {
| + | |
− | float4 clipPosition : POSITION;
| + | |
− | float4 diffuseColor: COLOR0;
| + | |
− | float4 specularColor: COLOR1;
| + | |
− | float3 reflection : TEXCOORD0;
| + | |
− |
| + | |
− | };
| + | |
− | | + | |
− |
| + | |
− |
| + | |
− | OutputVertex VertexMain( InputVertex inputVertex)
| + | |
− | {
| + | |
− | // Do Y-direction waves
| + | |
− | // r0 = (x, y, z, t)
| + | |
− |
| + | |
− | OutputVertex outputVertex;
| + | |
− |
| + | |
− | float4 posAndTime;
| + | |
− | posAndTime.xyz = inputVertex.position;
| + | |
− | posAndTime.w = frameInfo.w;
| + | |
− |
| + | |
− | float temp = dot(posAndTime, waveDataX);
| + | |
− |
| + | |
− | // z = h * sin(...)
| + | |
− | | + | |
− | float z;
| + | |
− | // scale temp to fit -pi +pi range
| + | |
− | //temp = temp * (1 / (2 * 3.14159)) + 0.5;
| + | |
− |
| + | |
− | float3 waveNormal;
| + | |
− |
| + | |
− | z = sin(temp) * waveDataX.z + inputVertex.position.z;
| + | |
− |
| + | |
− | waveNormal.x = cos(temp) * waveDataHelper.x + inputVertex.normal.x;
| + | |
− |
| + | |
− | temp = dot(posAndTime, waveDataY);
| + | |
− | //temp = temp * (1 / (2 * 3.14159)) + 0.5;
| + | |
− |
| + | |
− | z += sin(temp) * waveDataY.z;
| + | |
− |
| + | |
− | waveNormal.y = cos(temp) * waveDataHelper.y + inputVertex.normal.y;
| + | |
− |
| + | |
− | waveNormal.z = inputVertex.normal.z;
| + | |
− |
| + | |
− | waveNormal = normalize(waveNormal);
| + | |
− |
| + | |
− | posAndTime.w = 1.0;
| + | |
− | posAndTime.z = z;
| + | |
− |
| + | |
− | outputVertex.clipPosition = mul( posAndTime, clipSpaceMatrix);
| + | |
− |
| + | |
− | float3 cameraSpaceNormal = normalize(mul(waveNormal, cameraSpaceMatrix));
| + | |
− | | + | |
− | float3 cameraSpacePosition = mul( posAndTime, cameraSpaceMatrix);
| + | |
− |
| + | |
− | float3 viewVector = normalize(-cameraSpacePosition);
| + | |
− |
| + | |
− | float3 R = reflect(viewVector, cameraSpaceNormal);
| + | |
− |
| + | |
− | outputVertex.reflection = mul( -R, cameraToGlobalMatrix);
| + | |
− |
| + | |
− |
| + | |
− | float fresnel = dot(viewVector , cameraSpaceNormal);
| + | |
− |
| + | |
− | float rdotl = saturate(dot(R, lightDirection));
| + | |
− |
| + | |
− | float I = pow(rdotl+0.1, 15); // fudge factor to punch up the highlights.
| + | |
− |
| + | |
− | nightColor = nightColor * 2;
| + | |
− |
| + | |
− | outputVertex.diffuseColor = ((1.0 - fresnel) * saturate(nightColor) * 0.5) * layerBlue;
| + | |
− |
| + | |
− | outputVertex.specularColor = I;
| + | |
− | return(outputVertex);
| + | |
− |
| + | |
− | }
| + | |
− | | + | |
− | | + | |
− | endShaderSource
| + | |
− | end # shaderProgram
| + | |
− |
| + | |
− | stage
| + | |
− | texture $wmReflectionTexture
| + | |
− | textureAddressing clamp clamp clamp
| + | |
− | textureBlend multiply(texture diffuse) select(diffuse)
| + | |
− | end
| + | |
− |
| + | |
− | | + | |
− | addSpecular true
| + | |
− |
| + | |
− | end # end pass
| + | |
− | | + | |
− | | + | |
| enddef | | enddef |
| | | |
− | | + | define TransparentMirrorReflectionMaterial() |
− | define HighEndWaterSurface() | + | |
− |
| + | |
− | pass -clipAlways -modifiedEachFrameHint
| + | |
− | #fillmode wireframe
| + | |
− | alphaBlend srcFactor(srcAlpha) add dstFactor(invSrcAlpha)
| + | |
− | seti textureLights (numLightsOfType(environmentCube))
| + | |
− | depthTest true -enableDepthWrite false
| + | |
− |
| + | |
− | shaderProgram -target vertexProgram -method compile -version 1_1
| + | |
− | | + | |
− | bindConstants 0 -bindingID geomToClip -constantCount 4
| + | |
− | bindConstants 4 -bindingID geomToCamera -constantCount 3
| + | |
− | | + | |
− | bindConstants 7 -bindingID frameInfo
| + | |
− | | + | |
− | bindConstants 11 -bindingID immediateData -data ($wmXRepeat, 0, $wmXWaveHeight, $wmXSpeed)
| + | |
− | bindConstants 12 -bindingID immediateData -data (0, $wmYRepeat, $wmYWaveHeight, $wmYSpeed)
| + | |
− | | + | |
− | # pre-evaluate these
| + | |
− | setf xscale (-$wmXRepeat * $wmXWaveHeight)
| + | |
− | setf yscale (-$wmYRepeat * $wmYWaveHeight)
| + | |
− | bindConstants 13 -bindingID immediateData -data ($xscale,$yscale, 1,0)
| + | |
− | bindConstants 14 -bindingID allStandardLightData -constantCount 4 -constantType float
| + | |
− | bindConstants 18 -bindingID cameraToGlobal -constantCount 3
| + | |
− | bindConstants 21 -bindingID cameraToGeom -constantCount 3
| + | |
− |
| + | |
− | if (tsIsDay)
| + | |
− | bindConstants 25 -bindingID immediateData -data (0.75, 0.75, 0.75, 1)
| + | |
− | else
| + | |
− | bindConstants 25 -bindingID immediateData -data (0.2, 0.2, 0.2, 1)
| + | |
− | endif
| + | |
− | | + | |
− | shaderSource
| + | |
− | | + | |
− | float4 frameInfo : register(c7);
| + | |
− | float4 waveDataX : register(c11);
| + | |
− | float4 waveDataY : register(c12);
| + | |
− | float4 waveDataHelper : register(c13);
| + | |
− | float4x4 clipSpaceMatrix : register(c0);
| + | |
− | float4x3 cameraSpaceMatrix : register(c4);
| + | |
− | float4x3 cameraToGlobalMatrix : register(c18);
| + | |
− | float4x3 cameraToGeomMatrix : register(c21);
| + | |
− |
| + | |
− |
| + | |
− | float4 nightColor: register(c25);
| + | |
− |
| + | |
− | float4 lightDirection : register(c14);
| + | |
− | float4 lightColor : register(c15);
| + | |
− | float4 lightSpecular : register(c16);
| + | |
− | const static float4 refractionWeights={1,1,2,0};
| + | |
− |
| + | |
− | const static float4 layerBlue={0.3, 0.7, 1.0, 1};
| + | |
− |
| + | |
− | struct InputVertex
| + | |
− | {
| + | |
− | float3 position: POSITION0;
| + | |
− | float3 normal : NORMAL0;
| + | |
− | };
| + | |
− |
| + | |
− | struct OutputVertex
| + | |
− | {
| + | |
− | float4 clipPosition : POSITION;
| + | |
− | float4 sPos : TEXCOORD0;
| + | |
− | float2 Wave0 : TEXCOORD1;
| + | |
− | float2 Wave1 : TEXCOORD2;
| + | |
− | float2 Wave2 : TEXCOORD3;
| + | |
− | float2 Wave3 : TEXCOORD4;
| + | |
− | float3 Eye : TEXCOORD5;
| + | |
− | float4 specular : COLOR0;
| + | |
− | };
| + | |
− |
| + | |
− |
| + | |
− |
| + | |
− | OutputVertex VertexMain( InputVertex inputVertex)
| + | |
− | {
| + | |
− | // Do Y-direction waves
| + | |
− | // r0 = (x, y, z, t)
| + | |
− |
| + | |
− | OutputVertex outputVertex;
| + | |
− |
| + | |
− | float4 posAndTime;
| + | |
− | posAndTime.xyz = inputVertex.position;
| + | |
− | posAndTime.w = frameInfo.w;
| + | |
− |
| + | |
− | float temp = dot(posAndTime, waveDataX);
| + | |
− | float z = sin(temp) * waveDataX.z + inputVertex.position.z;
| + | |
− | temp = dot(posAndTime, waveDataY);
| + | |
− | posAndTime.z = z + sin(temp) * waveDataY.z;
| + | |
− | posAndTime.w = 1.0f;
| + | |
− |
| + | |
− | outputVertex.clipPosition = mul( posAndTime, clipSpaceMatrix);
| + | |
− | outputVertex.sPos = float4(0.5f*(outputVertex.clipPosition.ww - outputVertex.clipPosition.xy), outputVertex.clipPosition.ww);
| + | |
− |
| + | |
− | float3 waveNormal = normalize(inputVertex.normal + float3(cos(temp)*waveDataHelper.xy, 0));
| + | |
− | float3 cameraSpaceNormal = normalize(mul(waveNormal, cameraSpaceMatrix));
| + | |
− | float3 cameraSpacePosition = mul( posAndTime, cameraSpaceMatrix);
| + | |
− | float3 viewVector = normalize(-cameraSpacePosition);
| + | |
− |
| + | |
− | float3 halfVector = normalize(viewVector + lightDirection);
| + | |
− | outputVertex.specular = lightSpecular*pow(dot(cameraSpaceNormal, halfVector), 50)*nightColor*lightColor*0.5;
| + | |
− |
| + | |
− |
| + | |
− | float2 fTranslation=float2(fmod(frameInfo.w, 100)*0.005, fmod(frameInfo.w, 100)*0.005);
| + | |
− | float2 vTexCoords = posAndTime.xy*0.05;
| + | |
− |
| + | |
− | // Output bump layers texture coordinates
| + | |
− | float fSinTranslation=sin(fTranslation*100)*0.005;
| + | |
− | float2 vTranslation0=fTranslation+fSinTranslation;
| + | |
− | float2 vTranslation1=fTranslation-fSinTranslation;
| + | |
− | float2 vTranslation2=fTranslation;
| + | |
− |
| + | |
− | // Scale texture coordinates to get mix of low/high frequency details
| + | |
− | outputVertex.Wave0.xy = vTexCoords.xy+fTranslation*2.0;
| + | |
− | outputVertex.Wave1.xy = vTexCoords.xy*2.0+fTranslation*4.0;
| + | |
− | outputVertex.Wave2.xy = vTexCoords.xy*7.0+fTranslation*2.0;
| + | |
− | outputVertex.Wave3.xy = vTexCoords.xy*12.0+fTranslation;
| + | |
− |
| + | |
− | // compute binormal
| + | |
− | float3 binormal = normalize(cross(waveNormal, float3(1.0f, 0.0f, 0.0f)));
| + | |
− | float3 tangent = normalize(cross(binormal, waveNormal));
| + | |
− |
| + | |
− | // tangent space matrix
| + | |
− | float3x3 objToTangentSpace = float3x3(tangent, binormal, waveNormal);
| + | |
− |
| + | |
− | float3 viewVectorInObjSpace = mul(viewVector, (float3x3)cameraToGeomMatrix);
| + | |
− |
| + | |
− | outputVertex.Eye.xyz = mul(objToTangentSpace, viewVectorInObjSpace);
| + | |
− |
| + | |
− |
| + | |
− | return(outputVertex);
| + | |
− | }
| + | |
− | | + | |
− | | + | |
− | endShaderSource
| + | |
− | end # shaderProgram
| + | |
− |
| + | |
− | shaderProgram -target pixelProgram -method compile -version 2_0
| + | |
− | shaderSource
| + | |
− | sampler reflect;
| + | |
− | sampler bump;
| + | |
− | struct cInputPixel
| + | |
− | {
| + | |
− | float4 sPos : TEXCOORD0;
| + | |
− | float2 Wave0 : TEXCOORD1;
| + | |
− | float2 Wave1 : TEXCOORD2;
| + | |
− | float2 Wave2 : TEXCOORD3;
| + | |
− | float2 Wave3 : TEXCOORD4;
| + | |
− | float3 Eye : TEXCOORD5;
| + | |
− | float4 specular : COLOR0;
| + | |
− | };
| + | |
− |
| + | |
− | float Fresnel(float NdotL, float fresnelBias, float fresnelPow, float facing)
| + | |
− | {
| + | |
− | return max(fresnelBias + (1.0f - fresnelBias)*pow(facing, fresnelPow), 0.0);
| + | |
− | }
| + | |
− |
| + | |
− | float4 PixelMain(cInputPixel pi) : COLOR
| + | |
− | {
| + | |
− | float3 vEye = normalize(pi.Eye);
| + | |
− | | + | |
− | // Get bump layers
| + | |
− | float3 vBumpTexA = tex2D(bump, pi.Wave0.xy).xyz;
| + | |
− | float3 vBumpTexB = tex2D(bump, pi.Wave1.xy).xyz;
| + | |
− | float3 vBumpTexC = tex2D(bump, pi.Wave2.xy).xyz;
| + | |
− | float3 vBumpTexD = tex2D(bump, pi.Wave3.xy).xyz;
| + | |
− |
| + | |
− | // Average bump layers
| + | |
− | float3 vBumpTex=normalize(2.0 * (vBumpTexA.xyz + vBumpTexB.xyz + vBumpTexC.xyz + vBumpTexD.xyz)-4.0);
| + | |
− |
| + | |
− | // Apply individual bump scale for refraction and reflection
| + | |
− | float3 vReflBump = vBumpTex.xyz * float3(0.1, 0.1, 1.0);
| + | |
− |
| + | |
− | float4 vReflection = tex2Dproj(reflect, pi.sPos + float4(vReflBump.xy, 0.0f, 0.0f));//*0.001 + float4(2.0*vBumpTexD-1.0f.xxx, 1);
| + | |
− |
| + | |
− | // Compute Fresnel term
| + | |
− | float NdotL = max(dot(vEye, vReflBump), 0);
| + | |
− | float facing = (1.0 - NdotL);
| + | |
− | float fresnel = Fresnel(NdotL, 0.2, 5.0, facing);
| + | |
− |
| + | |
− | vReflection.a = fresnel;
| + | |
− | return saturate(vReflection + float4(0.0, 0.25, 0.5, 0.0) + pi.specular);
| + | |
− | }
| + | |
− | endShaderSource
| + | |
− | end
| + | |
| | | |
− | sampler reflect | + | shader -layer -9998 # this material must render first |
− | texture "PoolReflection"
| + | validateRenderShaderContext -viewerRenderType $kRenderTypeMirror # reflection render |
− | textureAddressing clamp clamp
| + | |
− | end
| + | |
− |
| + | |
− | sampler bump
| + | |
− | texture "poolShape-body-bump"
| + | |
− | textureAddressing tile tile | + | |
− | end
| + | |
− |
| + | |
− | end # end pass
| + | |
− |
| + | |
− | enddef
| + | |
| | | |
| + | pass -renderEachFrame |
| + | renderTarget $reflectionRenderTarget -setViewport viewportFromParentRenderContext |
| | | |
− | #endshader PoolWaterSurfaceMaterial
| + | depthTest true -enableDepthWrite true |
| | | |
| + | applyStencilStateForOverlappingReflections |
| | | |
| + | alphaBlend srcFactor(zero) add dstFactor(one) |
| | | |
− | # NOTE:
| + | cullmode none |
− | # refraction in vector terms:
| + | |
− | # v = incoming unit vector
| + | |
− | # n = surface normal
| + | |
− | # v' = refracted vector
| + | |
− | # a = refraction ratio, ni / nr =~ 0.75 for air->water
| + | |
− | #
| + | |
− | # v' = v - sn
| + | |
− | # where s = sqrt(1 - a^2 (1 - (v.n)^2)) - v.n.
| + | |
| | | |
| + | shaderProgram -target vertexProgram -method assemble |
| + | bindConstants 0 -bindingID geomToClipFromParentView -constantCount 4 |
| + | shaderSource |
| + | vs_1_1 |
| + | dcl_position v0 |
| + | def c5, 1,0,0,1 |
| + | m4x4 r0, v0, c0 |
| + | mov oPos.x, -r0 |
| + | mov oPos.yzw, r0 |
| + | endShaderSource |
| + | end |
| + | end |
| + | end |
| | | |
| + | shader -layer 6 |
| + | validateRenderShaderContext -viewerRenderType $kRenderTypeNormal |
| + | pass -modifiedEachFrameHint |
| + | shaderProgram -target vertexProgram -method assemble |
| + | bindConstants 0 -bindingID geomToClip -constantCount 4 |
| + | bindConstants 4 -bindingID clipToViewTarget -constantCount 4 |
| + | shaderSource |
| + | vs_1_1 |
| + | dcl_position v0 |
| + | def c8, -0.5, -0.5, 1, 1 |
| + | def c9, 0.5, 0.5, 0, 0 |
| + | def c10, 0.25, 0.25, 0, 0 |
| + | m4x4 r0, v0, c0 |
| + | mov oPos, r0 |
| + | mul r2, c9, r0.w |
| + | mad r4, r0, c8, r2 |
| + | rcp r3.x, c4.x |
| + | rcp r3.y, c5.y |
| + | mov r3.zw, c9.zw |
| + | mul r3, r3, c10 |
| + | mad r6, r0, r3, r4 |
| + | mov oT0, r6.xyww |
| + | endShaderSource |
| + | end |
| | | |
− | ##########################################################
| + | alphaBlend srcFactor(srcAlpha) add dstFactor(invSrcAlpha) |
− | # Caustics
| + | depthTest true -enableDepthWrite false |
− | #
| + | colorScalar (0,0,0) 0.25 |
| | | |
− | define TiledTextureAnimShaderProgram(tilesX tilesY speed)
| + | stage |
− | shaderProgram -target vertexProgram -method assemble
| + | textureTransformType vector3 homogeneous |
− |
| + | textureAddressing clamp clamp |
− | bindConstants 0 -bindingID frameInfo # for time in .w
| + | texture $reflectionRenderTarget |
− | bindConstants 1 -data (&tilesX, &tilesY, &speed, 1) # tx, ty, speed
| + | textureBlend select(texture) select(colorScalar) |
− | bindConstants 2 -data ((1/&tilesX), (1/&tilesY), (&tilesY - 1), 1) # 1/tx 1/ty ty-1
| + | end |
− | if (tsIsDay)
| + | |
− | bindConstants 3 -bindingID immediateData -data (0.75, 0.75, 0.75, 1)
| + | end |
− | else
| + | end |
− | bindConstants 3 -bindingID immediateData -data (0.2, 0.2, 0.2, 1) | + | |
− | endif | + | |
| | | |
− | shaderSource | + | shader -layer 6 |
− | vs_1_1 | + | validateRenderShaderContext -viewerRenderType $kRenderTypeNormal |
− | dcl_position v0 | + | pass -modifiedEachFrameHint |
− | dcl_texcoord v1
| + | shaderProgram -target vertexProgram -method assemble |
| + | bindConstants 0 -bindingID geomToClip -constantCount 4 |
| + | bindConstants 4 -bindingID clipToViewTarget -constantCount 4 |
| + | shaderSource |
| + | vs_1_1 |
| + | dcl_position v0 |
| + | def c8, -0.5, -0.5, 1, 1 |
| + | def c9, 0.5, 0.5, 0, 0 |
| + | def c10, 0.25, 0.25, 0, 0 |
| + | m4x4 r0, v0, c0 |
| + | mov oPos, r0 |
| + | mul r2, c9, r0.w |
| + | mad r4, r0, c8, r2 |
| + | rcp r3.x, c4.x |
| + | rcp r3.y, c5.y |
| + | mov r3.zw, c9.zw |
| + | mul r3, r3, c10 |
| + | mad r1, r0, r3, r4 |
| + | rcp r1.w, r1.w |
| + | mul oT0.xy, r1.w, r1.xy |
| + | endShaderSource |
| + | end |
| | | |
− | mov oPos, v0 # clip space quad, no transforms needed.
| + | alphaBlend srcFactor(srcAlpha) add dstFactor(invSrcAlpha) |
− |
| + | depthTest true -enableDepthWrite false |
− | # tiled texture animation
| + | colorScalar (0,0,0) 0.25 |
− | mov r0, c0
| + | |
− | mul r1, c1.z, r0.w
| + | |
− | frc r5.y, r1.y
| + | |
− |
| + | |
− | mul r1, c1.y, r5.y # f -> [0, ty)
| + | |
− | frc r5.y, r1
| + | |
− | sub r3.y, r1, r5.y # v' = floor(f)
| + | |
− |
| + | |
− | mul r1, c1.x, r5.y # f -> [0, tx)
| + | |
− | frc r5.y, r1
| + | |
− | sub r3.x, r1, r5.y # u' = floor(f)
| + | |
| | | |
− | add r8.xy, v1.xy, r3.xy
| + | stage |
− | mul oT0.xy, r8.xy, c2.xy
| + | textureAddressing clamp clamp |
− |
| + | texture $reflectionRenderTarget |
− | mov oD0, c3 # also spit out diffuse color with modcolor information
| + | textureBlend select(texture) select(colorScalar) |
− |
| + | end |
− | endShaderSource
| + | |
− |
| + | |
− | end
| + | |
− | enddef
| + | |
− | | + | |
− | define CausticsGeneratorMaterial()
| + | |
− | material
| + | |
− | # This material updates a render target with the current frame
| + | |
− | # of the tile animation. This is the only way to handle a repeated
| + | |
− | # animating texture (not to mention using it for projective texturing)
| + | |
− | # in the absence of clip maps.
| + | |
− |
| + | |
− | create DetermineHardwareSupport()
| + | |
− |
| + | |
− | if ($causticsEnabled and $useFixedFunctionPath = false and $useSWVertexShaderPath = false)
| + | |
− |
| + | |
− | shader -layer +9999
| + | |
− | | + | |
− | pass | + | |
− | renderClipSpaceRect | + | |
− | | + | |
− | renderTarget causticsTile -fixed (64, 64) -allocateDepthBuffer false -undo
| + | |
− | | + | |
− | create TiledTextureAnimShaderProgram(8 4 1)
| + | |
− |
| + | |
− | alphaBlend srcFactor(one) add dstFactor(zero)
| + | |
− | alphaTest false 0
| + | |
− | alphaTestFunction acceptIfGreater
| + | |
− | | + | |
− | depthTest false -enableDepthWrite false
| + | |
− | depthTestFunction accept
| + | |
− | | + | |
− | # 7/24/2004 Fix bug with kRenderTypeNormal default stencil state and nv40.
| + | |
− | # It reads random stencil values even this target has no depth stencil target.
| + | |
− | # This stencil call will break pixo, but pixo does not show caustics.
| + | |
− | stencil false
| + | |
− | | + | |
− | fillmode $stdMatFillMode
| + | |
− | | + | |
− | shaderProgram -target pixelProgram -method compile -version 1_1
| + | |
− | shaderSource
| + | |
− | sampler caustics;
| + | |
− | struct cInputPixel
| + | |
− | {
| + | |
− | float4 color : COLOR;
| + | |
− | float2 tc0 : TEXCOORD0;
| + | |
− | };
| + | |
− | float4 PixelMain(cInputPixel pi) : COLOR
| + | |
− | {
| + | |
− | float4 texColor = tex2D(caustics, pi.tc0);
| + | |
− | return texColor*pi.color;
| + | |
− | }
| + | |
− | endShaderSource
| + | |
− | end
| + | |
− |
| + | |
− | sampler 0
| + | |
− | texture causticsTiled
| + | |
− | textureAddressing tile tile
| + | |
− | end
| + | |
− |
| + | |
− | end | + | |
− | end
| + | |
− | else
| + | |
− | shader
| + | |
− |
| + | |
− | end
| + | |
− | endif
| + | |
− | end
| + | |
− | enddef
| + | |
− |
| + | |
− | setf causticsStrength 0.8
| + | |
− | setf causticsBaseStrength 0.5
| + | |
− | | + | |
− | | + | |
− | ###################################################
| + | |
− | # Materials
| + | |
− | #
| + | |
− | | + | |
− | | + | |
− | # Pool surface materials
| + | |
− | materialDefinition "poolWater-0"
| + | |
− | setDefinition PoolWaterSurfaceMaterial
| + | |
− | addParam stdMatDiffCoef (0, 0, 1)
| + | |
− | addParam wmRefractionEnabled true
| + | |
− | end
| + | |
− | | + | |
− | materialDefinition "poolWater-1"
| + | |
− | setDefinition PoolWaterSurfaceMaterial
| + | |
− | addParam stdMatLightingEnabled false
| + | |
− | addParam stdMatLayer 0
| + | |
− |
| + | |
− | addParam stdMatDiffCoef (1, 1, 1)
| + | |
− | | + | |
− | addParam wmReflectionTexture swimming_pool-envcube
| + | |
− | | + | |
− | addParam wmTransparency 0.4
| + | |
− | | + | |
− | addParam wmXSpeed 3
| + | |
− | addParam wmXRepeat 5
| + | |
− | addParam wmXWaveHeight 0.01
| + | |
− |
| + | |
− | addParam wmYSpeed 3
| + | |
− | addParam wmYRepeat 6
| + | |
− | addParam wmYWaveHeight 0.01
| + | |
− | end
| + | |
− | | + | |
− | materialDefinition "poolWater-2"
| + | |
− | setDefinition PoolWaterSurfaceMaterial
| + | |
− | addParam stdMatLightingEnabled false
| + | |
− | addParam stdMatLayer 0
| + | |
− |
| + | |
− | addParam stdMatDiffCoef (0, 0, 1)
| + | |
− | | + | |
− | addParam wmTransparency 0.5
| + | |
− | | + | |
− | addParam wmXSpeed 3
| + | |
− | addParam wmXRepeat 12
| + | |
− | addParam wmXWaveHeight 0 #0.02
| + | |
− |
| + | |
− | addParam wmYSpeed 3
| + | |
− | addParam wmYRepeat 12
| + | |
− | addParam wmYWaveHeight 0 # 0.02
| + | |
− | end
| + | |
− | | + | |
− | materialDefinition "poolWater-4"
| + | |
− | setDefinition WaterAnimatingTextures
| + | |
− | addParam waterSpeed 0.3
| + | |
− | end
| + | |
− | | + | |
− | | + | |
− | # Pool depth layer materials
| + | |
− | | + | |
− | # this is here soley because the layering on standard material
| + | |
− | # is too constrained. We need a layer less than 7, or we'll
| + | |
− | # render over transparent areas of Sims (e.g. hair) when
| + | |
− | # they're in the pool at a shallow view angle.
| + | |
− | setc poolLayerColour (0, 0.5, 1.0, 1.0)
| + | |
− | define PoolDepthLayerMaterial()
| + | |
− | material
| + | |
− | create DetermineHardwareSupport()
| + | |
− | if ($useSWVertexShaderPath or $useFixedFunctionPath)
| + | |
− | shader
| + | |
− | end
| + | |
− | else
| + | |
− | shader -layer $poolWaterLayer
| + | |
− | validateRenderShaderContext -vertexFormat position 0 required
| + | |
− | validateRenderShaderContext -vertexFormat texcoord 0 required
| + | |
| | | |
− | pass
| |
− | alphaBlend srcFactor(srcAlpha) add dstFactor(invSrcAlpha)
| |
− | depthTest true -enableDepthWrite false
| |
− | #fillmode wireframe
| |
− | shaderProgram -target vertexProgram -method compile -version 1_1
| |
− | bindConstants 0 -bindingID geomToClip -constantCount 4
| |
− | bindConstants 4 -bindingID immediateData -data ($poolLayerColour)
| |
− |
| |
− | shaderSource
| |
− | float4x4 clipSpaceMatrix : register(c0);
| |
− | float4 poolLayer : register(c4);
| |
− |
| |
− | struct cVertexIn
| |
− | {
| |
− | float3 mPosition : POSITION0;
| |
− | float2 alpha : TEXCOORD0;
| |
− | };
| |
− |
| |
− | struct cVertexOut
| |
− | {
| |
− | float4 mClipPosition : POSITION;
| |
− | float4 mColor : COLOR0;
| |
− | };
| |
− |
| |
− | cVertexOut VertexMain(cVertexIn vertexIn)
| |
− | {
| |
− | cVertexOut result;
| |
− | result.mClipPosition = mul(float4(vertexIn.mPosition, 1), clipSpaceMatrix);
| |
− | result.mColor = float4(poolLayer.r, poolLayer.g, poolLayer.b, poolLayer.a * vertexIn.alpha.x);
| |
− | return result;
| |
− | }
| |
− |
| |
− | endShaderSource
| |
− | end
| |
− |
| |
− | shaderProgram -target pixelProgram -method compile -version 1_1
| |
− | shaderSource
| |
− | float4 PixelMain(float4 color : COLOR) : COLOR
| |
− | {
| |
− | return color;
| |
− | }
| |
− | endShaderSource
| |
− | end
| |
− | end
| |
| end | | end |
− | endif | + | end |
− | end
| + | |
| enddef | | enddef |
| | | |
− | materialDefinition "poolWaterLayer-0"
| + | #---------------------------------------------------------------------------------------------------------------# |
− | # this layer does nothing but create the caustics tile.
| + | |
− | setDefinition CausticsGeneratorMaterial
| + | |
− | end
| + | |
− | | + | |
− | materialDefinition "poolWaterLayer-1"
| + | |
− | setDefinition PoolDepthLayerMaterial
| + | |
− | addParam poolLayerColour (0, 0.5, 1.0, 0.2)
| + | |
− | end
| + | |
− | materialDefinition "poolWaterLayer-2"
| + | |
− | setDefinition PoolDepthLayerMaterial
| + | |
− | addParam poolLayerColour (0, 0.5, 1.0, 0.2)
| + | |
− | end
| + | |
− | materialDefinition "poolWaterLayer-3"
| + | |
− | setDefinition PoolDepthLayerMaterial
| + | |
− | addParam poolLayerColour (0, 0.5, 1.0, 0.5)
| + | |
− | end
| + | |
− | | + | |
− | materialDefinition mtl_0
| + | |
− | setDefinition CausticsGeneratorMaterial
| + | |
− | end
| + | |
| | | |
− | materialDefinition "lightingwallpoolsimple_reflective" | + | materialDefinition transparent_mirror_reflection |
− | setDefinition StandardMaterial | + | setDefinition TransparentMirrorReflection |
− | addParam stdMatDiffCoef (0.8, 0.8, 0.8)
| + | |
− | addParam stdMatAlphaMultiplier 1.0
| + | |
− | addParam stdMatAlphaBlendMode none
| + | |
− | addParam stdMatSpecCoef 0.091,0.091,0.091
| + | |
− | addParam stdMatBaseTextureEnabled true
| + | |
− | addParam stdMatBaseTextureName lightingwallpoolsimple-surface
| + | |
− | addParam stdMatEnvCubeLockedToCamera 0
| + | |
− | addParam stdMatEnvCubeMode reflection
| + | |
− | addParam stdMatEnvCubeTextureName reflectionkitchenhighcontrast-envcube
| + | |
− | addParam forceIgnoreShapeBlend true
| + | |
| end | | end |