/** Some VRPN orientation sensors may be rotated differently than what we * expect them to be (for example, orientation is correct except that * the camera is pointing in the wrong direction). This function will * adjust the orientation matrix so that the camera is pointing in the * correct direction. */ static void viewmat_fix_rotation(float orient[16]) { // Fix rotation for a hard-wired orientation sensor. if(viewmat_control_mode == VIEWMAT_CONTROL_ORIENT) { float adjustLeft[16] = { 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1 }; mat4f_transpose(adjustLeft); // transpose to column-major order float adjustRight[16] = { 0, 0, -1, 0, -1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1 }; mat4f_transpose(adjustRight); mat4f_mult_mat4f_new(orient, adjustLeft, orient); mat4f_mult_mat4f_new(orient, orient, adjustRight); return; } // Fix rotation for VRPN if(viewmat_vrpn_obj == NULL || strlen(viewmat_vrpn_obj) == 0) return; char *hostname = vrpn_default_host(); if(hostname == NULL) return; /* Some objects in the IVS lab need to be rotated to match the * orientation that we expect. Apply the fix here. */ if(vrpn_is_vicon(hostname)) // MTU vicon tracker { /* Note, orient has not been transposed/inverted yet. Doing * orient*offset will effectively effectively be rotating the * camera---not the world. */ if(strcmp(viewmat_vrpn_obj, "DK2") == 0) { float offsetVicon[16]; mat4f_identity(offsetVicon); mat4f_rotateAxis_new(offsetVicon, 90, 1,0,0); mat4f_mult_mat4f_new(orient, orient, offsetVicon); } if(strcmp(viewmat_vrpn_obj, "DSight") == 0) { float offsetVicon1[16]; mat4f_identity(offsetVicon1); mat4f_rotateAxis_new(offsetVicon1, 90, 1,0,0); float offsetVicon2[16]; mat4f_identity(offsetVicon2); mat4f_rotateAxis_new(offsetVicon2, 180, 0,1,0); // orient = orient * offsetVicon1 * offsetVicon2 mat4f_mult_mat4f_many(orient, orient, offsetVicon1, offsetVicon2, NULL); } } }
/** Draw a object at the location and orientation of the tracked vrpn object */ void drawObject(const int objectIndex, float viewMat[16]) { const char *vrpnObject = global_argv[objectIndex]; const float scaleFactor = .5; float pos[4], orient[16]; vrpn_get(vrpnObject, NULL, pos, orient); float modelMat[16],translate[16],scale[16]; mat4f_scale_new(scale, scaleFactor, scaleFactor, scaleFactor); mat4f_translateVec_new(translate, pos); mat4f_mult_mat4f_many(modelMat, translate, orient, scale, NULL); float modelview[16]; mat4f_mult_mat4f_new(modelview, viewMat, modelMat); // modelview = view * model /* Send the modelview matrix to the vertex program. */ glUniformMatrix4fv(kuhl_get_uniform("ModelView"), 1, // number of 4x4 float matrices 0, // transpose modelview); // value glUniform1i(kuhl_get_uniform("renderStyle"), 2); kuhl_errorcheck(); kuhl_geometry_draw(modelgeom); /* Draw the model */ kuhl_errorcheck(); /* Transparency of labels may not appear right because we aren't * sorting them by depth. */ float labelScale[16]; mat4f_scale_new(labelScale, 1, 1/labelAspectRatio[objectIndex-1], 1); mat4f_mult_mat4f_new(modelview, modelview, labelScale); glUniformMatrix4fv(kuhl_get_uniform("ModelView"), 1, 0, modelview); glUniform1i(kuhl_get_uniform("renderStyle"), 1); kuhl_geometry_texture(&quad, label[objectIndex-1], "tex", 1); kuhl_geometry_draw(&quad); #if 0 printf("%s is at\n", vrpnObject); vec3f_print(pos); mat4f_print(orient); #endif }