vrshoot
diff src/main_glut.cc @ 0:b2f14e535253
initial commit
author | John Tsiombikas <nuclear@member.fsf.org> |
---|---|
date | Sat, 01 Feb 2014 19:58:19 +0200 |
parents | |
children |
line diff
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/src/main_glut.cc Sat Feb 01 19:58:19 2014 +0200 1.3 @@ -0,0 +1,205 @@ 1.4 +#include <stdlib.h> 1.5 +#include <ctype.h> 1.6 +#include <assert.h> 1.7 +#include "opengl.h" 1.8 + 1.9 +#include "game.h" 1.10 +#include "input.h" 1.11 +#include "screen.h" 1.12 +#include "logger.h" 1.13 + 1.14 +/* called by any other part of the game when a redisplay is needed 1.15 + * (mostly useful for tools which do not redisplay continuously) 1.16 + */ 1.17 +void request_redisplay(); 1.18 + 1.19 +void swap_buffers(); 1.20 + 1.21 +static void display(void); 1.22 +static void reshape(int x, int y); 1.23 +static void keydown(unsigned char key, int x, int y); 1.24 +static void keyup(unsigned char key, int x, int y); 1.25 +static void skeydown(int key, int x, int y); 1.26 +static void skeyup(int key, int x, int y); 1.27 +static void mouse(int bn, int state, int x, int y); 1.28 +static void motion(int x, int y); 1.29 +static void passive_motion(int x, int y); 1.30 + 1.31 +static long redisp_interval; 1.32 + 1.33 +int main(int argc, char **argv) 1.34 +{ 1.35 + glutInit(&argc, argv); 1.36 + glutInitWindowSize(800, 600); 1.37 + glutInitDisplayMode(GLUT_RGB | GLUT_DEPTH | GLUT_DOUBLE | GLUT_MULTISAMPLE); 1.38 + glutCreateWindow("Xmass inferno"); 1.39 + 1.40 + glutDisplayFunc(display); 1.41 + glutReshapeFunc(reshape); 1.42 + glutKeyboardFunc(keydown); 1.43 + glutKeyboardUpFunc(keyup); 1.44 + glutSpecialFunc(skeydown); 1.45 + glutSpecialUpFunc(skeyup); 1.46 + glutMouseFunc(mouse); 1.47 + glutMotionFunc(motion); 1.48 + glutPassiveMotionFunc(passive_motion); 1.49 + 1.50 + game_set_args(argc, argv); 1.51 + if(!game_init()) { 1.52 + return 1; 1.53 + } 1.54 + atexit(game_cleanup); 1.55 + 1.56 + glutMainLoop(); 1.57 + return 0; 1.58 +} 1.59 + 1.60 +void request_redisplay() 1.61 +{ 1.62 + glutPostRedisplay(); 1.63 +} 1.64 + 1.65 +void swap_buffers() 1.66 +{ 1.67 + glUseProgram(0); 1.68 + glutSwapBuffers(); 1.69 +} 1.70 + 1.71 +static void display() 1.72 +{ 1.73 + long ival = current_screen()->redisplay_interval(); 1.74 + if(ival && !redisp_interval) { 1.75 + debug_log("switching to auto-redisplay (interval: %ld)\n", redisp_interval); 1.76 + glutIdleFunc(request_redisplay); 1.77 + } 1.78 + if(!ival && redisp_interval) { 1.79 + debug_log("switching to manual redisplay\n"); 1.80 + glutIdleFunc(0); 1.81 + } 1.82 + redisp_interval = ival; 1.83 + 1.84 + game_display(); 1.85 + // TODO implement framerate limiter 1.86 +} 1.87 + 1.88 + 1.89 +static void reshape(int x, int y) 1.90 +{ 1.91 + game_reshape(x, y); 1.92 +} 1.93 + 1.94 +/* GLUT doesn't have any callbacks for modifier keys, so we fake it by calling 1.95 + * this function all over the place, to generate fake events whenever a modifier 1.96 + * key is detected to have changed state. 1.97 + * The limitation is that this will only detect modkey changes whenever a regular 1.98 + * key is pressed or released, or when a mouse button is pressed or released. 1.99 + */ 1.100 +static void handle_modkeys() 1.101 +{ 1.102 + static int modstate; 1.103 + 1.104 + int mod = glutGetModifiers(); 1.105 + if(mod != modstate) { 1.106 + int diff = mod ^ modstate; 1.107 + 1.108 + if(diff & GLUT_ACTIVE_SHIFT) { 1.109 + bool pressed = mod & GLUT_ACTIVE_SHIFT; 1.110 + game_key(KEY_LSHIFT, pressed); 1.111 + } 1.112 + if(diff & GLUT_ACTIVE_CTRL) { 1.113 + bool pressed = mod & GLUT_ACTIVE_CTRL; 1.114 + game_key(KEY_LCTRL, pressed); 1.115 + } 1.116 + if(diff & GLUT_ACTIVE_ALT) { 1.117 + bool pressed = mod & GLUT_ACTIVE_ALT; 1.118 + game_key(KEY_LALT, pressed); 1.119 + } 1.120 + } 1.121 + modstate = mod; 1.122 +} 1.123 + 1.124 +static int translate_special_key(int key) 1.125 +{ 1.126 + if(key >= GLUT_KEY_F1 && key <= GLUT_KEY_F12) { 1.127 + return (key - GLUT_KEY_F1) + KEY_F1; 1.128 + } 1.129 + if(key >= GLUT_KEY_LEFT && key <= GLUT_KEY_PAGE_DOWN) { 1.130 + return (key - GLUT_KEY_LEFT) + KEY_LEFT; 1.131 + } 1.132 + 1.133 + switch(key) { 1.134 + case GLUT_KEY_HOME: 1.135 + return KEY_HOME; 1.136 + case GLUT_KEY_END: 1.137 + return KEY_END; 1.138 + case GLUT_KEY_INSERT: 1.139 + return KEY_INSERT; 1.140 + 1.141 + default: 1.142 + break; 1.143 + } 1.144 + return 0; 1.145 +} 1.146 + 1.147 +static void keydown(unsigned char c, int x, int y) 1.148 +{ 1.149 + int key = c; 1.150 + if(key == 127) { 1.151 + key = KEY_DELETE; 1.152 + } 1.153 + 1.154 + handle_modkeys(); 1.155 + game_key(key, true); 1.156 +} 1.157 + 1.158 +static void keyup(unsigned char c, int x, int y) 1.159 +{ 1.160 + int key = c; 1.161 + if(key == 127) { 1.162 + key = KEY_DELETE; 1.163 + } 1.164 + 1.165 + handle_modkeys(); 1.166 + game_key(key, false); 1.167 +} 1.168 + 1.169 +static void skeydown(int key, int x, int y) 1.170 +{ 1.171 + handle_modkeys(); 1.172 + 1.173 + if((key = translate_special_key(key)) > 0) { 1.174 + game_key(key, true); 1.175 + } 1.176 +} 1.177 + 1.178 +static void skeyup(int key, int x, int y) 1.179 +{ 1.180 + handle_modkeys(); 1.181 + 1.182 + if((key = translate_special_key(key)) > 0) { 1.183 + game_key(key, false); 1.184 + } 1.185 +} 1.186 + 1.187 +static void mouse(int bn, int state, int x, int y) 1.188 +{ 1.189 + handle_modkeys(); 1.190 + 1.191 + int bnidx = bn - GLUT_LEFT_BUTTON; 1.192 + bool bnstate = state == GLUT_DOWN; 1.193 + 1.194 + current_screen()->button(bnidx, bnstate, x, y); 1.195 + set_mouse_state(x, y, bnidx, bnstate); // this MUST be after the event dispatch 1.196 +} 1.197 + 1.198 +static void motion(int x, int y) 1.199 +{ 1.200 + set_mouse_state(x, y); 1.201 + current_screen()->motion(x, y, false); 1.202 +} 1.203 + 1.204 +static void passive_motion(int x, int y) 1.205 +{ 1.206 + set_mouse_state(x, y); 1.207 + current_screen()->motion(x, y, true); 1.208 +}