第1週目 ステレオマッチング


【概要】

第1週目では,3次元形状復元方法の一つである, ステレオマッチング法の実験を行う. ステレオマッチング法とは, 左右に配置された2台のカメラで撮影された2枚1組の画像を用いて, 左のカメラで撮影された画像が, 右のカメラで撮影された画像のどの部分に対応するかを面積相関の計算により求め, その対応関係を使った三角測量により,各点の3次元的位置を推測する方法である.

実際に行う作業は,左右に配置されたカメラで同じ物体を撮った2枚の画像を使い,

(1) 面積相関の計算により,左のカメラの画像の全ての点について, 右のカメラで撮った画像のどの点に対応するかを求める. 対応する点のずれ(視差と呼ぶ)を画素値とする画像を視差画像として出力する.

(2)視差画像を入力とし,左のカメラの画像の各点の3次元位置を, 三角測量の原理により計算するプログラムを作成する. 得られた3次元空間中の点の集合の様子を描画プログラムで確認する.

という2点である. どちらも,プログラムの雛形が用意されているので, それをもとに,下記の手順の解説,およびテキストを参考にしながら, 上記目的を達成するプログラムを完成させること.

プログラムは,C言語で作成すること. C言語から画像ファイルにアクセスして操作するには, TEOと呼ばれるライブラリを使用する. 画像表示にはコマンドteoeyesが用意されている.


【手順】

1.ステレオマッチング

ステレオ画像の例を図1に示す. この2枚の画像は,12cmの間隔で並んだ2台のカメラによって, 同じ対象を同時に撮影したものである. これらのカメラの輻輳角は0(右のカメラの光軸と左のカメラの光軸は平行)で, エピポーラ線は一致している (2つのカメラが画像の縦横の横方向にきっちり並んで配置されている).

遠くの背景は,2枚の画像でほぼ同じ位置に見える. しかし,手前にある物体は視差(ずれ)が大きいことに気付くだろう. つまり,視差が小さいほど遠くに,視差が大きいほど手前にあるということがわかる.

左目画像右目画像

図1:サンプル画像

入力画像をそれぞれの画素値を値にもつ2次元の配列と見たとき, 同じ行における点の対応関係を求めるときに, その点の画素の比較だけでは結果が非常に不安定になってしまう. そこで,面積相関法では,注目している画素の周りの面 (ウィンドウとよぶ)で比較し, その面中の点それぞれについて左右の画像中で差をとり, その合計がもっとも小さいものを対応点とする. 図2においてその例を示す. ここで,エピポーラ線が一致していることから, 対応点を探すときは,ウインドウの縦方向は同じ高さに固定し, 横方向のみをずらしながら探索すればよい. ここで,2つのカメラの輻輳角が0であるので, 左目画像からみた右目画像の対応点は, すべて左目画像のものより左側にあること に注意すること(無限遠であれば同じ位置).

図2:面積相関法

具体的計算の手順を以下に詳しく述べる. 左のカメラで撮った画像を Ileftとし, 横方向にx番目,縦方向にy番目の画素の明るさを Ileft[x][y]とする. 同様に,右のカメラの画素の明るさを Iright[x][y]とする. 面積相関の計算は,左の画像の画素 Ileft[x][y]と, 右の画像上でその画素から左にdずれた画素 Iright[x-d][y]を比較をすることになる. つまり,

m/2m/2
ΣΣ | Ileft[x+i][y+j] - Iright[x+i-d][y+j] |
i=-m/2j=-m/2

を計算し,これが最も小さくなるdを探す.dが求めたい視差である.

カラー画像の場合には,R,G,B値(赤成分,緑成分,青成分)があるため, 色成分毎に差の絶対値を算出し,総和を求める. つまり,左画像の横方向にx番目,縦方向にy番目の画素のR,G,B値を, それぞれ IleftR[x][y], IleftG[x][y], IleftB[x][y]とする. 同様に,右画像の画素のR,G,B値を,それぞれ IrightR[x][y], IrightG[x][y], IrightB[x][y]とする. ウインドウ内の差分は

Σ Σ ( | IleftR[x+i][y+j] - IrightR[x+i-d][y+j] | + | IleftG[x+i][y+j] - IrightG[x+i-d][y+j] | + | IleftB[x+i][y+j] - IrightB[x+i-d][y+j] | )

