Flutter Impeller
framebuffer_blend_contents.cc
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
6 
9 
10 namespace impeller {
11 
13 
15 
17  blend_mode_ = blend_mode;
18 }
19 
21  std::shared_ptr<Contents> child_contents) {
22  child_contents_ = std::move(child_contents);
23 }
24 
25 // |Contents|
26 std::optional<Rect> FramebufferBlendContents::GetCoverage(
27  const Entity& entity) const {
28  return child_contents_->GetCoverage(entity);
29 }
30 
31 bool FramebufferBlendContents::Render(const ContentContext& renderer,
32  const Entity& entity,
33  RenderPass& pass) const {
34  if (!renderer.GetDeviceCapabilities().SupportsFramebufferFetch()) {
35  return false;
36  }
37 
40 
41  auto& host_buffer = renderer.GetTransientsBuffer();
42 
43  auto src_snapshot = child_contents_->RenderToSnapshot(
44  renderer, // renderer
45  entity, // entity
46  Rect::MakeSize(pass.GetRenderTargetSize()), // coverage_limit
47  std::nullopt, // sampler_descriptor
48  true, // msaa_enabled
49  /*mip_count=*/1,
50  "FramebufferBlendContents Snapshot"); // label
51 
52  if (!src_snapshot.has_value()) {
53  return true;
54  }
55  auto coverage = src_snapshot->GetCoverage();
56  if (!coverage.has_value()) {
57  return true;
58  }
59  Rect src_coverage = coverage.value();
60 
61  auto size = src_coverage.GetSize();
62  VertexBufferBuilder<VS::PerVertexData> vtx_builder;
63  vtx_builder.AddVertices({
64  {Point(0, 0), Point(0, 0)},
65  {Point(size.width, 0), Point(1, 0)},
66  {Point(0, size.height), Point(0, 1)},
67  {Point(size.width, size.height), Point(1, 1)},
68  });
69 
70  auto options = OptionsFromPass(pass);
71  options.blend_mode = BlendMode::kSource;
72  options.primitive_type = PrimitiveType::kTriangleStrip;
73 
74  pass.SetCommandLabel("Framebuffer Advanced Blend Filter");
75  pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
76  pass.SetStencilReference(entity.GetClipDepth());
77 
78  switch (blend_mode_) {
79  case BlendMode::kScreen:
80  pass.SetPipeline(renderer.GetFramebufferBlendScreenPipeline(options));
81  break;
83  pass.SetPipeline(renderer.GetFramebufferBlendOverlayPipeline(options));
84  break;
85  case BlendMode::kDarken:
86  pass.SetPipeline(renderer.GetFramebufferBlendDarkenPipeline(options));
87  break;
89  pass.SetPipeline(renderer.GetFramebufferBlendLightenPipeline(options));
90  break;
92  pass.SetPipeline(renderer.GetFramebufferBlendColorDodgePipeline(options));
93  break;
95  pass.SetPipeline(renderer.GetFramebufferBlendColorBurnPipeline(options));
96  break;
98  pass.SetPipeline(renderer.GetFramebufferBlendHardLightPipeline(options));
99  break;
101  pass.SetPipeline(renderer.GetFramebufferBlendSoftLightPipeline(options));
102  break;
104  pass.SetPipeline(renderer.GetFramebufferBlendDifferencePipeline(options));
105  break;
107  pass.SetPipeline(renderer.GetFramebufferBlendExclusionPipeline(options));
108  break;
110  pass.SetPipeline(renderer.GetFramebufferBlendMultiplyPipeline(options));
111  break;
112  case BlendMode::kHue:
113  pass.SetPipeline(renderer.GetFramebufferBlendHuePipeline(options));
114  break;
116  pass.SetPipeline(renderer.GetFramebufferBlendSaturationPipeline(options));
117  break;
118  case BlendMode::kColor:
119  pass.SetPipeline(renderer.GetFramebufferBlendColorPipeline(options));
120  break;
122  pass.SetPipeline(renderer.GetFramebufferBlendLuminosityPipeline(options));
123  break;
124  default:
125  return false;
126  }
127 
128  VS::FrameInfo frame_info;
129  FS::FragInfo frag_info;
130 
131  auto src_sampler_descriptor = src_snapshot->sampler_descriptor;
132  if (renderer.GetDeviceCapabilities().SupportsDecalSamplerAddressMode()) {
133  src_sampler_descriptor.width_address_mode = SamplerAddressMode::kDecal;
134  src_sampler_descriptor.height_address_mode = SamplerAddressMode::kDecal;
135  }
136  const std::unique_ptr<const Sampler>& src_sampler =
137  renderer.GetContext()->GetSamplerLibrary()->GetSampler(
138  src_sampler_descriptor);
139  FS::BindTextureSamplerSrc(pass, src_snapshot->texture, src_sampler);
140 
141  frame_info.mvp = Entity::GetShaderTransform(entity.GetShaderClipDepth(), pass,
142  src_snapshot->transform);
143  frame_info.src_y_coord_scale = src_snapshot->texture->GetYCoordScale();
144  VS::BindFrameInfo(pass, host_buffer.EmplaceUniform(frame_info));
145 
146  frag_info.src_input_alpha = src_snapshot->opacity;
147  FS::BindFragInfo(pass, host_buffer.EmplaceUniform(frag_info));
148 
149  return pass.Draw().ok();
150 }
151 
152 } // namespace impeller
impeller::Entity::GetShaderTransform
Matrix GetShaderTransform(const RenderPass &pass) const
Get the vertex shader transform used for drawing this Entity.
Definition: entity.cc:53
impeller::OptionsFromPass
ContentContextOptions OptionsFromPass(const RenderPass &pass)
Definition: contents.cc:20
impeller::BlendMode
BlendMode
Definition: color.h:59
impeller::BlendMode::kLuminosity
@ kLuminosity
impeller::BlendMode::kSource
@ kSource
impeller::BlendMode::kColorDodge
@ kColorDodge
impeller::BlendMode::kDarken
@ kDarken
impeller::BlendMode::kColor
@ kColor
impeller::RenderPipelineT::FragmentShader
FragmentShader_ FragmentShader
Definition: pipeline.h:94
impeller::BlendMode::kOverlay
@ kOverlay
framebuffer_blend_contents.h
impeller::FramebufferBlendContents::~FramebufferBlendContents
~FramebufferBlendContents() override
impeller::BlendMode::kSaturation
@ kSaturation
impeller::BlendMode::kDifference
@ kDifference
impeller::VS
SolidFillVertexShader VS
Definition: stroke_path_geometry.cc:15
impeller::Entity
Definition: entity.h:21
impeller::BlendMode::kLighten
@ kLighten
impeller::PrimitiveType::kTriangleStrip
@ kTriangleStrip
impeller::BlendMode::kSoftLight
@ kSoftLight
impeller::Point
TPoint< Scalar > Point
Definition: point.h:316
render_pass.h
impeller::BlendMode::kColorBurn
@ kColorBurn
impeller::BlendMode::kHardLight
@ kHardLight
impeller::FramebufferBlendContents::FramebufferBlendContents
FramebufferBlendContents()
impeller::Rect
TRect< Scalar > Rect
Definition: rect.h:661
impeller::FramebufferBlendContents::SetChildContents
void SetChildContents(std::shared_ptr< Contents > child_contents)
Definition: framebuffer_blend_contents.cc:20
impeller::BlendMode::kExclusion
@ kExclusion
content_context.h
impeller::TRect::GetSize
constexpr TSize< Type > GetSize() const
Returns the size of the rectangle which may be negative in either width or height and may have been c...
Definition: rect.h:294
impeller::TRect< Scalar >::MakeSize
constexpr static TRect MakeSize(const TSize< U > &size)
Definition: rect.h:146
impeller::FramebufferBlendContents::SetBlendMode
void SetBlendMode(BlendMode blend_mode)
Definition: framebuffer_blend_contents.cc:16
impeller::BlendMode::kScreen
@ kScreen
impeller::BlendMode::kHue
@ kHue
impeller::RenderPipelineT::VertexShader
VertexShader_ VertexShader
Definition: pipeline.h:93
impeller
Definition: aiks_blur_unittests.cc:20
impeller::BlendMode::kMultiply
@ kMultiply
impeller::SamplerAddressMode::kDecal
@ kDecal
decal sampling mode is only supported on devices that pass the Capabilities.SupportsDecalSamplerAddre...