Răsfoiți Sursa

Fixed framebuffer clear.

Branimir Karadžić 10 ani în urmă
părinte
comite
e5db297ba8
6 a modificat fișierele cu 102 adăugiri și 24 ștergeri
  1. 56 12
      src/renderer_d3d11.cpp
  2. 12 8
      src/renderer_d3d11.h
  3. 24 2
      src/renderer_d3d12.cpp
  4. 4 0
      src/renderer_d3d12.h
  5. 5 1
      src/shader_dxbc.cpp
  6. 1 1
      src/shader_dxbc.h

+ 56 - 12
src/renderer_d3d11.cpp

@@ -2966,8 +2966,20 @@ BX_PRAGMA_DIAGNOSTIC_POP();
 
 
 		void clearQuad(ClearQuad& _clearQuad, const Rect& _rect, const Clear& _clear, const float _palette[][4])
 		void clearQuad(ClearQuad& _clearQuad, const Rect& _rect, const Clear& _clear, const float _palette[][4])
 		{
 		{
-			uint32_t width  = getBufferWidth();
-			uint32_t height = getBufferHeight();
+			uint32_t width;
+			uint32_t height;
+
+			if (isValid(m_fbh) )
+			{
+				const FrameBufferD3D11& fb = m_frameBuffers[m_fbh.idx];
+				width  = fb.m_width;
+				height = fb.m_height;
+			}
+			else
+			{
+				width  = getBufferWidth();
+				height = getBufferHeight();
+			}
 
 
 			if (0      == _rect.m_x
 			if (0      == _rect.m_x
 			&&  0      == _rect.m_y
 			&&  0      == _rect.m_y
@@ -3443,35 +3455,38 @@ BX_PRAGMA_DIAGNOSTIC_POP();
 		BufferD3D11::create(_size, _data, _flags, stride, true);
 		BufferD3D11::create(_size, _data, _flags, stride, true);
 	}
 	}
 
 
-	static bool hasDiscard(const void* _code, uint32_t _size)
+	static bool hasDepthOp(const void* _code, uint32_t _size)
 	{
 	{
 		bx::MemoryReader rd(_code, _size);
 		bx::MemoryReader rd(_code, _size);
 
 
 		DxbcContext dxbc;
 		DxbcContext dxbc;
 		read(&rd, dxbc);
 		read(&rd, dxbc);
 
 
-		struct FindDiscard
+		struct FindDepthOp
 		{
 		{
-			FindDiscard()
+			FindDepthOp()
 				: m_found(false)
 				: m_found(false)
 			{
 			{
 			}
 			}
 
 
-			static void find(uint32_t /*_offset*/, const DxbcInstruction& _instruction, void* _userData)
+			static bool find(uint32_t /*_offset*/, const DxbcInstruction& _instruction, void* _userData)
 			{
 			{
-				FindDiscard& out = *reinterpret_cast<FindDiscard*>(_userData);
-				if (_instruction.opcode == DxbcOpcode::DISCARD)
+				FindDepthOp& out = *reinterpret_cast<FindDepthOp*>(_userData);
+				if (_instruction.opcode == DxbcOpcode::DISCARD
+				|| (0 != _instruction.numOperands &&  DxbcOperandType::OutputDepth == _instruction.operand[0].type) )
 				{
 				{
 					out.m_found = true;
 					out.m_found = true;
-					return;
+					return false;
 				}
 				}
+
+				return true;
 			}
 			}
 
 
 			bool m_found;
 			bool m_found;
 
 
 		} find;
 		} find;
 
 
-		parse(dxbc.shader, FindDiscard::find, &find);
+		parse(dxbc.shader, FindDepthOp::find, &find);
 
 
 		return find.m_found;
 		return find.m_found;
 	}
 	}
@@ -3592,7 +3607,7 @@ BX_PRAGMA_DIAGNOSTIC_POP();
 
 
 		if (BGFX_CHUNK_MAGIC_FSH == magic)
 		if (BGFX_CHUNK_MAGIC_FSH == magic)
 		{
 		{
-			m_hasDiscard = hasDiscard(code, shaderSize);
+			m_hasDepthOp = hasDepthOp(code, shaderSize);
 			DX_CHECK(s_renderD3D11->m_device->CreatePixelShader(code, shaderSize, NULL, &m_pixelShader) );
 			DX_CHECK(s_renderD3D11->m_device->CreatePixelShader(code, shaderSize, NULL, &m_pixelShader) );
 			BGFX_FATAL(NULL != m_ptr, bgfx::Fatal::InvalidShader, "Failed to create fragment shader.");
 			BGFX_FATAL(NULL != m_ptr, bgfx::Fatal::InvalidShader, "Failed to create fragment shader.");
 		}
 		}
@@ -4052,6 +4067,9 @@ BX_PRAGMA_DIAGNOSTIC_POP();
 
 
 	void FrameBufferD3D11::postReset()
 	void FrameBufferD3D11::postReset()
 	{
 	{
+		m_width  = 0;
+		m_height = 0;
+
 		if (0 < m_numTh)
 		if (0 < m_numTh)
 		{
 		{
 			m_num = 0;
 			m_num = 0;
@@ -4061,6 +4079,32 @@ BX_PRAGMA_DIAGNOSTIC_POP();
 				if (isValid(handle) )
 				if (isValid(handle) )
 				{
 				{
 					const TextureD3D11& texture = s_renderD3D11->m_textures[handle.idx];
 					const TextureD3D11& texture = s_renderD3D11->m_textures[handle.idx];
+
+					if (0 == m_width)
+					{
+						switch (texture.m_type)
+						{
+						case TextureD3D11::Texture2D:
+						case TextureD3D11::TextureCube:
+							{
+								D3D11_TEXTURE2D_DESC desc;
+								texture.m_texture2d->GetDesc(&desc);
+								m_width  = desc.Width;
+								m_height = desc.Height;
+							}
+							break;
+
+						case TextureD3D11::Texture3D:
+							{
+								D3D11_TEXTURE3D_DESC desc;
+								texture.m_texture3d->GetDesc(&desc);
+								m_width  = desc.Width;
+								m_height = desc.Height;
+							}
+							break;
+						}
+					}
+
 					if (isDepth( (TextureFormat::Enum)texture.m_textureFormat) )
 					if (isDepth( (TextureFormat::Enum)texture.m_textureFormat) )
 					{
 					{
 						BX_CHECK(NULL == m_dsv, "Frame buffer already has depth-stencil attached.");
 						BX_CHECK(NULL == m_dsv, "Frame buffer already has depth-stencil attached.");
@@ -4718,7 +4762,7 @@ BX_PRAGMA_DIAGNOSTIC_POP();
 
 
 						const ShaderD3D11* fsh = program.m_fsh;
 						const ShaderD3D11* fsh = program.m_fsh;
 						if (NULL != m_currentColor
 						if (NULL != m_currentColor
-						||  fsh->m_hasDiscard)
+						||  fsh->m_hasDepthOp)
 						{
 						{
 							deviceCtx->PSSetShader(fsh->m_pixelShader, NULL, 0);
 							deviceCtx->PSSetShader(fsh->m_pixelShader, NULL, 0);
 							deviceCtx->PSSetConstantBuffers(0, 1, &fsh->m_buffer);
 							deviceCtx->PSSetConstantBuffers(0, 1, &fsh->m_buffer);

+ 12 - 8
src/renderer_d3d11.h

@@ -113,7 +113,7 @@ namespace bgfx { namespace d3d11
 			, m_hash(0)
 			, m_hash(0)
 			, m_numUniforms(0)
 			, m_numUniforms(0)
 			, m_numPredefined(0)
 			, m_numPredefined(0)
-			, m_hasDiscard(false)
+			, m_hasDepthOp(false)
 		{
 		{
 		}
 		}
 
 
@@ -163,7 +163,7 @@ namespace bgfx { namespace d3d11
 
 
 		uint16_t m_numUniforms;
 		uint16_t m_numUniforms;
 		uint8_t m_numPredefined;
 		uint8_t m_numPredefined;
-		bool m_hasDiscard;
+		bool m_hasDepthOp;
 	};
 	};
 
 
 	struct ProgramD3D11
 	struct ProgramD3D11
@@ -231,25 +231,27 @@ namespace bgfx { namespace d3d11
 
 
 		union
 		union
 		{
 		{
-			ID3D11Resource* m_ptr;
+			ID3D11Resource*  m_ptr;
 			ID3D11Texture2D* m_texture2d;
 			ID3D11Texture2D* m_texture2d;
 			ID3D11Texture3D* m_texture3d;
 			ID3D11Texture3D* m_texture3d;
 		};
 		};
 
 
-		ID3D11ShaderResourceView* m_srv;
+		ID3D11ShaderResourceView*  m_srv;
 		ID3D11UnorderedAccessView* m_uav;
 		ID3D11UnorderedAccessView* m_uav;
 		ID3D11SamplerState* m_sampler;
 		ID3D11SamplerState* m_sampler;
 		uint32_t m_flags;
 		uint32_t m_flags;
-		uint8_t m_type;
-		uint8_t m_requestedFormat;
-		uint8_t m_textureFormat;
-		uint8_t m_numMips;
+		uint8_t  m_type;
+		uint8_t  m_requestedFormat;
+		uint8_t  m_textureFormat;
+		uint8_t  m_numMips;
 	};
 	};
 
 
 	struct FrameBufferD3D11
 	struct FrameBufferD3D11
 	{
 	{
 		FrameBufferD3D11()
 		FrameBufferD3D11()
 			: m_dsv(NULL)
 			: m_dsv(NULL)
+			, m_width(0)
+			, m_height(0)
 			, m_denseIdx(UINT16_MAX)
 			, m_denseIdx(UINT16_MAX)
 			, m_num(0)
 			, m_num(0)
 			, m_numTh(0)
 			, m_numTh(0)
@@ -268,6 +270,8 @@ namespace bgfx { namespace d3d11
 		ID3D11ShaderResourceView* m_srv[BGFX_CONFIG_MAX_FRAME_BUFFER_ATTACHMENTS-1];
 		ID3D11ShaderResourceView* m_srv[BGFX_CONFIG_MAX_FRAME_BUFFER_ATTACHMENTS-1];
 		ID3D11DepthStencilView* m_dsv;
 		ID3D11DepthStencilView* m_dsv;
 		IDXGISwapChain* m_swapChain;
 		IDXGISwapChain* m_swapChain;
+		uint32_t m_width;
+		uint32_t m_height;
 		uint16_t m_denseIdx;
 		uint16_t m_denseIdx;
 		uint8_t m_num;
 		uint8_t m_num;
 		uint8_t m_numTh;
 		uint8_t m_numTh;

+ 24 - 2
src/renderer_d3d12.cpp

@@ -2422,8 +2422,20 @@ data.NumQualityLevels = 0;
 
 
 		void clearQuad(const Rect& _rect, const Clear& _clear, const float _palette[][4])
 		void clearQuad(const Rect& _rect, const Clear& _clear, const float _palette[][4])
 		{
 		{
-			uint32_t width  = m_scd.BufferDesc.Width;
-			uint32_t height = m_scd.BufferDesc.Height;
+			uint32_t width;
+			uint32_t height;
+
+			if (isValid(m_fbh) )
+			{
+				const FrameBufferD3D12& fb = m_frameBuffers[m_fbh.idx];
+				width  = fb.m_width;
+				height = fb.m_height;
+			}
+			else
+			{
+				width  = m_scd.BufferDesc.Width;
+				height = m_scd.BufferDesc.Height;
+			}
 
 
 			if (0      == _rect.m_x
 			if (0      == _rect.m_x
 			&&  0      == _rect.m_y
 			&&  0      == _rect.m_y
@@ -4038,6 +4050,8 @@ data.NumQualityLevels = 0;
 			uint32_t fbhIdx = (uint32_t)(this - s_renderD3D12->m_frameBuffers);
 			uint32_t fbhIdx = (uint32_t)(this - s_renderD3D12->m_frameBuffers);
 			rtvDescriptor.ptr += (BX_COUNTOF(s_renderD3D12->m_backBufferColor) + fbhIdx * BGFX_CONFIG_MAX_FRAME_BUFFER_ATTACHMENTS) * rtvDescriptorSize;
 			rtvDescriptor.ptr += (BX_COUNTOF(s_renderD3D12->m_backBufferColor) + fbhIdx * BGFX_CONFIG_MAX_FRAME_BUFFER_ATTACHMENTS) * rtvDescriptorSize;
 
 
+			m_width  = 0;
+			m_height = 0;
 			m_depth.idx = bgfx::invalidHandle;
 			m_depth.idx = bgfx::invalidHandle;
 			m_num = 0;
 			m_num = 0;
 			for (uint32_t ii = 0; ii < m_numTh; ++ii)
 			for (uint32_t ii = 0; ii < m_numTh; ++ii)
@@ -4046,6 +4060,14 @@ data.NumQualityLevels = 0;
 				if (isValid(handle) )
 				if (isValid(handle) )
 				{
 				{
 					const TextureD3D12& texture = s_renderD3D12->m_textures[handle.idx];
 					const TextureD3D12& texture = s_renderD3D12->m_textures[handle.idx];
+
+					if (0 == m_width)
+					{
+						D3D12_RESOURCE_DESC desc = texture.m_ptr->GetDesc();
+						m_width  = uint32_t(desc.Width);
+						m_height = uint32_t(desc.Height);
+					}
+
 					if (isDepth( (TextureFormat::Enum)texture.m_textureFormat) )
 					if (isDepth( (TextureFormat::Enum)texture.m_textureFormat) )
 					{
 					{
 						BX_CHECK(!isValid(m_depth), "");
 						BX_CHECK(!isValid(m_depth), "");

+ 4 - 0
src/renderer_d3d12.h

@@ -283,6 +283,8 @@ namespace bgfx { namespace d3d12
 	{
 	{
 		FrameBufferD3D12()
 		FrameBufferD3D12()
 			: m_swapChain(NULL)
 			: m_swapChain(NULL)
+			, m_width(0)
+			, m_height(0)
 			, m_denseIdx(UINT16_MAX)
 			, m_denseIdx(UINT16_MAX)
 			, m_num(0)
 			, m_num(0)
 			, m_numTh(0)
 			, m_numTh(0)
@@ -301,6 +303,8 @@ namespace bgfx { namespace d3d12
 		TextureHandle m_texture[BGFX_CONFIG_MAX_FRAME_BUFFER_ATTACHMENTS];
 		TextureHandle m_texture[BGFX_CONFIG_MAX_FRAME_BUFFER_ATTACHMENTS];
 		TextureHandle m_depth;
 		TextureHandle m_depth;
 		IDXGISwapChain* m_swapChain;
 		IDXGISwapChain* m_swapChain;
+		uint32_t m_width;
+		uint32_t m_height;
 		uint16_t m_denseIdx;
 		uint16_t m_denseIdx;
 		uint8_t m_num;
 		uint8_t m_num;
 		uint8_t m_numTh;
 		uint8_t m_numTh;

+ 5 - 1
src/shader_dxbc.cpp

@@ -1884,7 +1884,11 @@ namespace bgfx
 			uint32_t size = read(&reader, instruction);
 			uint32_t size = read(&reader, instruction);
 			BX_CHECK(size/4 == instruction.length, "read %d, expected %d", size/4, instruction.length); BX_UNUSED(size);
 			BX_CHECK(size/4 == instruction.length, "read %d, expected %d", size/4, instruction.length); BX_UNUSED(size);
 
 
-			_fn(token * sizeof(uint32_t), instruction, _userData);
+			bool cont = _fn(token * sizeof(uint32_t), instruction, _userData);
+			if (!cont)
+			{
+				return;
+			}
 
 
 			token += instruction.length;
 			token += instruction.length;
 		}
 		}

+ 1 - 1
src/shader_dxbc.h

@@ -575,7 +575,7 @@ namespace bgfx
 	int32_t read(bx::ReaderSeekerI* _reader, DxbcShader& _shader);
 	int32_t read(bx::ReaderSeekerI* _reader, DxbcShader& _shader);
 	int32_t write(bx::WriterI* _writer, const DxbcShader& _shader);
 	int32_t write(bx::WriterI* _writer, const DxbcShader& _shader);
 
 
-	typedef void (*DxbcParseFn)(uint32_t _offset, const DxbcInstruction& _instruction, void* _userData);
+	typedef bool (*DxbcParseFn)(uint32_t _offset, const DxbcInstruction& _instruction, void* _userData);
 	void parse(const DxbcShader& _src, DxbcParseFn _fn, void* _userData);
 	void parse(const DxbcShader& _src, DxbcParseFn _fn, void* _userData);
 
 
 	typedef void (*DxbcFilterFn)(DxbcInstruction& _instruction, void* _userData);
 	typedef void (*DxbcFilterFn)(DxbcInstruction& _instruction, void* _userData);