diff --git a/Source/Core/VideoBackends/D3D/DXTexture.cpp b/Source/Core/VideoBackends/D3D/DXTexture.cpp index 0431155549..7121dcf0b7 100644 --- a/Source/Core/VideoBackends/D3D/DXTexture.cpp +++ b/Source/Core/VideoBackends/D3D/DXTexture.cpp @@ -43,19 +43,71 @@ DXGI_FORMAT GetDXGIFormatForHostFormat(AbstractTextureFormat format) return DXGI_FORMAT_R8G8B8A8_UNORM; case AbstractTextureFormat::BGRA8: return DXGI_FORMAT_B8G8R8A8_UNORM; + case AbstractTextureFormat::R16: + return DXGI_FORMAT_R16_UNORM; + case AbstractTextureFormat::R32F: + return DXGI_FORMAT_R32_FLOAT; + case AbstractTextureFormat::D16: + return DXGI_FORMAT_R16_TYPELESS; + case AbstractTextureFormat::D32F: + return DXGI_FORMAT_R32_TYPELESS; + case AbstractTextureFormat::D32F_S8: + return DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS; default: PanicAlert("Unhandled texture format."); return DXGI_FORMAT_R8G8B8A8_UNORM; } } +DXGI_FORMAT GetSRVFormatForHostFormat(AbstractTextureFormat format) +{ + switch (format) + { + case AbstractTextureFormat::D16: + return DXGI_FORMAT_R16_UNORM; + case AbstractTextureFormat::D32F: + return DXGI_FORMAT_R32_FLOAT; + case AbstractTextureFormat::D32F_S8: + return DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS; + default: + return GetDXGIFormatForHostFormat(format); + } +} +DXGI_FORMAT GetDSVFormatForHostFormat(AbstractTextureFormat format) +{ + switch (format) + { + case AbstractTextureFormat::D16: + return DXGI_FORMAT_D16_UNORM; + case AbstractTextureFormat::D32F: + return DXGI_FORMAT_D32_FLOAT; + case AbstractTextureFormat::D32F_S8: + return DXGI_FORMAT_D32_FLOAT_S8X24_UINT; + default: + return GetDXGIFormatForHostFormat(format); + } +} } // Anonymous namespace DXTexture::DXTexture(const TextureConfig& tex_config) : AbstractTexture(tex_config) { DXGI_FORMAT tex_format = GetDXGIFormatForHostFormat(m_config.format); + DXGI_FORMAT srv_format = GetSRVFormatForHostFormat(m_config.format); + DXGI_FORMAT rtv_format = DXGI_FORMAT_UNKNOWN; + DXGI_FORMAT dsv_format = DXGI_FORMAT_UNKNOWN; UINT bind_flags = D3D11_BIND_SHADER_RESOURCE; if (tex_config.rendertarget) - bind_flags |= D3D11_BIND_RENDER_TARGET; + { + if (IsDepthFormat(tex_config.format)) + { + bind_flags |= D3D11_BIND_DEPTH_STENCIL; + dsv_format = GetDSVFormatForHostFormat(m_config.format); + } + else + { + bind_flags |= D3D11_BIND_RENDER_TARGET; + rtv_format = tex_format; + } + } CD3D11_TEXTURE2D_DESC texdesc(tex_format, tex_config.width, tex_config.height, tex_config.layers, tex_config.levels, bind_flags, D3D11_USAGE_DEFAULT, 0, @@ -65,13 +117,8 @@ DXTexture::DXTexture(const TextureConfig& tex_config) : AbstractTexture(tex_conf HRESULT hr = D3D::device->CreateTexture2D(&texdesc, nullptr, &pTexture); CHECK(SUCCEEDED(hr), "Create backing DXTexture"); - m_texture = new D3DTexture2D( - pTexture, static_cast(bind_flags), tex_format, DXGI_FORMAT_UNKNOWN, - tex_config.rendertarget ? tex_format : DXGI_FORMAT_UNKNOWN, tex_config.samples > 1); - - D3D::SetDebugObjectName(m_texture->GetTex(), "a texture of the TextureCache"); - D3D::SetDebugObjectName(m_texture->GetSRV(), - "shader resource view of a texture of the TextureCache"); + m_texture = new D3DTexture2D(pTexture, static_cast(bind_flags), srv_format, + dsv_format, rtv_format, tex_config.samples > 1); SAFE_RELEASE(pTexture); } diff --git a/Source/Core/VideoBackends/OGL/OGLTexture.cpp b/Source/Core/VideoBackends/OGL/OGLTexture.cpp index b42852d499..60b33886c6 100644 --- a/Source/Core/VideoBackends/OGL/OGLTexture.cpp +++ b/Source/Core/VideoBackends/OGL/OGLTexture.cpp @@ -35,6 +35,16 @@ GLenum GetGLInternalFormatForTextureFormat(AbstractTextureFormat format, bool st return storage ? GL_RGBA8 : GL_RGBA; case AbstractTextureFormat::BGRA8: return storage ? GL_RGBA8 : GL_BGRA; + case AbstractTextureFormat::R16: + return GL_R16; + case AbstractTextureFormat::R32F: + return GL_R32F; + case AbstractTextureFormat::D16: + return GL_DEPTH_COMPONENT16; + case AbstractTextureFormat::D32F: + return GL_DEPTH_COMPONENT32F; + case AbstractTextureFormat::D32F_S8: + return GL_DEPTH32F_STENCIL8; default: PanicAlert("Unhandled texture format."); return storage ? GL_RGBA8 : GL_RGBA; @@ -49,6 +59,14 @@ GLenum GetGLFormatForTextureFormat(AbstractTextureFormat format) return GL_RGBA; case AbstractTextureFormat::BGRA8: return GL_BGRA; + case AbstractTextureFormat::R16: + case AbstractTextureFormat::R32F: + return GL_RED; + case AbstractTextureFormat::D16: + case AbstractTextureFormat::D32F: + return GL_DEPTH_COMPONENT; + case AbstractTextureFormat::D32F_S8: + return GL_DEPTH_STENCIL; // Compressed texture formats don't use this parameter. default: return GL_UNSIGNED_BYTE; @@ -62,6 +80,16 @@ GLenum GetGLTypeForTextureFormat(AbstractTextureFormat format) case AbstractTextureFormat::RGBA8: case AbstractTextureFormat::BGRA8: return GL_UNSIGNED_BYTE; + case AbstractTextureFormat::R16: + return GL_UNSIGNED_SHORT; + case AbstractTextureFormat::R32F: + return GL_FLOAT; + case AbstractTextureFormat::D16: + return GL_UNSIGNED_SHORT; + case AbstractTextureFormat::D32F: + return GL_FLOAT; + case AbstractTextureFormat::D32F_S8: + return GL_FLOAT_32_UNSIGNED_INT_24_8_REV; // Compressed texture formats don't use this parameter. default: return GL_UNSIGNED_BYTE; diff --git a/Source/Core/VideoBackends/Vulkan/Util.cpp b/Source/Core/VideoBackends/Vulkan/Util.cpp index 8fbdfbb72c..4977a270a3 100644 --- a/Source/Core/VideoBackends/Vulkan/Util.cpp +++ b/Source/Core/VideoBackends/Vulkan/Util.cpp @@ -112,6 +112,21 @@ VkFormat GetVkFormatForHostTextureFormat(AbstractTextureFormat format) case AbstractTextureFormat::BGRA8: return VK_FORMAT_B8G8R8A8_UNORM; + case AbstractTextureFormat::R16: + return VK_FORMAT_R16_UNORM; + + case AbstractTextureFormat::D16: + return VK_FORMAT_D16_UNORM; + + case AbstractTextureFormat::R32F: + return VK_FORMAT_R32_SFLOAT; + + case AbstractTextureFormat::D32F: + return VK_FORMAT_D32_SFLOAT; + + case AbstractTextureFormat::D32F_S8: + return VK_FORMAT_D32_SFLOAT_S8_UINT; + default: PanicAlert("Unhandled texture format."); return VK_FORMAT_R8G8B8A8_UNORM; diff --git a/Source/Core/VideoBackends/Vulkan/VKTexture.cpp b/Source/Core/VideoBackends/Vulkan/VKTexture.cpp index 974a8578a1..f51a9150de 100644 --- a/Source/Core/VideoBackends/Vulkan/VKTexture.cpp +++ b/Source/Core/VideoBackends/Vulkan/VKTexture.cpp @@ -79,14 +79,29 @@ std::unique_ptr VKTexture::Create(const TextureConfig& tex_config) return nullptr; } - // Clear render targets before use to prevent reading uninitialized memory. - VkClearColorValue clear_value = {{0.0f, 0.0f, 0.0f, 1.0f}}; - VkImageSubresourceRange clear_range = {VK_IMAGE_ASPECT_COLOR_BIT, 0, tex_config.levels, 0, - tex_config.layers}; - texture->TransitionToLayout(g_command_buffer_mgr->GetCurrentInitCommandBuffer(), - VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL); - vkCmdClearColorImage(g_command_buffer_mgr->GetCurrentInitCommandBuffer(), texture->GetImage(), - texture->GetLayout(), &clear_value, 1, &clear_range); + if (!IsDepthFormat(tex_config.format)) + { + // Clear render targets before use to prevent reading uninitialized memory. + VkClearColorValue clear_value = {{0.0f, 0.0f, 0.0f, 1.0f}}; + VkImageSubresourceRange clear_range = {VK_IMAGE_ASPECT_COLOR_BIT, 0, tex_config.levels, 0, + tex_config.layers}; + texture->TransitionToLayout(g_command_buffer_mgr->GetCurrentInitCommandBuffer(), + VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL); + vkCmdClearColorImage(g_command_buffer_mgr->GetCurrentInitCommandBuffer(), texture->GetImage(), + texture->GetLayout(), &clear_value, 1, &clear_range); + } + else + { + // Clear render targets before use to prevent reading uninitialized memory. + VkClearDepthStencilValue clear_value = {0.0f, 0}; + VkImageSubresourceRange clear_range = {VK_IMAGE_ASPECT_DEPTH_BIT, 0, tex_config.levels, 0, + tex_config.layers}; + texture->TransitionToLayout(g_command_buffer_mgr->GetCurrentInitCommandBuffer(), + VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL); + vkCmdClearDepthStencilImage(g_command_buffer_mgr->GetCurrentInitCommandBuffer(), + texture->GetImage(), texture->GetLayout(), &clear_value, 1, + &clear_range); + } } return std::unique_ptr(new VKTexture(tex_config, std::move(texture), framebuffer)); diff --git a/Source/Core/VideoCommon/AbstractTexture.cpp b/Source/Core/VideoCommon/AbstractTexture.cpp index 98872f5c59..0f7602a0df 100644 --- a/Source/Core/VideoCommon/AbstractTexture.cpp +++ b/Source/Core/VideoCommon/AbstractTexture.cpp @@ -64,6 +64,20 @@ bool AbstractTexture::IsCompressedFormat(AbstractTextureFormat format) } } +bool AbstractTexture::IsDepthFormat(AbstractTextureFormat format) +{ + switch (format) + { + case AbstractTextureFormat::D16: + case AbstractTextureFormat::D32F: + case AbstractTextureFormat::D32F_S8: + return true; + + default: + return false; + } +} + size_t AbstractTexture::CalculateStrideForFormat(AbstractTextureFormat format, u32 row_length) { switch (format) @@ -74,9 +88,16 @@ size_t AbstractTexture::CalculateStrideForFormat(AbstractTextureFormat format, u case AbstractTextureFormat::DXT5: case AbstractTextureFormat::BPTC: return static_cast(std::max(1u, row_length / 4)) * 16; + case AbstractTextureFormat::R16: + case AbstractTextureFormat::D16: + return static_cast(row_length) * 2; case AbstractTextureFormat::RGBA8: case AbstractTextureFormat::BGRA8: + case AbstractTextureFormat::R32F: + case AbstractTextureFormat::D32F: return static_cast(row_length) * 4; + case AbstractTextureFormat::D32F_S8: + return static_cast(row_length) * 8; default: PanicAlert("Unhandled texture format."); return 0; @@ -93,9 +114,16 @@ size_t AbstractTexture::GetTexelSizeForFormat(AbstractTextureFormat format) case AbstractTextureFormat::DXT5: case AbstractTextureFormat::BPTC: return 16; + case AbstractTextureFormat::R16: + case AbstractTextureFormat::D16: + return 2; case AbstractTextureFormat::RGBA8: case AbstractTextureFormat::BGRA8: + case AbstractTextureFormat::R32F: + case AbstractTextureFormat::D32F: return 4; + case AbstractTextureFormat::D32F_S8: + return 8; default: PanicAlert("Unhandled texture format."); return 0; diff --git a/Source/Core/VideoCommon/AbstractTexture.h b/Source/Core/VideoCommon/AbstractTexture.h index 01b56faa18..b7de94820d 100644 --- a/Source/Core/VideoCommon/AbstractTexture.h +++ b/Source/Core/VideoCommon/AbstractTexture.h @@ -39,6 +39,7 @@ public: bool Save(const std::string& filename, unsigned int level); static bool IsCompressedFormat(AbstractTextureFormat format); + static bool IsDepthFormat(AbstractTextureFormat format); static size_t CalculateStrideForFormat(AbstractTextureFormat format, u32 row_length); static size_t GetTexelSizeForFormat(AbstractTextureFormat format); diff --git a/Source/Core/VideoCommon/TextureConfig.h b/Source/Core/VideoCommon/TextureConfig.h index 3d24bf3b93..1aa27cca4c 100644 --- a/Source/Core/VideoCommon/TextureConfig.h +++ b/Source/Core/VideoCommon/TextureConfig.h @@ -18,6 +18,11 @@ enum class AbstractTextureFormat : u32 DXT3, DXT5, BPTC, + R16, + D16, + R32F, + D32F, + D32F_S8, Undefined };