読者です 読者をやめる 読者になる 読者になる

EM-ICPによる点群間の位置合わせをwindowsで動かす

概要

Kinectを始めとする、低価格の距離センサの出現によるPointCloudの処理は最近ホットです。 最近だと、日本でも点群処理のビジネス活用を推進するポイントクラウドコンソーシアムが発足しています。

ある点群と別の点群のマッチングはこの分野の伝統的で、尚且つ大事な処理の1つです。(写真で言うと、何枚かの写真を合成して、パノラマ写真を作るようなもの)これを点群処理では位置合わせ(registration)と呼びます。
このアルゴリズムとしては古来よりICP(Iterate Closet Point)が有名です。 原理などの説明は下記リンクから読むと、非常に分かりやすいです。 http://derivecv.tumblr.com/post/25762361937

こういった点群間のregistrationでGPGPU(CUDA)でめっちゃ速くて良い物としてEM-ICPと言うのがあります。 http://home.hiroshima-u.ac.jp/tamaki/study/cuda_softassign_emicp/

github で公開されていて、コードもコンパクト、依存ライブラリも少なく、ライブラリ固有の前提知識も少ないので、興味が湧いた人はすぐ試すことが出来ます。
ただ、基本的にLinuxを想定していて残念ながらwindowsは非対応だったので、折角なのでforkしてwindows版を作ってみました。
VS2012 Pro,Windows 8.1(x64)で動作確認済み
https://github.com/neon-izm/cuda_emicp_softassign

f:id:izm_11:20140514230900g:plain

是非これを機に点群処理に興味を持ってもらえる(そしてPointCloud関連情報が増える)と、とても嬉しいです。

以下は僕の行った作業メモと、使い方等の説明です。

用意する物

やった作業

VS2012で適当にプロジェクトを作成

ソースを一式プロジェクトに追加します。

CLAPACK,freeglutを追加

過去のコミットcuda_emicp_softassign rev0.1 から引っ張ってきて、プロジェクト設定を行います。 CLAPACKは線形代数ライブラリ、freeglutは可視化する為のOpenGLラッパーです。

CUDAの設定

CUDA 6.0の NVIDIA CUDA Getting Started Guide の既存プロジェクトへのCUDA追加  を参考にVS2012上で設定 (v6.0からはVS2012でそのまますんなり設定出来て素晴らしい!5.0とか5.5の頃はVS2012で使うときはバッドノウハウがあった気がします)

デバッグ引数で適当なパラメータを指定

今回のwindows向けで、動作確認を容易にするため、仮にコマンドライン引数を与えています。

-ply -pointFileX=./data/bun000.ply -pointFileY=./data/bun045.ply -pointsReductionRate=5 -em_icp

別のファイルを読み込んだり、registrationのアルゴリズムを切り替える時等は、適宜変更してください。

使い方

VS2012でビルドしてそのままデバッグ無しで開始出来ます。
マウス左ドラッグでカメラの回転
qキーでregistrationの開始
exeへの引数を変えることで、softassignやCUDAではなく、cpuでの実行に変えられるので、速度や収束について検討出来ます。詳しくはREADMEを参照下さい。

他の点群で試すには

KinectFusion等で手軽に3Dスキャンは出来ます(そしてメッシュのobjファイルも作れます) それを例えば meshlab http://meshlab.sourceforge.net/ で余分な点群を削除したり、頂点数を削減して plyでexportすれば、別のモデルで追試出来ます。 得意な形状や、そうでない物などを確認出来ます。

ハマったこと

CLAPACKのlib

debugでもreleaseでも、どちらでもdがついていないlibを使います(例えばblasd.lib ではなくblas.lib)

rply.cのply_open()

引数が"rb"になっているが、(linuxmacではなく)windowsだと"r"にしないと改行コードの関係でplyファイルを読んでくれないです。(forkした版では変更済)

cuファイルの項目の種類

既存のプロジェクトにCUDAを追加した場合、 ちゃんとCUDAのファイルだとコンパイラに教える必要があります。

f:id:izm_11:20140515000001p:plain