去掉初始化成功后才进行里程计。

    void laserCloudInfoHandler(const lio_sam::cloud_infoConstPtr& msgIn){// extract time stamp//addedtimeLaserInfoStamp = msgIn->header.stamp;timeLaserCloudInfoLast = msgIn->header.stamp.toSec();// extract info and feature cloudcloudInfo = *msgIn;pcl::fromROSMsg(msgIn->cloud_corner,  *laserCloudCornerLast);pcl::fromROSMsg(msgIn->cloud_surface, *laserCloudSurfLast);/************************************added by gc*****************************///if the sysytem is not initialized ffer the first scan for the system to initialize//the LIO system start working only when the localization initializing is finished/*if(initializedFlag == NonInitialized || initializedFlag == Initializing){if(cloudScanForInitialize->points.size() == 0){downsampleCurrentScan();mtx_general.lock();*cloudScanForInitialize += *laserCloudCornerLastDS;*cloudScanForInitialize += *laserCloudSurfLastDS;mtx_general.unlock();laserCloudCornerLastDS->clear();laserCloudSurfLastDS->clear();laserCloudCornerLastDSNum = 0;laserCloudSurfLastDSNum = 0;transformTobeMapped[0] = cloudInfo.imuRollInit;transformTobeMapped[1] = cloudInfo.imuPitchInit;transformTobeMapped[2] = cloudInfo.imuYawInit;if (!useImuHeadingInitialization)//gc: if not use the heading of init_IMU as InitializationtransformTobeMapped[2] = 0;}return;}frameNum++;*//************************************added by gc*****************************/std::lock_guard<std::mutex> lock(mtx);if (timeLaserCloudInfoLast - timeLastProcessing >= mappingProcessInterval) {//gc:control the rate of mapping processtimeLastProcessing = timeLaserCloudInfoLast;updateInitialGuess();//gc: update initial value for statesextractSurroundingKeyFrames();//gc:downsampleCurrentScan();//gc:down sample the current corner points and surface pointsscan2MapOptimization();//gc: calculate the tranformtion using lidar measurement with the Imu preintegration as initial values//and then interpolate roll and pitch angle using IMU measurement and above measurementsaveKeyFramesAndFactor();//gc: save corner cloud and surface cloud of this scan, and add odom and GPS factors//correctPoses();publishOdometry();publishFrames();}}

在接收到重定位位姿后直接进行全局匹配,然后更新odomToWorld

void initialpose_callback(const geometry_msgs::PoseWithCovarianceStampedConstPtr& pose_msg){//first calculate global pose//x-y-zif(initializedFlag == Initialized)return;float x = pose_msg->pose.pose.position.x;float y = pose_msg->pose.pose.position.y;float z = pose_msg->pose.pose.position.z;//roll-pitch-yawtf::Quaternion q_global;double roll_global; double pitch_global; double yaw_global;q_global.setX(pose_msg->pose.pose.orientation.x);q_global.setY(pose_msg->pose.pose.orientation.y);q_global.setZ(pose_msg->pose.pose.orientation.z);q_global.setW(pose_msg->pose.pose.orientation.w);tf::Matrix3x3(q_global).getRPY(roll_global, pitch_global, yaw_global);//global transformationtransformInTheWorld[0] = roll_global;transformInTheWorld[1] = pitch_global;transformInTheWorld[2] = yaw_global;transformInTheWorld[3] = x;transformInTheWorld[4] = y;transformInTheWorld[5] = z;PointTypePose thisPose6DInWorld = trans2PointTypePose(transformInTheWorld);Eigen::Affine3f T_thisPose6DInWorld = pclPointToAffine3f(thisPose6DInWorld);//Odom transformationPointTypePose thisPose6DInOdom = trans2PointTypePose(transformTobeMapped);Eigen::Affine3f T_thisPose6DInOdom = pclPointToAffine3f(thisPose6DInOdom);//transformation: Odom to MapEigen::Affine3f T_OdomToMap = T_thisPose6DInWorld * T_thisPose6DInOdom.inverse();float delta_x, delta_y, delta_z, delta_roll, delta_pitch, delta_yaw;pcl::getTranslationAndEulerAngles (T_OdomToMap, delta_x, delta_y, delta_z, delta_roll, delta_pitch, delta_yaw);mtxtranformOdomToWorld.lock();//keep for co-operate the initializing and lio, not useful for the presenttranformOdomToWorld[0] = delta_roll;tranformOdomToWorld[1] = delta_pitch;tranformOdomToWorld[2] = delta_yaw;tranformOdomToWorld[3] = delta_x;tranformOdomToWorld[4] = delta_y;tranformOdomToWorld[5] = delta_z;mtxtranformOdomToWorld.unlock();initializedFlag = NonInitialized;//okagvstd::cout << "transformInTheWorld R P Y X Y Z " << transformInTheWorld[0] << " "<< transformInTheWorld[1] << " "<< transformInTheWorld[2] << " "<< transformInTheWorld[3] << " "<< transformInTheWorld[4] << " "<< transformInTheWorld[5] << std::endl;std::cout << "tranformOdomToWorld R P Y X Y Z "<< tranformOdomToWorld[0] << " "<< tranformOdomToWorld[1] << " "<< tranformOdomToWorld[2] << " "<< tranformOdomToWorld[3] << " "<< tranformOdomToWorld[4] << " "<< tranformOdomToWorld[5] << std::endl; ICPscanMatchGlobal();initializedFlag = Initialized;//globalLocalizeInitialiized = false;}

新增一个bool变量global_match_state用于检测是否重定位成功

 void ICPscanMatchGlobal(){//initializing
/*if(initializedFlag == NonInitialized){ICPLocalizeInitialize();return;}*/if (cloudKeyPoses3D->points.empty() == true)return;//change-5/******************added by gc************************/mtxWin.lock();int latestFrameIDGlobalLocalize;latestFrameIDGlobalLocalize = win_cloudKeyPoses3D.size() - 1;pcl::PointCloud<PointType>::Ptr latestCloudIn(new pcl::PointCloud<PointType>());*latestCloudIn += *transformPointCloud(win_cornerCloudKeyFrames[latestFrameIDGlobalLocalize], &win_cloudKeyPoses6D[latestFrameIDGlobalLocalize]);*latestCloudIn += *transformPointCloud(win_surfCloudKeyFrames[latestFrameIDGlobalLocalize],   &win_cloudKeyPoses6D[latestFrameIDGlobalLocalize]);std::cout << "the size of input cloud: " << latestCloudIn->points.size() <<std::endl;mtxWin.unlock();/******************added by gc************************///        int latestFrameIDGlobalLocalize;
//        latestFrameIDGlobalLocalize = cloudKeyPoses3D->size() - 1;
//
//
//        //latest Frame cloudpoints In the odom Frame
//
//        pcl::PointCloud<PointType>::Ptr latestCloudIn(new pcl::PointCloud<PointType>());
//        *latestCloudIn += *transformPointCloud(cornerCloudKeyFrames[latestFrameIDGlobalLocalize], &cloudKeyPoses6D->points[latestFrameIDGlobalLocalize]);
//        *latestCloudIn += *transformPointCloud(surfCloudKeyFrames[latestFrameIDGlobalLocalize],   &cloudKeyPoses6D->points[latestFrameIDGlobalLocalize]);
//        std::cout << "the size of input cloud: " << latestCloudIn->points.size() <<std::endl;pcl::NormalDistributionsTransform<PointType, PointType> ndt;ndt.setTransformationEpsilon(0.01);ndt.setResolution(1.0);pcl::IterativeClosestPoint<PointType, PointType> icp;icp.setMaxCorrespondenceDistance(100);icp.setMaximumIterations(100);icp.setTransformationEpsilon(1e-6);icp.setEuclideanFitnessEpsilon(1e-6);icp.setRANSACIterations(0);// Align cloud//3. calculate the tranform of odom relative to world//Eigen::Affine3f transodomToWorld_init = pcl::getTransformation(0,0,0,0,0,0);mtxtranformOdomToWorld.lock();std::cout << "ICPscanMatchGlobal R P Y X Y Z "<< tranformOdomToWorld[0] << " "<< tranformOdomToWorld[1] << " "<< tranformOdomToWorld[2] << " "<< tranformOdomToWorld[3] << " "<< tranformOdomToWorld[4] << " "<< tranformOdomToWorld[5] << std::endl;Eigen::Affine3f transodomToWorld_init = pcl::getTransformation(tranformOdomToWorld[3], tranformOdomToWorld[4], tranformOdomToWorld[5], tranformOdomToWorld[0], tranformOdomToWorld[1], tranformOdomToWorld[2]);mtxtranformOdomToWorld.unlock();//okagv//PointTypePose thisPose6DInWorld = trans2PointTypePose(transformInTheWorld);//Eigen::Affine3f T_thisPose6DInWorld = pclPointToAffine3f(thisPose6DInWorld);Eigen::Matrix4f matricInitGuess = transodomToWorld_init.matrix();//std::cout << "matricInitGuess: " << matricInitGuess << std::endl;//Firstly perform ndt in coarse resolutionndt.setInputSource(latestCloudIn);ndt.setInputTarget(cloudGlobalMapDS);pcl::PointCloud<PointType>::Ptr unused_result_0(new pcl::PointCloud<PointType>());ndt.align(*unused_result_0, matricInitGuess);//use the outcome of ndt as the initial guess for ICPicp.setInputSource(latestCloudIn);icp.setInputTarget(cloudGlobalMapDS);pcl::PointCloud<PointType>::Ptr unused_result(new pcl::PointCloud<PointType>());icp.align(*unused_result, ndt.getFinalTransformation());std::cout << "ICP converg flag:" << icp.hasConverged() << ". Fitness score: " << icp.getFitnessScore() << std::endl << std::endl;//if (icp.hasConverged() == false || icp.getFitnessScore() > historyKeyframeFitnessScore)// return;Eigen::Affine3f transodomToWorld_New;transodomToWorld_New = icp.getFinalTransformation();float x, y, z, roll, pitch, yaw;pcl::getTranslationAndEulerAngles (transodomToWorld_New, x, y, z, roll, pitch, yaw);//std::cout << " in test 0.03: deltaX = " << x << " deltay = " << y << " deltaZ = " << z << std::endl;mtxtranformOdomToWorld.lock();//renew tranformOdomToWorldtranformOdomToWorld[0] = roll;tranformOdomToWorld[1] = pitch;tranformOdomToWorld[2] = yaw;tranformOdomToWorld[3] = x;tranformOdomToWorld[4] = y;tranformOdomToWorld[5] = z;mtxtranformOdomToWorld.unlock();//publish the laserpointcloud in world frame//publish global mappublishCloud(&pubMapWorld, cloudGlobalMapDS, timeLaserInfoStamp, "map");//publish world mapif (icp.hasConverged() == true && icp.getFitnessScore() < historyKeyframeFitnessScore){geometry_msgs::PoseStamped pose_odomTo_map;tf::Quaternion q_odomTo_map = tf::createQuaternionFromRPY(roll, pitch, yaw);pose_odomTo_map.header.stamp = timeLaserInfoStamp;pose_odomTo_map.header.frame_id = "map";pose_odomTo_map.pose.position.x = x; pose_odomTo_map.pose.position.y = y; pose_odomTo_map.pose.position.z = z;pose_odomTo_map.pose.orientation.x = q_odomTo_map.x();pose_odomTo_map.pose.orientation.y = q_odomTo_map.y();pose_odomTo_map.pose.orientation.z = q_odomTo_map.z();pose_odomTo_map.pose.orientation.w = q_odomTo_map.w();pubOdomToMapPose.publish(pose_odomTo_map);global_match_state = true;}else{initializedFlag = NonInitialized;}//publish the trsformation between map and odom}

检测重定位成功后才发布匹配后的位姿

    void publishFrames(){if (cloudKeyPoses3D->points.empty())return;// publish key posespublishCloud(&pubKeyPoses, cloudKeyPoses3D, timeLaserInfoStamp, "odom");// Publish surrounding key framespublishCloud(&pubRecentKeyFrames, laserCloudSurfFromMapDS, timeLaserInfoStamp, "odom");// publish registered key frame//gc: feature pointsif (pubRecentKeyFrame.getNumSubscribers() != 0){pcl::PointCloud<PointType>::Ptr cloudOut(new pcl::PointCloud<PointType>());PointTypePose thisPose6D = trans2PointTypePose(transformTobeMapped);*cloudOut += *transformPointCloud(laserCloudCornerLastDS,  &thisPose6D);*cloudOut += *transformPointCloud(laserCloudSurfLastDS,    &thisPose6D);publishCloud(&pubRecentKeyFrame, cloudOut, timeLaserInfoStamp, "odom");}//added *****************by gcif(pubLaserCloudInWorld.getNumSubscribers() != 0 && global_match_state == true){/*std::cout << "transformTobeMapped R P Y X Y Z"<< " " << transformTobeMapped[0] << " " << transformTobeMapped[1] << " " << transformTobeMapped[2] << " " << transformTobeMapped[3] << " " << transformTobeMapped[4] << " " << transformTobeMapped[5] << std::endl;*/pcl::PointCloud<PointType>::Ptr cloudInBase(new pcl::PointCloud<PointType>());pcl::PointCloud<PointType>::Ptr cloudOutInWorld(new pcl::PointCloud<PointType>());PointTypePose thisPose6DInOdom = trans2PointTypePose(transformTobeMapped);Eigen::Affine3f T_thisPose6DInOdom = pclPointToAffine3f(thisPose6DInOdom);mtxtranformOdomToWorld.lock();PointTypePose pose_Odom_Map = trans2PointTypePose(tranformOdomToWorld);mtxtranformOdomToWorld.unlock();Eigen::Affine3f T_pose_Odom_Map = pclPointToAffine3f(pose_Odom_Map);Eigen::Affine3f T_poseInMap = T_pose_Odom_Map * T_thisPose6DInOdom;*cloudInBase += *laserCloudCornerLastDS;*cloudInBase += *laserCloudSurfLastDS;pcl::transformPointCloud(*cloudInBase, *cloudOutInWorld, T_poseInMap.matrix());publishCloud(&pubLaserCloudInWorld, cloudOutInWorld, timeLaserInfoStamp, "map");}//added *********************by gc// publish registered high-res raw cloud//gc: whole point_cloud of the scanif (pubCloudRegisteredRaw.getNumSubscribers() != 0){pcl::PointCloud<PointType>::Ptr cloudOut(new pcl::PointCloud<PointType>());pcl::fromROSMsg(cloudInfo.cloud_deskewed, *cloudOut);PointTypePose thisPose6D = trans2PointTypePose(transformTobeMapped);*cloudOut = *transformPointCloud(cloudOut,  &thisPose6D);publishCloud(&pubCloudRegisteredRaw, cloudOut, timeLaserInfoStamp, "odom");}// publish pathif (pubPath.getNumSubscribers() != 0){globalPath.header.stamp = timeLaserInfoStamp;globalPath.header.frame_id = "odom";pubPath.publish(globalPath);}}

这样,一开启软件后程序会直接执行里程计计算,然后给一个初始位姿后会进行重定位,然后定位成功后就会发布匹配后的当前激光数据了。

适当修改LIO-SAM_based_relocalization解决初始重定位显示错误相关推荐

  1. 注册表桌面显示计算机,电脑开机后不显示桌面图标怎么办?修改注册表解决开机后不显示桌面图标的3种方法...

    解决方法一: 1.按Win+R打开运行,输入regedit并回车: 2.在注册表展开:HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersi ...

  2. 微信修改文件路径后任务栏图标显示错误

    如下图,在修改了微信的文件保存路径后,图标就变成了这个样子,看着烦死了,然后我就试着卸载重装,表示并没有什么用,因为我受不了呀,然后就试 上面都是废话,嘻嘻 解决办法: 右键失效图标,点将此程序锁定到 ...

  3. (解决)mysql1366中文显示错误的终极解决方案

    在创建表格后录入数据时,数据库发生1366错误,百度后发现是中文编码问题,不过按照百度的将my.ini文件中的default-character-set改成utf8,重启后依然没有 任何作用, 使用该 ...

  4. S5PV210体系结构与接口04:代码重定位 SDRAM初始化

    目录 1. C语言环境初始化 1.1 C语言运行所需环境 1.2 初始化栈 1.2.1 栈的概念 1.2.2 栈的作用 1.2.3 如何初始化 1.3 初始化bss段 1.3.1 bss段的作用 1. ...

  5. 韦东山第一期学习笔记——重定位

    重定位 说明 必须知道的几个概念 什么是代码重定位? 什么是位置无关码 什么是运行地址 为什么要代码重定位? nand flash启动的情况 nor flash启动的情况 两种方式的重定位 代码重定位 ...

  6. 【Android 逆向】逆向修改游戏应用 ( 分析应用结构 | 定位动态库位置 | 定位动态库中的修改点 | 修改动态库 | 重打包 )

    文章目录 一.应用结构分析 二.定位动态库位置 三.定位动态库中的修改点 四.修改动态库 五.重打包 一.应用结构分析 分析上一篇博客 [Android 逆向]逆向修改游戏应用 ( APK 解析工具 ...

  7. PE文件-手工修改重定位表-WinHex-CFF Explorer

    文章目录 1.CFF Explorer 2.计算添加后的重定位大小 3.作者答疑 1.CFF Explorer   如果需要修改exe,dll等的二进制代码,遇到添加绝对地址时,需要将绝对地址的位置添 ...

  8. uboot2012(一)分析重定位

    目录 引入 环境配置 编译体验 入口查找 代码分析 board_init_f pie 内存分布分析 SP设置 board_init_f 重定位 代码段重定位实现 变量地址修改 参考 引入 关于移植,搜 ...

  9. 第四天:关看门狗、设置栈、控制icache、重定位、链接脚本

    1.汇编写启动代码:关看门狗 什么是看门狗? 看门狗(watch dog timer看门狗定时器),比如:家门口有一只狗,这个狗定时会饿(譬如两小时一饿),狗饿了就会胡乱咬人,人进进出出要想保证安全必 ...

  10. 《5.SDRAM和重定位relocate》

    转自 https://edu.csdn.net/lecturer/505 朱老师物联网大讲堂 <5.SDRAM和重定位relocate> 第一部分.章节目录 1.5.1.汇编写启动代码之关 ...

最新文章

  1. 100年前伦敦爆发的霍乱,教会了人类什么?
  2. Lync server 2010部署及解决方案
  3. spring cloud组件服务架构
  4. [系统安全] 四十六.Powershell恶意代码检测系列 (1)Powershell基础入门及管道和变量的用法
  5. [Codeforces702F]T-Shirts——非旋转treap+贪心
  6. mysql字段唯一确定_验证表里某不确定的字段的值是否唯一的方法?
  7. 【深入浅出WF】——持久化的过程
  8. 《深入理解分布式事务》第一章 事务的基本概念
  9. scala学习-11-package object
  10. 字节跳动宣布要做全网搜索,百度真正的危机来了
  11. StringBuilder 详解 (String系列之2)
  12. document.documentElement.clientWidth与document.body.clientWidth在浏览器滚动条的情况
  13. Docker(包括docker、mysql、tomcat的安装,以及部署web工程文件)
  14. 史上最详细解说!小白iriver T60拆机
  15. 软件工程电商系统数据库定义_电商数据库详细设计说明书V0.4
  16. 我与“萝卜坑”的点点滴滴
  17. 计算机专业学生参加igem,喜讯:深圳大学iGEM团队再获金奖,并获得最佳单项奖,为今年大中华地区iGEM参赛队伍最佳成绩!-深圳大学生命与海洋科学学院...
  18. openbravo erp介绍(一)
  19. matlab零阶保持器的作用,5.8 记忆模块、零阶保持器、一阶保持器
  20. Oracle数据库表空间不足 ORA-01653:unable to extend table 表名称 by 8192 in tablespace 表空间名称

热门文章

  1. 爬虫入门(1)——requests(1)
  2. 【史上最最最高仿】V2EX论坛源码—React + Golang开源库,求高手拍砖提建议~
  3. Ir_scheduler模块
  4. 科目二倒车入库学车技巧_学车必看_保过。
  5. Windows Server 2016-增强IPAM
  6. UVC之MJPEG流
  7. 服务器修改密码后任务暂停,windows server 2012 改密码后计划任务执行失败
  8. 绝不要用的 Linux 命令 !
  9. AXI_DMAC的寄存器说明
  10. Windows 下网卡对802.1Q tag 的支持