Right,
I seem to have gotten over the issue above by swapping my cube for one that came with the FX Composer, I think the cube I am creating is not going down to well, have never created one before so I have no way of knowing what I am doing wrong.
But this has moved me on to another issue....
My glass.fx shader does not seem to be behaving at all, all I get is the black mask of the mesh with no effect on it at all.
Could one of you guys be so kind as to have a look at the shader and my code and tell me where I am going wrong?
First up, the shader:
float Script : STANDARDSGLOBAL <
string UIWidget = "none";
string ScriptClass = "object";
string ScriptOrder = "standard";
string ScriptOutput = "color";
string Script = "Technique=dx9;";
> = 0.8;
/************* TWEAKABLES **************/
float4x4 worldIT : WorldInverseTranspose;
float4x4 wvp : WorldViewProjection;
float4x4 world : World;
float4x4 viewI : ViewInverse;
float reflectStrength
<
string UIWidget = "slider";
float UIMin = 0.0;
float UIMax = 2.0;
float UIStep = 0.01;
string UIName = "Reflection";
> = 1.0;
float refractStrength
<
string UIWidget = "slider";
float UIMin = 0.0;
float UIMax = 2.0;
float UIStep = 0.01;
string UIName = "Refraction";
> = 1.0;
half3 etas
<
string UIName = "Refraction indices";
> = { 0.80, 0.82, 0.84 };
texture cubeMap : Environment
<
string ResourceName = "default_reflection.dds";
string ResourceType = "Cube";
>;
texture fresnelTex : Environment
<
string ResourceType = "2D";
string function = "generateFresnelTex";
float2 Dimensions = { 256.0f, 1.0f};
>;
samplerCUBE environmentMapSampler = sampler_state
{
Texture = <cubeMap>;
MinFilter = Linear;
MagFilter = Linear;
MipFilter = Linear;
};
sampler2D fresnelSampler = sampler_state
{
Texture = <fresnelTex>;
MinFilter = Linear;
MagFilter = Linear;
MipFilter = None;
};
/************* DATA STRUCTS **************/
/* data from application vertex buffer */
struct appdata {
float4 Position : POSITION;
float4 UV : TEXCOORD0;
float3 Normal : NORMAL;
};
/* data passed from vertex shader to pixel shader */
struct vertexOutput {
float4 HPosition : POSITION;
float4 TexCoord : TEXCOORD0;
float3 WorldNormal : TEXCOORD1;
float3 WorldView : TEXCOORD2;
};
/*********** vertex shader ******/
vertexOutput mainVS(appdata IN,
uniform float4x4 WorldViewProj,
uniform float4x4 WorldIT,
uniform float4x4 World,
uniform float4x4 viewI
) {
vertexOutput OUT;
float3 normal = normalize(IN.Normal);
OUT.WorldNormal = mul(normal, (float3x3) WorldIT);
float3 Pw = mul(IN.Position, World).xyz;
OUT.TexCoord = IN.UV;
OUT.WorldView = viewI[3].xyz - Pw;
OUT.HPosition = mul(IN.Position, WorldViewProj);
return OUT;
}
/********* pixel shader ********/
// modified refraction function that returns boolean for total internal reflection
float3
refract2( float3 I, float3 N, float eta, out bool fail )
{
float IdotN = dot(I, N);
float k = 1 - eta*eta*(1 - IdotN*IdotN);
// return k < 0 ? (0,0,0) : eta*I - (eta*IdotN + sqrt(k))*N;
fail = k < 0;
return eta*I - (eta*IdotN + sqrt(k))*N;
}
// approximate Fresnel function
float fresnel(float NdotV, float bias, float power)
{
return bias + (1.0-bias)*pow(1.0 - max(NdotV, 0), power);
}
// function to generate a texture encoding the Fresnel function
float4 generateFresnelTex(float NdotV : POSITION) : COLOR
{
return fresnel(NdotV, 0.2, 4.0);
}
float4 mainPS(vertexOutput IN,
uniform samplerCUBE EnvironmentMap,
uniform half reflectStrength,
uniform half refractStrength,
uniform half3 etas
) : COLOR
{
half3 N = normalize(IN.WorldNormal);
float3 V = normalize(IN.WorldView);
// reflection
half3 R = reflect(-V, N);
half4 reflColor = texCUBE(EnvironmentMap, R);
// half fresnel = fresnel(dot(N, V), 0.2, 4.0);
half fresnel = tex2D(fresnelSampler, dot(N, V));
// wavelength colors
const half4 colors[3] = {
{ 1, 0, 0, 0 },
{ 0, 1, 0, 0 },
{ 0, 0, 1, 0 },
};
// transmission
half4 transColor = 0;
bool fail = false;
for(int i=0; i<3; i++) {
half3 T = refract2(-V, N, etas[i], fail);
transColor += texCUBE(EnvironmentMap, T) * colors[i];
}
return lerp(transColor*refractStrength, reflColor*reflectStrength, fresnel);
}
/*************/
technique dx9 <
string Script = "Pass=p0;";
> {
pass p0 <
string Script = "Draw=geometry;";
> {
VertexShader = compile vs_2_0 mainVS(wvp,worldIT,world,viewI);
PixelShader = compile ps_2_0 mainPS(environmentMapSampler,reflectStrength, refractStrength,etas);
}
}
/***************************** eof ***/
As before with my bloom.fx shader I have simply taken the one from the nVidia FX Composer.
Here are my calls:-
In LoadGraphicsContent of the shader I am loading the cube and fresnel, I dont think I have ot but it behaves the same even if I dont:
myCube = myLoader.Load<TextureCube>("Content/Textures/SkyBox/HazyMind/default_reflection");
myFresnel = myLoader.Load<Texture2D>("Content/Textures/SkyBox/HazyMind/fresnel");
In SetParameters of the shader:
if (myEffect.Parameters["worldIT"] != null)
myEffect.Parameters["worldIT"].SetValue(Matrix.Transpose(Matrix.Invert(World)));
if (myEffect.Parameters["wvp"] != null)
myEffect.Parameters["wvp"].SetValue(World * RCCameraManager.ActiveCamera.View * RCCameraManager.ActiveCamera.Projection);
if (myEffect.Parameters["world"] != null)
myEffect.Parameters["world"].SetValue(World);
if (myEffect.Parameters["viewI"] != null)
myEffect.Parameters["viewI"].SetValue(Matrix.Invert(RCCameraManager.ActiveCamera.View));
if (myEffect.Parameters["cubeMap"] != null)
myEffect.Parameters["cubeMap"].SetValue(myCube);
if (myEffect.Parameters["fresnelTex"] != null)
myEffect.Parameters["fresnelTex"].SetValue(myFresnel);
if (myEffect.Parameters["reflectStrength"] != null)
myEffect.Parameters["reflectStrength"].SetValue(1.0f);
if (myEffect.Parameters["refractStrength"] != null)
myEffect.Parameters["refractStrength"].SetValue(1.0f);
if (myEffect.Parameters["etas"] != null)
myEffect.Parameters["etas"].SetValue(new Vector3(0.80f, 0.82f, 0.84f));
Thanks in advance for putting up with my noob obsession with shaders
