Load opengl32.dll before gdi32.dll

According to
http://stackoverflow.com/questions/199016/wglcreatecontext-in-c-sharp-failing-but-not-in-managed-c,
opengl32.dll must be loaded before gdi32.dll. Affect issue #19.
This commit is contained in:
Stefanos A. 2013-12-17 21:24:25 +01:00
parent f4f793a5d3
commit dd31b41f08
2 changed files with 22 additions and 15 deletions

View file

@ -34,6 +34,7 @@ namespace OpenTK.Platform.Windows
{ {
using Graphics; using Graphics;
using OpenTK.Input; using OpenTK.Input;
using System.Runtime.InteropServices;
class WinFactory : IPlatformFactory class WinFactory : IPlatformFactory
{ {
@ -41,6 +42,9 @@ namespace OpenTK.Platform.Windows
readonly object SyncRoot = new object(); readonly object SyncRoot = new object();
IInputDriver2 inputDriver; IInputDriver2 inputDriver;
internal static IntPtr OpenGLHandle { get; private set; }
const string OpenGLName = "OPENGL32.DLL";
public WinFactory() public WinFactory()
{ {
if (System.Environment.OSVersion.Version.Major <= 4) if (System.Environment.OSVersion.Version.Major <= 4)
@ -48,6 +52,11 @@ namespace OpenTK.Platform.Windows
throw new PlatformNotSupportedException("OpenTK requires Windows XP or higher"); throw new PlatformNotSupportedException("OpenTK requires Windows XP or higher");
} }
// Dynamically load opengl32.dll in order to use the extension loading capabilities of Wgl.
// Note: opengl32.dll must be loaded before gdi32.dll, otherwise strange failures may occur
// (such as "error: 2000" when calling wglSetPixelFormat or slowness/lag on specific GPUs).
LoadOpenGL();
if (System.Environment.OSVersion.Version.Major >= 6) if (System.Environment.OSVersion.Version.Major >= 6)
{ {
if (Toolkit.Options.EnableHighResolution) if (Toolkit.Options.EnableHighResolution)
@ -60,6 +69,17 @@ namespace OpenTK.Platform.Windows
} }
} }
static void LoadOpenGL()
{
OpenGLHandle = Functions.LoadLibrary(OpenGLName);
if (OpenGLHandle == IntPtr.Zero)
{
throw new ApplicationException(String.Format("LoadLibrary(\"{0}\") call failed with code {1}",
OpenGLName, Marshal.GetLastWin32Error()));
}
Debug.WriteLine(String.Format("Loaded opengl32.dll: {0}", OpenGLHandle));
}
#region IPlatformFactory Members #region IPlatformFactory Members
public virtual INativeWindow CreateNativeWindow(int x, int y, int width, int height, string title, GraphicsMode mode, GameWindowFlags options, DisplayDevice device) public virtual INativeWindow CreateNativeWindow(int x, int y, int width, int height, string title, GraphicsMode mode, GameWindowFlags options, DisplayDevice device)

View file

@ -30,9 +30,6 @@ namespace OpenTK.Platform.Windows
static readonly object LoadLock = new object(); static readonly object LoadLock = new object();
static readonly object SyncRoot = new object(); static readonly object SyncRoot = new object();
static IntPtr opengl32Handle;
const string opengl32Name = "OPENGL32.DLL";
bool vsync_supported; bool vsync_supported;
readonly WinGraphicsMode ModeSelector; readonly WinGraphicsMode ModeSelector;
@ -43,16 +40,6 @@ namespace OpenTK.Platform.Windows
{ {
lock (LoadLock) lock (LoadLock)
{ {
// Dynamically load opengl32.dll in order to use the extension loading capabilities of Wgl.
if (opengl32Handle == IntPtr.Zero)
{
opengl32Handle = Functions.LoadLibrary(opengl32Name);
if (opengl32Handle == IntPtr.Zero)
throw new ApplicationException(String.Format("LoadLibrary(\"{0}\") call failed with code {1}",
opengl32Name, Marshal.GetLastWin32Error()));
Debug.WriteLine(String.Format("Loaded opengl32.dll: {0}", opengl32Handle));
}
// We need to create a temp context in order to load // We need to create a temp context in order to load
// wgl extensions (e.g. for multisampling or GL3). // wgl extensions (e.g. for multisampling or GL3).
// We cannot rely on OpenTK.Platform.Wgl until we // We cannot rely on OpenTK.Platform.Wgl until we
@ -341,7 +328,7 @@ namespace OpenTK.Platform.Windows
IntPtr address = Wgl.GetProcAddress(function_string); IntPtr address = Wgl.GetProcAddress(function_string);
if (!IsValid(address)) if (!IsValid(address))
{ {
address = Functions.GetProcAddress(opengl32Handle, function_string); address = Functions.GetProcAddress(WinFactory.OpenGLHandle, function_string);
} }
return address; return address;
} }
@ -351,7 +338,7 @@ namespace OpenTK.Platform.Windows
IntPtr address = Wgl.GetProcAddress(function_string); IntPtr address = Wgl.GetProcAddress(function_string);
if (!IsValid(address)) if (!IsValid(address))
{ {
address = Functions.GetProcAddress(opengl32Handle, function_string); address = Functions.GetProcAddress(WinFactory.OpenGLHandle, function_string);
} }
return address; return address;
} }