68f6a23e0620f07331c296e007398b00230a401f
[vrtris] / src / game.c
1 #include <assert.h>
2 #include <goatvr.h>
3 #include <cgmath/cgmath.h>
4 #include "opengl.h"
5 #include "game.h"
6 #include "screen.h"
7 #include "osd.h"
8 #include "opt.h"
9
10 #define DEFSCR  "game"
11
12 static void calc_framerate(void);
13 static void print_framerate(void);
14
15 static int should_swap;
16 static unsigned long framerate;
17
18
19 int game_init(int argc, char **argv)
20 {
21         if(init_opengl() == -1) {
22                 return -1;
23         }
24
25         if(init_options(argc, argv, "vrtris.conf") == -1) {
26                 return -1;
27         }
28
29         if(init_screens() == -1) {
30                 return -1;
31         }
32
33         if(opt.flags & OPT_VR) {
34                 if(goatvr_init() == -1) {
35                         return -1;
36                 }
37                 goatvr_set_origin_mode(GOATVR_HEAD);
38                 goatvr_set_units_scale(10.0f);
39
40                 goatvr_startvr();
41                 should_swap = goatvr_should_swap();
42         }
43
44         glEnable(GL_DEPTH_TEST);
45         glEnable(GL_CULL_FACE);
46         glEnable(GL_LIGHTING);
47         glEnable(GL_LIGHT0);
48
49         return 0;
50 }
51
52 void game_cleanup()
53 {
54         if(opt.flags & OPT_VR) {
55                 goatvr_shutdown();
56         }
57         cleanup_screens();
58 }
59
60 static void update(float dt)
61 {
62         screen->update(dt);
63 }
64
65 void game_display(void)
66 {
67         static long prev_msec;
68         int i;
69         float dt = (float)(time_msec - prev_msec) / 1000.0f;
70         prev_msec = time_msec;
71
72         update(dt);
73
74         if(opt.flags & OPT_VR) {
75                 goatvr_draw_start();
76                 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
77
78                 for(i=0; i<2; i++) {
79                         /* for each eye */
80                         goatvr_draw_eye(i);
81
82                         cgm_mcopy(proj_matrix, goatvr_projection_matrix(i, 0.5, 500.0));
83                         glMatrixMode(GL_PROJECTION);
84                         glLoadMatrixf(proj_matrix);
85
86                         cgm_mcopy(view_matrix, goatvr_view_matrix(i));
87                         glMatrixMode(GL_MODELVIEW);
88                         glLoadMatrixf(view_matrix);
89
90                         screen->draw();
91                         print_framerate();
92                         draw_osd();
93                 }
94
95                 goatvr_draw_done();
96
97                 if(should_swap) {
98                         game_swap_buffers();
99                 }
100
101         } else {
102                 /* non-VR mode */
103                 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
104
105                 cgm_mperspective(proj_matrix, cgm_deg_to_rad(40.0), win_aspect, 0.5, 500.0);
106                 glMatrixMode(GL_PROJECTION);
107                 glLoadMatrixf(proj_matrix);
108
109                 cgm_midentity(view_matrix);
110                 glMatrixMode(GL_MODELVIEW);
111                 glLoadMatrixf(view_matrix);
112
113                 screen->draw();
114                 print_framerate();
115                 draw_osd();
116
117                 game_swap_buffers();
118         }
119
120         assert(glGetError() == GL_NO_ERROR);
121
122         calc_framerate();
123 }
124
125 void game_reshape(int x, int y)
126 {
127         glViewport(0, 0, x, y);
128         goatvr_set_fb_size(x, y, 1.0f);
129
130         reshape_screens(x, y);
131 }
132
133 void game_keyboard(int key, int pressed)
134 {
135         unsigned int mod = game_get_modifiers();
136
137         if(pressed) {
138                 switch(key) {
139                 case 27:
140                         game_quit();
141                         return;
142
143                 case '\n':
144                 case '\r':
145                         if(mod & MOD_ALT) {
146                                 game_toggle_fullscreen();
147                                 return;
148                         }
149                         break;
150
151                 case KEY_HOME:
152                         if(opt.flags & OPT_VR) {
153                                 goatvr_recenter();
154                         }
155                         break;
156
157                 default:
158                         break;
159                 }
160         }
161
162         screen->keyboard(key, pressed);
163 }
164
165 void game_mouse_button(int bn, int pressed, int x, int y)
166 {
167         screen->mouse(bn, pressed, x, y);
168 }
169
170 void game_mouse_motion(int x, int y)
171 {
172         screen->motion(x, y);
173 }
174
175 void game_mouse_wheel(int dir)
176 {
177         screen->wheel(dir);
178 }
179
180
181 void game_gamepad_axis(int axis, float val)
182 {
183         joy_axis[axis] = val;
184 }
185
186 void game_gamepad_button(int bn, int pressed)
187 {
188         if(pressed) {
189                 joy_bnstate |= (1 << bn);
190         } else {
191                 joy_bnstate &= ~(1 << bn);
192         }
193 }
194
195 static void calc_framerate(void)
196 {
197         static unsigned long nframes;
198         static long prev_upd;
199
200         long elapsed = time_msec - prev_upd;
201         if(elapsed >= 1000) {
202                 framerate = nframes * 10000 / elapsed;
203                 nframes = 1;
204                 prev_upd = time_msec;
205         } else {
206                 ++nframes;
207         }
208 }
209
210 static void print_framerate(void)
211 {
212         print_text(9 * win_width / 10, 20, 1, 1, 0, "fps: %d.%d", framerate / 10, framerate % 10);
213 }