VINS-Mono: A Robust and Versatile Monocular Visual-Inertial State Estimatorは単眼カメラで最も大きい弱点である実スケールでの環境マップ生成という課題をIMUとの融合で解決する手法です。iOS用の環境が提供されているので、iPhone 11で動作させてみましたので、その手順を説明します。ソースコードはここにあります。
まず、~/gitで下記を実行してソースコードをGitからクローンします。
$ cd ~/git
$ git clone https://github.com/HKUST-Aerial-Robotics/VINS-Mobile.git
$ cd ~/git/VINS-Mobile
次に、boostをインストールします。
$ ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
$ brew install boost
OpenCVをここからダウンロードして、VINS_ThirdPartyLib以下にopencv2.frameworkディレクトリを作成し、ダウンロードしたZIPファイルをそこに展開します。展開後の内容は下記のようになります。
$ ls ./VINS_ThirdPartyLib/opencv2.framework/
Resources headers opencv2 versions
ここからはXcodeでの作業です。XcodeでVINS_ios.xcodeprojを開きます。
Xcodeのメニューで [Product]-[Scheme]-[Edit Scheme]でScheme編集画面を開き左側ウィンドウで[Run]を選択し、[Info]タブを選択、[Build Configuration]で[Release]を選択します。
対象デバイスとして私はiPhone11を選択しました。iPhone11はこのプロジェクトの対象外デバイスなので無理矢理下記の修正をして、対象としました。
global_param.cpp
switch (device) { case iPhone11: printf("Device iPhone11 param"); FOCUS_LENGTH_X = 1445.7809; FOCUS_LENGTH_Y = 1445.7809; PX = 959.4973; PY = 719.6924; SOLVER_TIME = 0.06; FREQ = 3; TIC_X = 0.0; TIC_Y = 0.092; TIC_Z = 0.01; return true; break;
global_param.hpp
enum DeviceType { iPhone11, iPhone7P, iPhone7, iPhone6sP, iPhone6s, iPadPro97, iPadPro129, unDefine };
ViewController.mm
if(([device compare:@"iPhone12,1"] == NSOrderedSame)) { printf("Device iPhone11"); device_type = iPhone11; } else if(([device compare:@"iPhone9,1"] == NSOrderedSame) || ([device compare:@"iPhone9,3"] == NSOrderedSame)) { printf("Device iPhone7"); device_type = iPhone7; }
デバイスのコード定義については、このページが参考になります。
上記のiPhone11のカメラの焦点距離などのいわゆるカメラの内部パラメータは、ARCamera::intrinsicで取得しました。
これで準備が整ったので、ビルドして実行します。実行した結果が下記です。iPhoneを動かすと特徴点が現在のフレームと直前のキーフレームとの視差に応じして赤から青に変化した色の点で表示されます。視差30ピクセルを100%として、100%の特徴点は赤色で0%に近づくにつれて青色で表示されています。画面右側には視差(PARALLAX)や特徴点数(FEATURE)などの情報が表示されています。
[2020年6月9日追記]
上記のコードで何度か実行してみたのですが、全然Initializeが完了しないので、いろいろとトライした結果を追記します。
まず、根本的な問題としてストーリーボード上のレイアウトがiPhone11にあっていなかったので、上記のBUFから下にも部品があるのに表示されていませんでした。Constraintsを修正して、なんとか表示できるように修正しました。
次が、iPhone11カメラの内部パラメータ(Intrinsic)がおかしいようです。パラメータを調べたのですが、情報が得られなかったので、とりあえずiPhone11の広角カメラはiPhone7と焦点距離などは同じなので、ひとまず下記の通りiPhone7と同じ値に設定したところ、無事にInitializeは完了出来ました。ソースは下記の通りです。ストーリボードでのレイアアウト修正については、一般的なiOSプログラミング技術なので詳細は割愛させていただきます。
case iPhone11: printf("Device iPhone11 param "); FOCUS_LENGTH_X = 526.600; FOCUS_LENGTH_Y = 526.678; PX = 243.481; PY = 315.280; // FOCUS_LENGTH_X = 1445.7809; // FOCUS_LENGTH_Y = 1445.7809; // PX = 959.4973; // PY = 719.6924 ;
この設定で何とかInitializationが完了して、下記のようにVINSで軌跡を取ることができました。結構正確に自己位置推定してループクローズまで出来ました。
あと、画面の[AR][VINS]を選択する部品(UISegmentedControl)が上図のように選択されている方が青色にならないので、下図のようにプロパティを変更しました。