diff --git a/impeller/renderer/backend/gles/blit_command_gles.cc b/impeller/renderer/backend/gles/blit_command_gles.cc index d6e56b6996081..5fbfc802e5f9c 100644 --- a/impeller/renderer/backend/gles/blit_command_gles.cc +++ b/impeller/renderer/backend/gles/blit_command_gles.cc @@ -41,7 +41,7 @@ static std::optional ConfigureFBO( gl.BindFramebuffer(fbo_type, fbo); if (!TextureGLES::Cast(*texture).SetAsFramebufferAttachment( - fbo_type, fbo, TextureGLES::AttachmentPoint::kColor0)) { + fbo_type, TextureGLES::AttachmentPoint::kColor0)) { VALIDATION_LOG << "Could not attach texture to framebuffer."; DeleteFBO(gl, fbo, fbo_type); return std::nullopt; diff --git a/impeller/renderer/backend/gles/capabilities_gles.cc b/impeller/renderer/backend/gles/capabilities_gles.cc index 37bd3e665d90d..638069fc30721 100644 --- a/impeller/renderer/backend/gles/capabilities_gles.cc +++ b/impeller/renderer/backend/gles/capabilities_gles.cc @@ -106,6 +106,17 @@ CapabilitiesGLES::CapabilitiesGLES(const ProcTableGLES& gl) { gl.GetDescription()->HasExtension(kOESTextureBorderClampExt)) { supports_decal_sampler_address_mode_ = true; } + + if (gl.GetDescription()->HasExtension( + "GL_EXT_multisampled_render_to_texture")) { + supports_offscreen_msaa_ = true; + + // We hard-code 4x MSAA for now, so let's make sure it's supported. + GLint value = 0; + gl.GetIntegerv(GL_MAX_SAMPLES, &value); + FML_DCHECK(value == 4) << "Unexpected max samples: " << value << ". " + << "Only 4x MSAA is currently supported."; + } } size_t CapabilitiesGLES::GetMaxTextureUnits(ShaderStage stage) const { @@ -124,7 +135,7 @@ size_t CapabilitiesGLES::GetMaxTextureUnits(ShaderStage stage) const { } bool CapabilitiesGLES::SupportsOffscreenMSAA() const { - return false; + return supports_offscreen_msaa_; } bool CapabilitiesGLES::SupportsSSBO() const { diff --git a/impeller/renderer/backend/gles/capabilities_gles.h b/impeller/renderer/backend/gles/capabilities_gles.h index 3bcd0cfd85d27..edb9a1b33bb41 100644 --- a/impeller/renderer/backend/gles/capabilities_gles.h +++ b/impeller/renderer/backend/gles/capabilities_gles.h @@ -118,6 +118,7 @@ class CapabilitiesGLES final private: bool supports_framebuffer_fetch_ = false; bool supports_decal_sampler_address_mode_ = false; + bool supports_offscreen_msaa_ = false; }; } // namespace impeller diff --git a/impeller/renderer/backend/gles/render_pass_gles.cc b/impeller/renderer/backend/gles/render_pass_gles.cc index 4816a2973b0da..02356fdd58748 100644 --- a/impeller/renderer/backend/gles/render_pass_gles.cc +++ b/impeller/renderer/backend/gles/render_pass_gles.cc @@ -176,19 +176,19 @@ struct RenderPassData { if (auto color = TextureGLES::Cast(pass_data.color_attachment.get())) { if (!color->SetAsFramebufferAttachment( - GL_FRAMEBUFFER, fbo, TextureGLES::AttachmentPoint::kColor0)) { + GL_FRAMEBUFFER, TextureGLES::AttachmentPoint::kColor0)) { return false; } } if (auto depth = TextureGLES::Cast(pass_data.depth_attachment.get())) { if (!depth->SetAsFramebufferAttachment( - GL_FRAMEBUFFER, fbo, TextureGLES::AttachmentPoint::kDepth)) { + GL_FRAMEBUFFER, TextureGLES::AttachmentPoint::kDepth)) { return false; } } if (auto stencil = TextureGLES::Cast(pass_data.stencil_attachment.get())) { if (!stencil->SetAsFramebufferAttachment( - GL_FRAMEBUFFER, fbo, TextureGLES::AttachmentPoint::kStencil)) { + GL_FRAMEBUFFER, TextureGLES::AttachmentPoint::kStencil)) { return false; } } diff --git a/impeller/renderer/backend/gles/texture_gles.cc b/impeller/renderer/backend/gles/texture_gles.cc index 1ea904c602f0a..2cfe0e8cd9540 100644 --- a/impeller/renderer/backend/gles/texture_gles.cc +++ b/impeller/renderer/backend/gles/texture_gles.cc @@ -22,7 +22,11 @@ static TextureGLES::Type GetTextureTypeFromDescriptor( const auto render_target = static_cast(TextureUsage::kRenderTarget); if (usage == render_target) { - return TextureGLES::Type::kRenderBuffer; + if (desc.sample_count == SampleCount::kCount1) { + return TextureGLES::Type::kRenderBuffer; + } else { + return TextureGLES::Type::kRenderBufferMultisampled; + } } return TextureGLES::Type::kTexture; } @@ -382,7 +386,6 @@ void TextureGLES::InitializeContentsIfNecessary() const { nullptr // data ); } - } break; case Type::kRenderBuffer: { auto render_buffer_format = @@ -402,6 +405,27 @@ void TextureGLES::InitializeContentsIfNecessary() const { } } break; case Type::kRenderBufferMultisampled: { + gl.BindTexture(GL_TEXTURE_2D, handle.value()); + { + TRACE_EVENT0("impeller", "TexImage2DInitialization"); + TexImage2DData tex_data(GetTextureDescriptor().format); + // TODO: Remove this before submitting. + FML_LOG(ERROR) << "*** " << __PRETTY_FUNCTION__ + << " size_w=" << size.width << " h=" << size.height + << " iformat=" << tex_data.internal_format + << " eformat=" << tex_data.external_format; + // https://github.com/flutter/engine/blob/main/impeller/renderer/backend/gles/texture_gles.cc#L96 + gl.TexImage2D(GL_TEXTURE_2D, // target + 0u, // LOD level (base mip level size checked) + tex_data.internal_format, // internal format + size.width, // width + size.height, // height + 0u, // border + tex_data.external_format, // format + tex_data.type, // type + nullptr // data + ); + } auto render_buffer_msaa = ToRenderBufferFormat(GetTextureDescriptor().format); if (!render_buffer_msaa.has_value()) { @@ -506,7 +530,6 @@ static GLenum ToAttachmentPoint(TextureGLES::AttachmentPoint point) { } bool TextureGLES::SetAsFramebufferAttachment(GLenum target, - GLuint fbo, AttachmentPoint point) const { if (!IsValid()) { return false; diff --git a/impeller/renderer/backend/gles/texture_gles.h b/impeller/renderer/backend/gles/texture_gles.h index effee19d80fbd..7f5cb90e4d00b 100644 --- a/impeller/renderer/backend/gles/texture_gles.h +++ b/impeller/renderer/backend/gles/texture_gles.h @@ -46,7 +46,6 @@ class TextureGLES final : public Texture, kStencil, }; [[nodiscard]] bool SetAsFramebufferAttachment(GLenum target, - GLuint fbo, AttachmentPoint point) const; Type GetType() const;