mrpt_rbpf_slam.cpp
Go to the documentation of this file.
00001 /*
00002  *  File: mrpt_slam.cpp
00003  *  Author: Vladislav Tananaev
00004  *
00005  *
00006  */
00007 #include <mrpt/version.h>
00008 #include <mrpt_bridge/utils.h>
00009 #include <mrpt_rbpf_slam/mrpt_rbpf_slam.h>
00010 
00011 #if MRPT_VERSION >= 0x199
00012 #include <mrpt/serialization/CArchive.h>
00013 #endif
00014 
00015 namespace mrpt_rbpf_slam {
00016 PFslam::~PFslam() {
00017   try {
00018     std::string sOutMap = "mrpt_rbpfslam_";
00019     mrpt::system::TTimeParts parts;
00020     mrpt::system::timestampToParts(mrpt::system::now(), parts, true);
00021     sOutMap +=
00022         mrpt::format("%04u-%02u-%02u_%02uh%02um%02us", (unsigned int)parts.year,
00023                      (unsigned int)parts.month, (unsigned int)parts.day,
00024                      (unsigned int)parts.hour, (unsigned int)parts.minute,
00025                      (unsigned int)parts.second);
00026     sOutMap += ".simplemap";
00027 
00028     sOutMap = mrpt::system::fileNameStripInvalidChars(sOutMap);
00029     if (mrpt::system::directoryExists(options_.simplemap_path_prefix)) {
00030       sOutMap = options_.simplemap_path_prefix + sOutMap;
00031     } else {
00032       std::cerr << "Folder " << options_.simplemap_path_prefix
00033                 << " doesn't exist, cannot save simplemap there! Default "
00034                    "'~/.ros/' path will be used.\n";
00035     }
00036     std::cout << "Saving built map " << sOutMap << "\n";
00037     mapBuilder_.saveCurrentMapToFile(sOutMap);
00038   } catch (const std::exception &e) {
00039     std::cerr << "Exception: " << e.what() << "\n";
00040   }
00041 }
00042 
00043 void PFslam::readIniFile(const std::string &ini_filename) {
00044 #if MRPT_VERSION >= 0x199
00045   mrpt::config::CConfigFile iniFile(ini_filename);
00046 #else
00047   mrpt::utils::CConfigFile iniFile(ini_filename);
00048 #endif
00049   options_.rbpfMappingOptions_.loadFromConfigFile(iniFile,
00050                                                   "MappingApplication");
00051   options_.rbpfMappingOptions_.dumpToConsole();
00052 }
00053 
00054 void PFslam::readRawlog(
00055     const std::string &rawlog_filename,
00056     std::vector<std::pair<mrpt::obs::CActionCollection,
00057                           mrpt::obs::CSensoryFrame>> &data) {
00058   size_t rawlogEntry = 0;
00059 #if MRPT_VERSION >= 0x199
00060   mrpt::io::CFileGZInputStream rawlog_stream(rawlog_filename);
00061   auto rawlogFile = mrpt::serialization::archiveFrom(rawlog_stream);
00062 #else
00063   mrpt::utils::CFileGZInputStream rawlogFile(rawlog_filename);
00064 #endif
00065   mrpt::obs::CActionCollection::Ptr action;
00066   mrpt::obs::CSensoryFrame::Ptr observations;
00067 
00068   for (;;) {
00069     if (mrpt::system::os::kbhit()) {
00070       char c = mrpt::system::os::getch();
00071       if (c == 27)
00072         break;
00073     }
00074 
00075     // Load action/observation pair from the rawlog:
00076     // --------------------------------------------------
00077     if (!mrpt::obs::CRawlog::readActionObservationPair(
00078             rawlogFile, action, observations, rawlogEntry)) {
00079       break; // file EOF
00080     }
00081     data.emplace_back(*action, *observations);
00082   }
00083 }
00084 
00085 void PFslam::observation(
00086     const mrpt::obs::CSensoryFrame::ConstPtr sensory_frame,
00087     const mrpt::obs::CObservationOdometry::ConstPtr odometry) {
00088   action_ = mrpt::obs::CActionCollection::Create();
00089   mrpt::obs::CActionRobotMovement2D odom_move;
00090   odom_move.timestamp = sensory_frame->getObservationByIndex(0)->timestamp;
00091 
00092   if (odometry) {
00093     if (odomLastObservation_.empty()) {
00094       odomLastObservation_ = odometry->odometry;
00095     }
00096 
00097     mrpt::poses::CPose2D incOdoPose = odometry->odometry - odomLastObservation_;
00098     odomLastObservation_ = odometry->odometry;
00099     odom_move.computeFromOdometry(incOdoPose, options_.motion_model_options_);
00100     action_->insert(odom_move);
00101   }
00102 }
00103 
00104 void PFslam::initSlam(PFslam::Options options) {
00105   log4cxx::LoggerPtr ros_logger =
00106       log4cxx::Logger::getLogger(ROSCONSOLE_DEFAULT_NAME);
00107   mapBuilder_.setVerbosityLevel(
00108       mrpt_bridge::rosLoggerLvlToMRPTLoggerLvl(ros_logger->getLevel()));
00109   mapBuilder_.logging_enable_console_output = false;
00110 #if MRPT_VERSION < 0x199
00111   mapBuilder_.logRegisterCallback(static_cast<output_logger_callback_t>(
00112       &mrpt_bridge::mrptToROSLoggerCallback_mrpt_15));
00113 #else
00114   mapBuilder_.logRegisterCallback(static_cast<output_logger_callback_t>(
00115       &mrpt_bridge::mrptToROSLoggerCallback));
00116 #endif
00117   mapBuilder_.options.enableMapUpdating = true;
00118   mapBuilder_.options.debugForceInsertion = false;
00119 
00120 #if MRPT_VERSION >= 0x199
00121   mrpt::random::getRandomGenerator().randomize();
00122 #else
00123   mrpt::random::randomGenerator.randomize();
00124 #endif
00125 
00126   options_ = std::move(options);
00127 
00128   //  use_motion_model_default_options_ = false;
00129   //  //  motion_model_default_options_.modelSelection =
00130   //  mrpt::obs::CActionRobotMovement2D::mmGaussian;
00131   //  //  motion_model_default_options_.gaussianModel.minStdXY = 0.10;
00132   //  //  motion_model_default_options_.gaussianModel.minStdPHI = 2.0;
00133 
00134   //  motion_model_options_.modelSelection =
00135   //  mrpt::obs::CActionRobotMovement2D::mmGaussian;
00136   //  motion_model_options_.gaussianModel.a1 = 0.034f;
00137   //  motion_model_options_.gaussianModel.a2 = 0.057f;
00138   //  motion_model_options_.gaussianModel.a3 = 0.014f;
00139   //  motion_model_options_.gaussianModel.a4 = 0.097f;
00140   //  motion_model_options_.gaussianModel.minStdXY = 0.005f;
00141   //  motion_model_options_.gaussianModel.minStdPHI = 0.05f;
00142 
00143   //  PROGRESS_WINDOW_WIDTH_ = 600;
00144   //  PROGRESS_WINDOW_HEIGHT_ = 500;
00145   //  SHOW_PROGRESS_IN_WINDOW_ = false;
00146   //  SHOW_PROGRESS_IN_WINDOW_DELAY_MS_ = 0;
00147   //  CAMERA_3DSCENE_FOLLOWS_ROBOT_ = false;
00148 }
00149 
00150 void PFslam::init3Dwindow() {
00151 #if MRPT_HAS_WXWIDGETS
00152   if (options_.SHOW_PROGRESS_IN_WINDOW_) {
00153     win3D_ = mrpt::gui::CDisplayWindow3D::Create(
00154         "RBPF-SLAM @ MRPT C++ Library", options_.PROGRESS_WINDOW_WIDTH_,
00155         options_.PROGRESS_WINDOW_HEIGHT_);
00156     win3D_->setCameraZoom(40);
00157     win3D_->setCameraAzimuthDeg(-50);
00158     win3D_->setCameraElevationDeg(70);
00159   }
00160 #endif
00161 }
00162 void PFslam::run3Dwindow() {
00163   // Save a 3D scene view of the mapping process:
00164   if (options_.SHOW_PROGRESS_IN_WINDOW_ && win3D_) {
00165     // get the current map and pose
00166     metric_map_ = mapBuilder_.mapPDF.getCurrentMostLikelyMetricMap();
00167     mapBuilder_.mapPDF.getEstimatedPosePDF(curPDF);
00168     mrpt::opengl::COpenGLScene::Ptr scene;
00169     scene = mrpt::opengl::COpenGLScene::Create();
00170 
00171     // The ground:
00172     mrpt::opengl::CGridPlaneXY::Ptr groundPlane =
00173         mrpt::opengl::CGridPlaneXY::Create(-200, 200, -200, 200, 0, 5);
00174     groundPlane->setColor(0.4, 0.4, 0.4);
00175     scene->insert(groundPlane);
00176 
00177     // The camera pointing to the current robot pose:
00178     if (options_.CAMERA_3DSCENE_FOLLOWS_ROBOT_) {
00179       mrpt::opengl::CCamera::Ptr objCam = mrpt::opengl::CCamera::Create();
00180       mrpt::poses::CPose3D robotPose;
00181       curPDF.getMean(robotPose);
00182 
00183       objCam->setPointingAt(robotPose);
00184       objCam->setAzimuthDegrees(-30);
00185       objCam->setElevationDegrees(30);
00186       scene->insert(objCam);
00187     }
00188     // Draw the map(s):
00189     mrpt::opengl::CSetOfObjects::Ptr objs =
00190         mrpt::opengl::CSetOfObjects::Create();
00191     metric_map_->getAs3DObject(objs);
00192     scene->insert(objs);
00193 
00194     // Draw the robot particles:
00195     size_t M = mapBuilder_.mapPDF.particlesCount();
00196     mrpt::opengl::CSetOfLines::Ptr objLines =
00197         mrpt::opengl::CSetOfLines::Create();
00198     objLines->setColor(0, 1, 1);
00199     for (size_t i = 0; i < M; i++) {
00200       std::deque<mrpt::math::TPose3D> path;
00201       mapBuilder_.mapPDF.getPath(i, path);
00202 
00203       float x0 = 0, y0 = 0, z0 = 0;
00204       for (size_t k = 0; k < path.size(); k++) {
00205         objLines->appendLine(x0, y0, z0 + 0.001, path[k].x, path[k].y,
00206                              path[k].z + 0.001);
00207         x0 = path[k].x;
00208         y0 = path[k].y;
00209         z0 = path[k].z;
00210       }
00211     }
00212     scene->insert(objLines);
00213 
00214     // An ellipsoid:
00215     mrpt::poses::CPose3D lastMeanPose;
00216     float minDistBtwPoses = -1;
00217     std::deque<mrpt::math::TPose3D> dummyPath;
00218     mapBuilder_.mapPDF.getPath(0, dummyPath);
00219     for (int k = (int)dummyPath.size() - 1; k >= 0; k--) {
00220       mrpt::poses::CPose3DPDFParticles poseParts;
00221       mapBuilder_.mapPDF.getEstimatedPosePDFAtTime(k, poseParts);
00222 
00223 #if MRPT_VERSION >= 0x199
00224           const auto [COV, meanPose] = poseParts.getCovarianceAndMean();
00225 #else
00226           mrpt::poses::CPose3D meanPose;
00227           mrpt::math::CMatrixDouble66 COV;
00228           poseParts.getCovarianceAndMean(COV, meanPose);
00229 #endif
00230 
00231       if (meanPose.distanceTo(lastMeanPose) > minDistBtwPoses) {
00232                 mrpt::math::CMatrixDouble33 COV3 =
00233 #if MRPT_VERSION >= 0x199
00234                         COV.blockCopy<3, 3>(0, 0);
00235 #else
00236                         COV.block(0, 0, 3, 3);
00237 #endif
00238 
00239         minDistBtwPoses = 6 * sqrt(COV3(0, 0) + COV3(1, 1));
00240 
00241         mrpt::opengl::CEllipsoid::Ptr objEllip =
00242             mrpt::opengl::CEllipsoid::Create();
00243         objEllip->setLocation(meanPose.x(), meanPose.y(), meanPose.z() + 0.001);
00244         objEllip->setCovMatrix(COV3, COV3(2, 2) == 0 ? 2 : 3);
00245 
00246         objEllip->setColor(0, 0, 1);
00247         objEllip->enableDrawSolid3D(false);
00248         scene->insert(objEllip);
00249 
00250         lastMeanPose = meanPose;
00251       }
00252     }
00253 
00254     mrpt::opengl::COpenGLScene::Ptr &scenePtr = win3D_->get3DSceneAndLock();
00255     scenePtr = scene;
00256     win3D_->unlockAccess3DScene();
00257     win3D_->forceRepaint();
00258   }
00259 }
00260 } // namespace mrpt_rbpf_slam


mrpt_rbpf_slam
Author(s): Vladislav Tananaev
autogenerated on Thu Jun 6 2019 21:40:36