Depth shadow mapping question

Started by
35 comments, last by DividedByZero 5 years, 2 months ago
13 hours ago, DividedByZero said:

Following along the RasterTek tutorial, my shaders are now the same as what are in the tutorial. I also found that my texture formats for the depth buffer creation were wrong. (I was using R8G8B8A8 and have now expanded these to R32G32B32A32 etc...)

 

I'm not a directx developer, but these formats look very weird and very eager to store depth information.

Advertisement

As PCMaster mentioned on the 1st page, for depth buffers (such as your shadow texture) you should be using R32, not R32B32G32A32

Depth doesnt need the green,blue.alpha components. It needs to be able to store one 32 bit float.

I have changed to formats to the ones that PCMaster first mentioned. The results are still identical to the last image I posted.

The changes to the formats came about from following tutorials that other members posted. In those, the preferred formats were the last ones I mentioned.

I have created a third program from scratch today, adding plenty of output to the console window.

Scene renders fine but still no shadows.

This is what my output looks like, in case I am missing some very silly step.

Quote

Create window - ok
Create device and swapchain - ok
Create back buffer RTV - ok
Create back buffer DSV - ok
Create Input Layout (P3D, N, T) - ok
Texture load from file - ok
Create default blend state - ok
Create raster state (cull backface) - ok
Vertex buffer create - ok
Shader create (vs depth map) - ok
Shader create (ps depth map) - ok
Shader create (vs shadow) - ok
Shader create (ps shadow) - ok
Constant buffer create camera (6x DirectX::XMMATRIX) - ok
Constant buffer create light (4x float) - ok
Create shadow map RTV and SRV (R32G32B32A32_FLOAT) - ok
Create shadow map DSV and SRV (R32_TYPELESS / DXGI_FORMAT_R32_FLOAT) - ok
Sampler state create 'Clamp'
Sampler state create 'Wrap'

*** Main loop ***

BEGIN
STATE: Raster state cull back faces

TARGET: Shadow map RTV and DSV
CLEAR: Shadow map RTV cleared (0,0,0,1)
CLEAR: Shadow map DSV cleared (1,0)
VIEWPORT: Viewport set - 1024, 1024
SCISSORS: Scissors rect set - 1024, 1024
SHADER: Set VS depth map
SHADER: Set PS depth map
SUBMIT (CB0): CAMERA (Ortho): Pos(0, 4, -4) Look(0, 0, 0) FovY (60) Aspect (1) Near/Far (1, 10)

DRAW: Draw model 4 trianges

TARGET: Back buffer
CLEAR: Back buffer RTV clear (0, 0, 0)
CLEAR: Back buffer DSV clear (1,0)
SHADER: Set VS shadow
SHADER: Set PS shadow
SUBMIT (CB0): CAMERA (Persp): Pos(2, 2, -3) Look(0, 0.5, 0) FovY (60) Aspect (1.77778) Near/Far (1, 10)
              LIGHT (Ortho): Pos(0, 4, -4) Look(0, 0, 0) Near/Far (1, 10)
