Support both X11 and Wayland in the same build. (#3360)

* Support both X11 and Wayland in the same build.

 - Works for both Vulkan and OpenGL.
 - Remove --with-wayland from genie options.
 - Vulkan loads all three extensions for surface creation instead of only one.
 - Add width and height parameter to GlContext::createSwapChain(), which is needed for EGL to create
   a SwapChain with the given window size.
 - Dirty-fix the example-22-windows to recreate the FrameBuffer by first destroying and then
   recreating to make sure the window is released of its swapchain.
 - Fix dbgText glitch in example-22-windows.
 - Remove old X11-related dependencies for GLFW3.

* Formatting.
This commit is contained in:
Martijn Courteaux
2024-10-05 23:33:22 +02:00
committed by GitHub
parent 3f9fe0d34e
commit e488a07f1b
21 changed files with 224 additions and 242 deletions

View File

@@ -204,6 +204,20 @@ public:
m_fbh[viewId].idx = bgfx::kInvalidHandle;
}
// Before we reattach a SwapChain to the window
// we must actually free up the previous one.
// The DestroyFrameBuffer command goes in the
// cmdPost CommandBuffer, which happens after
// the frame. The CreateFrameBuffer command goes
// int the cmdPre CommandBuffer, which happens
// at the beginning of the frame. Without this
// bgfx::frame() call, the creation would happen
// before it's destroyed, which would cause
// the platform window to have two SwapChains
// associated with it.
// Ideally, we have an operation of ResizeFrameBuffer.
bgfx::frame();
win.m_nwh = m_state.m_nwh;
win.m_width = m_state.m_width;
win.m_height = m_state.m_height;
@@ -276,6 +290,7 @@ public:
int64_t now = bx::getHPCounter();
float time = (float)( (now-m_timeOffset)/double(bx::getHPFrequency() ) );
bgfx::dbgTextClear();
if (NULL != m_bindings)
{
bgfx::dbgTextPrintf(0, 1, 0x2f, "Press 'c' to create or 'd' to destroy window.");

View File

@@ -68,11 +68,15 @@ public:
static void remapIndices(uint32_t* _indices, uint32_t _num)
{
uint32_t target = 0;
for (uint32_t i = 0; i < _num; i++) {
for (uint32_t i = 0; i < _num; i++)
{
uint32_t map = _indices[i];
if (i != map) {
if (i != map)
{
_indices[i] = _indices[map];
} else {
}
else
{
_indices[i] = target;
++target;
}

View File

@@ -15,13 +15,9 @@
#endif // GLFW_VERSION_MINOR < 2
#if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
# include <wayland-egl.h>
# define GLFW_EXPOSE_NATIVE_WAYLAND
# else
# define GLFW_EXPOSE_NATIVE_X11
# define GLFW_EXPOSE_NATIVE_GLX
# endif
# define GLFW_EXPOSE_NATIVE_WAYLAND
# define GLFW_EXPOSE_NATIVE_X11
# define GLFW_EXPOSE_NATIVE_GLX
#elif BX_PLATFORM_OSX
# define GLFW_EXPOSE_NATIVE_COCOA
# define GLFW_EXPOSE_NATIVE_NSGL
@@ -45,12 +41,14 @@ namespace entry
static void* glfwNativeWindowHandle(GLFWwindow* _window)
{
# if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
struct wl_surface* surface = (struct wl_surface*)glfwGetWaylandWindow(_window);
return (void*)surface;
# else
return (void*)(uintptr_t)glfwGetX11Window(_window);
# endif
if (glfwGetPlatform() == GLFW_PLATFORM_WAYLAND)
{
return glfwGetWaylandWindow(_window);
}
else
{
return (void*)(uintptr_t)glfwGetX11Window(_window);
}
# elif BX_PLATFORM_OSX
return glfwGetCocoaWindow(_window);
# elif BX_PLATFORM_WINDOWS
@@ -58,23 +56,6 @@ namespace entry
# endif // BX_PLATFORM_
}
static void glfwDestroyWindowImpl(GLFWwindow *_window)
{
if(!_window)
return;
# if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
wl_egl_window *win_impl = (wl_egl_window*)glfwGetWindowUserPointer(_window);
if(win_impl)
{
glfwSetWindowUserPointer(_window, nullptr);
wl_egl_window_destroy(win_impl);
}
# endif
# endif
glfwDestroyWindow(_window);
}
static uint8_t translateKeyModifiers(int _glfw)
{
uint8_t modifiers = 0;
@@ -515,7 +496,7 @@ namespace entry
{
GLFWwindow* window = m_window[msg->m_handle.idx];
m_eventQueue.postWindowEvent(msg->m_handle);
glfwDestroyWindowImpl(window);
glfwDestroyWindow(window);
m_window[msg->m_handle.idx] = NULL;
}
}
@@ -607,7 +588,7 @@ namespace entry
m_eventQueue.postExitEvent();
m_thread.shutdown();
glfwDestroyWindowImpl(m_window[0]);
glfwDestroyWindow(m_window[0]);
glfwTerminate();
return m_thread.getExitCode();
@@ -855,11 +836,14 @@ namespace entry
void* getNativeDisplayHandle()
{
# if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
return glfwGetWaylandDisplay();
# else
return glfwGetX11Display();
# endif // ENTRY_CONFIG_USE_WAYLAND
if (glfwGetPlatform() == GLFW_PLATFORM_WAYLAND)
{
return glfwGetWaylandDisplay();
}
else
{
return glfwGetX11Display();
}
# else
return NULL;
# endif // BX_PLATFORM_*
@@ -868,11 +852,14 @@ namespace entry
bgfx::NativeWindowHandleType::Enum getNativeWindowHandleType()
{
# if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
return bgfx::NativeWindowHandleType::Wayland;
# else
return bgfx::NativeWindowHandleType::Default;
# endif // ENTRY_CONFIG_USE_WAYLAND
if (glfwGetPlatform() == GLFW_PLATFORM_WAYLAND)
{
return bgfx::NativeWindowHandleType::Wayland;
}
else
{
return bgfx::NativeWindowHandleType::Default;
}
# else
return bgfx::NativeWindowHandleType::Default;
# endif // BX_PLATFORM_*

View File

@@ -25,10 +25,6 @@
# define ENTRY_CONFIG_USE_GLFW 0
#endif // ENTRY_CONFIG_USE_GLFW
#ifndef ENTRY_CONFIG_USE_WAYLAND
# define ENTRY_CONFIG_USE_WAYLAND 0
#endif // ENTRY_CONFIG_USE_WAYLAND
#if !defined(ENTRY_CONFIG_USE_NATIVE) \
&& !ENTRY_CONFIG_USE_NOOP \
&& !ENTRY_CONFIG_USE_SDL \

View File

@@ -46,12 +46,14 @@ namespace entry
}
# if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
if (wmi.subsystem == SDL_SYSWM_WAYLAND)
return (void*)wmi.info.wl.surface;
else
# endif // ENTRY_CONFIG_USE_WAYLAND
return (void*)wmi.info.x11.window;
if (wmi.subsystem == SDL_SYSWM_WAYLAND)
{
return (void*)wmi.info.wl.surface;
}
else
{
return (void*)wmi.info.x11.window;
}
# elif BX_PLATFORM_OSX || BX_PLATFORM_IOS || BX_PLATFORM_VISIONOS
return wmi.info.cocoa.window;
# elif BX_PLATFORM_WINDOWS
@@ -61,13 +63,6 @@ namespace entry
# endif // BX_PLATFORM_
}
static void sdlDestroyWindow(SDL_Window* _window)
{
if(!_window)
return;
SDL_DestroyWindow(_window);
}
static uint8_t translateKeyModifiers(uint16_t _sdl)
{
uint8_t modifiers = 0;
@@ -779,7 +774,7 @@ namespace entry
if (isValid(handle) )
{
m_eventQueue.postWindowEvent(handle);
sdlDestroyWindow(m_window[handle.idx]);
SDL_DestroyWindow(m_window[handle.idx]);
m_window[handle.idx] = NULL;
}
}
@@ -873,7 +868,7 @@ namespace entry
while (bgfx::RenderFrame::NoContext != bgfx::renderFrame() ) {};
m_thread.shutdown();
sdlDestroyWindow(m_window[0]);
SDL_DestroyWindow(m_window[0]);
SDL_Quit();
return m_thread.getExitCode();
@@ -1063,12 +1058,10 @@ namespace entry
return NULL;
}
# if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
if (wmi.subsystem == SDL_SYSWM_WAYLAND)
return wmi.info.wl.display;
else
# endif // ENTRY_CONFIG_USE_WAYLAND
return wmi.info.x11.display;
if (wmi.subsystem == SDL_SYSWM_WAYLAND)
return wmi.info.wl.display;
else
return wmi.info.x11.display;
# else
return NULL;
# endif // BX_PLATFORM_*
@@ -1083,13 +1076,11 @@ namespace entry
return bgfx::NativeWindowHandleType::Default;
}
# if BX_PLATFORM_LINUX
# if ENTRY_CONFIG_USE_WAYLAND
if (wmi.subsystem == SDL_SYSWM_WAYLAND)
{
return bgfx::NativeWindowHandleType::Wayland;
}
else
# endif // ENTRY_CONFIG_USE_WAYLAND
{
return bgfx::NativeWindowHandleType::Default;
}

View File

@@ -851,14 +851,18 @@ namespace entry
if (utf16[0] >= 0xD800 && utf16[0] <= 0xDBFF) {
m_surrogate = utf16[0];
} else {
}
else
{
int utf16_len;
if (utf16[0] >= 0xDC00 && utf16[0] <= 0xDFFF) {
utf16[1] = utf16[0];
utf16[0] = m_surrogate;
m_surrogate = 0;
utf16_len = 2;
} else {
}
else
{
utf16_len = 1;
}

View File

@@ -79,12 +79,6 @@ project ("example-common")
}
end
if _OPTIONS["with-wayland"] then
defines {
"ENTRY_CONFIG_USE_WAYLAND=1",
}
end
configuration { "android-*" }
includedirs {
path.join(BGFX_DIR, "3rdparty/native_app_glue")

View File

@@ -20,11 +20,6 @@ newoption {
description = "Enable GLFW entry.",
}
newoption {
trigger = "with-wayland",
description = "Enable Wayland support.",
}
newoption {
trigger = "with-profiler",
description = "Enable build with intrusive profiler.",
@@ -187,10 +182,6 @@ end
function copyLib()
end
if _OPTIONS["with-wayland"] then
defines { "WL_EGL_PLATFORM=1" }
end
if _OPTIONS["with-sdl"] then
if os.is("windows") then
if not os.getenv("SDL2_DIR") then
@@ -245,15 +236,6 @@ function exampleProjectDefaults()
defines { "ENTRY_CONFIG_USE_GLFW=1" }
links { "glfw3" }
configuration { "linux or freebsd" }
links {
"Xrandr",
"Xinerama",
"Xi",
"Xxf86vm",
"Xcursor",
}
configuration { "osx*" }
linkoptions {
"-framework CoreVideo",

View File

@@ -35,13 +35,6 @@ project ("geometryv")
defines { "ENTRY_CONFIG_USE_SDL=1" }
links { "SDL2" }
configuration { "linux or freebsd" }
if _OPTIONS["with-wayland"] then
links {
"wayland-egl",
}
end
configuration { "x32", "windows" }
libdirs { "$(SDL2_DIR)/lib/x86" }
@@ -55,21 +48,6 @@ project ("geometryv")
defines { "ENTRY_CONFIG_USE_GLFW=1" }
links { "glfw3" }
configuration { "linux or freebsd" }
if _OPTIONS["with-wayland"] then
links {
"wayland-egl",
}
else
links {
"Xrandr",
"Xinerama",
"Xi",
"Xxf86vm",
"Xcursor",
}
end
configuration { "osx*" }
linkoptions {
"-framework CoreVideo",

View File

@@ -35,13 +35,6 @@ project "texturev"
defines { "ENTRY_CONFIG_USE_SDL=1" }
links { "SDL2" }
configuration { "linux or freebsd" }
if _OPTIONS["with-wayland"] then
links {
"wayland-egl",
}
end
configuration { "x32", "windows" }
libdirs { "$(SDL2_DIR)/lib/x86" }
@@ -55,21 +48,6 @@ project "texturev"
defines { "ENTRY_CONFIG_USE_GLFW=1" }
links { "glfw3" }
configuration { "linux or freebsd" }
if _OPTIONS["with-wayland"] then
links {
"wayland-egl",
}
else
links {
"Xrandr",
"Xinerama",
"Xi",
"Xxf86vm",
"Xcursor",
}
end
configuration { "osx*" }
linkoptions {
"-framework CoreVideo",

View File

@@ -124,7 +124,7 @@ EGL_IMPORT
}
#endif // BGFX_USE_GL_DYNAMIC_LIB
#if defined(WL_EGL_PLATFORM)
#if BX_PLATFORM_LINUX
# define WL_EGL_IMPORT \
WL_EGL_FUNC(struct wl_egl_window *, wl_egl_window_create, (struct wl_surface *, int, int) ) \
WL_EGL_FUNC(void, wl_egl_window_destroy, (struct wl_egl_window *)) \
@@ -159,7 +159,7 @@ WL_EGL_IMPORT
WL_EGL_IMPORT
# undef WL_EGL_FUNC
}
#endif // defined(WL_EGL_PLATFORM)
#endif // BX_PLATFORM_LINUX
# define GL_IMPORT(_optional, _proto, _func, _import) _proto _func = NULL
# include "glimports.h"
@@ -168,18 +168,32 @@ WL_EGL_IMPORT
struct SwapChainGL
{
SwapChainGL(EGLDisplay _display, EGLConfig _config, EGLContext _context, EGLNativeWindowType _nwh)
SwapChainGL(EGLDisplay _display, EGLConfig _config, EGLContext _context, EGLNativeWindowType _nwh, int _width, int _height)
: m_nwh(_nwh)
, m_display(_display)
# if BX_PLATFORM_LINUX
, m_eglWindow(NULL)
# endif
{
EGLSurface defaultSurface = eglGetCurrentSurface(EGL_DRAW);
BX_UNUSED(_width, _height);
if (EGLNativeWindowType(0) == _nwh)
{
m_surface = eglCreatePbufferSurface(m_display, _config, NULL);
}
else
{
# if BX_PLATFORM_LINUX
if (g_platformData.type == NativeWindowHandleType::Wayland)
{
// A wl_surface needs to be first wrapped in a wl_egl_window
// before it can be used to create the EGLSurface.
m_eglWindow = BGFX_WAYLAND_wl_egl_window_create( (wl_surface*)_nwh, _width, _height);
_nwh = (EGLNativeWindowType) m_eglWindow;
}
# endif
m_surface = eglCreateWindowSurface(m_display, _config, _nwh, NULL);
}
@@ -207,6 +221,12 @@ WL_EGL_IMPORT
EGL_CHECK(eglMakeCurrent(m_display, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT) );
EGL_CHECK(eglDestroyContext(m_display, m_context) );
EGL_CHECK(eglDestroySurface(m_display, m_surface) );
# if BX_PLATFORM_LINUX
if (m_eglWindow)
{
BGFX_WAYLAND_wl_egl_window_destroy(m_eglWindow);
}
# endif
EGL_CHECK(eglMakeCurrent(m_display, defaultSurface, defaultSurface, defaultContext) );
}
@@ -224,6 +244,9 @@ WL_EGL_IMPORT
EGLContext m_context;
EGLDisplay m_display;
EGLSurface m_surface;
# if BX_PLATFORM_LINUX
wl_egl_window *m_eglWindow;
# endif
};
# if BX_PLATFORM_RPI
@@ -366,17 +389,12 @@ WL_EGL_IMPORT
vc_dispmanx_update_submit_sync(dispmanUpdate);
# endif // BX_PLATFORM_ANDROID
# if defined(WL_EGL_PLATFORM)
# if BX_PLATFORM_LINUX
if (g_platformData.type == NativeWindowHandleType::Wayland)
{
m_waylandEglDll = waylandEglOpen();
// A wl_surface needs to be first wrapped in a wl_egl_window
// before it can be used to create the EGLSurface.
m_eglWindow = BGFX_WAYLAND_wl_egl_window_create( (wl_surface*)nwh, _width, _height);
nwh = m_eglWindow;
}
# endif // defined(WL_EGL_PLATFORM)
# endif
if (headless)
{
@@ -392,6 +410,15 @@ WL_EGL_IMPORT
}
else
{
# if BX_PLATFORM_LINUX
if (g_platformData.type == NativeWindowHandleType::Wayland)
{
// A wl_surface needs to be first wrapped in a wl_egl_window
// before it can be used to create the EGLSurface.
m_eglWindow = BGFX_WAYLAND_wl_egl_window_create( (wl_surface*)nwh, _width, _height);
nwh = (EGLNativeWindowType) m_eglWindow;
}
# endif
m_surface = eglCreateWindowSurface(m_display, m_config, nwh, NULL);
}
@@ -474,20 +501,21 @@ WL_EGL_IMPORT
void GlContext::destroy()
{
BX_TRACE("GLContext::destroy()");
if (NULL != m_display)
{
EGL_CHECK(eglMakeCurrent(m_display, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT) );
EGL_CHECK(eglDestroyContext(m_display, m_context) );
EGL_CHECK(eglDestroySurface(m_display, m_surface) );
# if defined(WL_EGL_PLATFORM)
# if BX_PLATFORM_LINUX
if (m_eglWindow)
{
BGFX_WAYLAND_wl_egl_window_destroy(m_eglWindow);
waylandEglClose(m_waylandEglDll);
m_waylandEglDll = NULL;
}
# endif // defined(WL_EGL_PLATFORM)
# endif
EGL_CHECK(eglTerminate(m_display) );
m_context = NULL;
@@ -521,7 +549,7 @@ WL_EGL_IMPORT
}
# elif BX_PLATFORM_EMSCRIPTEN
EMSCRIPTEN_CHECK(emscripten_set_canvas_element_size(HTML5_TARGET_CANVAS_SELECTOR, _width, _height) );
# elif defined(WL_EGL_PLATFORM)
# elif BX_PLATFORM_LINUX
if (NULL != m_eglWindow)
{
BGFX_WAYLAND_wl_egl_window_resize(m_eglWindow, _width, _height, 0, 0);
@@ -549,9 +577,9 @@ WL_EGL_IMPORT
;
}
SwapChainGL* GlContext::createSwapChain(void* _nwh)
SwapChainGL* GlContext::createSwapChain(void* _nwh, int _width, int _height)
{
return BX_NEW(g_allocator, SwapChainGL)(m_display, m_config, m_context, (EGLNativeWindowType)_nwh);
return BX_NEW(g_allocator, SwapChainGL)(m_display, m_config, m_context, (EGLNativeWindowType)_nwh, _width, _height);
}
void GlContext::destroySwapChain(SwapChainGL* _swapChain)

View File

@@ -11,6 +11,7 @@
#include <EGL/egl.h>
#include <EGL/eglext.h>
struct wl_egl_window;
// EGL pulls X11 crap...
#if defined(None)
@@ -32,14 +33,15 @@ namespace bgfx { namespace gl
struct GlContext
{
GlContext()
: m_current(NULL)
: m_eglDll(NULL)
, m_current(NULL)
, m_context(NULL)
, m_display(NULL)
, m_surface(NULL)
#if defined(WL_EGL_PLATFORM)
#if BX_PLATFORM_LINUX
, m_waylandEglDll(NULL)
, m_eglWindow(NULL)
#endif // defined(WL_EGL_PLATFORM)
#endif
, m_msaaContext(false)
{
}
@@ -49,7 +51,7 @@ namespace bgfx { namespace gl
void resize(uint32_t _width, uint32_t _height, uint32_t _flags);
uint64_t getCaps() const;
SwapChainGL* createSwapChain(void* _nwh);
SwapChainGL* createSwapChain(void* _nwh, int _w, int _h);
void destroySwapChain(SwapChainGL* _swapChain);
void swap(SwapChainGL* _swapChain = NULL);
void makeCurrent(SwapChainGL* _swapChain = NULL);
@@ -68,10 +70,10 @@ namespace bgfx { namespace gl
EGLDisplay m_display;
EGLSurface m_surface;
#if defined(WL_EGL_PLATFORM)
#if BX_PLATFORM_LINUX
void* m_waylandEglDll;
struct wl_egl_window *m_eglWindow;
#endif // defined(WL_EGL_PLATFORM)
#endif
// true when MSAA is handled by the context instead of using MSAA FBO
bool m_msaaContext;

View File

@@ -86,7 +86,7 @@ namespace bgfx { namespace gl
}
else
{
m_primary = createSwapChain((void*)canvas);
m_primary = createSwapChain((void*)canvas, (int)_width, (int)_height) );
}
if (0 != _width
@@ -122,9 +122,10 @@ namespace bgfx { namespace gl
EMSCRIPTEN_CHECK(emscripten_set_canvas_element_size(m_primary->m_canvas, (int) _width, (int) _height) );
}
SwapChainGL* GlContext::createSwapChain(void* _nwh)
SwapChainGL* GlContext::createSwapChain(void* _nwh, int _width, int _height)
{
emscripten_webgl_init_context_attributes(&s_attrs);
BX_UNUSED(_width, _height);
// Work around bug https://bugs.chromium.org/p/chromium/issues/detail?id=1045643 in Chrome
// by having alpha always enabled.

View File

@@ -26,7 +26,7 @@ namespace bgfx { namespace gl
void resize(uint32_t _width, uint32_t _height, uint32_t _flags);
uint64_t getCaps() const;
SwapChainGL* createSwapChain(void* _nwh);
SwapChainGL* createSwapChain(void* _nwh, int _width, int _height);
void destroySwapChain(SwapChainGL* _swapChain);
void swap(SwapChainGL* _swapChain = NULL);
void makeCurrent(SwapChainGL* _swapChain = NULL);

View File

@@ -335,8 +335,9 @@ namespace bgfx { namespace gl
return BGFX_CAPS_SWAP_CHAIN;
}
SwapChainGL* GlContext::createSwapChain(void* _nwh)
SwapChainGL* GlContext::createSwapChain(void* _nwh, int _width, int _height)
{
BX_UNUSED(_width, _height);
SwapChainGL* swapChain = BX_NEW(g_allocator, SwapChainGL)(_nwh);
int result = SetPixelFormat(swapChain->m_hdc, m_pixelFormat, &m_pfd);

View File

@@ -74,7 +74,7 @@ typedef void (APIENTRYP PFNGLSTENCILOPPROC) (GLenum fail, GLenum zfail, GLenum z
void resize(uint32_t _width, uint32_t _height, uint32_t _flags);
uint64_t getCaps() const;
SwapChainGL* createSwapChain(void* _nwh);
SwapChainGL* createSwapChain(void* _nwh, int _width, int _height);
void destroySwapChain(SwapChainGL* _swapChain);
void swap(SwapChainGL* _swapChain = NULL);
void makeCurrent(SwapChainGL* _swapChain = NULL);

View File

@@ -3399,10 +3399,10 @@ namespace bgfx { namespace d3d11
{
case UniformType::Mat3:
case UniformType::Mat3|kUniformFragmentBit:
{
{
float* value = (float*)data;
for (uint32_t ii = 0, count = num/3; ii < count; ++ii, loc += 3*16, value += 9)
{
{
Matrix4 mtx;
mtx.un.val[ 0] = value[0];
mtx.un.val[ 1] = value[1];

View File

@@ -3060,7 +3060,8 @@ namespace bgfx { namespace gl
}
#if BGFX_CONFIG_RENDERER_OPENGLES && (BGFX_CONFIG_RENDERER_OPENGLES < 30)
if (!m_maxMsaa && s_extension[Extension::IMG_multisampled_render_to_texture].m_supported) {
if (!m_maxMsaa && s_extension[Extension::IMG_multisampled_render_to_texture].m_supported)
{
GL_CHECK(glGetIntegerv(GL_MAX_SAMPLES_IMG, &m_maxMsaa) );
}
#endif // BGFX_CONFIG_RENDERER_OPENGLES < 30
@@ -7121,7 +7122,9 @@ namespace bgfx { namespace gl
{
attachment = GL_DEPTH_ATTACHMENT;
}
} else {
}
else
{
attachment = GL_COLOR_ATTACHMENT0 + colorIdx;
++colorIdx;
}
@@ -7151,7 +7154,7 @@ namespace bgfx { namespace gl
void FrameBufferGL::create(uint16_t _denseIdx, void* _nwh, uint32_t _width, uint32_t _height, TextureFormat::Enum _format, TextureFormat::Enum _depthFormat)
{
BX_UNUSED(_format, _depthFormat);
m_swapChain = s_renderGL->m_glctx.createSwapChain(_nwh);
m_swapChain = s_renderGL->m_glctx.createSwapChain(_nwh, _width, _height);
m_width = _width;
m_height = _height;
m_numTh = 0;

View File

@@ -533,7 +533,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
, TextureFormat::Unknown
, TextureFormat::UnknownDepth
);
#if BX_PLATFORM_VISIONOS
if (m_mainFrameBuffer.m_swapChain->m_useLayerRenderer)
{
@@ -923,7 +923,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
MTL_RELEASE(m_vertexDescriptor);
MTL_RELEASE(m_textureDescriptor);
MTL_RELEASE(m_samplerDescriptor);
#if BX_PLATFORM_VISIONOS
if (m_mainFrameBuffer.m_swapChain->m_useLayerRenderer)
{
@@ -1077,7 +1077,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
return cp_layer_renderer_configuration_get_color_format(layerConfiguration);
}
#endif // BX_PLATFORM_VISIONOS
return swapChain->m_metalLayer.pixelFormat;
}
@@ -1328,18 +1328,21 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
{
BX_UNUSED(_blitter);
}
#if BX_PLATFORM_VISIONOS
void calculateViewPorts(MTLViewport (&viewports)[2]) {
void calculateViewPorts(MTLViewport (&viewports)[2])
{
const int viewCount = 2;
for (int i = 0; i < viewCount; i++) {
for (int i = 0; i < viewCount; i++)
{
cp_view_t view = cp_drawable_get_view(m_mainFrameBuffer.m_swapChain->m_layerRendererDrawable, i);
cp_view_texture_map_t texture_map = cp_view_get_view_texture_map(view);
viewports[i] = cp_view_texture_map_get_viewport(texture_map);
}
}
void setVertexAmplification(RenderCommandEncoder& _rce) {
void setVertexAmplification(RenderCommandEncoder& _rce)
{
MTLVertexAmplificationViewMapping mapping0;
MTLVertexAmplificationViewMapping mapping1;
@@ -1399,7 +1402,8 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
#if BX_PLATFORM_VISIONOS
if (m_mainFrameBuffer.m_swapChain->m_useLayerRenderer)
{
if (cp_layer_renderer_configuration_get_layout(m_mainFrameBuffer.m_swapChain->m_layerRendererConfiguration) == cp_layer_renderer_layout_layered) {
if (cp_layer_renderer_configuration_get_layout(m_mainFrameBuffer.m_swapChain->m_layerRendererConfiguration) == cp_layer_renderer_layout_layered)
{
MTLViewport viewports[2];
calculateViewPorts(viewports);
rce.setViewports(viewports, 2);
@@ -1411,7 +1415,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
{
MTLViewport viewport = { 0.0f, 0.0f, (float)width, (float)height, 0.0f, 1.0f };
rce.setViewport(viewport);
MTLScissorRect rc = { 0, 0, width, height };
rce.setScissorRect(rc);
}
@@ -1499,7 +1503,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
}
}
#endif // BX_PLATFORM_VISIONOS
void flip() override
{
if (NULL == m_commandBuffer)
@@ -1983,7 +1987,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
Texture texture = cp_drawable_get_depth_texture(swapChain->m_layerRendererDrawable, 0);
_renderPassDescriptor.depthAttachment.texture = texture;
_renderPassDescriptor.stencilAttachment.texture = swapChain->m_backBufferStencil;
cp_layer_renderer_configuration_t layerConfiguration = cp_layer_renderer_get_configuration(swapChain->m_layerRenderer);
cp_layer_renderer_layout layout = cp_layer_renderer_configuration_get_layout(layerConfiguration);
if (layout == cp_layer_renderer_layout_layered)
@@ -2530,7 +2534,8 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
}
}
if (streamUsed) {
if (streamUsed)
{
vertexDesc.layouts[stream+1].stride = layout.getStride();
vertexDesc.layouts[stream+1].stepFunction = MTLVertexStepFunctionPerVertex;
}
@@ -2574,9 +2579,12 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
BX_PRAGMA_DIAGNOSTIC_PUSH();
BX_PRAGMA_DIAGNOSTIC_IGNORED_CLANG("-Wunguarded-availability-new");
BX_PRAGMA_DIAGNOSTIC_IGNORED_CLANG("-Wincompatible-pointer-types");
if (m_usesMTLBindings) {
if (m_usesMTLBindings)
{
processArguments(pso, reflection.vertexBindings, reflection.fragmentBindings);
} else {
}
else
{
processArguments(pso, reflection.vertexArguments, reflection.fragmentArguments);
}
BX_PRAGMA_DIAGNOSTIC_POP();
@@ -2630,9 +2638,12 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
BX_PRAGMA_DIAGNOSTIC_PUSH();
BX_PRAGMA_DIAGNOSTIC_IGNORED_CLANG("-Wunguarded-availability-new");
BX_PRAGMA_DIAGNOSTIC_IGNORED_CLANG("-Wincompatible-pointer-types");
if (m_usesMTLBindings) {
if (m_usesMTLBindings)
{
processArguments(pso, reflection.bindings, NULL);
} else {
}
else
{
processArguments(pso, reflection.arguments, NULL);
}
BX_PRAGMA_DIAGNOSTIC_POP();
@@ -3486,11 +3497,12 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
cp_layer_renderer_t layerRenderer = (cp_layer_renderer_t)_nwh;
m_layerRenderer = layerRenderer;
m_layerRendererConfiguration = cp_layer_renderer_get_configuration(m_layerRenderer);
if (cp_layer_renderer_configuration_get_layout(m_layerRendererConfiguration) == cp_layer_renderer_layout_dedicated) {
if (cp_layer_renderer_configuration_get_layout(m_layerRendererConfiguration) == cp_layer_renderer_layout_dedicated)
{
BX_WARN(false, "Dedicated layer renderer layout is not supported.");
}
retain(m_layerRendererConfiguration);
retain(m_layerRenderer);
}
@@ -3501,12 +3513,12 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
{
release(m_metalLayer);
}
#if !BX_PLATFORM_VISIONOS
if (NULL != NSClassFromString(@"MTKView") )
{
MTKView *view = (MTKView *)_nwh;
if (NULL != view
&& [view isKindOfClass:NSClassFromString(@"MTKView")])
{
@@ -3514,7 +3526,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
}
}
#endif
if (NULL != NSClassFromString(@"CAMetalLayer") )
{
if (NULL == m_metalLayer)
@@ -3527,7 +3539,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
BX_WARN(false, "Unable to create Metal device. Please set platform data window to a CAMetalLayer");
return;
}
m_metalLayer = metalLayer;
}
# elif BX_PLATFORM_OSX
@@ -3541,7 +3553,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
else
{
NSView *contentView;
if ([nvh isKindOfClass:[NSView class]])
{
contentView = (NSView*)nvh;
@@ -3556,7 +3568,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
BX_WARN(0, "Unable to create Metal device. Please set platform data window to an NSWindow, NSView, or CAMetalLayer");
return;
}
void (^setLayer)(void) = ^{
CALayer* layer = contentView.layer;
if(NULL != layer && [layer isKindOfClass:NSClassFromString(@"CAMetalLayer")])
@@ -3570,7 +3582,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
[contentView setLayer:m_metalLayer];
}
};
if ([NSThread isMainThread])
{
setLayer();
@@ -3579,7 +3591,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
{
bx::Semaphore semaphore;
bx::Semaphore* psemaphore = &semaphore;
CFRunLoopPerformBlock([[NSRunLoop mainRunLoop] getCFRunLoop],
kCFRunLoopCommonModes,
^{
@@ -3592,13 +3604,13 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
}
# endif // BX_PLATFORM_*
}
if (NULL == m_metalLayer)
{
BX_WARN(NULL != s_renderMtl->m_device, "Unable to create Metal device.");
return;
}
m_metalLayer.device = s_renderMtl->m_device;
m_metalLayer.pixelFormat = MTLPixelFormatBGRA8Unorm;
m_metalLayer.magnificationFilter = kCAFilterNearest;
@@ -3750,11 +3762,11 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
{
cp_frame_timing_t timing = cp_frame_predict_timing(m_frame);
if (timing == nullptr) { return nullptr; }
cp_frame_start_update(m_frame);
cp_frame_end_update(m_frame);
cp_time_wait_until(cp_frame_timing_get_optimal_input_time(timing));
cp_frame_start_submission(m_frame);
m_layerRendererDrawable = cp_frame_query_drawable(m_frame);
@@ -4616,7 +4628,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
vp.znear = 0.0f;
vp.zfar = 1.0f;
rce.setViewport(vp);
MTLScissorRect sciRect = {
viewState.m_rect.m_x,
viewState.m_rect.m_y,
@@ -4625,7 +4637,7 @@ BX_STATIC_ASSERT(BX_COUNTOF(s_accessNames) == Access::Count, "Invalid s_accessNa
};
rce.setScissorRect(sciRect);
}
if (BGFX_CLEAR_NONE != (clr.m_flags & BGFX_CLEAR_MASK)
&& !clearWithRenderPass)
{

View File

@@ -362,6 +362,20 @@ VK_IMPORT_DEVICE
KHR_draw_indirect_count,
KHR_get_physical_device_properties2,
# if BX_PLATFORM_ANDROID
KHR_android_surface,
# elif BX_PLATFORM_LINUX
KHR_wayland_surface,
KHR_xlib_surface,
KHR_xcb_surface,
# elif BX_PLATFORM_WINDOWS
KHR_win32_surface,
# elif BX_PLATFORM_OSX
MVK_macos_surface,
# elif BX_PLATFORM_NX
NN_vi_surface,
# endif
Count
};
@@ -386,6 +400,19 @@ VK_IMPORT_DEVICE
{ "VK_EXT_shader_viewport_index_layer", 1, false, false, true, Layer::Count },
{ "VK_KHR_draw_indirect_count", 1, false, false, true, Layer::Count },
{ "VK_KHR_get_physical_device_properties2", 1, false, false, true, Layer::Count },
# if BX_PLATFORM_ANDROID
{ VK_KHR_ANDROID_SURFACE_EXTENSION_NAME, 1, false, false, true, Layer::Count },
# elif BX_PLATFORM_LINUX
{ VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME, 1, false, false, true, Layer::Count },
{ VK_KHR_XLIB_SURFACE_EXTENSION_NAME, 1, false, false, true, Layer::Count },
{ VK_KHR_XCB_SURFACE_EXTENSION_NAME, 1, false, false, true, Layer::Count },
# elif BX_PLATFORM_WINDOWS
{ VK_KHR_WIN32_SURFACE_EXTENSION_NAME, 1, false, false, true, Layer::Count },
# elif BX_PLATFORM_OSX
{ VK_MVK_MACOS_SURFACE_EXTENSION_NAME, 1, false, false, true, Layer::Count },
# elif BX_PLATFORM_NX
{ VK_NN_VI_SURFACE_EXTENSION_NAME, 1, false, false, true, Layer::Count },
# endif
};
BX_STATIC_ASSERT(Extension::Count == BX_COUNTOF(s_extension) );
@@ -1178,7 +1205,7 @@ VK_IMPORT_DEVICE
#else
"libvulkan.so.1"
#endif // BX_PLATFORM_*
);
);
if (NULL == m_vulkan1Dll)
{
@@ -1244,12 +1271,11 @@ VK_IMPORT
}
uint32_t numEnabledExtensions = 0;
const char* enabledExtension[Extension::Count + 2];
const char* enabledExtension[Extension::Count + 1];
if (!headless)
{
enabledExtension[numEnabledExtensions++] = VK_KHR_SURFACE_EXTENSION_NAME;
enabledExtension[numEnabledExtensions++] = KHR_SURFACE_EXTENSION_NAME;
}
for (uint32_t ii = 0; ii < Extension::Count; ++ii)
@@ -4149,10 +4175,10 @@ VK_IMPORT_DEVICE
{
case UniformType::Mat3:
case UniformType::Mat3|kUniformFragmentBit:
{
{
float* value = (float*)data;
for (uint32_t ii = 0, count = num/3; ii < count; ++ii, loc += 3*16, value += 9)
{
{
Matrix4 mtx;
mtx.un.val[ 0] = value[0];
mtx.un.val[ 1] = value[1];
@@ -6514,7 +6540,8 @@ VK_DESTROY
bimg::TextureFormat::Enum tf = bimg::TextureFormat::Enum(m_textureFormat);
const bimg::ImageBlockInfo &blockInfo = bimg::getBlockInfo(tf);
for (uint32_t i = 0; i < _bufferImageCopyCount; ++i) {
for (uint32_t i = 0; i < _bufferImageCopyCount; ++i)
{
BX_ASSERT(
bx::uint32_mod(_bufferImageCopy[i].bufferOffset, blockInfo.blockSize) == 0
, "Misaligned texture of type %s to offset %u, which is not a multiple of %u."
@@ -6928,9 +6955,10 @@ VK_DESTROY
}
#elif BX_PLATFORM_LINUX
{
# if defined(WL_EGL_PLATFORM)
if (g_platformData.type == bgfx::NativeWindowHandleType::Wayland)
{
BGFX_FATAL(s_extension[Extension::KHR_wayland_surface].m_supported, Fatal::UnableToInitialize, VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME " not supported");
BGFX_FATAL(NULL != vkCreateWaylandSurfaceKHR, Fatal::UnableToInitialize, "vkCreateWaylandSurfaceKHR == 0");
VkWaylandSurfaceCreateInfoKHR sci;
sci.sType = VK_STRUCTURE_TYPE_WAYLAND_SURFACE_CREATE_INFO_KHR;
sci.pNext = NULL;
@@ -6940,10 +6968,10 @@ VK_DESTROY
result = vkCreateWaylandSurfaceKHR(instance, &sci, allocatorCb, &m_surface);
}
else
# endif // defined(WL_EGL_PLATFORM)
{
if (NULL != vkCreateXlibSurfaceKHR)
if (s_extension[Extension::KHR_xlib_surface].m_supported)
{
BGFX_FATAL(NULL != vkCreateXlibSurfaceKHR, Fatal::UnableToInitialize, "vkCreateXlibSurfaceKHR == 0")
VkXlibSurfaceCreateInfoKHR sci;
sci.sType = VK_STRUCTURE_TYPE_XLIB_SURFACE_CREATE_INFO_KHR;
sci.pNext = NULL;
@@ -6953,7 +6981,7 @@ VK_DESTROY
result = vkCreateXlibSurfaceKHR(instance, &sci, allocatorCb, &m_surface);
}
if (VK_SUCCESS != result)
if (VK_SUCCESS != result && s_extension[Extension::KHR_xcb_surface].m_supported)
{
void* xcbdll = bx::dlopen("libX11-xcb.so.1");
@@ -6965,6 +6993,8 @@ VK_DESTROY
union { void* ptr; xcb_window_t window; } cast = { m_nwh };
BGFX_FATAL(NULL != vkCreateXcbSurfaceKHR, Fatal::UnableToInitialize, "vkCreateXcbSurfaceKHR == 0")
VkXcbSurfaceCreateInfoKHR sci;
sci.sType = VK_STRUCTURE_TYPE_XCB_SURFACE_CREATE_INFO_KHR;
sci.pNext = NULL;

View File

@@ -8,34 +8,22 @@
#if BX_PLATFORM_ANDROID
# define VK_USE_PLATFORM_ANDROID_KHR
# define KHR_SURFACE_EXTENSION_NAME VK_KHR_ANDROID_SURFACE_EXTENSION_NAME
# define VK_IMPORT_INSTANCE_PLATFORM VK_IMPORT_INSTANCE_ANDROID
#elif BX_PLATFORM_LINUX
# if defined(WL_EGL_PLATFORM)
# define VK_USE_PLATFORM_WAYLAND_KHR
# endif // defined(WL_EGL_PLATFORM)
# define VK_USE_PLATFORM_WAYLAND_KHR
# define VK_USE_PLATFORM_XLIB_KHR
# define VK_USE_PLATFORM_XCB_KHR
# if defined(WL_EGL_PLATFORM)
# define KHR_SURFACE_EXTENSION_NAME VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME
# else
# define KHR_SURFACE_EXTENSION_NAME VK_KHR_XCB_SURFACE_EXTENSION_NAME
# endif // defined(WL_EGL_PLATFORM)
# define VK_IMPORT_INSTANCE_PLATFORM VK_IMPORT_INSTANCE_LINUX
#elif BX_PLATFORM_WINDOWS
# define VK_USE_PLATFORM_WIN32_KHR
# define KHR_SURFACE_EXTENSION_NAME VK_KHR_WIN32_SURFACE_EXTENSION_NAME
# define VK_IMPORT_INSTANCE_PLATFORM VK_IMPORT_INSTANCE_WINDOWS
#elif BX_PLATFORM_OSX
# define VK_USE_PLATFORM_MACOS_MVK
# define KHR_SURFACE_EXTENSION_NAME VK_MVK_MACOS_SURFACE_EXTENSION_NAME
# define VK_IMPORT_INSTANCE_PLATFORM VK_IMPORT_INSTANCE_MACOS
#elif BX_PLATFORM_NX
# define VK_USE_PLATFORM_VI_NN
# define KHR_SURFACE_EXTENSION_NAME VK_NN_VI_SURFACE_EXTENSION_NAME
# define VK_IMPORT_INSTANCE_PLATFORM VK_IMPORT_INSTANCE_NX
#else
# define KHR_SURFACE_EXTENSION_NAME ""
# define VK_IMPORT_INSTANCE_PLATFORM
#endif // BX_PLATFORM_*
@@ -73,7 +61,6 @@
/* VK_KHR_android_surface */ \
VK_IMPORT_INSTANCE_FUNC(true, vkCreateAndroidSurfaceKHR); \
#if defined(WL_EGL_PLATFORM)
#define VK_IMPORT_INSTANCE_LINUX \
/* VK_KHR_wayland_surface */ \
VK_IMPORT_INSTANCE_FUNC(true, vkCreateWaylandSurfaceKHR); \
@@ -85,17 +72,6 @@
VK_IMPORT_INSTANCE_FUNC(true, vkCreateXcbSurfaceKHR); \
VK_IMPORT_INSTANCE_FUNC(true, vkGetPhysicalDeviceXcbPresentationSupportKHR); \
#else
#define VK_IMPORT_INSTANCE_LINUX \
/* VK_KHR_xlib_surface */ \
VK_IMPORT_INSTANCE_FUNC(true, vkCreateXlibSurfaceKHR); \
VK_IMPORT_INSTANCE_FUNC(true, vkGetPhysicalDeviceXlibPresentationSupportKHR); \
/* VK_KHR_xcb_surface */ \
VK_IMPORT_INSTANCE_FUNC(true, vkCreateXcbSurfaceKHR); \
VK_IMPORT_INSTANCE_FUNC(true, vkGetPhysicalDeviceXcbPresentationSupportKHR); \
#endif // defined(WL_EGL_PLATFORM)
#define VK_IMPORT_INSTANCE_WINDOWS \
/* VK_KHR_win32_surface */ \
VK_IMPORT_INSTANCE_FUNC(true, vkCreateWin32SurfaceKHR); \