CVD 0.8
|
00001 /* 00002 This file is part of the CVD Library. 00003 00004 Copyright (C) 2005 The Authors 00005 00006 This library is free software; you can redistribute it and/or 00007 modify it under the terms of the GNU Lesser General Public 00008 License as published by the Free Software Foundation; either 00009 version 2.1 of the License, or (at your option) any later version. 00010 00011 This library is distributed in the hope that it will be useful, 00012 but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00014 Lesser General Public License for more details. 00015 00016 You should have received a copy of the GNU Lesser General Public 00017 License along with this library; if not, write to the Free Software 00018 Foundation, Inc., 00019 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 00020 */ 00021 #ifndef CVD_GL_HELPERS_H 00022 #define CVD_GL_HELPERS_H 00023 00024 #include <iostream> 00025 #include <map> 00026 #include <utility> 00027 00028 #include <cvd/image_ref.h> 00029 #include <cvd/image.h> 00030 #include <cvd/byte.h> 00031 #include <cvd/rgb.h> 00032 #include <cvd/byte.h> 00033 #include <cvd/rgb8.h> 00034 #include <cvd/rgba.h> 00035 #include <cvd/config.h> 00036 #ifdef WIN32 00037 #include <windows.h> 00038 #endif 00039 00040 #ifdef _OSX 00041 #include <OpenGL/gl.h> 00042 #include <OpenGL/glu.h> 00043 #else 00044 #include <GL/gl.h> 00045 #include <GL/glu.h> 00046 #endif 00047 00048 00049 00050 #include <cvd/internal/gl_types.h> 00051 00052 #ifdef CVD_HAVE_TOON 00053 #include <TooN/TooN.h> 00054 #include <cvd/se3.h> 00055 #include <cvd/so3.h> 00056 #include <cvd/se2.h> 00057 #include <cvd/so2.h> 00058 #endif 00059 00060 namespace CVD 00061 { 00062 00066 inline void glVertex(const ImageRef& i) 00067 { 00068 glVertex2i(i.x, i.y); 00069 } 00070 00074 inline void glTexCoord(const ImageRef& i) 00075 { 00076 glTexCoord2i(i.x, i.y); 00077 } 00078 00079 #ifdef GL_GLEXT_PROTOTYPES 00080 00081 00082 00083 00084 inline void glMultiTexCoord(GLenum unit, const ImageRef& i) 00085 { 00086 glMultiTexCoord2i(unit, i.x, i.y); 00087 } 00088 #endif 00089 00090 00091 00092 inline void glRasterPos(const ImageRef& i) 00093 { 00094 glRasterPos2i(i.x, i.y); 00095 } 00096 00101 inline void glRect( const ImageRef & p, const ImageRef & q) 00102 { 00103 glRecti(p.x, p.y, q.x, q.y); 00104 } 00105 00106 #ifdef CVD_HAVE_TOON 00107 00108 00109 00110 inline void glVertex(const TooN::Vector<2>& v) 00111 { 00112 glVertex2d(v[0], v[1]); 00113 } 00114 00118 inline void glVertex(const TooN::Vector<3>& v) 00119 { 00120 glVertex3d(v[0], v[1], v[2]); 00121 } 00122 00126 inline void glVertex(const TooN::Vector<4>& v) 00127 { 00128 glVertex4d(v[0], v[1], v[2], v[3]); 00129 } 00130 00134 inline void glTexCoord(const TooN::Vector<2>& v) 00135 { 00136 glTexCoord2d(v[0], v[1]); 00137 } 00138 00142 inline void glTexCoord(const TooN::Vector<3>& v) 00143 { 00144 glTexCoord3d(v[0], v[1], v[2]); 00145 } 00146 00150 inline void glTexCoord(const TooN::Vector<4>& v) 00151 { 00152 glTexCoord4d(v[0], v[1], v[2], v[3]); 00153 } 00154 00159 inline void glRect( const TooN::Vector<2> & p, const TooN::Vector<2> & q) 00160 { 00161 glRectd(p[0], p[1], q[0], q[1]); 00162 } 00163 00164 #ifdef GL_GLEXT_PROTOTYPES 00165 00166 00167 00168 00169 inline void glMultiTexCoord(GLenum unit, const TooN::Vector<2>& v) 00170 { 00171 glMultiTexCoord2d(unit, v[0], v[1]); 00172 } 00173 00178 inline void glMultiTexCoord(GLenum unit, const TooN::Vector<3>& v) 00179 { 00180 glMultiTexCoord3d(unit, v[0], v[1], v[2]); 00181 } 00182 00187 inline void glMultiTexCoord(GLenum unit, const TooN::Vector<4>& v) 00188 { 00189 glMultiTexCoord4d(unit, v[0], v[1], v[2], v[3]); 00190 } 00191 #endif 00192 00196 inline void glRasterPos(const TooN::Vector<2>& v) 00197 { 00198 glRasterPos2d(v[0], v[1]); 00199 } 00200 00204 inline void glRasterPos(const TooN::Vector<3>& v) 00205 { 00206 glRasterPos3d(v[0], v[1], v[2]); 00207 } 00208 00212 inline void glRasterPos(const TooN::Vector<4>& v) 00213 { 00214 glRasterPos4d(v[0], v[1], v[2], v[3]); 00215 } 00216 00220 inline void glNormal(const TooN::Vector<3>& n) 00221 { 00222 glNormal3d(n[0], n[1], n[2]); 00223 } 00224 00228 inline void glTranslate( const ImageRef & v ) 00229 { 00230 glTranslatef( static_cast<GLfloat>(v.x), static_cast<GLfloat>(v.y), 0); 00231 } 00232 00236 template <int N> inline void glTranslate( const TooN::Vector<N> & v) 00237 { 00238 glTranslated(v[0], v[1], v[2]); 00239 } 00240 00245 template <> inline void glTranslate( const TooN::Vector<2> & v) 00246 { 00247 glTranslated(v[0], v[1], 0); 00248 } 00249 00254 template <> inline void glTranslate( const TooN::Vector<1> & v) 00255 { 00256 glTranslated(v[0], 0, 0); 00257 } 00258 00264 template <int N, class P, class A> inline void glMultMatrix( const TooN::Matrix<N,N,P,A> & m ) 00265 { 00266 GLdouble glm[16]; 00267 glm[0] = m[0][0]; glm[1] = m[1][0]; glm[2] = m[2][0]; glm[3] = m[3][0]; 00268 glm[4] = m[0][1]; glm[5] = m[1][1]; glm[6] = m[2][1]; glm[7] = m[3][1]; 00269 glm[8] = m[0][2]; glm[9] = m[1][2]; glm[10] = m[2][2]; glm[11] = m[3][2]; 00270 glm[12] = m[0][3]; glm[13] = m[1][3]; glm[14] = m[2][3]; glm[15] = m[3][3]; 00271 glMultMatrixd(glm); 00272 } 00273 00279 template <class P, class A> inline void glMultMatrix( const TooN::Matrix<3,3,P,A> & m ) 00280 { 00281 GLdouble glm[16]; 00282 glm[0] = m[0][0]; glm[1] = m[1][0]; glm[2] = m[2][0]; glm[3] = 0; 00283 glm[4] = m[0][1]; glm[5] = m[1][1]; glm[6] = m[2][1]; glm[7] = 0; 00284 glm[8] = m[0][2]; glm[9] = m[1][2]; glm[10] = m[2][2]; glm[11] = 0; 00285 glm[12] = 0; glm[13] = 0; glm[14] = 0; glm[15] = 1; 00286 glMultMatrixd(glm); 00287 } 00288 00294 template <class P, class A> inline void glMultMatrix( const TooN::Matrix<2,2,P,A> & m ) 00295 { 00296 GLdouble glm[16]; 00297 glm[0] = m[0][0]; glm[1] = m[1][0]; glm[2] = 0; glm[3] = 0; 00298 glm[4] = m[0][1]; glm[5] = m[1][1]; glm[6] = 0; glm[7] = 0; 00299 glm[8] = 0; glm[9] = 0; glm[10] = 1; glm[11] = 0; 00300 glm[12] = 0; glm[13] = 0; glm[14] = 0; glm[15] = 1; 00301 glMultMatrixd(glm); 00302 } 00303 00307 template <typename P> 00308 inline void glMultMatrix( const TooN::SO3<P> & so3 ) 00309 { 00310 glMultMatrix( so3.get_matrix()); 00311 } 00312 00317 template <typename P> 00318 inline void glMultMatrix( const TooN::SE3<P> & se3 ) 00319 { 00320 glTranslate( se3.get_translation()); 00321 glMultMatrix( se3.get_rotation()); 00322 } 00323 00327 template <typename P> 00328 inline void glMultMatrix( const TooN::SO2<P> & so2 ) 00329 { 00330 glMultMatrix( so2.get_matrix()); 00331 } 00332 00337 template <typename P> 00338 inline void glMultMatrix( const TooN::SE2<P> & se2 ) 00339 { 00340 glTranslate( se2.get_translation()); 00341 glMultMatrix( se2.get_rotation()); 00342 } 00343 00351 inline void glOrtho( const CVD::ImageRef & size, const double nearPlane = -1.0, const double farPlane = 1.0) 00352 { 00353 ::glOrtho( -0.375, size.x - 0.375, size.y - 0.375, -0.375, nearPlane, farPlane ); 00354 } 00355 00360 inline void glOrtho( const TooN::Vector<6> & param) 00361 { 00362 ::glOrtho( param[0], param[1], param[2], param[3], param[4], param[5]); 00363 } 00364 00377 template <typename P, typename A> 00378 inline void glFrustum( const TooN::Vector<4,P,A> & params, double width, double height, double nearPlane = 0.1, double farPlane = 100) 00379 { 00380 GLdouble left, right, bottom, top; 00381 left = -nearPlane * params[2] / params[0]; 00382 top = nearPlane * params[3] / params[1]; 00383 right = nearPlane * ( width - params[2] ) / params[0]; 00384 bottom = - nearPlane * ( height - params[3] ) / params[1]; 00385 ::glFrustum( left, right, bottom, top, nearPlane, farPlane ); 00386 } 00387 00396 template <class CAMERA> inline void glFrustum( const CAMERA & camera, double width, double height, double nearPlane = 0.1, double farPlane = 100) 00397 { 00398 glFrustum( camera.get_parameters().template slice<0,4>(), width, height, nearPlane, farPlane); 00399 } 00400 00405 inline void glFrustum( const TooN::Vector<6> & param) 00406 { 00407 ::glFrustum( param[0], param[1], param[2], param[3], param[4], param[5]); 00408 } 00409 00414 inline void glColor(const TooN::Vector<3>& v) 00415 { 00416 glColor3d(v[0], v[1], v[2]); 00417 } 00418 00423 inline void glColor(const TooN::Vector<4>& v) 00424 { 00425 glColor4d(v[0], v[1], v[2], v[3]); 00426 } 00427 00432 inline void glClearColor(const TooN::Vector<4>& v) 00433 { 00434 ::glClearColor((GLclampf)v[0], (GLclampf)v[1], (GLclampf)v[2], (GLclampf)v[3]); 00435 } 00436 00441 inline void glClearColor(const TooN::Vector<3>& v) 00442 { 00443 ::glClearColor((GLclampf)v[0], (GLclampf)v[1], (GLclampf)v[2], 0); 00444 } 00445 00446 00447 00451 inline void glColor(const TooN::Vector<-1> & v) 00452 { 00453 switch(v.size()){ 00454 case 3: glColor3d(v[0], v[1], v[2]); 00455 break; 00456 case 4: glColor4d(v[0], v[1], v[2], v[3]); 00457 break; 00458 } 00459 } 00460 #endif 00461 00465 template <class P1, class P2> inline void glLine(const P1& x1, const P2& x2) { 00466 glBegin(GL_LINES); 00467 glVertex(x1); 00468 glVertex(x2); 00469 glEnd(); 00470 } 00471 00476 template<class C> inline void glVertex( const C & list ) 00477 { 00478 for(typename C::const_iterator v = list.begin(); v != list.end(); ++v) 00479 glVertex(*v); 00480 } 00481 00486 inline void glColor(const CVD::Rgb<byte>& c) 00487 { 00488 glColor3ub(c.red, c.green, c.blue); 00489 } 00490 00495 inline void glColor(const CVD::Rgb<float>& c) 00496 { 00497 glColor3f(c.red, c.green, c.blue); 00498 } 00499 00504 inline void glColor3(const CVD::Rgb8& c) 00505 { 00506 glColor3ub(c.red, c.green, c.blue); 00507 } 00508 00513 inline void glColor4(const CVD::Rgb8& c) 00514 { 00515 glColor4ub(c.red, c.green, c.blue, c.dummy); 00516 } 00517 00522 inline void glColor(const CVD::Rgba<unsigned char>& c) 00523 { 00524 glColor4ub(c.red, c.green, c.blue, c.alpha); 00525 } 00526 00531 inline void glColor(const CVD::Rgba<float>& c) 00532 { 00533 glColor4f(c.red, c.green, c.blue, c.alpha); 00534 } 00535 00536 namespace Internal{ 00537 static inline int alignof(const void* ptr) 00538 { 00539 size_t p = (size_t)ptr; 00540 00541 if(p&3) 00542 if(p&1) 00543 return 1; 00544 else 00545 return 2; 00546 else 00547 if(p&4) 00548 return 4; 00549 else 00550 return 8; 00551 } 00552 } 00553 00558 template<class C> inline void glDrawPixels(const SubImage<C>& i) 00559 { 00560 ::glPixelStorei(GL_UNPACK_ALIGNMENT, std::min(Internal::alignof(i[0]), Internal::alignof(i[1]))); 00561 ::glPixelStorei(GL_UNPACK_ROW_LENGTH, i.row_stride()); 00562 ::glDrawPixels(i.size().x, i.size().y, gl::data<C>::format, gl::data<C>::type, i.data()); 00563 ::glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); 00564 } 00565 00570 template<class C> inline void glReadPixels(BasicImage<C>& i, ImageRef origin=ImageRef(0,0)) 00571 { 00572 ::glReadPixels(origin.x, origin.y, i.size().x, i.size().y, gl::data<C>::format, gl::data<C>::type, i.data()); 00573 } 00574 00579 template<class C> inline Image<C> glReadPixels(ImageRef size, ImageRef origin=ImageRef(0,0)) 00580 { 00581 Image<C> i(size); 00582 ::glReadPixels(origin.x, origin.y, i.size().x, i.size().y, gl::data<C>::format, gl::data<C>::type, i.data()); 00583 return i; 00584 } 00585 00590 template<class C> inline void glTexSubImage2D( const SubImage<C> &i, GLint xoffset = 0, GLint yoffset = 0, GLenum target = GL_TEXTURE_2D, GLint level = 0) 00591 { 00592 ::glPixelStorei(GL_UNPACK_ALIGNMENT, 1); 00593 ::glPixelStorei(GL_UNPACK_ROW_LENGTH, i.row_stride()); 00594 ::glTexSubImage2D(target, level, xoffset, yoffset, i.size().x, i.size().y, gl::data<C>::format, gl::data<C>::type, i.data()); 00595 ::glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); 00596 } 00597 00602 template<class C> inline void glTexImage2D( const SubImage<C> &i, GLint border = 0, GLenum target = GL_TEXTURE_2D, GLint level = 0) 00603 { 00604 ::glPixelStorei(GL_UNPACK_ALIGNMENT, 1); 00605 ::glPixelStorei(GL_UNPACK_ROW_LENGTH, i.row_stride()); 00606 ::glTexImage2D(target, level, gl::data<C>::format, i.size().x, i.size().y, border, gl::data<C>::format, gl::data<C>::type, i.data()); 00607 ::glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); 00608 } 00609 00612 inline void glPrintErrors(void){ 00613 GLenum code; 00614 while((code = glGetError()) != GL_NO_ERROR){ 00615 std::cout << "GL:" << code << ":" << gluGetString(code) << std::endl; 00616 } 00617 } 00618 00622 00625 void glSetFont( const std::string & fontname ); 00626 00628 const std::string & glGetFont(); 00629 00631 enum TEXT_STYLE { 00632 FILL = 0, 00633 OUTLINE = 1, 00634 NICE = 2 00635 }; 00636 00646 std::pair<double, double> glDrawText(const std::string & text, enum TEXT_STYLE style = NICE, double spacing = 1.5, double kerning = 0.1); 00647 00649 std::pair<double, double> glGetExtends(const std::string & text, double spacing = 1.5, double kerning = 0.1); 00650 00652 00653 }; 00654 00655 #endif