# HG changeset patch # User John Tsiombikas # Date 1380887450 -10800 # Node ID 9dc19419f52be3570ad664e322b3721636528261 # Parent 8419d8a13cee8b262ffb096c5d6c17067eaf63b5# Parent ef4c9d8eeca7c3d4852f8352d14068aa24edc79c merged diff -r 8419d8a13cee -r 9dc19419f52b oculus1.sln --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/oculus1.sln Fri Oct 04 14:50:50 2013 +0300 @@ -0,0 +1,20 @@ + +Microsoft Visual Studio Solution File, Format Version 10.00 +# Visual Studio 2008 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "oculus1", "oculus1.vcproj", "{BF4DEBD4-BA07-4DEF-82A7-ACAF8F20110B}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Release|Win32 = Release|Win32 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {BF4DEBD4-BA07-4DEF-82A7-ACAF8F20110B}.Debug|Win32.ActiveCfg = Debug|Win32 + {BF4DEBD4-BA07-4DEF-82A7-ACAF8F20110B}.Debug|Win32.Build.0 = Debug|Win32 + {BF4DEBD4-BA07-4DEF-82A7-ACAF8F20110B}.Release|Win32.ActiveCfg = Release|Win32 + {BF4DEBD4-BA07-4DEF-82A7-ACAF8F20110B}.Release|Win32.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff -r 8419d8a13cee -r 9dc19419f52b oculus1.vcproj --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/oculus1.vcproj Fri Oct 04 14:50:50 2013 +0300 @@ -0,0 +1,575 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff -r 8419d8a13cee -r 9dc19419f52b src/main.cc --- a/src/main.cc Fri Oct 04 14:50:26 2013 +0300 +++ b/src/main.cc Fri Oct 04 14:50:50 2013 +0300 @@ -500,26 +500,6 @@ { width = x; height = y; - - if(!use_vr) { - rtarg_width = width; - rtarg_height = height; - - int new_tex_width = next_pow2(width); - int new_tex_height = next_pow2(height); - - if(new_tex_width != rtarg_tex_width || new_tex_height != rtarg_tex_width) { - // TODO - exit(1); - } - - rtarg_tex_width = new_tex_width; - rtarg_tex_height = new_tex_height; - - tex_scale_x = (float)rtarg_width / (float)rtarg_tex_width; - tex_scale_y = (float)rtarg_height / (float)rtarg_tex_height; - - } } static void keyb(unsigned char key, int x, int y) @@ -535,6 +515,13 @@ case 'f': toggle_fullscreen(); break; + + case '\\': + { + extern bool dbg_enable; + dbg_enable = !dbg_enable; + } + break; } keystate[key] = true; diff -r 8419d8a13cee -r 9dc19419f52b src/vr.cc --- a/src/vr.cc Fri Oct 04 14:50:26 2013 +0300 +++ b/src/vr.cc Fri Oct 04 14:50:50 2013 +0300 @@ -4,13 +4,46 @@ #include "vr_impl.h" #include "vr_sdr.h" +#ifndef WIN32 +#include +#else +#include +#endif + +#define USUB 28 +#define VSUB 40 + +/* these are just used for the shaderless precomputed distortion method */ +struct Mesh { + int prim; + int num_verts, num_faces; + unsigned int vbo; + unsigned int ibo; +}; +struct Vertex { + float x, y, z; + float tx, ty; +}; + + static void init_ctx(); static bool init_ovr(); static bool init_sdr(); +static Mesh gen_view_mesh(int usub, int vsub, float aspect, float lens_center_offset, + float scale, const float *dist_factors, float tex_scale_x, float tex_scale_y); +static void distort_texcoords(float *tc, float aspect, float lens_center_offset, float scale, const float *dist_factors); +static float barrel_scale(float rad, const float *k); + VRContext vr_ctx; static unsigned int sdrprog; +static Mesh wrapmesh[2]; +static bool mesh_valid; + +bool dbg_enable; + + extern "C" int vr_init(enum vr_init_mode mode) { glewInit(); @@ -332,49 +365,204 @@ {-1, -1, 0, 1}, {0, -1, 1, 1} }; + static const float quad_trans[3] = {0, -1, 1}; + static const float quad_scale[3] = {1, 0.5, 0.5}; static const float offs_scale[3] = {0.0, -1.0, 1.0}; + static int prev_tex_scale_x, prev_tex_scale_y; glPushAttrib(GL_ENABLE_BIT); glDisable(GL_DEPTH_TEST); glDisable(GL_LIGHTING); - glEnable(GL_TEXTURE_2D); + glDisable(GL_CULL_FACE); + + glMatrixMode(GL_PROJECTION); + glPushMatrix(); + glLoadIdentity(); glMatrixMode(GL_MODELVIEW); glPushMatrix(); glLoadIdentity(); - glMatrixMode(GL_PROJECTION); - glPushMatrix(); - glLoadIdentity(); + if(!dbg_enable) { + glUseProgram(sdrprog); - glUseProgram(sdrprog); + if(sdrprog) { + int loc; + if((loc = glGetUniformLocation(sdrprog, "lens_center_offset")) != -1) { + float offset = vr_ctx.info.lens_center_offset * offs_scale[eye]; + glUniform1f(loc, offset); + } - if(sdrprog) { - int loc; - if((loc = glGetUniformLocation(sdrprog, "lens_center_offset")) != -1) { - float offset = vr_ctx.info.lens_center_offset * offs_scale[eye]; - glUniform1f(loc, offset); + if((loc = glGetUniformLocation(sdrprog, "tex_scale")) != -1) { + glUniform2f(loc, tex_scale_x, tex_scale_y); + } } - if((loc = glGetUniformLocation(sdrprog, "tex_scale")) != -1) { - glUniform2f(loc, tex_scale_x, tex_scale_y); + glBindTexture(GL_TEXTURE_2D, tex); + glBegin(GL_QUADS); + glColor4f(1, 1, 1, 1); + glTexCoord2f(0, 0); glVertex2f(rects[eye][0], rects[eye][1]); + glTexCoord2f(1, 0); glVertex2f(rects[eye][2], rects[eye][1]); + glTexCoord2f(1, 1); glVertex2f(rects[eye][2], rects[eye][3]); + glTexCoord2f(0, 1); glVertex2f(rects[eye][0], rects[eye][3]); + glEnd(); + + glUseProgram(0); + + } else { + + if(!mesh_valid || tex_scale_x != prev_tex_scale_x || tex_scale_y != prev_tex_scale_y) { + for(int i=0; i<2; i++) { + int eye = i + VR_EYE_LEFT; + + if(wrapmesh[i].vbo) { + glDeleteBuffers(1, &wrapmesh[i].vbo); + } + if(wrapmesh[i].ibo) { + glDeleteBuffers(1, &wrapmesh[i].ibo); + } + + float aspect = vr_ctx.info.aspect / 2.0; + float offset = vr_ctx.info.lens_center_offset * offs_scale[eye]; + wrapmesh[i] = gen_view_mesh(USUB, VSUB, aspect, offset, vr_ctx.info.scale, vr_ctx.info.distort, + tex_scale_x, tex_scale_y); + } + mesh_valid = true; + prev_tex_scale_x = tex_scale_x; + prev_tex_scale_y = tex_scale_y; } + + glScalef(quad_scale[eye], 1.0, 1.0); + glTranslatef(quad_trans[eye], 0, 0); + + glUseProgram(0); + glBindTexture(GL_TEXTURE_2D, tex); + glEnable(GL_TEXTURE_2D); + + glColor3f(1, 1, 1); + + glEnableClientState(GL_VERTEX_ARRAY); + glEnableClientState(GL_TEXTURE_COORD_ARRAY); + + int meshidx = eye - VR_EYE_LEFT; + glBindBuffer(GL_ARRAY_BUFFER, wrapmesh[meshidx].vbo); + glVertexPointer(3, GL_FLOAT, sizeof(Vertex), 0); + glTexCoordPointer(2, GL_FLOAT, sizeof(Vertex), (void*)offsetof(Vertex, tx)); + + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, wrapmesh[meshidx].ibo); + glDrawElements(GL_TRIANGLES, wrapmesh[meshidx].num_faces * 3, GL_UNSIGNED_INT, 0); + + glBindBuffer(GL_ARRAY_BUFFER, 0); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0); + + glDisableClientState(GL_VERTEX_ARRAY); + glDisableClientState(GL_TEXTURE_COORD_ARRAY); } - glBindTexture(GL_TEXTURE_2D, tex); - glBegin(GL_QUADS); - glColor4f(1, 1, 1, 1); - glTexCoord2f(0, 0); glVertex2f(rects[eye][0], rects[eye][1]); - glTexCoord2f(1, 0); glVertex2f(rects[eye][2], rects[eye][1]); - glTexCoord2f(1, 1); glVertex2f(rects[eye][2], rects[eye][3]); - glTexCoord2f(0, 1); glVertex2f(rects[eye][0], rects[eye][3]); - glEnd(); - - glUseProgram(0); - + glMatrixMode(GL_PROJECTION); glPopMatrix(); glMatrixMode(GL_MODELVIEW); glPopMatrix(); glPopAttrib(); } + +static Mesh gen_view_mesh(int usub, int vsub, float aspect, float lens_center_offset, + float scale, const float *dist_factors, float tex_scale_x, float tex_scale_y) +{ + int uverts = usub + 1; + int vverts = vsub + 1; + + int num_verts = uverts * vverts; + int num_quads = usub * vsub; + int num_tris = num_quads * 2; + + Vertex *varr = new Vertex[num_verts]; + unsigned int *iarr = new unsigned int[num_tris * 3]; + + float du = 1.0 / (float)usub; + float dv = 1.0 / (float)vsub; + + Vertex *vptr = varr; + for(int i=0; ix = x; + vptr->y = y; + vptr->z = 0; + vptr->tx = tc[0] * tex_scale_x; + vptr->ty = tc[1] * tex_scale_y; + vptr++; + } + } + + unsigned int *iptr = iarr; + for(int i=0; i [-1, 1] + float ptx = tc[0] * 2.0 - 1.0; + float pty = tc[1] * 2.0 - 1.0; + + ptx += lens_center_offset * 2.0; + pty /= aspect; // correct for aspect ratio + + float rad = barrel_scale(ptx * ptx + pty * pty, dist_factors); + ptx *= rad; // scale the point by the computer distortion radius + pty *= rad; + + ptx /= scale; + pty /= scale; + + pty *= aspect; + ptx -= lens_center_offset * 2.0; + + // map back to range [0, 1] + tc[0] = ptx * 0.5 + 0.5; + tc[1] = pty * 0.5 + 0.5; +} + +static float barrel_scale(float rad, const float *k) +{ + float radsq = rad * rad; + float radquad = radsq * radsq; + return k[0] + k[1] * radsq + k[2] * radquad + k[3] * radquad * radsq; +}