3dphotoshoot

annotate src/game.cc @ 27:3d082c566b53

fixed all the bugs, pc version works
author John Tsiombikas <nuclear@member.fsf.org>
date Thu, 18 Jun 2015 04:32:25 +0300
parents a460b1e5af4a
children
rev   line source
nuclear@0 1 #include <stdio.h>
nuclear@0 2 #include <stdlib.h>
nuclear@0 3 #include <math.h>
nuclear@11 4 #include <assert.h>
nuclear@25 5 #include <algorithm>
nuclear@0 6 #include "opengl.h"
nuclear@0 7 #include "game.h"
nuclear@7 8 #include "camera.h"
nuclear@11 9 #include "sanegl.h"
nuclear@17 10 #include "texture.h"
nuclear@21 11 #include "shader.h"
nuclear@22 12 #include "text.h"
nuclear@24 13 #include "vmath/vmath.h"
nuclear@25 14 #include "mesh.h"
nuclear@25 15 #include "meshgen.h"
nuclear@7 16
nuclear@21 17 static void draw_quad(float hsz, float vsz);
nuclear@25 18 static void draw_rotation_gizmo();
nuclear@25 19 static void draw_disc_wedge(float start, float end, int subdiv);
nuclear@0 20
nuclear@22 21 int win_width, win_height;
nuclear@22 22
nuclear@9 23 static float win_aspect;
nuclear@9 24 static int video_width, video_height;
nuclear@9 25 static float video_aspect;
nuclear@17 26 static struct texture *test_tex;
nuclear@17 27
nuclear@25 28 static SdrProg *sdr_tex, *sdr_color, *sdr_debug;
nuclear@0 29
nuclear@25 30 static Quaternion last_rot;
nuclear@25 31 static Vector3 last_trans;
nuclear@25 32
nuclear@25 33 static Quaternion rot;
nuclear@25 34 static Vector3 rot_euler;
nuclear@25 35
nuclear@25 36 static Mesh *mesh;
nuclear@24 37
nuclear@20 38 extern "C" int game_init(void)
nuclear@0 39 {
nuclear@27 40 glEnable(GL_DEPTH_TEST);
nuclear@27 41 glEnable(GL_CULL_FACE);
nuclear@0 42
nuclear@0 43 glClearColor(0.4, 0.4, 0.4, 1);
nuclear@8 44
nuclear@25 45 if(!(sdr_tex = get_sdrprog("sdr/vertex.glsl", "sdr/tex.p.glsl"))) {
nuclear@10 46 return -1;
nuclear@10 47 }
nuclear@25 48 if(!(sdr_color = get_sdrprog("sdr/vertex.glsl", "sdr/color.p.glsl"))) {
nuclear@25 49 return -1;
nuclear@25 50 }
nuclear@25 51 if(!(sdr_debug = get_sdrprog("sdr/vertex.glsl", "sdr/normvis.p.glsl"))) {
nuclear@17 52 return -1;
nuclear@17 53 }
nuclear@17 54
nuclear@17 55 if(!(test_tex = get_texture("data/opengl.png"))) {
nuclear@17 56 return -1;
nuclear@17 57 }
nuclear@10 58
nuclear@25 59 mesh = new Mesh;
nuclear@25 60 gen_cylinder(mesh, 0.2, 1.0, 16, 1);
nuclear@25 61
nuclear@8 62 cam_start_video();
nuclear@9 63 cam_video_size(&video_width, &video_height);
nuclear@9 64 if(video_height) {
nuclear@9 65 video_aspect = (float)video_width / (float)video_height;
nuclear@9 66 } else {
nuclear@9 67 video_aspect = 1.0;
nuclear@9 68 }
nuclear@9 69
nuclear@9 70 printf("started video %dx%d (aspect: %g)\n", video_width, video_height, video_aspect);
nuclear@0 71 return 0;
nuclear@0 72 }
nuclear@0 73
nuclear@20 74 extern "C" void game_shutdown(void)
nuclear@0 75 {
nuclear@8 76 cam_shutdown();
nuclear@21 77 delete sdr_tex;
nuclear@0 78 }
nuclear@0 79
nuclear@20 80 extern "C" void game_display(unsigned long msec)
nuclear@0 81 {
nuclear@9 82 unsigned int tex;
nuclear@9 83 float xscale, yscale;
nuclear@9 84
nuclear@8 85 cam_update();
nuclear@9 86 tex = cam_texture();
nuclear@7 87
nuclear@4 88 //float tsec = (float)msec / 1000.0f;
nuclear@0 89
nuclear@0 90 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
nuclear@0 91
nuclear@27 92 glDisable(GL_DEPTH_TEST);
nuclear@27 93
nuclear@25 94 // draw video preview frame
nuclear@25 95 gl_matrix_mode(GL_PROJECTION);
nuclear@25 96 gl_push_matrix();
nuclear@25 97 gl_load_identity();
nuclear@25 98 gl_scalef((float)win_height / (float)win_width, 1, 1);
nuclear@11 99 gl_matrix_mode(GL_MODELVIEW);
nuclear@11 100 gl_load_identity();
nuclear@7 101
nuclear@9 102 if(video_aspect > win_aspect) {
nuclear@9 103 xscale = 1.0;
nuclear@9 104 yscale = 1.0 / video_aspect;
nuclear@9 105 } else {
nuclear@9 106 xscale = video_aspect;
nuclear@9 107 yscale = 1.0;
nuclear@9 108 }
nuclear@25 109 gl_scalef(xscale, yscale, 1);
nuclear@17 110
nuclear@25 111 cam_draw_preview();
nuclear@25 112
nuclear@25 113 gl_matrix_mode(GL_PROJECTION);
nuclear@25 114 gl_pop_matrix();
nuclear@25 115 // done drawing preview
nuclear@25 116
nuclear@27 117 glEnable(GL_DEPTH_TEST);
nuclear@25 118
nuclear@17 119 gl_matrix_mode(GL_MODELVIEW);
nuclear@17 120 gl_load_identity();
nuclear@25 121 gl_translatef(0, 0, -6);
nuclear@17 122
nuclear@25 123 draw_rotation_gizmo();
nuclear@22 124
nuclear@24 125 // print the rotation quaternion
nuclear@22 126 text_color(1, 1, 1, 1);
nuclear@24 127 text_position(0, 0);
nuclear@25 128 text_printf("translation (% .3f, % .3f, % .3f)", last_trans.x, last_trans.y, last_trans.z);
nuclear@24 129 text_position(0, 1);
nuclear@25 130 text_printf("Rotation quat ([% 1.3f, % 1.3f, % 1.3f], % 1.3f)", last_rot.v.x, last_rot.v.y, last_rot.v.z, last_rot.s);
nuclear@7 131 }
nuclear@7 132
nuclear@21 133 static void draw_quad(float hsz, float vsz)
nuclear@7 134 {
nuclear@7 135 static const float varr[] = {-1, -1, 1, -1, 1, 1, -1, 1};
nuclear@9 136 static const float tcarr[] = {0, 0, 1, 0, 1, 1, 0, 1};
nuclear@7 137
nuclear@11 138 gl_matrix_mode(GL_MODELVIEW);
nuclear@11 139 gl_push_matrix();
nuclear@11 140 gl_scalef(hsz, vsz, 1);
nuclear@11 141
nuclear@21 142 if(SdrProg::active) {
nuclear@21 143 gl_apply_xform(SdrProg::active->get_globj());
nuclear@21 144 }
nuclear@7 145
nuclear@21 146 glEnableVertexAttribArray(SDR_ATTR_VERTEX);
nuclear@21 147 glEnableVertexAttribArray(SDR_ATTR_TEXCOORD);
nuclear@21 148 glVertexAttribPointer(SDR_ATTR_VERTEX, 2, GL_FLOAT, 0, 0, varr);
nuclear@21 149 glVertexAttribPointer(SDR_ATTR_TEXCOORD, 2, GL_FLOAT, 0, 0, tcarr);
nuclear@7 150
nuclear@8 151 glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
nuclear@7 152
nuclear@21 153 glDisableVertexAttribArray(SDR_ATTR_VERTEX);
nuclear@21 154 glDisableVertexAttribArray(SDR_ATTR_TEXCOORD);
nuclear@11 155
nuclear@11 156 gl_pop_matrix();
nuclear@0 157 }
nuclear@0 158
nuclear@25 159 static void draw_rotation_gizmo()
nuclear@25 160 {
nuclear@25 161 /*static const float axis[][3] = {
nuclear@25 162 {1, 0, 0}, {0, 1, 0}, {0, 0, 1}
nuclear@25 163 };*/
nuclear@25 164
nuclear@25 165 last_rot.normalize();
nuclear@25 166 Matrix4x4 rmat = last_rot.get_rotation_matrix().transposed();
nuclear@25 167 gl_matrix_mode(GL_MODELVIEW);
nuclear@25 168 gl_push_matrix();
nuclear@25 169 gl_mult_matrixf(rmat[0]);
nuclear@25 170
nuclear@25 171 sdr_debug->bind();
nuclear@26 172 gl_apply_xform(sdr_debug->get_globj());
nuclear@25 173
nuclear@25 174 mesh->draw();
nuclear@25 175
nuclear@25 176 gl_pop_matrix();
nuclear@25 177 }
nuclear@25 178
nuclear@25 179 static void draw_disc_wedge(float start, float end, int subdiv)
nuclear@25 180 {
nuclear@25 181 if(start > end) {
nuclear@25 182 float tmp = start;
nuclear@25 183 start = end;
nuclear@25 184 end = tmp;
nuclear@25 185 }
nuclear@25 186
nuclear@25 187 float arc_size = end - start;
nuclear@25 188 subdiv = std::max<int>(subdiv * arc_size, 1);
nuclear@25 189 int nverts = subdiv + 2;
nuclear@25 190
nuclear@25 191 float *varr = (float*)alloca(nverts * 3 * sizeof *varr);
nuclear@25 192 float *vptr = varr;
nuclear@25 193
nuclear@25 194 // start with the center vertex
nuclear@25 195 vptr[0] = vptr[1] = vptr[2] = 0;
nuclear@25 196 vptr += 3;
nuclear@25 197
nuclear@25 198 // then add the arc vertices in sequence
nuclear@25 199 float u = start;
nuclear@25 200 float du = arc_size / (float)subdiv;
nuclear@25 201 for(int i=0; i<subdiv + 1; i++) {
nuclear@25 202 float angle = u * M_PI * 2.0;
nuclear@25 203 vptr[0] = sin(angle);
nuclear@25 204 vptr[1] = cos(angle);
nuclear@25 205 vptr[2] = 0.0;
nuclear@25 206 vptr += 3;
nuclear@25 207 u += du;
nuclear@25 208 }
nuclear@25 209
nuclear@25 210 glEnableVertexAttribArray(SDR_ATTR_VERTEX);
nuclear@25 211 glVertexAttribPointer(SDR_ATTR_VERTEX, 3, GL_FLOAT, 0, 0, varr);
nuclear@25 212
nuclear@25 213 glDrawArrays(GL_TRIANGLE_FAN, 0, nverts);
nuclear@25 214
nuclear@25 215 glDisableVertexAttribArray(SDR_ATTR_VERTEX);
nuclear@25 216 }
nuclear@25 217
nuclear@20 218 extern "C" void game_reshape(int x, int y)
nuclear@0 219 {
nuclear@0 220 win_width = x;
nuclear@0 221 win_height = y;
nuclear@9 222 win_aspect = y ? (float)x / (float)y : 1.0;
nuclear@0 223 glViewport(0, 0, x, y);
nuclear@0 224
nuclear@11 225 gl_matrix_mode(GL_PROJECTION);
nuclear@25 226 glu_perspective(50.0, win_aspect, 0.5, 500.0);
nuclear@0 227 }
nuclear@0 228
nuclear@20 229 extern "C" void game_keyboard(int key, int pressed)
nuclear@0 230 {
nuclear@0 231 if(!pressed) return;
nuclear@0 232
nuclear@0 233 switch(key) {
nuclear@0 234 case 27:
nuclear@0 235 exit(0);
nuclear@0 236
nuclear@0 237 default:
nuclear@0 238 break;
nuclear@0 239 }
nuclear@0 240 }
nuclear@0 241
nuclear@0 242 #define MAX_TOUCH_IDS 16
nuclear@0 243 static struct {
nuclear@0 244 int bnstate[8];
nuclear@0 245 int prev_x, prev_y;
nuclear@0 246 } mstate[MAX_TOUCH_IDS];
nuclear@0 247
nuclear@20 248 extern "C" void game_mouse_button(int id, int bn, int pressed, int x, int y)
nuclear@0 249 {
nuclear@0 250 if(id >= MAX_TOUCH_IDS) return;
nuclear@0 251
nuclear@0 252 mstate[id].prev_x = x;
nuclear@0 253 mstate[id].prev_y = y;
nuclear@0 254 mstate[id].bnstate[bn] = pressed;
nuclear@0 255 }
nuclear@0 256
nuclear@20 257 extern "C" void game_mouse_motion(int id, int x, int y)
nuclear@0 258 {
nuclear@0 259 /*
nuclear@0 260 int dx, dy, cx, cy;
nuclear@0 261
nuclear@0 262 if(id >= MAX_TOUCH_IDS) return;
nuclear@0 263
nuclear@0 264 cx = win_width / 2;
nuclear@0 265 cy = win_height / 2;
nuclear@0 266
nuclear@0 267 dx = x - mstate[id].prev_x;
nuclear@0 268 dy = y - mstate[id].prev_y;
nuclear@0 269 mstate[id].prev_x = x;
nuclear@0 270 mstate[id].prev_y = y;
nuclear@0 271
nuclear@0 272 if(!dx && !dy) return;
nuclear@0 273
nuclear@0 274 if(mouselook || mstate[id].bnstate[0]) {
nuclear@0 275 player_turn(&player, dx * 0.5, dy * 0.5);
nuclear@0 276 }
nuclear@0 277 if(mstate[id].bnstate[2]) {
nuclear@0 278 dbg_cam_dist += 0.1 * dy;
nuclear@0 279 if(dbg_cam_dist < 0.0) dbg_cam_dist = 0.0;
nuclear@0 280 }
nuclear@0 281
nuclear@0 282 if(mouselook) {
nuclear@0 283 warping_mouse = 1;
nuclear@0 284 set_mouse_pos(cx, cy);
nuclear@0 285 mstate[id].prev_x = cx;
nuclear@0 286 mstate[id].prev_y = cy;
nuclear@0 287 }
nuclear@0 288 */
nuclear@0 289 }
nuclear@0 290
nuclear@24 291 void game_6dof_translation(float dx, float dy, float dz)
nuclear@24 292 {
nuclear@25 293 last_trans.x = dx;
nuclear@25 294 last_trans.y = dy;
nuclear@25 295 last_trans.z = dz;
nuclear@24 296 }
nuclear@24 297
nuclear@24 298 void game_6dof_rotation(float qx, float qy, float qz, float qw)
nuclear@24 299 {
nuclear@25 300 last_rot.v.x = qx;
nuclear@25 301 last_rot.v.y = qy;
nuclear@25 302 last_rot.v.z = qz;
nuclear@25 303 last_rot.s = qw;
nuclear@25 304
nuclear@25 305 rot.rotate(last_rot);
nuclear@24 306 }