imu_state.h
Go to the documentation of this file.
00001 /*********************************************************************
00002  *
00003  * Software License Agreement (BSD License)
00004  *
00005  *  Copyright (c) 2011, Willow Garage, Inc.
00006  *  All rights reserved.
00007  *
00008  *  Redistribution and use in source and binary forms, with or without
00009  *  modification, are permitted provided that the following conditions
00010  *  are met:
00011  *
00012  *   * Redistributions of source code must retain the above copyright
00013  *     notice, this list of conditions and the following disclaimer.
00014  *   * Redistributions in binary form must reproduce the above
00015  *     copyright notice, this list of conditions and the following
00016  *     disclaimer in the documentation and/or other materials provided
00017  *     with the distribution.
00018  *   * Neither the name of Willow Garage, Inc. nor the names of its
00019  *     contributors may be used to endorse or promote products derived
00020  *     from this software without specific prior written permission.
00021  *
00022  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
00023  *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00024  *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
00025  *  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
00026  *  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
00027  *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
00028  *  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
00029  *  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
00030  *  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00031  *  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
00032  *  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00033  *  POSSIBILITY OF SUCH DAMAGE.
00034  *
00035  * Author: Sebastian Klose
00036  *********************************************************************/
00037 
00038 #ifndef IMU_FILTER_IMU_STATE_H_
00039 #define IMU_FILTER_IMU_STATE_H_
00040 
00041 #include <iostream>
00042 
00043 #include <Eigen/Core>
00044 #include <Eigen/Geometry>
00045 
00046 #include <imu_filter/quaternion_helper.h>
00047 #include <imu_filter/utils.h>
00048 
00049 #define EARTH_GRAVITY   ( 9.80665 )
00050 //#define       EARTH_GRAVITY   ( 9.79944 ) // menlo park
00051 
00052 namespace imu_filter
00053 {
00054         //* Class modelling the state of the IMU in the filter
00058         class ImuState
00059         {
00060                 public:
00061                         static const size_t Dimension = 19;     
00062                         typedef Eigen::Matrix<double, Dimension, 1> StateVector;
00063                         typedef Eigen::Matrix<double, Dimension, Dimension> CovarianceMatrix;
00065                         ImuState() : 
00066                                 orientation_( Eigen::Quaterniond::Identity() ), 
00067                                 position_( Eigen::Vector3d::Zero() ), 
00068                                 velocity_( Eigen::Vector3d::Zero() ), 
00069                                 gyroBias_( Eigen::Vector3d::Zero() ), 
00070                                 accBias_( Eigen::Vector3d::Zero() ),
00071                                 gravity_( 0, 0, -EARTH_GRAVITY ),
00072                                 covariance_( CovarianceMatrix::Zero() ),
00073                                 gyroBiasRange_( Eigen::Vector3d( 0.01, 0.01, 0.01 ) ),
00074                                 accBiasRange_( Eigen::Vector3d( 0.3, 0.3, 0.3 ) ),
00075                                 body2ImuR_( Eigen::Quaterniond::Identity() ),
00076                                 body2ImuT_( Eigen::Vector3d::Zero() ),
00077                                 estimate_gravity_( true ),
00078                                 estimate_gyro_bias_( true ),
00079                                 estimate_acc_bias_( true ),
00080                                 world2ImuPose_( Eigen::Affine3d::Identity() )
00081                         {
00082                         }
00083 
00084                         ImuState( const ImuState & other ) : 
00085                                 orientation_( other.orientation_ ), 
00086                                 position_( other.position_ ), 
00087                                 velocity_( other.velocity_ ), 
00088                                 gyroBias_( other.gyroBias_ ), 
00089                                 accBias_( other.accBias_ ),
00090                                 gravity_( other.gravity_ ),
00091                                 covariance_( other.covariance_ ),
00092                                 gyroBiasRange_( other.gyroBiasRange_ ),
00093                                 accBiasRange_( other.accBiasRange_ ),
00094                                 body2ImuR_( other.body2ImuR_ ),
00095                                 body2ImuT_( other.body2ImuT_ )
00096                         {
00097                         }
00098 
00099                         ImuState & operator=( const ImuState & other )
00100                         {
00101                                 orientation_    = other.orientation_;
00102                                 position_               = other.position_;
00103                                 velocity_               = other.velocity_;
00104                                 gyroBias_               = other.gyroBias_;
00105                                 accBias_                = other.accBias_;
00106                                 gravity_                = other.gravity_;
00107                                 covariance_             = other.covariance_;
00108                                 gyroBiasRange_  = other.gyroBiasRange_;
00109                                 accBiasRange_   = other.accBiasRange_;
00110                                 body2ImuR_              = other.body2ImuR_;
00111                                 body2ImuT_              = other.body2ImuT_;
00112                                 return *this;
00113                         }
00114 
00119                         void update( const StateVector & updateVector )
00120                         {
00121                                 orientation_.x() += updateVector[ 0 ];
00122                                 orientation_.y() += updateVector[ 1 ];
00123                                 orientation_.z() += updateVector[ 2 ];
00124                                 orientation_.w() += updateVector[ 3 ];
00125 
00126                                 orientation_.normalize();
00127 
00128                                 position_ += updateVector.block<3, 1>( 4, 0 );
00129                                 velocity_ += updateVector.block<3, 1>( 7, 0 );
00130 
00131                                 if( estimate_gyro_bias_ )
00132                                         gyroBias_ += updateVector.block<3, 1>( 10, 0 );
00133 
00134                                 if( estimate_acc_bias_ )
00135                                         accBias_  += updateVector.block<3, 1>( 13, 0 );
00136 
00137                                 if( estimate_gravity_ )
00138                                         gravity_  += updateVector.block<3, 1>( 16, 0 );
00139 
00140                                 // clamp the biases
00141                                 gyroBias_[ 0 ] = utils::clamp( gyroBias_[ 0 ], -gyroBiasRange_[ 0 ], gyroBiasRange_[ 0 ] );
00142                                 gyroBias_[ 1 ] = utils::clamp( gyroBias_[ 1 ], -gyroBiasRange_[ 1 ], gyroBiasRange_[ 1 ] );
00143                                 gyroBias_[ 2 ] = utils::clamp( gyroBias_[ 2 ], -gyroBiasRange_[ 2 ], gyroBiasRange_[ 2 ] );
00144 
00145                                 accBias_[ 0 ] = utils::clamp( accBias_[ 0 ], -accBiasRange_[ 0 ], accBiasRange_[ 0 ] );
00146                                 accBias_[ 1 ] = utils::clamp( accBias_[ 1 ], -accBiasRange_[ 1 ], accBiasRange_[ 1 ] );
00147                                 accBias_[ 2 ] = utils::clamp( accBias_[ 2 ], -accBiasRange_[ 2 ], accBiasRange_[ 2 ] );
00148                         }
00149 
00154                         void setParameter( const StateVector & vector )
00155                         {
00156                                 orientation_.x() = vector[  0 ];
00157                                 orientation_.y() = vector[  1 ];
00158                                 orientation_.z() = vector[  2 ];
00159                                 orientation_.w() = vector[  3 ];
00160                                 position_[ 0 ]   = vector[  4 ];
00161                                 position_[ 1 ]   = vector[  5 ];
00162                                 position_[ 2 ]   = vector[  6 ];
00163                                 velocity_[ 0 ]   = vector[  7 ];
00164                                 velocity_[ 1 ]   = vector[  8 ];
00165                                 velocity_[ 2 ]   = vector[  9 ];
00166                                 gyroBias_[ 0 ]   = vector[ 10 ];
00167                                 gyroBias_[ 1 ]   = vector[ 11 ];
00168                                 gyroBias_[ 2 ]   = vector[ 12 ];
00169                                 accBias_[ 0 ]    = vector[ 13 ];
00170                                 accBias_[ 1 ]    = vector[ 14 ];
00171                                 accBias_[ 2 ]    = vector[ 15 ];
00172                                 gravity_[ 0 ]    = vector[ 16 ];
00173                                 gravity_[ 1 ]    = vector[ 17 ];
00174                                 gravity_[ 2 ]    = vector[ 18 ];
00175                         }
00176 
00180                         const Eigen::Quaterniond & orientation() const { return orientation_; }
00181 
00185                         Eigen::Quaterniond & orientation() { return orientation_; }
00186 
00190                         void setOrientation( const Eigen::Quaterniond & newOrientation ) 
00191                         { 
00192                                 orientation_ = newOrientation; 
00193                         }
00194 
00198                         const Eigen::Vector3d & position() const { return position_; }
00199 
00203                         Eigen::Vector3d & position() { return position_; }
00204 
00208                         void setPosition( const Eigen::Vector3d & newPosition ) { position_ = newPosition; }
00209 
00213                         const Eigen::Vector3d & velocity() const { return velocity_; }
00214                         
00218                         Eigen::Vector3d & velocity() { return velocity_; }
00219                         
00223                         void setVelocity( const Eigen::Vector3d & newVelocity ) { velocity_ = newVelocity; }
00224 
00228                         const Eigen::Vector3d & gyroBias() const { return gyroBias_; }
00229 
00233                         Eigen::Vector3d & gyroBias() { return gyroBias_; }
00234                         
00238                         void setGyroBias( const Eigen::Vector3d & newGyroBias ) { gyroBias_ = newGyroBias; }
00239 
00243                         const Eigen::Vector3d & accBias() const { return accBias_; }
00244                         
00248                         Eigen::Vector3d & accBias() { return accBias_; }
00249 
00253                         void setAccBias( const Eigen::Vector3d & newAccBias ) { accBias_ = newAccBias; }
00254 
00258                         const Eigen::Vector3d & gravity() const { return gravity_; }
00259 
00263                         Eigen::Vector3d & gravity() { return gravity_; }
00264 
00268                         void setGravity( const Eigen::Vector3d & newGravity ) { gravity_ = newGravity; }
00269 
00273                         const CovarianceMatrix & covariance() const { return covariance_; } 
00274                         
00278                         CovarianceMatrix & covariance() { return covariance_; }
00279 
00283                         const Eigen::Quaterniond & body2ImuRotation() const { return body2ImuR_; }
00284                         
00288                         void setBody2ImuRotation( const Eigen::Quaterniond & rot ) { body2ImuR_ = rot; }
00289 
00293                         const Eigen::Vector3d & body2ImuTranslation() const { return body2ImuT_; }
00294                         
00298                         void setBody2ImuTranslation( const Eigen::Vector3d & trans ) { body2ImuT_ = trans; }
00299 
00303                         void setEstimateGravity( bool v ) { estimate_gravity_ = v; }
00304                         
00308                         void setEstimateGyroBias( bool v ) { estimate_gyro_bias_ = v; }
00309                         
00313                         void setEstimateAccBias( bool v ) { estimate_acc_bias_ = v; }
00314                         
00320                         void setGyroBiasRange( double rx, double ry, double rz )
00321                         {
00322                                 gyroBiasRange_[ 0 ] = rx;
00323                                 gyroBiasRange_[ 1 ] = ry;
00324                                 gyroBiasRange_[ 2 ] = rz;
00325                         }
00326 
00332                         void setAccBiasRange( double rx, double ry, double rz )
00333                         {
00334                                 accBiasRange_[ 0 ] = rx;
00335                                 accBiasRange_[ 1 ] = ry;
00336                                 accBiasRange_[ 2 ] = rz;
00337                         }
00338                         
00343                         void toVector( StateVector & vec ) const
00344                         {
00345                                 vec[ 0 ] = orientation_.x();
00346                                 vec[ 1 ] = orientation_.y();
00347                                 vec[ 2 ] = orientation_.z();
00348                                 vec[ 3 ] = orientation_.w();
00349 
00350                                 vec[ 4 ] = position_.x();
00351                                 vec[ 5 ] = position_.y();
00352                                 vec[ 6 ] = position_.z();
00353 
00354                                 vec[ 7 ] = velocity_.x();
00355                                 vec[ 8 ] = velocity_.y();
00356                                 vec[ 9 ] = velocity_.z();
00357 
00358                                 vec[ 10 ] = gyroBias_.x();
00359                                 vec[ 11 ] = gyroBias_.y();
00360                                 vec[ 12 ] = gyroBias_.z();
00361 
00362                                 vec[ 13 ] = accBias_.x();
00363                                 vec[ 14 ] = accBias_.y();
00364                                 vec[ 15 ] = accBias_.z();
00365 
00366                                 vec[ 16 ] = gravity_.x();
00367                                 vec[ 17 ] = gravity_.y();
00368                                 vec[ 18 ] = gravity_.z();
00369                         }
00370 
00374                         void fixCovariance()
00375                         {
00376                                 // gyroBias
00377                                 if( !estimate_gyro_bias_ ){
00378                                         covariance_.block<3, 3>( 10, 10 ).setZero();
00379                                 }
00380 
00381                                 // accBias
00382                                 if( !estimate_acc_bias_ ){
00383                                         covariance_.block<3, 3>( 13, 13 ).setZero();
00384                                 }
00385 
00386                                 // gravity
00387                                 if( !estimate_gravity_ ){
00388                                         covariance_.block<3, 3>( 16, 16 ).setZero();
00389                                 }
00390                         }
00391 
00395                         const Eigen::Affine3d & world2Imu() 
00396                         {
00397                                 world2ImuPose_.linear() = orientation_.toRotationMatrix();
00398                                 world2ImuPose_.translation() = position_;
00399                                 return world2ImuPose_;
00400                         }
00401 
00402                 private:
00403                         // orientation relative to base frame
00404                         Eigen::Quaterniond      orientation_;
00405 
00406                         // position relative to base frame
00407                         Eigen::Vector3d         position_;
00408 
00409                         // velocity relative to base frame
00410                         Eigen::Vector3d         velocity_;
00411 
00412                         // bias in accelerometer measurements 
00413                         Eigen::Vector3d         gyroBias_;
00414 
00415                         // bias in accelerometer measurements 
00416                         Eigen::Vector3d         accBias_;
00417 
00418                         // gravity vector 
00419                         Eigen::Vector3d         gravity_;
00420 
00421                         // the state covariance matrix
00422                         CovarianceMatrix        covariance_;
00423 
00424                         // ranges for the biases
00425                         Eigen::Vector3d         gyroBiasRange_;
00426                         Eigen::Vector3d         accBiasRange_;
00427 
00428                         // calibration data
00429                         Eigen::Quaterniond      body2ImuR_;
00430                         Eigen::Vector3d         body2ImuT_;
00431 
00432                         bool estimate_gravity_;
00433                         bool estimate_gyro_bias_;
00434                         bool estimate_acc_bias_;
00435 
00436                         Eigen::Affine3d         world2ImuPose_;
00437         };
00438 
00439         inline std::ostream & operator<<( std::ostream & os, const ImuState & state )
00440         {
00441                 os << "ImuState:\n"
00442                         << "\torientation: [" 
00443                         << state.orientation().w() << ", " 
00444                         << state.orientation().x() << ", " 
00445                         << state.orientation().y() << ", " 
00446                         << state.orientation().z() << " ]\n" 
00447                         << "\tposition: [" 
00448                         << state.position().x() << ", " 
00449                         << state.position().y() << ", " 
00450                         << state.position().z() << " ]\n" 
00451                         << "\tvelocity: [" 
00452                         << state.velocity().x() << ", " 
00453                         << state.velocity().y() << ", " 
00454                         << state.velocity().z() << " ]\n" 
00455                         << "\tgyroBias: [" 
00456                         << state.gyroBias().x() << ", " 
00457                         << state.gyroBias().y() << ", " 
00458                         << state.gyroBias().z() << " ]\n" 
00459                         << "\taccBias: [" 
00460                         << state.accBias().x() << ", " 
00461                         << state.accBias().y() << ", " 
00462                         << state.accBias().z() << " ]\n" 
00463                         << "\tgravity: [" 
00464                         << state.gravity().x() << ", " 
00465                         << state.gravity().y() << ", " 
00466                         << state.gravity().z() << " ] (Norm: " << state.gravity().norm() << " )\n" << std::endl;
00467                 return os;      
00468         }
00469 
00470 }
00471 #endif


imu_filter
Author(s): Sebastian Klose
autogenerated on Thu Dec 12 2013 11:24:42