From 99e72830eaa956dacf614b4ac0f53a1046832b4d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Camilla=20L=C3=B6wy?= Date: Wed, 16 Aug 2017 20:54:14 +0200 Subject: [PATCH] X11: Add dynamic loading of libXcursor --- CMakeLists.txt | 4 +--- src/x11_init.c | 20 ++++++++++++++++++++ src/x11_platform.h | 14 ++++++++++++++ 3 files changed, 35 insertions(+), 3 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index fa543418..91becda9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -266,12 +266,10 @@ if (_GLFW_X11) # Check for Xcursor if (NOT X11_Xcursor_FOUND) - message(FATAL_ERROR "The Xcursor libraries and headers were not found") + message(FATAL_ERROR "The Xcursor headers were not found") endif() list(APPEND glfw_INCLUDE_DIR "${X11_Xcursor_INCLUDE_PATH}") - list(APPEND glfw_LIBRARIES "${X11_Xcursor_LIB}") - list(APPEND glfw_PKG_DEPS "xcursor") endif() diff --git a/src/x11_init.c b/src/x11_init.c index 90f5e34c..d6e58bb5 100644 --- a/src/x11_init.c +++ b/src/x11_init.c @@ -593,6 +593,17 @@ static GLFWbool initExtensions(void) RROutputChangeNotifyMask); } + _glfw.x11.xcursor.handle = dlopen("libXcursor.so.1", RTLD_LAZY | RTLD_GLOBAL); + if (_glfw.x11.xcursor.handle) + { + _glfw.x11.xcursor.ImageCreate = (PFN_XcursorImageCreate) + dlsym(_glfw.x11.xcursor.handle, "XcursorImageCreate"); + _glfw.x11.xcursor.ImageDestroy = (PFN_XcursorImageDestroy) + dlsym(_glfw.x11.xcursor.handle, "XcursorImageDestroy"); + _glfw.x11.xcursor.ImageLoadCursor = (PFN_XcursorImageLoadCursor) + dlsym(_glfw.x11.xcursor.handle, "XcursorImageLoadCursor"); + } + _glfw.x11.xinerama.handle = dlopen("libXinerama.so.1", RTLD_LAZY | RTLD_GLOBAL); if (_glfw.x11.xinerama.handle) { @@ -782,6 +793,9 @@ Cursor _glfwCreateCursorX11(const GLFWimage* image, int xhot, int yhot) int i; Cursor cursor; + if (!_glfw.x11.xcursor.handle) + return None; + XcursorImage* native = XcursorImageCreate(image->width, image->height); if (native == NULL) return None; @@ -894,6 +908,12 @@ void _glfwPlatformTerminate(void) _glfw.x11.randr.handle = NULL; } + if (_glfw.x11.xcursor.handle) + { + dlclose(_glfw.x11.xcursor.handle); + _glfw.x11.xcursor.handle = NULL; + } + if (_glfw.x11.xinerama.handle) { dlclose(_glfw.x11.xinerama.handle); diff --git a/src/x11_platform.h b/src/x11_platform.h index 05a6def8..50cba346 100644 --- a/src/x11_platform.h +++ b/src/x11_platform.h @@ -82,6 +82,13 @@ typedef int (* PFN_XRRUpdateConfiguration)(XEvent*); #define XRRSetCrtcGamma _glfw.x11.randr.SetCrtcGamma #define XRRUpdateConfiguration _glfw.x11.randr.UpdateConfiguration +typedef XcursorImage* (* PFN_XcursorImageCreate)(int,int); +typedef void (* PFN_XcursorImageDestroy)(XcursorImage*); +typedef Cursor (* PFN_XcursorImageLoadCursor)(Display*,const XcursorImage*); +#define XcursorImageCreate _glfw.x11.xcursor.ImageCreate +#define XcursorImageDestroy _glfw.x11.xcursor.ImageDestroy +#define XcursorImageLoadCursor _glfw.x11.xcursor.ImageLoadCursor + typedef Bool (* PFN_XineramaIsActive)(Display*); typedef Bool (* PFN_XineramaQueryExtension)(Display*,int*,int*); typedef XineramaScreenInfo* (* PFN_XineramaQueryScreens)(Display*,int*); @@ -319,6 +326,13 @@ typedef struct _GLFWlibraryX11 Atom format; } xdnd; + struct { + void* handle; + PFN_XcursorImageCreate ImageCreate; + PFN_XcursorImageDestroy ImageDestroy; + PFN_XcursorImageLoadCursor ImageLoadCursor; + } xcursor; + struct { GLFWbool available; void* handle;