mirror of
https://github.com/MobileGL-Dev/MobileGL
synced 2026-09-08 20:28:32 +09:00
[Fix] (DirectGLES): report the alpha added by the multisample widening as ONE
A three-channel format widened to four for a multisample target gains an alpha channel the application never asked for, and it holds whatever the draw that filled the texture happened to write there. GL says a format without alpha reads back as 1.0, so KHR-GL33.texture_swizzle - which fills such a texture by rendering vec4(r, g, b, 0.0) and then swizzles red from alpha - read 0 where it expected the maximum. Fold ONE into the texture's swizzle for exactly those textures, composed with the swizzle the application set, so the promotion stays invisible.
This commit is contained in:
@@ -2405,7 +2405,19 @@ namespace MobileGL::MG_Backend::DirectGLES {
|
||||
MGLOG_D("%s(%s:%d) ES error %s", func, file, line, MG_Util::ConvertGLEnumToString(err).c_str());
|
||||
});
|
||||
|
||||
const auto& swizzleParams = stateTextureObject->GetAllSwizzleParams();
|
||||
// A three-channel format widened to four for a multisample target (see
|
||||
// NormalizePixelFormat) gains an alpha channel the frontend format does not have, and
|
||||
// whatever the draw that filled it wrote there is not what GL would report: a format
|
||||
// without alpha reads back as 1.0. Answer the ALPHA swizzle source with ONE so the
|
||||
// promotion stays invisible, composed with the swizzle the application asked for.
|
||||
Vec4<TextureSwizzleParam> swizzleParams = stateTextureObject->GetAllSwizzleParams();
|
||||
if (TextureImpl::BackendTextureFormatAddsAlpha(stateTextureObject->GetFormat(), targetInternal)) {
|
||||
for (SizeT channel = 0; channel < 4; ++channel) {
|
||||
if (swizzleParams[channel] == TextureSwizzleParam::Alpha) {
|
||||
swizzleParams[channel] = TextureSwizzleParam::One;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (swizzleParams != m_cacheSwizzleParams) {
|
||||
#define SYNC_TEX_SWIZZLE_PARAM_IF_CHANGED(func, glEnum) \
|
||||
if (m_cacheSwizzleParams.func != swizzleParams.func) { \
|
||||
|
||||
@@ -177,6 +177,22 @@ namespace MobileGL::MG_Backend::DirectGLES {
|
||||
Bool ShouldUseCaveatRenderbufferFormat(TextureInternalFormat internalFormat) {
|
||||
return ShouldUseCaveatFormat(internalFormat, GetRenderbufferFormatCapabilityTargetIndex());
|
||||
}
|
||||
|
||||
Bool BackendTextureFormatAddsAlpha(TextureInternalFormat internalFormat, TextureTarget target) {
|
||||
const SizeT targetIndex =
|
||||
target == TextureTarget::Unknown ? kFormatCapabilityTargetCount : GetFormatCapabilityTargetIndex(target);
|
||||
if (!TargetRequiresRenderableFormat(targetIndex)) {
|
||||
return false;
|
||||
}
|
||||
if (pActiveBackendObject && !ShouldUseCaveatFormat(internalFormat, targetIndex)) {
|
||||
return false;
|
||||
}
|
||||
const GLenum requestedInternalFormat = MG_Util::ConvertTextureInternalFormatToGLEnum(internalFormat);
|
||||
const Flags<PixelFormatNormalizeOptionBit> options =
|
||||
GetRuntimeFallbackNormalizeOptions(requestedInternalFormat,
|
||||
GetRenderTargetNormalizeOptions(targetIndex));
|
||||
return static_cast<Bool>(options & PixelFormatNormalizeOptionBit::NoThreeChannelRenderTarget);
|
||||
}
|
||||
} // namespace TextureImpl
|
||||
namespace PrgramImpl {
|
||||
String ProcessOutColorLocations(const String& glslCode) {
|
||||
|
||||
@@ -40,6 +40,11 @@ namespace MobileGL::MG_Backend::DirectGLES {
|
||||
void GenerateRenderbufferFormatInfo(TextureInternalFormat internalFormat, GLenum* outInternalFormat,
|
||||
GLenum* outFormat, GLenum* outType);
|
||||
Bool ShouldUseCaveatTextureFormat(TextureInternalFormat internalFormat, TextureTarget target);
|
||||
|
||||
// True when the format the texture is actually created with has an alpha channel the
|
||||
// frontend format does not (the three-channel multisample widening). GL reads such a
|
||||
// channel back as 1.0, so any swizzle source of ALPHA has to be answered with ONE.
|
||||
Bool BackendTextureFormatAddsAlpha(TextureInternalFormat internalFormat, TextureTarget target);
|
||||
Bool ShouldUseCaveatRenderbufferFormat(TextureInternalFormat internalFormat);
|
||||
} // namespace TextureImpl
|
||||
|
||||
|
||||
Reference in New Issue
Block a user