public static PixelFormatValue[] PrioritizePixelFormats(Gdi.PIXELFORMATDESCRIPTOR[] unsortedFormats, bool requireDoubleBuffering, bool requireHardwareAccerleration) { ArrayList sortedFormats = new ArrayList(); for (int i = 0; i < unsortedFormats.Length; i++) { Gdi.PIXELFORMATDESCRIPTOR pfd = unsortedFormats[i]; long bpp = pfd.cColorBits; long depth = pfd.cDepthBits; bool pal = FormatUsesPalette(pfd); bool hardware = FormatSupportsAcceleration(pfd); bool opengl = FormatSupportsOpenGL(pfd); bool window = FormatSupportsWindow(pfd); bool bitmap = FormatSupportsBitmap(pfd); bool dbuff = FormatSupportsDoubleBuffering(pfd); //Recognize formats which do not meet minimum requirements first and foremost. if (!opengl || !window || bpp < 8 || depth < 8 || pal || requireDoubleBuffering != dbuff || requireHardwareAccerleration != hardware) { continue; } PixelFormatValue pfv = new PixelFormatValue(); pfv.pfd = pfd; pfv.formatNumber = i + 1; sortedFormats.Add(pfv); } sortedFormats.Sort(); return((PixelFormatValue[])sortedFormats.ToArray(typeof(PixelFormatValue))); }
protected Gdi.PIXELFORMATDESCRIPTOR GetPixelFormat() { Gdi.PIXELFORMATDESCRIPTOR lRet = new Gdi.PIXELFORMATDESCRIPTOR(); lRet.nSize = (short)Marshal.SizeOf(lRet); lRet.nVersion = 1; lRet.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; lRet.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; lRet.cColorBits = 16; lRet.cRedBits = 0; lRet.cRedShift = 0; lRet.cGreenBits = 0; lRet.cGreenShift = 0; lRet.cBlueBits = 0; lRet.cBlueShift = 0; lRet.cAlphaBits = 0; lRet.cAlphaShift = 0; lRet.cAccumBits = 0; lRet.cAccumRedBits = 0; lRet.cAccumGreenBits = 0; lRet.cAccumBlueBits = 0; lRet.cAccumAlphaBits = 0; lRet.cDepthBits = 16; lRet.cStencilBits = 0; lRet.cAuxBuffers = 0; lRet.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; lRet.bReserved = 0; lRet.dwLayerMask = 0; lRet.dwVisibleMask = 0; lRet.dwDamageMask = 0; return(lRet); }
private static void PopulatePixelFormatDescriptor(ref Gdi.PIXELFORMATDESCRIPTOR pfd) { pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; pfd.cColorBits = (byte)32; pfd.cRedBits = 0; pfd.cRedShift = 0; pfd.cGreenBits = 0; pfd.cGreenShift = 0; pfd.cBlueBits = 0; pfd.cBlueShift = 0; pfd.cAlphaBits = 0; pfd.cAlphaShift = 0; pfd.cAccumBits = 0; pfd.cAccumRedBits = 0; pfd.cAccumGreenBits = 0; pfd.cAccumBlueBits = 0; pfd.cAccumAlphaBits = 0; pfd.cDepthBits = 32; pfd.cStencilBits = 0; pfd.cAuxBuffers = 0; pfd.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; pfd.bReserved = 0; pfd.dwLayerMask = 0; pfd.dwVisibleMask = 0; pfd.dwDamageMask = 0; }
public bool SelectPixelFormat(IntPtr hdc, int colorDepth, int multisample) { Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; pfd.cColorBits = (byte)((colorDepth > 16) ? 24 : colorDepth); pfd.cAlphaBits = (byte)((colorDepth > 16) ? 8 : 0); pfd.cDepthBits = 24; pfd.cStencilBits = 8; int[] format = new int[1]; if (multisample != 0) { // only available with driver support if (!_hasMultisample || !_hasPixelFormatARB) { return(false); } int[] iattr = { Wgl.WGL_DRAW_TO_WINDOW_ARB, 1, Wgl.WGL_SUPPORT_OPENGL_ARB, 1, Wgl.WGL_DOUBLE_BUFFER_ARB, 1, Wgl.WGL_SAMPLE_BUFFERS_ARB, 1, Wgl.WGL_ACCELERATION_ARB, Wgl.WGL_FULL_ACCELERATION_ARB, Wgl.WGL_COLOR_BITS_ARB, pfd.cColorBits, Wgl.WGL_ALPHA_BITS_ARB, pfd.cAlphaBits, Wgl.WGL_DEPTH_BITS_ARB, pfd.cDepthBits, Wgl.WGL_STENCIL_BITS_ARB, pfd.cStencilBits, Wgl.WGL_SAMPLES_ARB, multisample, 0 }; int[] nformats = new int[1]; //int nformats; Debug.Assert(_wglChoosePixelFormatARB != null, "failed to get proc address for ChoosePixelFormatARB"); // ChoosePixelFormatARB proc address was obtained when setting up a dummy GL context in initialiseWGL() // since glew hasn't been initialized yet, we have to cheat and use the previously obtained address bool result = Wgl.wglChoosePixelFormatARB(hdc, iattr, null, 1, format, nformats); // Tao 2.0 //int result = Wgl.wglChoosePixelFormatARB( _wglChoosePixelFormatARB, hdc, iattr, null, 1, format, out nformats ); if (!result || nformats[0] <= 0) // Tao 2.0 //if ( result == 0 || nformats <= 0 ) { return(false); } } else { format[0] = Gdi.ChoosePixelFormat(hdc, ref pfd); } return(format[0] != 0 && Gdi.SetPixelFormat(hdc, format[0], ref pfd)); }
private void SetupGL() { _hDC = User.GetDC(_controlHandle); Debug.Assert(_hDC != IntPtr.Zero); if (_hDC == IntPtr.Zero) { return; } Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); //ZeroMemory( &pfd, sizeof( pfd ) ); pfd.nSize = ( short )sizeof(Gdi.PIXELFORMATDESCRIPTOR); pfd.nVersion = 1; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_TYPE_RGBA; #if VSYNC //pfd.dwFlags |= Gdi.PFD_DOUBLEBUFFER; #endif pfd.iPixelType = Gdi.PFD_TYPE_RGBA; pfd.cColorBits = 24; pfd.cDepthBits = 32; pfd.iLayerType = Gdi.PFD_MAIN_PLANE; int iFormat = Gdi.ChoosePixelFormat(_hDC, ref pfd); bool spf = Gdi.SetPixelFormat(_hDC, iFormat, ref pfd); Wgl.wglMakeCurrent(IntPtr.Zero, IntPtr.Zero); _hRC = Wgl.wglCreateContext(_hDC); Debug.Assert(_hRC != IntPtr.Zero); if (_hRC == IntPtr.Zero) { User.ReleaseDC(_controlHandle, _hDC); _hDC = IntPtr.Zero; return; } bool mc = Wgl.wglMakeCurrent(_hDC, _hRC); Gl.glShadeModel(Gl.GL_SMOOTH); Gl.glClearColor(0.0f, 0.5f, 0.5f, 1.0f); Gl.glClearDepth(0.0f); //Gl.glEnable( Gl.GL_DEPTH_TEST ); Gl.glDepthFunc(Gl.GL_LEQUAL); Gl.glDepthRange(1.0f, 0.0f); Gl.glAlphaFunc(Gl.GL_GREATER, 0.03f); Gl.glHint(Gl.GL_PERSPECTIVE_CORRECTION_HINT, Gl.GL_NICEST); Gl.glFogi(Gl.GL_FOG_MODE, Gl.GL_LINEAR); Gl.glFogf(Gl.GL_FOG_DENSITY, 0.1f); Gl.glHint(Gl.GL_FOG_HINT, Gl.GL_DONT_CARE); #if !VSYNC Wgl.wglSwapIntervalEXT(0); #endif this.Resize(_screenWidth, _screenHeight); _defaultProgram = new DefaultProgram(); _defaultProgram.Prepare(); }
public static void EnableOpenGL(IntPtr ghDC) { int PixFormat; // pixed format // Pixed descriptor Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // Set memory //ZeroMemory(pfd, Microsoft.VisualBasic.Strings.Len(pfd)); // Pixel descriptor configuration pfd.nSize = (short)Microsoft.VisualBasic.Strings.Len(pfd); pfd.nVersion = 1; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = Gdi.PFD_TYPE_RGBA; pfd.cColorBits = 24; pfd.cDepthBits = 32; pfd.cAlphaBits = 24; pfd.iLayerType = Gdi.PFD_MAIN_PLANE; // Chose pixel format PixFormat = Gdi.ChoosePixelFormat((IntPtr)ghDC, ref pfd); // If the operation failed let user know if (PixFormat == 0) { //MessageBox.Show("Can't create OpenGL context!", "Saturn", MessageBoxButtons.OK, MessageBoxIcon.Error); enable = false; return; } if (!Gdi.SetPixelFormat((IntPtr)ghDC, PixFormat, ref pfd)) { //MessageBox.Show("Unable to set pixel format", "Saturn", MessageBoxButtons.OK, MessageBoxIcon.Error); enable = false; return; } // Set graphic context hRC = Wgl.wglCreateContext(ghDC); // If the operation failed let user know if (hRC.ToInt32() == 0) { //MessageBox.Show("Unable to get rendering context", "Saturn", MessageBoxButtons.OK, MessageBoxIcon.Error); enable = false; return; } if (!(Wgl.wglMakeCurrent(ghDC, hRC))) { //MessageBox.Show("Unable to make rendering context current", "Saturn", MessageBoxButtons.OK, MessageBoxIcon.Error); enable = false; return; } enable = true; // GL has been enabled }
/// <summary> /// ピクセルフォーマットの設定をする /// </summary> protected void SetupPixelFormat() { try { //PIXELFORMATDESCRIPTORの設定 Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // OpenGLをサポート、ウィンドウに描画、ダブルバッファ。 pfd.dwFlags = Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = Gdi.PFD_TYPE_RGBA; //RGBAフォーマット pfd.cColorBits = 32; // 32bit/pixel pfd.cAlphaBits = 8; // アルファチャンネル8bit (0にするとアルファチャンネル無しになる) pfd.cDepthBits = 32; // デプスバッファ32bit //デバイスコンテキストハンドルの収録 this.hDC = User.GetDC(viewCtlObj.Handle); //ピクセルフォーマットを選択 int pixelFormat = Gdi.ChoosePixelFormat(this.hDC, ref pfd); if (pixelFormat == 0) { this.viewCtlObj = null; throw new Exception("Error: Cant't Find A Suitable PixelFormat."); } //ピクセルフォーマットを設定 if (!Gdi.SetPixelFormat(this.hDC, pixelFormat, ref pfd)) { this.viewCtlObj = null; throw new Exception("Error: Cant't Set The PixelFormat."); } //レンダリングコンテキストを生成 this.hRC = Wgl.wglCreateContext(this.hDC); if (this.hRC == IntPtr.Zero) { this.viewCtlObj = null; throw new Exception("Error: Cant Create A GLRendering Context."); } //レンダリングコンテキストをカレントにする Wgl.wglMakeCurrent(this.hDC, this.hRC); //GLエラーのチェック int err = Gl.glGetError(); if (err != Gl.GL_NO_ERROR) { this.viewCtlObj = null; throw new Exception("GL Error:" + err.ToString()); } } catch (Exception ex) { Tracer.WriteError("ピクセルフォーマットの設定中にエラー発生 メッセージ {0} \r\n{1}", ex.Message.ToString(), ex.StackTrace.ToString()); } }
/// <summary> /// Creates the device and rendering contexts using the supplied settings /// in accumBits, colorBits, depthBits, and stencilBits. /// </summary> protected virtual void CreateContexts() { //Make sure the handle for this control has been created #if !MONO if (this.Handle == IntPtr.Zero) { throw new Exception("CreateContexts: The control's window handle has not been created."); } //Create device context deviceContext = User.GetDC(this.Handle); if (deviceContext == IntPtr.Zero) { throw new Exception("CreateContexts: Unable to create an OpenGL device context"); } int selectedFormat = 100; //Don't try more than 100 formats (too time consuming). Gdi.PIXELFORMATDESCRIPTOR pixelFormat = ChoosePixelFormatEx(deviceContext, //The window context. colorBits, //Bits-per-pixel of color depthBits, //Z-depth autoSwapBuffers?1:0, //Don't use double buffering. usehardware?1:0, ref selectedFormat); //Make sure the requested pixel format is available if (selectedFormat == 0) { throw new Exception("CreateContexts: Unable to find a suitable pixel format"); } if (!Gdi.SetPixelFormat(deviceContext, selectedFormat, ref pixelFormat)) { throw new Exception(string.Format("CreateContexts: Unable to set the requested pixel format ({0})", selectedFormat)); } //Create rendering context renderContext = Wgl.wglCreateContext(deviceContext); if (renderContext == IntPtr.Zero) { throw new Exception("CreateContexts: Unable to create an OpenGL rendering context"); } //Make this the current context MakeCurrentContext(); #else #warning OpenGLWinFormsControl currently broken in the Mono build. return; #endif }
///<summary>Returns the pixel formats from 1 to Max(maximumCount,maximum available pixel formats).</summary> public static Gdi.PIXELFORMATDESCRIPTOR[] GetPixelFormats(System.IntPtr hdc) { Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; int numFormats = _DescribePixelFormat(hdc, 1, (uint)pfd.nSize, ref pfd); Gdi.PIXELFORMATDESCRIPTOR[] pixelFormats = new Gdi.PIXELFORMATDESCRIPTOR[numFormats]; for (int i = 0; i < pixelFormats.Length; i++) { pixelFormats[i] = new Gdi.PIXELFORMATDESCRIPTOR(); pixelFormats[i].nSize = (short)Marshal.SizeOf(pixelFormats[i]); pixelFormats[i].nVersion = 1; _DescribePixelFormat(hdc, i + 1, (uint)pixelFormats[i].nSize, ref pixelFormats[i]); } return(pixelFormats); }
/// <summary> /// ピクセルフォーマットの設定をする /// </summary> private void SetupPixelFormat() { //PIXELFORMATDESCRIPTORの設定 Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.dwFlags = Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = Gdi.PFD_TYPE_RGBA; pfd.cColorBits = 32; pfd.cAlphaBits = 8; pfd.cDepthBits = 16; //デバイスコンテキストハンドルの収録 this.hDC = User.GetDC(this.Handle); //ピクセルフォーマットを選択 int pixelFormat = Gdi.ChoosePixelFormat(this.hDC, ref pfd); if (pixelFormat == 0) { throw new Exception("Error: Cant't Find A Suitable PixelFormat."); } //ピクセルフォーマットを設定 if (!Gdi.SetPixelFormat(this.hDC, pixelFormat, ref pfd)) { throw new Exception("Error: Cant't Set The PixelFormat."); } //レンダリングコンテキストを生成 this.hRC = Wgl.wglCreateContext(this.hDC); if (this.hRC == IntPtr.Zero) { throw new Exception("Error: Cant Create A GLRendering Context."); } //レンダリングコンテキストをカレントにする Wgl.wglMakeCurrent(this.hDC, this.hRC); //GLエラーのチェック int err = Gl.glGetError(); if (err != Gl.GL_NO_ERROR) { throw new Exception("GL Error:" + err.ToString()); } }
/// <summary> /// Add a context using the given win32 handle. /// </summary> /// <param name="handle">The win32 handle.</param> /// <param name="width">Width of the context.</param> /// <param name="height">Height of the context.</param> /// <returns></returns> public Context AddContext(IntPtr handle, int width, int height) { IntPtr deviceContext, renderingContext; Gdi.PIXELFORMATDESCRIPTOR pdf = new Gdi.PIXELFORMATDESCRIPTOR(); pdf.nSize = (short)Marshal.SizeOf(pdf); pdf.nVersion = 1; pdf.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pdf.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; pdf.cColorBits = 32; pdf.cDepthBits = 16; deviceContext = User.GetDC(handle); if (deviceContext == IntPtr.Zero) { return(null); } int pixelFormat = Gdi.ChoosePixelFormat(deviceContext, ref pdf); Gdi.SetPixelFormat(deviceContext, pixelFormat, ref pdf); renderingContext = Wgl.wglCreateContext(deviceContext); if (renderingContext == IntPtr.Zero) { return(null); } Context context = new Context(deviceContext, renderingContext, handle, width, height); contextList.Add(context); CurrentContext = context; SetBlend(BlendMode.ALPHA); SetClearColor(100, 100, 200); SetDrawColor(255, 255, 255); SetDrawAlpha(1.0f); SetOffset(0.0f, 0.0f); SetScale(1.0f, 1.0f); return(context); }
void AttachGLToWindow(/*FlurryAnimateChildInfo *child*/) { Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); //HACK pfd.nSize = (short)System.Runtime.InteropServices.Marshal.SizeOf(pfd); pfd.nVersion = 1; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL; pfd.iPixelType = Gdi.PFD_TYPE_RGBA; pfd.iLayerType = Gdi.PFD_MAIN_PLANE; pfd.cDepthBits = 16; pfd.cColorBits = 24; #if !USEFADEHACK if (Types.iSettingBufferMode != Types.BUFFER.BUFFER_MODE_SINGLE) { pfd.dwFlags |= Gdi.PFD_DOUBLEBUFFER; } #endif hdc = User.GetDC(this.Handle); //Win32.GDI.SetBkColor(hdc, 0); int iPixelFormat = Gdi.ChoosePixelFormat(hdc, ref pfd); Gdi.SetPixelFormat(hdc, iPixelFormat, ref pfd); // then use this to create a rendering context hglrc = Wgl.wglCreateContext(hdc); Wgl.wglMakeCurrent(hdc, hglrc); // tell Flurry to use the whole window as viewport //GetClientRect(child->hWnd, &rc); flgroup.SetSize(this.Width, this.Height); // some nice debug output //_RPT4(_CRT_WARN, " child 0x%08x: hWnd 0x%08x, hdc 0x%08x, hglrc 0x%08x\n", // child, child->hWnd, child->hdc, child->hglrc); //_RPT1(_CRT_WARN, " GL vendor: %s\n", glGetString(GL_VENDOR)); //_RPT1(_CRT_WARN, " GL renderer: %s\n", glGetString(GL_RENDERER)); //_RPT1(_CRT_WARN, " GL version: %s\n", glGetString(GL_VERSION)); //_RPT1(_CRT_WARN, " GL extensions: %s\n", glGetString(GL_EXTENSIONS)); //_RPT0(_CRT_WARN, "\n"); }
public RenderingSurface() { if (!DesignMode) { this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); this.SetStyle(ControlStyles.Opaque, true); this.SetStyle(ControlStyles.UserPaint, true); this.SetStyle(ControlStyles.ResizeRedraw, true); try { Gdi.PIXELFORMATDESCRIPTOR lPixelFormatDescription = GetPixelFormat(); mDeviceContext = User.GetDC(Handle); if (mDeviceContext == IntPtr.Zero) { throw new Exception("Could not get device context"); } int lPixelFormat = Gdi.ChoosePixelFormat(mDeviceContext, ref lPixelFormatDescription); if (Gdi.ChoosePixelFormat(mDeviceContext, ref lPixelFormatDescription) == 0) { throw new Exception("Could not find pixel format"); } if (!Gdi.SetPixelFormat(mDeviceContext, lPixelFormat, ref lPixelFormatDescription)) { throw new Exception("Could not set pixel format"); } } catch { Release(); } } }
internal GLContext(IntPtr handle) { _handle = handle; var descriptor = new Gdi.PIXELFORMATDESCRIPTOR(); descriptor.nSize = (short)Marshal.SizeOf(descriptor); descriptor.nVersion = 1; descriptor.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER | Gdi.PFD_SWAP_EXCHANGE; descriptor.iPixelType = Gdi.PFD_TYPE_RGBA; descriptor.cColorBits = 32; descriptor.cRedBits = 0; descriptor.cRedShift = 0; descriptor.cGreenBits = 0; descriptor.cGreenShift = 0; descriptor.cBlueBits = 0; descriptor.cBlueShift = 0; descriptor.cAlphaBits = 0; descriptor.cAlphaShift = 0; descriptor.cAccumBits = 0; descriptor.cAccumRedBits = 0; descriptor.cAccumGreenBits = 0; descriptor.cAccumBlueBits = 0; descriptor.cAccumAlphaBits = 0; descriptor.cDepthBits = 24; descriptor.cStencilBits = 8; descriptor.cAuxBuffers = 0; descriptor.iLayerType = Gdi.PFD_MAIN_PLANE; descriptor.bReserved = 0; descriptor.dwLayerMask = 0; descriptor.dwVisibleMask = 0; descriptor.dwDamageMask = 0; // Attempt to get the device context DeviceContext = User.GetDC(_handle); // Did we not get a device context? if (DeviceContext == IntPtr.Zero) { throw new GLContextException("Can not create a GL device context."); } // Attempt to find an appropriate pixel format var pixelFormat = Gdi.ChoosePixelFormat(DeviceContext, ref descriptor); // Did windows not find a matching pixel format? if (pixelFormat == 0) { throw new GLContextException("Can not find a suitable PixelFormat."); } // Are we not able to set the pixel format? if (!Gdi.SetPixelFormat(DeviceContext, pixelFormat, ref descriptor)) { throw new GLContextException($"Can not set the chosen PixelFormat. Chosen PixelFormat was {pixelFormat}."); } // Attempt to get the rendering context RenderingContext = Wgl.wglCreateContext(DeviceContext); if (RenderingContext == IntPtr.Zero) { throw new GLContextException("Can not create a GL rendering context."); } // Attempt to activate the rendering context MakeCurrent(); }
private void _initializeWgl() { // wglGetProcAddress does not work without an active OpenGL context, // but we need wglChoosePixelFormatARB's address before we can // create our main window. Thank you very much, Microsoft! // // The solution is to create a dummy OpenGL window first, and then // test for WGL_ARB_pixel_format support. If it is not supported, // we make sure to never call the ARB pixel format functions. // // If is is supported, we call the pixel format functions at least once // to initialize them (pointers are stored by glprocs.h). We can also // take this opportunity to enumerate the valid FSAA modes. SWF.Form frm = new SWF.Form(); IntPtr hwnd = frm.Handle; // if a simple CreateWindow fails, then boy are we in trouble... if (hwnd == IntPtr.Zero) { throw new Exception("Window creation failed"); } // no chance of failure and no need to release thanks to CS_OWNDC IntPtr hdc = User.GetDC(hwnd); // assign a simple OpenGL pixel format that everyone supports Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); ; pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; pfd.cColorBits = 16; pfd.cDepthBits = 15; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = Gdi.PFD_TYPE_RGBA; // if these fail, wglCreateContext will also quietly fail int format; format = Gdi.ChoosePixelFormat(hdc, ref pfd); if (format != 0) { Gdi.SetPixelFormat(hdc, format, ref pfd); } IntPtr hrc = Wgl.wglCreateContext(hdc); if (hrc != IntPtr.Zero) { // if wglMakeCurrent fails, wglGetProcAddress will return null Wgl.wglMakeCurrent(hdc, hrc); Wgl.ReloadFunctions(); // Tao 2.0 // check for pixel format and multisampling support //IntPtr wglGetExtensionsStringARB = Wgl.wglGetProcAddress( "wglGetExtensionsStringARB" ); //if ( wglGetExtensionsStringARB != IntPtr.Zero ) //{ // string exts = Wgl.wglGetExtensionsStringARB( wglGetExtensionsStringARB, hdc ); // _hasPixelFormatARB = exts.Contains( "WGL_ARB_pixel_format" ); // _hasMultisample = exts.Contains( "WGL_ARB_multisample" ); //} _hasPixelFormatARB = Wgl.IsExtensionSupported("WGL_ARB_pixel_format"); _hasMultisample = Wgl.IsExtensionSupported("WGL_ARB_multisample"); if (_hasPixelFormatARB && _hasMultisample) { // enumerate all formats w/ multisampling int[] iattr = { Wgl.WGL_DRAW_TO_WINDOW_ARB, 1, Wgl.WGL_SUPPORT_OPENGL_ARB, 1, Wgl.WGL_DOUBLE_BUFFER_ARB, 1, Wgl.WGL_SAMPLE_BUFFERS_ARB, 1, Wgl.WGL_ACCELERATION_ARB, Wgl.WGL_FULL_ACCELERATION_ARB, // We are no matter about the colour, depth and stencil buffers here //WGL_COLOR_BITS_ARB, 24, //WGL_ALPHA_BITS_ARB, 8, //WGL_DEPTH_BITS_ARB, 24, //WGL_STENCIL_BITS_ARB, 8, // Wgl.WGL_SAMPLES_ARB, 2, 0 }; int[] formats = new int[256]; int[] count = new int[256]; // Tao 2.0 //int count; // cheating here. wglChoosePixelFormatARB proc address needed later on // when a valid GL context does not exist and glew is not initialized yet. _wglChoosePixelFormatARB = Wgl.wglGetProcAddress("wglChoosePixelFormatARB"); if (Wgl.wglChoosePixelFormatARB(hdc, iattr, null, 256, formats, count)) // Tao 2.0 //if ( Wgl.wglChoosePixelFormatARB( _wglChoosePixelFormatARB, hdc, iattr, null, 256, formats, out count ) != 0 ) { // determine what multisampling levels are offered int query = Wgl.WGL_SAMPLES_ARB, samples; for (int i = 0; i < count[0]; ++i) // Tao 2.0 //for ( int i = 0; i < count[ 0 ]; ++i ) { IntPtr wglGetPixelFormatAttribivARB = Wgl.wglGetProcAddress("wglGetPixelFormatAttribivARB"); if (Wgl.wglGetPixelFormatAttribivARB(hdc, formats[i], 0, 1, ref query, out samples)) // Tao 2.0 //if ( Wgl.wglGetPixelFormatAttribivARB( wglGetPixelFormatAttribivARB, hdc, formats[ i ], 0, 1, ref query, out samples ) != 0 ) { if (!_fsaaLevels.Contains(samples)) { _fsaaLevels.Add(samples); } } } } } Wgl.wglMakeCurrent(IntPtr.Zero, IntPtr.Zero); Wgl.wglDeleteContext(hrc); } // clean up our dummy window and class frm.Dispose(); frm = null; }
public bool InitGLWindow(Control parent, int width, int height, int bits) { int pixelFormat; // Holds The Results After Searching For A Match this.parent = parent; GC.Collect(); // Request A Collection // This Forces A Swap Kernel.SetProcessWorkingSetSize(Process.GetCurrentProcess().Handle, -1, -1); Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // pfd Tells Windows How We Want Things To Be pfd.nSize = (short)Marshal.SizeOf(pfd); // Size Of This Pixel Format Descriptor pfd.nVersion = 1; // Version Number pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | // Format Must Support Window Gdi.PFD_SUPPORT_OPENGL | // Format Must Support OpenGL Gdi.PFD_DOUBLEBUFFER; // Format Must Support Double Buffering pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; // Request An RGBA Format pfd.cColorBits = (byte)bits; // Select Our Color Depth pfd.cRedBits = 0; // Color Bits Ignored pfd.cRedShift = 0; pfd.cGreenBits = 0; pfd.cGreenShift = 0; pfd.cBlueBits = 0; pfd.cBlueShift = 0; pfd.cAlphaBits = 0; // No Alpha Buffer pfd.cAlphaShift = 0; // Shift Bit Ignored pfd.cAccumBits = 0; // No Accumulation Buffer pfd.cAccumRedBits = 0; // Accumulation Bits Ignored pfd.cAccumGreenBits = 0; pfd.cAccumBlueBits = 0; pfd.cAccumAlphaBits = 0; pfd.cDepthBits = 16; // 16Bit Z-Buffer (Depth Buffer) pfd.cStencilBits = 0; // No Stencil Buffer pfd.cAuxBuffers = 0; // No Auxiliary Buffer pfd.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; // Main Drawing Layer pfd.bReserved = 0; // Reserved pfd.dwLayerMask = 0; // Layer Masks Ignored pfd.dwVisibleMask = 0; pfd.dwDamageMask = 0; hDC = User.GetDC(parent.Handle); // Attempt To Get A Device Context if (hDC == IntPtr.Zero) { // Did We Get A Device Context? KillGLWindow(); // Reset The Display MessageBox.Show("Can't Create A GL Device Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } pixelFormat = Gdi.ChoosePixelFormat(hDC, ref pfd); // Attempt To Find An Appropriate Pixel Format if (pixelFormat == 0) { // Did Windows Find A Matching Pixel Format? KillGLWindow(); // Reset The Display MessageBox.Show("Can't Find A Suitable PixelFormat.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } if (!Gdi.SetPixelFormat(hDC, pixelFormat, ref pfd)) { // Are We Able To Set The Pixel Format? KillGLWindow(); // Reset The Display MessageBox.Show("Can't Set The PixelFormat.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } hRC = Wgl.wglCreateContext(hDC); // Attempt To Get The Rendering Context if (hRC == IntPtr.Zero) { // Are We Able To Get A Rendering Context? KillGLWindow(); // Reset The Display MessageBox.Show("Can't Create A GL Rendering Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } if (!Wgl.wglMakeCurrent(hDC, hRC)) { // Try To Activate The Rendering Context KillGLWindow(); // Reset The Display MessageBox.Show("Can't Activate The GL Rendering Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } ReSizeGLScene(width, height); // Set Up Our Perspective GL Screen if (!InitGL()) { // Initialize Our Newly Created GL Window KillGLWindow(); // Reset The Display MessageBox.Show("Initialization Failed.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } return(true); // Everything Went OK }
/// <summary> /// Creates and sets the pixel format and creates and connects the deviceContext and renderContext. /// </summary> public void InitContexts() { int selectedPixelFormat; //Make sure the handle for this control has been created if (this.Handle == IntPtr.Zero) { throw new Exception("InitContexts: The control's window handle has not been created!"); } //Setup pixel format Gdi.PIXELFORMATDESCRIPTOR pixelFormat = new Gdi.PIXELFORMATDESCRIPTOR(); pixelFormat.nSize = (short)Marshal.SizeOf(pixelFormat); //Größe in Byte der Struktur pixelFormat.nVersion = 1; //Versionsnummer pixelFormat.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | //Kennzeichen Gdi.PFD_DOUBLEBUFFER; pixelFormat.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; //Echtfarb- bzw. Farbindexwerte pixelFormat.cColorBits = 32; //Anzahl der Farbbits pro Pixel; 4,8,16,24,32 = Summe von cRedBits+cGreenBits+cBlueBits pixelFormat.cRedBits = 0; //Anzahl Bits pro Pixel für Rotanteil pixelFormat.cRedShift = 0; //Verschiebung der Rotbits in der Farbe pixelFormat.cGreenBits = 0; //Anzahl Bits pro Pixel für Grünanteil pixelFormat.cGreenShift = 0; //Verschiebung der Grünbits in der Farbe pixelFormat.cBlueBits = 0; //Anzahl Bits pro Pixel für Blauanteil pixelFormat.cBlueShift = 0; //Verschiebung der Blaubits in der Farbe pixelFormat.cAlphaBits = 0; //nicht in der generischen Version pixelFormat.cAlphaShift = 0; //nicht in der generischen Version pixelFormat.cAccumBits = 0; //Anzahl Bits pro Pixel im Akkumulationsbuffer = Summe der folgenden vier Angaben pixelFormat.cAccumRedBits = 0; //BpP für Rot pixelFormat.cAccumGreenBits = 0; //BpP für Grün pixelFormat.cAccumBlueBits = 0; //BpP für Blau pixelFormat.cAccumAlphaBits = 0; //BpP für Alpha-Anteil pixelFormat.cDepthBits = 16; //16 oder 32 pixelFormat.cStencilBits = 0; //BpP im Stencilbuffer pixelFormat.cAuxBuffers = 0; //nicht in der generischen Version pixelFormat.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; //PFD_MAIN_PLANE pixelFormat.bReserved = 0; // = 0 pixelFormat.dwLayerMask = 0; //nicht in der generischen Version pixelFormat.dwVisibleMask = 0; //nicht in der generischen Version pixelFormat.dwDamageMask = 0; //nicht in der generischen Version //Create device context this.deviceContext = User.GetDC(this.Handle); if (this.deviceContext == IntPtr.Zero) { MessageBox.Show("InitContexts: Unable to create an OpenGL device context!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } //Choose the Pixel Format that is the closest to our pixelFormat selectedPixelFormat = Gdi.ChoosePixelFormat(this.deviceContext, ref pixelFormat); //Make sure the requested pixel format is available if (selectedPixelFormat == 0) { MessageBox.Show("InitContexts: Unable to find a suitable pixel format!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } //Sets the selected Pixel Format if (!Gdi.SetPixelFormat(this.deviceContext, selectedPixelFormat, ref pixelFormat)) { MessageBox.Show("InitContexts: Unable to set the requested pixel format!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } //Create rendering context this.renderContext = Wgl.wglCreateContext(this.deviceContext); if (this.renderContext == IntPtr.Zero) { MessageBox.Show("InitContexts: Unable to create an OpenGL rendering context!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } this.MakeCurrentContext(); }
public override void Create(string name, int width, int height, int colorDepth, bool isFullScreen, int left, int top, bool depthBuffer, params object[] miscParams) { // see if a OpenGLContext has been created yet if (hDC == IntPtr.Zero) { // grab the current display settings User.EnumDisplaySettings(null, User.ENUM_CURRENT_SETTINGS, out intialScreenSettings); if (isFullScreen) { Gdi.DEVMODE screenSettings = new Gdi.DEVMODE(); screenSettings.dmSize = (short)Marshal.SizeOf(screenSettings); screenSettings.dmPelsWidth = width; // Selected Screen Width screenSettings.dmPelsHeight = height; // Selected Screen Height screenSettings.dmBitsPerPel = colorDepth; // Selected Bits Per Pixel screenSettings.dmFields = Gdi.DM_BITSPERPEL | Gdi.DM_PELSWIDTH | Gdi.DM_PELSHEIGHT; // Try To Set Selected Mode And Get Results. NOTE: CDS_FULLSCREEN Gets Rid Of Start Bar. int result = User.ChangeDisplaySettings(ref screenSettings, User.CDS_FULLSCREEN); if (result != User.DISP_CHANGE_SUCCESSFUL) { throw new System.ComponentModel.Win32Exception(Marshal.GetLastWin32Error(), "Unable to change user display settings."); } } // grab the HWND from the supplied target control hWnd = (IntPtr)((Control)this.Handle).Handle; Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; pfd.cColorBits = (byte)colorDepth; pfd.cDepthBits = 32; // TODO: Find the best setting and use that pfd.cStencilBits = 8; pfd.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; // get the device context hDC = User.GetDC(hWnd); if (hDC == IntPtr.Zero) { throw new Exception("Cannot create a GL device context."); } // attempt to find an appropriate pixel format int pixelFormat = Gdi.ChoosePixelFormat(hDC, ref pfd); if (pixelFormat == 0) { throw new System.ComponentModel.Win32Exception(Marshal.GetLastWin32Error(), "Unable to find a suitable pixel format."); } if (!Gdi.SetPixelFormat(hDC, pixelFormat, ref pfd)) { throw new System.ComponentModel.Win32Exception(Marshal.GetLastWin32Error(), "Unable to set the pixel format."); } // attempt to get the rendering context hRC = Wgl.wglCreateContext(hDC); if (hRC == IntPtr.Zero) { throw new System.ComponentModel.Win32Exception(Marshal.GetLastWin32Error(), "Unable to create a GL rendering context."); } if (!Wgl.wglMakeCurrent(hDC, hRC)) { throw new System.ComponentModel.Win32Exception(Marshal.GetLastWin32Error(), "Unable to activate the GL rendering context."); } // init the GL context Gl.glShadeModel(Gl.GL_SMOOTH); // Enable Smooth Shading Gl.glClearColor(0.0f, 0.0f, 0.0f, 0.5f); // Black Background Gl.glClearDepth(1.0f); // Depth Buffer Setup Gl.glEnable(Gl.GL_DEPTH_TEST); // Enables Depth Testing Gl.glDepthFunc(Gl.GL_LEQUAL); // The Type Of Depth Testing To Do Gl.glHint(Gl.GL_PERSPECTIVE_CORRECTION_HINT, Gl.GL_NICEST); // Really Nice Perspective Calculations } // set the params of the window // TODO: deal with depth buffer this.Name = name; this.colorDepth = colorDepth; this.width = width; this.height = height; this.isFullScreen = isFullScreen; this.top = top; this.left = left; // make this window active this.isActive = true; }
void createGLWindow(string title) { int height = 400; int width = 600; int bpp = 16; int pixelFormat; form = null; GC.Collect(); Gdi.DEVMODE dmScreenSettings = new Gdi.DEVMODE(); dmScreenSettings.dmSize = (short)Marshal.SizeOf(dmScreenSettings); dmScreenSettings.dmPelsWidth = width; dmScreenSettings.dmPelsHeight = height; dmScreenSettings.dmBitsPerPel = bpp; dmScreenSettings.dmFields = Gdi.DM_BITSPERPEL | Gdi.DM_PELSWIDTH | Gdi.DM_PELSHEIGHT; form = new EngineOld();; //form.FormBorderStyle = FormBorderStyle.None; form.Width = width; // Set Window Width form.Height = height; // Set Window Height form.Text = title; Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // pfd Tells Windows How We Want Things To Be pfd.nSize = (short)Marshal.SizeOf(pfd); // Size Of This Pixel Format Descriptor pfd.nVersion = 1; // Version Number pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | // Format Must Support Window Gdi.PFD_SUPPORT_OPENGL | // Format Must Support OpenGL Gdi.PFD_DOUBLEBUFFER; // Format Must Support Double Buffering pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; // Request An RGBA Format pfd.cColorBits = (byte)bpp; // Select Our Color Depth pfd.cRedBits = 0; // Color Bits Ignored pfd.cRedShift = 0; pfd.cGreenBits = 0; pfd.cGreenShift = 0; pfd.cBlueBits = 0; pfd.cBlueShift = 0; pfd.cAlphaBits = 0; // No Alpha Buffer pfd.cAlphaShift = 0; // Shift Bit Ignored pfd.cAccumBits = 0; // No Accumulation Buffer pfd.cAccumRedBits = 0; // Accumulation Bits Ignored pfd.cAccumGreenBits = 0; pfd.cAccumBlueBits = 0; pfd.cAccumAlphaBits = 0; pfd.cDepthBits = 16; // 16Bit Z-Buffer (Depth Buffer) pfd.cStencilBits = 0; // No Stencil Buffer pfd.cAuxBuffers = 0; // No Auxiliary Buffer pfd.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; // Main Drawing Layer pfd.bReserved = 0; // Reserved pfd.dwLayerMask = 0; // Layer Masks Ignored pfd.dwVisibleMask = 0; pfd.dwDamageMask = 0; DC = User.GetDC(form.Handle); // Attempt To Get A Device Context if (DC == IntPtr.Zero) { // Did We Get A Device Context? killGLWindow(); // Reset The Display MessageBox.Show("Can't Create A GL Device Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); //**errorHandler } // Attempt To Find An Appropriate Pixel Format pixelFormat = Gdi.ChoosePixelFormat(DC, ref pfd); if (pixelFormat == 0) { // Did Windows Find A Matching Pixel Format? killGLWindow(); // Reset The Display MessageBox.Show("Can't Find A Suitable PixelFormat.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); } if (!Gdi.SetPixelFormat(DC, pixelFormat, ref pfd)) { // Are We Able To Set The Pixel Format? killGLWindow(); // Reset The Display MessageBox.Show("Can't Set The PixelFormat.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); } RC = Wgl.wglCreateContext(DC); // Attempt To Get The Rendering Context if (RC == IntPtr.Zero) { // Are We Able To Get A Rendering Context? killGLWindow(); // Reset The Display MessageBox.Show("Can't Create A GL Rendering Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); } if (!Wgl.wglMakeCurrent(DC, RC)) { // Try To Activate The Rendering Context killGLWindow(); // Reset The Display MessageBox.Show("Can't Activate The GL Rendering Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); } form.Show(); // Show The Window //form.TopMost = true; // Topmost Window form.Focus(); // Focus The Window InitLayout(); }
/// <summary> /// Creates and sets the pixel format and creates and connects the deviceContext and renderContext. /// </summary> internal void InitContexts() { int selectedPixelFormat; //Make sure the handle for this control has been created if (this.Handle == IntPtr.Zero) { throw new Exception("InitContexts: The control's window handle has not been created!"); } //Setup pixel format Gdi.PIXELFORMATDESCRIPTOR pixelFormat = new Gdi.PIXELFORMATDESCRIPTOR(); pixelFormat.nSize = (short)Marshal.SizeOf(pixelFormat); pixelFormat.nVersion = 1; pixelFormat.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pixelFormat.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; pixelFormat.cColorBits = 32; pixelFormat.cRedBits = 0; pixelFormat.cRedShift = 0; pixelFormat.cGreenBits = 0; pixelFormat.cGreenShift = 0; pixelFormat.cBlueBits = 0; pixelFormat.cBlueShift = 0; pixelFormat.cAlphaBits = 0; pixelFormat.cAlphaShift = 0; pixelFormat.cAccumBits = 0; pixelFormat.cAccumRedBits = 0; pixelFormat.cAccumGreenBits = 0; pixelFormat.cAccumBlueBits = 0; pixelFormat.cAccumAlphaBits = 0; pixelFormat.cDepthBits = 16; pixelFormat.cStencilBits = 0; pixelFormat.cAuxBuffers = 0; pixelFormat.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; pixelFormat.bReserved = 0; pixelFormat.dwLayerMask = 0; pixelFormat.dwVisibleMask = 0; pixelFormat.dwDamageMask = 0; //Create device context this.deviceContext = User.GetDC(this.Handle); if (this.deviceContext == IntPtr.Zero) { MessageBox.Show("InitContexts: Unable to create an OpenGL device context!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } //Choose the Pixel Format that is the closest to our pixelFormat selectedPixelFormat = Gdi.ChoosePixelFormat(this.deviceContext, ref pixelFormat); //Make sure the requested pixel format is available if (selectedPixelFormat == 0) { MessageBox.Show("InitContexts: Unable to find a suitable pixel format!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } //Sets the selected Pixel Format if (!Gdi.SetPixelFormat(this.deviceContext, selectedPixelFormat, ref pixelFormat)) { MessageBox.Show("InitContexts: Unable to set the requested pixel format!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } //Create rendering context this.renderContext = Wgl.wglCreateContext(this.deviceContext); if (this.renderContext == IntPtr.Zero) { MessageBox.Show("InitContexts: Unable to create an OpenGL rendering context!", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } this.MakeCurrentContext(); }
///<summary>Returns true if the given pixel format supports double-buffering, false otherwise.</summary> public static bool FormatSupportsDoubleBuffering(Gdi.PIXELFORMATDESCRIPTOR pfd) { return((pfd.dwFlags & Gdi.PFD_DOUBLEBUFFER) != 0); }
/// <summary> /// Creates the OpenGL contexts. /// </summary> public void InitializeContexts() { int pixelFormat; // Holds the selected pixel format windowHandle = this.Handle; // Get window handle if (windowHandle == IntPtr.Zero) // No window handle means something is wrong { MessageBox.Show("Window creation error. No window handle.", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // The pixel format descriptor pfd.nSize = (short)Marshal.SizeOf(pfd); // Size of the pixel format descriptor pfd.nVersion = 1; // Version number (always 1) pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | // Format must support windowed mode Gdi.PFD_SUPPORT_OPENGL | // Format must support OpenGL Gdi.PFD_DOUBLEBUFFER; // Must support double buffering pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; // Request an RGBA format pfd.cColorBits = (byte)colorBits; // Select our color depth pfd.cRedBits = 0; // Individual color bits ignored pfd.cRedShift = 0; pfd.cGreenBits = 0; pfd.cGreenShift = 0; pfd.cBlueBits = 0; pfd.cBlueShift = 0; pfd.cAlphaBits = 0; // No alpha buffer pfd.cAlphaShift = 0; // Alpha shift bit ignored pfd.cAccumBits = accumBits; // Accumulation buffer pfd.cAccumRedBits = 0; // Individual accumulation bits ignored pfd.cAccumGreenBits = 0; pfd.cAccumBlueBits = 0; pfd.cAccumAlphaBits = 0; pfd.cDepthBits = depthBits; // Z-buffer (depth buffer) pfd.cStencilBits = stencilBits; // No stencil buffer pfd.cAuxBuffers = 0; // No auxiliary buffer pfd.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; // Main drawing layer pfd.bReserved = 0; // Reserved pfd.dwLayerMask = 0; // Layer masks ignored pfd.dwVisibleMask = 0; pfd.dwDamageMask = 0; deviceContext = User.GetDC(windowHandle); // Attempt to get the device context if (deviceContext == IntPtr.Zero) // Did we not get a device context? { MessageBox.Show("Can not create a GL device context.", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } pixelFormat = Gdi.ChoosePixelFormat(deviceContext, ref pfd); // Attempt to find an appropriate pixel format if (pixelFormat == 0) // Did windows not find a matching pixel format? { MessageBox.Show("Can not find a suitable PixelFormat.", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } if (!Gdi.SetPixelFormat(deviceContext, pixelFormat, ref pfd)) // Are we not able to set the pixel format? { MessageBox.Show("Can not set the chosen PixelFormat. Chosen PixelFormat was " + pixelFormat + ".", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } renderingContext = Wgl.wglCreateContext(deviceContext); // Attempt to get the rendering context if (renderingContext == IntPtr.Zero) // Are we not able to get a rendering context? { MessageBox.Show("Can not create a GL rendering context.", "Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Error); Environment.Exit(-1); } MakeCurrent(); // Attempt to activate the rendering context // Force A Reset On The Working Set Size Kernel.SetProcessWorkingSetSize(Process.GetCurrentProcess().Handle, -1, -1); }
public bool SelectPixelFormat(IntPtr hdc, int colorDepth, int multisample) { Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; pfd.cColorBits = (byte)((colorDepth > 16) ? 24 : colorDepth); pfd.cAlphaBits = (byte)((colorDepth > 16) ? 8 : 0); pfd.cDepthBits = 24; pfd.cStencilBits = 8; int[] format = new int[1]; if (multisample != 0) { // only available with driver support if (!_hasMultisample || !_hasPixelFormatARB) return false; int[] iattr = { Wgl.WGL_DRAW_TO_WINDOW_ARB, 1, Wgl.WGL_SUPPORT_OPENGL_ARB, 1, Wgl.WGL_DOUBLE_BUFFER_ARB, 1, Wgl.WGL_SAMPLE_BUFFERS_ARB, 1, Wgl.WGL_ACCELERATION_ARB, Wgl.WGL_FULL_ACCELERATION_ARB, Wgl.WGL_COLOR_BITS_ARB, pfd.cColorBits, Wgl.WGL_ALPHA_BITS_ARB, pfd.cAlphaBits, Wgl.WGL_DEPTH_BITS_ARB, pfd.cDepthBits, Wgl.WGL_STENCIL_BITS_ARB, pfd.cStencilBits, Wgl.WGL_SAMPLES_ARB, multisample, 0 }; int[] nformats = new int[1]; //int nformats; Debug.Assert(_wglChoosePixelFormatARB != null, "failed to get proc address for ChoosePixelFormatARB"); // ChoosePixelFormatARB proc address was obtained when setting up a dummy GL context in initialiseWGL() // since glew hasn't been initialized yet, we have to cheat and use the previously obtained address bool result = Wgl.wglChoosePixelFormatARB(hdc, iattr, null, 1, format, nformats); // Tao 2.0 //int result = Wgl.wglChoosePixelFormatARB( _wglChoosePixelFormatARB, hdc, iattr, null, 1, format, out nformats ); if (!result || nformats[0] <= 0) // Tao 2.0 //if ( result == 0 || nformats <= 0 ) return false; } else { format[0] = Gdi.ChoosePixelFormat(hdc, ref pfd); } return (format[0] != 0 && Gdi.SetPixelFormat(hdc, format[0], ref pfd)); }
///<summary> ///hdc: A pointer to the Windows device context to which the setting will apply. ///bpp: Desired color depth in bits-per-pixel. -1 means "don't care", positive otherwise (8,16,24,32). ///depth: Desired z-buffer or depth-sorting bits. -1 means "don't care", positive otherwise (8,16,24,32). ///dbl: Indicates the desire for double-buffering. -1 means "don't care", 0 for none, otherwise 1. ///acc: Indicates the desire for hardware-acceleration. -1 means "don't care", 0 for none, otherwise 1. ///formatRef: Specifies the maximum reference number to be returned (to help with loading times). The final format ///selection is returned in this reference variable, which corresponds to the returned Gdi.PIXELFORMATDESCRIPTOR. Specify a ///non-positive number for "don't care". ///</summary> Gdi.PIXELFORMATDESCRIPTOR ChoosePixelFormatEx(System.IntPtr hdc, int p_bpp, int p_depth, int p_dbl, int p_acc, ref int formatRef) { Logger.openlog.curSev = Logger.Severity.DEBUG; Logger.openlog.Log(this, "ChoosePixelFormatEx", "Beginning", false); Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; int num = _DescribePixelFormat(hdc, 1, (uint)pfd.nSize, ref pfd); Logger.openlog.Log(this, "ChoosePixelFormatEx", "There are " + num + " available formats.", false); num = (formatRef < 1?num:Math.Min(num, formatRef)); Logger.openlog.curSev = Logger.Severity.INFO; Logger.openlog.Log(this, "ChoosePixelFormatEx", "Maximum number of formats to choose from is " + num, false); long maxqual = -0xEFFFFFFF; int maxindex = 0; bool goodEnough = false; if (num > 0) { for (int i = 1; i <= num && !goodEnough; i++) { goodEnough = true; //This format is assumed to be good enough until proven otherwise. pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; _DescribePixelFormat(hdc, i, (uint)pfd.nSize, ref pfd); long bpp = pfd.cColorBits; long depth = pfd.cDepthBits; bool pal = (pfd.iPixelType == Gdi.PFD_TYPE_COLORINDEX); bool mcd = (pfd.dwFlags & Gdi.PFD_GENERIC_FORMAT) != 0 && (pfd.dwFlags & Gdi.PFD_GENERIC_ACCELERATED) != 0; //hard or soft bool soft = (pfd.dwFlags & Gdi.PFD_GENERIC_FORMAT) != 0 && (pfd.dwFlags & Gdi.PFD_GENERIC_ACCELERATED) == 0; //soft only bool icd = (pfd.dwFlags & Gdi.PFD_GENERIC_FORMAT) == 0 && (pfd.dwFlags & Gdi.PFD_GENERIC_ACCELERATED) == 0; bool opengl = (pfd.dwFlags & Gdi.PFD_SUPPORT_OPENGL) != 0; bool window = (pfd.dwFlags & Gdi.PFD_DRAW_TO_WINDOW) != 0; bool bitmap = (pfd.dwFlags & Gdi.PFD_DRAW_TO_BITMAP) != 0; bool dbuff = (pfd.dwFlags & Gdi.PFD_DOUBLEBUFFER) != 0; long q = 0; if (opengl && window) { q += 0x8000; } else { goodEnough = false; } if (depth > 0 && bpp > 0) { q += 0x4000; } else { goodEnough = false; } if ((p_dbl == 0 && !dbuff) || (p_dbl == 1 && dbuff)) { q += 0x2000; } else { goodEnough = false; } if ((p_acc == 0 && soft) || (p_acc == 1 && (mcd || icd))) { q += 0x1000; } else { goodEnough = false; } if (!pal) { q += 0x0080; } else { goodEnough = false; } if (bpp >= p_bpp) { q += 0x0800; } else { q -= 0x0800 * (p_bpp - bpp); //Penalty for color-depths which are less than the desired. goodEnough = false; } if (depth >= p_depth) { q += 0x0400; } else { q -= 0x0400 * (p_depth - depth); //Penalty for z-depths which are less than the desired. goodEnough = false; } if (bitmap) { q += 0x0001; } if (mcd) { q += 0x0040; } if (icd) { q += 0x0042; } if (q > maxqual || goodEnough) //Take the smallest index (the smallest options) that meet the requirements. { maxqual = q; maxindex = i; } Logger.openlog.Log(this, "ChoosePixelFormatEx", (i == maxindex?"*":"") + "Evaluated format with index=" + i + " qval=" + q + ":"); Logger.openlog.Log(this, "ChoosePixelFormatEx", "color depth=" + bpp); Logger.openlog.Log(this, "ChoosePixelFormatEx", "z-depth=" + depth); Logger.openlog.Log(this, "ChoosePixelFormatEx", "palette=" + (pal?"Yes":"No")); Logger.openlog.Log(this, "ChoosePixelFormatEx", "mcd=" + (mcd?"Yes":"No")); Logger.openlog.Log(this, "ChoosePixelFormatEx", "software graphics=" + (soft?"Yes":"No")); Logger.openlog.Log(this, "ChoosePixelFormatEx", "icd=" + (icd?"Yes":"No")); Logger.openlog.Log(this, "ChoosePixelFormatEx", "supports OpenGL=" + (opengl?"Yes":"No")); Logger.openlog.Log(this, "ChoosePixelFormatEx", "windowed=" + (window?"Yes":"No")); Logger.openlog.Log(this, "ChoosePixelFormatEx", "bitmap=" + (bitmap?"Yes":"No")); Logger.openlog.Log(this, "ChoosePixelFormatEx", "double buffering=" + (dbuff?"Yes":"No")); } } pfd = new Gdi.PIXELFORMATDESCRIPTOR(); pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; _DescribePixelFormat(hdc, maxindex, (uint)pfd.nSize, ref pfd); formatRef = maxindex; Logger.openlog.Log(this, "ChoosePixelFormatEx", "Done. Chosen format=" + maxindex); return(pfd); }
public static extern int _DescribePixelFormat(System.IntPtr hdc, int iPixelFormat, uint nBytes, ref Gdi.PIXELFORMATDESCRIPTOR ppfd);
private void _initializeWgl() { // wglGetProcAddress does not work without an active OpenGL context, // but we need wglChoosePixelFormatARB's address before we can // create our main window. Thank you very much, Microsoft! // // The solution is to create a dummy OpenGL window first, and then // test for WGL_ARB_pixel_format support. If it is not supported, // we make sure to never call the ARB pixel format functions. // // If is is supported, we call the pixel format functions at least once // to initialize them (pointers are stored by glprocs.h). We can also // take this opportunity to enumerate the valid FSAA modes. SWF.Form frm = new SWF.Form(); IntPtr hwnd = frm.Handle; // if a simple CreateWindow fails, then boy are we in trouble... if (hwnd == IntPtr.Zero) throw new Exception("Window creation failed"); // no chance of failure and no need to release thanks to CS_OWNDC IntPtr hdc = User.GetDC(hwnd); // assign a simple OpenGL pixel format that everyone supports Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); ; pfd.nSize = (short)Marshal.SizeOf(pfd); pfd.nVersion = 1; pfd.cColorBits = 16; pfd.cDepthBits = 15; pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = Gdi.PFD_TYPE_RGBA; // if these fail, wglCreateContext will also quietly fail int format; format = Gdi.ChoosePixelFormat(hdc, ref pfd); if (format != 0) Gdi.SetPixelFormat(hdc, format, ref pfd); IntPtr hrc = Wgl.wglCreateContext(hdc); if (hrc != IntPtr.Zero) { // if wglMakeCurrent fails, wglGetProcAddress will return null Wgl.wglMakeCurrent(hdc, hrc); Wgl.ReloadFunctions(); // Tao 2.0 // check for pixel format and multisampling support //IntPtr wglGetExtensionsStringARB = Wgl.wglGetProcAddress( "wglGetExtensionsStringARB" ); //if ( wglGetExtensionsStringARB != IntPtr.Zero ) //{ // string exts = Wgl.wglGetExtensionsStringARB( wglGetExtensionsStringARB, hdc ); // _hasPixelFormatARB = exts.Contains( "WGL_ARB_pixel_format" ); // _hasMultisample = exts.Contains( "WGL_ARB_multisample" ); //} _hasPixelFormatARB = Wgl.IsExtensionSupported("WGL_ARB_pixel_format"); _hasMultisample = Wgl.IsExtensionSupported("WGL_ARB_multisample"); if (_hasPixelFormatARB && _hasMultisample) { // enumerate all formats w/ multisampling int[] iattr = { Wgl.WGL_DRAW_TO_WINDOW_ARB, 1, Wgl.WGL_SUPPORT_OPENGL_ARB, 1, Wgl.WGL_DOUBLE_BUFFER_ARB, 1, Wgl.WGL_SAMPLE_BUFFERS_ARB, 1, Wgl.WGL_ACCELERATION_ARB, Wgl.WGL_FULL_ACCELERATION_ARB, // We are no matter about the colour, depth and stencil buffers here //WGL_COLOR_BITS_ARB, 24, //WGL_ALPHA_BITS_ARB, 8, //WGL_DEPTH_BITS_ARB, 24, //WGL_STENCIL_BITS_ARB, 8, // Wgl.WGL_SAMPLES_ARB, 2, 0 }; int[] formats = new int[256]; int[] count = new int[256]; // Tao 2.0 //int count; // cheating here. wglChoosePixelFormatARB proc address needed later on // when a valid GL context does not exist and glew is not initialized yet. _wglChoosePixelFormatARB = Wgl.wglGetProcAddress("wglChoosePixelFormatARB"); if (Wgl.wglChoosePixelFormatARB(hdc, iattr, null, 256, formats, count)) // Tao 2.0 //if ( Wgl.wglChoosePixelFormatARB( _wglChoosePixelFormatARB, hdc, iattr, null, 256, formats, out count ) != 0 ) { // determine what multisampling levels are offered int query = Wgl.WGL_SAMPLES_ARB, samples; for (int i = 0; i < count[0]; ++i) // Tao 2.0 //for ( int i = 0; i < count[ 0 ]; ++i ) { IntPtr wglGetPixelFormatAttribivARB = Wgl.wglGetProcAddress("wglGetPixelFormatAttribivARB"); if (Wgl.wglGetPixelFormatAttribivARB(hdc, formats[i], 0, 1, ref query, out samples)) // Tao 2.0 //if ( Wgl.wglGetPixelFormatAttribivARB( wglGetPixelFormatAttribivARB, hdc, formats[ i ], 0, 1, ref query, out samples ) != 0 ) { if (!_fsaaLevels.Contains(samples)) _fsaaLevels.Add(samples); } } } } Wgl.wglMakeCurrent(IntPtr.Zero, IntPtr.Zero); Wgl.wglDeleteContext(hrc); } // clean up our dummy window and class frm.Dispose(); frm = null; }
public static extern void ZeroMemory(Gdi.PIXELFORMATDESCRIPTOR ptr, int numBytes);
float mag_speed, rotate_speed; //マウスの拡大縮小,回転速度 protected override void OnHandleCreated(EventArgs e) { base.OnHandleCreated(e); this.SetStyle(ControlStyles.UserPaint, true); this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); this.SetStyle(ControlStyles.DoubleBuffer, false); this.SetStyle(ControlStyles.Opaque, true); this.SetStyle(ControlStyles.ResizeRedraw, true); Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // OpenGLをサポート ウィンドウに描画 ダブルバッファ pfd.dwFlags = Gdi.PFD_SUPPORT_OPENGL | Gdi.PFD_DRAW_TO_WINDOW | Gdi.PFD_DOUBLEBUFFER; pfd.iPixelType = Gdi.PFD_TYPE_RGBA; //RGBAフォーマット pfd.cColorBits = 32; // 32bit/pixel pfd.cAlphaBits = 8; // アルファチャンネル8bit (0にするとアルファチャンネル無しになる) pfd.cDepthBits = 16; // デプスバッファ16bit pfd.cStencilBits = 8; //ステンシルバッファを利用するときはこれを追加しなければならない //デバイスコンテキストのハンドルを取得。 this.hDC = User.GetDC(this.Handle); //ピクセルフォーマットを選択。 int pixFormat = Gdi.ChoosePixelFormat(this.hDC, ref pfd); if (pixFormat <= 0) { throw new Exception("ChoosePixelFormat failed."); } //ピクセルフォーマットの正確な設定を取得 Wgl.wglDescribePixelFormat(this.hDC, pixFormat, 40, ref pfd); //デバイスコンテキストにピクセルフォーマットを設定。 bool valid = Gdi.SetPixelFormat(this.hDC, pixFormat, ref pfd); if (!valid) { throw new Exception("SetPixelFormat failed"); } //OpenGLのレンダリングコンテキストを作成。 this.hRC = Wgl.wglCreateContext(this.hDC); if (this.hRC == IntPtr.Zero) { throw new Exception("wglCreateContext failed."); } //作成したコンテキストをカレントに設定。 Wgl.wglMakeCurrent(this.hDC, this.hRC); //レンダリングコンテキストを作成、カレントに設定したら、 //1度だけこれを呼び出しておく。 //Tao.OpenGl.GL、Tao.Platform.Windows.WGLの仕様。 Gl.ReloadFunctions(); Wgl.ReloadFunctions(); //一応、エラーがないか確認。 int err = Gl.glGetError(); if (err != Gl.GL_NO_ERROR) { throw new Exception("Error code = " + err.ToString()); } this.addModel("c:\\bmw.3ds"); camera.setViewPort(this.Width, this.Height); this.SetupGL(); }
private void CreateDevice(int width, int height, int bits) { int pixelFormat; // Holds The Results After Searching For A Match //this.Fullscreen = fullscreenflag; GC.Collect(); // Request A Collection // This Forces A Swap Kernel.SetProcessWorkingSetSize(Process.GetCurrentProcess().Handle, -1, -1); if (this.m_bFullscreen) // Attempt Fullscreen Mode? { Gdi.DEVMODE dmScreenSettings = new Gdi.DEVMODE(); // Device Mode // Size Of The Devmode Structure dmScreenSettings.dmSize = (short)Marshal.SizeOf(dmScreenSettings); dmScreenSettings.dmPelsWidth = width; // Selected Screen Width dmScreenSettings.dmPelsHeight = height; // Selected Screen Height dmScreenSettings.dmBitsPerPel = bits; // Selected Bits Per Pixel dmScreenSettings.dmFields = Gdi.DM_BITSPERPEL | Gdi.DM_PELSWIDTH | Gdi.DM_PELSHEIGHT; // Try To Set Selected Mode And Get Results. NOTE: CDS_FULLSCREEN Gets Rid Of Start Bar. if (User.ChangeDisplaySettings(ref dmScreenSettings, User.CDS_FULLSCREEN) != User.DISP_CHANGE_SUCCESSFUL) { // The Mode Fails throw new Exception("Fullscreen not supported"); } } Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // pfd Tells Windows How We Want Things To Be pfd.nSize = (short)Marshal.SizeOf(pfd); // Size Of This Pixel Format Descriptor pfd.nVersion = 1; // Version Number pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | // Format Must Support Window Gdi.PFD_SUPPORT_OPENGL | // Format Must Support OpenGL Gdi.PFD_DOUBLEBUFFER; // Format Must Support Double Buffering pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; // Request An RGBA Format pfd.cColorBits = (byte)bits; // Select Our Color Depth pfd.cRedBits = 0; // Color Bits Ignored pfd.cRedShift = 0; pfd.cGreenBits = 0; pfd.cGreenShift = 0; pfd.cBlueBits = 0; pfd.cBlueShift = 0; pfd.cAlphaBits = 0; // No Alpha Buffer pfd.cAlphaShift = 0; // Shift Bit Ignored pfd.cAccumBits = 0; // No Accumulation Buffer pfd.cAccumRedBits = 0; // Accumulation Bits Ignored pfd.cAccumGreenBits = 0; pfd.cAccumBlueBits = 0; pfd.cAccumAlphaBits = 0; pfd.cDepthBits = 16; // 16Bit Z-Buffer (Depth Buffer) pfd.cStencilBits = 0; // No Stencil Buffer pfd.cAuxBuffers = 0; // No Auxiliary Buffer pfd.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; // Main Drawing Layer pfd.bReserved = 0; // Reserved pfd.dwLayerMask = 0; // Layer Masks Ignored pfd.dwVisibleMask = 0; pfd.dwDamageMask = 0; this._hDC = User.GetDC(this.RenderControl.Handle); // Attempt To Get A Device Context if (this._hDC == IntPtr.Zero) { this.KillGLWindow(); throw new Exception("Can't Create A GL Device Context."); } pixelFormat = Gdi.ChoosePixelFormat(this._hDC, ref pfd); // Attempt To Find An Appropriate Pixel Format if (pixelFormat == 0) { // Did Windows Find A Matching Pixel Format? this.KillGLWindow(); throw new Exception("Can't Find A Suitable PixelFormat."); } if (!Gdi.SetPixelFormat(this._hDC, pixelFormat, ref pfd)) // Are We Able To Set The Pixel Format? { this.KillGLWindow(); // Reset The Display throw new Exception("Can't Set The PixelFormat."); } this._hRC = Wgl.wglCreateContext(this._hDC); // Attempt To Get The Rendering Context if (this._hRC == IntPtr.Zero) { this.KillGLWindow(); throw new Exception("Can't Create A GL Rendering Context."); } if (!Wgl.wglMakeCurrent(this._hDC, this._hRC)) // Try To Activate The Rendering Context { this.KillGLWindow(); // Reset The Display throw new Exception("Can't Activate The GL Rendering Context."); } //form.Show(); //form.TopMost = true; //form.Focus(); this.ReSizeGLScene(this.RenderControl.Width, this.RenderControl.Height); // Set Up Our Perspective GL Screen if (!InitGL()) { // Initialize Our Newly Created GL Window this.KillGLWindow(); // Reset The Display throw new Exception("Initialization Failed."); } }
///<summary>Returns true if the given pixel format supports bitmapped rendering, false otherwise.</summary> public static bool FormatSupportsBitmap(Gdi.PIXELFORMATDESCRIPTOR pfd) { return((pfd.dwFlags & Gdi.PFD_DRAW_TO_BITMAP) != 0); }
// --- Private Static Methods --- #region bool CreateGLWindow(string title, int width, int height, int bits, bool fullscreenflag) /// <summary> /// Creates our OpenGL Window. /// </summary> /// <param name="title"> /// The title to appear at the top of the window. /// </param> /// <param name="width"> /// The width of the GL window or fullscreen mode. /// </param> /// <param name="height"> /// The height of the GL window or fullscreen mode. /// </param> /// <param name="bits"> /// The number of bits to use for color (8/16/24/32). /// </param> /// <param name="fullscreenflag"> /// Use fullscreen mode (<c>true</c>) or windowed mode (<c>false</c>). /// </param> /// <returns> /// <c>true</c> on successful window creation, otherwise <c>false</c>. /// </returns> private static bool CreateGLWindow(string title, int width, int height, int bits, bool fullscreenflag) { int pixelFormat; // Holds The Results After Searching For A Match fullscreen = fullscreenflag; // Set The Global Fullscreen Flag form = null; // Null The Form GC.Collect(); // Request A Collection // This Forces A Swap Kernel.SetProcessWorkingSetSize(Process.GetCurrentProcess().Handle, -1, -1); if (fullscreen) // Attempt Fullscreen Mode? { Gdi.DEVMODE dmScreenSettings = new Gdi.DEVMODE(); // Device Mode // Size Of The Devmode Structure dmScreenSettings.dmSize = (short)Marshal.SizeOf(dmScreenSettings); dmScreenSettings.dmPelsWidth = width; // Selected Screen Width dmScreenSettings.dmPelsHeight = height; // Selected Screen Height dmScreenSettings.dmBitsPerPel = bits; // Selected Bits Per Pixel dmScreenSettings.dmFields = Gdi.DM_BITSPERPEL | Gdi.DM_PELSWIDTH | Gdi.DM_PELSHEIGHT; // Try To Set Selected Mode And Get Results. NOTE: CDS_FULLSCREEN Gets Rid Of Start Bar. if (User.ChangeDisplaySettings(ref dmScreenSettings, User.CDS_FULLSCREEN) != User.DISP_CHANGE_SUCCESSFUL) { // If The Mode Fails, Offer Two Options. Quit Or Use Windowed Mode. if (MessageBox.Show("The Requested Fullscreen Mode Is Not Supported By\nYour Video Card. Use Windowed Mode Instead?", "NeHe GL", MessageBoxButtons.YesNo, MessageBoxIcon.Exclamation) == DialogResult.Yes) { fullscreen = false; // Windowed Mode Selected. Fullscreen = false } else { // Pop up A Message Box Lessing User Know The Program Is Closing. MessageBox.Show("Program Will Now Close.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Stop); return(false); // Return false } } } form = new Lesson11(); // Create The Window if (fullscreen) // Are We Still In Fullscreen Mode? { form.FormBorderStyle = FormBorderStyle.None; // No Border Cursor.Hide(); // Hide Mouse Pointer } else // If Windowed { form.FormBorderStyle = FormBorderStyle.Sizable; // Sizable Cursor.Show(); // Show Mouse Pointer } form.Width = width; // Set Window Width form.Height = height; // Set Window Height form.Text = title; // Set Window Title Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); // pfd Tells Windows How We Want Things To Be pfd.nSize = (short)Marshal.SizeOf(pfd); // Size Of This Pixel Format Descriptor pfd.nVersion = 1; // Version Number pfd.dwFlags = Gdi.PFD_DRAW_TO_WINDOW | // Format Must Support Window Gdi.PFD_SUPPORT_OPENGL | // Format Must Support OpenGL Gdi.PFD_DOUBLEBUFFER; // Format Must Support Double Buffering pfd.iPixelType = (byte)Gdi.PFD_TYPE_RGBA; // Request An RGBA Format pfd.cColorBits = (byte)bits; // Select Our Color Depth pfd.cRedBits = 0; // Color Bits Ignored pfd.cRedShift = 0; pfd.cGreenBits = 0; pfd.cGreenShift = 0; pfd.cBlueBits = 0; pfd.cBlueShift = 0; pfd.cAlphaBits = 0; // No Alpha Buffer pfd.cAlphaShift = 0; // Shift Bit Ignored pfd.cAccumBits = 0; // No Accumulation Buffer pfd.cAccumRedBits = 0; // Accumulation Bits Ignored pfd.cAccumGreenBits = 0; pfd.cAccumBlueBits = 0; pfd.cAccumAlphaBits = 0; pfd.cDepthBits = 16; // 16Bit Z-Buffer (Depth Buffer) pfd.cStencilBits = 0; // No Stencil Buffer pfd.cAuxBuffers = 0; // No Auxiliary Buffer pfd.iLayerType = (byte)Gdi.PFD_MAIN_PLANE; // Main Drawing Layer pfd.bReserved = 0; // Reserved pfd.dwLayerMask = 0; // Layer Masks Ignored pfd.dwVisibleMask = 0; pfd.dwDamageMask = 0; hDC = User.GetDC(form.Handle); // Attempt To Get A Device Context if (hDC == IntPtr.Zero) // Did We Get A Device Context? { KillGLWindow(); // Reset The Display MessageBox.Show("Can't Create A GL Device Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } pixelFormat = Gdi.ChoosePixelFormat(hDC, ref pfd); // Attempt To Find An Appropriate Pixel Format if (pixelFormat == 0) // Did Windows Find A Matching Pixel Format? { KillGLWindow(); // Reset The Display MessageBox.Show("Can't Find A Suitable PixelFormat.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } if (!Gdi.SetPixelFormat(hDC, pixelFormat, ref pfd)) // Are We Able To Set The Pixel Format? { KillGLWindow(); // Reset The Display MessageBox.Show("Can't Set The PixelFormat.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } hRC = Wgl.wglCreateContext(hDC); // Attempt To Get The Rendering Context if (hRC == IntPtr.Zero) // Are We Able To Get A Rendering Context? { KillGLWindow(); // Reset The Display MessageBox.Show("Can't Create A GL Rendering Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } if (!Wgl.wglMakeCurrent(hDC, hRC)) // Try To Activate The Rendering Context { KillGLWindow(); // Reset The Display MessageBox.Show("Can't Activate The GL Rendering Context.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } form.Show(); // Show The Window form.TopMost = true; // Topmost Window form.Focus(); // Focus The Window if (fullscreen) // This Shouldn't Be Necessary, But Is { Cursor.Hide(); } ReSizeGLScene(width, height); // Set Up Our Perspective GL Screen if (!InitGL()) // Initialize Our Newly Created GL Window { KillGLWindow(); // Reset The Display MessageBox.Show("Initialization Failed.", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error); return(false); } return(true); // Success }
/// <summary> /// Initializes an OpenGL context with the associated Win32 device context</summary> /// <param name="hdc">HDC from the window to which the new OpenGL context is bound</param> /// <param name="hglrc">Handle to the new OpenGL context</param> public static void InitOpenGl(IntPtr hdc, out IntPtr hglrc) { Gdi.PIXELFORMATDESCRIPTOR pfd = new Gdi.PIXELFORMATDESCRIPTOR(); PopulatePixelFormatDescriptor(ref pfd); // Attempt To Find An Appropriate Pixel Format int pixelFormat = Gdi.ChoosePixelFormat(hdc, ref pfd); if (pixelFormat == 0) { throw new InvalidOperationException("Can't find a suitable PixelFormat"); } // Attempt To Set The Pixel Format? if (!Gdi.SetPixelFormat(hdc, pixelFormat, ref pfd)) { throw new InvalidOperationException("Can't set the PixelFormat"); } // Attempt To Get The Rendering Context hglrc = Wgl.wglCreateContext(hdc); if (hglrc == IntPtr.Zero) { throw new InvalidOperationException("Can't create GL rendering context"); } if (s_sharedHglrc == IntPtr.Zero) { s_sharedHglrc = hglrc; } else { // We don't throw an exception on failure because the caller may be on another thread or is // using a different pixel format. Wgl.wglShareLists(s_sharedHglrc, hglrc); } if (!Wgl.wglMakeCurrent(hdc, hglrc)) { throw new InvalidOperationException("Can't make the OpenGL rendering context to be the current context."); } // Load all extensions for mainline rendering if (!s_initialized) { LoadAllExtensions(); s_initialized = true; } // Init fonts Gdi.SelectObject(hdc, SystemFonts.DefaultFont.ToHfont()); foreach (IntSet.Range range in s_fontMap.Ranges) { int baseDisplayListId = range.PreviousItemsCount + TEXT_DISPLAY_LIST_BASE; if (!wglUseFontBitmaps(hdc, range.Min, range.Count, (uint)baseDisplayListId)) { throw new InvalidOperationException("Font bitmaps were unable to be created."); } } s_fontMap.Lock(); Util3D.ReportErrors(); }