From 5e676b338b8f5c343ce4f68fe48ad370cecda710 Mon Sep 17 00:00:00 2001 From: Swung0x48 Date: Sun, 26 Jul 2026 13:28:30 -0400 Subject: [PATCH] [Fix] (DirectVulkan): back legacy low-bit formats (RGB565/RGB5A1/RGBA4/R3G3B2/RGB4/RGBA2/RGB10/12) with their UNorm8/16 canonical shadow layouts and add capability fallbacks - they mapped to VK_FORMAT_UNDEFINED and crashed or wedged the GPU on upload; also admit 2DMSArray/CubeMap/3D color attachment targets in the render pass --- .../DirectVulkan/BackendObject_DirectVulkan.cpp | 14 ++++++++++++++ .../Renderer/VkRenderPassManager.cpp | 4 ++++ .../DirectVulkan/Renderer/VkTextureManager.cpp | 16 ++++++++++++++++ 3 files changed, 34 insertions(+) diff --git a/MobileGL/MG_Backend/DirectVulkan/BackendObject_DirectVulkan.cpp b/MobileGL/MG_Backend/DirectVulkan/BackendObject_DirectVulkan.cpp index a10ee89a..686ba19b 100644 --- a/MobileGL/MG_Backend/DirectVulkan/BackendObject_DirectVulkan.cpp +++ b/MobileGL/MG_Backend/DirectVulkan/BackendObject_DirectVulkan.cpp @@ -140,6 +140,20 @@ namespace MobileGL::MG_Backend::DirectVulkan { case TextureInternalFormat::RGB: case TextureInternalFormat::RGB8: return TextureInternalFormat::RGBA8; + // Legacy low-bit-depth formats with no (or rarely supported) native Vulkan + // encoding; a wider normalized fallback keeps at least the required precision. + case TextureInternalFormat::R3G3B2: + case TextureInternalFormat::RGB4: + case TextureInternalFormat::RGB5: + case TextureInternalFormat::RGBA2: + case TextureInternalFormat::RGBA4: + case TextureInternalFormat::RGB5A1: + return TextureInternalFormat::RGBA8; + case TextureInternalFormat::RGB10: + return TextureInternalFormat::RGB10A2; + case TextureInternalFormat::RGB12: + case TextureInternalFormat::RGBA12: + return TextureInternalFormat::RGBA16; case TextureInternalFormat::SRGB8: return TextureInternalFormat::SRGB8Alpha8; case TextureInternalFormat::RGB8Snorm: diff --git a/MobileGL/MG_Backend/DirectVulkan/Renderer/VkRenderPassManager.cpp b/MobileGL/MG_Backend/DirectVulkan/Renderer/VkRenderPassManager.cpp index 99b276cb..fcf09ddc 100644 --- a/MobileGL/MG_Backend/DirectVulkan/Renderer/VkRenderPassManager.cpp +++ b/MobileGL/MG_Backend/DirectVulkan/Renderer/VkRenderPassManager.cpp @@ -791,6 +791,10 @@ namespace MobileGL::MG_Backend::DirectVulkan { case TextureTarget::Texture2D: case TextureTarget::Texture2DArray: case TextureTarget::Texture2DMultisample: + case TextureTarget::Texture2DMultisampleArray: + case TextureTarget::Texture3D: + case TextureTarget::TextureCubeMap: + case TextureTarget::TextureCubeMapArray: case TextureTarget::TextureRectangle: { desc.flags = 0; desc.format = isDefaultFbo ? diff --git a/MobileGL/MG_Backend/DirectVulkan/Renderer/VkTextureManager.cpp b/MobileGL/MG_Backend/DirectVulkan/Renderer/VkTextureManager.cpp index 2b52e333..8cb2dad9 100644 --- a/MobileGL/MG_Backend/DirectVulkan/Renderer/VkTextureManager.cpp +++ b/MobileGL/MG_Backend/DirectVulkan/Renderer/VkTextureManager.cpp @@ -375,7 +375,23 @@ namespace MobileGL::MG_Backend::DirectVulkan { switch (format) { case TextureInternalFormat::RGB: case TextureInternalFormat::RGB8: + // Legacy low-bit RGB formats share the UNorm8 canonical shadow layout (see + // TextureFormatProcessor), so they upload exactly like RGB8 with an alpha expand. + case TextureInternalFormat::R3G3B2: + case TextureInternalFormat::RGB4: + case TextureInternalFormat::RGB5: return {VK_FORMAT_R8G8B8A8_UNORM, true, 1, {0xFF, 0x00, 0x00, 0x00}}; + // Low-bit RGBA formats: UNorm8x4 canonical shadow, no expansion needed. + case TextureInternalFormat::RGBA2: + case TextureInternalFormat::RGBA4: + case TextureInternalFormat::RGB5A1: + return {VK_FORMAT_R8G8B8A8_UNORM, false, 0, {0, 0, 0, 0}}; + // 10/12-bit RGB(A): UNorm16 canonical shadow. + case TextureInternalFormat::RGB10: + case TextureInternalFormat::RGB12: + return {VK_FORMAT_R16G16B16A16_UNORM, true, 2, {0xFF, 0xFF, 0x00, 0x00}}; + case TextureInternalFormat::RGBA12: + return {VK_FORMAT_R16G16B16A16_UNORM, false, 0, {0, 0, 0, 0}}; case TextureInternalFormat::SRGB8: return {VK_FORMAT_R8G8B8A8_SRGB, true, 1, {0xFF, 0x00, 0x00, 0x00}}; case TextureInternalFormat::RGB8Snorm: