From 25fbfd7a891a7afc36cac4a6ca12bcb59f6411b7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Rydg=C3=A5rd?= Date: Sun, 12 Mar 2023 12:18:55 +0100 Subject: [PATCH] Finish up OpenGL compressed texture format checks. Show in dev screen --- Common/GPU/D3D9/thin3d_d3d9.cpp | 2 +- Common/GPU/OpenGL/DataFormatGL.cpp | 12 +++++++++ Common/GPU/OpenGL/GLFeatures.cpp | 40 +++++++++++++++++++++++++++++- Common/GPU/OpenGL/GLFeatures.h | 13 ++++++++++ Common/GPU/OpenGL/thin3d_gl.cpp | 18 +++++++++++++- UI/DevScreens.cpp | 10 ++++++++ 6 files changed, 92 insertions(+), 3 deletions(-) diff --git a/Common/GPU/D3D9/thin3d_d3d9.cpp b/Common/GPU/D3D9/thin3d_d3d9.cpp index 0326a22305..a560a78fe3 100644 --- a/Common/GPU/D3D9/thin3d_d3d9.cpp +++ b/Common/GPU/D3D9/thin3d_d3d9.cpp @@ -113,7 +113,7 @@ static const D3DSTENCILOP stencilOpToD3D9[] = { D3DSTENCILOP_DECR, }; -D3DFORMAT FormatToD3DFMT(DataFormat fmt) { +static D3DFORMAT FormatToD3DFMT(DataFormat fmt) { switch (fmt) { case DataFormat::R16_UNORM: return D3DFMT_L16; // closest match, should be a fine substitution if we ignore channels except R. case DataFormat::R8G8B8A8_UNORM: return D3DFMT_A8R8G8B8; diff --git a/Common/GPU/OpenGL/DataFormatGL.cpp b/Common/GPU/OpenGL/DataFormatGL.cpp index 16529d9f5a..67a4fdbc72 100644 --- a/Common/GPU/OpenGL/DataFormatGL.cpp +++ b/Common/GPU/OpenGL/DataFormatGL.cpp @@ -105,6 +105,18 @@ bool Thin3DFormatToGLFormatAndType(DataFormat fmt, GLuint &internalFormat, GLuin type = GL_FLOAT; alignment = 16; break; + case DataFormat::BC4_UNORM_BLOCK: + internalFormat = GL_COMPRESSED_RED_RGTC1; + format = GL_R; + type = GL_FLOAT; + alignment = 16; + break; + case DataFormat::BC5_UNORM_BLOCK: + internalFormat = GL_COMPRESSED_RG_RGTC2; + format = GL_RG; + type = GL_FLOAT; + alignment = 16; + break; case DataFormat::BC7_UNORM_BLOCK: internalFormat = GL_COMPRESSED_RGBA_BPTC_UNORM; format = GL_RGBA; diff --git a/Common/GPU/OpenGL/GLFeatures.cpp b/Common/GPU/OpenGL/GLFeatures.cpp index 96bc41a6e3..802ae1b28f 100644 --- a/Common/GPU/OpenGL/GLFeatures.cpp +++ b/Common/GPU/OpenGL/GLFeatures.cpp @@ -182,7 +182,9 @@ bool CheckGLExtensions() { gl_extensions.gpuVendor = GPU_VENDOR_IMGTEC; } else if (vendor == "Qualcomm") { gl_extensions.gpuVendor = GPU_VENDOR_QUALCOMM; - sscanf(renderer, "Adreno (TM) %d", &gl_extensions.modelNumber); + if (1 != sscanf(renderer, "Adreno (TM) %d", &gl_extensions.modelNumber)) { + gl_extensions.modelNumber = 300; // or what should we default to? + } } else if (vendor == "Broadcom") { gl_extensions.gpuVendor = GPU_VENDOR_BROADCOM; // Just for reference: Galaxy Y has renderer == "VideoCore IV HW" @@ -378,6 +380,12 @@ bool CheckGLExtensions() { gl_extensions.ARB_explicit_attrib_location = g_set_gl_extensions.count("GL_ARB_explicit_attrib_location") != 0; gl_extensions.ARB_texture_non_power_of_two = g_set_gl_extensions.count("GL_ARB_texture_non_power_of_two") != 0; gl_extensions.ARB_shader_stencil_export = g_set_gl_extensions.count("GL_ARB_shader_stencil_export") != 0; + gl_extensions.ARB_texture_compression_bptc = g_set_gl_extensions.count("GL_ARB_texture_compression_bptc") != 0; + gl_extensions.ARB_texture_compression_rgtc = g_set_gl_extensions.count("GL_ARB_texture_compression_rgtc") != 0; + gl_extensions.KHR_texture_compression_astc_ldr = g_set_gl_extensions.count("GL_KHR_texture_compression_astc_ldr") != 0; + gl_extensions.EXT_texture_compression_s3tc = g_set_gl_extensions.count("GL_EXT_texture_compression_s3tc") != 0; + gl_extensions.OES_texture_compression_astc = g_set_gl_extensions.count("GL_OES_texture_compression_astc") != 0; + if (gl_extensions.IsGLES) { gl_extensions.EXT_blend_func_extended = g_set_gl_extensions.count("GL_EXT_blend_func_extended") != 0; gl_extensions.OES_texture_npot = g_set_gl_extensions.count("GL_OES_texture_npot") != 0; @@ -575,6 +583,36 @@ bool CheckGLExtensions() { gl_extensions.EXT_clip_cull_distance = false; } + // Check the old query API. It doesn't seem to be very reliable (can miss stuff). + GLint numCompressedFormats = 0; + glGetIntegerv(GL_NUM_COMPRESSED_TEXTURE_FORMATS, &numCompressedFormats); + GLint *compressedFormats = new GLint[numCompressedFormats]; + if (numCompressedFormats > 0) { + glGetIntegerv(GL_COMPRESSED_TEXTURE_FORMATS, compressedFormats); + for (int i = 0; i < numCompressedFormats; i++) { + switch (compressedFormats[i]) { + case GL_COMPRESSED_RGB8_ETC2: gl_extensions.supportsETC2 = true; break; + case GL_COMPRESSED_RGBA_ASTC_4x4_KHR: gl_extensions.supportsASTC = true; break; + case GL_COMPRESSED_RGBA_S3TC_DXT5_EXT: gl_extensions.supportsBC123 = true; break; + case GL_COMPRESSED_RGBA_BPTC_UNORM: gl_extensions.supportsBC7 = true; break; + } + } + } + + // Enable additional formats based on extensions. + if (gl_extensions.EXT_texture_compression_s3tc) gl_extensions.supportsBC123 = true; + if (gl_extensions.ARB_texture_compression_bptc) gl_extensions.supportsBC7 = true; + if (gl_extensions.ARB_texture_compression_rgtc) gl_extensions.supportsBC45 = true; + if (gl_extensions.KHR_texture_compression_astc_ldr) gl_extensions.supportsASTC = true; + if (gl_extensions.OES_texture_compression_astc) gl_extensions.supportsASTC = true; + + // Now, disable known-emulated texture formats. + if (gl_extensions.gpuVendor == GPU_VENDOR_NVIDIA && !gl_extensions.IsGLES) { + gl_extensions.supportsETC2 = false; + gl_extensions.supportsASTC = false; + } + delete[] compressedFormats; + ProcessGPUFeatures(); int error = glGetError(); diff --git a/Common/GPU/OpenGL/GLFeatures.h b/Common/GPU/OpenGL/GLFeatures.h index fe72d037b2..04df20f87f 100644 --- a/Common/GPU/OpenGL/GLFeatures.h +++ b/Common/GPU/OpenGL/GLFeatures.h @@ -52,6 +52,7 @@ struct GLExtensions { bool OES_copy_image; bool OES_texture_float; bool OES_texture_3D; + bool OES_texture_compression_astc; // ARB bool ARB_framebuffer_object; @@ -73,8 +74,14 @@ struct GLExtensions { bool ARB_texture_non_power_of_two; bool ARB_stencil_texturing; bool ARB_shader_stencil_export; + bool ARB_texture_compression_bptc; + bool ARB_texture_compression_rgtc; + + // KHR + bool KHR_texture_compression_astc_ldr; // EXT + bool EXT_texture_compression_s3tc; bool EXT_swap_control_tear; bool EXT_discard_framebuffer; bool EXT_unpack_subimage; // always supported on desktop and ES3 @@ -115,6 +122,12 @@ struct GLExtensions { int maxVertexTextureUnits; + bool supportsETC2; + bool supportsBC123; + bool supportsBC45; + bool supportsBC7; + bool supportsASTC; + // greater-or-equal than bool VersionGEThan(int major, int minor, int sub = 0); int GLSLVersion(); diff --git a/Common/GPU/OpenGL/thin3d_gl.cpp b/Common/GPU/OpenGL/thin3d_gl.cpp index 5cb85ac9c7..0f04ee0415 100644 --- a/Common/GPU/OpenGL/thin3d_gl.cpp +++ b/Common/GPU/OpenGL/thin3d_gl.cpp @@ -1556,7 +1556,23 @@ uint32_t OpenGLContext::GetDataFormatSupport(DataFormat fmt) const { case DataFormat::BC1_RGBA_UNORM_BLOCK: case DataFormat::BC2_UNORM_BLOCK: case DataFormat::BC3_UNORM_BLOCK: - return FMT_TEXTURE; + return gl_extensions.supportsBC123 ? FMT_TEXTURE : 0; + + case DataFormat::BC4_UNORM_BLOCK: + case DataFormat::BC5_UNORM_BLOCK: + return gl_extensions.supportsBC45 ? FMT_TEXTURE : 0; + + case DataFormat::BC7_UNORM_BLOCK: + return gl_extensions.supportsBC7 ? FMT_TEXTURE : 0; + + case DataFormat::ASTC_4x4_UNORM_BLOCK: + return gl_extensions.supportsASTC ? FMT_TEXTURE : 0; + + case DataFormat::ETC2_R8G8B8_UNORM_BLOCK: + case DataFormat::ETC2_R8G8B8A1_UNORM_BLOCK: + case DataFormat::ETC2_R8G8B8A8_UNORM_BLOCK: + return gl_extensions.supportsETC2 ? FMT_TEXTURE : 0; + default: return 0; } diff --git a/UI/DevScreens.cpp b/UI/DevScreens.cpp index 82cb3c159e..f54480ef51 100644 --- a/UI/DevScreens.cpp +++ b/UI/DevScreens.cpp @@ -554,6 +554,16 @@ void SystemInfoScreen::CreateViews() { } } deviceSpecs->Add(new InfoItem(si->T("Depth buffer format"), DataFormatToString(draw->GetDeviceCaps().preferredDepthBufferFormat))); + + std::string texCompressionFormats; + // Simple non-detailed summary of supported tex compression formats. + if (draw->GetDataFormatSupport(Draw::DataFormat::ETC2_R8G8B8_UNORM_BLOCK)) texCompressionFormats += "ETC2 "; + if (draw->GetDataFormatSupport(Draw::DataFormat::ASTC_4x4_UNORM_BLOCK)) texCompressionFormats += "ASTC "; + if (draw->GetDataFormatSupport(Draw::DataFormat::BC1_RGBA_UNORM_BLOCK)) texCompressionFormats += "BC1,2,3 "; + if (draw->GetDataFormatSupport(Draw::DataFormat::BC4_UNORM_BLOCK)) texCompressionFormats += "BC4,5 "; + if (draw->GetDataFormatSupport(Draw::DataFormat::BC7_UNORM_BLOCK)) texCompressionFormats += "BC7 "; + deviceSpecs->Add(new InfoItem(si->T("Compressed texture formats"), texCompressionFormats)); + deviceSpecs->Add(new ItemHeader(si->T("OS Information"))); deviceSpecs->Add(new InfoItem(si->T("Memory Page Size"), StringFromFormat(si->T("%d bytes"), GetMemoryProtectPageSize()))); deviceSpecs->Add(new InfoItem(si->T("RW/RX exclusive"), PlatformIsWXExclusive() ? di->T("Active") : di->T("Inactive")));