/*********************************************************************NVMH3**** Copyright NVIDIA Corporation 2003 TO THE MAXIMUM EXTENT PERMITTED BY APPLICABLE LAW, THIS SOFTWARE IS PROVIDED *AS IS* AND NVIDIA AND ITS SUPPLIERS DISCLAIM ALL WARRANTIES, EITHER EXPRESS OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL NVIDIA OR ITS SUPPLIERS BE LIABLE FOR ANY SPECIAL, INCIDENTAL, INDIRECT, OR CONSEQUENTIAL DAMAGES WHATSOEVER (INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF BUSINESS PROFITS, BUSINESS INTERRUPTION, LOSS OF BUSINESS INFORMATION, OR ANY OTHER PECUNIARY LOSS) ARISING OUT OF THE USE OF OR INABILITY TO USE THIS SOFTWARE, EVEN IF NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. Comments: Simple ocean shader with animated bump map and geometric waves Based partly on "Effective Water Simulation From Physical Models", GPU Gems 11 Aug 05: converted from HLSL to GLSL by Jeff Doyle (nfz) to work in Ogre 15 Jun 25: modified to work with OgreUnifiedShader.h ******************************************************************************/ OGRE_NATIVE_GLSL_VERSION_DIRECTIVE #include #if NEW_WATER_SHADER OGRE_UNIFORMS( uniform mat4 projectionMatrix; uniform mat4 viewMatrix; uniform mat4 modelMatrix; ) const float tiling = 0.012; MAIN_PARAMETERS IN(vec4 position, POSITION) OUT(vec4 clipSpace, TEXCOORD0) OUT(vec2 textureCoords, TEXCOORD1) MAIN_DECLARATION { clipSpace = projectionMatrix * viewMatrix * modelMatrix * vec4(position.xyz, 1.0); vec4 worldPos = modelMatrix * vec4(position.xyz, 1.0); gl_Position = clipSpace; textureCoords = vec2(worldPos.x / 2.0 + 0.5, worldPos.z / 2.0 + 0.5) * tiling; } #else OGRE_UNIFORMS( uniform vec3 eyePosition; uniform float BumpScale; uniform vec2 textureScale; uniform vec2 bumpSpeed; uniform highp float time; uniform float waveFreq; uniform float waveAmp; uniform vec4 cameraPositionOS; uniform mat4 world; uniform mat4 viewProj; uniform mat4 worldView; uniform mat4 worldViewProj; uniform mat4 textureProjMatrix; uniform mat3 normalMatrix; uniform vec3 lightDirection; uniform float scale; // the amount to scale the noise texture by uniform float scroll; // the amount by which to scroll the noise uniform float noise; // the noise perturb as a factor of the time ) #line 41 //vec4 wave_a = vec4(1.0, 1.0, 0.35, 3.0); // xy = Direction, z = Steepness, w = Length f32vec4 wave_a = vec4(1.0, 1.0, 0.08, 35.3); // xy = Direction, z = Steepness, w = Length f32vec4 wave_b = vec4(1.0, 0.6, 0.02, 21.55); // xy = Direction, z = Steepness, w = Length f32vec4 wave_c = vec4(1.0, 1.41, 0.01, 0.8); // xy = Direction, z = Steepness, w = Length f32vec4 wave_d = vec4(-1.2, 1.0, 0.01, 0.1); // xy = Direction, z = Steepness, w = Length f32vec4 wave(f32vec4 parameter, f32vec2 position, float32_t t, inout f32vec3 tangent, inout f32vec3 binormal) { #line 51 f32vec2 dir = normalize(parameter.xy); float32_t wave_steepness = parameter.z; float32_t wave_length = parameter.w; float32_t freq = 2.0 * 3.14159265359 / wave_length; float32_t phase = sqrt(9.8 / freq); float32_t f = freq * (dot(dir, position) - phase * t); float32_t a = wave_steepness / freq; tangent += normalize( vec3(1.0 - dir.x * dir.x * (wave_steepness * sin(f)), dir.x * (wave_steepness * cos(f)), -dir.x * dir.y * (wave_steepness * sin(f))) ); binormal += normalize( vec3( -dir.x * dir.y * (wave_steepness * sin(f)), dir.y * (wave_steepness * cos(f)), 1.0-dir.y * dir.y * (wave_steepness * sin(f))) ); f32vec4 result = vec4(dir.x * a * cos(f), a * sin(f) * 0.25, dir.y * (a * cos(f)), 0.0); return result; } vec4 wave2(vec4 parameter, vec2 position, float t, inout vec3 tangent, inout vec3 binormal) { vec2 dir = normalize(parameter.xy); float wave_steepness = parameter.z; float wave_length = parameter.w; float freq = 2.0 * 3.14159265359 / wave_length; float phase = sqrt(9.8 / freq); float f = freq * (dot(dir, position) - phase * t); float a = wave_steepness / freq; float m = freq * (position.x - phase * t); float n = freq * (position.y - phase * t); tangent += normalize( vec3(1.0-sin(m), cos(m), -sin(m)) ); binormal += normalize( vec3( -sin(n), cos(n), 1.0-sin(n)) ); return vec4(dir.x * a * cos(f), a * sin(f) * 0.25, dir.y * (a * cos(f)), 0.0); } MAIN_PARAMETERS IN(vec4 vertex, POSITION) IN(vec3 normal, NORMAL) IN(vec3 tangent, TANGENT) IN(vec4 uv0, TEXCOORD0) OUT(f32vec3 positionWS, TEXCOORD0) OUT(f32vec3 vnormal, TEXCOORD1) OUT(f32vec3 viewDirection, TEXCOORD2) OUT(f32vec3 viewDirectionTS, TEXCOORD3) OUT(f32vec3 olightDirection, TEXCOORD4) // OUT(f32vec3 vbinormal, TEXCOORD2) // OUT(f32vec3 vtangent, TEXCOORD3) // OUT(float vertex_height, TEXCOORD4) OUT(f32vec3 lightDirectionTS, TEXCOORD5) OUT(f32vec2 bumpCoord0, TEXCOORD6) MAIN_DECLARATION { float textureScale = 0.6; float bumpSpeed = 0.8; f32vec4 position = vec4(mul(world, vertex).xyz, 1.0); f32vec3 vertex_position = position.xyz; f32vec3 tang = tangent; f32vec3 bin = cross(tangent, normal); position += wave(wave_a, vertex_position.xz, time, tang, bin); position += wave(wave_b, vertex_position.xz, time, tang, bin); position += wave(wave_c, vertex_position.xz, time, tang, bin); position += wave(wave_d, vertex_position.xz, time, tang, bin); // vtangent = tang; // vbinormal = bin; // vertex_position = position.xyz; // vnormal = normalize(mul(mat3(world), cross(vbinormal, vtangent))); vnormal = normalize(cross(bin, tang)); mat3 TBN = mtxFromRows(tang, bin, vnormal); // vnormal = normalize(vec3(0.0, 1.0, 0.0)); // gl_Position = mul(worldViewProj, vertex); viewDirection = vertex.xyz - cameraPositionOS.xyz; viewDirectionTS = mul(TBN, viewDirection); olightDirection = lightDirection; lightDirectionTS = mul(TBN, lightDirection); gl_Position = mul(viewProj, position); positionWS = mul(world, vertex).xyz; bumpCoord0.xy = uv0.xy * textureScale + time * bumpSpeed; } #endif