00001 #ifndef OPENTISSUE_UTILITY_GL_GL_DRAW_JOINT_LIMITS_H
00002 #define OPENTISSUE_UTILITY_GL_GL_DRAW_JOINT_LIMITS_H
00003
00004
00005
00006
00007
00008
00009
00010 #include <OpenTissue/configuration.h>
00011
00012 #include <OpenTissue/utility/gl/gl_util.h>
00013 #include <OpenTissue/kinematics/skeleton/skeleton_bone_access.h>
00014
00015 namespace OpenTissue
00016 {
00017 namespace gl
00018 {
00019
00025 template<typename bone_type>
00026 inline void DrawJointLimits(bone_type const & bone)
00027 {
00028 using std::cos;
00029 using std::sin;
00030
00031 typedef typename bone_type::bone_traits bone_traits;
00032 typedef typename bone_type::math_types math_types;
00033 typedef typename math_types::value_traits value_traits;
00034 typedef typename math_types::real_type real_type;
00035 typedef typename math_types::vector3_type vector3_type;
00036 typedef typename math_types::quaternion_type quaternion_type;
00037
00038 float const r = length( bone.relative().T() )* 0.4f ;
00039
00040 glPushMatrix();
00041
00042
00043 if(!bone.is_root())
00044 {
00045 Transform( bone.parent()->absolute() );
00046 }
00047
00048 if(bone.type() == bone_traits::ball_type)
00049 {
00050
00051 size_t const N = 10;
00052
00053 std::vector<real_type> x;
00054 std::vector<real_type> y;
00055 std::vector<real_type> z;
00056 std::vector<real_type> nx;
00057 std::vector<real_type> ny;
00058 std::vector<real_type> nz;
00059 x.resize(N*N);
00060 y.resize(N*N);
00061 z.resize(N*N);
00062 nx.resize(N*N);
00063 ny.resize(N*N);
00064 nz.resize(N*N);
00065 bone_type const * child = OpenTissue::skeleton::BoneAccess::get_first_child_ptr( &bone );
00066 vector3_type const T_child = child ? child->bind_pose().T() : vector3_type(value_traits::zero(), value_traits::zero(), value_traits::zero() );
00067
00068
00069 real_type const & phi_min = bone.min_joint_limit(0);
00070 real_type const & psi_min = bone.min_joint_limit(1);
00071 real_type const & theta_min = bone.min_joint_limit(2);
00072
00073 real_type const & phi_max = bone.max_joint_limit(0);
00074 real_type const & psi_max = bone.max_joint_limit(1);
00075 real_type const & theta_max = bone.max_joint_limit(2);
00076
00077
00078
00079
00080 quaternion_type orientation;
00081
00082 real_type const delta_phi = (phi_max - phi_min)/(N -1u);
00083 real_type const delta_psi = (psi_max - psi_min)/(N -1u);
00084 real_type const delta_theta = (theta_max - theta_min)/(N -1u);
00085
00086 glPushMatrix();
00087 Transform( bone.relative().T() );
00088
00089 ColorPicker(0.5,1.0,0.5);
00090
00091 if( phi_min < phi_max && psi_min < psi_max)
00092 {
00093
00094
00095 real_type theta = theta_min;
00096 for(size_t k=0;k<N;++k)
00097 {
00098
00099 real_type phi = phi_min;
00100 for(size_t j=0;j<N;++j)
00101 {
00102 real_type psi = psi_min;
00103 for(size_t i=0;i<N;++i)
00104 {
00105 orientation = OpenTissue::math::Rz( phi ) * OpenTissue::math::Ry( psi )* OpenTissue::math::Rz( theta );
00106 vector3_type p = orientation.rotate( T_child );
00107
00108
00109 vector3_type n = unit( p );
00110
00111 nx[k] = n(0);
00112 ny[k] = n(1);
00113 nz[k] = n(2);
00114
00115 x[k] = p(0);
00116 y[k] = p(1);
00117 z[k] = p(2);
00118 ++k;
00119 psi += delta_psi;
00120 }
00121 phi += delta_phi;
00122 }
00123 theta += delta_theta;
00124 }
00125 }
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154 glBegin(GL_QUADS);
00155 for(size_t j=0;j<(N-1u);++j)
00156 {
00157 for(size_t i=0;i<(N-1u);++i)
00158 {
00159 size_t i0 = j*N + i;
00160 size_t i1 = i0 + 1u;
00161 size_t i2 = i1 + N;
00162 size_t i3 = i2 - 1u;
00163
00164
00165 glVertex3f( x[i0], y[i0], z[i0] );
00166 glNormal3f( nx[i0], ny[i0], nz[i0] );
00167
00168
00169 glVertex3f( x[i1],y[i1],z[i1]);
00170 glNormal3f(nx[i1],ny[i1],nz[i1]);
00171
00172
00173 glVertex3f( x[i2],y[i2],z[i2]);
00174 glNormal3f(nx[i2],ny[i2],nz[i2]);
00175
00176
00177 glVertex3f( x[i3],y[i3],z[i3]);
00178 glNormal3f(nx[i3],ny[i3],nz[i3]);
00179
00180 }
00181
00182 }
00183 glEnd();
00184
00185 glPopMatrix();
00186 }
00187
00188
00189 else if(bone.type() == bone_traits::hinge_type)
00190 {
00191 real_type const & theta_min = bone.min_joint_limit(0);
00192 real_type const & theta_max = bone.max_joint_limit(0);
00193
00194 size_t const N = 10;
00195
00196 float x[N];
00197 float y[N];
00198 float z[N];
00199
00200 real_type delta_theta = (theta_max - theta_min)/(N -1u);
00201
00202 bone_type * child = OpenTissue::skeleton::BoneAccess::get_first_child_ptr( &bone );
00203 vector3_type T = vector3_type(value_traits::zero(), value_traits::zero(), value_traits::zero() );
00204 if(child)
00205 T = unit( child->bind_pose().T() );
00206
00207 real_type theta = theta_min;
00208 for(size_t i=0;i<N;++i)
00209 {
00210 vector3_type p = OpenTissue::math::Ru( theta, bone.u() )*T;
00211
00212 x[i] = r*p(0);
00213 y[i] = r*p(1);
00214 z[i] = r*p(2);
00215
00216 theta += delta_theta;
00217 }
00218
00219 glPushMatrix();
00220 Transform( bone.relative().T() );
00221
00222 ColorPicker(1.0,0.0,0.0);
00223 DrawVector(vector3_type( 0, 0, 0 ), bone.u() , 0.5 , false);
00224 ColorPicker(0.0,0.0,1.0);
00225
00226 vector3_type max_limit ;
00227 vector3_type min_limit ;
00228 vector3_type starting = vector3_type(0,1,0);
00229
00230
00231 vector3_type w = cross( bone.u() , cross(bone.u() ,starting));
00232 w = dot(w,starting)*w;
00233 max_limit = unit( starting * cos(bone.max_joint_limit(0)) + cross(bone.u() ,starting)* sin(bone.max_joint_limit(0)) + w * (1 - cos(bone.max_joint_limit(0))));
00234
00235 min_limit = unit(starting * cos(bone.min_joint_limit(0)) + cross(bone.u() ,starting)* sin(bone.min_joint_limit(0)) + w * (1 - cos(bone.min_joint_limit(0))));
00236
00237 vector3_type norman = - unit(max_limit + min_limit);
00238
00239
00240
00241 glBegin(GL_TRIANGLES);
00242
00243
00244 for(size_t i=0;i<(N-1u);++i)
00245 {
00246 glVertex3f( x[i], y[i], z[i] );
00247 glNormal3f( bone.u()(0), bone.u()(1), bone.u()(2) );
00248
00249 size_t i1 = i + 1u;
00250 glVertex3f( x[i1], y[i1], z[i1] );
00251 glNormal3f( bone.u()(0), bone.u()(1), bone.u()(2) );
00252
00253 glVertex3f( 0.0f, 0.0f, 0.0f );
00254 glNormal3f( bone.u()(0), bone.u()(1), bone.u()(2) );
00255 }
00256 glEnd();
00257 glPopMatrix();
00258 }
00259 else if(bone.type() == bone_traits::slider_type)
00260 {
00261 real_type const & theta_min = bone.min_joint_limit(0);
00262 real_type const & theta_max = bone.max_joint_limit(0);
00263 DrawVector( bone.u()*theta_min, bone.u()*(theta_max-theta_min) );
00264 }
00265 else
00266 {
00267 assert( false || !"DrawJointLimits(): Unrecognized joint type");
00268 }
00269
00270 glPopMatrix();
00271 }
00272
00273
00274 }
00275
00276 }
00277
00278
00279 #endif