diff --git a/README.md b/README.md index d3089261..7d28f407 100644 --- a/README.md +++ b/README.md @@ -87,6 +87,7 @@ GLFW bundles a number of dependencies in the `deps/` directory. - [X11] Bugfix: The original video mode was not restored on iconification of full screen windows - [X11] Bugfix: `GLFW_ARROW_CURSOR` selected the wrong cursor image + - [WGL] Made all WGL functions dynamically loaded - [WGL] Removed `GLFW_USE_DWM_SWAP_INTERVAL` compile-time option - [WGL] Bugfix: Swap interval was ignored when DWM was enabled - [GLX] Added dependency on `libdl` on systems where it provides `dlopen` diff --git a/src/wgl_context.c b/src/wgl_context.c index e76f3cf7..0d44c9ce 100644 --- a/src/wgl_context.c +++ b/src/wgl_context.c @@ -39,21 +39,21 @@ static void initWGLExtensions(_GLFWwindow* window) // Functions for WGL_EXT_extension_string // NOTE: These are needed by _glfwPlatformExtensionSupported window->wgl.GetExtensionsStringEXT = (PFNWGLGETEXTENSIONSSTRINGEXTPROC) - wglGetProcAddress("wglGetExtensionsStringEXT"); + _glfw_wglGetProcAddress("wglGetExtensionsStringEXT"); window->wgl.GetExtensionsStringARB = (PFNWGLGETEXTENSIONSSTRINGARBPROC) - wglGetProcAddress("wglGetExtensionsStringARB"); + _glfw_wglGetProcAddress("wglGetExtensionsStringARB"); // Functions for WGL_ARB_create_context window->wgl.CreateContextAttribsARB = (PFNWGLCREATECONTEXTATTRIBSARBPROC) - wglGetProcAddress("wglCreateContextAttribsARB"); + _glfw_wglGetProcAddress("wglCreateContextAttribsARB"); // Functions for WGL_EXT_swap_control window->wgl.SwapIntervalEXT = (PFNWGLSWAPINTERVALEXTPROC) - wglGetProcAddress("wglSwapIntervalEXT"); + _glfw_wglGetProcAddress("wglSwapIntervalEXT"); // Functions for WGL_ARB_pixel_format window->wgl.GetPixelFormatAttribivARB = (PFNWGLGETPIXELFORMATATTRIBIVARBPROC) - wglGetProcAddress("wglGetPixelFormatAttribivARB"); + _glfw_wglGetProcAddress("wglGetPixelFormatAttribivARB"); // This needs to include every extension used below except for // WGL_ARB_extensions_string and WGL_EXT_extensions_string @@ -282,6 +282,28 @@ int _glfwInitContextAPI(void) return GL_FALSE; } + _glfw.wgl.opengl32.CreateContext = (WGLCREATECONTEXT_T) + GetProcAddress(_glfw.wgl.opengl32.instance, "wglCreateContext"); + _glfw.wgl.opengl32.DeleteContext = (WGLDELETECONTEXT_T) + GetProcAddress(_glfw.wgl.opengl32.instance, "wglDeleteContext"); + _glfw.wgl.opengl32.GetProcAddress = (WGLGETPROCADDRESS_T) + GetProcAddress(_glfw.wgl.opengl32.instance, "wglGetProcAddress"); + _glfw.wgl.opengl32.MakeCurrent = (WGLMAKECURRENT_T) + GetProcAddress(_glfw.wgl.opengl32.instance, "wglMakeCurrent"); + _glfw.wgl.opengl32.ShareLists = (WGLSHARELISTS_T) + GetProcAddress(_glfw.wgl.opengl32.instance, "wglShareLists"); + + if (!_glfw.wgl.opengl32.CreateContext || + !_glfw.wgl.opengl32.DeleteContext || + !_glfw.wgl.opengl32.GetProcAddress || + !_glfw.wgl.opengl32.MakeCurrent || + !_glfw.wgl.opengl32.ShareLists) + { + _glfwInputError(GLFW_PLATFORM_ERROR, + "WGL: Failed to load opengl32 functions"); + return GL_FALSE; + } + return GL_TRUE; } @@ -426,7 +448,7 @@ int _glfwCreateContext(_GLFWwindow* window, } else { - window->wgl.context = wglCreateContext(window->wgl.dc); + window->wgl.context = _glfw_wglCreateContext(window->wgl.dc); if (!window->wgl.context) { _glfwInputError(GLFW_VERSION_UNAVAILABLE, @@ -436,7 +458,7 @@ int _glfwCreateContext(_GLFWwindow* window, if (share) { - if (!wglShareLists(share, window->wgl.context)) + if (!_glfw_wglShareLists(share, window->wgl.context)) { _glfwInputError(GLFW_PLATFORM_ERROR, "WGL: Failed to enable sharing with specified OpenGL context"); @@ -459,7 +481,7 @@ void _glfwDestroyContext(_GLFWwindow* window) { if (window->wgl.context) { - wglDeleteContext(window->wgl.context); + _glfw_wglDeleteContext(window->wgl.context); window->wgl.context = NULL; } @@ -568,9 +590,9 @@ int _glfwAnalyzeContext(const _GLFWwindow* window, void _glfwPlatformMakeContextCurrent(_GLFWwindow* window) { if (window) - wglMakeCurrent(window->wgl.dc, window->wgl.context); + _glfw_wglMakeCurrent(window->wgl.dc, window->wgl.context); else - wglMakeCurrent(NULL, NULL); + _glfw_wglMakeCurrent(NULL, NULL); _glfwSetContextTLS(window); } @@ -634,7 +656,7 @@ int _glfwPlatformExtensionSupported(const char* extension) GLFWglproc _glfwPlatformGetProcAddress(const char* procname) { - const GLFWglproc proc = (GLFWglproc) wglGetProcAddress(procname); + const GLFWglproc proc = (GLFWglproc) _glfw_wglGetProcAddress(procname); if (proc) return proc; diff --git a/src/wgl_context.h b/src/wgl_context.h index f7d41874..12e305d8 100644 --- a/src/wgl_context.h +++ b/src/wgl_context.h @@ -33,6 +33,18 @@ // extensions and not all operating systems come with an up-to-date version #include "../deps/GL/wglext.h" +// opengl32.dll function pointer typedefs +typedef HGLRC (WINAPI * WGLCREATECONTEXT_T)(HDC); +typedef BOOL (WINAPI * WGLDELETECONTEXT_T)(HGLRC); +typedef PROC (WINAPI * WGLGETPROCADDRESS_T)(LPCSTR); +typedef BOOL (WINAPI * WGLMAKECURRENT_T)(HDC,HGLRC); +typedef BOOL (WINAPI * WGLSHARELISTS_T)(HGLRC,HGLRC); +#define _glfw_wglCreateContext _glfw.wgl.opengl32.CreateContext +#define _glfw_wglDeleteContext _glfw.wgl.opengl32.DeleteContext +#define _glfw_wglGetProcAddress _glfw.wgl.opengl32.GetProcAddress +#define _glfw_wglMakeCurrent _glfw.wgl.opengl32.MakeCurrent +#define _glfw_wglShareLists _glfw.wgl.opengl32.ShareLists + #define _GLFW_PLATFORM_FBCONFIG int wgl #define _GLFW_PLATFORM_CONTEXT_STATE _GLFWcontextWGL wgl #define _GLFW_PLATFORM_LIBRARY_CONTEXT_STATE _GLFWlibraryWGL wgl @@ -70,9 +82,13 @@ typedef struct _GLFWcontextWGL // typedef struct _GLFWlibraryWGL { - // opengl32.dll (for glfwGetProcAddress) struct { - HINSTANCE instance; + HINSTANCE instance; + WGLCREATECONTEXT_T CreateContext; + WGLDELETECONTEXT_T DeleteContext; + WGLGETPROCADDRESS_T GetProcAddress; + WGLMAKECURRENT_T MakeCurrent; + WGLSHARELISTS_T ShareLists; } opengl32; } _GLFWlibraryWGL;