/* Basic ambient lighting vertex program */ void ambientOneTexture_vp(float4 position : POSITION, float2 uv : TEXCOORD0, out float4 oPosition : POSITION, out float2 oUv : TEXCOORD0, out float4 colour : COLOR, uniform float4x4 worldViewProj, uniform float4 ambient) { oPosition = mul(worldViewProj, position); oUv = uv; colour = ambient; } /* Basic ambient lighting vertex program */ void ambientOneTexture2_vp(float4 position : POSITION, float2 uv : TEXCOORD1, out float4 oPosition : POSITION, out float2 oUv : TEXCOORD1, out float4 colour : COLOR, uniform float4x4 worldViewProj, uniform float4 ambient) { oPosition = mul(worldViewProj, position); oUv = uv; colour = ambient; } /* Basic ambient lighting vertex program */ void ambientTwoTexture_vp(float4 position : POSITION, float2 uv0 : TEXCOORD0, float2 uv1 : TEXCOORD1, out float4 oPosition : POSITION, out float2 oUv0 : TEXCOORD0, out float2 oUv1 : TEXCOORD1, out float4 colour : COLOR, uniform float4x4 worldViewProj, uniform float4 ambient) { oPosition = mul(worldViewProj, position); oUv0 = uv0; oUv1 = uv1; colour = ambient; } /* Single-weight-per-vertex hardware skinning, 2 lights The trouble with vertex programs is they're not general purpose, but fixed function hardware skinning is very poorly supported */ void hardwareSkinningOneWeight_vp( float4 position : POSITION, float3 normal : NORMAL, float2 uv : TEXCOORD0, float blendIdx : BLENDINDICES, out float4 oPosition : POSITION, out float2 oUv : TEXCOORD0, out float4 colour : COLOR, // Support up to 24 bones of float3x4 // vs_1_1 only supports 96 params so more than this is not feasible uniform float3x4 worldMatrix3x4Array[24], uniform float4x4 viewProjectionMatrix, uniform float4 lightPos[2], uniform float4 lightDiffuseColour[2], uniform float4 ambient) { // transform by indexed matrix float4 blendPos = float4(mul(worldMatrix3x4Array[blendIdx], position).xyz, 1.0); // view / projection oPosition = mul(viewProjectionMatrix, blendPos); // transform normal float3 norm = mul((float3x3)worldMatrix3x4Array[blendIdx], normal); // Lighting - support point and directional float3 lightDir0 = normalize( lightPos[0].xyz - (blendPos.xyz * lightPos[0].w)); float3 lightDir1 = normalize( lightPos[1].xyz - (blendPos.xyz * lightPos[1].w)); oUv = uv; colour = ambient + (saturate(dot(lightDir0, norm)) * lightDiffuseColour[0]) + (saturate(dot(lightDir1, norm)) * lightDiffuseColour[1]); } /* Single-weight-per-vertex hardware skinning, shadow-caster pass */ void hardwareSkinningOneWeightCaster_vp( float4 position : POSITION, float3 normal : NORMAL, float blendIdx : BLENDINDICES, out float4 oPosition : POSITION, out float4 colour : COLOR, // Support up to 24 bones of float3x4 // vs_1_1 only supports 96 params so more than this is not feasible uniform float3x4 worldMatrix3x4Array[24], uniform float4x4 viewProjectionMatrix, uniform float4 ambient) { // transform by indexed matrix float4 blendPos = float4(mul(worldMatrix3x4Array[blendIdx], position).xyz, 1.0); // view / projection oPosition = mul(viewProjectionMatrix, blendPos); colour = ambient; } /* Two-weight-per-vertex hardware skinning, 2 lights The trouble with vertex programs is they're not general purpose, but fixed function hardware skinning is very poorly supported */ void hardwareSkinningTwoWeights_vp( float4 position : POSITION, float3 normal : NORMAL, float2 uv : TEXCOORD0, float4 blendIdx : BLENDINDICES, float4 blendWgt : BLENDWEIGHT, out float4 oPosition : POSITION, out float2 oUv : TEXCOORD0, out float4 colour : COLOR, // Support up to 24 bones of float3x4 // vs_1_1 only supports 96 params so more than this is not feasible uniform float3x4 worldMatrix3x4Array[24], uniform float4x4 viewProjectionMatrix, uniform float4 lightPos[2], uniform float4 lightDiffuseColour[2], uniform float4 ambient) { // transform by indexed matrix float4 blendPos = float4(0,0,0,0); int i; for (i = 0; i < 2; ++i) { blendPos += float4(mul(worldMatrix3x4Array[blendIdx[i]], position).xyz, 1.0) * blendWgt[i]; } // view / projection oPosition = mul(viewProjectionMatrix, blendPos); // transform normal float3 norm = float3(0,0,0); for (i = 0; i < 2; ++i) { norm += mul((float3x3)worldMatrix3x4Array[blendIdx[i]], normal) * blendWgt[i]; } norm = normalize(norm); // Lighting - support point and directional float3 lightDir0 = normalize( lightPos[0].xyz - (blendPos.xyz * lightPos[0].w)); float3 lightDir1 = normalize( lightPos[1].xyz - (blendPos.xyz * lightPos[1].w)); oUv = uv; colour = float4(0.5, 0.5, 0.5, 1) + (saturate(dot(lightDir0, norm)) * lightDiffuseColour[0]) + (saturate(dot(lightDir1, norm)) * lightDiffuseColour[1]); } /* Two-weight-per-vertex hardware skinning, shadow caster pass */ void hardwareSkinningTwoWeightsCaster_vp( float4 position : POSITION, float3 normal : NORMAL, float2 uv : TEXCOORD0, float4 blendIdx : BLENDINDICES, float4 blendWgt : BLENDWEIGHT, out float4 oPosition : POSITION, out float4 colour : COLOR, // Support up to 24 bones of float3x4 // vs_1_1 only supports 96 params so more than this is not feasible uniform float3x4 worldMatrix3x4Array[24], uniform float4x4 viewProjectionMatrix, uniform float4 ambient) { // transform by indexed matrix float4 blendPos = float4(0,0,0,0); int i; for (i = 0; i < 2; ++i) { blendPos += float4(mul(worldMatrix3x4Array[blendIdx[i]], position).xyz, 1.0) * blendWgt[i]; } // view / projection oPosition = mul(viewProjectionMatrix, blendPos); colour = ambient; } /* Four-weight-per-vertex hardware skinning, 2 lights The trouble with vertex programs is they're not general purpose, but fixed function hardware skinning is very poorly supported */ void hardwareSkinningFourWeights_vp( float4 position : POSITION, float3 normal : NORMAL, float2 uv : TEXCOORD0, float4 blendIdx : BLENDINDICES, float4 blendWgt : BLENDWEIGHT, out float4 oPosition : POSITION, out float2 oUv : TEXCOORD0, out float4 colour : COLOR, // Support up to 24 bones of float3x4 // vs_1_1 only supports 96 params so more than this is not feasible uniform float3x4 worldMatrix3x4Array[24], uniform float4x4 viewProjectionMatrix, uniform float4 lightPos[2], uniform float4 lightDiffuseColour[2], uniform float4 ambient) { // transform by indexed matrix float4 blendPos = float4(0,0,0,0); int i; for (i = 0; i < 4; ++i) { blendPos += float4(mul(worldMatrix3x4Array[blendIdx[i]], position).xyz, 1.0) * blendWgt[i]; } // view / projection oPosition = mul(viewProjectionMatrix, blendPos); // transform normal float3 norm = float3(0,0,0); for (i = 0; i < 4; ++i) { norm += mul((float3x3)worldMatrix3x4Array[blendIdx[i]], normal) * blendWgt[i]; } norm = normalize(norm); // Lighting - support point and directional float3 lightDir0 = normalize( lightPos[0].xyz - (blendPos.xyz * lightPos[0].w)); float3 lightDir1 = normalize( lightPos[1].xyz - (blendPos.xyz * lightPos[1].w)); oUv = uv; colour = ambient + (saturate(dot(lightDir0, norm)) * lightDiffuseColour[0]) + (saturate(dot(lightDir1, norm)) * lightDiffuseColour[1]); } void hardwareMorphAnimation(float3 pos1 : POSITION, float4 normal : NORMAL, float2 uv : TEXCOORD0, float3 pos2 : TEXCOORD1, out float4 oPosition : POSITION, out float2 oUv : TEXCOORD0, out float4 colour : COLOR, uniform float4x4 worldViewProj, uniform float4 anim_t) { // interpolate float4 interp = float4(pos1 + anim_t.x*(pos2 - pos1), 1.0f); oPosition = mul(worldViewProj, interp); oUv = uv; colour = float4(1,0,0,1); } void hardwarePoseAnimation(float3 pos : POSITION, float4 normal : NORMAL, float2 uv : TEXCOORD0, float3 pose1 : TEXCOORD1, float3 pose2 : TEXCOORD2, out float4 oPosition : POSITION, out float2 oUv : TEXCOORD0, out float4 colour : COLOR, uniform float4x4 worldViewProj, uniform float4 anim_t) { // interpolate float4 interp = float4(pos + anim_t.x*pose1 + anim_t.y*pose2, 1.0f); oPosition = mul(worldViewProj, interp); oUv = uv; colour = float4(1,0,0,1); } void basicPassthroughTangent_v(float4 position : POSITION, float3 tangent : TANGENT, out float4 oPosition : POSITION, out float3 oTangent : TEXCOORD0, uniform float4x4 worldViewProj) { oPosition = mul(worldViewProj, position); oTangent = tangent; } void basicPassthroughNormal_v(float4 position : POSITION, float3 normal : NORMAL, out float4 oPosition : POSITION, out float3 oNormal : TEXCOORD0, uniform float4x4 worldViewProj) { oPosition = mul(worldViewProj, position); oNormal = normal; } // Basic fragment program to display UV float4 showuv_p (float2 uv : TEXCOORD0) : COLOR { // wrap values using frac return float4(frac(uv.x), frac(uv.y), 0, 1); } // Basic fragment program to display 3d uv float4 showuvdir3d_p (float3 uv : TEXCOORD0) : COLOR { float3 n = normalize(uv); return float4(n.x, n.y, n.z, 1); } void Ambient_vp(float4 position : POSITION, out float4 oPosition : POSITION, out float4 colour : COLOR, uniform float4x4 worldViewProj, uniform float4 ambient) { oPosition = mul(worldViewProj, position); colour = ambient; } void PerVertex_Vert ( float4 position : POSITION, float3 normal : NORMAL, uniform float4 lightPosition, uniform float3 eyePosition, uniform float4x4 worldviewproj, uniform float4 lightDiffuse, uniform float4 lightSpecular, uniform float exponent, out float4 oColor : COLOR, out float4 oPos : POSITION ) { oPos = mul(worldviewproj, position); float3 EyeDir = normalize(eyePosition - position.xyz); float3 LightDir = normalize(lightPosition.xyz - (position.xyz * lightPosition.w)); float3 HalfAngle = normalize(LightDir + EyeDir); float3 N = normalize(normal); float NdotL = dot(N, LightDir); float NdotH = dot(N, HalfAngle); float4 Lit = lit(NdotL,NdotH,exponent); oColor = lightDiffuse * Lit.y + lightSpecular * Lit.z; } //**************************************************************************************// // // // PERPIXEL LIGHTING // // A + D + S // // // //**************************************************************************************// void Simple_Perpixel_Vert( float4 position : POSITION, float3 normal : NORMAL, uniform float4 lightPosition0, // uniform float4 lightPosition1, // uniform float4 lightPosition2, uniform float4x4 worldviewproj, // uniform float3 eyePosition, out float4 oClipPos : POSITION, out float3 oNorm : TEXCOORD0, out float4 oLightPos0 : TEXCOORD1, // out float4 oLightPos1 : TEXCOORD2, // out float4 oLightPos2 : TEXCOORD3, out float4 oPos : TEXCOORD4, out float3 EyeDir : TEXCOORD5 ) { oClipPos = mul(worldviewproj, position); oLightPos0 = lightPosition0; // oLightPos1 = lightPosition1; // oLightPos2 = lightPosition2; oPos = position; oNorm = normal; } void Simple_PerPixel_Frag( float3 normal : TEXCOORD0, float4 LightPos0 : TEXCOORD1, // float4 LightPos1 : TEXCOORD2, // float4 LightPos2 : TEXCOORD3, float4 position : TEXCOORD4, uniform float3 eyePosition, uniform float4 lightDiffuse0, // uniform float4 lightDiffuse1, // uniform float4 lightDiffuse2, uniform float4 lightSpecular0, // uniform float4 lightSpecular1, // uniform float4 lightSpecular2, uniform float exponent0, // uniform float exponent1, // uniform float exponent2, uniform float4 ambient, out float4 oColor : COLOR ) { //could I do this, or whole halfangle calculus in vertex shader? float3 N = normalize(normal); float3 EyeDir = normalize(eyePosition - position.xyz); float3 LightDir = normalize(LightPos0.xyz - (position * LightPos0.w)); float3 HalfAngle = normalize(LightDir + EyeDir); float NdotL = dot(LightDir, N); float NdotH = dot(HalfAngle, N); float4 Lit = lit(NdotL,NdotH,exponent0); oColor = lightDiffuse0 * Lit.y + lightSpecular0 * Lit.z + ambient; // LightDir = normalize(LightPos1.xyz - (position * LightPos1.w)); // HalfAngle = normalize(LightDir + EyeDir); // NdotL = dot(LightDir, N); // NdotH = dot(HalfAngle, N); // Lit = lit(NdotL,NdotH,exponent0); // oColor += lightDiffuse1 * Lit.y + lightSpecular1 * Lit.z; // LightDir = normalize(LightPos2.xyz - (position * LightPos2.w)); // HalfAngle = normalize(LightDir + EyeDir); // NdotL = dot(LightDir, N); // NdotH = dot(HalfAngle, N); // Lit = lit(NdotL,NdotH,exponent0); // oColor += lightDiffuse2 * Lit.y + lightSpecular2 * Lit.z + ambient; //do I need to normalize here the normal? } void PerPixel_Vert ( float4 position : POSITION, float3 normal : NORMAL, uniform float4 lightPosition, uniform float3 eyePosition, uniform float4x4 worldviewproj, out float4 oPos : POSITION, out float3 oNorm: TEXCOORD0, out float3 oLightDir: TEXCOORD1, out float3 oHalfAngle: TEXCOORD2 ) { oPos = mul(worldviewproj, position); float3 EyeDir = normalize(eyePosition - position.xyz); oLightDir = normalize(lightPosition.xyz - (position.xyz * lightPosition.w)); oHalfAngle = normalize(oLightDir + EyeDir); oNorm = normal; //what if I leave normalization of normal, and oHalfAngle to Fragshader? } void PerPixel_Frag ( float3 normal: TEXCOORD0, float3 LightDir : TEXCOORD1, float3 HalfAngle : TEXCOORD2, uniform float4 lightDiffuse, uniform float4 lightSpecular, uniform float exponent, out float4 oColor : COLOR ) { float3 N = normalize(normal); float NdotL = dot(normalize(LightDir), N); float NdotH = dot(normalize(HalfAngle), N); float4 Lit = lit(NdotL,NdotH,exponent); oColor = lightDiffuse * Lit.y + lightSpecular * Lit.z; //do I need to normalize here the normal? // oColor = float4(normal,1); } void PerPixel_Lim3_Vert(float4 position : POSITION, float3 normal : NORMAL, uniform float4 lightPosition0, uniform float4 lightPosition1, uniform float4 lightPosition2, uniform float3 eyePosition, uniform float4x4 worldviewproj, out float4 oPos : POSITION, out float3 oNorm: TEXCOORD0, out float3 oLightDir0: TEXCOORD1, out float3 oLightDir1: TEXCOORD2, out float3 oLightDir2: TEXCOORD3, out float3 oHalfAngle0: TEXCOORD4, out float3 oHalfAngle1: TEXCOORD5, out float3 oHalfAngle2: TEXCOORD6 ) { oPos = mul(worldviewproj, position); oLightDir0 = normalize(lightPosition0.xyz - (position * lightPosition0.w)); oLightDir1 = normalize(lightPosition1.xyz - (position * lightPosition1.w)); oLightDir2 = normalize(lightPosition2.xyz - (position * lightPosition2.w)); float3 EyeDir = normalize(eyePosition - position.xyz); oHalfAngle0 = normalize(oLightDir0 + EyeDir); oHalfAngle1 = normalize(oLightDir1 + EyeDir); oHalfAngle2 = normalize(oLightDir2 + EyeDir); oNorm = normal; //what if I leave normalization of normal and oHalfAngle to Fragshader? } void PerPixel_Lim3_Frag(float3 normal: TEXCOORD0, float3 LightDir0 : TEXCOORD1, float3 LightDir1 : TEXCOORD2, float3 LightDir2 : TEXCOORD3, float3 HalfAngle0: TEXCOORD4, float3 HalfAngle1: TEXCOORD5, float3 HalfAngle2: TEXCOORD6, uniform float4 lightDiffuse0, uniform float4 lightDiffuse1, uniform float4 lightDiffuse2, uniform float4 lightSpecular0, uniform float4 lightSpecular1, uniform float4 lightSpecular2, uniform float exponent0, // uniform float exponent1, // uniform float exponent2, uniform float4 ambient, out float4 oColor : COLOR ) { float3 N = normalize(normal); float NdotL = dot(normalize(LightDir0), N); float NdotH = dot(normalize(HalfAngle0), N); float4 Lit = lit(NdotL,NdotH,exponent0); oColor = lightDiffuse0 * Lit.y + lightSpecular0 * Lit.z; NdotL = dot(normalize(LightDir1), N); NdotH = dot(normalize(HalfAngle1), N); Lit = lit(NdotL,NdotH,exponent0); oColor += lightDiffuse1 * Lit.y + lightSpecular1 * Lit.z; NdotL = dot(normalize(LightDir2), N); NdotH = dot(normalize(HalfAngle2), N); Lit = lit(NdotL,NdotH,exponent0); oColor += lightDiffuse2 * Lit.y + lightSpecular2 * Lit.z + ambient; //do I need to normalize here the normal? }