Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Revert "Introduce a delegate class for gpu metal rendering (#22611)" #22775

Merged
merged 1 commit into from
Nov 30, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 0 additions & 4 deletions ci/licenses_golden/licenses_flutter
Original file line number Diff line number Diff line change
Expand Up @@ -673,8 +673,6 @@ FILE: ../../../flutter/shell/gpu/gpu_surface_gl_delegate.cc
FILE: ../../../flutter/shell/gpu/gpu_surface_gl_delegate.h
FILE: ../../../flutter/shell/gpu/gpu_surface_metal.h
FILE: ../../../flutter/shell/gpu/gpu_surface_metal.mm
FILE: ../../../flutter/shell/gpu/gpu_surface_metal_delegate.cc
FILE: ../../../flutter/shell/gpu/gpu_surface_metal_delegate.h
FILE: ../../../flutter/shell/gpu/gpu_surface_software.cc
FILE: ../../../flutter/shell/gpu/gpu_surface_software.h
FILE: ../../../flutter/shell/gpu/gpu_surface_software_delegate.cc
Expand Down Expand Up @@ -934,8 +932,6 @@ FILE: ../../../flutter/shell/platform/darwin/common/framework/Source/FlutterStan
FILE: ../../../flutter/shell/platform/darwin/common/framework/Source/FlutterStandardCodec_Internal.h
FILE: ../../../flutter/shell/platform/darwin/common/framework/Source/flutter_codecs_unittest.mm
FILE: ../../../flutter/shell/platform/darwin/common/framework/Source/flutter_standard_codec_unittest.mm
FILE: ../../../flutter/shell/platform/darwin/graphics/FlutterDarwinContextMetal.h
FILE: ../../../flutter/shell/platform/darwin/graphics/FlutterDarwinContextMetal.mm
FILE: ../../../flutter/shell/platform/darwin/ios/framework/Flutter.podspec
FILE: ../../../flutter/shell/platform/darwin/ios/framework/Headers/Flutter.h
FILE: ../../../flutter/shell/platform/darwin/ios/framework/Headers/FlutterAppDelegate.h
Expand Down
6 changes: 3 additions & 3 deletions shell/common/animator.cc
Original file line number Diff line number Diff line change
Expand Up @@ -29,9 +29,9 @@ Animator::Animator(Delegate& delegate,
last_vsync_start_time_(),
last_frame_target_time_(),
dart_frame_deadline_(0),
#if SHELL_ENABLE_METAL
#if FLUTTER_SHELL_ENABLE_METAL
layer_tree_pipeline_(fml::MakeRefCounted<LayerTreePipeline>(2)),
#else // SHELL_ENABLE_METAL
#else // FLUTTER_SHELL_ENABLE_METAL
// TODO(dnfield): We should remove this logic and set the pipeline depth
// back to 2 in this case. See
// https://github.com/flutter/engine/pull/9132 for discussion.
Expand All @@ -40,7 +40,7 @@ Animator::Animator(Delegate& delegate,
task_runners.GetRasterTaskRunner()
? 1
: 2)),
#endif // SHELL_ENABLE_METAL
#endif // FLUTTER_SHELL_ENABLE_METAL
pending_frame_semaphore_(1),
frame_number_(1),
paused_(false),
Expand Down
2 changes: 0 additions & 2 deletions shell/gpu/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,6 @@ source_set("gpu_surface_metal") {
sources = [
"gpu_surface_metal.h",
"gpu_surface_metal.mm",
"gpu_surface_metal_delegate.cc",
"gpu_surface_metal_delegate.h",
]

deps = gpu_common_deps
Expand Down
29 changes: 14 additions & 15 deletions shell/gpu/gpu_surface_metal.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,30 +5,35 @@
#ifndef FLUTTER_SHELL_GPU_GPU_SURFACE_METAL_H_
#define FLUTTER_SHELL_GPU_GPU_SURFACE_METAL_H_

#include <Metal/Metal.h>

#include "flutter/flow/surface.h"
#include "flutter/fml/macros.h"
#include "flutter/shell/gpu/gpu_surface_metal_delegate.h"
#include "flutter/fml/platform/darwin/scoped_nsobject.h"
#include "third_party/skia/include/gpu/GrDirectContext.h"
#include "third_party/skia/include/gpu/mtl/GrMtlTypes.h"

@class CAMetalLayer;

namespace flutter {

class SK_API_AVAILABLE_CA_METAL_LAYER GPUSurfaceMetal : public Surface {
public:
GPUSurfaceMetal(GPUSurfaceMetalDelegate* delegate,
sk_sp<GrDirectContext> context);
GPUSurfaceMetal(fml::scoped_nsobject<CAMetalLayer> layer,
sk_sp<GrDirectContext> context,
fml::scoped_nsprotocol<id<MTLCommandQueue>> command_queue);

// |Surface|
~GPUSurfaceMetal();

// |Surface|
bool IsValid() override;

private:
const GPUSurfaceMetalDelegate* delegate_;
const MTLRenderTargetType render_target_type_;
GrMTLHandle next_drawable_ = nullptr;
fml::scoped_nsobject<CAMetalLayer> layer_;
sk_sp<GrDirectContext> context_;
fml::scoped_nsprotocol<id<MTLCommandQueue>> command_queue_;
GrMTLHandle next_drawable_ = nullptr;

// |Surface|
bool IsValid() override;

// |Surface|
std::unique_ptr<SurfaceFrame> AcquireFrame(const SkISize& size) override;
Expand All @@ -42,12 +47,6 @@ class SK_API_AVAILABLE_CA_METAL_LAYER GPUSurfaceMetal : public Surface {
// |Surface|
std::unique_ptr<GLContextResult> MakeRenderContextCurrent() override;

std::unique_ptr<SurfaceFrame> AcquireFrameFromCAMetalLayer(
const SkISize& frame_info);

std::unique_ptr<SurfaceFrame> AcquireFrameFromMTLTexture(
const SkISize& frame_info);

void ReleaseUnusedDrawableIfNecessary();

FML_DISALLOW_COPY_AND_ASSIGN(GPUSurfaceMetal);
Expand Down
133 changes: 49 additions & 84 deletions shell/gpu/gpu_surface_metal.mm
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,9 @@

#include "flutter/shell/gpu/gpu_surface_metal.h"

#import <Metal/Metal.h>
#include <QuartzCore/CAMetalLayer.h>

#include "flutter/fml/make_copyable.h"
#include "flutter/fml/platform/darwin/cf_utils.h"
#include "flutter/fml/trace_event.h"
#include "flutter/shell/gpu/gpu_surface_metal_delegate.h"
#include "third_party/skia/include/core/SkSurface.h"
#include "third_party/skia/include/gpu/GrBackendSurface.h"
#include "third_party/skia/include/ports/SkCFObject.h"
Expand All @@ -18,18 +15,25 @@

namespace flutter {

GPUSurfaceMetal::GPUSurfaceMetal(GPUSurfaceMetalDelegate* delegate, sk_sp<GrDirectContext> context)
: delegate_(delegate),
render_target_type_(delegate->GetRenderTargetType()),
context_(std::move(context)) {}
GPUSurfaceMetal::GPUSurfaceMetal(fml::scoped_nsobject<CAMetalLayer> layer,
sk_sp<GrDirectContext> context,
fml::scoped_nsprotocol<id<MTLCommandQueue>> command_queue)
: layer_(std::move(layer)),
context_(std::move(context)),
command_queue_(std::move(command_queue)) {
layer_.get().pixelFormat = MTLPixelFormatBGRA8Unorm;
// Flutter needs to read from the color attachment in cases where there are effects such as
// backdrop filters.
layer_.get().framebufferOnly = NO;
}

GPUSurfaceMetal::~GPUSurfaceMetal() {
ReleaseUnusedDrawableIfNecessary();
}

// |Surface|
bool GPUSurfaceMetal::IsValid() {
return context_ != nullptr;
return layer_ && context_ && command_queue_;
}

// |Surface|
Expand All @@ -44,99 +48,60 @@
return nullptr;
}

switch (render_target_type_) {
case MTLRenderTargetType::kCAMetalLayer:
return AcquireFrameFromCAMetalLayer(frame_size);
case MTLRenderTargetType::kMTLTexture:
return AcquireFrameFromMTLTexture(frame_size);
default:
FML_CHECK(false) << "Unknown MTLRenderTargetType type.";
}

return nullptr;
}
const auto drawable_size = CGSizeMake(frame_size.width(), frame_size.height());

std::unique_ptr<SurfaceFrame> GPUSurfaceMetal::AcquireFrameFromCAMetalLayer(
const SkISize& frame_info) {
auto layer = delegate_->GetCAMetalLayer(frame_info);
if (!layer) {
FML_LOG(ERROR) << "Invalid CAMetalLayer given by the embedder.";
return nullptr;
if (!CGSizeEqualToSize(drawable_size, layer_.get().drawableSize)) {
layer_.get().drawableSize = drawable_size;
}

ReleaseUnusedDrawableIfNecessary();
sk_sp<SkSurface> surface =
SkSurface::MakeFromCAMetalLayer(context_.get(), // context
layer, // layer
kTopLeft_GrSurfaceOrigin, // origin
1, // sample count
kBGRA_8888_SkColorType, // color type
nullptr, // colorspace
nullptr, // surface properties
&next_drawable_ // drawable (transfer out)
);

if (!surface) {
FML_LOG(ERROR) << "Could not create the SkSurface from the CAMetalLayer.";
return nullptr;
}

auto submit_callback =
fml::MakeCopyable([drawable = next_drawable_, delegate = delegate_](
const SurfaceFrame& surface_frame, SkCanvas* canvas) -> bool {
TRACE_EVENT0("flutter", "GPUSurfaceMetal::Submit");
if (canvas == nullptr) {
FML_DLOG(ERROR) << "Canvas not available.";
return false;
}

canvas->flush();

if (!drawable) {
FML_DLOG(ERROR) << "Unable to obtain a metal drawable.";
return false;
}

return delegate->PresentDrawable(drawable);
});

return std::make_unique<SurfaceFrame>(std::move(surface), true, submit_callback);
}

std::unique_ptr<SurfaceFrame> GPUSurfaceMetal::AcquireFrameFromMTLTexture(
const SkISize& frame_info) {
GPUMTLTextureInfo texture = delegate_->GetMTLTexture(frame_info);
id<MTLTexture> mtl_texture = (id<MTLTexture>)(texture.texture);

if (!mtl_texture) {
FML_LOG(ERROR) << "Invalid MTLTexture given by the embedder.";
return nullptr;
}

GrMtlTextureInfo info;
info.fTexture.reset([mtl_texture retain]);
GrBackendTexture backend_texture(frame_info.width(), frame_info.height(), GrMipmapped::kNo, info);

sk_sp<SkSurface> surface =
SkSurface::MakeFromBackendTexture(context_.get(), backend_texture, kTopLeft_GrSurfaceOrigin,
1, kBGRA_8888_SkColorType, nullptr, nullptr);
// When there are platform views in the scene, the drawable needs to be presented in the same
// transaction as the one created for platform views. When the drawable are being presented from
// the raster thread, there is no such transaction.
layer_.get().presentsWithTransaction = [[NSThread currentThread] isMainThread];

auto surface = SkSurface::MakeFromCAMetalLayer(context_.get(), // context
layer_.get(), // layer
kTopLeft_GrSurfaceOrigin, // origin
1, // sample count
kBGRA_8888_SkColorType, // color type
nullptr, // colorspace
nullptr, // surface properties
&next_drawable_ // drawable (transfer out)
);

if (!surface) {
FML_LOG(ERROR) << "Could not create the SkSurface from the metal texture.";
return nullptr;
}

auto submit_callback = [texture_id = texture.texture_id, delegate = delegate_](
const SurfaceFrame& surface_frame, SkCanvas* canvas) -> bool {
TRACE_EVENT0("flutter", "GPUSurfaceMetal::PresentTexture");
auto submit_callback = [this](const SurfaceFrame& surface_frame, SkCanvas* canvas) -> bool {
TRACE_EVENT0("flutter", "GPUSurfaceMetal::Submit");
if (canvas == nullptr) {
FML_DLOG(ERROR) << "Canvas not available.";
return false;
}

canvas->flush();

return delegate->PresentTexture(texture_id);
if (next_drawable_ == nullptr) {
FML_DLOG(ERROR) << "Could not acquire next Metal drawable from the SkSurface.";
return false;
}

auto command_buffer =
fml::scoped_nsprotocol<id<MTLCommandBuffer>>([[command_queue_.get() commandBuffer] retain]);

fml::scoped_nsprotocol<id<CAMetalDrawable>> drawable(
reinterpret_cast<id<CAMetalDrawable>>(next_drawable_));
next_drawable_ = nullptr;

[command_buffer.get() commit];
[command_buffer.get() waitUntilScheduled];
[drawable.get() present];

return true;
};

return std::make_unique<SurfaceFrame>(std::move(surface), true, submit_callback);
Expand Down
19 changes: 0 additions & 19 deletions shell/gpu/gpu_surface_metal_delegate.cc

This file was deleted.

Loading