となる.

ウインドウの中の画素値が完全に一致していれば, 最小値は0になる(実際にそのようなことはまず起きない). ウインドウのサイズは,小さすぎると誤対応が多くなり, 大きすぎるとエッジ(境界部)がぼけるなどの問題が生じる. 本来はシーンにあわせて適切に設定すべきであるが, 本実験では m=9(つまり9×9の窓の大きさ)と固定する.

一方,視差の範囲(対応点を探す幅)を広くしすぎると,誤対応が増えるばかりでなく, 対応点を探す処理時間も増える.シーンの奥行きの幅と, 2台のカメラ間の距離(基線長)から,視差の最小値と最大値が決まる. 本実験では,効率よく,そして精度良く対応点を求めるために, 予め与えられた視差の範囲を用いる.

実験で用いる画像

以下のステレオ画像のうち,最低4組の画像組を選んで実験すること. ステレオ法は万能ではなく,安定して精度良く距離計測できるシーンと, 誤対応のために不安定になるシーンがある. 以下のステレオ画像は,それぞれ何らかの意味がある. 予想を立てて画像組を選択し,予想通りの結果が得られたかどうかを検証すること.

img00_左画像 img01_左画像 img02_左画像 img03_左画像
img00_右画像 img01_右画像 img02_右画像 img03_右画像
視差:1-55 視差:10-35 視差:30-135 視差:30-135
img04_左画像 img05_左画像 img06_左画像 img07_左画像
img04_右画像 img05_右画像 img06_右画像 img07_右画像
視差:20-65 視差:30-65 視差:1-60 視差:1-40

サンプルソース

TEOライブラリを用いたプログラムの雛形が用意されている. 以下のソースとメイクファイルをダウンロードし, これを書き換えながら実験を進めると良い.

2.三角測量による位置検出

次に,先ほどの結果を元に,三角測量による位置検出をおこなう.三角測量のモ デルを図3に示す.ここでは,左のカメラ画像の中心を空間座標の原点として, 左のカメラ画像のそれぞれの画素の3次元位置を求める.まずは,2次元的に考 えてみよう(図4).ここで,図4は3次元の光線をXZ平面(以下,カメラの 左右方向をX,カメラの上下方向をY,カメラの前後方向をZとする)に正射影 したものである.

図3:三角測量 図4:簡略図

ここで,カメラの視野角が横方向に70度であることを情報と して与えておく必要がある.カメラの受光素子では,70度の画角を640画素に 等間隔に分けていることになる.図5に示すとおり,第i画素の角度γは arctan(tan35°(320-i)/320)となる.図から明らかなように,図4のαはα=γ +90°で与えられる.左のカメラの第i画素に写っているものが,右のカメラ では第i-d画素に写っているのであるから,右カメラについて,左カメラのγに 相当する角度δはarctan(tan35°(320-(i-d))/320)となる.上と同様に考えると, β=180°−(δ+90°)=90°−δが得られる.αとβが分かると,r は正弦定理

r/sinβ=12/sin(180°-α-β)

より得ることができる.rとαを用いれば,左カメラの第i画素,右カメラの第 i-d画素で捉えている点について,左カメラ位置を原点としたX座標とZ座標を求 めることができる.

図5 αの求め方

次に,残りのもう1次元(Y方向)を考慮に入れよう.このカメラは縦横比3: 4であるので,図6のように,画像のY方向の第j画素の角度φはarctan( tan35°× 3/4×(240-i)/240)となる.以上で得られたr,α,φを使うと,画素(i,j)に写っ た点について,左カメラを原点とし,Y方向を加えた3次元座標値が最終的にも とまる.

図6 Y座標の求め方

なお,プログラムを書く際には,定数(例えば320)を書く際には小数点をつける(320.0のように)ことを忘れると,割り算で余りを切り捨てる計算になり,おかしな結果が出ることがあるから気をつけること.また,Cでは三角関数は引数は「度」ではなくradを想定している点も注意する必要がある.

(x,y,z)を出力した後,復元された3次元形状データを見るには, gl3Dviewを用いる.

実行方法

 % gl3Dview 距離画像 テクスチャ画像(左画像)