1 #ifndef _MSC_VER // MSVC really needs a definition for wchar_t
2 #define _WCHAR_T_DEFINED 1 // Glut needs this, or else it tries to
10 #include <simgear/compiler.h>
16 #include "fg_props.hxx"
20 // fg_os callback registration APIs
21 // (These are not glut-specific)
24 static fgIdleHandler IdleHandler = 0;
25 static fgDrawHandler DrawHandler = 0;
26 static fgWindowResizeHandler WindowResizeHandler = 0;
27 static fgKeyHandler KeyHandler = 0;
28 static fgMouseClickHandler MouseClickHandler = 0;
29 static fgMouseMotionHandler MouseMotionHandler = 0;
31 // We need to flush all pending mouse move events past a mouse warp to avoid
32 // a race condition ending in warping twice and having huge increments for the
34 // I am not aware of such a flush function in glut. So we emulate that by
35 // ignoring mouse move events between a warp mouse and the next frame.
36 static bool mouseWarped = false;
38 void fgRegisterIdleHandler(fgIdleHandler func)
43 void fgRegisterDrawHandler(fgDrawHandler func)
48 void fgRegisterWindowResizeHandler(fgWindowResizeHandler func)
50 WindowResizeHandler = func;
53 void fgRegisterKeyHandler(fgKeyHandler func)
58 void fgRegisterMouseClickHandler(fgMouseClickHandler func)
60 MouseClickHandler = func;
63 void fgRegisterMouseMotionHandler(fgMouseMotionHandler func)
65 MouseMotionHandler = func;
69 // Native glut callbacks.
70 // These translate the glut event model into fg*Handler callbacks
73 static int GlutModifiers = 0;
75 static void callKeyHandler(int k, int mods, int x, int y)
77 int puiup = mods & KEYMOD_RELEASED ? PU_UP : PU_DOWN;
78 if(puKeyboard(k, puiup))
80 if(KeyHandler) (*KeyHandler)(k, mods, x, y);
83 static void GLUTmotion (int x, int y)
87 if(MouseMotionHandler) (*MouseMotionHandler)(x, y);
90 static void GLUTmouse (int button, int updown, int x, int y)
92 GlutModifiers = glutGetModifiers();
93 if(MouseClickHandler) (*MouseClickHandler)(button, updown, x, y);
96 static void GLUTspecialkeyup(int k, int x, int y)
98 GlutModifiers = glutGetModifiers();
99 callKeyHandler(256 + k, fgGetKeyModifiers() | KEYMOD_RELEASED, x, y);
102 static void GLUTspecialkey(int k, int x, int y)
104 GlutModifiers = glutGetModifiers();
105 callKeyHandler(256 + k, fgGetKeyModifiers(), x, y);
108 static void GLUTkeyup(unsigned char k, int x, int y)
110 GlutModifiers = glutGetModifiers();
111 callKeyHandler(k, fgGetKeyModifiers() | KEYMOD_RELEASED, x, y);
114 static void GLUTkey(unsigned char k, int x, int y)
116 GlutModifiers = glutGetModifiers();
117 callKeyHandler(k, fgGetKeyModifiers(), x, y);
120 static void GLUTidle()
122 if(IdleHandler) (*IdleHandler)();
126 static void GLUTdraw()
128 if(DrawHandler) (*DrawHandler)();
133 static void GLUTreshape(int w, int h)
135 if(WindowResizeHandler) (*WindowResizeHandler)(w, h);
139 // fg_os API definition
142 void fgOSInit(int* argc, char** argv)
144 glutInit(argc, argv);
147 void fgOSFullScreen()
157 void fgOSExit(int code)
162 static int CurrentCursor = MOUSE_CURSOR_POINTER;
164 int fgGetMouseCursor()
166 return CurrentCursor;
169 void fgSetMouseCursor(int cursor)
171 CurrentCursor = cursor;
172 if (cursor == MOUSE_CURSOR_NONE) cursor = GLUT_CURSOR_NONE;
173 else if(cursor == MOUSE_CURSOR_POINTER) cursor = GLUT_CURSOR_INHERIT;
174 else if(cursor == MOUSE_CURSOR_WAIT) cursor = GLUT_CURSOR_WAIT;
175 else if(cursor == MOUSE_CURSOR_CROSSHAIR) cursor = GLUT_CURSOR_CROSSHAIR;
176 else if(cursor == MOUSE_CURSOR_LEFTRIGHT) cursor = GLUT_CURSOR_LEFT_RIGHT;
177 // Otherwise, pass it through unchanged...
178 glutSetCursor(cursor);
181 void fgWarpMouse(int x, int y)
184 glutWarpPointer(x, y);
187 int fgGetKeyModifiers()
190 if(GlutModifiers & GLUT_ACTIVE_SHIFT) result |= KEYMOD_SHIFT;
191 if(GlutModifiers & GLUT_ACTIVE_CTRL) result |= KEYMOD_CTRL;
192 if(GlutModifiers & GLUT_ACTIVE_ALT) result |= KEYMOD_ALT;
196 void fgRequestRedraw()
201 void fgOSOpenWindow(int w, int h, int bpp, bool alpha,
202 bool stencil, bool fullscreen)
204 int mode = GLUT_RGB | GLUT_DEPTH | GLUT_DOUBLE;
205 if(alpha) mode |= GLUT_ALPHA;
206 if(stencil && bpp > 16) mode |= GLUT_STENCIL;
208 glutInitDisplayMode(mode);
209 glutInitWindowSize(w, h);
210 if(!fgGetBool("/sim/startup/game-mode")) {
211 glutCreateWindow("FlightGear");
213 char game_mode_str[20];
214 SGPropertyNode *p = fgGetNode("/sim/frame-rate-throttle-hz", false);
216 int hz = p->getIntValue();
217 snprintf(game_mode_str, 20, "%dx%d:%d@%d", w, h, bpp, hz);
219 snprintf(game_mode_str, 20, "%dx%d:%d", w, h, bpp);
221 glutGameModeString( game_mode_str );
225 // Register these here. Calling them before the window is open
227 glutMotionFunc(GLUTmotion);
228 glutPassiveMotionFunc(GLUTmotion);
229 glutMouseFunc(GLUTmouse);
230 glutSpecialUpFunc(GLUTspecialkeyup);
231 glutSpecialFunc(GLUTspecialkey);
232 glutKeyboardUpFunc(GLUTkeyup);
233 glutKeyboardFunc(GLUTkey);
234 glutIdleFunc(GLUTidle);
235 glutDisplayFunc(GLUTdraw);
236 glutReshapeFunc(GLUTreshape);
239 // Noop; the graphics context is always current