#region --- License --- /* Copyright (c) 2006, 2007 Stefanos Apostolopoulos * See license.txt for license info */ #endregion #region --- Using Directives --- using System; using System.Collections.Generic; using System.Text; using System.Windows.Forms; using System.Runtime.InteropServices; #endregion namespace OpenTK.Platform { /// /// Provides cross-platform utilities to help interact with the underlying platform. /// public static class Utilities { #region --- LoadAddress --- internal interface ILoadAddress { IntPtr LoadAddress(string function); } internal class LoadAddressWindows : ILoadAddress { public IntPtr LoadAddress(string function) { return OpenTK.Platform.Windows.Wgl.Imports.GetProcAddress(function); } } internal class LoadAddressX11 : ILoadAddress { public IntPtr LoadAddress(string function) { return X11.Glx.GetProcAddress(function); } } internal class LoadAddressOSX : ILoadAddress { public IntPtr LoadAddress(string function) { string fname = "_" + function; if (!OSX.Functions.NSIsSymbolNameDefined(fname)) return IntPtr.Zero; IntPtr symbol = OSX.Functions.NSLookupAndBindSymbol(fname); if (symbol != IntPtr.Zero) symbol = OSX.Functions.NSAddressOfSymbol(symbol); return symbol; } } #endregion #region --- Fields --- /// /// Enumerates the platforms OpenTK can run on. /// private enum Platform { Unknown, Windows, X11, X11_ARB, OSX }; private static ILoadAddress loadAddress; #endregion private static Platform platform = Platform.Unknown; public static IWindowInfo GetWindowInfo(Form form) { throw new NotImplementedException(); } #region public static IntPtr GetAddress(string function) /// /// Retrieves the entry point for a dynamically exported OpenGL function. /// /// The function string for the OpenGL function (eg. "glNewList") /// /// An IntPtr contaning the address for the entry point, or IntPtr.Zero if the specified /// OpenGL function is not dynamically exported. /// /// /// /// The Marshal.GetDelegateForFunctionPointer method can be used to turn the return value /// into a call-able delegate. /// /// /// This function is cross-platform. It determines the underlying platform and uses the /// correct wgl, glx or agl GetAddress function to retrieve the function pointer. /// /// /// /// public static IntPtr GetAddress(string function) { if (platform == Platform.Unknown) { if (System.Environment.OSVersion.Platform == PlatformID.Win32NT || System.Environment.OSVersion.Platform == PlatformID.Win32S || System.Environment.OSVersion.Platform == PlatformID.Win32Windows || System.Environment.OSVersion.Platform == PlatformID.WinCE) { platform = Platform.Windows; loadAddress = new LoadAddressWindows(); } else if (System.Environment.OSVersion.Platform == PlatformID.Unix) { platform = Platform.X11; loadAddress = new LoadAddressX11(); } else { throw new PlatformNotSupportedException( "Extension loading is only supported under X11 and Windows. We are sorry for the inconvience."); } } return loadAddress.LoadAddress(function); } #endregion #region private static Delegate GetExtensionDelegate(string name, Type signature) /// /// Creates a System.Delegate that can be used to call a dynamically exported OpenGL function. /// /// The name of the OpenGL function (eg. "glNewList") /// The signature of the OpenGL function. /// /// A System.Delegate that can be used to call this OpenGL function or null /// if the function is not available in the current OpenGL context. /// internal static Delegate GetExtensionDelegate(string name, Type signature) { IntPtr address = GetAddress(name); if (address == IntPtr.Zero || address == new IntPtr(1) || // Workaround for buggy nvidia drivers which return address == new IntPtr(2)) // 1 or 2 instead of IntPtr.Zero for some extensions. { return null; } else { return Marshal.GetDelegateForFunctionPointer(address, signature); } } #endregion static bool throw_on_error; internal static bool ThrowOnX11Error { get { return throw_on_error; } set { if (value && !throw_on_error) { Type.GetType("System.Windows.Forms.XplatUIX11, System.Windows.Forms") .GetField("ErrorExceptions", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.NonPublic) .SetValue(null, true); throw_on_error = true; } else if (!value && throw_on_error) { Type.GetType("System.Windows.Forms.XplatUIX11, System.Windows.Forms") .GetField("ErrorExceptions", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.NonPublic) .SetValue(null, false); throw_on_error = false; } } } } }