summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authoriwubcode <iwubcode@users.noreply.github.com>2023-07-21 19:09:40 -0500
committeriwubcode <iwubcode@users.noreply.github.com>2023-07-21 19:09:40 -0500
commite892b7f1ac426fdc8a3ac1fa28026b86cc06279b (patch)
treecc63449c3ab8ff924a39f23624bbaa9efddd3279
parent2764978bebce9cedf0e329c320951ff0508f7139 (diff)
VideoBackends: add support for cube maps for OGL, Vulkan, and D3D
-rw-r--r--Source/Core/VideoBackends/D3D/DXTexture.cpp4
-rw-r--r--Source/Core/VideoBackends/D3D12/DX12Context.cpp3
-rw-r--r--Source/Core/VideoBackends/D3D12/DX12Texture.cpp29
-rw-r--r--Source/Core/VideoBackends/OGL/OGLTexture.cpp57
-rw-r--r--Source/Core/VideoBackends/OGL/OGLTexture.h4
-rw-r--r--Source/Core/VideoBackends/Vulkan/VKTexture.cpp6
-rw-r--r--Source/Core/VideoCommon/TextureConfig.h2
7 files changed, 81 insertions, 24 deletions
diff --git a/Source/Core/VideoBackends/D3D/DXTexture.cpp b/Source/Core/VideoBackends/D3D/DXTexture.cpp
index c20a8d9204..7a260eae4a 100644
--- a/Source/Core/VideoBackends/D3D/DXTexture.cpp
+++ b/Source/Core/VideoBackends/D3D/DXTexture.cpp
@@ -46,7 +46,8 @@ std::unique_ptr<DXTexture> DXTexture::Create(const TextureConfig& config, std::s
bindflags |= D3D11_BIND_UNORDERED_ACCESS;
CD3D11_TEXTURE2D_DESC desc(tex_format, config.width, config.height, config.layers, config.levels,
- bindflags, D3D11_USAGE_DEFAULT, 0, config.samples, 0, 0);
+ bindflags, D3D11_USAGE_DEFAULT, 0, config.samples, 0,
+ config.IsCubeMap() ? D3D11_RESOURCE_MISC_TEXTURECUBE : 0);
ComPtr<ID3D11Texture2D> d3d_texture;
HRESULT hr = D3D::device->CreateTexture2D(&desc, nullptr, d3d_texture.GetAddressOf());
if (FAILED(hr))
@@ -90,6 +91,7 @@ bool DXTexture::CreateSRV()
{
const CD3D11_SHADER_RESOURCE_VIEW_DESC desc(
m_texture.Get(),
+ m_config.IsCubeMap() ? D3D11_SRV_DIMENSION_TEXTURECUBE :
m_config.IsMultisampled() ? D3D11_SRV_DIMENSION_TEXTURE2DMSARRAY :
D3D11_SRV_DIMENSION_TEXTURE2DARRAY,
D3DCommon::GetSRVFormatForAbstractFormat(m_config.format), 0, m_config.levels, 0,
diff --git a/Source/Core/VideoBackends/D3D12/DX12Context.cpp b/Source/Core/VideoBackends/D3D12/DX12Context.cpp
index bf156b2fdb..dd8630ac3b 100644
--- a/Source/Core/VideoBackends/D3D12/DX12Context.cpp
+++ b/Source/Core/VideoBackends/D3D12/DX12Context.cpp
@@ -88,7 +88,8 @@ std::vector<u32> DXContext::GetAAModes(u32 adapter_index)
bool DXContext::SupportsTextureFormat(DXGI_FORMAT format)
{
- constexpr u32 required = D3D12_FORMAT_SUPPORT1_TEXTURE2D | D3D12_FORMAT_SUPPORT1_SHADER_SAMPLE;
+ constexpr u32 required = D3D12_FORMAT_SUPPORT1_TEXTURE2D | D3D12_FORMAT_SUPPORT1_TEXTURECUBE |
+ D3D12_FORMAT_SUPPORT1_SHADER_SAMPLE;
D3D12_FEATURE_DATA_FORMAT_SUPPORT support = {format};
return SUCCEEDED(m_device->CheckFeatureSupport(D3D12_FEATURE_FORMAT_SUPPORT, &support,
diff --git a/Source/Core/VideoBackends/D3D12/DX12Texture.cpp b/Source/Core/VideoBackends/D3D12/DX12Texture.cpp
index f20c37354b..a51fe7ff38 100644
--- a/Source/Core/VideoBackends/D3D12/DX12Texture.cpp
+++ b/Source/Core/VideoBackends/D3D12/DX12Texture.cpp
@@ -165,19 +165,30 @@ bool DXTexture::CreateSRVDescriptor()
return false;
}
- D3D12_SHADER_RESOURCE_VIEW_DESC desc = {D3DCommon::GetSRVFormatForAbstractFormat(m_config.format),
- m_config.IsMultisampled() ?
- D3D12_SRV_DIMENSION_TEXTURE2DMSARRAY :
- D3D12_SRV_DIMENSION_TEXTURE2DARRAY,
- D3D12_DEFAULT_SHADER_4_COMPONENT_MAPPING};
- if (m_config.IsMultisampled())
+ D3D12_SHADER_RESOURCE_VIEW_DESC desc = {
+ D3DCommon::GetSRVFormatForAbstractFormat(m_config.format),
+ m_config.IsCubeMap() ? D3D12_SRV_DIMENSION_TEXTURECUBE :
+ m_config.IsMultisampled() ? D3D12_SRV_DIMENSION_TEXTURE2DMSARRAY :
+ D3D12_SRV_DIMENSION_TEXTURE2DARRAY,
+ D3D12_DEFAULT_SHADER_4_COMPONENT_MAPPING};
+
+ if (m_config.IsCubeMap())
{
- desc.Texture2DMSArray.ArraySize = m_config.layers;
+ desc.TextureCube.MostDetailedMip = 0;
+ desc.TextureCube.MipLevels = m_config.levels;
+ desc.TextureCube.ResourceMinLODClamp = 0.0f;
}
else
{
- desc.Texture2DArray.MipLevels = m_config.levels;
- desc.Texture2DArray.ArraySize = m_config.layers;
+ if (m_config.IsMultisampled())
+ {
+ desc.Texture2DMSArray.ArraySize = m_config.layers;
+ }
+ else
+ {
+ desc.Texture2DArray.MipLevels = m_config.levels;
+ desc.Texture2DArray.ArraySize = m_config.layers;
+ }
}
g_dx_context->GetDevice()->CreateShaderResourceView(m_resource.Get(), &desc,
m_srv_descriptor.cpu_handle);
diff --git a/Source/Core/VideoBackends/OGL/OGLTexture.cpp b/Source/Core/VideoBackends/OGL/OGLTexture.cpp
index f8894a365b..70c38d14ff 100644
--- a/Source/Core/VideoBackends/OGL/OGLTexture.cpp
+++ b/Source/Core/VideoBackends/OGL/OGLTexture.cpp
@@ -140,7 +140,11 @@ OGLTexture::OGLTexture(const TextureConfig& tex_config, std::string_view name)
glTexParameteri(target, GL_TEXTURE_MAX_LEVEL, m_config.levels - 1);
GLenum gl_internal_format = GetGLInternalFormatForTextureFormat(m_config.format, true);
- if (tex_config.IsMultisampled())
+ if (g_ogl_config.bSupportsTextureStorage && m_config.IsCubeMap())
+ {
+ glTexStorage2D(target, m_config.levels, gl_internal_format, m_config.width, m_config.height);
+ }
+ else if (tex_config.IsMultisampled())
{
ASSERT(g_ogl_config.bSupportsMSAA);
if (g_ogl_config.SupportedMultisampleTexStorage != MultisampleTexStorageType::TexStorageNone)
@@ -267,29 +271,62 @@ void OGLTexture::Load(u32 level, u32 width, u32 height, u32 row_length, const u8
GLenum gl_internal_format = GetGLInternalFormatForTextureFormat(m_config.format, false);
if (IsCompressedFormat(m_config.format))
{
- if (g_ogl_config.bSupportsTextureStorage)
+ if (m_config.IsCubeMap())
{
- glCompressedTexSubImage3D(target, level, 0, 0, layer, width, height, 1, gl_internal_format,
- static_cast<GLsizei>(buffer_size), buffer);
+ if (g_ogl_config.bSupportsTextureStorage)
+ {
+ glCompressedTexSubImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + layer, level, 0, 0, width,
+ height, gl_internal_format, static_cast<GLsizei>(buffer_size),
+ buffer);
+ }
+ else
+ {
+ glCompressedTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + layer, level, gl_internal_format,
+ width, height, 0, static_cast<GLsizei>(buffer_size), buffer);
+ }
}
else
{
- glCompressedTexImage3D(target, level, gl_internal_format, width, height, 1, 0,
- static_cast<GLsizei>(buffer_size), buffer);
+ if (g_ogl_config.bSupportsTextureStorage)
+ {
+ glCompressedTexSubImage3D(target, level, 0, 0, layer, width, height, 1, gl_internal_format,
+ static_cast<GLsizei>(buffer_size), buffer);
+ }
+ else
+ {
+ glCompressedTexImage3D(target, level, gl_internal_format, width, height, 1, 0,
+ static_cast<GLsizei>(buffer_size), buffer);
+ }
}
}
else
{
GLenum gl_format = GetGLFormatForTextureFormat(m_config.format);
GLenum gl_type = GetGLTypeForTextureFormat(m_config.format);
- if (g_ogl_config.bSupportsTextureStorage)
+ if (m_config.IsCubeMap())
{
- glTexSubImage3D(target, level, 0, 0, layer, width, height, 1, gl_format, gl_type, buffer);
+ if (g_ogl_config.bSupportsTextureStorage)
+ {
+ glTexSubImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + layer, level, 0, 0, width, height,
+ gl_format, gl_type, buffer);
+ }
+ else
+ {
+ glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + layer, level, gl_internal_format, width,
+ height, 0, gl_format, gl_type, buffer);
+ }
}
else
{
- glTexImage3D(target, level, gl_internal_format, width, height, 1, 0, gl_format, gl_type,
- buffer);
+ if (g_ogl_config.bSupportsTextureStorage)
+ {
+ glTexSubImage3D(target, level, 0, 0, layer, width, height, 1, gl_format, gl_type, buffer);
+ }
+ else
+ {
+ glTexImage3D(target, level, gl_internal_format, width, height, 1, 0, gl_format, gl_type,
+ buffer);
+ }
}
}
diff --git a/Source/Core/VideoBackends/OGL/OGLTexture.h b/Source/Core/VideoBackends/OGL/OGLTexture.h
index 53d9d7f589..91879a6564 100644
--- a/Source/Core/VideoBackends/OGL/OGLTexture.h
+++ b/Source/Core/VideoBackends/OGL/OGLTexture.h
@@ -34,7 +34,9 @@ public:
GLuint GetGLTextureId() const { return m_texId; }
GLenum GetGLTarget() const
{
- return IsMultisampled() ? GL_TEXTURE_2D_MULTISAMPLE_ARRAY : GL_TEXTURE_2D_ARRAY;
+ return m_config.IsCubeMap() ? GL_TEXTURE_CUBE_MAP :
+ IsMultisampled() ? GL_TEXTURE_2D_MULTISAMPLE_ARRAY :
+ GL_TEXTURE_2D_ARRAY;
}
static GLenum GetGLInternalFormatForTextureFormat(AbstractTextureFormat format, bool storage);
GLenum GetGLFormatForImageTexture() const;
diff --git a/Source/Core/VideoBackends/Vulkan/VKTexture.cpp b/Source/Core/VideoBackends/Vulkan/VKTexture.cpp
index f8923b4edc..e80ce4f2f7 100644
--- a/Source/Core/VideoBackends/Vulkan/VKTexture.cpp
+++ b/Source/Core/VideoBackends/Vulkan/VKTexture.cpp
@@ -70,7 +70,8 @@ std::unique_ptr<VKTexture> VKTexture::Create(const TextureConfig& tex_config, st
VkImageCreateInfo image_info = {VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
nullptr,
- 0,
+ tex_config.IsCubeMap() ? VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT :
+ static_cast<VkImageCreateFlags>(0),
VK_IMAGE_TYPE_2D,
GetVkFormatForHostTextureFormat(tex_config.format),
{tex_config.width, tex_config.height, 1},
@@ -106,7 +107,8 @@ std::unique_ptr<VKTexture> VKTexture::Create(const TextureConfig& tex_config, st
std::unique_ptr<VKTexture> texture = std::make_unique<VKTexture>(
tex_config, alloc, image, name, VK_IMAGE_LAYOUT_UNDEFINED, ComputeImageLayout::Undefined);
- if (!texture->CreateView(VK_IMAGE_VIEW_TYPE_2D_ARRAY))
+ if (!texture->CreateView(tex_config.IsCubeMap() ? VK_IMAGE_VIEW_TYPE_CUBE :
+ VK_IMAGE_VIEW_TYPE_2D_ARRAY))
return nullptr;
return texture;
diff --git a/Source/Core/VideoCommon/TextureConfig.h b/Source/Core/VideoCommon/TextureConfig.h
index c076ff85c0..75d7387f17 100644
--- a/Source/Core/VideoCommon/TextureConfig.h
+++ b/Source/Core/VideoCommon/TextureConfig.h
@@ -39,6 +39,7 @@ enum AbstractTextureFlag : u32
{
AbstractTextureFlag_RenderTarget = (1 << 0), // Texture is used as a framebuffer.
AbstractTextureFlag_ComputeImage = (1 << 1), // Texture is used as a compute image.
+ AbstractTextureFlag_CubeMap = (1 << 2), // Texture is used as a cube map.
};
struct TextureConfig
@@ -61,6 +62,7 @@ struct TextureConfig
bool IsMultisampled() const { return samples > 1; }
bool IsRenderTarget() const { return (flags & AbstractTextureFlag_RenderTarget) != 0; }
bool IsComputeImage() const { return (flags & AbstractTextureFlag_ComputeImage) != 0; }
+ bool IsCubeMap() const { return (flags & AbstractTextureFlag_CubeMap) != 0; }
u32 width = 0;
u32 height = 0;