diff --git a/impeller/aiks/canvas.cc b/impeller/aiks/canvas.cc index f50dd36af7ad9..ae4c9d512037f 100644 --- a/impeller/aiks/canvas.cc +++ b/impeller/aiks/canvas.cc @@ -64,7 +64,7 @@ void Canvas::Save(bool create_subpass, entry.cull_rect = xformation_stack_.back().cull_rect; entry.stencil_depth = xformation_stack_.back().stencil_depth; if (create_subpass) { - entry.is_subpass = true; + entry.rendering_mode = Entity::RenderingMode::kSubpass; auto subpass = std::make_unique(); subpass->SetEnableOffscreenCheckerboard( debug_options.offscreen_texture_checkerboard); @@ -72,10 +72,10 @@ void Canvas::Save(bool create_subpass, EntityPass::BackdropFilterProc backdrop_filter_proc = [backdrop_filter = backdrop_filter->Clone()]( const FilterInput::Ref& input, const Matrix& effect_transform, - bool is_subpass) { + Entity::RenderingMode rendering_mode) { auto filter = backdrop_filter->WrapInput(input); filter->SetEffectTransform(effect_transform); - filter->SetIsForSubpass(is_subpass); + filter->SetRenderingMode(rendering_mode); return filter; }; subpass->SetBackdropFilter(backdrop_filter_proc); @@ -93,7 +93,8 @@ bool Canvas::Restore() { if (xformation_stack_.size() == 1) { return false; } - if (xformation_stack_.back().is_subpass) { + if (xformation_stack_.back().rendering_mode == + Entity::RenderingMode::kSubpass) { current_pass_ = GetCurrentPass().GetSuperpass(); FML_DCHECK(current_pass_); } diff --git a/impeller/aiks/canvas.h b/impeller/aiks/canvas.h index 0ea187c39a5ad..a7a5652229b03 100644 --- a/impeller/aiks/canvas.h +++ b/impeller/aiks/canvas.h @@ -35,7 +35,7 @@ struct CanvasStackEntry { // |cull_rect| is conservative screen-space bounds of the clipped output area std::optional cull_rect; size_t stencil_depth = 0u; - bool is_subpass = false; + Entity::RenderingMode rendering_mode = Entity::RenderingMode::kDirect; bool contains_clips = false; }; diff --git a/impeller/aiks/paint.cc b/impeller/aiks/paint.cc index 5c2b808c69eb3..9b9b713c90014 100644 --- a/impeller/aiks/paint.cc +++ b/impeller/aiks/paint.cc @@ -60,7 +60,8 @@ std::shared_ptr Paint::WithFilters( std::shared_ptr input) const { input = WithColorFilter(input, /*absorb_opacity=*/true); input = WithInvertFilter(input); - auto image_filter = WithImageFilter(input, Matrix(), /*is_subpass=*/false); + auto image_filter = + WithImageFilter(input, Matrix(), Entity::RenderingMode::kDirect); if (image_filter) { input = image_filter; } @@ -71,7 +72,7 @@ std::shared_ptr Paint::WithFiltersForSubpassTarget( std::shared_ptr input, const Matrix& effect_transform) const { auto image_filter = - WithImageFilter(input, effect_transform, /*is_subpass=*/true); + WithImageFilter(input, effect_transform, Entity::RenderingMode::kSubpass); if (image_filter) { input = image_filter; } @@ -91,12 +92,12 @@ std::shared_ptr Paint::WithMaskBlur(std::shared_ptr input, std::shared_ptr Paint::WithImageFilter( const FilterInput::Variant& input, const Matrix& effect_transform, - bool is_subpass) const { + Entity::RenderingMode rendering_mode) const { if (!image_filter) { return nullptr; } auto filter = image_filter->WrapInput(FilterInput::Make(input)); - filter->SetIsForSubpass(is_subpass); + filter->SetRenderingMode(rendering_mode); filter->SetEffectTransform(effect_transform); return filter; } diff --git a/impeller/aiks/paint.h b/impeller/aiks/paint.h index 384b4bdb1f150..741044b3e4d7e 100644 --- a/impeller/aiks/paint.h +++ b/impeller/aiks/paint.h @@ -26,7 +26,7 @@ struct Paint { using ImageFilterProc = std::function( FilterInput::Ref, const Matrix& effect_transform, - bool is_subpass)>; + Entity::RenderingMode rendering_mode)>; using MaskFilterProc = std::function( FilterInput::Ref, bool is_solid_color, @@ -101,7 +101,7 @@ struct Paint { std::shared_ptr WithImageFilter( const FilterInput::Variant& input, const Matrix& effect_transform, - bool is_subpass) const; + Entity::RenderingMode rendering_mode) const; private: std::shared_ptr WithColorFilter(std::shared_ptr input, diff --git a/impeller/aiks/paint_pass_delegate.cc b/impeller/aiks/paint_pass_delegate.cc index 6a72338028d5a..f9a081a0b55cf 100644 --- a/impeller/aiks/paint_pass_delegate.cc +++ b/impeller/aiks/paint_pass_delegate.cc @@ -51,7 +51,8 @@ std::shared_ptr PaintPassDelegate::CreateContentsForSubpassTarget( std::shared_ptr PaintPassDelegate::WithImageFilter( const FilterInput::Variant& input, const Matrix& effect_transform) const { - return paint_.WithImageFilter(input, effect_transform, true); + return paint_.WithImageFilter(input, effect_transform, + Entity::RenderingMode::kSubpass); } /// OpacityPeepholePassDelegate @@ -151,7 +152,8 @@ OpacityPeepholePassDelegate::CreateContentsForSubpassTarget( std::shared_ptr OpacityPeepholePassDelegate::WithImageFilter( const FilterInput::Variant& input, const Matrix& effect_transform) const { - return paint_.WithImageFilter(input, effect_transform, true); + return paint_.WithImageFilter(input, effect_transform, + Entity::RenderingMode::kSubpass); } } // namespace impeller diff --git a/impeller/entity/contents/filters/filter_contents.cc b/impeller/entity/contents/filters/filter_contents.cc index 3d4fa96a6321b..57653b10b739f 100644 --- a/impeller/entity/contents/filters/filter_contents.cc +++ b/impeller/entity/contents/filters/filter_contents.cc @@ -298,9 +298,9 @@ void FilterContents::SetLeafInputs(const FilterInput::Vector& inputs) { } } -void FilterContents::SetIsForSubpass(bool is_subpass) { +void FilterContents::SetRenderingMode(Entity::RenderingMode rendering_mode) { for (auto& input : inputs_) { - input->SetIsForSubpass(is_subpass); + input->SetRenderingMode(rendering_mode); } } diff --git a/impeller/entity/contents/filters/filter_contents.h b/impeller/entity/contents/filters/filter_contents.h index c14393444980c..fb1c6b59f1cb3 100644 --- a/impeller/entity/contents/filters/filter_contents.h +++ b/impeller/entity/contents/filters/filter_contents.h @@ -157,7 +157,7 @@ class FilterContents : public Contents { /// that the current transformation matrix of the entity is not stored /// in the Entity transformation matrix. Instead, the effect transform /// is used in this case. - virtual void SetIsForSubpass(bool is_subpass); + virtual void SetRenderingMode(Entity::RenderingMode rendering_mode); private: virtual std::optional GetFilterCoverage( diff --git a/impeller/entity/contents/filters/inputs/filter_contents_filter_input.cc b/impeller/entity/contents/filters/inputs/filter_contents_filter_input.cc index 78a1cec98e3b2..3e43132c1320d 100644 --- a/impeller/entity/contents/filters/inputs/filter_contents_filter_input.cc +++ b/impeller/entity/contents/filters/inputs/filter_contents_filter_input.cc @@ -75,8 +75,9 @@ void FilterContentsFilterInput::SetEffectTransform(const Matrix& matrix) { filter_->SetEffectTransform(matrix); } -void FilterContentsFilterInput::SetIsForSubpass(bool is_for_subpass) { - filter_->SetIsForSubpass(is_for_subpass); +void FilterContentsFilterInput::SetRenderingMode( + Entity::RenderingMode rendering_mode) { + filter_->SetRenderingMode(rendering_mode); } } // namespace impeller diff --git a/impeller/entity/contents/filters/inputs/filter_contents_filter_input.h b/impeller/entity/contents/filters/inputs/filter_contents_filter_input.h index 45d44993520cf..e21cb7acc451c 100644 --- a/impeller/entity/contents/filters/inputs/filter_contents_filter_input.h +++ b/impeller/entity/contents/filters/inputs/filter_contents_filter_input.h @@ -49,7 +49,7 @@ class FilterContentsFilterInput final : public FilterInput { virtual void SetEffectTransform(const Matrix& matrix) override; // |FilterInput| - virtual void SetIsForSubpass(bool is_for_subpass) override; + virtual void SetRenderingMode(Entity::RenderingMode rendering_mode) override; private: explicit FilterContentsFilterInput(std::shared_ptr filter); diff --git a/impeller/entity/contents/filters/inputs/filter_input.cc b/impeller/entity/contents/filters/inputs/filter_input.cc index e438212688a44..b3ecc69895b92 100644 --- a/impeller/entity/contents/filters/inputs/filter_input.cc +++ b/impeller/entity/contents/filters/inputs/filter_input.cc @@ -88,6 +88,6 @@ void FilterInput::SetLeafInputs(const FilterInput::Vector& inputs) {} void FilterInput::SetEffectTransform(const Matrix& matrix) {} -void FilterInput::SetIsForSubpass(bool is_for_subpass) {} +void FilterInput::SetRenderingMode(Entity::RenderingMode rendering_mode) {} } // namespace impeller diff --git a/impeller/entity/contents/filters/inputs/filter_input.h b/impeller/entity/contents/filters/inputs/filter_input.h index 43db41eb6a8ef..955932885ea07 100644 --- a/impeller/entity/contents/filters/inputs/filter_input.h +++ b/impeller/entity/contents/filters/inputs/filter_input.h @@ -85,7 +85,7 @@ class FilterInput { virtual void SetEffectTransform(const Matrix& matrix); /// @brief Turns on subpass mode for filter inputs. - virtual void SetIsForSubpass(bool is_for_subpass); + virtual void SetRenderingMode(Entity::RenderingMode rendering_mode); }; } // namespace impeller diff --git a/impeller/entity/contents/filters/matrix_filter_contents.cc b/impeller/entity/contents/filters/matrix_filter_contents.cc index c767ffe6cd19f..612e2e7b43eda 100644 --- a/impeller/entity/contents/filters/matrix_filter_contents.cc +++ b/impeller/entity/contents/filters/matrix_filter_contents.cc @@ -14,9 +14,10 @@ void MatrixFilterContents::SetMatrix(Matrix matrix) { matrix_ = matrix; } -void MatrixFilterContents::SetIsForSubpass(bool is_subpass) { - is_for_subpass_ = is_subpass; - FilterContents::SetIsForSubpass(is_subpass); +void MatrixFilterContents::SetRenderingMode( + Entity::RenderingMode rendering_mode) { + rendering_mode_ = rendering_mode; + FilterContents::SetRenderingMode(rendering_mode); } bool MatrixFilterContents::IsTranslationOnly() const { @@ -54,8 +55,9 @@ std::optional MatrixFilterContents::RenderFilter( // mentioned above). And so we sneak the subpass's captured CTM in through the // effect transform. - auto transform = - is_for_subpass_ ? effect_transform : entity.GetTransformation(); + auto transform = rendering_mode_ == Entity::RenderingMode::kSubpass + ? effect_transform + : entity.GetTransformation(); snapshot->transform = transform * // matrix_ * // transform.Invert() * // @@ -78,8 +80,9 @@ std::optional MatrixFilterContents::GetFilterCoverage( if (!coverage.has_value()) { return std::nullopt; } - auto& m = - is_for_subpass_ ? effect_transform : inputs[0]->GetTransform(entity); + auto& m = rendering_mode_ == Entity::RenderingMode::kSubpass + ? effect_transform + : inputs[0]->GetTransform(entity); auto transform = m * // matrix_ * // m.Invert(); // diff --git a/impeller/entity/contents/filters/matrix_filter_contents.h b/impeller/entity/contents/filters/matrix_filter_contents.h index ea221301d8e33..9f2cb9d0d1774 100644 --- a/impeller/entity/contents/filters/matrix_filter_contents.h +++ b/impeller/entity/contents/filters/matrix_filter_contents.h @@ -18,7 +18,7 @@ class MatrixFilterContents final : public FilterContents { void SetMatrix(Matrix matrix); // |FilterContents| - void SetIsForSubpass(bool is_for_subpass) override; + void SetRenderingMode(Entity::RenderingMode rendering_mode) override; // |FilterContents| bool IsTranslationOnly() const override; @@ -43,7 +43,7 @@ class MatrixFilterContents final : public FilterContents { Matrix matrix_; SamplerDescriptor sampler_descriptor_ = {}; - bool is_for_subpass_ = false; + Entity::RenderingMode rendering_mode_ = Entity::RenderingMode::kDirect; FML_DISALLOW_COPY_AND_ASSIGN(MatrixFilterContents); }; diff --git a/impeller/entity/entity.h b/impeller/entity/entity.h index 929824fbf5354..8cbcfaa9440b7 100644 --- a/impeller/entity/entity.h +++ b/impeller/entity/entity.h @@ -23,6 +23,17 @@ class Entity { static constexpr BlendMode kLastPipelineBlendMode = BlendMode::kModulate; static constexpr BlendMode kLastAdvancedBlendMode = BlendMode::kLuminosity; + enum class RenderingMode { + /// In direct mode, the Entity's transform is used as the current + /// local-to-screen transformation matrix. + kDirect, + /// In subpass mode, the Entity passed through the filter is in screen space + /// rather than local space, and so some filters (namely, + /// MatrixFilterContents) need to interpret the given EffectTransform as the + /// current transformation matrix. + kSubpass, + }; + /// An enum to define how to repeat, fold, or omit colors outside of the /// typically defined range of the source of the colors (such as the /// bounds of an image or the defining geometry of a gradient). diff --git a/impeller/entity/entity_pass.cc b/impeller/entity/entity_pass.cc index b93d997d468d2..6b4017ad0a19c 100644 --- a/impeller/entity/entity_pass.cc +++ b/impeller/entity/entity_pass.cc @@ -530,9 +530,9 @@ EntityPass::EntityResult EntityPass::GetEntityForElement( auto texture = pass_context.GetTexture(); // Render the backdrop texture before any of the pass elements. const auto& proc = subpass->backdrop_filter_proc_; - subpass_backdrop_filter_contents = proc( - FilterInput::Make(std::move(texture)), subpass->xformation_.Basis(), - /*is_subpass*/ true); + subpass_backdrop_filter_contents = + proc(FilterInput::Make(std::move(texture)), + subpass->xformation_.Basis(), Entity::RenderingMode::kSubpass); // The subpass will need to read from the current pass texture when // rendering the backdrop, so if there's an active pass, end it prior to diff --git a/impeller/entity/entity_pass.h b/impeller/entity/entity_pass.h index f00c9d3653978..d09649abfd9d0 100644 --- a/impeller/entity/entity_pass.h +++ b/impeller/entity/entity_pass.h @@ -41,7 +41,7 @@ class EntityPass { using BackdropFilterProc = std::function( FilterInput::Ref, const Matrix& effect_transform, - bool is_subpass)>; + Entity::RenderingMode rendering_mode)>; struct StencilCoverageLayer { std::optional coverage;