4 * The Windows-specific state query methods.
6 * Copyright (c) 2012 Stephen J. Baker. All Rights Reserved.
7 * Written by John F. Fay, <fayjf@sourceforge.net>
8 * Creation date: Sun Jan 22, 2012
10 * Permission is hereby granted, free of charge, to any person obtaining a
11 * copy of this software and associated documentation files (the "Software"),
12 * to deal in the Software without restriction, including without limitation
13 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
14 * and/or sell copies of the Software, and to permit persons to whom the
15 * Software is furnished to do so, subject to the following conditions:
17 * The above copyright notice and this permission notice shall be included
18 * in all copies or substantial portions of the Software.
20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
21 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
23 * PAWEL W. OLSZTA BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
24 * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
25 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
28 #include <GL/freeglut.h>
29 #include "../fg_internal.h"
32 extern GLboolean fgSetupPixelFormat( SFG_Window* window, GLboolean checkOnly,
33 unsigned char layer_type );
36 * Helper functions for getting client area from the window rect
37 * and the window rect from the client area given the style of the window
38 * (or a valid window pointer from which the style can be queried).
40 extern void fghGetClientArea( RECT *clientRect, const SFG_Window *window, BOOL posIsOutside );
41 extern void fghGetStyleFromWindow( const SFG_Window *window, DWORD *windowStyle, DWORD *windowExStyle );
42 extern void fghComputeWindowRectFromClientArea_UseStyle( RECT *clientRect, const DWORD windowStyle, const DWORD windowExStyle, BOOL posIsOutside );
45 /* The following include file is available from SGI but is not standard:
46 * #include <GL/wglext.h>
47 * So we copy the necessary parts out of it to support the multisampling query
49 #ifndef WGL_SAMPLES_ARB
50 #define WGL_SAMPLES_ARB 0x2042
52 #ifndef WGL_FRAMEBUFFER_SRGB_CAPABLE_ARB
53 #define WGL_FRAMEBUFFER_SRGB_CAPABLE_ARB 0x20A9
56 typedef BOOL (WINAPI * PFNWGLGETPIXELFORMATATTRIBIVARBPROC) (HDC hdc, int iPixelFormat, int iLayerPlane, UINT nAttributes, const int *piAttributes, int *piValues);
58 #if defined(_WIN32_WCE)
59 # include <Aygshell.h>
60 # ifdef FREEGLUT_LIB_PRAGMAS
61 # pragma comment( lib, "Aygshell.lib" )
63 #endif /* defined(_WIN32_WCE) */
67 int fgPlatformGlutGet ( GLenum eWhat )
76 case GLUT_WINDOW_NUM_SAMPLES:
77 glGetIntegerv(WGL_SAMPLES_ARB, &nsamples);
80 /* Handle the OpenGL inquiries */
81 case GLUT_WINDOW_RGBA:
82 #if defined(_WIN32_WCE)
83 boolValue = (GLboolean)0; /* WinCE doesn't support this feature */
85 glGetBooleanv ( GL_RGBA_MODE, &boolValue );
86 returnValue = boolValue ? 1 : 0;
89 case GLUT_WINDOW_DOUBLEBUFFER:
90 #if defined(_WIN32_WCE)
91 boolValue = (GLboolean)0; /* WinCE doesn't support this feature */
93 glGetBooleanv ( GL_DOUBLEBUFFER, &boolValue );
94 returnValue = boolValue ? 1 : 0;
97 case GLUT_WINDOW_STEREO:
98 #if defined(_WIN32_WCE)
99 boolValue = (GLboolean)0; /* WinCE doesn't support this feature */
101 glGetBooleanv ( GL_STEREO, &boolValue );
102 returnValue = boolValue ? 1 : 0;
106 case GLUT_WINDOW_RED_SIZE:
107 glGetIntegerv ( GL_RED_BITS, &returnValue );
109 case GLUT_WINDOW_GREEN_SIZE:
110 glGetIntegerv ( GL_GREEN_BITS, &returnValue );
112 case GLUT_WINDOW_BLUE_SIZE:
113 glGetIntegerv ( GL_BLUE_BITS, &returnValue );
115 case GLUT_WINDOW_ALPHA_SIZE:
116 glGetIntegerv ( GL_ALPHA_BITS, &returnValue );
118 case GLUT_WINDOW_ACCUM_RED_SIZE:
119 #if defined(_WIN32_WCE)
120 returnValue = 0; /* WinCE doesn't support this feature */
122 glGetIntegerv ( GL_ACCUM_RED_BITS, &returnValue );
125 case GLUT_WINDOW_ACCUM_GREEN_SIZE:
126 #if defined(_WIN32_WCE)
127 returnValue = 0; /* WinCE doesn't support this feature */
129 glGetIntegerv ( GL_ACCUM_GREEN_BITS, &returnValue );
132 case GLUT_WINDOW_ACCUM_BLUE_SIZE:
133 #if defined(_WIN32_WCE)
134 returnValue = 0; /* WinCE doesn't support this feature */
136 glGetIntegerv ( GL_ACCUM_BLUE_BITS, &returnValue );
139 case GLUT_WINDOW_ACCUM_ALPHA_SIZE:
140 #if defined(_WIN32_WCE)
141 returnValue = 0; /* WinCE doesn't support this feature */
143 glGetIntegerv ( GL_ACCUM_ALPHA_BITS, &returnValue );
146 case GLUT_WINDOW_DEPTH_SIZE:
147 glGetIntegerv ( GL_DEPTH_BITS, &returnValue );
150 case GLUT_WINDOW_BUFFER_SIZE:
152 PIXELFORMATDESCRIPTOR pfd;
153 HDC hdc = fgStructure.CurrentWindow->Window.pContext.Device;
154 int iPixelFormat = GetPixelFormat( hdc );
155 DescribePixelFormat(hdc, iPixelFormat, sizeof(PIXELFORMATDESCRIPTOR), &pfd);
157 returnValue = pfd.cColorBits;
158 if (pfd.iPixelType==PFD_TYPE_RGBA)
159 returnValue += pfd.cAlphaBits;
163 case GLUT_WINDOW_STENCIL_SIZE:
164 glGetIntegerv ( GL_STENCIL_BITS, &returnValue );
172 * - When you create a window with position (x,y) and size
173 * (w,h), the upper left hand corner of the outside of the
174 * window is at (x,y) and the size of the drawable area is
176 * - When you query the size and position of the window--as
177 * is happening here for Windows--"freeglut" will return
178 * the size of the drawable area--the (w,h) that you
179 * specified when you created the window--and the coordinates
180 * of the upper left hand corner of the drawable area, i.e.
181 * of the client rect--which is NOT the (x,y) you specified.
185 POINT topLeft = {0,0};
187 freeglut_return_val_if_fail( fgStructure.CurrentWindow != NULL, 0 );
189 #if defined(_WIN32_WCE)
190 GetWindowRect( fgStructure.CurrentWindow->Window.Handle, &winRect);
192 ClientToScreen(fgStructure.CurrentWindow->Window.Handle, &topLeft);
194 if (fgStructure.CurrentWindow->Parent)
195 /* For child window, we should return relative to upper-left
196 * of parent's client area.
198 ScreenToClient(fgStructure.CurrentWindow->Parent->Window.Handle,&topLeft);
200 winRect.left = topLeft.x;
201 winRect.top = topLeft.y;
202 #endif /* defined(_WIN32_WCE) */
206 case GLUT_WINDOW_X: return winRect.left;
207 case GLUT_WINDOW_Y: return winRect.top ;
212 case GLUT_WINDOW_WIDTH:
213 case GLUT_WINDOW_HEIGHT:
216 freeglut_return_val_if_fail( fgStructure.CurrentWindow != NULL, 0 );
218 GetClientRect( fgStructure.CurrentWindow->Window.Handle, &winRect);
222 case GLUT_WINDOW_WIDTH: return winRect.right-winRect.left;
223 case GLUT_WINDOW_HEIGHT: return winRect.bottom-winRect.top;
228 case GLUT_WINDOW_BORDER_WIDTH :
229 case GLUT_WINDOW_BORDER_HEIGHT :
230 #if defined(_WIN32_WCE)
234 /* We can't get the border width or header height in the simple way
235 * with some calls to GetSystemMetrics. We'd then have to assume which
236 * elements are present for a given decoration, and such calculations
237 * wouldn't be valid for every version of Windows. The below should be
239 int borderWidth, captionHeight;
240 DWORD windowStyle, windowExStyle;
241 RECT clientRect, winRect;
243 /* Get style of window, or default style */
244 fghGetStyleFromWindow( fgStructure.CurrentWindow, &windowStyle, &windowExStyle );
245 /* Get client area if we have a current window, else use dummy rect */
246 /* Also get window rect (including non-client area) */
247 if (fgStructure.CurrentWindow && fgStructure.CurrentWindow->Window.Handle)
249 fghGetClientArea(&clientRect,fgStructure.CurrentWindow, FALSE);
250 GetWindowRect(fgStructure.CurrentWindow->Window.Handle,&winRect);
254 SetRect(&clientRect,0,0,200,200);
255 CopyRect(&winRect,&clientRect);
256 fghComputeWindowRectFromClientArea_UseStyle(&winRect,windowStyle,windowExStyle,FALSE);
259 /* Calculate border width by taking width of whole window minus width of client area and divide by two
260 * NB: we assume horizontal and vertical borders have the same size, which should always be the case
261 * unless the user bypassed FreeGLUT and messed with the windowstyle himself.
262 * Once borderwidth is known, account for it when comparing height of window to height of client area.
263 * all other extra pixels are assumed to be atop the window, forming the caption.
265 borderWidth = ((winRect.right-winRect.left)-(clientRect.right-clientRect.left))/2;
266 captionHeight = (winRect.bottom-winRect.top)-(clientRect.bottom-clientRect.top)-borderWidth; /* include top border in caption height */
270 case GLUT_WINDOW_BORDER_WIDTH:
272 case GLUT_WINDOW_BORDER_HEIGHT:
273 return captionHeight;
276 #endif /* defined(_WIN32_WCE) */
278 case GLUT_DISPLAY_MODE_POSSIBLE:
279 #if defined(_WIN32_WCE)
282 return fgSetupPixelFormat( fgStructure.CurrentWindow, GL_TRUE,
284 #endif /* defined(_WIN32_WCE) */
287 case GLUT_WINDOW_FORMAT_ID:
288 #if !defined(_WIN32_WCE)
289 if( fgStructure.CurrentWindow != NULL )
290 return GetPixelFormat( fgStructure.CurrentWindow->Window.pContext.Device );
291 #endif /* defined(_WIN32_WCE) */
294 case GLUT_WINDOW_SRGB:
295 if( fgStructure.CurrentWindow != NULL ) {
296 static int attr = WGL_FRAMEBUFFER_SRGB_CAPABLE_ARB;
297 static PFNWGLGETPIXELFORMATATTRIBIVARBPROC wglGetPixelFormatAttribivARB;
298 HDC hdc = fgStructure.CurrentWindow->Window.pContext.Device;
299 int ipixfmt = GetPixelFormat(hdc);
302 if(!wglGetPixelFormatAttribivARB) {
303 if(!(wglGetPixelFormatAttribivARB = (PFNWGLGETPIXELFORMATATTRIBIVARBPROC)wglGetProcAddress("wglGetPixelFormatAttribivARB"))) {
307 if(wglGetPixelFormatAttribivARB(hdc, ipixfmt, 0, 1, &attr, &val)) {
314 fgWarning( "glutGet(): missing enum handle %d", eWhat );
322 int fgPlatformGlutDeviceGet ( GLenum eWhat )
326 case GLUT_HAS_KEYBOARD:
328 * Win32 is assumed a keyboard, and this cannot be queried,
329 * except for WindowsCE.
331 #if defined(_WIN32_CE)
332 return ( GetKeyboardStatus() & KBDI_KEYBOARD_PRESENT ) ? 1 : 0;
333 # if FREEGLUT_LIB_PRAGMAS
334 # pragma comment (lib,"Kbdui.lib")
343 * MS Windows can be booted without a mouse.
345 return GetSystemMetrics( SM_MOUSEPRESENT );
347 case GLUT_NUM_MOUSE_BUTTONS:
348 # if defined(_WIN32_WCE)
351 return GetSystemMetrics( SM_CMOUSEBUTTONS );
355 fgWarning( "glutDeviceGet(): missing enum handle %d", eWhat );
362 * This is for querying the number of supported auxiliary or multisample
363 * buffers for a (the current?) display mode.
364 * see http://old.nabble.com/-GLX--glutGetModeValues-to13514723.html#a13514723
365 * Not currently implemented, but we should be able to query the relevant
367 * http://www.opengl.org/registry/specs/ARB/wgl_pixel_format.txt
368 * (if supported on the executing machine!)
370 int *fgPlatformGlutGetModeValues(GLenum eWhat, int *size)