Fawkes API
Fawkes Development Version
|
00001 00002 /*************************************************************************** 00003 * texture_drawer.cpp - Skeleton Visualization GUI: texture drawer 00004 * 00005 * Created: Tue Mar 29 17:09:25 2011 (on the way to Magdeburg for GO2011) 00006 * Copyright 2006-2011 Tim Niemueller [www.niemueller.de] 00007 * 00008 ****************************************************************************/ 00009 00010 /* This program is free software; you can redistribute it and/or modify 00011 * it under the terms of the GNU General Public License as published by 00012 * the Free Software Foundation; either version 2 of the License, or 00013 * (at your option) any later version. 00014 * 00015 * This program is distributed in the hope that it will be useful, 00016 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00017 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00018 * GNU Library General Public License for more details. 00019 * 00020 * Read the full text in the LICENSE.GPL file in the doc directory. 00021 */ 00022 00023 #include "texture_drawer.h" 00024 00025 #include <fvcams/camera.h> 00026 #include <fvutils/color/colorspaces.h> 00027 #include <fvutils/color/conversions.h> 00028 00029 #include <cstdlib> 00030 #include <cstdio> 00031 #include <algorithm> 00032 #include <GL/glut.h> 00033 00034 using namespace fawkes; 00035 using namespace firevision; 00036 00037 /** @class SkelGuiTextureDrawer "texture_drawer.h" 00038 * Draw images from camera in texture. 00039 * Uses texture mapping to show an image acquired from a camera in the 00040 * background. 00041 * @author Tim Niemueller 00042 * 00043 * @fn SkelGuiTextureDrawer::fill_texture() 00044 * Fill texture with data. 00045 * This function is called during draw() and the sub-class shall implement it 00046 * to fill the texture with the data to show. Be aware that the texture size 00047 * and the actually shown size will likely differ. 00048 */ 00049 00050 /** Constructor. 00051 * @param width width of visible area 00052 * @param height height of visible area 00053 */ 00054 SkelGuiTextureDrawer::SkelGuiTextureDrawer(unsigned int width, unsigned int height) 00055 : __width(width), __height(height), 00056 __texture_width(get_closest_power_of_two(__width)), 00057 __texture_height(get_closest_power_of_two(__height)) 00058 { 00059 __texture = (unsigned char *)malloc(__texture_width *__texture_height * 3); 00060 memset(__texture, 0, __texture_width * __texture_height * 3); 00061 00062 __texture_initialized = false; 00063 } 00064 00065 /** Destructor. */ 00066 SkelGuiTextureDrawer::~SkelGuiTextureDrawer() 00067 { 00068 free(__texture); 00069 } 00070 00071 unsigned int 00072 SkelGuiTextureDrawer::get_closest_power_of_two(unsigned int n) 00073 { 00074 unsigned int m = 2; 00075 while(m < n) m<<=1; 00076 00077 return m; 00078 } 00079 00080 void 00081 SkelGuiTextureDrawer::init_texture() 00082 { 00083 glGenTextures(1, &__texture_id); 00084 glBindTexture(GL_TEXTURE_2D, __texture_id); 00085 00086 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 00087 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 00088 00089 memset(__texture_coords, 0, sizeof(__texture_coords)); 00090 __texture_coords[0] = (float)__width / __texture_width; 00091 __texture_coords[1] = (float)__height / __texture_height; 00092 __texture_coords[2] = (float)__width / __texture_width; 00093 __texture_coords[7] = (float)__height / __texture_height; 00094 00095 __texture_initialized = true; 00096 } 00097 00098 00099 void 00100 SkelGuiTextureDrawer::draw_rectangle(float topLeftX, float topLeftY, 00101 float bottomRightX, float bottomRightY) 00102 { 00103 GLfloat verts[8] = { topLeftX, topLeftY, topLeftX, bottomRightY, 00104 bottomRightX, bottomRightY, bottomRightX, topLeftY }; 00105 glVertexPointer(2, GL_FLOAT, 0, verts); 00106 glDrawArrays(GL_TRIANGLE_FAN, 0, 4); 00107 glFlush(); 00108 } 00109 00110 /** Draw texture to screen. */ 00111 void 00112 SkelGuiTextureDrawer::draw() 00113 { 00114 if (!__texture_initialized) init_texture(); 00115 00116 fill_texture(); 00117 00118 glBindTexture(GL_TEXTURE_2D, __texture_id); 00119 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, __texture_width, __texture_height, 00120 0, GL_RGB, GL_UNSIGNED_BYTE, __texture); 00121 00122 // Display the OpenGL texture map 00123 glColor4f(0.75,0.75,0.75,1); 00124 00125 glEnable(GL_TEXTURE_2D); 00126 glEnableClientState(GL_TEXTURE_COORD_ARRAY); 00127 glTexCoordPointer(2, GL_FLOAT, 0, __texture_coords); 00128 draw_rectangle(__width, __height, 0, 0); 00129 glDisableClientState(GL_TEXTURE_COORD_ARRAY); 00130 glDisable(GL_TEXTURE_2D); 00131 } 00132 00133 /** Copy an RGB buffer to texture. 00134 * @param rgb_buf the RGB buffer to copy, it must exactly of dimensions __width 00135 * and __height. 00136 */ 00137 void 00138 SkelGuiTextureDrawer::copy_rgb_to_texture(const unsigned char *rgb_buf) 00139 { 00140 unsigned char *row = __texture; 00141 unsigned char *tex = __texture; 00142 const unsigned char *rgb = rgb_buf; 00143 unsigned int bytes = 0; 00144 for (unsigned int h = 0; h < __height; ++h) { 00145 tex = row; 00146 for (unsigned int w = 0; w < __width; ++w) { 00147 *tex++ = *rgb++; 00148 *tex++ = *rgb++; 00149 *tex++ = *rgb++; 00150 ++bytes; 00151 } 00152 row += __texture_width * 3; 00153 } 00154 }