vulkan: Add fallback extent for swap chain sizing (#6495)

vulkan: Add fallback extent for swap chain sizing
This commit is contained in:
Powei Feng
2023-01-30 19:29:10 -08:00
committed by GitHub
parent 1077405bc1
commit 906da033dd
19 changed files with 175 additions and 69 deletions

View File

@@ -27,8 +27,19 @@ namespace filament::backend {
class VulkanPlatform : public Platform {
public:
struct SurfaceBundle {
void* surface;
// On certain platforms, the extent of the surface cannot be queried from Vulkan. In those
// situations, we allow the frontend to pass in the extent to use in creating the swap
// chains. Platform implementation should set extent to 0 if they do not expect to set the
// swap chain extent.
uint32_t width;
uint32_t height;
};
// Given a Vulkan instance and native window handle, creates the platform-specific surface.
virtual void* createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept = 0;
virtual SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept = 0;
~VulkanPlatform() override;
};

View File

@@ -29,23 +29,32 @@ using namespace bluevk;
namespace filament::backend {
Driver* PlatformVkAndroid::createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept {
using SurfaceBundle = VulkanPlatform::SurfaceBundle;
Driver* PlatformVkAndroid::createDriver(void* const sharedContext,
const Platform::DriverConfig& driverConfig) noexcept {
ASSERT_PRECONDITION(sharedContext == nullptr, "Vulkan does not support shared contexts.");
static const char* requiredInstanceExtensions[] = { "VK_KHR_android_surface" };
return VulkanDriverFactory::create(this, requiredInstanceExtensions, 1, driverConfig);
}
void* PlatformVkAndroid::createVkSurfaceKHR(void* nativeWindow, void* vkinstance, uint64_t flags) noexcept {
SurfaceBundle PlatformVkAndroid::createVkSurfaceKHR(void* nativeWindow, void* vkinstance,
uint64_t flags) noexcept {
const VkInstance instance = (VkInstance) vkinstance;
ANativeWindow* aNativeWindow = (ANativeWindow*) nativeWindow;
VkAndroidSurfaceCreateInfoKHR createInfo {
.sType = VK_STRUCTURE_TYPE_ANDROID_SURFACE_CREATE_INFO_KHR,
.window = aNativeWindow
};
VkSurfaceKHR surface = VK_NULL_HANDLE;
VkResult result = vkCreateAndroidSurfaceKHR(instance, &createInfo, VKALLOC, &surface);
SurfaceBundle bundle {
.surface = VK_NULL_HANDLE,
.width = 0,
.height = 0
};
VkResult result = vkCreateAndroidSurfaceKHR(instance, &createInfo, VKALLOC,
(VkSurfaceKHR*) &bundle.surface);
ASSERT_POSTCONDITION(result == VK_SUCCESS, "vkCreateAndroidSurfaceKHR error.");
return (void*) surface;
return bundle;
}
} // namespace filament::backend

View File

@@ -29,7 +29,8 @@ public:
Driver* createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept override;
void* createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept override;
VulkanPlatform::SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
int getOSVersion() const noexcept override { return 0; }
};

View File

@@ -27,7 +27,8 @@ namespace filament::backend {
class PlatformVkCocoa final : public VulkanPlatform {
public:
Driver* createDriver(void* sharedContext, const Platform::DriverConfig& driverConfig) noexcept override;
void* createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept override;
VulkanPlatform::SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
int getOSVersion() const noexcept override { return 0; }
};

View File

@@ -34,6 +34,8 @@ using namespace bluevk;
namespace filament::backend {
using SurfaceBundle = VulkanPlatform::SurfaceBundle;
Driver* PlatformVkCocoa::createDriver(void* sharedContext, const Platform::DriverConfig& driverConfig) noexcept {
ASSERT_PRECONDITION(sharedContext == nullptr, "Vulkan does not support shared contexts.");
static const char* requiredInstanceExtensions[] = {
@@ -42,21 +44,28 @@ Driver* PlatformVkCocoa::createDriver(void* sharedContext, const Platform::Drive
return VulkanDriverFactory::create(this, requiredInstanceExtensions, 1, driverConfig);
}
void* PlatformVkCocoa::createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept {
SurfaceBundle PlatformVkCocoa::createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept {
// Obtain the CAMetalLayer-backed view.
NSView* nsview = (__bridge NSView*) nativeWindow;
ASSERT_POSTCONDITION(nsview, "Unable to obtain Metal-backed NSView.");
// Create the VkSurface.
ASSERT_POSTCONDITION(vkCreateMacOSSurfaceMVK, "Unable to load vkCreateMacOSSurfaceMVK.");
VkSurfaceKHR surface = nullptr;
VkMacOSSurfaceCreateInfoMVK createInfo = {};
createInfo.sType = VK_STRUCTURE_TYPE_MACOS_SURFACE_CREATE_INFO_MVK;
createInfo.pView = (__bridge void*) nsview;
VkResult result = vkCreateMacOSSurfaceMVK((VkInstance) instance, &createInfo, VKALLOC, &surface);
SurfaceBundle bundle {
.surface = nullptr,
.width = 0,
.height = 0
};
VkResult result = vkCreateMacOSSurfaceMVK((VkInstance) instance, &createInfo, VKALLOC,
(VkSurfaceKHR*) &bundle.surface);
ASSERT_POSTCONDITION(result == VK_SUCCESS, "vkCreateMacOSSurfaceMVK error.");
return surface;
return bundle;
}
} // namespace filament::backend

View File

@@ -27,7 +27,8 @@ namespace filament::backend {
class PlatformVkCocoaTouch final : public VulkanPlatform {
public:
Driver* createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept override;
void* createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept override;
VulkanPlatform::SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
int getOSVersion() const noexcept override { return 0; }
};

View File

@@ -39,31 +39,37 @@ using namespace bluevk;
namespace filament::backend {
using SurfaceBundle = VulkanPlatform::SurfaceBundle;
Driver* PlatformVkCocoaTouch::createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept {
ASSERT_PRECONDITION(sharedContext == nullptr, "Vulkan does not support shared contexts.");
static const char* requestedExtensions[] = {"VK_MVK_ios_surface"};
return VulkanDriverFactory::create(this, requestedExtensions, 1, driverConfig);
}
void* PlatformVkCocoaTouch::createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept {
SurfaceBundle PlatformVkCocoaTouch::createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept {
SurfaceBundle bundle {
.surface = nullptr,
.width = 0,
.height = 0
};
#if METAL_AVAILABLE
CAMetalLayer* metalLayer = (CAMetalLayer*) nativeWindow;
// Create the VkSurface.
ASSERT_POSTCONDITION(vkCreateIOSSurfaceMVK, "Unable to load vkCreateIOSSurfaceMVK function.");
VkSurfaceKHR surface = nullptr;
VkIOSSurfaceCreateInfoMVK createInfo = {};
createInfo.sType = VK_STRUCTURE_TYPE_IOS_SURFACE_CREATE_INFO_MVK;
createInfo.pNext = NULL;
createInfo.flags = 0;
createInfo.pView = metalLayer;
VkResult result = vkCreateIOSSurfaceMVK((VkInstance) instance, &createInfo, VKALLOC, &surface);
ASSERT_POSTCONDITION(result == VK_SUCCESS, "vkCreateIOSSurfaceMVK error.");
return surface;
#else
return nullptr;
VkResult result = vkCreateIOSSurfaceMVK((VkInstance) instance, &createInfo, VKALLOC,
(VkSurfaceKHR*) &bundle.surface);
ASSERT_POSTCONDITION(result == VK_SUCCESS, "vkCreateIOSSurfaceMVK error.");
#endif
return bundle;
}
} // namespace filament::backend

View File

@@ -28,6 +28,8 @@ using namespace bluevk;
namespace filament::backend {
using SurfaceBundle = VulkanPlatform::SurfaceBundle;
Driver* PlatformVkLinuxGGP::createDriver(
void* const sharedContext,
const Platform::DriverConfig& driverConfig) noexcept {
@@ -46,8 +48,13 @@ Driver* PlatformVkLinuxGGP::createDriver(
#endif
}
void* PlatformVkLinuxGGP::createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept {
SurfaceBundle PlatformVkLinuxGGP::createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept {
SurfaceBundle bundle {
.surface = nullptr,
.width = 0,
.height = 0
};
#if defined(FILAMENT_SUPPORTS_GGP)
VkStreamDescriptorSurfaceCreateInfoGGP surface_create_info = {
VK_STRUCTURE_TYPE_STREAM_DESCRIPTOR_SURFACE_CREATE_INFO_GGP};
@@ -59,16 +66,14 @@ void* PlatformVkLinuxGGP::createVkSurfaceKHR(void* nativeWindow, void* instance,
ASSERT_PRECONDITION(fpCreateStreamDescriptorSurfaceGGP != nullptr,
"Error getting VkInstance "
"function vkCreateStreamDescriptorSurfaceGGP");
VkSurfaceKHR surface = nullptr;
VkResult res = fpCreateStreamDescriptorSurfaceGGP(
static_cast<VkInstance>(instance), &surface_create_info, nullptr,
&surface);
(VkSurfaceKHR*) &bundle.surface);
ASSERT_PRECONDITION(res == VK_SUCCESS, "Error in vulkan: %d", res);
return surface;
#else
PANIC_PRECONDITION("Filament does not support GGP.");
return nullptr;
#endif
return bundle;
}
} // namespace filament::backend

View File

@@ -30,8 +30,8 @@ class PlatformVkLinuxGGP final : public VulkanPlatform {
void* const sharedContext,
const Platform::DriverConfig& driverConfig) noexcept override;
void* createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
VulkanPlatform::SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
int getOSVersion() const noexcept override { return 0; }
};

View File

@@ -27,8 +27,19 @@
using namespace bluevk;
namespace {
typedef struct _wl {
struct wl_display *display;
struct wl_surface *surface;
uint32_t width;
uint32_t height;
} wl;
} // anonymous namespace
namespace filament::backend {
using SurfaceBundle = VulkanPlatform::SurfaceBundle;
Driver* PlatformVkLinuxWayland::createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept {
ASSERT_PRECONDITION(sharedContext == nullptr, "Vulkan does not support shared contexts.");
const char* requiredInstanceExtensions[] = {
@@ -38,15 +49,8 @@ Driver* PlatformVkLinuxWayland::createDriver(void* const sharedContext, const Pl
sizeof(requiredInstanceExtensions) / sizeof(requiredInstanceExtensions[0]), driverConfig);
}
void* PlatformVkLinuxWayland::createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept {
typedef struct _wl {
struct wl_display *display;
struct wl_surface *surface;
} wl;
VkSurfaceKHR surface = nullptr;
SurfaceBundle PlatformVkLinuxWayland::createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept {
wl* ptrval = reinterpret_cast<wl*>(nativeWindow);
VkWaylandSurfaceCreateInfoKHR createInfo = {
@@ -56,11 +60,15 @@ void* PlatformVkLinuxWayland::createVkSurfaceKHR(void* nativeWindow, void* insta
.display = ptrval->display,
.surface = ptrval->surface
};
VkResult result = vkCreateWaylandSurfaceKHR((VkInstance) instance, &createInfo, VKALLOC, &surface);
SurfaceBundle bundle {
.surface = VK_NULL_HANDLE,
.width = ptrval->width,
.height = ptrval->height
};
VkResult result = vkCreateWaylandSurfaceKHR((VkInstance) instance, &createInfo, VKALLOC,
(VkSurfaceKHR*) &bundle.surface);
ASSERT_POSTCONDITION(result == VK_SUCCESS, "vkCreateWaylandSurfaceKHR error.");
return surface;
return bundle;
}
} // namespace filament::backend

View File

@@ -30,7 +30,8 @@ public:
Driver* createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept override;
void* createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept override;
VulkanPlatform::SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
int getOSVersion() const noexcept override { return 0; }
};

View File

@@ -29,6 +29,8 @@ using namespace bluevk;
namespace filament::backend {
using SurfaceBundle = VulkanPlatform::SurfaceBundle;
static constexpr const char* LIBRARY_X11 = "libX11.so.6";
#ifdef FILAMENT_SUPPORTS_XCB
@@ -50,7 +52,8 @@ struct X11Functions {
void* library = nullptr;
} g_x11;
Driver* PlatformVkLinuxX11::createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept {
Driver* PlatformVkLinuxX11::createDriver(void* const sharedContext,
const Platform::DriverConfig& driverConfig) noexcept {
ASSERT_PRECONDITION(sharedContext == nullptr, "Vulkan does not support shared contexts.");
const char* requiredInstanceExtensions[] = {
#ifdef FILAMENT_SUPPORTS_XCB
@@ -64,7 +67,8 @@ Driver* PlatformVkLinuxX11::createDriver(void* const sharedContext, const Platfo
sizeof(requiredInstanceExtensions) / sizeof(requiredInstanceExtensions[0]), driverConfig);
}
void* PlatformVkLinuxX11::createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept {
SurfaceBundle PlatformVkLinuxX11::createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept {
if (g_x11.library == nullptr) {
g_x11.library = dlopen(LIBRARY_X11, RTLD_LOCAL | RTLD_NOW);
ASSERT_PRECONDITION(g_x11.library, "Unable to open X11 library.");
@@ -85,7 +89,11 @@ void* PlatformVkLinuxX11::createVkSurfaceKHR(void* nativeWindow, void* instance,
}
VkSurfaceKHR surface = nullptr;
SurfaceBundle bundle {
.surface = nullptr,
.width = 0,
.height = 0
};
#ifdef FILAMENT_SUPPORTS_XCB
#ifdef FILAMENT_SUPPORTS_XLIB
@@ -101,8 +109,9 @@ const bool windowIsXCB = true;
.connection = mConnection,
.window = (xcb_window_t) ptrval,
};
vkCreateXcbSurfaceKHR((VkInstance) instance, &createInfo, VKALLOC, &surface);
return surface;
vkCreateXcbSurfaceKHR((VkInstance) instance, &createInfo, VKALLOC,
(VkSurfaceKHR*) &bundle.surface);
return bundle;
}
#endif
@@ -112,10 +121,11 @@ const bool windowIsXCB = true;
.dpy = mDisplay,
.window = (Window) nativeWindow,
};
vkCreateXlibSurfaceKHR((VkInstance) instance, &createInfo, VKALLOC, &surface);
vkCreateXlibSurfaceKHR((VkInstance) instance, &createInfo, VKALLOC,
(VkSurfaceKHR*) &bundle.surface);
#endif
return surface;
return bundle;
}
} // namespace filament::backend

View File

@@ -37,7 +37,8 @@ public:
Driver* createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept override;
void* createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept override;
VulkanPlatform::SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
int getOSVersion() const noexcept override { return 0; }

View File

@@ -27,15 +27,22 @@ using namespace bluevk;
namespace filament::backend {
Driver* PlatformVkWindows::createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept {
using SurfaceBundle = VulkanPlatform::SurfaceBundle;
Driver* PlatformVkWindows::createDriver(void* const sharedContext,
const Platform::DriverConfig& driverConfig) noexcept {
ASSERT_PRECONDITION(sharedContext == nullptr, "Vulkan does not support shared contexts.");
const char* requiredInstanceExtensions[] = { "VK_KHR_win32_surface" };
return VulkanDriverFactory::create(this, requiredInstanceExtensions, 1, driverConfig);
}
void* PlatformVkWindows::createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept {
VkSurfaceKHR surface = nullptr;
SurfaceBundle PlatformVkWindows::createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept {
SurfaceBundle bundle {
.surface = nullptr,
.width = 0,
.height = 0
};
HWND window = (HWND) nativeWindow;
VkWin32SurfaceCreateInfoKHR createInfo = {};
@@ -43,10 +50,11 @@ void* PlatformVkWindows::createVkSurfaceKHR(void* nativeWindow, void* instance,
createInfo.hwnd = window;
createInfo.hinstance = GetModuleHandle(nullptr);
VkResult result = vkCreateWin32SurfaceKHR((VkInstance) instance, &createInfo, nullptr, &surface);
VkResult result = vkCreateWin32SurfaceKHR((VkInstance) instance, &createInfo, nullptr,
(VkSurfaceKHR*) &bundle.surface);
ASSERT_POSTCONDITION(result == VK_SUCCESS, "vkCreateWin32SurfaceKHR error.");
return surface;
return bundle;
}
} // namespace filament::backend

View File

@@ -29,7 +29,8 @@ public:
Driver* createDriver(void* const sharedContext, const Platform::DriverConfig& driverConfig) noexcept override;
void* createVkSurfaceKHR(void* nativeWindow, void* instance, uint64_t flags) noexcept override;
VulkanPlatform::SurfaceBundle createVkSurfaceKHR(void* nativeWindow, void* instance,
uint64_t flags) noexcept override;
int getOSVersion() const noexcept override { return 0; }

View File

@@ -395,9 +395,14 @@ void VulkanDriver::createSyncR(Handle<HwSync> sh, int) {
void VulkanDriver::createSwapChainR(Handle<HwSwapChain> sch, void* nativeWindow, uint64_t flags) {
const VkInstance instance = mContext.instance;
auto vksurface = (VkSurfaceKHR) mContextManager.createVkSurfaceKHR(nativeWindow, instance,
flags);
construct<VulkanSwapChain>(sch, mContext, mStagePool, vksurface);
auto bundle = mContextManager.createVkSurfaceKHR(nativeWindow, instance, flags);
VkSurfaceKHR surface = (VkSurfaceKHR) bundle.surface;
VkExtent2D fallback{bundle.width, bundle.height};
if (fallback.width > 0 && fallback.height > 0) {
construct<VulkanSwapChain>(sch, mContext, mStagePool, surface, fallback);
} else {
construct<VulkanSwapChain>(sch, mContext, mStagePool, surface);
}
}
void VulkanDriver::createSwapChainHeadlessR(Handle<HwSwapChain> sch,

View File

@@ -23,6 +23,10 @@
using namespace bluevk;
using namespace utils;
namespace {
constexpr uint32_t VULKAN_UNDEFINED_EXTENT = 0xFFFFFFFF;
} // anonymous namespace
namespace filament::backend {
bool VulkanSwapChain::acquire() {
@@ -127,8 +131,12 @@ void VulkanSwapChain::create(VulkanStagePool& stagePool) {
ASSERT_POSTCONDITION(foundSuitablePresentMode, "Desired present mode is not supported by this device.");
// Create the low-level swap chain.
clientSize = caps.currentExtent;
if (caps.currentExtent.width == VULKAN_UNDEFINED_EXTENT ||
caps.currentExtent.height == VULKAN_UNDEFINED_EXTENT) {
clientSize = mFallbackExtent;
} else {
clientSize = caps.currentExtent;
}
const VkCompositeAlphaFlagBitsKHR compositeAlpha = (caps.supportedCompositeAlpha & VK_COMPOSITE_ALPHA_INHERIT_BIT_KHR) ?
VK_COMPOSITE_ALPHA_INHERIT_BIT_KHR : VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR;
@@ -297,8 +305,10 @@ static void getPresentationQueue(VulkanContext& mContext, VulkanSwapChain& sc) {
}
// Primary SwapChain constructor. (not headless)
VulkanSwapChain::VulkanSwapChain(VulkanContext& context, VulkanStagePool& stagePool, VkSurfaceKHR vksurface) :
mContext(context) {
VulkanSwapChain::VulkanSwapChain(VulkanContext& context, VulkanStagePool& stagePool, VkSurfaceKHR vksurface,
VkExtent2D fallbackExtent) :
mContext(context),
mFallbackExtent(fallbackExtent) {
suboptimal = false;
surface = vksurface;
firstRenderPass = true;
@@ -341,9 +351,15 @@ bool VulkanSwapChain::hasResized() const {
if (surface == VK_NULL_HANDLE) {
return false;
}
VkSurfaceCapabilitiesKHR surfaceCapabilities;
vkGetPhysicalDeviceSurfaceCapabilitiesKHR(mContext.physicalDevice, surface, &surfaceCapabilities);
return !equivalent(clientSize, surfaceCapabilities.currentExtent);
VkSurfaceCapabilitiesKHR caps;
vkGetPhysicalDeviceSurfaceCapabilitiesKHR(mContext.physicalDevice, surface, &caps);
VkExtent2D perceivedExtent = caps.currentExtent;
// Create the low-level swap chain.
if (caps.currentExtent.width == VULKAN_UNDEFINED_EXTENT ||
caps.currentExtent.height == VULKAN_UNDEFINED_EXTENT) {
perceivedExtent = mFallbackExtent;
}
return !equivalent(clientSize, perceivedExtent);
}
VulkanTexture& VulkanSwapChain::getColorTexture() {

View File

@@ -28,10 +28,14 @@ namespace filament::backend {
struct VulkanSwapChain : public HwSwapChain {
VulkanSwapChain(VulkanContext& context, VulkanStagePool& stagePool, VkSurfaceKHR vksurface);
// The *fallbackExtent* parameter is for the case where the extent returned by the physical
// surface is 0xFFFFFFFF.
VulkanSwapChain(VulkanContext& context, VulkanStagePool& stagePool, VkSurfaceKHR vksurface,
VkExtent2D fallbackExtent={.width=640, .height=320});
// Headless constructor.
VulkanSwapChain(VulkanContext& context, VulkanStagePool& stagePool, uint32_t width, uint32_t height);
VulkanSwapChain(VulkanContext& context, VulkanStagePool& stagePool, uint32_t width,
uint32_t height);
bool acquire();
void create(VulkanStagePool& stagePool);
@@ -63,6 +67,7 @@ struct VulkanSwapChain : public HwSwapChain {
private:
VulkanContext& mContext;
uint32_t mCurrentSwapIndex = 0u;
const VkExtent2D mFallbackExtent = {};
// Color attachments are swapped, but depth is not. Typically there are 2 or 3 color attachments
// in a swap chain.

View File

@@ -32,15 +32,23 @@ void* getNativeWindow(SDL_Window* sdlWindow) {
}
else if (wmi.subsystem == SDL_SYSWM_WAYLAND) {
#if defined(FILAMENT_SUPPORTS_WAYLAND)
int width = 0;
int height = 0;
SDL_GetWindowSize(sdlWindow, &width, &height);
// Static is used here to allocate the struct pointer for the lifetime of the program.
// Without static the valid struct quickyly goes out of scope, and ends with seemingly
// random segfaults.
static struct {
struct wl_display *display;
struct wl_surface *surface;
uint32_t width;
uint32_t height;
} wayland {
wmi.info.wl.display,
wmi.info.wl.surface,
static_cast<uint32_t>(width),
static_cast<uint32_t>(height)
};
return (void *) &wayland;
#endif