Subversion Repositories AndroidProjects

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
1452 chris 1
#region --- License ---
2
/* Copyright (c) 2006, 2007 Stefanos Apostolopoulos
3
 * See license.txt for license info
4
 */
5
#endregion
6
 
7
#region --- Using Directives ---
8
 
9
using System;
10
using System.Collections.Generic;
11
using System.Text;
12
using System.Windows.Forms;
13
using System.Runtime.InteropServices;
14
using System.Reflection;
15
using System.Diagnostics;
16
using OpenTK.Graphics;
17
 
18
#endregion
19
 
20
namespace OpenTK.Platform
21
{
22
    /// <summary>
23
    /// Provides cross-platform utilities to help interact with the underlying platform.
24
    /// </summary>
25
    public static class Utilities
26
    {
27
        #region internal static bool ThrowOnX11Error
28
 
29
        static bool throw_on_error;
30
        internal static bool ThrowOnX11Error
31
        {
32
            get { return throw_on_error; }
33
            set
34
            {
35
                if (value && !throw_on_error)
36
                {
37
                    Type.GetType("System.Windows.Forms.XplatUIX11, System.Windows.Forms")
38
                        .GetField("ErrorExceptions", System.Reflection.BindingFlags.Static |
39
                            System.Reflection.BindingFlags.NonPublic)
40
                        .SetValue(null, true);
41
                    throw_on_error = true;
42
                }
43
                else if (!value && throw_on_error)
44
                {
45
                    Type.GetType("System.Windows.Forms.XplatUIX11, System.Windows.Forms")
46
                        .GetField("ErrorExceptions", System.Reflection.BindingFlags.Static |
47
                            System.Reflection.BindingFlags.NonPublic)
48
                        .SetValue(null, false);
49
                    throw_on_error = false;
50
                }
51
            }
52
        }
53
 
54
        #endregion
55
 
56
        #region internal static void LoadExtensions(Type type)
57
 
58
        delegate Delegate LoadDelegateFunction(string name, Type signature);
59
 
60
        /// <internal />
61
        /// <summary>Loads all extensions for the specified class. This function is intended
62
        /// for OpenGL, Wgl, Glx, OpenAL etc.</summary>
63
        /// <param name="type">The class to load extensions for.</param>
64
        /// <remarks>
65
        /// <para>The Type must contain a nested class called "Delegates".</para>
66
        /// <para>
67
        /// The Type must also implement a static function called LoadDelegate with the
68
        /// following signature:
69
        /// <code>static Delegate LoadDelegate(string name, Type signature)</code>
70
        /// </para>
71
        /// <para>This function allocates memory.</para>
72
        /// </remarks>
73
        internal static void LoadExtensions(Type type)
74
        {
75
            // Using reflection is more than 3 times faster than directly loading delegates on the first
76
            // run, probably due to code generation overhead. Subsequent runs are faster with direct loading
77
            // than with reflection, but the first time is more significant.
78
 
79
            int supported = 0;
80
            Type extensions_class = type.GetNestedType("Delegates", BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public);
81
            if (extensions_class == null)
82
                throw new InvalidOperationException("The specified type does not have any loadable extensions.");
83
 
84
            FieldInfo[] delegates = extensions_class.GetFields(BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public);
85
            if (delegates == null)
86
                throw new InvalidOperationException("The specified type does not have any loadable extensions.");
87
 
88
            MethodInfo load_delegate_method_info = type.GetMethod("LoadDelegate", BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public);
89
            if (load_delegate_method_info == null)
90
                throw new InvalidOperationException(type.ToString() + " does not contain a static LoadDelegate method.");
91
            LoadDelegateFunction LoadDelegate = (LoadDelegateFunction)Delegate.CreateDelegate(
92
                typeof(LoadDelegateFunction), load_delegate_method_info);
93
 
94
            Debug.Write("Load extensions for " + type.ToString() + "... ");
95
 
96
            System.Diagnostics.Stopwatch time = new System.Diagnostics.Stopwatch();
97
            time.Reset();
98
            time.Start();
99
 
100
            foreach (FieldInfo f in delegates)
101
            {
102
                Delegate d = LoadDelegate(f.Name, f.FieldType);
103
                if (d != null)
104
                    ++supported;
105
 
106
                f.SetValue(null, d);
107
            }
108
 
109
            FieldInfo rebuildExtensionList = type.GetField("rebuildExtensionList", BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public);
110
            if (rebuildExtensionList != null)
111
                rebuildExtensionList.SetValue(null, true);
112
 
113
            time.Stop();
114
            Debug.Print("{0} extensions loaded in {1} ms.", supported, time.ElapsedMilliseconds);
115
            time.Reset();
116
        }
117
 
118
        #endregion
119
 
120
        #region internal static bool TryLoadExtension(Type type, string extension)
121
 
122
        /// <internal />
123
        /// <summary>Loads the specified extension for the specified class. This function is intended
124
        /// for OpenGL, Wgl, Glx, OpenAL etc.</summary>
125
        /// <param name="type">The class to load extensions for.</param>
126
        /// <param name="extension">The extension to load.</param>
127
        /// <remarks>
128
        /// <para>The Type must contain a nested class called "Delegates".</para>
129
        /// <para>
130
        /// The Type must also implement a static function called LoadDelegate with the
131
        /// following signature:
132
        /// <code>static Delegate LoadDelegate(string name, Type signature)</code>
133
        /// </para>
134
        /// <para>This function allocates memory.</para>
135
        /// </remarks>
136
        internal static bool TryLoadExtension(Type type, string extension)
137
        {
138
            Type extensions_class = type.GetNestedType("Delegates", BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public);
139
            if (extensions_class == null)
140
            {
141
                Debug.Print(type.ToString(), " does not contain extensions.");
142
                return false;
143
            }
144
 
145
            LoadDelegateFunction LoadDelegate = (LoadDelegateFunction)Delegate.CreateDelegate(typeof(LoadDelegateFunction),
146
                type.GetMethod("LoadDelegate", BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public));
147
            if (LoadDelegate == null)
148
            {
149
                Debug.Print(type.ToString(), " does not contain a static LoadDelegate method.");
150
                return false;
151
            }
152
 
153
            FieldInfo f = extensions_class.GetField(extension, BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public);
154
            if (f == null)
155
            {
156
                Debug.Print("Extension \"", extension, "\" not found in ", type.ToString());
157
                return false;
158
            }
159
 
160
            Delegate old = f.GetValue(null) as Delegate;
161
            Delegate @new = LoadDelegate(f.Name, f.FieldType);
162
            if ((old != null ? old.Target : null) != (@new != null ? @new.Target : null))
163
            {
164
                f.SetValue(null, @new);
165
                FieldInfo rebuildExtensionList = type.GetField("rebuildExtensionList", BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public);
166
                if (rebuildExtensionList != null)
167
                    rebuildExtensionList.SetValue(null, true);
168
            }
169
            return @new != null;
170
        }
171
 
172
        #endregion
173
 
174
        #region --- Creating a Graphics Context ---
175
 
176
        /// <summary>
177
        /// Creates an IGraphicsContext instance for the specified window.
178
        /// </summary>
179
        /// <param name="mode">The GraphicsMode for the GraphicsContext.</param>
180
        /// <param name="window">An IWindowInfo instance describing the parent window for this IGraphicsContext.</param>
181
        /// <param name="major">The major OpenGL version number for this IGraphicsContext.</param>
182
        /// <param name="minor">The minor OpenGL version number for this IGraphicsContext.</param>
183
        /// <param name="flags">A bitwise collection of GraphicsContextFlags with specific options for this IGraphicsContext.</param>
184
        /// <returns>A new IGraphicsContext instance.</returns>
185
        [Obsolete("Call new OpenTK.Graphics.GraphicsContext() directly, instead.")]
186
        public static IGraphicsContext CreateGraphicsContext(
187
            GraphicsMode mode, IWindowInfo window,
188
            int major, int minor, GraphicsContextFlags flags)
189
        {
190
            GraphicsContext context = new GraphicsContext(mode, window, major, minor, flags);
191
            context.MakeCurrent(window);
192
 
193
            (context as IGraphicsContextInternal).LoadAll();
194
 
195
            return context;
196
        }
197
 
198
        #region CreateX11WindowInfo
199
 
200
        /// <summary>
201
        /// Constructs a new IWindowInfo instance for the X11 platform.
202
        /// </summary>
203
        /// <param name="display">The display connection.</param>
204
        /// <param name="screen">The screen.</param>
205
        /// <param name="windowHandle">The handle for the window.</param>
206
        /// <param name="rootWindow">The root window for screen.</param>
207
        /// <param name="visualInfo">A pointer to a XVisualInfo structure obtained through XGetVisualInfo.</param>
208
        /// <returns>A new IWindowInfo instance.</returns>
209
        public static IWindowInfo CreateX11WindowInfo(IntPtr display, int screen, IntPtr windowHandle, IntPtr rootWindow, IntPtr visualInfo)
210
        {
211
            Platform.X11.X11WindowInfo window = new OpenTK.Platform.X11.X11WindowInfo();
212
            window.Display = display;
213
            window.Screen = screen;
214
            window.WindowHandle = windowHandle;
215
            window.RootWindow = rootWindow;
216
            window.VisualInfo = (X11.XVisualInfo)Marshal.PtrToStructure(visualInfo, typeof(X11.XVisualInfo));
217
 
218
            return window;
219
        }
220
 
221
        #endregion
222
 
223
        #region CreateWindowsWindowInfo
224
 
225
        /// <summary>
226
        /// Creates an IWindowInfo instance for the windows platform.
227
        /// </summary>
228
        /// <param name="windowHandle">The handle of the window.</param>
229
        /// <returns>A new IWindowInfo instance.</returns>
230
        public static IWindowInfo CreateWindowsWindowInfo(IntPtr windowHandle)
231
        {
232
            return new OpenTK.Platform.Windows.WinWindowInfo(windowHandle, null);
233
        }
234
 
235
        #endregion
236
 
237
        #region CreateMacOSCarbonWindowInfo
238
 
239
        /// <summary>
240
        /// Creates an IWindowInfo instance for the Mac OS X platform.
241
        /// </summary>
242
        /// <param name="windowHandle">The handle of the window.</param>
243
        /// <param name="ownHandle">Ignored. This is reserved for future use.</param>
244
        /// <param name="isControl">Set to true if windowHandle corresponds to a System.Windows.Forms control.</param>
245
        /// <returns>A new IWindowInfo instance.</returns>
246
        public static IWindowInfo CreateMacOSCarbonWindowInfo(IntPtr windowHandle, bool ownHandle, bool isControl)
247
        {
248
            return new OpenTK.Platform.MacOS.CarbonWindowInfo(windowHandle, false, isControl);
249
        }
250
 
251
        #endregion
252
 
253
        #region CreateDummyWindowInfo
254
 
255
        /// <summary>
256
        /// Creates an IWindowInfo instance for the dummy platform.
257
        /// </summary>
258
        /// <returns>A new IWindowInfo instance.</returns>
259
        public static IWindowInfo CreateDummyWindowInfo()
260
        {
261
            return new Dummy.DummyWindowInfo();
262
        }
263
 
264
        #endregion
265
 
266
        #endregion
267
 
268
 
269
    }
270
}