Bomberman-OverlordEngine-x64 / BombermanGame / Resources / Effects / Shadow / ShadowMapGenerator.fx
ShadowMapGenerator.fx
Raw
float4x4 gWorld;
float4x4 gLightViewProj;
float4x4 gBones[70];

Texture2D gOpacityMap;
bool gUseOpacity;
 
DepthStencilState depthStencilState
{
	DepthEnable = TRUE;
	DepthWriteMask = ALL;
};

RasterizerState rasterizerState
{
	FillMode = SOLID;
	CullMode = NONE;
};

struct VS_OUTPUT_OPACITY
{
    float4 pos : SV_POSITION;
    float2 texCoord : TEXCOORD;
};

SamplerState gOpacitySamplerLinear
{
    Filter = MIN_MAG_MIP_LINEAR;
    AddressU = Wrap; // or Mirror or Clamp or Border
    AddressV = Wrap; // or Mirror or Clamp or Border
};

//--------------------------------------------------------------------------------------
// Vertex Shader [STATIC]
//--------------------------------------------------------------------------------------
float4 ShadowMapVS(float3 position:POSITION) : SV_POSITION
{
	//TODO: return the position of the vertex in correct space (hint: seen from the view of the light)
    return mul(float4(position, 1.0), mul(gWorld, gLightViewProj));
}

//--------------------------------------------------------------------------------------
// Vertex Shader [STATIC OPACITY]
//--------------------------------------------------------------------------------------
VS_OUTPUT_OPACITY ShadowMapVS_Opacity(float3 position : POSITION, float2 texCoords : TEXCOORD0)
{
    VS_OUTPUT_OPACITY output = (VS_OUTPUT_OPACITY) 0;
    
    // Transform the transformedPosition to Clipping Space (WVP Matrix)
    output.pos = mul(float4(position, 1.0), mul(gWorld, gLightViewProj));
    
    // Save texcoord for pixel shader
    output.texCoord = texCoords;
    
    return output;
}

//--------------------------------------------------------------------------------------
// Vertex Shader [SKINNED]
//--------------------------------------------------------------------------------------
float4 ShadowMapVS_Skinned(float3 position:POSITION, float4 BoneIndices : BLENDINDICES, float4 BoneWeights : BLENDWEIGHTS) : SV_POSITION
{
	//TODO: return the position of the ANIMATED vertex in correct space (hint: seen from the view of the light)
    float4 transformedPosition = float4(0, 0, 0, 0);

	// For each bone
    for (int i = 0; i < 4; ++i)
    {
        if (BoneIndices[i] >= 0)
        {
            int boneIndex = BoneIndices[i];
            float boneWeight = BoneWeights[i];

			// Calculate BoneSpace Position & Normal
            float4 boneSpacePos = mul(float4(position, 1.0f), gBones[boneIndex]);

			// Append this Position & Normal to the transformedPosition & transformedNormal
            transformedPosition += boneSpacePos * boneWeight;
        }
    }

	// Ensure that the w-component of the transformedPosition is 1
    transformedPosition.w = 1.0f;

	// Step 1:	Transform the transformedPosition to Clipping Space (WVP Matrix)
    return mul(transformedPosition, mul(gWorld, gLightViewProj));
}

//--------------------------------------------------------------------------------------
// Vertex Shader [SKINNED OPACITY]
//--------------------------------------------------------------------------------------
VS_OUTPUT_OPACITY ShadowMapVS_Skinned_Opacity(float3 position : POSITION, float2 texCoords : TEXCOORD0, float4 BoneIndices : BLENDINDICES, float4 BoneWeights : BLENDWEIGHTS)
{
    VS_OUTPUT_OPACITY output = (VS_OUTPUT_OPACITY) 0;
   
    float4 transformedPosition = float4(0, 0, 0, 0);

	// For each bone
    for (int i = 0; i < 4; ++i)
    {
        if (BoneIndices[i] >= 0)
        {
            int boneIndex = BoneIndices[i];
            float boneWeight = BoneWeights[i];

			// Calculate BoneSpace Position & Normal
            float4 boneSpacePos = mul(float4(position, 1.0f), gBones[boneIndex]);

			// Append this Position & Normal to the transformedPosition & transformedNormal
            transformedPosition += boneSpacePos * boneWeight;
        }
    }

	// Ensure that the w-component of the transformedPosition is 1
    transformedPosition.w = 1.0f;
    
    // Transform the transformedPosition to Clipping Space (WVP Matrix)
    output.pos = mul(transformedPosition, mul(gWorld, gLightViewProj));
    
    // Save texcoord for pixel shader
    output.texCoord = texCoords;
    
    return output;
}
 
//--------------------------------------------------------------------------------------
// Pixel Shaders
//--------------------------------------------------------------------------------------
void ShadowMapPS_VOID(float4 position:SV_POSITION){}

void ShadowMapPS_Opacity(VS_OUTPUT_OPACITY input)
{
    if (!gUseOpacity)
        return;
    
    float opacityValue = gOpacityMap.Sample(gOpacitySamplerLinear, input.texCoord).r;
    if (opacityValue < 0.5f)
        discard;
}

technique11 GenerateShadows
{
	pass P0
	{
		SetRasterizerState(rasterizerState);
	    SetDepthStencilState(depthStencilState, 0);
		//SetVertexShader(CompileShader(vs_4_0, ShadowMapVS()));
        SetVertexShader(CompileShader(vs_4_0, ShadowMapVS_Opacity()));
		SetGeometryShader(NULL);
		//SetPixelShader(CompileShader(ps_4_0, ShadowMapPS_VOID()));
        SetPixelShader(CompileShader(ps_4_0, ShadowMapPS_Opacity()));
    }
}

technique11 GenerateShadows_Skinned
{
	pass P0
	{
		SetRasterizerState(rasterizerState);
		SetDepthStencilState(depthStencilState, 0);
		//SetVertexShader(CompileShader(vs_4_0, ShadowMapVS_Skinned()));
        SetVertexShader(CompileShader(vs_4_0, ShadowMapVS_Skinned_Opacity()));
		SetGeometryShader(NULL);
		//SetPixelShader(CompileShader(ps_4_0, ShadowMapPS_VOID()));
        SetPixelShader(CompileShader(ps_4_0, ShadowMapPS_Opacity()));
    }
}