ORB_SLAM2的单目SLAM提高关键帧的个数

一、前言

最近在结合ORB_SLAM2和Map2DFusion,来做无人机航拍视频建图,基本完成了pipeline,但发现出来的效果没有Map2DFusion官方的效果好。

ORB_SLAM2的单目SLAM提高关键帧的个数_第1张图片   ORB_SLAM2的单目SLAM提高关键帧的个数_第2张图片

(第一张图是我自己处理的效果,在一些地方可以看到明显断层;第二张图是官方的效果)

我有一个想法,能不能通过提高ORB_SLAM2关键帧的个数来改善建图?

于是我开始调研如何增加ORB_SLAM2关键帧的个数。

二、调研

ORB_SLAM2的Tracking线程的NeedNewKeyFrame()函数中会经过四个条件判断,来决定是否添加关键帧:

const bool c1a = mCurrentFrame.mnId>=mnLastKeyFrameId+mMaxFrames;
const bool c1b = (mCurrentFrame.mnId>=mnLastKeyFrameId+mMinFrames && bLocalMappingIdle);
const bool c1c =  mSensor!=System::MONOCULAR && (mnMatchesInliers15);
if((c1a||c1b||c1c)&&c2)
{
    ...增加关键帧...
}

我用一个单目的视频(25fps)来测试,发现一个规律:

  • c1a的值一直为0
  • c1b的值0多1少(由于mMinFrames=0,c1b本质上取决于bLocalMappingIdle。即LocalMapping线程空闲的时候,c1b = 1)
  • c1c的值一直为0(因为单目系统,这个值被置为0)
  • c2的值1多0少。(c2的判断条件是:(当前帧的跟踪点数 < 90%的参考关键帧跟踪点数 )  而且  ( 当前帧跟踪点数 > 15 ) )

我试过调整这些条件,尝试增加关键帧个数。但实际上没法做到稳定增加关键帧个数。

之后,我发现再LocalMapping线程中,有一个去除冗余关键帧的函数:KeyFrameCulling(),正是这个函数阻止了增加过多的关键帧。

KeyFrameCulling()会将那些有90%的点能够被超过三个关键帧观察到的帧认为是冗余帧,并去除。

三、实际操作

1. 在NeedNewKeyFrame(),把

if((c1a||c1b||c1c)&&c2)

改为

if(c1a)

因为mMaxFrames的数值是fps的缘故,c1a的判断相当于每1s产生一个关键帧

2. 注释掉LocalMapping线程中的KeyFrameCulling()函数,即不用剔除冗余关键帧。

四、效果

经过这两点操作后,ORB_SLAM2产生的关键帧数量大大增加,从原来的355个增加到698个(使用同一个视频做测试)。

如下图所示,第一张是原本ORB_SLAM2产生的关键帧效果(一个蓝色的框代表一个关键帧),第二张是更改过代码后产生的关键帧效果,可以看到关键帧变了密集了不少。

ORB_SLAM2的单目SLAM提高关键帧的个数_第3张图片ORB_SLAM2的单目SLAM提高关键帧的个数_第4张图片

五、后续

虽然增加了关键帧个数,可还是没办法提高Map2DFusion的建图效果,只能另找其他突破口了......

你可能感兴趣的:(SLAM)