tgCamera.cpp
Go to the documentation of this file.
00001 //CPP:
00002 //                      Title:                  class tgCamera
00003 //                      File:                           tgCamera.cpp
00004 //
00005 //                      Function:               Viewing tgCamera for free movement in space
00006 //                                                                      Forward, Backward, Strafe, Rotate
00007 //
00008 //                      Author:                 Thomas Mörwald
00009 //                      Date:                           09.01.2007
00010 // ----------------------------------------------------------------------------
00011 #include <blort/TomGine/tgCamera.h>
00012 
00013 using namespace TomGine;
00014 
00015 tgCamera::Parameter::Parameter(){
00016     width = 640;
00017     height = 480;
00018     fx = 520.0f;
00019     fy = 520.0f;
00020     cx = 320.0f;
00021     cy = 240.0f;
00022     k1 = 0.0f;
00023     k2 = 0.0f;
00024     k3 = 0.0f;
00025     p1 = 0.0f;
00026     p2 = 0.0f;
00027     rot.fromRotVector(vec3(-2.0f,-1.0f,0.5f));
00028     pos = vec3(0.6f, -0.2f, 0.5f);
00029     zNear = 0.01f;
00030     zFar = 4.0f;
00031 }
00032 
00033 tgCamera::Parameter::Parameter(const sensor_msgs::CameraInfo& cam_info)
00034 {
00035     width = cam_info.width;
00036     height = cam_info.height;
00037     fx =cam_info.K.at(0);
00038     cx = cam_info.K.at(2);
00039     fy = cam_info.K.at(4);
00040     cy = cam_info.K.at(5);
00041     if (!cam_info.D.empty())
00042     {
00043       k1 = cam_info.D.at(0);
00044       k2 = cam_info.D.at(1);
00045       k3 = cam_info.D.at(4);
00046       p1 = cam_info.D.at(2);
00047       p2 = cam_info.D.at(3);
00048     }
00049     else
00050     {
00051       k1 = 0.0;
00052       k2 = 0.0;
00053       k3 = 0.0;
00054       p1 = 0.0;
00055       p2 = 0.0;
00056     }
00057     zNear = 0.1f;
00058     zFar = 5.0f;
00059     rot.fromRotVector(vec3(-2.0f,-1.0f,0.5f));
00060     pos = vec3(0.6f, -0.2f, 0.5f);
00061 }
00062 
00063 void tgCamera::Parameter::setPose(const TomGine::tgPose& camPose)
00064 {
00065 //    pos = camPose.t;
00066 //    rot = camPose.q;
00067 }
00068 
00069 tgCamera::tgCamera(){
00070     f = tgVector3(0.0f,0.0f,-1.0f);
00071     s = tgVector3(1.0f,0.0f,0.0f);
00072     u = tgVector3(0.0f,1.0f,0.0f);
00073 }
00074 
00075 void tgCamera::Load(tgCamera::Parameter camPars){
00076 
00077     // intrinsic parameters
00078     // transform the coordinate system of computer vision to OpenGL
00079     //   Vision: origin is in the up left corner, x-axis pointing right, y-axis pointing down
00080     //   OpenGL: origin is in the middle, x-axis pointing right, y-axis pointing up
00081     float fx = 2.0f*camPars.fx / camPars.width;                                 // scale range from [0 ... 640] to [0 ... 2]
00082     float fy = 2.0f*camPars.fy / camPars.height;                                        // scale range from [0 ... 480] to [0 ... 2]
00083     float cx = 1.0f-(2.0f*camPars.cx / camPars.width);          // move coordinates from left to middle of image: [0 ... 2] -> [-1 ... 1] (not negative z value at w-division)
00084     float cy = (2.0f*camPars.cy / camPars.height)-1.0f;         // flip and move coordinates from top to middle of image: [0 ... 2] -> [-1 ... 1] (not negative z value at w-division)
00085     float z1 = (camPars.zFar+camPars.zNear)/(camPars.zNear-camPars.zFar);                                                               // entries for clipping planes
00086     float z2 = 2.0f*camPars.zFar*camPars.zNear/(camPars.zNear-camPars.zFar);                                                            // look up for gluPerspective
00087 
00088     // intrinsic matrix
00089     mat4 intrinsic;
00090     intrinsic[0]=fx;    intrinsic[4]=0; intrinsic[8]=cx;        intrinsic[12]=0;
00091     intrinsic[1]=0;     intrinsic[5]=fy;        intrinsic[9]=cy;        intrinsic[13]=0;
00092     intrinsic[2]=0;     intrinsic[6]=0;         intrinsic[10]=z1;       intrinsic[14]=z2;
00093     intrinsic[3]=0;     intrinsic[7]=0;         intrinsic[11]=-1;       intrinsic[15]=0;        // last row assigns w=-z which inverts cx and cy at w-division
00094 
00095     // computer vision camera coordinates to OpenGL camera coordinates transform
00096     // rotate 180� about x-axis
00097     mat4 cv2gl;
00098     cv2gl[0]=1.0; cv2gl[4]=0.0;         cv2gl[8]=0.0;   cv2gl[12]=0.0;
00099     cv2gl[1]=0.0; cv2gl[5]=-1.0;        cv2gl[9]=0.0;   cv2gl[13]=0.0;
00100     cv2gl[2]=0.0; cv2gl[6]=0.0;         cv2gl[10]=-1.0; cv2gl[14]=0.0;
00101     cv2gl[3]=0.0; cv2gl[7]=0.0;         cv2gl[11]=0.0;  cv2gl[15]=1.0;
00102 
00103     // extrinsic parameters
00104     // look up comments in tools/hardware/video/src/slice/Video.ice
00105     // p = R^T*(w - t) = (R^T, -R^T*t) * (w,1)
00106     mat3 R = camPars.rot;
00107     vec3 t = camPars.pos;
00108     mat4 extrinsic;
00109     extrinsic[0]=R[0];  extrinsic[4]=R[3];      extrinsic[8]=R[6];              extrinsic[12]=0.0;
00110     extrinsic[1]=R[1];  extrinsic[5]=R[4];      extrinsic[9]=R[7];              extrinsic[13]=0.0;
00111     extrinsic[2]=R[2];  extrinsic[6]=R[5];      extrinsic[10]=R[8];             extrinsic[14]=0.0;
00112     extrinsic[3]=0.0;   extrinsic[7]=0.0;       extrinsic[11]=0.0;              extrinsic[15]=1.0;
00113     //  extrinsic = extrinsic.transpose();                                                      // R^T
00114     vec4 tp = -(extrinsic * vec4(t.x, t.y, t.z, 1.0));                  // -R^T*t
00115     extrinsic[12]=tp.x; extrinsic[13]=tp.y; extrinsic[14]=tp.z;
00116     extrinsic = cv2gl * extrinsic;
00117 
00118     // set camera parameters
00119     SetViewport(camPars.width,camPars.height);
00120     SetZRange(camPars.zNear, camPars.zFar);
00121     SetIntrinsic(intrinsic);
00122     SetExtrinsic(extrinsic);
00123     SetPos(camPars.pos.x, camPars.pos.y, camPars.pos.z);
00124 }
00125 
00126 void tgCamera::Set(     float posx,  float posy,  float posz,
00127                         float viewx, float viewy, float viewz,
00128                         float upx,   float upy,   float upz,
00129                         float fovy, unsigned width, unsigned height,
00130                         float zNear, float zFar,
00131                         unsigned short projection){
00132     m_vPos      = tgVector3(posx,  posy,  posz ); // set position
00133     m_vView     = tgVector3(viewx, viewy, viewz); // set view point
00134     m_vUp       = tgVector3(upx,   upy,   upz  ); // set the up vector
00135     pvu2fsu();
00136 
00137     m_fovy = fovy;
00138     m_width = width;
00139     m_height = height;
00140     m_zNear = zNear;
00141     m_zFar = zFar;
00142     m_projection = projection;
00143 
00144     fwh2intrinsic();
00145     fsu2extrinsic();
00146 }
00147 
00148 void tgCamera::SetExtrinsic(float* M){  
00149     m_extrinsic = mat4(M);
00150 
00151     extrinsic2fsu();
00152     fsu2pvu();
00153 
00154     Activate();
00155 }
00156 
00157 void tgCamera::SetIntrinsic(float* M){
00158     m_intrinsic = mat4(M);
00159 
00160     Activate();
00161 }
00162 
00163 void tgCamera::SetIntrinsic(    float fovy, unsigned width, unsigned height,
00164                                 float zNear, float zFar,
00165                                 unsigned short projection)
00166 {
00167     m_fovy = fovy;
00168     m_width = width;
00169     m_height = height;
00170     m_zNear = zNear;
00171     m_zFar = zFar;
00172     m_projection = projection;
00173 
00174     float m[16];
00175     glMatrixMode(GL_PROJECTION);
00176     glLoadIdentity();
00177 
00178     if(m_projection == GL_ORTHO){
00179         glOrtho(0, m_width, 0, m_height, m_zNear, m_zFar);
00180     }
00181     else if(m_projection == GL_PERSPECTIVE){
00182         gluPerspective( m_fovy, float(m_width)/float(m_height), m_zNear, m_zFar);
00183     }
00184     glGetFloatv(GL_PROJECTION_MATRIX, m);
00185     m_intrinsic = mat4(m);
00186 
00187     Activate();
00188 }
00189 
00190 void tgCamera::SetViewport(unsigned w, unsigned h){
00191     m_width = w;
00192     m_height = h;
00193 }
00194 
00195 void tgCamera::SetZRange(float _near, float _far){
00196     m_zNear = _near;
00197     m_zFar = _far;
00198 }
00199 
00200 vec2 tgCamera::ToImageSpace(const vec3 &world_space){
00201     vec2 ret;
00202     vec4 tmp = m_intrinsic * m_extrinsic * vec4(world_space.x,world_space.y,world_space.z,1.0f);
00203 
00204     tmp.x = tmp.x / tmp.w;
00205     tmp.y = tmp.y / tmp.w;
00206 
00207     ret.x = (tmp.x + 1.0f) * 0.5f * m_width;
00208     ret.y = (tmp.y + 1.0f) * 0.5f * m_height;
00209 
00210     return ret;
00211 }
00212 
00213 void tgCamera::Activate(){
00214     // Apply intrinsic parameters
00215     glMatrixMode(GL_PROJECTION);
00216     glLoadMatrixf(m_intrinsic);
00217 
00218     // Apply extrinsic parameters
00219     glMatrixMode(GL_MODELVIEW);
00220     glLoadMatrixf(m_extrinsic);
00221 
00222     glViewport(0,0,m_width,m_height);
00223     glDepthRange(m_zNear,m_zFar);
00224 
00225     // Extract frustum planes
00226     m_frustum.ExtractFrustum();
00227 }
00228 
00229 void tgCamera::Print(){
00230     //  float m[16];
00231     //  float p[16];
00232     //
00233     //  glGetFloatv(GL_MODELVIEW_MATRIX, m);
00234     //  glGetFloatv(GL_PROJECTION_MATRIX, p);
00235 
00236     mat4 m = m_extrinsic;
00237     mat4 p = m_intrinsic;
00238 
00239     printf("Modelview matrix:\n");
00240     printf("%f %f %f %f\n", m[0], m[4], m[8],  m[12]);
00241     printf("%f %f %f %f\n", m[1], m[5], m[9],  m[13]);
00242     printf("%f %f %f %f\n", m[2], m[6], m[10], m[14]);
00243     printf("%f %f %f %f\n", m[3], m[7], m[11], m[15]);
00244     printf("Projection matrix:\n");
00245     printf("%f %f %f %f\n", p[0], p[4], p[8],  p[12]);
00246     printf("%f %f %f %f\n", p[1], p[5], p[9],  p[13]);
00247     printf("%f %f %f %f\n", p[2], p[6], p[10], p[14]);
00248     printf("%f %f %f %f\n", p[3], p[7], p[11], p[15]);
00249 }
00250 
00251 void tgCamera::pvu2fsu(){
00252     f = m_vView - m_vPos; f.normalize();
00253     s = f.cross(m_vUp); s.normalize();
00254     u = s.cross(f); u.normalize();
00255 }
00256 
00257 void tgCamera::fsu2pvu(){
00258     m_vView = m_vPos + f;
00259     m_vUp = u;
00260 }
00261 
00262 void tgCamera::fsu2extrinsic(){
00263     float fR[16] = {    s.x,  u.x, -f.x,  0.0,
00264                         s.y,  u.y, -f.y,  0.0,
00265                         s.z,  u.z, -f.z,  0.0,
00266                         0.0,    0.0,    0.0,  1.0};
00267 
00268     float ft[16] = {    1.0,  0.0, 0.0, 0.0,
00269                         0.0,  1.0, 0.0, 0.0,
00270                         0.0,  0.0, 1.0, 0.0,
00271                         -m_vPos.x,      -m_vPos.y, -m_vPos.z, 1.0};
00272     mat4 R(fR);
00273     mat4 t(ft);
00274 
00275     m_extrinsic = R * t;
00276 }
00277 
00278 
00279 void tgCamera::extrinsic2fsu(){
00280     s.x=m_extrinsic[0]; u.x=m_extrinsic[1]; f.x=-m_extrinsic[2];
00281     s.y=m_extrinsic[4]; u.y=m_extrinsic[5]; f.y=-m_extrinsic[6];
00282     s.z=m_extrinsic[8]; u.z=m_extrinsic[9]; f.z=-m_extrinsic[10];
00283 
00284     float fR[16] = {    s.x,  u.x, -f.x,  0.0,
00285                         s.y,  u.y, -f.y,  0.0,
00286                         s.z,  u.z, -f.z,  0.0,
00287                         0.0,    0.0,    0.0,  1.0};
00288     mat4 R(fR);
00289     mat4 t;
00290 
00291     t = R.inverse() * m_extrinsic;
00292 
00293     m_vPos.x=-t[12]; m_vPos.x=-t[13]; m_vPos.x=-t[14];
00294 }
00295 
00296 void tgCamera::fwh2intrinsic(){
00297     float m[16];
00298     glMatrixMode(GL_PROJECTION);
00299     glLoadIdentity();
00300 
00301     if(m_projection == GL_ORTHO){
00302         glOrtho(0, m_width, 0, m_height, m_zNear, m_zFar);
00303     }
00304     else if(m_projection == GL_PERSPECTIVE){
00305         gluPerspective( m_fovy, float(m_width)/float(m_height), m_zNear, m_zFar);
00306     }
00307     glGetFloatv(GL_PROJECTION_MATRIX, m);
00308     m_intrinsic = mat4(m);
00309 }
00310 
00311 tgPose tgCamera::GetPose(){
00312     printf("[tgCamera::GetPose()] Not implemented yet\n");
00313     return tgPose();
00314 }
00315 //****************************************************************************
00316 // Translations
00317 void tgCamera::Translate(tgVector3 v){
00318     m_vPos = m_vPos + v;
00319     m_vView = m_vPos + f;
00320 }
00321 
00322 void tgCamera::Translate(float x, float y, float z, float fWay){
00323     tgVector3 v = tgVector3(x,y,z);
00324     v.normalize();
00325     m_vPos = m_vPos + v * fWay;
00326     m_vView = m_vPos + f;
00327 }
00328 
00329 void tgCamera::TranslateF(float fWay){
00330     m_vPos = m_vPos + f * fWay;
00331     m_vView = m_vPos + f;
00332 }
00333 
00334 void tgCamera::TranslateS(float fWay){
00335     m_vPos = m_vPos + s * fWay;
00336     m_vView = m_vPos + f;
00337 }
00338 
00339 void tgCamera::TranslateU(float fWay){
00340     m_vPos = m_vPos + u * fWay;
00341     m_vView = m_vPos + f;
00342 }
00343 
00344 //****************************************************************************
00345 // Rotations
00346 void tgCamera::Rotate(float x, float y, float z, float fAngle){
00347     tgVector3 v = tgVector3(x,y,z);
00348     f.rotate(fAngle, v);
00349     s.rotate(fAngle, v);
00350     u.rotate(fAngle, v);
00351     fsu2pvu();
00352 }
00353 
00354 void tgCamera::RotateF(float fAngle){
00355     s.rotate(fAngle, f);
00356     u = s.cross(f); u.normalize();
00357     fsu2pvu();
00358 }
00359 
00360 void tgCamera::RotateS(float fAngle){
00361     f.rotate(fAngle, s);
00362     u = s.cross(f); u.normalize();
00363     fsu2pvu();
00364 }
00365 
00366 void tgCamera::RotateU(float fAngle){
00367     f.rotate(fAngle, u);
00368     s = f.cross(u); s.normalize();
00369     fsu2pvu();
00370 }
00371 
00372 void tgCamera::RotateX(float fAngle){
00373     printf("tgCamera.RotateX not implemented! \n");
00374 }
00375 
00376 void tgCamera::RotateY(float fAngle){
00377     tgVector3 y = tgVector3(0.0f,1.0f,0.0f);
00378     f.rotate(fAngle, y);
00379     s = f.cross(y); s.normalize();
00380     u = s.cross(f); u.normalize();
00381     fsu2pvu();
00382 }
00383 
00384 void tgCamera::RotateZ(float fAngle){
00385     printf("tgCamera.RotateZ not implemented! \n");
00386 }
00387 
00388 void tgCamera::Orbit(tgVector3 vPoint, tgVector3 vAxis, float fAngle){
00389     tgVector3 d = m_vPos - vPoint;
00390 
00391     d.rotate(fAngle, vAxis);
00392     m_vPos = vPoint + d;
00393 
00394     f.rotate(fAngle, vAxis);
00395     s.rotate(fAngle, vAxis);
00396     u.rotate(fAngle, vAxis);
00397 }
00398 
00399 //****************************************************************************
00400 // Movement
00401 void tgCamera::ApplyTransform(){
00402     fsu2extrinsic();
00403 }
00404 
00405 
00406 


blort
Author(s): Thomas Mörwald , Michael Zillich , Andreas Richtsfeld , Johann Prankl , Markus Vincze , Bence Magyar
autogenerated on Wed Aug 26 2015 15:24:12