SUBMIT (CB1): Light position (0, 4, -4
TEXTURE: Scene texture PSSET slot 0
TEXTURE: d3dShadowMapSRV PSSET slot 1
VIEWPORT: Viewport set - 1280, 720
SCISSORS: Scissors rect set - 1280, 720
SAMPLER S0: Clamp
SAMPLER S1: Wrap

DRAW: Draw model 4 trianges

PRESENT: Present back buffer
RESET: Reset shader resources

I have been pedantic about sorting out any DX debug warnings and making sure everything releases correctly on exit.

The debugger says that every single line of DX is behaving nicely.

And the depth map looks ok to me (as far as my untrained eyes can tell)

OhZBIhg.png

This is killing me, man...

I'll try to download your code at home, run and see what happens. That'll be in some 10 hours. If anyone is faster, give it a try, @DividedByZero posted a dropbox link somewhere above.

In the meantime, I'd check the matrix which is used to transform positions into light-space (shadow-map-space) when applying the shadow.

Hi @pcmaster that would be awesome.

It does seem matrix related to me somewhere along the line. But I have been over and over and not seeing it.

This is the current project file as of today.

https://www.dropbox.com/s/pgblx3448qoi2b7/DX11ShadowMapping.zip?dl=0

It is basically just in plain function form (no classes etc...) until I iron out what is wrong. DX debug isn't reporting any issues and there are no leaks. So code-wise it is pretty solid.

Dude, I'm looking into it...

A bare-bones example should work like this:

  1. Draw the scene from light perspective into a shadow-map depth render target - with no colour render target connected, no pixel shader
  2. Draw the scene from camera perspective into the main colour render target + main depth target
  3. ...and for each pixel, project it into the shadow-map space, fetch from the shadow-map and output colorLight for lit pixels and colorDark for shadowed pixels

Your shadow-map depth SRV still doesn't come from the same texture as the shadow-map texture, but the RTV. Okay, for now it should work as your shadow-map RTV and DSV contain the same data. So the textures are kind-of fine.

I don't like your matrices. Why the transpose? I think the problem's there.  I EDIT: DX is left-handed and the transpose there's most probably because of the default column_major matrix layout. It should be fine. I see you copied it from http://www.rastertek.com/dx11tut40.html

Other than that, it should work, but I'm done debugging it for now, I'm too tired (it's almost 1 AM here). Good luck.

Hi @pcmaster, thanks for taking a look. That is huge of you and above and beyond.

Hard to know where to go from here as it seems like I am doing everything needed in order for it to work.

I'll have another look with fresh eyes today.

Thanks again, it it hugely appreciated.

In the meantime I have revised the shadow map DSV and SRV side of things.


int ShadowMapCreate2(int width, int height)
{
	// Creating a render target so we can render the scene to this and use as a texture
	D3D11_TEXTURE2D_DESC textureDesc;
	ZeroMemory(&textureDesc, sizeof(textureDesc));
	textureDesc.Width = width;
	textureDesc.Height = height;
	textureDesc.MipLevels = 1;
	textureDesc.ArraySize = 1;
	textureDesc.Format = DXGI_FORMAT_R24G8_TYPELESS;
	textureDesc.SampleDesc.Count = 1;
	textureDesc.SampleDesc.Quality = 0;
	textureDesc.Usage = D3D11_USAGE_DEFAULT;
	textureDesc.BindFlags = D3D11_BIND_DEPTH_STENCIL | D3D11_BIND_SHADER_RESOURCE;
	textureDesc.CPUAccessFlags = 0;
	textureDesc.MiscFlags = 0;
	
	ID3D11Texture2D* renderTexture = NULL;
	HRESULT result = d3dDevice->CreateTexture2D(&textureDesc, NULL, &renderTexture);
	if (FAILED(result)) return 1;

	D3D11_DEPTH_STENCIL_VIEW_DESC descDSV;
	descDSV.Format = DXGI_FORMAT_D24_UNORM_S8_UINT;
	descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
	descDSV.Texture2D.MipSlice = 0;
	descDSV.Flags = 0;

	if (FAILED(d3dDevice->CreateDepthStencilView(renderTexture, &descDSV, &d3dShadowMapDSV)))
		return 2;

	D3D11_SHADER_RESOURCE_VIEW_DESC descSRV;
	descSRV.Format = DXGI_FORMAT_R24_UNORM_X8_TYPELESS;
	descSRV.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
	descSRV.Texture2D.MostDetailedMip = 0;
	descSRV.Texture2D.MipLevels = -1;

	result = d3dDevice->CreateShaderResourceView(renderTexture, &descSRV, &d3dShadowMapSRV);
	if (FAILED(result)) return 3;

	renderTexture->Release();

	return 0;
}

In doing so, I have gotten rid of the un-needed RTV. And am using a NULL pixel shader, during the depth map creation draw.


d3dContext->PSSetShader(NULL, NULL, 0);

 

As of yet it still hasn't changed the outcome. But I am hopefully getting closer each day.

 

@blicilidid confuse me with this though...


float4 shadowMapPixelShader(shadowPSInput_s input) : SV_TARGET
{
	float z = input.position.z;
	return float4(z, z, z, 1);
}

...which made me think that the initial pass did need a pixel shader to process the map somewhere. Although the RasterTek tutorial says to do the same thing, which leaves me in a confused state about this I guess.

So is this step not required? Am I right in trying to sample direct from the depth buffers SRV (d3dShadowMapSRV as was created in the above snippet)?

This topic is closed to new replies.

Advertisement