tags:

views:

95

answers:

2

I am busy climbing the learning curve for OpenGL, using Delphi (pascal); I am using an excellent text, but every example in the book draws to the entire Form. I want to place an image component on the from, and draw to that. I tried assigning the Device context handle (GDC) to the handle of the image control's canvas, rather than to the handle of the form, but that returns an error when ChoosePixelFormat is invoked.

So, if anyone knows how to get this to occur, I'd appreciate any suggestions.

Thanks in advance for any help.

jrDoner

+5  A: 

I always use the following code to setup the window HWND for OpenGL output:

procedure rglSetupGL(Handle: HWnd);
var
  DC: HDC;
  PixelFormat: integer;
const
  PFD: TPixelFormatDescriptor = (
         nSize: sizeOf(TPixelFormatDescriptor);
         nVersion: 1;
         dwFlags: PFD_SUPPORT_OPENGL or PFD_DRAW_TO_WINDOW or PFD_DOUBLEBUFFER;
         iPixelType: PFD_TYPE_RGBA;
         cColorBits: 24;
         cRedBits: 0;
         cRedShift: 0;
         cGreenBits: 0;
         cGreenShift: 0;
         cBlueBits: 0;
         cBlueShift: 0;
         cAlphaBits: 24;
         cAlphaShift: 0;
         cAccumBits: 0;
         cAccumRedBits: 0;
         cAccumGreenBits: 0;
         cAccumBlueBits: 0;
         cAccumAlphaBits: 0;
         cDepthBits: 16;
         cStencilBits: 0;
         cAuxBuffers: 0;
         iLayerType: PFD_MAIN_PLANE;
         bReserved: 0;
         dwLayerMask: 0;
         dwVisibleMask: 0;
         dwDamageMask: 0);
begin
  DC := GetDC(Handle);
  PixelFormat := ChoosePixelFormat(DC, @PFD);
  SetPixelFormat(DC, PixelFormat, @PFD);
  RC := wglCreateContext(DC);
  wglMakeCurrent(DC, RC);
end;

As you know (?), there is a huge difference between window handles (HWNDs) and device contexts (DCs). Every window has a HWND, and every window that you can draw to has a HDC. Given a form, Handle is its HWND, and Canvas.Handle is its HDC.

To get the DC associated with a window, you can use GetDC(HWND).

You have to setup OpenGL on a window, that is, on a HWND. So you cannot render OpenGL on a control without a window handle, such as a TImage. Use a TPanel or some other decendant of TWinControl.

Andreas Rejbrand
+1 for the good explanation. I've actually got a VCL component I wrote that sets up an OpenGL context inside a form. It's designed to do more than that--it's not just OpenGL, but an interface to the SDL multimedia library using an OpenGL backend--but it provides a real GL context that you can use standard OpenGL routines on. If anyone's interested I could make it available for people to use...
Mason Wheeler
A: 

Create a Window where you want your OpenGL output to show up, and create the OpenGL context associated with that window. In essence, you'll be creating a control that uses OpenGL to draw itself.

Jerry Coffin
This doesn't actually explain anything about how to do it in the context of the VCL.
Mason Wheeler