PID.C

Go to the documentation of this file.
00001 /*!@file Controllers/PID.C Encapsulation of PID */
00002 
00003 // //////////////////////////////////////////////////////////////////// //
00004 // The iLab Neuromorphic Vision C++ Toolkit - Copyright (C) 2000-2003   //
00005 // by the University of Southern California (USC) and the iLab at USC.  //
00006 // See http://iLab.usc.edu for information about this project.          //
00007 // //////////////////////////////////////////////////////////////////// //
00008 // Major portions of the iLab Neuromorphic Vision Toolkit are protected //
00009 // under the U.S. patent ``Computation of Intrinsic Perceptual Saliency //
00010 // in Visual Environments, and Applications'' by Christof Koch and      //
00011 // Laurent Itti, California Institute of Technology, 2001 (patent       //
00012 // pending; application number 09/912,225 filed July 23, 2001; see      //
00013 // http://pair.uspto.gov/cgi-bin/final/home.pl for current status).     //
00014 // //////////////////////////////////////////////////////////////////// //
00015 // This file is part of the iLab Neuromorphic Vision C++ Toolkit.       //
00016 //                                                                      //
00017 // The iLab Neuromorphic Vision C++ Toolkit is free software; you can   //
00018 // redistribute it and/or modify it under the terms of the GNU General  //
00019 // Public License as published by the Free Software Foundation; either  //
00020 // version 2 of the License, or (at your option) any later version.     //
00021 //                                                                      //
00022 // The iLab Neuromorphic Vision C++ Toolkit is distributed in the hope  //
00023 // that it will be useful, but WITHOUT ANY WARRANTY; without even the   //
00024 // implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR      //
00025 // PURPOSE.  See the GNU General Public License for more details.       //
00026 //                                                                      //
00027 // You should have received a copy of the GNU General Public License    //
00028 // along with the iLab Neuromorphic Vision C++ Toolkit; if not, write   //
00029 // to the Free Software Foundation, Inc., 59 Temple Place, Suite 330,   //
00030 // Boston, MA 02111-1307 USA.                                           //
00031 // //////////////////////////////////////////////////////////////////// //
00032 //
00033 // Primary maintainer for this file: Laurent Itti <itti@usc.edu>
00034 // $HeadURL: svn://isvn.usc.edu/software/invt/trunk/saliency/src/Controllers/PID.C $
00035 // $Id: PID.C 11533 2009-07-28 04:35:43Z lior $
00036 //
00037 
00038 #include "Controllers/PID.H"
00039 
00040 //hack to adjust for buoyancy
00041 #define BUOYANCY_OFFSET 0
00042 
00043 // ######################################################################
00044 template <class T>
00045 PID<T>::PID(const float pGain, const float iGain,
00046     const float dGain, const T& iMin, const T& iMax,
00047     const T& errThresh,
00048     const T& posThresh, const T& negThresh,
00049     const T& maxMotor, const T& minMotor,
00050     const int noMoveThresh,
00051     const bool runPID,
00052     const float speed,
00053     const T& posStaticErrThresh,
00054     const T& negStaticErrThresh
00055     ) :
00056   itsIstate(0), itsDstate(0),
00057   itsPgain(pGain), itsIgain(iGain), itsDgain(dGain),
00058   itsImin(iMin), itsImax(iMax),
00059   itsErrThresh(errThresh), itsPosStaticErrThresh(posStaticErrThresh),
00060   itsNegStaticErrThresh(negStaticErrThresh),
00061   itsPosThresh(posThresh), itsNegThresh(negThresh),
00062   itsMaxMotor(maxMotor), itsMinMotor(minMotor) ,
00063   itsNoMoveThresh(noMoveThresh),
00064   itsRunPID(runPID),
00065   itsSpeed(speed),
00066   itsNoMoveCount(0)
00067 
00068 { }
00069 
00070 // ######################################################################
00071 template <class T>
00072 PID<T>::~PID()
00073 { }
00074 
00075 // ######################################################################
00076 template <class T>
00077 void PID<T>::setPIDPgain(float p)
00078 {
00079   itsPgain = p;
00080 }
00081 
00082 template <class T>
00083 void PID<T>::setPIDIgain(float i)
00084 {
00085   itsIgain = i;
00086 }
00087 
00088 template <class T>
00089 void PID<T>::setPIDDgain(float d)
00090 {
00091   itsDgain = d;
00092 }
00093 
00094 template <class T>
00095 void PID<T>::setSpeed(float s)
00096 {
00097   itsSpeed = s;
00098 }
00099 
00100 template <class T>
00101 void PID<T>::setPIDOn(bool val)
00102 {
00103   itsRunPID = val;
00104   itsNoMoveCount = 0;
00105 }
00106 
00107 // ######################################################################
00108 template <class T>
00109 T PID<T>::update(const T& target, const T& val)
00110 {
00111   // NOTE: we only use unary operators on T for compatibility with Angle...
00112 
00113   itsVal = val;
00114   itsTarget = target;
00115 
00116   if (!itsRunPID) return 0;
00117 
00118   // compute the error:
00119   T err = target - val;
00120   itsErr = err;
00121   T pterm = err; pterm *= itsPgain;
00122 
00123   // update the integral state:
00124   itsIstate += err;
00125   if (itsIstate > itsImax) itsIstate = itsImax;
00126   else if (itsIstate < itsImin) itsIstate = itsImin;
00127   T iterm = itsIstate; iterm *= itsIgain;
00128 
00129   // update the derivative term:
00130   T diff = (val - itsDstate);
00131   itsVel = diff;
00132   itsDstate = val;
00133   T dterm = diff; dterm *= itsDgain;
00134 
00135   // Command is just the P-I-D combination of the above:
00136   pterm += iterm; pterm -= dterm;
00137 
00138   //process some non linear controls
00139   //if (itsErrThresh > 0)
00140   //{
00141   //  if (itsErr > itsPosStaticErrThresh  || itsErr < itsNegStaticErrThresh)
00142   //  {
00143   //    if(itsVel != 0)
00144   //    {
00145   //      itsNoMoveCount = 0;
00146   //    }
00147   //    else
00148   //    {
00149   //      if (pterm != 0)
00150   //      {
00151   //        if (itsErr > 0)
00152   //          pterm = itsPosThresh;
00153   //        else
00154   //          pterm = itsNegThresh;
00155   //      }
00156 
00157   //      itsNoMoveCount++;
00158   //    }
00159   // }
00160    // else
00161    // {
00162    //   pterm = 0;
00163    //   itsNoMoveCount = 0;
00164    // }
00165     //Over move Handling
00166     //TODO Fix it
00167     //if (itsNoMoveCount > itsNoMoveThresh)
00168     //{
00169     //  //Stop Motor
00170     //  pterm = 0;
00171     //  itsRunPID = false;
00172     //}
00173   //}
00174 
00175 
00176   if (pterm > itsSpeed) pterm = itsSpeed;
00177   if (pterm < -itsSpeed) pterm = -itsSpeed;
00178 
00179   if (pterm > itsMaxMotor) pterm = itsMaxMotor;
00180   if (pterm < itsMinMotor) pterm = itsMinMotor;
00181   itsPTerm = pterm;
00182 
00183 
00184   return pterm;
00185 }
00186 
00187 template <class T>
00188 T PID<T>::update(const T& targetPos, const T& targetVel, const T& currentVal)
00189 {
00190   // NOTE: we only use unary operators on T for compatibility with Angle...
00191 
00192 
00193   if (!itsRunPID) return 0;
00194 
00195   // compute the error:
00196   T posErr = targetPos - currentVal;
00197   itsErr = posErr;
00198 
00199   // update the integral state:
00200   //itsIstate += err;
00201   //if (itsIstate > itsImax) itsIstate = itsImax;
00202   //else if (itsIstate < itsImin) itsIstate = itsImin;
00203   //T iterm = itsIstate; iterm *= itsIgain;
00204 
00205   // update the velocity term:
00206 
00207   T vel = (currentVal - itsLastVal);
00208   T velErr = (targetVel - vel);
00209 
00210   T pTerm = posErr; //To avoid angle multiplication
00211   pTerm *= itsPgain;
00212 
00213   T dTerm = velErr;
00214   dTerm *= itsDgain;
00215 
00216   T pid = pTerm + dTerm;
00217 
00218   //if (fabs(velErr) > 0 && posErr > 0 && vel == 0 && pid < itsPosThresh)
00219   //  pid = itsPosThresh;
00220   //else if (fabs(velErr) > 0 && posErr < 0 && vel == 0 && pid > itsNegThresh)
00221   //  pid = itsNegThresh;
00222 
00223   itsLastVal = currentVal;
00224 
00225 
00226   if (pid > itsMaxMotor) pid = itsMaxMotor;
00227   if (pid < itsMinMotor) pid = itsMinMotor;
00228 
00229   return pid;
00230 }
00231 
00232 // Instantiations:
00233 template class PID<float>;
00234 template class PID<Angle>;
00235 
00236 // ######################################################################
00237 /* So things look consistent in everyone's emacs... */
00238 /* Local Variables: */
00239 /* indent-tabs-mode: nil */
00240 /* End: */
Generated on Sun May 8 08:40:23 2011 for iLab Neuromorphic Vision Toolkit by  doxygen 1.6.3