Tekkotsu Homepage
Demos
Overview
Downloads
Dev. Resources
Reference
Credits

CreateMotionModel.cc

Go to the documentation of this file.
00001 #include "Shared/RobotInfo.h"
00002 
00003 #if defined(TGT_IS_CREATE) || defined(TGT_IS_CREATE2)
00004 
00005 #include "CreateMotionModel.h"
00006 
00007 void CreateOdometry::getCreateOdometry(float &dd, AngSignPi &da) {
00008   float dist = state->sensors[EncoderDistanceOffset];
00009   AngTwoPi ang = state->sensors[EncoderAngleOffset]/180.0*(float)M_PI;
00010 
00011   dd = dist - lastdist;
00012   da = float(ang - lastang);
00013   if (fabs(dd) < minUpdateDistance && fabs(da) < minUpdateAngle)
00014     return;
00015 
00016   lastdist = dist;
00017   lastang = ang;
00018 
00019   // *** Visual odometry is presently disabled; need to revisit this
00020   // now that the lastdist/lastang update bug was fixed on 4/3/2013.
00021 
00022   // Apply visual odometry for better rotation estimation.
00023   //
00024   // In Mirage, the simulated Create odometry is nearly perfect,
00025   // while visual odometry overestimates turns.  On the physical robot,
00026   // the Create's poor hardware odometry favors relying on visual
00027   // odometry.  But if visual odometry is failing, revert to the Create.
00028   // 
00029   if (fabs(da) > minUpdateAngle) {  // don't bother if we're not turning
00030     if ( DualCoding::VRmixin::imageOdometry != NULL ) {
00031       AngTwoPi odoAng = DualCoding::VRmixin::imageOdometry->getIntegratedAngle()/180.0*(float)M_PI;
00032       AngSignPi odoDa = AngSignPi(odoAng - lastOdoAng);
00033       lastOdoAng = odoAng;
00034       // std::cout << "old da = " << da << "   odoDa = " << odoDa;
00035       if ( state->sensors[GPSXOffset] == 0.0 )  // no GPS means we're not running in Mirage
00036   if ( da*odoDa > 0 && fabs(odoDa) > fabs(da) ) // ignore odoDa if sign doesn't match da
00037     da = odoDa;
00038     }
00039   }
00040   // std::cout << "   new da = " << da << std::endl;
00041 }
00042 
00043 void CreateOdometry::computeCreateMotion(float len, float omega, float theta, float &dx, float &dy, float &dtheta) { 
00044   // check for linear motion
00045   if ( omega == 0 ) {
00046     dx = len*std::cos(theta);
00047     dy = len*std::sin(theta);
00048     dtheta = 0;
00049   }
00050   // curved motion, if len = 0, just rotation
00051   else {
00052     // solve for radius of circle
00053     // note that we don't need to use abs here
00054     // if len, omega are negative then we want r to be
00055     // negative because we are effectively flipping the circle
00056     float r = len / omega;
00057       
00058     // find new angles
00059     // would be this if theta was position around circle:
00060     //dx = r*cos(theta + omega) - r*cos(theta);
00061     //dy = r*sin(theta + omega) - r*sin(theta);
00062     // but it's actually the tangent to the circle,
00063     // so we shift by -pi/2 giving:
00064     dx = r*std::sin(theta + omega) - r*std::sin(theta);
00065     dy = -r*std::cos(theta + omega) + r*std::cos(theta);
00066     dtheta = omega;
00067   }
00068 }
00069 
00070 #endif

Tekkotsu v5.1CVS
Generated Mon May 9 04:58:37 2016 by Doxygen 1.6.3