/home/fwph/code/wurde/modules/rFlexBase/rFlexServer.cpp

Go to the documentation of this file.
00001 #include <CommsManager.H>
00002 #include <RobotDrive.H>
00003 #include <Egomotion.H>
00004 #include <Power.H>
00005 #include <RobotUtil.H>
00006 #include <RangeFinder.H>
00007 #include "RFlex.H"
00008 #include <cmath>
00009 #include <Logger.H>
00010 
00011 using namespace WURDE;
00012 using namespace std;
00013 
00014 string parseRflexConfig(std::string config,std::string rflexName);
00015 
00016 CommsManager myManager("TomRFlex");
00017 
00018 void handler(int signum){
00019        myManager.setQuit();
00020 }
00021 
00022 int main(int argc, char *argv[]){
00023 
00024         myManager.setRealName("RFlexServer");
00025         myManager.setHelpString("\t-c: Specify a config file to use. Default is rflex-config.xml\n\n Note that the -n flag is used to select the configuration block to be used from the config file.\n\nThis module provides access to the RFlex controller on iRobot/RWI B21r and ATRV Jr. robots. It has not been tested with other iRobot/RWI robots.\n\n");
00026         myManager.parseOptions(argc,argv,"c:");
00027         Logger myLogger(myManager.getName());
00028         
00029         string port,confFile,robotType;
00030         bool unsafeBrake=false;
00031         unsigned char type=0;
00032         if(g_globalConfiguration.haveOption("c")){
00033                 confFile=g_globalConfiguration.getOption("c");
00034                 if(confFile[0]!='/'){
00035                         confFile=g_globalConfiguration.getConfigDirectory()+"/"+confFile;
00036                 }
00037         }else{
00038                 confFile=g_globalConfiguration.getConfigDirectory()+"/"+"rflex-config.xml";
00039         }
00040         
00041         g_logdebug << "Reading configuration for " << myManager.getName() << endl;
00042         port=parseRflexConfig(confFile,myManager.getName());
00043 
00044         if(g_globalConfiguration.getOption("rFlexUnsafeBrake")=="true"){
00045                 unsafeBrake=true;
00046         }
00047         
00048         double trans=0, steer=0, tlimit=1.0, slimit=M_PI/2.0;
00049         
00050         if(g_globalConfiguration.haveOption("rFlexMaxTrans")){
00051                 tlimit=strtod(g_globalConfiguration.getOption("rFlexMaxTrans").c_str(),NULL);
00052         }
00053         
00054         if(g_globalConfiguration.haveOption("rFlexMaxSteer")){
00055                 slimit=strtod(g_globalConfiguration.getOption("rFlexMaxSteer").c_str(),NULL);
00056         }
00057         
00058         if(g_globalConfiguration.haveOption("rFlexType")){
00059                 robotType=g_globalConfiguration.getOption("rFlexType");
00060                 
00061         }else{
00062                 robotType="B21r"; // default to B21; other possible value-- ATRVJr
00063         }
00064         
00065         RFlex rflex(port,robotType);
00066         
00067         rflex.setBrake();
00068         rflex.systemUpdate();
00069         rflex.motorSetVelocity(0,0);
00070         rflex.odometryOn();
00071         rflex.systemUpdate();
00072         
00073         RobotDrive myDrive(myManager.getName()+"Drive");
00074         Egomotion myEgomotion(myManager.getName()+"Motion");
00075         Power myPower(myManager.getName()+"Power");       
00076         RangeFinder mySonar(myManager.getName()+"Sonar");
00077         
00078         if(robotType=="B21r"){
00079                 type=RFLEX_B21R;
00080         }else if(robotType=="ATRVJr"){
00081                 type=RFLEX_ATRVJR;
00082         }
00083         
00084         Pose currentPose(0,0,0);
00085         bool brakestat=true;
00086         
00087         double baseX, baseY, baseT;
00088         //       char logbuf[1024];
00089         
00090         usleep(2000);
00091         
00092         baseX=rflex.x();
00093         baseY=rflex.y();
00094         baseT=rflex.heading();
00095         
00096         myManager.registerSupplier(&myLogger);
00097         myManager.registerSupplier(&myDrive);
00098         myManager.registerSupplier(&myEgomotion);
00099         myManager.registerSupplier(&myPower);
00100         if(type==RFLEX_ATRVJR){
00101                 myManager.registerSupplier(&mySonar);
00102                 rflex.sonarOn();
00103                 g_logdebug << "Turning on sonar..." << endl;
00104                 for(int i=0;i<rflex.getNumSonars();i++){
00105                         mySonar.data.ranges.push_back(0);
00106                 }
00107                 mySonar.info.uniform.setValueAndLock(false);
00108                 mySonar.info.half_angle.setValueAndLock((7.5/180)*M_PI);
00109                 mySonar.info.angle_min.setValueAndLock(0);
00110                 
00111                 vector<Pose3D> tmpPositions(rflex.getNumSonars());
00112                 for(int i=0;i<rflex.getNumSonars();i++){
00113                         tmpPositions[i]=Pose3D(0,0,0.33);
00114                 }
00115                 
00116                 mySonar.info.sensor_positions.setValueAndLock(tmpPositions);
00117                 mySonar.publishInfo();
00118         }
00119         myManager.setSleep(0.02);
00120         
00121         /* these are more or less reasonable values. Not super
00122            safe, but we expect the obstacle avoider to pay more
00123            attention */
00124         myDrive.info.transLimit.setValue(tlimit);
00125         myDrive.info.angularLimit.setValue(slimit);
00126         
00127         /* we can set these values in Mage, but for now, we won't */
00128         myDrive.info.transAccel.setValue(-1);
00129         myDrive.info.angularAccel.setValue(-1);
00130         myDrive.info.transDecel.setValue(-1);
00131         myDrive.info.angularDecel.setValue(-1);
00132         
00133         myDrive.info.brake.setValue(true);
00134         
00135         /* finally, set the current velocities */
00136         myDrive.info.trans.setValue(0);
00137         myDrive.info.angular.setValue(0);
00138         
00139         myDrive.publishInfo();
00140         
00141         myEgomotion.data.location=currentPose;
00142         myEgomotion.data.transVelocity=0;
00143         myEgomotion.data.angularVelocity=0;
00144         myEgomotion.data.transAccel=0;
00145         myEgomotion.data.angularAccel=0;
00146         
00147         myEgomotion.publishData();
00148         //there's some question as to whether this interface is actualy useful
00149         // as is. we should probably have some sort of reasonable power percentage
00150         // measure, plus average drain rate, etc.
00151         myPower.data.volts=rflex.batteryVoltage();
00152         // guess values; we need to determine these all empirically like
00153         myPower.data.max_volts=25.0;
00154         myPower.data.min_volts=21.0;
00155         //this is arbitrary at present, but we can almost certainly determine it by the
00156         //voltage level-- the power level on the robot is at a distinct level when plugged in.
00157         myPower.data.ac_online=false;
00158         myPower.publishData();
00159         
00160         while(myManager.runUpdate()==STATE_RUN||
00161               myManager.getState()==STATE_IDLE){
00162                 
00163                 if(myManager.getState()==STATE_IDLE){
00164                         rflex.motorSetVelocity(0,0);
00165                         continue;
00166                 }
00167                 
00168                 rflex.systemUpdate();
00169                 
00170                 if(myDrive.newRequest()){
00171                         //                   cout << "received request" << endl;
00172                         myDrive.getNextRequest();
00173                         tlimit=myDrive.requests.transLimit.getValue();
00174                         slimit=myDrive.requests.angularLimit.getValue();
00175                         trans=myDrive.requests.trans.getValue();
00176                         steer=myDrive.requests.angular.getValue();
00177                         
00178                         g_logdebug << "Received request: (trans,steer) " << trans << "," << steer << endl;
00179                         
00180                         if(myDrive.requests.brake.getValue()){
00181                                 //                          cout << "Turning brake on.\n";
00182                                 g_debug("Activating brake");
00183                                 rflex.setBrake();
00184                                 brakestat=true;
00185                         }else{
00186                                 //                          cout << "Turning software brake off.\n";
00187                                 g_debug("Turning off software brake. Hardware brake may still be active.");
00188                                 //we don't really want to turn the brake off if it's 
00189                                 // false, but we do want to turn the brake *on* if it's
00190                                 // true.
00191                                 
00192                                 //UnCOMMENTING THIS LINE IS EXTREMELY DANGEROUS AND 
00193                                 //NOT RECOMMENDED!
00194                                 if(unsafeBrake){
00195                                         rflex.brakeOff();
00196                                 }
00197                                 brakestat=false;
00198                         }
00199                         
00200                         if(trans>tlimit)
00201                                 trans=tlimit;
00202                         else if(trans<(-tlimit))
00203                                 trans=(-tlimit);
00204                         
00205                         if(steer>slimit)
00206                                 steer=slimit;
00207                         else if(steer<(-slimit))
00208                                 steer=(-slimit);
00209                         
00210                 }
00211                 
00212                 
00213                 if(!brakestat){
00214                         rflex.motorSetVelocity(trans,steer);
00215                 }else{
00216                         rflex.motorSetVelocity(0,0);
00217                 }
00218                 
00219                 myDrive.info.trans.setValue(trans);
00220                 myDrive.info.angular.setValue(steer);
00221                 myDrive.info.transLimit.setValue(tlimit);
00222                 myDrive.info.angularLimit.setValue(slimit);
00223                 myDrive.info.brake.setValue(rflex.brakeOn());
00224                 myDrive.publishInfo();
00225                 
00226                 currentPose.x(rflex.x());
00227                 currentPose.y(rflex.y());
00228                 currentPose.theta(rflex.heading());
00229                 
00230                 g_logdebug << "current pose " << rflex.x() << " " << rflex.y() << " " << rflex.heading() << endl;
00231                 
00232                 myEgomotion.data.location=currentPose;
00233                 myEgomotion.data.transVelocity=rflex.translateVelocity();
00234                 myEgomotion.data.angularVelocity=rflex.rotateVelocity();
00235                 myEgomotion.data.transAccel=rflex.translateAcceleration();
00236                 myEgomotion.data.angularAccel=rflex.rotateAcceleration();
00237                 
00238                 myEgomotion.publishData();
00239                 
00240                 if(type==RFLEX_ATRVJR){
00241                         for(int i=0;i<rflex.getNumSonars();i++){
00242                                 mySonar.data.ranges[i]=rflex.getSonar(i);
00243                         }
00244                         
00245                         mySonar.publishData();
00246                 }
00247                 
00248                 myPower.data.volts=rflex.batteryVoltage();
00249                 myPower.publishData();
00250                 
00251         }
00252         
00253         
00254         rflex.motorSetVelocity(0,0);
00255         
00256         if(type==RFLEX_ATRVJR){
00257                 rflex.sonarOff();
00258         }
00259         
00260         myDrive.info.trans.setValue(0);
00261         myDrive.info.angular.setValue(0);
00262         myDrive.info.transLimit.setValue(tlimit);
00263         myDrive.info.angularLimit.setValue(slimit);
00264         myDrive.publishInfo();
00265         
00266         currentPose.x(0);
00267         currentPose.y(0);
00268         currentPose.theta(0);
00269         myEgomotion.data.location=currentPose;
00270         myEgomotion.data.transVelocity=0;
00271         myEgomotion.data.angularVelocity=0;
00272         myEgomotion.data.transAccel=0;
00273         myEgomotion.data.angularAccel=0;
00274         
00275         myEgomotion.publishData();
00276         g_debug("Shutting down rFlex cleanly.");
00277         myManager.runUpdate();
00278         
00279         myManager.cleanUp();    
00280         
00281         return 0;
00282 }

Generated on Thu Feb 1 15:31:52 2007 for WURDE by  doxygen 1.5.1