| Flutter Impeller |

Public Member Functions | Static Public Member Functions | List of all members
impeller::SurfaceMTL Class Referencefinal

`#include <surface_mtl.h>`

Inheritance diagram for impeller::SurfaceMTL:

## Public Member Functions
| ~SurfaceMTL () override
id< MTLDrawable > | drawable () const
IRect | coverage () const
bool | Present () const override
Public Member Functions inherited from impeller::Surface
| Surface ()
| Surface (const RenderTarget &target_desc)
virtual | ~Surface ()
const ISize & | GetSize () const
bool | IsValid () const
const RenderTarget & | GetTargetRenderPassDescriptor () const

## Static Public Member Functions
static id< CAMetalDrawable > | GetMetalDrawableAndValidate (const std::shared_ptr< Context > &context, CAMetalLayer *layer)
| Wraps the current drawable of the given Metal layer to create a surface Impeller can render to. The surface must be created as late as possible and discarded immediately after rendering to it. More...
static std::unique_ptr< SurfaceMTL > | MakeFromMetalLayerDrawable (const std::shared_ptr< Context > &context, id< CAMetalDrawable > drawable, std::optional< IRect > clip_rect=std::nullopt)
static std::unique_ptr< SurfaceMTL > | MakeFromTexture (const std::shared_ptr< Context > &context, id< MTLTexture > texture, std::optional< IRect > clip_rect, id< CAMetalDrawable > drawable=nil)

## Detailed Description

Definition at line 18 of file surface_mtl.h.

## Constructor & Destructor Documentation

## ◆ ~SurfaceMTL()

impeller::SurfaceMTL::~SurfaceMTL | ( |  | ) |
| override default

## Member Function Documentation

## ◆ coverage()

IRect impeller::SurfaceMTL::coverage | ( |  | ) | const

Definition at line 217 of file surface_mtl.mm.

217 {
218 return IRect::MakeSize(resolve_texture_->GetSize());
219 }

References impeller::TRect< int64_t >::MakeSize().

## ◆ drawable()

id<MTLDrawable> impeller::SurfaceMTL::drawable | ( |  | ) | const
| inline

Definition at line 57 of file surface_mtl.h.

57 { return drawable_; }

Referenced by MakeFromMetalLayerDrawable(), MakeFromTexture(), and Present().

## ◆ GetMetalDrawableAndValidate()

id< CAMetalDrawable > impeller::SurfaceMTL::GetMetalDrawableAndValidate | ( | const std::shared_ptr< Context > & | context,
|  | CAMetalLayer * | layer
| ) |  |
| static

Wraps the current drawable of the given Metal layer to create a surface Impeller can render to. The surface must be created as late as possible and discarded immediately after rendering to it.

Parameters

  [in] | context | The context
  [in] | layer | The layer whose current drawable to wrap to create a surface.

Returns
  A pointer to the wrapped surface or null.

Definition at line 21 of file surface_mtl.mm.

23 {
24 TRACE_EVENT0("impeller", "SurfaceMTL::WrapCurrentMetalLayerDrawable");
25
26 if (context == nullptr || !context->IsValid() || layer == nil) {
27 return nullptr;
28 }
29
30 id<CAMetalDrawable> current_drawable = nil;
31 {
32 TRACE_EVENT0("impeller", "WaitForNextDrawable");
33 current_drawable = [layer nextDrawable];
34 }
35
36 if (!current_drawable) {
37 VALIDATION_LOG << "Could not acquire current drawable.";
38 return nullptr;
39 }
40 return current_drawable;
41 }

References VALIDATION_LOG.

## ◆ MakeFromMetalLayerDrawable()

std::unique_ptr< SurfaceMTL > impeller::SurfaceMTL::MakeFromMetalLayerDrawable | ( | const std::shared_ptr< Context > & | context,
|  | id< CAMetalDrawable > | drawable,
|  | std::optional< IRect > | clip_rect = `std::nullopt`
| ) |  |
| static

Definition at line 119 of file surface_mtl.mm.

122 {
123 return SurfaceMTL::MakeFromTexture(context, drawable.texture, clip_rect,
124 drawable);
125 }

References drawable(), and MakeFromTexture().

## ◆ MakeFromTexture()

std::unique_ptr< SurfaceMTL > impeller::SurfaceMTL::MakeFromTexture | ( | const std::shared_ptr< Context > & | context,
|  | id< MTLTexture > | texture,
|  | std::optional< IRect > | clip_rect,
|  | id< CAMetalDrawable > | drawable = `nil`
| ) |  |
| static

Definition at line 127 of file surface_mtl.mm.

