From 3eabf8bec29a831a0ae21980e88bb9fc1feb7e21 Mon Sep 17 00:00:00 2001 From: Aaron Clarke Date: Wed, 28 Feb 2024 14:59:54 -0800 Subject: [PATCH 1/5] [Impeller] implemented solid blur style --- impeller/aiks/aiks_blur_unittests.cc | 28 ++++++++++ .../filters/gaussian_blur_filter_contents.cc | 55 ++++++++++--------- 2 files changed, 58 insertions(+), 25 deletions(-) diff --git a/impeller/aiks/aiks_blur_unittests.cc b/impeller/aiks/aiks_blur_unittests.cc index 90492e95c8875..d6ad5ebe41884 100644 --- a/impeller/aiks/aiks_blur_unittests.cc +++ b/impeller/aiks/aiks_blur_unittests.cc @@ -644,5 +644,33 @@ TEST_P(AiksTest, GaussianBlurStyleOuter) { ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture())); } +TEST_P(AiksTest, GaussianBlurStyleSolid) { + Canvas canvas; + canvas.Scale(GetContentScale()); + + canvas.DrawPaint({.color = Color(0.1, 0.1, 0.1, 1.0)}); + + Paint paint; + paint.color = Color::Green(); + paint.mask_blur_descriptor = Paint::MaskBlurDescriptor{ + .style = FilterContents::BlurStyle::kSolid, + .sigma = Sigma(30), + }; + canvas.DrawPath(PathBuilder() + .MoveTo({200, 200}) + .LineTo({300, 400}) + .LineTo({100, 400}) + .Close() + .TakePath(), + paint); + + // Draw another thing to make sure the clip area is reset. + Paint red; + red.color = Color::Red(); + canvas.DrawRect(Rect::MakeXYWH(0, 0, 200, 200), red); + + ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture())); +} + } // namespace testing } // namespace impeller diff --git a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc index 62a2bd490baef..9a00232ff84e0 100644 --- a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc +++ b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc @@ -204,31 +204,12 @@ int ScaleBlurRadius(Scalar radius, Scalar scalar) { return static_cast(std::round(radius * scalar)); } -Entity ApplyBlurStyle(FilterContents::BlurStyle blur_style, - const Entity& entity, - const std::shared_ptr& input, - const Snapshot& input_snapshot, - Entity blur_entity, - const std::shared_ptr& geometry) { - if (blur_style == FilterContents::BlurStyle::kNormal) { - return blur_entity; - } - Entity::ClipOperation clip_operation; - switch (blur_style) { - case FilterContents::BlurStyle::kNormal: - FML_UNREACHABLE(); - break; - case FilterContents::BlurStyle::kInner: - clip_operation = Entity::ClipOperation::kIntersect; - break; - case FilterContents::BlurStyle::kOuter: - clip_operation = Entity::ClipOperation::kDifference; - break; - case FilterContents::BlurStyle::kSolid: - FML_DLOG(ERROR) << "Unimplemented blur style"; - return blur_entity; - } - +Entity ApplyClippedBlurStyle(Entity::ClipOperation clip_operation, + const Entity& entity, + const std::shared_ptr& input, + const Snapshot& input_snapshot, + Entity blur_entity, + const std::shared_ptr& geometry) { auto shared_blur_entity = std::make_shared(std::move(blur_entity)); shared_blur_entity->SetNewClipDepth(entity.GetNewClipDepth()); auto clipper = std::make_unique(); @@ -255,6 +236,30 @@ Entity ApplyBlurStyle(FilterContents::BlurStyle blur_style, })); return result; } + +Entity ApplyBlurStyle(FilterContents::BlurStyle blur_style, + const Entity& entity, + const std::shared_ptr& input, + const Snapshot& input_snapshot, + Entity blur_entity, + const std::shared_ptr& geometry) { + switch (blur_style) { + case FilterContents::BlurStyle::kNormal: + return blur_entity; + case FilterContents::BlurStyle::kInner: + return ApplyClippedBlurStyle(Entity::ClipOperation::kIntersect, entity, + input, input_snapshot, + std::move(blur_entity), geometry); + break; + case FilterContents::BlurStyle::kOuter: + return ApplyClippedBlurStyle(Entity::ClipOperation::kDifference, entity, + input, input_snapshot, + std::move(blur_entity), geometry); + case FilterContents::BlurStyle::kSolid: + FML_DLOG(ERROR) << "Unimplemented blur style"; + return blur_entity; + } +} } // namespace std::string_view GaussianBlurFilterContents::kNoMipsError = From 33ef3b9fd516aac3957222d6d17bfa7b5e4210fe Mon Sep 17 00:00:00 2001 From: Aaron Clarke Date: Wed, 28 Feb 2024 15:25:02 -0800 Subject: [PATCH 2/5] implemented solid --- .../filters/gaussian_blur_filter_contents.cc | 28 +++++++++++++++++-- 1 file changed, 25 insertions(+), 3 deletions(-) diff --git a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc index 9a00232ff84e0..25c3a0cabfff5 100644 --- a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc +++ b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc @@ -255,9 +255,31 @@ Entity ApplyBlurStyle(FilterContents::BlurStyle blur_style, return ApplyClippedBlurStyle(Entity::ClipOperation::kDifference, entity, input, input_snapshot, std::move(blur_entity), geometry); - case FilterContents::BlurStyle::kSolid: - FML_DLOG(ERROR) << "Unimplemented blur style"; - return blur_entity; + case FilterContents::BlurStyle::kSolid: { + Entity blurred = ApplyClippedBlurStyle(Entity::ClipOperation::kIntersect, + entity, input, input_snapshot, + std::move(blur_entity), geometry); + Entity snapshot_entity = + Entity::FromSnapshot(input_snapshot, entity.GetBlendMode(), + entity.GetClipDepth()) + .value(); + Entity result; + result.SetContents(Contents::MakeAnonymous( + fml::MakeCopyable([blurred = blurred.Clone(), + snapshot_entity = std::move(snapshot_entity)]( + const ContentContext& renderer, + const Entity& entity, + RenderPass& pass) mutable { + bool did_render = true; + did_render = blurred.Render(renderer, pass) && did_render; + did_render = snapshot_entity.Render(renderer, pass) && did_render; + return did_render; + }), + fml::MakeCopyable([blurred = blurred.Clone()](const Entity& entity) { + return blurred.GetCoverage(); + }))); + return result; + } } } } // namespace From 5bddd7b3c4ab5ca91519594ab6bc52d2afd5dbba Mon Sep 17 00:00:00 2001 From: Aaron Clarke Date: Thu, 29 Feb 2024 10:15:46 -0800 Subject: [PATCH 3/5] switched up FromSnapshot --- .../contents/filters/blend_filter_contents.cc | 6 +++--- .../filters/gaussian_blur_filter_contents.cc | 12 +++-------- .../filters/local_matrix_filter_contents.cc | 10 ++++++--- .../filters/matrix_filter_contents.cc | 5 ++++- impeller/entity/entity.cc | 21 +++++++------------ impeller/entity/entity.h | 7 +++---- 6 files changed, 28 insertions(+), 33 deletions(-) diff --git a/impeller/entity/contents/filters/blend_filter_contents.cc b/impeller/entity/contents/filters/blend_filter_contents.cc index 1018acffde16b..60d8a233360a1 100644 --- a/impeller/entity/contents/filters/blend_filter_contents.cc +++ b/impeller/entity/contents/filters/blend_filter_contents.cc @@ -111,7 +111,7 @@ static std::optional AdvancedBlend( if (!dst_snapshot.has_value()) { return std::nullopt; } - return Entity::FromSnapshot(dst_snapshot, entity.GetBlendMode(), + return Entity::FromSnapshot(dst_snapshot.value(), entity.GetBlendMode(), entity.GetClipDepth()); } auto maybe_src_uvs = src_snapshot->GetCoverageUVs(coverage); @@ -119,7 +119,7 @@ static std::optional AdvancedBlend( if (!dst_snapshot.has_value()) { return std::nullopt; } - return Entity::FromSnapshot(dst_snapshot, entity.GetBlendMode(), + return Entity::FromSnapshot(dst_snapshot.value(), entity.GetBlendMode(), entity.GetClipDepth()); } src_uvs = maybe_src_uvs.value(); @@ -426,7 +426,7 @@ std::optional BlendFilterContents::CreateForegroundPorterDuffBlend( } if (blend_mode == BlendMode::kDestination) { - return Entity::FromSnapshot(dst_snapshot, entity.GetBlendMode(), + return Entity::FromSnapshot(dst_snapshot.value(), entity.GetBlendMode(), entity.GetClipDepth()); } diff --git a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc index 25c3a0cabfff5..021a2b22fc99c 100644 --- a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc +++ b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc @@ -259,10 +259,8 @@ Entity ApplyBlurStyle(FilterContents::BlurStyle blur_style, Entity blurred = ApplyClippedBlurStyle(Entity::ClipOperation::kIntersect, entity, input, input_snapshot, std::move(blur_entity), geometry); - Entity snapshot_entity = - Entity::FromSnapshot(input_snapshot, entity.GetBlendMode(), - entity.GetClipDepth()) - .value(); + Entity snapshot_entity = Entity::FromSnapshot( + input_snapshot, entity.GetBlendMode(), entity.GetClipDepth()); Entity result; result.SetContents(Contents::MakeAnonymous( fml::MakeCopyable([blurred = blurred.Clone(), @@ -535,13 +533,9 @@ std::optional GaussianBlurFilterContents::RenderFilter( .opacity = input_snapshot->opacity}, entity.GetBlendMode(), entity.GetClipDepth()); - if (!blur_output_entity.has_value()) { - return std::nullopt; - } - return ApplyBlurStyle(mask_blur_style_, entity, inputs[0], input_snapshot.value(), - std::move(blur_output_entity.value()), mask_geometry_); + std::move(blur_output_entity), mask_geometry_); } Scalar GaussianBlurFilterContents::CalculateBlurRadius(Scalar sigma) { diff --git a/impeller/entity/contents/filters/local_matrix_filter_contents.cc b/impeller/entity/contents/filters/local_matrix_filter_contents.cc index e30edbd04e8d0..d5b52ef615349 100644 --- a/impeller/entity/contents/filters/local_matrix_filter_contents.cc +++ b/impeller/entity/contents/filters/local_matrix_filter_contents.cc @@ -37,9 +37,13 @@ std::optional LocalMatrixFilterContents::RenderFilter( const Matrix& effect_transform, const Rect& coverage, const std::optional& coverage_hint) const { - return Entity::FromSnapshot( - inputs[0]->GetSnapshot("LocalMatrix", renderer, entity), - entity.GetBlendMode(), entity.GetClipDepth()); + std::optional snapshot = + inputs[0]->GetSnapshot("LocalMatrix", renderer, entity); + if (!snapshot.has_value()) { + return std::nullopt; + } + return Entity::FromSnapshot(snapshot.value(), entity.GetBlendMode(), + entity.GetClipDepth()); } } // namespace impeller diff --git a/impeller/entity/contents/filters/matrix_filter_contents.cc b/impeller/entity/contents/filters/matrix_filter_contents.cc index 6bce41f2acfc7..7fe455c79d387 100644 --- a/impeller/entity/contents/filters/matrix_filter_contents.cc +++ b/impeller/entity/contents/filters/matrix_filter_contents.cc @@ -64,7 +64,10 @@ std::optional MatrixFilterContents::RenderFilter( snapshot->transform; snapshot->sampler_descriptor = sampler_descriptor_; - return Entity::FromSnapshot(snapshot, entity.GetBlendMode(), + if (!snapshot.has_value()) { + return std::nullopt; + } + return Entity::FromSnapshot(snapshot.value(), entity.GetBlendMode(), entity.GetClipDepth()); } diff --git a/impeller/entity/entity.cc b/impeller/entity/entity.cc index 472f4b534bee8..356dbe7e8086f 100644 --- a/impeller/entity/entity.cc +++ b/impeller/entity/entity.cc @@ -19,26 +19,21 @@ namespace impeller { -std::optional Entity::FromSnapshot( - const std::optional& snapshot, - BlendMode blend_mode, - uint32_t clip_depth) { - if (!snapshot.has_value()) { - return std::nullopt; - } - - auto texture_rect = Rect::MakeSize(snapshot->texture->GetSize()); +Entity Entity::FromSnapshot(const Snapshot& snapshot, + BlendMode blend_mode, + uint32_t clip_depth) { + auto texture_rect = Rect::MakeSize(snapshot.texture->GetSize()); auto contents = TextureContents::MakeRect(texture_rect); - contents->SetTexture(snapshot->texture); - contents->SetSamplerDescriptor(snapshot->sampler_descriptor); + contents->SetTexture(snapshot.texture); + contents->SetSamplerDescriptor(snapshot.sampler_descriptor); contents->SetSourceRect(texture_rect); - contents->SetOpacity(snapshot->opacity); + contents->SetOpacity(snapshot.opacity); Entity entity; entity.SetBlendMode(blend_mode); entity.SetClipDepth(clip_depth); - entity.SetTransform(snapshot->transform); + entity.SetTransform(snapshot.transform); entity.SetContents(contents); return entity; } diff --git a/impeller/entity/entity.h b/impeller/entity/entity.h index 430a0423e5257..d964dcd631987 100644 --- a/impeller/entity/entity.h +++ b/impeller/entity/entity.h @@ -62,10 +62,9 @@ class Entity { }; /// @brief Create an entity that can be used to render a given snapshot. - static std::optional FromSnapshot( - const std::optional& snapshot, - BlendMode blend_mode = BlendMode::kSourceOver, - uint32_t clip_depth = 0); + static Entity FromSnapshot(const Snapshot& snapshot, + BlendMode blend_mode = BlendMode::kSourceOver, + uint32_t clip_depth = 0); Entity(); From 4bdb5a12352b4fb330d572215e3059fd805a6c11 Mon Sep 17 00:00:00 2001 From: Aaron Clarke Date: Mon, 4 Mar 2024 10:25:03 -0800 Subject: [PATCH 4/5] removed auto --- .../contents/filters/gaussian_blur_filter_contents.cc | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc index 021a2b22fc99c..197dce8a6b279 100644 --- a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc +++ b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc @@ -524,7 +524,7 @@ std::optional GaussianBlurFilterContents::RenderFilter( SamplerDescriptor sampler_desc = MakeSamplerDescriptor( MinMagFilter::kLinear, SamplerAddressMode::kClampToEdge); - auto blur_output_entity = Entity::FromSnapshot( + Entity blur_output_entity = Entity::FromSnapshot( Snapshot{.texture = pass3_out.value().GetRenderTargetTexture(), .transform = input_snapshot->transform * padding_snapshot_adjustment * @@ -534,8 +534,8 @@ std::optional GaussianBlurFilterContents::RenderFilter( entity.GetBlendMode(), entity.GetClipDepth()); return ApplyBlurStyle(mask_blur_style_, entity, inputs[0], - input_snapshot.value(), - std::move(blur_output_entity), mask_geometry_); + input_snapshot.value(), std::move(blur_output_entity), + mask_geometry_); } Scalar GaussianBlurFilterContents::CalculateBlurRadius(Scalar sigma) { From cfa638db3a7ef7fb68e62f178c1bee4a8a4d7083 Mon Sep 17 00:00:00 2001 From: Aaron Clarke Date: Tue, 5 Mar 2024 14:27:01 -0800 Subject: [PATCH 5/5] feedback and updated the golden --- .../filters/gaussian_blur_filter_contents.cc | 14 ++++++-------- testing/impeller_golden_tests_output.txt | 3 +++ 2 files changed, 9 insertions(+), 8 deletions(-) diff --git a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc index 197dce8a6b279..46513f3b4bf85 100644 --- a/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc +++ b/impeller/entity/contents/filters/gaussian_blur_filter_contents.cc @@ -262,20 +262,18 @@ Entity ApplyBlurStyle(FilterContents::BlurStyle blur_style, Entity snapshot_entity = Entity::FromSnapshot( input_snapshot, entity.GetBlendMode(), entity.GetClipDepth()); Entity result; + std::optional coverage = blurred.GetCoverage(); result.SetContents(Contents::MakeAnonymous( - fml::MakeCopyable([blurred = blurred.Clone(), + fml::MakeCopyable([blurred = std::move(blurred), snapshot_entity = std::move(snapshot_entity)]( const ContentContext& renderer, const Entity& entity, RenderPass& pass) mutable { - bool did_render = true; - did_render = blurred.Render(renderer, pass) && did_render; - did_render = snapshot_entity.Render(renderer, pass) && did_render; - return did_render; + return blurred.Render(renderer, pass) && + snapshot_entity.Render(renderer, pass); }), - fml::MakeCopyable([blurred = blurred.Clone()](const Entity& entity) { - return blurred.GetCoverage(); - }))); + fml::MakeCopyable( + [coverage](const Entity& entity) { return coverage; }))); return result; } } diff --git a/testing/impeller_golden_tests_output.txt b/testing/impeller_golden_tests_output.txt index aeb18abee22e6..06783ca01e5e7 100644 --- a/testing/impeller_golden_tests_output.txt +++ b/testing/impeller_golden_tests_output.txt @@ -491,6 +491,9 @@ impeller_Play_AiksTest_GaussianBlurStyleInner_Vulkan.png impeller_Play_AiksTest_GaussianBlurStyleOuter_Metal.png impeller_Play_AiksTest_GaussianBlurStyleOuter_OpenGLES.png impeller_Play_AiksTest_GaussianBlurStyleOuter_Vulkan.png +impeller_Play_AiksTest_GaussianBlurStyleSolid_Metal.png +impeller_Play_AiksTest_GaussianBlurStyleSolid_OpenGLES.png +impeller_Play_AiksTest_GaussianBlurStyleSolid_Vulkan.png impeller_Play_AiksTest_GaussianBlurWithoutDecalSupport_Metal.png impeller_Play_AiksTest_GradientStrokesRenderCorrectly_Metal.png impeller_Play_AiksTest_GradientStrokesRenderCorrectly_OpenGLES.png