今回はフォトグラメトリ設備を作っているという話!
kimakuriは服をアバターに着せ替えるサービスなのでの3Dスキャンや顔の3Dスキャンにフォトグラメトリ設備があると大変嬉しいです。
ということで作ってみてました。
フォトグラメトリとは
たくさんの写真から共通点を抽出して立体情報を取得して、3Dモデルを生成するやつのこと

↓立体化

フォトグラメトリの流れ
たくさん写真をとる
↓
ソフトに流し込む
(RealityCaptureがとんでもなくよい)
↓
エクスポートしてBlenderにいれてよしなにする
たくさん写真をとる方法
1つのカメラで被写体のまわりをうろうろしながらたくさん写真をとる
- 無生物かつ静物に効く
- カメラ1つでいいので機材が安上がり
- 一瞬でとれない
たくさんのカメラで囲んで撮る
- 一瞬で撮れる
- 人間などでも、一瞬で撮れれば静物と同じなので立体化できる
たくさんのカメラで囲んでとれば簡単に人間を3Dモデル化できる!
…はずでした…
戦いの歴史
Windowsマシン + Webカメラ

てはじめにWindwosマシン+Webカメラで
フォトグラメトリ設備を構築しました
これだけ世の中にマシンがあるし、そろそろいろいろ整備されて簡単セットアップなはずでしょう
ハードウェアの壁
たくさん接続できない!
- USBハブで接続するのにはかなり低い限界がある
- 運が良くいいマザボつかってても1マシンにせいぜい6個ぐらいしかつなげない
たくさん接続できるマシンを作る

マイニング用マザーボードでマシンを構築しました。
- グラボをめちゃめちゃ積むためにPCIeスロットがいっぱいついている!
- PCIe USB Hubをめちゃめちゃいっぱいつける
- オンボードCPUつきで3万ぐらい
- m.2 SSD 4000円ぐらいでやすい
- やすい
- すごい
- やすい
ソフトウェアの壁
カメラ制御が全然簡単じゃない!!
- OpenCVでPythonでやればよいのでは?
- 解像度指定とかホワイトバランス・露出固定とか全然できない!
- Unityをつかってみる
- 解像度指定もできる!
- 複数カメラも使える!
- ホワイトバランス・露出固定できない!
ホワイトバランス・露出固定とは?
フォトグラメトリは写真の色から推定するものです。
- 撮影条件が全然違うと写真の色味が全然違ってしまうので推定できません
- ホワイトバランスや露出設定が違うと色味が全然違って全然推定できません
→ホワイトバランス・露出固定は必須!
しかたないからUWPアプリ
UWP=Universal Windows Platformアプリ
- フォームアプリの次のWindowsアプリのフレームワーク
- WebCamを深くいじろうとするとこれしかないっぽい
- 正直かなりめんどくさい気持ち!
がんばりました

しかし大きな問題が。
全然一瞬で撮影できてない!
USBカメラの問題点
- いっぱい接続できない
- 一度に撮れない!
- 1 USB Hubのカメラを全部起動すると帯域不足で落ちる
- PCIe Hubも1Hub 1つじゃないと同時起動無理
- 一個ずつ切り替えて撮ると大変時間がかかる
- 一周分32個ぐらい全部撮ると一分とかかかる
- これで人間を撮るのはちょっと無理
カメラをたくさんつかうには制御マシン自体がたくさん必要
アプローチ
- マイニングマザーボードで作ったマシンをいくつも増やす
-高い
- 高い
- 高い
- ネットワーク連携ソフトとかもかかなきゃいけない
- めんどくさい
- ラズパイで制御する
- ラズパイを全くいじったことがなかったのでカメラがほんとうに使えるのかどうか?からわからりませんでした
とりあえず実験
拍子抜けするほど簡単でした
中身はただのLinux。
USBカメラもカメラモジュールも超簡単に制御できました
Windowsでソフトごりっっごりに書いたのは一体なんだったのだろうか…
Raspberry PIで実装してみた


ハードウェア構成
- Raspberry PI 3 model B+
- 有線LAN接続
とりあえず最低構成でやる、ということで、1ラズパイに4カメラ接続でやってみました。
ラズパイ側ソフトウェア構成
- fswebcam
- ラズパイに用意されてるカメラを簡単に使えるナイスなソフト
- カメラ部分コーディング全くいりませんでした!
- django + restframework
- サーバープログラムを起動しておいて、リクエストがきたら撮影するようにしました
- ストックしておくこともできるし、そのままデータを取得することもできる
webアプリ開発の経験が生きましたね!
クライアント側ソフトウェア構成
Node.jsでいろいろ書きました。非同期実行が大変速くさすがでした。
Pythonだとおそすぎて、非同期の仕様上10倍以上差がでてしまいました。
- サーバーをサーチするもの
- ローカルネットワークのアドレスを全部叩いてサーバーを確認
- キャプチャリクエストを全部に送るもの
- 全部から画像を取得するもの
(雑感)Node.js vs Python(クライアントサイド)
- Node.jsの非同期関数は、実行する全部並列して走って一瞬で実行されて大変よい感じでした。
- コールバック関数で記述するのが簡単
- 標準httpライブラリで直で書くとエラー処理がデリケートすぎてしんどい
- バッチ処理的なスクリプトなのであまり依存関係とかインストールの手間を増やしたくなかったので
- 基本非同期なので、エラー処理ミスって戻らないと本当にずっとプログラムがかえってこない
- Pythonの非同期は内部の同期箇所とかを待てしまう
→ 一瞬で並列してリクエスト投げたいときはNode.js!
ということで撮影したのが冒頭の画像です


これで一瞬でフォトグラメトリだ!
…とはいきませんでした
問題点
- 全然一瞬じゃない
- 1ラズパイに4個もカメラつないでるのでやっぱり遅延があります
遅い~~~~~~!!!
ぜんぜんたりない~~~~!!!!

全く撮れていない後ろ姿
Next Step!!
Raspberry PI ZERO WHとカメラモジュールを使用して120台カメラユニットを作る
全身+顔フォトグラメトリを今度こそしたい~~~~!!!
めっちゃ大変ですが今度こそケリをつけたいですね。