Add method to delay drawable acquisition from MTKView
Change-Id: Iad9fadd113d0c97e8ece51df19c7824252d7eb9c Reviewed-on: https://skia-review.googlesource.com/c/skia/+/263197 Reviewed-by: Brian Salomon <bsalomon@google.com> Commit-Queue: Jim Van Verth <jvanverth@google.com>
This commit is contained in:
parent
04e77813f8
commit
e27670172b
@ -8,6 +8,10 @@ Milestone 81
|
||||
|
||||
<Insert new notes here- top is most recent.>
|
||||
|
||||
* Add support to create an SkSurface from an MTKView, with delayed acquisition of
|
||||
the MTLDrawable.
|
||||
Entry point: SkSurface::MakeFromMTKView
|
||||
|
||||
* Removed SkIRect::EmptyIRect(). Use SkIRect::MakeEmpty() instead.
|
||||
https://review.skia.org/262382/
|
||||
|
||||
|
@ -318,8 +318,7 @@ public:
|
||||
#endif
|
||||
|
||||
#ifdef SK_METAL
|
||||
/** Private.
|
||||
Creates SkSurface from CAMetalLayer.
|
||||
/** Creates SkSurface from CAMetalLayer.
|
||||
Returned SkSurface takes a reference on the CAMetalLayer. The ref on the layer will be
|
||||
released when the SkSurface is destroyed.
|
||||
|
||||
@ -354,6 +353,37 @@ public:
|
||||
const SkSurfaceProps* surfaceProps,
|
||||
GrMTLHandle* drawable);
|
||||
|
||||
/** Creates SkSurface from MTKView.
|
||||
Returned SkSurface takes a reference on the MTKView. The ref on the layer will be
|
||||
released when the SkSurface is destroyed.
|
||||
|
||||
Only available when Metal API is enabled.
|
||||
|
||||
Will grab the current drawable from the layer and use its texture as a backendRT to
|
||||
create a renderable surface.
|
||||
|
||||
@param context GPU context
|
||||
@param layer GrMTLHandle (expected to be a MTKView*)
|
||||
@param origin one of: kBottomLeft_GrSurfaceOrigin, kTopLeft_GrSurfaceOrigin
|
||||
@param sampleCnt samples per pixel, or 0 to disable full scene anti-aliasing
|
||||
@param colorType one of:
|
||||
kUnknown_SkColorType, kAlpha_8_SkColorType, kRGB_565_SkColorType,
|
||||
kARGB_4444_SkColorType, kRGBA_8888_SkColorType,
|
||||
kRGB_888x_SkColorType, kBGRA_8888_SkColorType,
|
||||
kRGBA_1010102_SkColorType, kRGB_101010x_SkColorType,
|
||||
kGray_8_SkColorType, kRGBA_F16_SkColorType
|
||||
@param colorSpace range of colors; may be nullptr
|
||||
@param surfaceProps LCD striping orientation and setting for device independent
|
||||
fonts; may be nullptr
|
||||
@return created SkSurface, or nullptr
|
||||
*/
|
||||
static sk_sp<SkSurface> MakeFromMTKView(GrContext* context,
|
||||
GrMTLHandle mtkView,
|
||||
GrSurfaceOrigin origin,
|
||||
int sampleCnt,
|
||||
SkColorType colorType,
|
||||
sk_sp<SkColorSpace> colorSpace,
|
||||
const SkSurfaceProps* surfaceProps);
|
||||
#endif
|
||||
|
||||
/** Returns SkSurface on GPU indicated by context. Allocates memory for
|
||||
|
@ -25,6 +25,7 @@
|
||||
#ifdef SK_METAL
|
||||
#import <Metal/Metal.h>
|
||||
#import <QuartzCore/CAMetalLayer.h>
|
||||
#import <MetalKit/MetalKit.h>
|
||||
|
||||
sk_sp<SkSurface> SkSurface::MakeFromCAMetalLayer(GrContext* context,
|
||||
GrMTLHandle layer,
|
||||
@ -110,6 +111,90 @@ sk_sp<SkSurface> SkSurface::MakeFromCAMetalLayer(GrContext* context,
|
||||
sk_sp<SkSurface> surface = SkSurface_Gpu::MakeWrappedRenderTarget(context, std::move(rtc));
|
||||
return surface;
|
||||
}
|
||||
|
||||
sk_sp<SkSurface> SkSurface::MakeFromMTKView(GrContext* context,
|
||||
GrMTLHandle view,
|
||||
GrSurfaceOrigin origin,
|
||||
int sampleCnt,
|
||||
SkColorType colorType,
|
||||
sk_sp<SkColorSpace> colorSpace,
|
||||
const SkSurfaceProps* surfaceProps) {
|
||||
GrProxyProvider* proxyProvider = context->priv().proxyProvider();
|
||||
const GrCaps* caps = context->priv().caps();
|
||||
|
||||
MTKView* mtkView = (__bridge MTKView*)view;
|
||||
GrBackendFormat backendFormat = GrBackendFormat::MakeMtl(mtkView.colorPixelFormat);
|
||||
|
||||
GrColorType grColorType = SkColorTypeToGrColorType(colorType);
|
||||
|
||||
GrPixelConfig config = caps->getConfigFromBackendFormat(backendFormat, grColorType);
|
||||
if (config == kUnknown_GrPixelConfig) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
GrSurfaceDesc desc;
|
||||
desc.fWidth = mtkView.drawableSize.width;
|
||||
desc.fHeight = mtkView.drawableSize.height;
|
||||
desc.fConfig = config;
|
||||
|
||||
GrProxyProvider::TextureInfo texInfo;
|
||||
texInfo.fMipMapped = GrMipMapped::kNo;
|
||||
texInfo.fTextureType = GrTextureType::k2D;
|
||||
|
||||
sk_sp<GrRenderTargetProxy> proxy = proxyProvider->createLazyRenderTargetProxy(
|
||||
[view, sampleCnt, config](GrResourceProvider* resourceProvider) {
|
||||
MTKView* mtkView = (__bridge MTKView*)view;
|
||||
id<CAMetalDrawable> currentDrawable = [mtkView currentDrawable];
|
||||
|
||||
GrSurfaceDesc desc;
|
||||
desc.fWidth = mtkView.drawableSize.width;
|
||||
desc.fHeight = mtkView.drawableSize.height;
|
||||
desc.fConfig = config;
|
||||
|
||||
GrMtlGpu* mtlGpu = (GrMtlGpu*) resourceProvider->priv().gpu();
|
||||
sk_sp<GrRenderTarget> surface;
|
||||
if (mtkView.framebufferOnly) {
|
||||
surface = GrMtlRenderTarget::MakeWrappedRenderTarget(
|
||||
mtlGpu, desc, sampleCnt, currentDrawable.texture);
|
||||
} else {
|
||||
surface = GrMtlTextureRenderTarget::MakeWrappedTextureRenderTarget(
|
||||
mtlGpu, desc, sampleCnt, currentDrawable.texture,
|
||||
GrWrapCacheable::kNo);
|
||||
}
|
||||
if (surface && sampleCnt > 1) {
|
||||
surface->setRequiresManualMSAAResolve();
|
||||
}
|
||||
|
||||
return GrSurfaceProxy::LazyCallbackResult(std::move(surface));
|
||||
},
|
||||
backendFormat,
|
||||
desc,
|
||||
sampleCnt,
|
||||
origin,
|
||||
sampleCnt > 1 ? GrInternalSurfaceFlags::kRequiresManualMSAAResolve
|
||||
: GrInternalSurfaceFlags::kNone,
|
||||
mtkView.framebufferOnly ? nullptr : &texInfo,
|
||||
GrMipMapsStatus::kNotAllocated,
|
||||
SkBackingFit::kExact,
|
||||
SkBudgeted::kYes,
|
||||
GrProtected::kNo,
|
||||
false,
|
||||
GrSurfaceProxy::UseAllocator::kYes);
|
||||
|
||||
const GrSwizzle& readSwizzle = caps->getReadSwizzle(backendFormat, grColorType);
|
||||
const GrSwizzle& outputSwizzle = caps->getOutputSwizzle(backendFormat, grColorType);
|
||||
|
||||
SkASSERT(readSwizzle == proxy->textureSwizzle());
|
||||
|
||||
auto rtc = std::make_unique<GrRenderTargetContext>(context, std::move(proxy),
|
||||
grColorType, origin,
|
||||
readSwizzle, outputSwizzle,
|
||||
colorSpace, surfaceProps);
|
||||
|
||||
sk_sp<SkSurface> surface = SkSurface_Gpu::MakeWrappedRenderTarget(context, std::move(rtc));
|
||||
return surface;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
@ -13,32 +13,20 @@
|
||||
#import <MetalKit/MetalKit.h>
|
||||
|
||||
sk_sp<SkSurface> SkMtkViewToSurface(MTKView* mtkView, GrContext* grContext) {
|
||||
if (![[mtkView currentDrawable] texture] ||
|
||||
!grContext ||
|
||||
if (!grContext ||
|
||||
MTLPixelFormatDepth32Float_Stencil8 != [mtkView depthStencilPixelFormat] ||
|
||||
MTLPixelFormatBGRA8Unorm != [mtkView colorPixelFormat]) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
const SkColorType colorType = kBGRA_8888_SkColorType; // MTLPixelFormatBGRA8Unorm
|
||||
sk_sp<SkColorSpace> colorSpace = nullptr; // MTLPixelFormatBGRA8Unorm
|
||||
const GrSurfaceOrigin origin = kTopLeft_GrSurfaceOrigin;
|
||||
const SkSurfaceProps surfaceProps(SkSurfaceProps::kLegacyFontHost_InitType);
|
||||
int sampleCount = (int)[mtkView sampleCount];
|
||||
CGSize size = [mtkView drawableSize];
|
||||
int width = (int)size.width;
|
||||
int height = (int)size.height;
|
||||
|
||||
GrMtlTextureInfo fbInfo;
|
||||
fbInfo.fTexture.retain((__bridge const void*)([[mtkView currentDrawable] texture]));
|
||||
if (sampleCount == 1) {
|
||||
GrBackendRenderTarget backendRT(width, height, 1, fbInfo);
|
||||
return SkSurface::MakeFromBackendRenderTarget(grContext, backendRT, origin,
|
||||
colorType, colorSpace, &surfaceProps);
|
||||
} else {
|
||||
GrBackendTexture backendTexture(width, height, GrMipMapped::kNo, fbInfo);
|
||||
return SkSurface::MakeFromBackendTexture(grContext, backendTexture, origin, sampleCount,
|
||||
colorType, colorSpace, &surfaceProps);
|
||||
}
|
||||
return SkSurface::MakeFromMTKView(grContext, (__bridge GrMTLHandle)mtkView, origin, sampleCount,
|
||||
colorType, colorSpace, &surfaceProps);
|
||||
}
|
||||
|
||||
void GrContextRelease::operator()(GrContext* ptr) { SkSafeUnref(ptr); }
|
||||
|
Loading…
Reference in New Issue
Block a user