diff options
Diffstat (limited to 'shaders/warsow/64.shader_test')
-rw-r--r-- | shaders/warsow/64.shader_test | 1979 |
1 files changed, 1519 insertions, 460 deletions
diff --git a/shaders/warsow/64.shader_test b/shaders/warsow/64.shader_test index b59d973..8033677 100644 --- a/shaders/warsow/64.shader_test +++ b/shaders/warsow/64.shader_test @@ -1,696 +1,1755 @@ [require] GLSL >= 1.10 -[fragment shader] -#define FRAGMENT_SHADER -#define APPLY_LIGHTSTYLE0 -#define APPLY_FBLIGHTMAP -#define APPLY_AMBIENT_COMPENSATION -// Warsow GLSL shader - -#if !defined(__GLSL_CG_DATA_TYPES) +[vertex shader] +#version 130 +#extension GL_ARB_draw_instanced : enable +#define QF_GLSL_VERSION 130 +#define VERTEX_SHADER +#if !defined(myhalf) +//#if !defined(__GLSL_CG_DATA_TYPES) #define myhalf float #define myhalf2 vec2 #define myhalf3 vec3 #define myhalf4 vec4 +//#else +//#define myhalf half +//#define myhalf2 half2 +//#define myhalf3 half3 +//#define myhalf4 half4 +//#endif +#endif + +#if QF_GLSL_VERSION >= 130 + precision highp float; + +# ifdef VERTEX_SHADER + out myhalf4 qf_FrontColor; +# define qf_varying out +# define qf_attribute in +# endif +# ifdef FRAGMENT_SHADER + in myhalf4 qf_FrontColor; + out myhalf4 qf_FragColor; +# define qf_varying in +# define qf_attribute in +# endif + +# define qf_texture texture +# define qf_textureCube texture +# define qf_textureLod textureLod +# define qf_textureOffset(a,b,c,d) textureOffset(a,b,ivec2(c,d)) +# define qf_shadow texture #else -#define myhalf half -#define myhalf2 half2 -#define myhalf3 half3 -#define myhalf4 half4 +# ifdef VERTEX_SHADER +# define qf_FrontColor gl_FrontColor +# define qf_varying varying +# define qf_attribute attribute +# endif + +# ifdef FRAGMENT_SHADER +# define qf_FrontColor gl_Color +# define qf_FragColor gl_FragColor +# define qf_varying varying +# define qf_attribute attribute +# endif +# define qf_texture texture2D +# define qf_textureLod texture2DLod +# define qf_textureCube textureCube +# define qf_textureOffset(a,b,c,d) texture2DOffset(a,b,ivec2(c,d)) +# define qf_shadow shadow2D #endif -varying vec2 TexCoord; -#ifdef APPLY_LIGHTSTYLE0 -varying vec4 LightmapTexCoord01; -#ifdef APPLY_LIGHTSTYLE2 -varying vec4 LightmapTexCoord23; +#ifndef M_PI +#define M_PI 3.14159265358979323846 #endif +#ifndef M_TWOPI +#define M_TWOPI 6.28318530717958647692 #endif -#if defined(APPLY_SPECULAR) || defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -varying vec3 EyeVector; +#ifndef MAX_UNIFORM_BONES +#define MAX_UNIFORM_BONES 100 #endif -#ifdef APPLY_DIRECTIONAL_LIGHT -varying vec3 LightVector; +#ifndef MAX_UNIFORM_INSTANCES +#define MAX_UNIFORM_INSTANCES 40 #endif +uniform vec3 u_QF_ViewOrigin; +uniform mat3 u_QF_ViewAxis; +uniform float u_QF_MirrorSide; +uniform vec3 u_QF_EntityOrigin; +uniform float u_QF_ShaderTime; + +#ifndef M_PI +#define M_PI 3.14159265358979323846 +#endif +#ifndef M_TWOPI +#define M_TWOPI 6.28318530717958647692 +#endif + +#ifndef WAVE_SIN +float QF_WaveFunc_Sin(float x) +{ +x -= floor(x); +return sin(x * M_TWOPI); +} +float QF_WaveFunc_Triangle(float x) +{ +x -= floor(x); +return step(x, 0.25) * x * 4.0 + (2.0 - 4.0 * step(0.25, x) * step(x, 0.75) * x) + ((step(0.75, x) * x - 0.75) * 4.0 - 1.0); +} +float QF_WaveFunc_Square(float x) +{ +x -= floor(x); +return step(x, 0.5) * 2.0 - 1.0; +} +float QF_WaveFunc_Sawtooth(float x) +{ +x -= floor(x); +return x; +} +float QF_QF_WaveFunc_InverseSawtooth(float x) +{ +x -= floor(x); +return 1.0 - x; +} -varying mat3 strMatrix; // directions of S/T/R texcoords (tangent, binormal, normal) +#define WAVE_SIN(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Sin((phase)+(time)*(freq)))) +#define WAVE_TRIANGLE(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Triangle((phase)+(time)*(freq)))) +#define WAVE_SQUARE(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Square((phase)+(time)*(freq)))) +#define WAVE_SAWTOOTH(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Sawtooth((phase)+(time)*(freq)))) +#define WAVE_INVERSESAWTOOTH(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_QF_WaveFunc_InverseSawtooth((phase)+(time)*(freq)))) +#endif #ifdef VERTEX_SHADER -// Vertex shader +attribute vec4 a_BonesIndices; +attribute vec4 a_BonesWeights; -uniform vec3 EyeOrigin; +uniform vec4 u_QF_DualQuats[MAX_UNIFORM_BONES*2]; -#ifdef APPLY_DIRECTIONAL_LIGHT -uniform vec3 LightDir; +#if defined(DUAL_QUAT_TRANSFORM_NORMALS) +#if defined(DUAL_QUAT_TRANSFORM_TANGENT) +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal, inout vec3 Tangent) +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal) +#endif +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position) #endif +{ +int index; +vec4 Indices = a_BonesIndices; +vec4 Weights = a_BonesWeights; +vec4 Indices_2 = Indices * 2.0; +vec4 DQReal, DQDual; + +index = int(Indices_2.x); +DQReal = u_QF_DualQuats[index+0]; +DQDual = u_QF_DualQuats[index+1]; -void main() +if (numWeights > 1) { -gl_FrontColor = gl_Color; +DQReal *= Weights.x; +DQDual *= Weights.x; -TexCoord = vec2 (gl_TextureMatrix[0] * gl_MultiTexCoord0); +vec4 DQReal1, DQDual1; +float scale; -#ifdef APPLY_LIGHTSTYLE0 -LightmapTexCoord01.st = gl_MultiTexCoord4.st; -#ifdef APPLY_LIGHTSTYLE1 -LightmapTexCoord01.pq = gl_MultiTexCoord5.st; -#ifdef APPLY_LIGHTSTYLE2 -LightmapTexCoord23.st = gl_MultiTexCoord6.st; -#ifdef APPLY_LIGHTSTYLE3 -LightmapTexCoord23.pq = gl_MultiTexCoord7.st; +index = int(Indices_2.y); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.y; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 2) +{ +index = int(Indices_2.z); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.z; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 3) +{ +index = int(Indices_2.w); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.w; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; +} +} +} + +float len = length(DQReal); +DQReal /= len; +DQDual /= len; + +Position.xyz = (cross(DQReal.xyz, cross(DQReal.xyz, Position.xyz) + Position.xyz*DQReal.w + DQDual.xyz) + DQDual.xyz*DQReal.w - DQReal.xyz*DQDual.w)*2.0 + Position.xyz; + +#ifdef DUAL_QUAT_TRANSFORM_NORMALS +Normal = cross(DQReal.xyz, cross(DQReal.xyz, Normal) + Normal*DQReal.w)*2.0 + Normal; #endif + +#ifdef DUAL_QUAT_TRANSFORM_TANGENT +Tangent = cross(DQReal.xyz, cross(DQReal.xyz, Tangent) + Tangent*DQReal.w)*2.0 + Tangent; #endif +} + +// use defines to overload the transform function + +#define DUAL_QUAT_TRANSFORM_NORMALS +#if defined(DUAL_QUAT_TRANSFORM_NORMALS) +#if defined(DUAL_QUAT_TRANSFORM_TANGENT) +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal, inout vec3 Tangent) +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal) #endif +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position) #endif +{ +int index; +vec4 Indices = a_BonesIndices; +vec4 Weights = a_BonesWeights; +vec4 Indices_2 = Indices * 2.0; +vec4 DQReal, DQDual; + +index = int(Indices_2.x); +DQReal = u_QF_DualQuats[index+0]; +DQDual = u_QF_DualQuats[index+1]; + +if (numWeights > 1) +{ +DQReal *= Weights.x; +DQDual *= Weights.x; + +vec4 DQReal1, DQDual1; +float scale; + +index = int(Indices_2.y); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.y; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 2) +{ +index = int(Indices_2.z); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.z; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 3) +{ +index = int(Indices_2.w); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.w; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; +} +} +} + +float len = length(DQReal); +DQReal /= len; +DQDual /= len; -strMatrix[0] = gl_MultiTexCoord1.xyz; -strMatrix[2] = gl_Normal.xyz; -strMatrix[1] = gl_MultiTexCoord1.w * cross (strMatrix[2], strMatrix[0]); +Position.xyz = (cross(DQReal.xyz, cross(DQReal.xyz, Position.xyz) + Position.xyz*DQReal.w + DQDual.xyz) + DQDual.xyz*DQReal.w - DQReal.xyz*DQDual.w)*2.0 + Position.xyz; -#if defined(APPLY_SPECULAR) || defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -vec3 EyeVectorWorld = EyeOrigin - gl_Vertex.xyz; -EyeVector = EyeVectorWorld * strMatrix; +#ifdef DUAL_QUAT_TRANSFORM_NORMALS +Normal = cross(DQReal.xyz, cross(DQReal.xyz, Normal) + Normal*DQReal.w)*2.0 + Normal; #endif -#ifdef APPLY_DIRECTIONAL_LIGHT -LightVector = LightDir * strMatrix; +#ifdef DUAL_QUAT_TRANSFORM_TANGENT +Tangent = cross(DQReal.xyz, cross(DQReal.xyz, Tangent) + Tangent*DQReal.w)*2.0 + Tangent; #endif +} -gl_Position = ftransform (); -#ifdef APPLY_CLIPPING -#ifdef __GLSL_CG_DATA_TYPES -gl_ClipVertex = gl_ModelViewMatrix * gl_Vertex; +#define DUAL_QUAT_TRANSFORM_TANGENT +#if defined(DUAL_QUAT_TRANSFORM_NORMALS) +#if defined(DUAL_QUAT_TRANSFORM_TANGENT) +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal, inout vec3 Tangent) +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal) #endif +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position) #endif -} +{ +int index; +vec4 Indices = a_BonesIndices; +vec4 Weights = a_BonesWeights; +vec4 Indices_2 = Indices * 2.0; +vec4 DQReal, DQDual; -#endif // VERTEX_SHADER +index = int(Indices_2.x); +DQReal = u_QF_DualQuats[index+0]; +DQDual = u_QF_DualQuats[index+1]; +if (numWeights > 1) +{ +DQReal *= Weights.x; +DQDual *= Weights.x; -#ifdef FRAGMENT_SHADER -// Fragment shader +vec4 DQReal1, DQDual1; +float scale; + +index = int(Indices_2.y); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.y; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; -#ifdef APPLY_LIGHTSTYLE0 -uniform sampler2D LightmapTexture0; -uniform float DeluxemapOffset0; // s-offset for LightmapTexCoord -uniform myhalf3 lsColor0; // lightstyle color - -#ifdef APPLY_LIGHTSTYLE1 -uniform sampler2D LightmapTexture1; -uniform float DeluxemapOffset1; -uniform myhalf3 lsColor1; +if (numWeights > 2) +{ +index = int(Indices_2.z); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.z; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 3) +{ +index = int(Indices_2.w); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.w; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; +} +} +} -#ifdef APPLY_LIGHTSTYLE2 -uniform sampler2D LightmapTexture2; -uniform float DeluxemapOffset2; -uniform myhalf3 lsColor2; +float len = length(DQReal); +DQReal /= len; +DQDual /= len; -#ifdef APPLY_LIGHTSTYLE3 -uniform sampler2D LightmapTexture3; -uniform float DeluxemapOffset3; -uniform myhalf3 lsColor3; +Position.xyz = (cross(DQReal.xyz, cross(DQReal.xyz, Position.xyz) + Position.xyz*DQReal.w + DQDual.xyz) + DQDual.xyz*DQReal.w - DQReal.xyz*DQDual.w)*2.0 + Position.xyz; +#ifdef DUAL_QUAT_TRANSFORM_NORMALS +Normal = cross(DQReal.xyz, cross(DQReal.xyz, Normal) + Normal*DQReal.w)*2.0 + Normal; #endif + +#ifdef DUAL_QUAT_TRANSFORM_TANGENT +Tangent = cross(DQReal.xyz, cross(DQReal.xyz, Tangent) + Tangent*DQReal.w)*2.0 + Tangent; #endif +} + #endif +#ifdef VERTEX_SHADER +#ifdef APPLY_INSTANCED_ATTRIB_TRASNFORMS +attribute vec4 a_InstanceQuat; +attribute vec4 a_InstancePosAndScale; +#elif defined(GL_ARB_draw_instanced) + +uniform vec4 u_QF_InstancePoints[MAX_UNIFORM_INSTANCES*2]; + +#define a_InstanceQuat u_QF_InstancePoints[gl_InstanceID*2] +#define a_InstancePosAndScale u_QF_InstancePoints[gl_InstanceID*2+1] +#else +uniform vec4 u_QF_InstancePoints[2]; +#define a_InstanceQuat u_QF_InstancePoints[0] +#define a_InstancePosAndScale u_QF_InstancePoints[1] #endif -uniform sampler2D BaseTexture; -uniform sampler2D NormalmapTexture; -uniform sampler2D GlossTexture; -#ifdef APPLY_DECAL -uniform sampler2D DecalTexture; +void QF_InstancedTransform(inout vec4 Position, inout vec3 Normal) +{ +Position.xyz = (cross(a_InstanceQuat.xyz, cross(a_InstanceQuat.xyz, Position.xyz) + Position.xyz*a_InstanceQuat.w)*2.0 + Position.xyz) * + a_InstancePosAndScale.w + a_InstancePosAndScale.xyz; +Normal = cross(a_InstanceQuat.xyz, cross(a_InstanceQuat.xyz, Normal) + Normal*a_InstanceQuat.w)*2.0 + Normal; +} + #endif +#define QF_LatLong2Norm(ll) vec3(cos((ll).y) * sin((ll).x), sin((ll).y) * sin((ll).x), cos((ll).x)) + +#define APPLY_RGB_CONST +#define APPLY_RGB_DISTANCERAMP +#define APPLY_ALPHA_CONST +#define APPLY_SOFT_PARTICLE + +#define DRAWFLAT_NORMAL_STEP 0.5 // floor or ceiling if < abs(normal.z) +uniform mat4 u_ModelViewMatrix; +uniform mat4 u_ModelViewProjectionMatrix; + +uniform float u_ShaderTime; + +uniform vec3 u_ViewOrigin; +uniform mat3 u_ViewAxis; + +uniform vec3 u_EntityDist; +uniform vec3 u_EntityOrigin; +uniform myhalf4 u_EntityColor; + +uniform myhalf4 u_ConstColor; +uniform myhalf4 u_RGBGenFuncArgs, u_AlphaGenFuncArgs; +uniform myhalf3 u_LightstyleColor[4]; // lightstyle colors + +uniform myhalf3 u_LightAmbient; +uniform myhalf3 u_LightDiffuse; +uniform vec3 u_LightDir; + +uniform myhalf2 u_BlendMix; + +uniform vec2 u_TextureMatrix[3]; +#define TextureMatrix2x3Mul(m2x3,tc) vec2(dot((m2x3)[0],(tc)) + (m2x3)[2][0], dot((m2x3)[1],(tc)) + (m2x3)[2][1]) + +uniform float u_MirrorSide; + +uniform float u_ZNear, u_ZFar; + +uniform ivec4 u_Viewport; // x, y, width, height -#if defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -uniform float OffsetMappingScale; +uniform vec4 u_TextureParams; + +uniform myhalf u_SoftParticlesScale; + + +#if defined(NUM_DLIGHTS) +#if defined(FRAGMENT_SHADER) +#if defined(NUM_DLIGHTS) + +struct DynamicLight +{ + myhalf Radius; + vec3 Position; + myhalf3 Diffuse; +}; + +uniform DynamicLight u_DynamicLights[NUM_DLIGHTS]; +uniform int u_NumDynamicLights; +#ifdef DLIGHTS_SURFACE_NORMAL_IN +myhalf3 DynamicLightsSummaryColor(in vec3 Position, in myhalf3 surfaceNormalModelspace) +#else +myhalf3 DynamicLightsSummaryColor(in vec3 Position) #endif +{ + myhalf3 Color = myhalf3(0.0); -uniform myhalf3 LightAmbient; -#ifdef APPLY_DIRECTIONAL_LIGHT -uniform myhalf3 LightDiffuse; +#if QF_GLSL_VERSION >= 330 + for (int i = 0; i < u_NumDynamicLights; i++) +#else + for (int i = 0; i < NUM_DLIGHTS; i++) #endif + { + myhalf3 STR = myhalf3(u_DynamicLights[i].Position - Position); + myhalf distance = length(STR); + myhalf falloff = clamp(1.0 - distance / u_DynamicLights[i].Radius, 0.0, 1.0); + + falloff *= falloff; + + #ifdef DLIGHTS_SURFACE_NORMAL_IN + falloff *= myhalf(max(dot(normalize(STR), surfaceNormalModelspace), 0.0)); + #endif + + Color += falloff * u_DynamicLights[i].Diffuse; + } + + return Color; +} -uniform myhalf GlossIntensity; // gloss scaling factor -uniform myhalf GlossExponent; // gloss exponent factor -#if defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -// The following reliefmapping and offsetmapping routine was taken from DarkPlaces -// The credit goes to LordHavoc (as always) -vec2 OffsetMapping(vec2 TexCoord) +#define DLIGHTS_SURFACE_NORMAL_IN +#ifdef DLIGHTS_SURFACE_NORMAL_IN +myhalf3 DynamicLightsSummaryColor(in vec3 Position, in myhalf3 surfaceNormalModelspace) +#else +myhalf3 DynamicLightsSummaryColor(in vec3 Position) +#endif { -#ifdef APPLY_RELIEFMAPPING -// 14 sample relief mapping: linear search and then binary search -// this basically steps forward a small amount repeatedly until it finds -// itself inside solid, then jitters forward and back using decreasing -// amounts to find the impact -//vec3 OffsetVector = vec3(EyeVector.xy * ((1.0 / EyeVector.z) * OffsetMappingScale) * vec2(-1, 1), -1); -//vec3 OffsetVector = vec3(normalize(EyeVector.xy) * OffsetMappingScale * vec2(-1, 1), -1); -vec3 OffsetVector = vec3(normalize(EyeVector).xy * OffsetMappingScale * vec2(-1, 1), -1); -vec3 RT = vec3(TexCoord, 1); -OffsetVector *= 0.1; -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) - 0.5); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.5 - 0.25); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.25 - 0.125); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.125 - 0.0625); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.0625 - 0.03125); -return RT.xy; + myhalf3 Color = myhalf3(0.0); + +#if QF_GLSL_VERSION >= 330 + for (int i = 0; i < u_NumDynamicLights; i++) #else -// 2 sample offset mapping (only 2 samples because of ATI Radeon 9500-9800/X300 limits) -// this basically moves forward the full distance, and then backs up based -// on height of samples -//vec2 OffsetVector = vec2(EyeVector.xy * ((1.0 / EyeVector.z) * OffsetMappingScale) * vec2(-1, 1)); -//vec2 OffsetVector = vec2(normalize(EyeVector.xy) * OffsetMappingScale * vec2(-1, 1)); -vec2 OffsetVector = vec2(normalize(EyeVector).xy * OffsetMappingScale * vec2(-1, 1)); -TexCoord += OffsetVector; -OffsetVector *= 0.5; -TexCoord -= OffsetVector * texture2D(NormalmapTexture, TexCoord).a; -TexCoord -= OffsetVector * texture2D(NormalmapTexture, TexCoord).a; -return TexCoord; + for (int i = 0; i < NUM_DLIGHTS; i++) #endif + { + myhalf3 STR = myhalf3(u_DynamicLights[i].Position - Position); + myhalf distance = length(STR); + myhalf falloff = clamp(1.0 - distance / u_DynamicLights[i].Radius, 0.0, 1.0); + + falloff *= falloff; + + #ifdef DLIGHTS_SURFACE_NORMAL_IN + falloff *= myhalf(max(dot(normalize(STR), surfaceNormalModelspace), 0.0)); + #endif + + Color += falloff * u_DynamicLights[i].Diffuse; + } + + return Color; } + + +#endif + +#endif #endif -void main() +#ifdef APPLY_FOG +struct Fog +{ + float EyeDist; + vec4 EyePlane, Plane; + myhalf3 Color; + float Scale; +}; + +uniform Fog u_Fog; + +#define FOG_TEXCOORD_STEP 1.0/256.0 + +#define FogDensity(coord) sqrt(clamp((coord)[0],0.0,1.0))*step(FOG_TEXCOORD_STEP,(coord)[1]) + +#define FOG_GEN_OUTPUT_COLOR +#if defined(FOG_GEN_OUTPUT_COLOR) +void FogGen(in vec4 Position, inout myhalf4 outColor, in myhalf2 blendMix) +#elif defined(FOG_GEN_OUTPUT_TEXCOORDS) +void FogGen(in vec4 Position, inout vec2 outTexCoord) +#endif { -#if defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -// apply offsetmapping -vec2 TexCoordOffset = OffsetMapping(TexCoord); -#define TexCoord TexCoordOffset + // side = vec2(inside, outside) + myhalf2 side = myhalf2(step(u_Fog.EyeDist, 0.0), step(0.0, u_Fog.EyeDist)); + myhalf FDist = dot(Position.xyz, u_Fog.EyePlane.xyz) - u_Fog.EyePlane.w; + myhalf FVdist = dot(Position.xyz, u_Fog.Plane.xyz) - u_Fog.Plane.w; + myhalf FogDistScale = FVdist / (FVdist - u_Fog.EyeDist); + +#if defined(FOG_GEN_OUTPUT_COLOR) + myhalf FogDist = FDist * dot(side, myhalf2(1.0, FogDistScale)); + myhalf FogScale = myhalf(clamp(1.0 - FogDist * u_Fog.Scale, 0.0, 1.0)); + outColor *= mix(myhalf4(1.0), myhalf4(FogScale), blendMix.xxxy); #endif -myhalf3 surfaceNormal; -myhalf3 diffuseNormalModelspace; -myhalf3 diffuseNormal = myhalf3 (0.0, 0.0, -1.0); -float diffuseProduct; -#ifdef APPLY_CELLSHADING -int lightcell; -float diffuseProductPositive; -float diffuseProductNegative; -float hardShadow; + +#if defined(FOG_GEN_OUTPUT_TEXCOORDS) + myhalf FogS = FDist * dot(side, myhalf2(1.0, step(FVdist, 0.0) * FogDistScale)); + myhalf FogT = -FVdist; + outTexCoord = vec2(FogS * u_Fog.Scale, FogT * u_Fog.Scale + 1.5*FOG_TEXCOORD_STEP); #endif +} -myhalf3 weightedDiffuseNormal; -myhalf3 specularNormal; -float specularProduct; -#if !defined(APPLY_DIRECTIONAL_LIGHT) && !defined(APPLY_LIGHTSTYLE0) -myhalf4 color = myhalf4 (1.0, 1.0, 1.0, 1.0); -#else -myhalf4 color = myhalf4 (0.0, 0.0, 0.0, 1.0); +#undef FOG_GEN_OUTPUT_COLOR +#define FOG_GEN_OUTPUT_TEXCOORDS +#if defined(FOG_GEN_OUTPUT_COLOR) +void FogGen(in vec4 Position, inout myhalf4 outColor, in myhalf2 blendMix) +#elif defined(FOG_GEN_OUTPUT_TEXCOORDS) +void FogGen(in vec4 Position, inout vec2 outTexCoord) +#endif +{ + // side = vec2(inside, outside) + myhalf2 side = myhalf2(step(u_Fog.EyeDist, 0.0), step(0.0, u_Fog.EyeDist)); + myhalf FDist = dot(Position.xyz, u_Fog.EyePlane.xyz) - u_Fog.EyePlane.w; + myhalf FVdist = dot(Position.xyz, u_Fog.Plane.xyz) - u_Fog.Plane.w; + myhalf FogDistScale = FVdist / (FVdist - u_Fog.EyeDist); + +#if defined(FOG_GEN_OUTPUT_COLOR) + myhalf FogDist = FDist * dot(side, myhalf2(1.0, FogDistScale)); + myhalf FogScale = myhalf(clamp(1.0 - FogDist * u_Fog.Scale, 0.0, 1.0)); + outColor *= mix(myhalf4(1.0), myhalf4(FogScale), blendMix.xxxy); +#endif + +#if defined(FOG_GEN_OUTPUT_TEXCOORDS) + myhalf FogS = FDist * dot(side, myhalf2(1.0, step(FVdist, 0.0) * FogDistScale)); + myhalf FogT = -FVdist; + outTexCoord = vec2(FogS * u_Fog.Scale, FogT * u_Fog.Scale + 1.5*FOG_TEXCOORD_STEP); #endif +} -// get the surface normal -surfaceNormal = normalize (myhalf3 (texture2D (NormalmapTexture, TexCoord)) - myhalf3 (0.5)); +#endif -#ifdef APPLY_DIRECTIONAL_LIGHT -diffuseNormal = myhalf3 (LightVector); -weightedDiffuseNormal = diffuseNormal; -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -#ifdef APPLY_CELLSHADING -hardShadow = 0.0; -diffuseProductPositive = max (diffuseProduct, 0.0); -diffuseProductNegative = (-min (diffuseProduct, 0.0) - 0.3); +#ifdef APPLY_GREYSCALE +myhalf3 Greyscale(myhalf3 color) +{ + return myhalf3(dot(color, myhalf3(0.299, 0.587, 0.114))); +} -// smooth the hard shadow edge -lightcell = int(max(diffuseProduct + 0.1, 0.0) * 2.0); -hardShadow += float(lightcell); +#endif -lightcell = int(max(diffuseProduct + 0.055, 0.0) * 2.0); -hardShadow += float(lightcell); +qf_varying vec3 v_Position; -lightcell = int(diffuseProductPositive * 2.0); -hardShadow += float(lightcell); +#ifdef APPLY_DRAWFLAT +qf_varying myhalf v_NormalZ; +#endif -color.rgb += myhalf(0.6 + hardShadow * 0.3333333333 * 0.27 + diffuseProductPositive * 0.14); +#ifdef APPLY_TC_GEN_REFLECTION +#define APPLY_CUBEMAP +#endif -// backlight -lightcell = int (diffuseProductNegative * 2.0); -color.rgb += myhalf (float(lightcell) * 0.085 + diffuseProductNegative * 0.085); +#ifdef APPLY_CUBEMAP +qf_varying vec3 v_TexCoord; #else -color.rgb += LightDiffuse.rgb * myhalf(max (diffuseProduct, 0.0)) + LightAmbient.rgb; +qf_varying vec2 v_TexCoord; +#endif + +#ifdef NUM_LIGHTMAPS +qf_varying vec2 v_LightmapTexCoord[NUM_LIGHTMAPS]; #endif +#if defined(APPLY_FOG) && !defined(APPLY_FOG_COLOR) +qf_varying vec2 v_FogCoord; #endif -// deluxemapping using light vectors in modelspace +#if defined(APPLY_SOFT_PARTICLE) +qf_varying float v_Depth; +#endif -#ifdef APPLY_LIGHTSTYLE0 +#ifdef VERTEX_SHADER +#ifdef VERTEX_SHADER +qf_attribute vec4 a_Position; +qf_attribute vec4 a_SVector; +qf_attribute vec4 a_Normal; +qf_attribute vec4 a_Color; +qf_attribute vec2 a_TexCoord; +qf_attribute vec2 a_LightmapCoord0, a_LightmapCoord1, a_LightmapCoord2, a_LightmapCoord3; +#endif +void TransformVerts(inout vec4 Position, inout vec3 Normal, inout vec2 TexCoord) +{ +#ifdef NUM_BONE_INFLUENCES + QF_VertexDualQuatsTransform(NUM_BONE_INFLUENCES, Position, Normal); +#endif -// get light normal -diffuseNormalModelspace = myhalf3 (texture2D(LightmapTexture0, vec2(LightmapTexCoord01.s+DeluxemapOffset0,LightmapTexCoord01.t))) - myhalf3 (0.5); -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -// calculate directional shading -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); +#ifdef APPLY_DEFORMVERTS + QF_DeformVerts(Position, Normal, TexCoord); +#endif -#ifdef APPLY_FBLIGHTMAP -weightedDiffuseNormal = diffuseNormal; -// apply lightmap color -color.rgb += myhalf3 (max (diffuseProduct, 0.0) * myhalf3 (texture2D (LightmapTexture0, LightmapTexCoord01.st))); -#else +#ifdef APPLY_INSTANCED_TRANSFORMS + QF_InstancedTransform(Position, Normal); +#endif +} -#define NORMALIZE_DIFFUSE_NORMAL +void TransformVerts(inout vec4 Position, inout vec3 Normal, inout vec3 Tangent, inout vec2 TexCoord) +{ +#ifdef NUM_BONE_INFLUENCES + QF_VertexDualQuatsTransform(NUM_BONE_INFLUENCES, Position, Normal, Tangent); +#endif -weightedDiffuseNormal = lsColor0 * diffuseNormal; -// apply lightmap color -color.rgb += lsColor0 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture0, LightmapTexCoord01.st)); +#ifdef APPLY_DEFORMVERTS + QF_DeformVerts(Position, Normal, TexCoord); #endif -#ifdef APPLY_AMBIENT_COMPENSATION -// compensate for ambient lighting -color.rgb += myhalf((1.0 - max (diffuseProduct, 0.0))) * LightAmbient; +#ifdef APPLY_INSTANCED_TRANSFORMS + QF_InstancedTransform(Position, Normal); +#endif +} +myhalf4 VertexRGBGen(in vec4 Position, in vec3 Normal, in myhalf4 VertexColor) +{ +#if defined(APPLY_RGB_DISTANCERAMP) || defined(APPLY_ALPHA_DISTANCERAMP) +#define DISTANCERAMP(x1,x2,y1,y2) ((y2 - y1) / (x2 - x1) * (clamp(myhalf(dot(u_EntityDist - Position.xyz, Normal)),0.0,x2) - x1) + y1) #endif -#ifdef APPLY_LIGHTSTYLE1 -diffuseNormalModelspace = myhalf3 (texture2D (LightmapTexture1, vec2(LightmapTexCoord01.p+DeluxemapOffset1,LightmapTexCoord01.q))) - myhalf3 (0.5); -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -weightedDiffuseNormal += lsColor1 * diffuseNormal; -color.rgb += lsColor1 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture1, LightmapTexCoord01.pq)); +#if defined(APPLY_RGB_CONST) && defined(APPLY_ALPHA_CONST) + myhalf4 Color = u_ConstColor; +#else + myhalf4 Color = myhalf4(1.0); + +#if defined(APPLY_RGB_CONST) + Color.rgb = u_ConstColor.rgb; +#elif defined(APPLY_RGB_VERTEX) + Color.rgb = VertexColor.rgb; +#elif defined(APPLY_RGB_ONE_MINUS_VERTEX) + Color.rgb = myhalf3(1.0) - VertexColor.rgb; +#elif defined(APPLY_RGB_GEN_DIFFUSELIGHT) + Color.rgb = myhalf3(u_LightAmbient + max(dot(u_LightDir, Normal), 0.0) * u_LightDiffuse); +#endif -#ifdef APPLY_LIGHTSTYLE2 -diffuseNormalModelspace = myhalf3 (texture2D (LightmapTexture2, vec2(LightmapTexCoord23.s+DeluxemapOffset2,LightmapTexCoord23.t))) - myhalf3 (0.5); -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -weightedDiffuseNormal += lsColor2 * diffuseNormal; -color.rgb += lsColor2 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture2, LightmapTexCoord23.st)); +#if defined(APPLY_ALPHA_CONST) + Color.a = u_ConstColor.a; +#elif defined(APPLY_ALPHA_VERTEX) + Color.a = VertexColor.a; +#elif defined(APPLY_ALPHA_ONE_MINUS_VERTEX) + Color.a = 1.0 - VertexColor.a; +#endif -#ifdef APPLY_LIGHTSTYLE3 -diffuseNormalModelspace = myhalf3 (texture2D (LightmapTexture3, vec2(LightmapTexCoord23.p+DeluxemapOffset3,LightmapTexCoord23.q))) - myhalf3 (0.5);; -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -weightedDiffuseNormal += lsColor3 * diffuseNormal; -color.rgb += lsColor3 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture3, LightmapTexCoord23.pq)); +#endif +#ifdef APPLY_RGB_DISTANCERAMP + Color.rgb *= DISTANCERAMP(u_RGBGenFuncArgs[2], u_RGBGenFuncArgs[3], u_RGBGenFuncArgs[0], u_RGBGenFuncArgs[1]); #endif + +#ifdef APPLY_ALPHA_DISTANCERAMP + Color.a *= DISTANCERAMP(u_AlphaGenFuncArgs[2], u_AlphaGenFuncArgs[3], u_AlphaGenFuncArgs[0], u_AlphaGenFuncArgs[1]); #endif + + return Color; +#if defined(APPLY_RGB_DISTANCERAMP) || defined(APPLY_ALPHA_DISTANCERAMP) +#undef DISTANCERAMP #endif +} + + +#if defined(APPLY_TC_GEN_REFLECTION) +uniform mat4 u_ReflectionTexMatrix; +#elif defined(APPLY_TC_GEN_VECTOR) +uniform mat4 u_VectorTexMatrix; #endif -#ifdef APPLY_SPECULAR +void main(void) +{ + vec4 Position = a_Position; + vec3 Normal = a_Normal.xyz; + vec2 TexCoord = a_TexCoord; + myhalf4 inColor = myhalf4(a_Color); + + TransformVerts(Position, Normal, TexCoord); -#ifdef NORMALIZE_DIFFUSE_NORMAL -specularNormal = normalize (myhalf3 (normalize (weightedDiffuseNormal)) + myhalf3 (normalize (EyeVector))); + myhalf4 outColor = VertexRGBGen(Position, Normal, inColor); + +#ifdef APPLY_FOG +#if defined(APPLY_FOG_COLOR) + FogGen(Position, outColor, u_BlendMix); #else -specularNormal = normalize (weightedDiffuseNormal + myhalf3 (normalize (EyeVector))); + FogGen(Position, v_FogCoord); #endif +#endif // APPLY_FOG -specularProduct = float (dot (surfaceNormal, specularNormal)); -color.rgb += (myhalf3(texture2D(GlossTexture, TexCoord)) * GlossIntensity) * pow(myhalf(max(specularProduct, 0.0)), GlossExponent); -#endif + qf_FrontColor = vec4(outColor); + +#if defined(APPLY_TC_GEN_ENV) + vec3 Projection; -#ifdef APPLY_BASETEX_ALPHA_ONLY -color = min(color, myhalf4(texture2D(BaseTexture, TexCoord).a)); + Projection = u_EntityDist - Position.xyz; + Projection = normalize(Projection); + + float Depth = dot(Normal.xyz, Projection) * 2.0; + v_TexCoord = vec2(0.5 + (Normal.y * Depth - Projection.y) * 0.5, 0.5 - (Normal.z * Depth - Projection.z) * 0.5); +#elif defined(APPLY_TC_GEN_VECTOR) + v_TexCoord = vec2(u_VectorTexMatrix * Position); +#elif defined(APPLY_TC_GEN_REFLECTION) + v_TexCoord = vec3(u_ReflectionTexMatrix * vec4(reflect(normalize(Position.xyz - u_EntityDist), Normal.xyz), 0.0)); +#elif defined(APPLY_TC_GEN_PROJECTION) + v_TexCoord = vec2(normalize(u_ModelViewProjectionMatrix * Position) * 0.5 + vec4(0.5)); #else -#ifdef APPLY_COLOR_CLAMPING -color = min(color, myhalf4(1.0)); + v_TexCoord = TextureMatrix2x3Mul(u_TextureMatrix, TexCoord); +#endif // defined(APPLY_TC_GEN_ENV) + + v_Position = Position.xyz; + +#ifdef APPLY_DRAWFLAT + v_NormalZ = Normal.z; +#endif + +#ifdef NUM_LIGHTMAPS + v_LightmapTexCoord[0] = a_LightmapCoord0; +#if NUM_LIGHTMAPS >= 2 + v_LightmapTexCoord[1] = a_LightmapCoord1; +#if NUM_LIGHTMAPS >= 3 + v_LightmapTexCoord[2] = a_LightmapCoord2; +#if NUM_LIGHTMAPS >= 4 + v_LightmapTexCoord[3] = a_LightmapCoord3; +#endif // NUM_LIGHTMAPS >= 4 +#endif // NUM_LIGHTMAPS >= 3 +#endif // NUM_LIGHTMAPS >= 2 +#endif // NUM_LIGHTMAPS + + gl_Position = u_ModelViewProjectionMatrix * Position; + +#if defined(APPLY_SOFT_PARTICLE) + vec4 modelPos = u_ModelViewMatrix * Position; + v_Depth = -modelPos.z; +#endif +} + +#endif // VERTEX_SHADER + +#ifdef FRAGMENT_SHADER +// Fragment shader + +#ifdef APPLY_CUBEMAP +uniform samplerCube u_BaseTexture; +#else +uniform sampler2D u_BaseTexture; +#endif + +#ifdef APPLY_DRAWFLAT +uniform myhalf3 u_WallColor; +uniform myhalf3 u_FloorColor; #endif -color = color * myhalf4(texture2D(BaseTexture, TexCoord)); + +#ifdef NUM_LIGHTMAPS +uniform sampler2D u_LightmapTexture[NUM_LIGHTMAPS]; #endif -#ifdef APPLY_DECAL -#ifdef APPLY_DECAL_ADD -myhalf3 decal = myhalf3(gl_Color.rgb) * myhalf3(texture2D(DecalTexture, TexCoord)); -color.rgb = decal.rgb + color.rgb; -color.a = color.a * myhalf(gl_Color.a); -#else -myhalf4 decal = myhalf4(gl_Color.rgba); -if (decal.a > 0.0) +#if defined(APPLY_SOFT_PARTICLE) +#ifdef FRAGMENT_SHADER + +myhalf FragmentSoftness(float Depth, sampler2D DepthTexture, in vec2 ScreenCoord, in ivec4 Viewport, in float ZNear, in float ZFar, myhalf Scale) { -decal = decal * myhalf4(texture2D(DecalTexture, TexCoord)); -color.rgb = decal.rgb * decal.a + color.rgb * (1.0-decal.a); + vec2 tc = ScreenCoord * u_TextureParams.zw; + + myhalf fragdepth = ZNear*ZFar/(ZFar - qf_texture(DepthTexture, tc).r*(ZFar-ZNear)); + myhalf partdepth = Depth; + + myhalf d = max((fragdepth - partdepth) * Scale, 0.0); + myhalf softness = 1.0 - min(1.0, d); + + softness *= softness; + softness = 1.0 - softness * softness; + return softness; } + +#endif + + +uniform sampler2D u_DepthTexture; + #endif + +void main(void) +{ + myhalf4 color; + +#ifdef NUM_LIGHTMAPS + color = myhalf4(0.0, 0.0, 0.0, qf_FrontColor.a); + color.rgb += myhalf3(qf_texture(u_LightmapTexture[0], v_LightmapTexCoord[0])) * u_LightstyleColor[0]; +#if NUM_LIGHTMAPS >= 2 + color.rgb += myhalf3(qf_texture(u_LightmapTexture[1], v_LightmapTexCoord[1])) * u_LightstyleColor[1]; +#if NUM_LIGHTMAPS >= 3 + color.rgb += myhalf3(qf_texture(u_LightmapTexture[2], v_LightmapTexCoord[2])) * u_LightstyleColor[2]; +#if NUM_LIGHTMAPS >= 4 + color.rgb += myhalf3(qf_texture(u_LightmapTexture[3], v_LightmapTexCoord[3])) * u_LightstyleColor[3]; +#endif // NUM_LIGHTMAPS >= 4 +#endif // NUM_LIGHTMAPS >= 3 +#endif // NUM_LIGHTMAPS >= 2 #else -color = color * myhalf4(gl_Color.rgba); + color = myhalf4(qf_FrontColor); +#endif // NUM_LIGHTMAPS + +#if defined(APPLY_FOG) && !defined(APPLY_FOG_COLOR) + myhalf fogDensity = FogDensity(v_FogCoord); #endif -#ifdef APPLY_GRAYSCALE -float grey = dot(color, myhalf3(0.299, 0.587, 0.114)); -gl_FragColor = vec4(vec3(grey),color.a); +#if defined(NUM_DLIGHTS) + color.rgb += DynamicLightsSummaryColor(v_Position); +#endif + + myhalf4 diffuse; + +#ifdef APPLY_CUBEMAP + diffuse = myhalf4(qf_textureCube(u_BaseTexture, v_TexCoord)); #else -gl_FragColor = vec4(color); + diffuse = myhalf4(qf_texture(u_BaseTexture, v_TexCoord)); #endif -} -#endif // FRAGMENT_SHADER +#ifdef APPLY_DRAWFLAT + myhalf n = myhalf(step(DRAWFLAT_NORMAL_STEP, abs(v_NormalZ))); + diffuse.rgb = myhalf3(mix(u_WallColor, u_FloorColor, n)); +#endif + color *= diffuse; +#ifdef NUM_LIGHTMAPS + // so that team-colored shaders work + color *= myhalf4(qf_FrontColor); +#endif -[vertex shader] -#define VERTEX_SHADER -#define APPLY_LIGHTSTYLE0 -#define APPLY_FBLIGHTMAP -#define APPLY_AMBIENT_COMPENSATION -// Warsow GLSL shader +#ifdef APPLY_GREYSCALE + color.rgb = Greyscale(color.rgb); +#endif + +#if defined(APPLY_FOG) && !defined(APPLY_FOG_COLOR) + color.rgb = mix(color.rgb, u_Fog.Color, fogDensity); +#endif + +#if defined(APPLY_SOFT_PARTICLE) + myhalf softness = FragmentSoftness(v_Depth, u_DepthTexture, gl_FragCoord.xy, u_Viewport, u_ZNear, u_ZFar, u_SoftParticlesScale); + color *= mix(myhalf4(1.0), myhalf4(softness), u_BlendMix.xxxy); +#endif + + qf_FragColor = vec4(color); +} -#if !defined(__GLSL_CG_DATA_TYPES) +#endif // FRAGMENT_SHADER + +[fragment shader] +#version 130 + +#define QF_GLSL_VERSION 130 +#define FRAGMENT_SHADER +#if !defined(myhalf) +//#if !defined(__GLSL_CG_DATA_TYPES) #define myhalf float #define myhalf2 vec2 #define myhalf3 vec3 #define myhalf4 vec4 +//#else +//#define myhalf half +//#define myhalf2 half2 +//#define myhalf3 half3 +//#define myhalf4 half4 +//#endif +#endif + +#if QF_GLSL_VERSION >= 130 + precision highp float; + +# ifdef VERTEX_SHADER + out myhalf4 qf_FrontColor; +# define qf_varying out +# define qf_attribute in +# endif +# ifdef FRAGMENT_SHADER + in myhalf4 qf_FrontColor; + out myhalf4 qf_FragColor; +# define qf_varying in +# define qf_attribute in +# endif + +# define qf_texture texture +# define qf_textureCube texture +# define qf_textureLod textureLod +# define qf_textureOffset(a,b,c,d) textureOffset(a,b,ivec2(c,d)) +# define qf_shadow texture #else -#define myhalf half -#define myhalf2 half2 -#define myhalf3 half3 -#define myhalf4 half4 +# ifdef VERTEX_SHADER +# define qf_FrontColor gl_FrontColor +# define qf_varying varying +# define qf_attribute attribute +# endif + +# ifdef FRAGMENT_SHADER +# define qf_FrontColor gl_Color +# define qf_FragColor gl_FragColor +# define qf_varying varying +# define qf_attribute attribute +# endif +# define qf_texture texture2D +# define qf_textureLod texture2DLod +# define qf_textureCube textureCube +# define qf_textureOffset(a,b,c,d) texture2DOffset(a,b,ivec2(c,d)) +# define qf_shadow shadow2D #endif -varying vec2 TexCoord; -#ifdef APPLY_LIGHTSTYLE0 -varying vec4 LightmapTexCoord01; -#ifdef APPLY_LIGHTSTYLE2 -varying vec4 LightmapTexCoord23; +#ifndef M_PI +#define M_PI 3.14159265358979323846 #endif +#ifndef M_TWOPI +#define M_TWOPI 6.28318530717958647692 #endif -#if defined(APPLY_SPECULAR) || defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -varying vec3 EyeVector; +#ifndef MAX_UNIFORM_BONES +#define MAX_UNIFORM_BONES 100 #endif -#ifdef APPLY_DIRECTIONAL_LIGHT -varying vec3 LightVector; +#ifndef MAX_UNIFORM_INSTANCES +#define MAX_UNIFORM_INSTANCES 40 #endif +uniform vec3 u_QF_ViewOrigin; +uniform mat3 u_QF_ViewAxis; +uniform float u_QF_MirrorSide; +uniform vec3 u_QF_EntityOrigin; +uniform float u_QF_ShaderTime; + +#ifndef M_PI +#define M_PI 3.14159265358979323846 +#endif +#ifndef M_TWOPI +#define M_TWOPI 6.28318530717958647692 +#endif + +#ifndef WAVE_SIN +float QF_WaveFunc_Sin(float x) +{ +x -= floor(x); +return sin(x * M_TWOPI); +} +float QF_WaveFunc_Triangle(float x) +{ +x -= floor(x); +return step(x, 0.25) * x * 4.0 + (2.0 - 4.0 * step(0.25, x) * step(x, 0.75) * x) + ((step(0.75, x) * x - 0.75) * 4.0 - 1.0); +} +float QF_WaveFunc_Square(float x) +{ +x -= floor(x); +return step(x, 0.5) * 2.0 - 1.0; +} +float QF_WaveFunc_Sawtooth(float x) +{ +x -= floor(x); +return x; +} +float QF_QF_WaveFunc_InverseSawtooth(float x) +{ +x -= floor(x); +return 1.0 - x; +} -varying mat3 strMatrix; // directions of S/T/R texcoords (tangent, binormal, normal) +#define WAVE_SIN(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Sin((phase)+(time)*(freq)))) +#define WAVE_TRIANGLE(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Triangle((phase)+(time)*(freq)))) +#define WAVE_SQUARE(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Square((phase)+(time)*(freq)))) +#define WAVE_SAWTOOTH(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_WaveFunc_Sawtooth((phase)+(time)*(freq)))) +#define WAVE_INVERSESAWTOOTH(time,base,amplitude,phase,freq) (((base)+(amplitude)*QF_QF_WaveFunc_InverseSawtooth((phase)+(time)*(freq)))) +#endif #ifdef VERTEX_SHADER -// Vertex shader +attribute vec4 a_BonesIndices; +attribute vec4 a_BonesWeights; -uniform vec3 EyeOrigin; +uniform vec4 u_QF_DualQuats[MAX_UNIFORM_BONES*2]; -#ifdef APPLY_DIRECTIONAL_LIGHT -uniform vec3 LightDir; +#if defined(DUAL_QUAT_TRANSFORM_NORMALS) +#if defined(DUAL_QUAT_TRANSFORM_TANGENT) +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal, inout vec3 Tangent) +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal) +#endif +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position) #endif +{ +int index; +vec4 Indices = a_BonesIndices; +vec4 Weights = a_BonesWeights; +vec4 Indices_2 = Indices * 2.0; +vec4 DQReal, DQDual; + +index = int(Indices_2.x); +DQReal = u_QF_DualQuats[index+0]; +DQDual = u_QF_DualQuats[index+1]; -void main() +if (numWeights > 1) { -gl_FrontColor = gl_Color; +DQReal *= Weights.x; +DQDual *= Weights.x; -TexCoord = vec2 (gl_TextureMatrix[0] * gl_MultiTexCoord0); +vec4 DQReal1, DQDual1; +float scale; -#ifdef APPLY_LIGHTSTYLE0 -LightmapTexCoord01.st = gl_MultiTexCoord4.st; -#ifdef APPLY_LIGHTSTYLE1 -LightmapTexCoord01.pq = gl_MultiTexCoord5.st; -#ifdef APPLY_LIGHTSTYLE2 -LightmapTexCoord23.st = gl_MultiTexCoord6.st; -#ifdef APPLY_LIGHTSTYLE3 -LightmapTexCoord23.pq = gl_MultiTexCoord7.st; +index = int(Indices_2.y); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.y; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 2) +{ +index = int(Indices_2.z); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.z; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 3) +{ +index = int(Indices_2.w); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.w; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; +} +} +} + +float len = length(DQReal); +DQReal /= len; +DQDual /= len; + +Position.xyz = (cross(DQReal.xyz, cross(DQReal.xyz, Position.xyz) + Position.xyz*DQReal.w + DQDual.xyz) + DQDual.xyz*DQReal.w - DQReal.xyz*DQDual.w)*2.0 + Position.xyz; + +#ifdef DUAL_QUAT_TRANSFORM_NORMALS +Normal = cross(DQReal.xyz, cross(DQReal.xyz, Normal) + Normal*DQReal.w)*2.0 + Normal; #endif + +#ifdef DUAL_QUAT_TRANSFORM_TANGENT +Tangent = cross(DQReal.xyz, cross(DQReal.xyz, Tangent) + Tangent*DQReal.w)*2.0 + Tangent; #endif +} + +// use defines to overload the transform function + +#define DUAL_QUAT_TRANSFORM_NORMALS +#if defined(DUAL_QUAT_TRANSFORM_NORMALS) +#if defined(DUAL_QUAT_TRANSFORM_TANGENT) +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal, inout vec3 Tangent) +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal) #endif +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position) #endif +{ +int index; +vec4 Indices = a_BonesIndices; +vec4 Weights = a_BonesWeights; +vec4 Indices_2 = Indices * 2.0; +vec4 DQReal, DQDual; + +index = int(Indices_2.x); +DQReal = u_QF_DualQuats[index+0]; +DQDual = u_QF_DualQuats[index+1]; + +if (numWeights > 1) +{ +DQReal *= Weights.x; +DQDual *= Weights.x; + +vec4 DQReal1, DQDual1; +float scale; + +index = int(Indices_2.y); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.y; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 2) +{ +index = int(Indices_2.z); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.z; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 3) +{ +index = int(Indices_2.w); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.w; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; +} +} +} + +float len = length(DQReal); +DQReal /= len; +DQDual /= len; -strMatrix[0] = gl_MultiTexCoord1.xyz; -strMatrix[2] = gl_Normal.xyz; -strMatrix[1] = gl_MultiTexCoord1.w * cross (strMatrix[2], strMatrix[0]); +Position.xyz = (cross(DQReal.xyz, cross(DQReal.xyz, Position.xyz) + Position.xyz*DQReal.w + DQDual.xyz) + DQDual.xyz*DQReal.w - DQReal.xyz*DQDual.w)*2.0 + Position.xyz; -#if defined(APPLY_SPECULAR) || defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -vec3 EyeVectorWorld = EyeOrigin - gl_Vertex.xyz; -EyeVector = EyeVectorWorld * strMatrix; +#ifdef DUAL_QUAT_TRANSFORM_NORMALS +Normal = cross(DQReal.xyz, cross(DQReal.xyz, Normal) + Normal*DQReal.w)*2.0 + Normal; #endif -#ifdef APPLY_DIRECTIONAL_LIGHT -LightVector = LightDir * strMatrix; +#ifdef DUAL_QUAT_TRANSFORM_TANGENT +Tangent = cross(DQReal.xyz, cross(DQReal.xyz, Tangent) + Tangent*DQReal.w)*2.0 + Tangent; #endif +} -gl_Position = ftransform (); -#ifdef APPLY_CLIPPING -#ifdef __GLSL_CG_DATA_TYPES -gl_ClipVertex = gl_ModelViewMatrix * gl_Vertex; +#define DUAL_QUAT_TRANSFORM_TANGENT +#if defined(DUAL_QUAT_TRANSFORM_NORMALS) +#if defined(DUAL_QUAT_TRANSFORM_TANGENT) +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal, inout vec3 Tangent) +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position, inout vec3 Normal) #endif +#else +void QF_VertexDualQuatsTransform(const int numWeights, inout vec4 Position) #endif -} +{ +int index; +vec4 Indices = a_BonesIndices; +vec4 Weights = a_BonesWeights; +vec4 Indices_2 = Indices * 2.0; +vec4 DQReal, DQDual; -#endif // VERTEX_SHADER +index = int(Indices_2.x); +DQReal = u_QF_DualQuats[index+0]; +DQDual = u_QF_DualQuats[index+1]; +if (numWeights > 1) +{ +DQReal *= Weights.x; +DQDual *= Weights.x; -#ifdef FRAGMENT_SHADER -// Fragment shader +vec4 DQReal1, DQDual1; +float scale; + +index = int(Indices_2.y); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.y; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; -#ifdef APPLY_LIGHTSTYLE0 -uniform sampler2D LightmapTexture0; -uniform float DeluxemapOffset0; // s-offset for LightmapTexCoord -uniform myhalf3 lsColor0; // lightstyle color - -#ifdef APPLY_LIGHTSTYLE1 -uniform sampler2D LightmapTexture1; -uniform float DeluxemapOffset1; -uniform myhalf3 lsColor1; +if (numWeights > 2) +{ +index = int(Indices_2.z); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.z; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; + +if (numWeights > 3) +{ +index = int(Indices_2.w); +DQReal1 = u_QF_DualQuats[index+0]; +DQDual1 = u_QF_DualQuats[index+1]; +// antipodality handling +scale = (dot(DQReal1, DQReal) < 0.0 ? -1.0 : 1.0) * Weights.w; +DQReal += DQReal1 * scale; +DQDual += DQDual1 * scale; +} +} +} -#ifdef APPLY_LIGHTSTYLE2 -uniform sampler2D LightmapTexture2; -uniform float DeluxemapOffset2; -uniform myhalf3 lsColor2; +float len = length(DQReal); +DQReal /= len; +DQDual /= len; -#ifdef APPLY_LIGHTSTYLE3 -uniform sampler2D LightmapTexture3; -uniform float DeluxemapOffset3; -uniform myhalf3 lsColor3; +Position.xyz = (cross(DQReal.xyz, cross(DQReal.xyz, Position.xyz) + Position.xyz*DQReal.w + DQDual.xyz) + DQDual.xyz*DQReal.w - DQReal.xyz*DQDual.w)*2.0 + Position.xyz; +#ifdef DUAL_QUAT_TRANSFORM_NORMALS +Normal = cross(DQReal.xyz, cross(DQReal.xyz, Normal) + Normal*DQReal.w)*2.0 + Normal; #endif + +#ifdef DUAL_QUAT_TRANSFORM_TANGENT +Tangent = cross(DQReal.xyz, cross(DQReal.xyz, Tangent) + Tangent*DQReal.w)*2.0 + Tangent; #endif +} + #endif +#ifdef VERTEX_SHADER +#ifdef APPLY_INSTANCED_ATTRIB_TRASNFORMS +attribute vec4 a_InstanceQuat; +attribute vec4 a_InstancePosAndScale; +#elif defined(GL_ARB_draw_instanced) + +uniform vec4 u_QF_InstancePoints[MAX_UNIFORM_INSTANCES*2]; + +#define a_InstanceQuat u_QF_InstancePoints[gl_InstanceID*2] +#define a_InstancePosAndScale u_QF_InstancePoints[gl_InstanceID*2+1] +#else +uniform vec4 u_QF_InstancePoints[2]; +#define a_InstanceQuat u_QF_InstancePoints[0] +#define a_InstancePosAndScale u_QF_InstancePoints[1] #endif -uniform sampler2D BaseTexture; -uniform sampler2D NormalmapTexture; -uniform sampler2D GlossTexture; -#ifdef APPLY_DECAL -uniform sampler2D DecalTexture; +void QF_InstancedTransform(inout vec4 Position, inout vec3 Normal) +{ +Position.xyz = (cross(a_InstanceQuat.xyz, cross(a_InstanceQuat.xyz, Position.xyz) + Position.xyz*a_InstanceQuat.w)*2.0 + Position.xyz) * + a_InstancePosAndScale.w + a_InstancePosAndScale.xyz; +Normal = cross(a_InstanceQuat.xyz, cross(a_InstanceQuat.xyz, Normal) + Normal*a_InstanceQuat.w)*2.0 + Normal; +} + #endif +#define QF_LatLong2Norm(ll) vec3(cos((ll).y) * sin((ll).x), sin((ll).y) * sin((ll).x), cos((ll).x)) + +#define APPLY_RGB_CONST +#define APPLY_RGB_DISTANCERAMP +#define APPLY_ALPHA_CONST +#define APPLY_SOFT_PARTICLE + +#define DRAWFLAT_NORMAL_STEP 0.5 // floor or ceiling if < abs(normal.z) +uniform mat4 u_ModelViewMatrix; +uniform mat4 u_ModelViewProjectionMatrix; + +uniform float u_ShaderTime; + +uniform vec3 u_ViewOrigin; +uniform mat3 u_ViewAxis; + +uniform vec3 u_EntityDist; +uniform vec3 u_EntityOrigin; +uniform myhalf4 u_EntityColor; + +uniform myhalf4 u_ConstColor; +uniform myhalf4 u_RGBGenFuncArgs, u_AlphaGenFuncArgs; +uniform myhalf3 u_LightstyleColor[4]; // lightstyle colors + +uniform myhalf3 u_LightAmbient; +uniform myhalf3 u_LightDiffuse; +uniform vec3 u_LightDir; + +uniform myhalf2 u_BlendMix; + +uniform vec2 u_TextureMatrix[3]; +#define TextureMatrix2x3Mul(m2x3,tc) vec2(dot((m2x3)[0],(tc)) + (m2x3)[2][0], dot((m2x3)[1],(tc)) + (m2x3)[2][1]) + +uniform float u_MirrorSide; + +uniform float u_ZNear, u_ZFar; + +uniform ivec4 u_Viewport; // x, y, width, height -#if defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -uniform float OffsetMappingScale; +uniform vec4 u_TextureParams; + +uniform myhalf u_SoftParticlesScale; + + +#if defined(NUM_DLIGHTS) +#if defined(FRAGMENT_SHADER) +#if defined(NUM_DLIGHTS) + +struct DynamicLight +{ + myhalf Radius; + vec3 Position; + myhalf3 Diffuse; +}; + +uniform DynamicLight u_DynamicLights[NUM_DLIGHTS]; +uniform int u_NumDynamicLights; +#ifdef DLIGHTS_SURFACE_NORMAL_IN +myhalf3 DynamicLightsSummaryColor(in vec3 Position, in myhalf3 surfaceNormalModelspace) +#else +myhalf3 DynamicLightsSummaryColor(in vec3 Position) #endif +{ + myhalf3 Color = myhalf3(0.0); -uniform myhalf3 LightAmbient; -#ifdef APPLY_DIRECTIONAL_LIGHT -uniform myhalf3 LightDiffuse; +#if QF_GLSL_VERSION >= 330 + for (int i = 0; i < u_NumDynamicLights; i++) +#else + for (int i = 0; i < NUM_DLIGHTS; i++) #endif + { + myhalf3 STR = myhalf3(u_DynamicLights[i].Position - Position); + myhalf distance = length(STR); + myhalf falloff = clamp(1.0 - distance / u_DynamicLights[i].Radius, 0.0, 1.0); + + falloff *= falloff; + + #ifdef DLIGHTS_SURFACE_NORMAL_IN + falloff *= myhalf(max(dot(normalize(STR), surfaceNormalModelspace), 0.0)); + #endif + + Color += falloff * u_DynamicLights[i].Diffuse; + } + + return Color; +} -uniform myhalf GlossIntensity; // gloss scaling factor -uniform myhalf GlossExponent; // gloss exponent factor -#if defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -// The following reliefmapping and offsetmapping routine was taken from DarkPlaces -// The credit goes to LordHavoc (as always) -vec2 OffsetMapping(vec2 TexCoord) +#define DLIGHTS_SURFACE_NORMAL_IN +#ifdef DLIGHTS_SURFACE_NORMAL_IN +myhalf3 DynamicLightsSummaryColor(in vec3 Position, in myhalf3 surfaceNormalModelspace) +#else +myhalf3 DynamicLightsSummaryColor(in vec3 Position) +#endif { -#ifdef APPLY_RELIEFMAPPING -// 14 sample relief mapping: linear search and then binary search -// this basically steps forward a small amount repeatedly until it finds -// itself inside solid, then jitters forward and back using decreasing -// amounts to find the impact -//vec3 OffsetVector = vec3(EyeVector.xy * ((1.0 / EyeVector.z) * OffsetMappingScale) * vec2(-1, 1), -1); -//vec3 OffsetVector = vec3(normalize(EyeVector.xy) * OffsetMappingScale * vec2(-1, 1), -1); -vec3 OffsetVector = vec3(normalize(EyeVector).xy * OffsetMappingScale * vec2(-1, 1), -1); -vec3 RT = vec3(TexCoord, 1); -OffsetVector *= 0.1; -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * step(texture2D(NormalmapTexture, RT.xy).a, RT.z); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) - 0.5); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.5 - 0.25); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.25 - 0.125); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.125 - 0.0625); -RT += OffsetVector * (step(texture2D(NormalmapTexture, RT.xy).a, RT.z) * 0.0625 - 0.03125); -return RT.xy; + myhalf3 Color = myhalf3(0.0); + +#if QF_GLSL_VERSION >= 330 + for (int i = 0; i < u_NumDynamicLights; i++) #else -// 2 sample offset mapping (only 2 samples because of ATI Radeon 9500-9800/X300 limits) -// this basically moves forward the full distance, and then backs up based -// on height of samples -//vec2 OffsetVector = vec2(EyeVector.xy * ((1.0 / EyeVector.z) * OffsetMappingScale) * vec2(-1, 1)); -//vec2 OffsetVector = vec2(normalize(EyeVector.xy) * OffsetMappingScale * vec2(-1, 1)); -vec2 OffsetVector = vec2(normalize(EyeVector).xy * OffsetMappingScale * vec2(-1, 1)); -TexCoord += OffsetVector; -OffsetVector *= 0.5; -TexCoord -= OffsetVector * texture2D(NormalmapTexture, TexCoord).a; -TexCoord -= OffsetVector * texture2D(NormalmapTexture, TexCoord).a; -return TexCoord; + for (int i = 0; i < NUM_DLIGHTS; i++) #endif + { + myhalf3 STR = myhalf3(u_DynamicLights[i].Position - Position); + myhalf distance = length(STR); + myhalf falloff = clamp(1.0 - distance / u_DynamicLights[i].Radius, 0.0, 1.0); + + falloff *= falloff; + + #ifdef DLIGHTS_SURFACE_NORMAL_IN + falloff *= myhalf(max(dot(normalize(STR), surfaceNormalModelspace), 0.0)); + #endif + + Color += falloff * u_DynamicLights[i].Diffuse; + } + + return Color; } + + +#endif + +#endif #endif -void main() +#ifdef APPLY_FOG +struct Fog +{ + float EyeDist; + vec4 EyePlane, Plane; + myhalf3 Color; + float Scale; +}; + +uniform Fog u_Fog; + +#define FOG_TEXCOORD_STEP 1.0/256.0 + +#define FogDensity(coord) sqrt(clamp((coord)[0],0.0,1.0))*step(FOG_TEXCOORD_STEP,(coord)[1]) + +#define FOG_GEN_OUTPUT_COLOR +#if defined(FOG_GEN_OUTPUT_COLOR) +void FogGen(in vec4 Position, inout myhalf4 outColor, in myhalf2 blendMix) +#elif defined(FOG_GEN_OUTPUT_TEXCOORDS) +void FogGen(in vec4 Position, inout vec2 outTexCoord) +#endif { -#if defined(APPLY_OFFSETMAPPING) || defined(APPLY_RELIEFMAPPING) -// apply offsetmapping -vec2 TexCoordOffset = OffsetMapping(TexCoord); -#define TexCoord TexCoordOffset + // side = vec2(inside, outside) + myhalf2 side = myhalf2(step(u_Fog.EyeDist, 0.0), step(0.0, u_Fog.EyeDist)); + myhalf FDist = dot(Position.xyz, u_Fog.EyePlane.xyz) - u_Fog.EyePlane.w; + myhalf FVdist = dot(Position.xyz, u_Fog.Plane.xyz) - u_Fog.Plane.w; + myhalf FogDistScale = FVdist / (FVdist - u_Fog.EyeDist); + +#if defined(FOG_GEN_OUTPUT_COLOR) + myhalf FogDist = FDist * dot(side, myhalf2(1.0, FogDistScale)); + myhalf FogScale = myhalf(clamp(1.0 - FogDist * u_Fog.Scale, 0.0, 1.0)); + outColor *= mix(myhalf4(1.0), myhalf4(FogScale), blendMix.xxxy); #endif -myhalf3 surfaceNormal; -myhalf3 diffuseNormalModelspace; -myhalf3 diffuseNormal = myhalf3 (0.0, 0.0, -1.0); -float diffuseProduct; -#ifdef APPLY_CELLSHADING -int lightcell; -float diffuseProductPositive; -float diffuseProductNegative; -float hardShadow; + +#if defined(FOG_GEN_OUTPUT_TEXCOORDS) + myhalf FogS = FDist * dot(side, myhalf2(1.0, step(FVdist, 0.0) * FogDistScale)); + myhalf FogT = -FVdist; + outTexCoord = vec2(FogS * u_Fog.Scale, FogT * u_Fog.Scale + 1.5*FOG_TEXCOORD_STEP); #endif +} -myhalf3 weightedDiffuseNormal; -myhalf3 specularNormal; -float specularProduct; -#if !defined(APPLY_DIRECTIONAL_LIGHT) && !defined(APPLY_LIGHTSTYLE0) -myhalf4 color = myhalf4 (1.0, 1.0, 1.0, 1.0); -#else -myhalf4 color = myhalf4 (0.0, 0.0, 0.0, 1.0); +#undef FOG_GEN_OUTPUT_COLOR +#define FOG_GEN_OUTPUT_TEXCOORDS +#if defined(FOG_GEN_OUTPUT_COLOR) +void FogGen(in vec4 Position, inout myhalf4 outColor, in myhalf2 blendMix) +#elif defined(FOG_GEN_OUTPUT_TEXCOORDS) +void FogGen(in vec4 Position, inout vec2 outTexCoord) +#endif +{ + // side = vec2(inside, outside) + myhalf2 side = myhalf2(step(u_Fog.EyeDist, 0.0), step(0.0, u_Fog.EyeDist)); + myhalf FDist = dot(Position.xyz, u_Fog.EyePlane.xyz) - u_Fog.EyePlane.w; + myhalf FVdist = dot(Position.xyz, u_Fog.Plane.xyz) - u_Fog.Plane.w; + myhalf FogDistScale = FVdist / (FVdist - u_Fog.EyeDist); + +#if defined(FOG_GEN_OUTPUT_COLOR) + myhalf FogDist = FDist * dot(side, myhalf2(1.0, FogDistScale)); + myhalf FogScale = myhalf(clamp(1.0 - FogDist * u_Fog.Scale, 0.0, 1.0)); + outColor *= mix(myhalf4(1.0), myhalf4(FogScale), blendMix.xxxy); +#endif + +#if defined(FOG_GEN_OUTPUT_TEXCOORDS) + myhalf FogS = FDist * dot(side, myhalf2(1.0, step(FVdist, 0.0) * FogDistScale)); + myhalf FogT = -FVdist; + outTexCoord = vec2(FogS * u_Fog.Scale, FogT * u_Fog.Scale + 1.5*FOG_TEXCOORD_STEP); #endif +} -// get the surface normal -surfaceNormal = normalize (myhalf3 (texture2D (NormalmapTexture, TexCoord)) - myhalf3 (0.5)); +#endif -#ifdef APPLY_DIRECTIONAL_LIGHT -diffuseNormal = myhalf3 (LightVector); -weightedDiffuseNormal = diffuseNormal; -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -#ifdef APPLY_CELLSHADING -hardShadow = 0.0; -diffuseProductPositive = max (diffuseProduct, 0.0); -diffuseProductNegative = (-min (diffuseProduct, 0.0) - 0.3); +#ifdef APPLY_GREYSCALE +myhalf3 Greyscale(myhalf3 color) +{ + return myhalf3(dot(color, myhalf3(0.299, 0.587, 0.114))); +} -// smooth the hard shadow edge -lightcell = int(max(diffuseProduct + 0.1, 0.0) * 2.0); -hardShadow += float(lightcell); +#endif -lightcell = int(max(diffuseProduct + 0.055, 0.0) * 2.0); -hardShadow += float(lightcell); +qf_varying vec3 v_Position; -lightcell = int(diffuseProductPositive * 2.0); -hardShadow += float(lightcell); +#ifdef APPLY_DRAWFLAT +qf_varying myhalf v_NormalZ; +#endif -color.rgb += myhalf(0.6 + hardShadow * 0.3333333333 * 0.27 + diffuseProductPositive * 0.14); +#ifdef APPLY_TC_GEN_REFLECTION +#define APPLY_CUBEMAP +#endif -// backlight -lightcell = int (diffuseProductNegative * 2.0); -color.rgb += myhalf (float(lightcell) * 0.085 + diffuseProductNegative * 0.085); +#ifdef APPLY_CUBEMAP +qf_varying vec3 v_TexCoord; #else -color.rgb += LightDiffuse.rgb * myhalf(max (diffuseProduct, 0.0)) + LightAmbient.rgb; +qf_varying vec2 v_TexCoord; +#endif + +#ifdef NUM_LIGHTMAPS +qf_varying vec2 v_LightmapTexCoord[NUM_LIGHTMAPS]; #endif +#if defined(APPLY_FOG) && !defined(APPLY_FOG_COLOR) +qf_varying vec2 v_FogCoord; #endif -// deluxemapping using light vectors in modelspace +#if defined(APPLY_SOFT_PARTICLE) +qf_varying float v_Depth; +#endif -#ifdef APPLY_LIGHTSTYLE0 +#ifdef VERTEX_SHADER +#ifdef VERTEX_SHADER +qf_attribute vec4 a_Position; +qf_attribute vec4 a_SVector; +qf_attribute vec4 a_Normal; +qf_attribute vec4 a_Color; +qf_attribute vec2 a_TexCoord; +qf_attribute vec2 a_LightmapCoord0, a_LightmapCoord1, a_LightmapCoord2, a_LightmapCoord3; +#endif +void TransformVerts(inout vec4 Position, inout vec3 Normal, inout vec2 TexCoord) +{ +#ifdef NUM_BONE_INFLUENCES + QF_VertexDualQuatsTransform(NUM_BONE_INFLUENCES, Position, Normal); +#endif -// get light normal -diffuseNormalModelspace = myhalf3 (texture2D(LightmapTexture0, vec2(LightmapTexCoord01.s+DeluxemapOffset0,LightmapTexCoord01.t))) - myhalf3 (0.5); -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -// calculate directional shading -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); +#ifdef APPLY_DEFORMVERTS + QF_DeformVerts(Position, Normal, TexCoord); +#endif -#ifdef APPLY_FBLIGHTMAP -weightedDiffuseNormal = diffuseNormal; -// apply lightmap color -color.rgb += myhalf3 (max (diffuseProduct, 0.0) * myhalf3 (texture2D (LightmapTexture0, LightmapTexCoord01.st))); -#else +#ifdef APPLY_INSTANCED_TRANSFORMS + QF_InstancedTransform(Position, Normal); +#endif +} -#define NORMALIZE_DIFFUSE_NORMAL +void TransformVerts(inout vec4 Position, inout vec3 Normal, inout vec3 Tangent, inout vec2 TexCoord) +{ +#ifdef NUM_BONE_INFLUENCES + QF_VertexDualQuatsTransform(NUM_BONE_INFLUENCES, Position, Normal, Tangent); +#endif -weightedDiffuseNormal = lsColor0 * diffuseNormal; -// apply lightmap color -color.rgb += lsColor0 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture0, LightmapTexCoord01.st)); +#ifdef APPLY_DEFORMVERTS + QF_DeformVerts(Position, Normal, TexCoord); #endif -#ifdef APPLY_AMBIENT_COMPENSATION -// compensate for ambient lighting -color.rgb += myhalf((1.0 - max (diffuseProduct, 0.0))) * LightAmbient; +#ifdef APPLY_INSTANCED_TRANSFORMS + QF_InstancedTransform(Position, Normal); +#endif +} +myhalf4 VertexRGBGen(in vec4 Position, in vec3 Normal, in myhalf4 VertexColor) +{ +#if defined(APPLY_RGB_DISTANCERAMP) || defined(APPLY_ALPHA_DISTANCERAMP) +#define DISTANCERAMP(x1,x2,y1,y2) ((y2 - y1) / (x2 - x1) * (clamp(myhalf(dot(u_EntityDist - Position.xyz, Normal)),0.0,x2) - x1) + y1) #endif -#ifdef APPLY_LIGHTSTYLE1 -diffuseNormalModelspace = myhalf3 (texture2D (LightmapTexture1, vec2(LightmapTexCoord01.p+DeluxemapOffset1,LightmapTexCoord01.q))) - myhalf3 (0.5); -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -weightedDiffuseNormal += lsColor1 * diffuseNormal; -color.rgb += lsColor1 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture1, LightmapTexCoord01.pq)); +#if defined(APPLY_RGB_CONST) && defined(APPLY_ALPHA_CONST) + myhalf4 Color = u_ConstColor; +#else + myhalf4 Color = myhalf4(1.0); + +#if defined(APPLY_RGB_CONST) + Color.rgb = u_ConstColor.rgb; +#elif defined(APPLY_RGB_VERTEX) + Color.rgb = VertexColor.rgb; +#elif defined(APPLY_RGB_ONE_MINUS_VERTEX) + Color.rgb = myhalf3(1.0) - VertexColor.rgb; +#elif defined(APPLY_RGB_GEN_DIFFUSELIGHT) + Color.rgb = myhalf3(u_LightAmbient + max(dot(u_LightDir, Normal), 0.0) * u_LightDiffuse); +#endif -#ifdef APPLY_LIGHTSTYLE2 -diffuseNormalModelspace = myhalf3 (texture2D (LightmapTexture2, vec2(LightmapTexCoord23.s+DeluxemapOffset2,LightmapTexCoord23.t))) - myhalf3 (0.5); -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -weightedDiffuseNormal += lsColor2 * diffuseNormal; -color.rgb += lsColor2 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture2, LightmapTexCoord23.st)); +#if defined(APPLY_ALPHA_CONST) + Color.a = u_ConstColor.a; +#elif defined(APPLY_ALPHA_VERTEX) + Color.a = VertexColor.a; +#elif defined(APPLY_ALPHA_ONE_MINUS_VERTEX) + Color.a = 1.0 - VertexColor.a; +#endif -#ifdef APPLY_LIGHTSTYLE3 -diffuseNormalModelspace = myhalf3 (texture2D (LightmapTexture3, vec2(LightmapTexCoord23.p+DeluxemapOffset3,LightmapTexCoord23.q))) - myhalf3 (0.5);; -diffuseNormal = normalize (myhalf3(dot(diffuseNormalModelspace,myhalf3(strMatrix[0])),dot(diffuseNormalModelspace,myhalf3(strMatrix[1])),dot(diffuseNormalModelspace,myhalf3(strMatrix[2])))); -diffuseProduct = float (dot (surfaceNormal, diffuseNormal)); -weightedDiffuseNormal += lsColor3 * diffuseNormal; -color.rgb += lsColor3 * myhalf(max (diffuseProduct, 0.0)) * myhalf3 (texture2D (LightmapTexture3, LightmapTexCoord23.pq)); +#endif +#ifdef APPLY_RGB_DISTANCERAMP + Color.rgb *= DISTANCERAMP(u_RGBGenFuncArgs[2], u_RGBGenFuncArgs[3], u_RGBGenFuncArgs[0], u_RGBGenFuncArgs[1]); #endif + +#ifdef APPLY_ALPHA_DISTANCERAMP + Color.a *= DISTANCERAMP(u_AlphaGenFuncArgs[2], u_AlphaGenFuncArgs[3], u_AlphaGenFuncArgs[0], u_AlphaGenFuncArgs[1]); #endif + + return Color; +#if defined(APPLY_RGB_DISTANCERAMP) || defined(APPLY_ALPHA_DISTANCERAMP) +#undef DISTANCERAMP #endif +} + + +#if defined(APPLY_TC_GEN_REFLECTION) +uniform mat4 u_ReflectionTexMatrix; +#elif defined(APPLY_TC_GEN_VECTOR) +uniform mat4 u_VectorTexMatrix; #endif -#ifdef APPLY_SPECULAR +void main(void) +{ + vec4 Position = a_Position; + vec3 Normal = a_Normal.xyz; + vec2 TexCoord = a_TexCoord; + myhalf4 inColor = myhalf4(a_Color); + + TransformVerts(Position, Normal, TexCoord); -#ifdef NORMALIZE_DIFFUSE_NORMAL -specularNormal = normalize (myhalf3 (normalize (weightedDiffuseNormal)) + myhalf3 (normalize (EyeVector))); + myhalf4 outColor = VertexRGBGen(Position, Normal, inColor); + +#ifdef APPLY_FOG +#if defined(APPLY_FOG_COLOR) + FogGen(Position, outColor, u_BlendMix); #else -specularNormal = normalize (weightedDiffuseNormal + myhalf3 (normalize (EyeVector))); + FogGen(Position, v_FogCoord); #endif +#endif // APPLY_FOG -specularProduct = float (dot (surfaceNormal, specularNormal)); -color.rgb += (myhalf3(texture2D(GlossTexture, TexCoord)) * GlossIntensity) * pow(myhalf(max(specularProduct, 0.0)), GlossExponent); -#endif + qf_FrontColor = vec4(outColor); + +#if defined(APPLY_TC_GEN_ENV) + vec3 Projection; -#ifdef APPLY_BASETEX_ALPHA_ONLY -color = min(color, myhalf4(texture2D(BaseTexture, TexCoord).a)); + Projection = u_EntityDist - Position.xyz; + Projection = normalize(Projection); + + float Depth = dot(Normal.xyz, Projection) * 2.0; + v_TexCoord = vec2(0.5 + (Normal.y * Depth - Projection.y) * 0.5, 0.5 - (Normal.z * Depth - Projection.z) * 0.5); +#elif defined(APPLY_TC_GEN_VECTOR) + v_TexCoord = vec2(u_VectorTexMatrix * Position); +#elif defined(APPLY_TC_GEN_REFLECTION) + v_TexCoord = vec3(u_ReflectionTexMatrix * vec4(reflect(normalize(Position.xyz - u_EntityDist), Normal.xyz), 0.0)); +#elif defined(APPLY_TC_GEN_PROJECTION) + v_TexCoord = vec2(normalize(u_ModelViewProjectionMatrix * Position) * 0.5 + vec4(0.5)); #else -#ifdef APPLY_COLOR_CLAMPING -color = min(color, myhalf4(1.0)); + v_TexCoord = TextureMatrix2x3Mul(u_TextureMatrix, TexCoord); +#endif // defined(APPLY_TC_GEN_ENV) + + v_Position = Position.xyz; + +#ifdef APPLY_DRAWFLAT + v_NormalZ = Normal.z; +#endif + +#ifdef NUM_LIGHTMAPS + v_LightmapTexCoord[0] = a_LightmapCoord0; +#if NUM_LIGHTMAPS >= 2 + v_LightmapTexCoord[1] = a_LightmapCoord1; +#if NUM_LIGHTMAPS >= 3 + v_LightmapTexCoord[2] = a_LightmapCoord2; +#if NUM_LIGHTMAPS >= 4 + v_LightmapTexCoord[3] = a_LightmapCoord3; +#endif // NUM_LIGHTMAPS >= 4 +#endif // NUM_LIGHTMAPS >= 3 +#endif // NUM_LIGHTMAPS >= 2 +#endif // NUM_LIGHTMAPS + + gl_Position = u_ModelViewProjectionMatrix * Position; + +#if defined(APPLY_SOFT_PARTICLE) + vec4 modelPos = u_ModelViewMatrix * Position; + v_Depth = -modelPos.z; +#endif +} + +#endif // VERTEX_SHADER + +#ifdef FRAGMENT_SHADER +// Fragment shader + +#ifdef APPLY_CUBEMAP +uniform samplerCube u_BaseTexture; +#else +uniform sampler2D u_BaseTexture; +#endif + +#ifdef APPLY_DRAWFLAT +uniform myhalf3 u_WallColor; +uniform myhalf3 u_FloorColor; #endif -color = color * myhalf4(texture2D(BaseTexture, TexCoord)); + +#ifdef NUM_LIGHTMAPS +uniform sampler2D u_LightmapTexture[NUM_LIGHTMAPS]; #endif -#ifdef APPLY_DECAL -#ifdef APPLY_DECAL_ADD -myhalf3 decal = myhalf3(gl_Color.rgb) * myhalf3(texture2D(DecalTexture, TexCoord)); -color.rgb = decal.rgb + color.rgb; -color.a = color.a * myhalf(gl_Color.a); -#else -myhalf4 decal = myhalf4(gl_Color.rgba); -if (decal.a > 0.0) +#if defined(APPLY_SOFT_PARTICLE) +#ifdef FRAGMENT_SHADER + +myhalf FragmentSoftness(float Depth, sampler2D DepthTexture, in vec2 ScreenCoord, in ivec4 Viewport, in float ZNear, in float ZFar, myhalf Scale) { -decal = decal * myhalf4(texture2D(DecalTexture, TexCoord)); -color.rgb = decal.rgb * decal.a + color.rgb * (1.0-decal.a); + vec2 tc = ScreenCoord * u_TextureParams.zw; + + myhalf fragdepth = ZNear*ZFar/(ZFar - qf_texture(DepthTexture, tc).r*(ZFar-ZNear)); + myhalf partdepth = Depth; + + myhalf d = max((fragdepth - partdepth) * Scale, 0.0); + myhalf softness = 1.0 - min(1.0, d); + + softness *= softness; + softness = 1.0 - softness * softness; + return softness; } + +#endif + + +uniform sampler2D u_DepthTexture; + #endif + +void main(void) +{ + myhalf4 color; + +#ifdef NUM_LIGHTMAPS + color = myhalf4(0.0, 0.0, 0.0, qf_FrontColor.a); + color.rgb += myhalf3(qf_texture(u_LightmapTexture[0], v_LightmapTexCoord[0])) * u_LightstyleColor[0]; +#if NUM_LIGHTMAPS >= 2 + color.rgb += myhalf3(qf_texture(u_LightmapTexture[1], v_LightmapTexCoord[1])) * u_LightstyleColor[1]; +#if NUM_LIGHTMAPS >= 3 + color.rgb += myhalf3(qf_texture(u_LightmapTexture[2], v_LightmapTexCoord[2])) * u_LightstyleColor[2]; +#if NUM_LIGHTMAPS >= 4 + color.rgb += myhalf3(qf_texture(u_LightmapTexture[3], v_LightmapTexCoord[3])) * u_LightstyleColor[3]; +#endif // NUM_LIGHTMAPS >= 4 +#endif // NUM_LIGHTMAPS >= 3 +#endif // NUM_LIGHTMAPS >= 2 #else -color = color * myhalf4(gl_Color.rgba); + color = myhalf4(qf_FrontColor); +#endif // NUM_LIGHTMAPS + +#if defined(APPLY_FOG) && !defined(APPLY_FOG_COLOR) + myhalf fogDensity = FogDensity(v_FogCoord); #endif -#ifdef APPLY_GRAYSCALE -float grey = dot(color, myhalf3(0.299, 0.587, 0.114)); -gl_FragColor = vec4(vec3(grey),color.a); +#if defined(NUM_DLIGHTS) + color.rgb += DynamicLightsSummaryColor(v_Position); +#endif + + myhalf4 diffuse; + +#ifdef APPLY_CUBEMAP + diffuse = myhalf4(qf_textureCube(u_BaseTexture, v_TexCoord)); #else -gl_FragColor = vec4(color); + diffuse = myhalf4(qf_texture(u_BaseTexture, v_TexCoord)); #endif + +#ifdef APPLY_DRAWFLAT + myhalf n = myhalf(step(DRAWFLAT_NORMAL_STEP, abs(v_NormalZ))); + diffuse.rgb = myhalf3(mix(u_WallColor, u_FloorColor, n)); +#endif + + color *= diffuse; + +#ifdef NUM_LIGHTMAPS + // so that team-colored shaders work + color *= myhalf4(qf_FrontColor); +#endif + +#ifdef APPLY_GREYSCALE + color.rgb = Greyscale(color.rgb); +#endif + +#if defined(APPLY_FOG) && !defined(APPLY_FOG_COLOR) + color.rgb = mix(color.rgb, u_Fog.Color, fogDensity); +#endif + +#if defined(APPLY_SOFT_PARTICLE) + myhalf softness = FragmentSoftness(v_Depth, u_DepthTexture, gl_FragCoord.xy, u_Viewport, u_ZNear, u_ZFar, u_SoftParticlesScale); + color *= mix(myhalf4(1.0), myhalf4(softness), u_BlendMix.xxxy); +#endif + + qf_FragColor = vec4(color); } #endif // FRAGMENT_SHADER - |