131 {
132 bool partial_repaint_blit_required = ShouldPerformPartialRepaint(clip_rect);
133
134 // The returned render target is the texture that Impeller will render the
135 // root pass to. If partial repaint is in use, this may be a new texture which
136 // is smaller than the given MTLTexture.
137 auto render_target =
138 WrapTextureWithRenderTarget(*context->GetResourceAllocator(), texture,
139 partial_repaint_blit_required, clip_rect);
140 if (!render_target) {
141 return nullptr;
142 }
143
144 // If partial repainting, set a "source" texture. The presence of a source
145 // texture and clip rect instructs the surface to blit this texture to the
146 // destination texture.
147 auto source_texture = partial_repaint_blit_required
148 ? render_target->GetRenderTargetTexture()
149 : nullptr;
150
151 // The final "destination" texture is the texture that will be presented. In
152 // this case, it's always the given drawable.
153 std::shared_ptr<Texture> destination_texture;
154 if (partial_repaint_blit_required) {
155 // If blitting for partial repaint, we need to wrap the drawable. Simply
156 // reuse the texture descriptor that was already formed for the new render
157 // target, but override the size with the drawable's size.
158 auto destination_descriptor =
159 render_target->GetRenderTargetTexture()->GetTextureDescriptor();
160 destination_descriptor.size = {static_cast<ISize::Type>(texture.width),
161 static_cast<ISize::Type>(texture.height)};
162 destination_texture = TextureMTL::Wrapper(destination_descriptor, texture);
163 } else {
164 // When not partial repaint blit is needed, the render target texture _is_
165 // the drawable texture.
166 destination_texture = render_target->GetRenderTargetTexture();
167 }
168
169 return std::unique_ptr<SurfaceMTL>(new SurfaceMTL(
170 context, // context
171 *render_target, // target
172 render_target->GetRenderTargetTexture(), // resolve_texture
173 drawable, // drawable
174 source_texture, // source_texture
175 destination_texture, // destination_texture
176 partial_repaint_blit_required, // requires_blit
177 clip_rect // clip_rect
178 ));
179 }

References drawable(), impeller::TextureMTL::Wrapper(), and impeller::WrapTextureWithRenderTarget().

Referenced by MakeFromMetalLayerDrawable().

## ◆ Present()

bool impeller::SurfaceMTL::Present | ( |  | ) | const
| override virtual

Reimplemented from impeller::Surface.

Definition at line 222 of file surface_mtl.mm.

222 {
223 auto context = context_.lock();
224 if (!context) {
225 return false;
226 }
227
228 if (requires_blit_) {
229 if (!(source_texture_ && destination_texture_)) {
230 return false;
231 }
232
233 auto blit_command_buffer = context->CreateCommandBuffer();
234 if (!blit_command_buffer) {
235 return false;
236 }
237 auto blit_pass = blit_command_buffer->CreateBlitPass();
238 if (!clip_rect_.has_value()) {
239 VALIDATION_LOG << "Missing clip rectangle.";
240 return false;
241 }
242 blit_pass->AddCopy(source_texture_, destination_texture_, std::nullopt,
243 clip_rect_->GetOrigin());
244 blit_pass->EncodeCommands(context->GetResourceAllocator());
245 if (!blit_command_buffer->SubmitCommands()) {
246 return false;
247 }
248 }
249 #ifdef IMPELLER_DEBUG
250 ContextMTL::Cast(context.get())->GetGPUTracer()->MarkFrameEnd();
251 #endif // IMPELLER_DEBUG
252
253 if (drawable_) {
254 id<MTLCommandBuffer> command_buffer =
255 ContextMTL::Cast(context.get())
256 ->CreateMTLCommandBuffer("Present Waiter Command Buffer");
257 // If the threads have been merged, or there is a pending frame capture,
258 // then block on cmd buffer scheduling to ensure that the
259 // transaction/capture work correctly.
260 if ([[NSThread currentThread] isMainThread] ||
261 [[MTLCaptureManager sharedCaptureManager] isCapturing]) {
262 TRACE_EVENT0("flutter", "waitUntilScheduled");
263 [command_buffer commit];
264 [command_buffer waitUntilScheduled];
265 [drawable_ present];
266 } else {
267 // The drawable may come from a FlutterMetalLayer, so it can't be
268 // presented through the command buffer.
269 id<CAMetalDrawable> drawable = drawable_;
270 [command_buffer addScheduledHandler:^(id<MTLCommandBuffer> buffer) {
271 [drawable present];
272 }];
273 [command_buffer commit];
274 }
275 }
276
277 return true;
278 }

References impeller::BackendCast< ContextMTL, Context >::Cast(), impeller::ContextMTL::CreateMTLCommandBuffer(), drawable(), and VALIDATION_LOG.

The documentation for this class was generated from the following files:

- impeller/renderer/backend/metal/surface_mtl.h
- impeller/renderer/backend/metal/surface_mtl.mm

impeller::TSize< int64_t >::Type
int64_t Type
Definition: size.h:20
impeller::WrapTextureWithRenderTarget
static std::optional< RenderTarget > WrapTextureWithRenderTarget(Allocator &allocator, id< MTLTexture > texture, bool requires_blit, std::optional< IRect > clip_rect)
Definition: surface_mtl.mm:43
impeller::SurfaceMTL::MakeFromTexture
static std::unique_ptr< SurfaceMTL > MakeFromTexture(const std::shared_ptr< Context > &context, id< MTLTexture > texture, std::optional< IRect > clip_rect, id< CAMetalDrawable > drawable=nil)
Definition: surface_mtl.mm:127
impeller::SurfaceMTL::drawable
id< MTLDrawable > drawable() const
Definition: surface_mtl.h:57
impeller::TextureMTL::Wrapper
static std::shared_ptr< TextureMTL > Wrapper(TextureDescriptor desc, id< MTLTexture > texture, std::function< void()> deletion_proc=nullptr)
Definition: texture_mtl.mm:40
VALIDATION_LOG
#define VALIDATION_LOG
Definition: validation.h:67
impeller::TRect< int64_t >::MakeSize
constexpr static TRect MakeSize(const TSize< U > &size)
Definition: rect.h:44
impeller::BackendCast< ContextMTL, Context >::Cast
static ContextMTL & Cast(Context &base)
Definition: backend_cast.h:15
impeller::ContextMTL::CreateMTLCommandBuffer
id< MTLCommandBuffer > CreateMTLCommandBuffer(const std::string &label) const
Definition: context_mtl.mm:390