• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1//
2// Copyright 2019 The ANGLE Project Authors. All rights reserved.
3// Use of this source code is governed by a BSD-style license that can be
4// found in the LICENSE file.
5//
6// WindowSurfaceVkMac.mm:
7//    Implements methods from WindowSurfaceVkMac.
8//
9
10#include "libANGLE/renderer/vulkan/mac/WindowSurfaceVkMac.h"
11
12#include <Metal/Metal.h>
13#include <QuartzCore/CAMetalLayer.h>
14
15#include "libANGLE/renderer/vulkan/RendererVk.h"
16#include "libANGLE/renderer/vulkan/vk_utils.h"
17
18namespace rx
19{
20
21WindowSurfaceVkMac::WindowSurfaceVkMac(const egl::SurfaceState &surfaceState,
22                                       EGLNativeWindowType window)
23    : WindowSurfaceVk(surfaceState, window), mMetalLayer(nullptr)
24{}
25
26WindowSurfaceVkMac::~WindowSurfaceVkMac()
27{
28    [mMetalDevice release];
29    [mMetalLayer release];
30}
31
32angle::Result WindowSurfaceVkMac::createSurfaceVk(vk::Context *context, gl::Extents *extentsOut)
33    API_AVAILABLE(macosx(10.11))
34{
35    mMetalDevice = MTLCreateSystemDefaultDevice();
36
37    CALayer *layer = reinterpret_cast<CALayer *>(mNativeWindowType);
38
39    mMetalLayer        = [[CAMetalLayer alloc] init];
40    mMetalLayer.frame  = CGRectMake(0, 0, layer.frame.size.width, layer.frame.size.height);
41    mMetalLayer.device = mMetalDevice;
42    mMetalLayer.drawableSize =
43        CGSizeMake(mMetalLayer.bounds.size.width * mMetalLayer.contentsScale,
44                   mMetalLayer.bounds.size.height * mMetalLayer.contentsScale);
45    mMetalLayer.framebufferOnly  = NO;
46    mMetalLayer.autoresizingMask = kCALayerWidthSizable | kCALayerHeightSizable;
47    mMetalLayer.contentsScale    = layer.contentsScale;
48
49    [layer addSublayer:mMetalLayer];
50
51    VkMetalSurfaceCreateInfoEXT createInfo = {};
52    createInfo.sType                       = VK_STRUCTURE_TYPE_METAL_SURFACE_CREATE_INFO_EXT;
53    createInfo.flags                       = 0;
54    createInfo.pNext                       = nullptr;
55    createInfo.pLayer                      = mMetalLayer;
56    ANGLE_VK_TRY(context, vkCreateMetalSurfaceEXT(context->getRenderer()->getInstance(),
57                                                  &createInfo, nullptr, &mSurface));
58
59    return getCurrentWindowSize(context, extentsOut);
60}
61
62angle::Result WindowSurfaceVkMac::getCurrentWindowSize(vk::Context *context,
63                                                       gl::Extents *extentsOut)
64    API_AVAILABLE(macosx(10.11))
65{
66    ANGLE_VK_CHECK(context, (mMetalLayer != nullptr), VK_ERROR_INITIALIZATION_FAILED);
67
68    mMetalLayer.drawableSize =
69        CGSizeMake(mMetalLayer.bounds.size.width * mMetalLayer.contentsScale,
70                   mMetalLayer.bounds.size.height * mMetalLayer.contentsScale);
71    *extentsOut = gl::Extents(static_cast<int>(mMetalLayer.drawableSize.width),
72                              static_cast<int>(mMetalLayer.drawableSize.height), 1);
73
74    return angle::Result::Continue;
75}
76
77}  // namespace rx
78