examples/poc_real_tless_6dof.py は、PrimeSense Carmine 1.09 の実測深度を点群へ戻し、法線推定、RANSAC による作業台除去、Euclidean clustering、Point Pair Features、ICP を順に適用します。BOP toolkit は使わず、BOP JSON、16-bit depth PNG、ASCII PLY、対称性を自前で読みます。
BOP の一次配布ページの T-LESS 欄は license: CC BY 4.0 と明記しています。このため再配布と派生物の公開が可能です。データはリポジトリに含めず、tools/fetch_tless.py が外部キャッシュへ取得します。
取得した公式 LFS オブジェクトは次のとおりです。
| ファイル | bytes | SHA-256 |
|---|---|---|
tless_base.zip |
49,597 | dd70ca884b7c471a530a952f70c5ab2c212f3d2c2f371be86397442b97d70a7e |
tless_models.zip |
33,468,762 | 6a29c59766b8d2af05e62e71739f0ca7243ad81bc3c7f9a24925504a8cb37928 |
tless_test_primesense_bop19.zip |
825,276,992 | 1a18f6bbfb5ac4ced8529f7a35225adfed88c0f62ef38067933e2b541ef1d00b |
BOP19 test_primesense の全20場面から、各場面に含まれる画像IDの最小値を決定的に1枚選びました。visib_fract >= 0.50 の全対象を採点したため、標本は20場面・132対象です。公開ベースラインは全テスト画像の値であり、この20画像 subset と同一標本の直接対決ではありません。
MSSD は物体径の 0.05d..0.50d、MSPD は 5..50 px の10閾値で recall を平均しました。PoC は VSD を計算しないため、公式ARは出しません。
Python 3.11で、同じ20場面・132対象に主経路だけを通しました。秒/対象は場面準備、PPFモデル構築、投票、ICP、採点を含む壁時計時間です。系列 ごとに基準行を再掲したため11設定です。密度以外の掃引は、10秒/対象以内で最も良かった1000/1000点・2 mmを固定して一変量ずつ振りました。
| 系列 | model点 | scene点 | voxel mm | ref_fraction | angle bins | ICP反復 | AR_MSSD | AR_MSPD | 秒/対象 |
|---|---|---|---|---|---|---|---|---|---|
| 密度 | 180 | 160 | 6 | 0.25 | 24 | 50 | 0.162 | 0.185 | 0.254 |
| 密度 | 500 | 500 | 3 | 0.25 | 24 | 50 | 0.180 | 0.213 | 1.423 |
| 密度 | 1000 | 1000 | 2 | 0.25 | 24 | 50 | 0.196 | 0.217 | 8.380 |
| 密度 | 2000 | 2000 | 2 | 0.25 | 24 | 50 | — | — | >54.6 |
| ref | 1000 | 1000 | 2 | 0.25 | 24 | 50 | 0.196 | 0.217 | 8.380 |
| ref | 1000 | 1000 | 2 | 0.50 | 24 | 50 | 0.201 | 0.233 | 15.068 |
| ref | 1000 | 1000 | 2 | 1.00 | 24 | 50 | 0.195 | 0.230 | 33.080 |
| angle | 1000 | 1000 | 2 | 0.25 | 24 | 50 | 0.196 | 0.217 | 8.380 |
| angle | 1000 | 1000 | 2 | 0.25 | 30 | 50 | 0.195 | 0.221 | 8.793 |
| ICP | 1000 | 1000 | 2 | 0.25 | 24 | 50 | 0.196 | 0.217 | 8.380 |
| ICP | 1000 | 1000 | 2 | 0.25 | 24 | 100 | 0.197 | 0.220 | 8.291 |
2000/2000点は全体を2時間走らせても完走せず、場面単位の再試行もscene 1の4対象だけで31分を超えたため打ち切りました。時間の下限は全体試行の 7204秒 / 132対象 > 54.6秒/対象 です。ARは一部標本から外挿せず未記録としました。
採用設定は1000/1000点、voxel 2 mm、ref_fraction=0.25、angle_bins=24、ICP 100反復です。10秒/対象以内の行で AR_MSSD が最大の0.197だったためです。0.5参照は0.201まで上がりましたが15.068秒/対象で上限外でした。
| 方法 | official AR | AR_MSSD | AR_MSPD |
|---|---|---|---|
| Fullseye PPF+ICP、採用設定1000/1000点(20場面・132対象) | — | 0.197 | 0.220 |
| Fullseye PPF+ICP、間引き180/160点(同じ20場面・132対象) | — | 0.162 | 0.185 |
| Fullseye PPF+ICP、クラスタなし1000点(20場面・132対象) | — | 0.111 | 0.113 |
| Fullseye PPF+ICP(前回2場面・10対象) | — | 0.290 | 0.320 |
| Drost-CVPR10-3D-Only(公式全test) | 0.444 | 0.478 | 0.480 |
| Vidal-Sensors18(公式全test) | 0.538 | 0.575 | 0.574 |
密度を上げると実機 AR_MSSD は0.162から0.197へ改善しました。したがって0.162をPPF自体の限界とは扱いません。一方、採用設定でも公開値を下回ります。ただし公開値は公式全test、PoCは固定20画像subsetで、同一標本の直接対決ではありません。
同じモデルと真値姿勢から作った理想 z-buffer 深度は0.985/0.985で、合成から実機への低下はMSSD 0.788、MSPD 0.765でした。ICPを外すと0.346/0.338、法線の符号をカメラ向きに揃えないと0.132/0.161です。ICPなしが良いのは、現行の局所refineが誤った大域仮説を別の局所解へ寄せる対象があるためで、次便の検討対象です。
クラスタ分割なしでは、平面除去後の場面点群全体を1000点へ決定的に間引き、各モデルを直接 surface_match しました。ARは0.111/0.113で、180/160点時の0.064/0.054からは改善しましたが、対象ごとの点を集中して残すクラスタありの0.197/0.220には届きませんでした。
ppf.py は全対距離行列を一括生成していません。しかし、ppf_model はモデルの各基準点について全点との差分を作り、Pythonの二重ループで全順序対をハッシュ辞書へ格納します。surface_match も ref_fraction × scene点数² の場面点対を走査し、各ハッシュ一致に入ったモデル候補列をPythonで一件ずつ投票します。形状によって大きなバケットができるため、2000点では単純な二乗増加以上に遅くなる対象がありました。
この便ではPPF本体を変更していません。次便ではモデル記述子の再利用、法線品質、dist_step の量子化、投票の正規化とバケット分布を調べます。
失敗は MSSD > 0.2d です。内訳の5列は失敗対象だけを数え、カテゴリ間の重複を許します。結合 は複数真値対象を同じクラスタへ割り当てた数、遮蔽 は可視率0.8未満、薄型 は厚さ/径0.45未満、欠測 は可視マスク内の欠測depthが1%超、対称 は対称変換を持つ対象です。
| obj_id | 件数 | AR_MSSD | AR_MSPD | 失敗 | 結合 | 遮蔽 | 薄型 | 欠測 | 対称 |
|---|---|---|---|---|---|---|---|---|---|
| 1 | 17 | 0.088 | 0.112 | 15 | 7 | 1 | 0 | 6 | 15 |
| 2 | 9 | 0.100 | 0.178 | 9 | 4 | 1 | 0 | 2 | 9 |
| 3 | 8 | 0.175 | 0.212 | 6 | 2 | 0 | 0 | 0 | 6 |
| 4 | 13 | 0.200 | 0.277 | 10 | 6 | 1 | 0 | 2 | 10 |
| 5 | 4 | 0.100 | 0.050 | 4 | 0 | 0 | 0 | 2 | 4 |
| 6 | 2 | 0.750 | 0.700 | 0 | 0 | 0 | 0 | 0 | 0 |
| 7 | 5 | 0.200 | 0.080 | 4 | 0 | 1 | 4 | 2 | 4 |
| 8 | 3 | 0.100 | 0.000 | 3 | 1 | 1 | 3 | 3 | 3 |
| 9 | 5 | 0.340 | 0.300 | 3 | 0 | 0 | 3 | 1 | 3 |
| 10 | 3 | 0.000 | 0.000 | 3 | 0 | 0 | 0 | 0 | 3 |
| 11 | 4 | 0.050 | 0.150 | 4 | 0 | 0 | 0 | 0 | 4 |
| 12 | 3 | 0.200 | 0.267 | 3 | 0 | 0 | 0 | 0 | 3 |
| 13 | 3 | 0.000 | 0.033 | 3 | 2 | 0 | 0 | 1 | 3 |
| 14 | 3 | 0.467 | 0.533 | 2 | 1 | 0 | 0 | 0 | 2 |
| 15 | 3 | 0.233 | 0.267 | 2 | 1 | 0 | 0 | 1 | 2 |
| 16 | 4 | 0.325 | 0.350 | 3 | 2 | 0 | 0 | 1 | 3 |
| 17 | 3 | 0.533 | 0.533 | 1 | 0 | 0 | 0 | 0 | 1 |
| 18 | 3 | 0.467 | 0.400 | 2 | 1 | 0 | 0 | 2 | 0 |
| 19 | 4 | 0.250 | 0.300 | 3 | 1 | 0 | 0 | 2 | 3 |
| 20 | 4 | 0.075 | 0.125 | 4 | 1 | 0 | 0 | 2 | 4 |
| 21 | 3 | 0.233 | 0.300 | 2 | 1 | 0 | 0 | 1 | 0 |
| 22 | 3 | 0.267 | 0.300 | 2 | 0 | 0 | 0 | 1 | 0 |
| 23 | 5 | 0.200 | 0.180 | 4 | 1 | 0 | 4 | 2 | 4 |
| 24 | 4 | 0.325 | 0.350 | 3 | 0 | 0 | 0 | 1 | 3 |
| 25 | 2 | 0.200 | 0.300 | 2 | 0 | 0 | 0 | 1 | 2 |
| 26 | 2 | 0.000 | 0.000 | 2 | 1 | 0 | 0 | 1 | 2 |
| 27 | 1 | 0.000 | 0.000 | 1 | 0 | 1 | 1 | 0 | 1 |
| 28 | 4 | 0.300 | 0.275 | 4 | 1 | 2 | 4 | 0 | 4 |
| 29 | 2 | 0.150 | 0.100 | 2 | 0 | 0 | 2 | 2 | 2 |
| 30 | 3 | 0.167 | 0.300 | 3 | 1 | 0 | 0 | 0 | 3 |
全体では109/132対象が失敗し、重複内訳は結合34、遮蔽8、薄型21、欠測36、対称103でした。
| scene | 最初のimage | 対象 | cluster | AR_MSSD | AR_MSPD | 失敗 |
|---|---|---|---|---|---|---|
| 1 | 1 | 4 | 6 | 0.125 | 0.225 | 4 |
| 2 | 3 | 3 | 5 | 0.500 | 0.367 | 1 |
| 3 | 5 | 5 | 8 | 0.320 | 0.440 | 4 |
| 4 | 0 | 4 | 5 | 0.325 | 0.250 | 4 |
| 5 | 7 | 5 | 6 | 0.140 | 0.180 | 4 |
| 6 | 2 | 5 | 13 | 0.160 | 0.140 | 4 |
| 7 | 3 | 8 | 9 | 0.362 | 0.350 | 5 |
| 8 | 1 | 5 | 8 | 0.500 | 0.600 | 2 |
| 9 | 0 | 12 | 13 | 0.300 | 0.400 | 8 |
| 10 | 5 | 6 | 9 | 0.300 | 0.383 | 4 |
| 11 | 4 | 4 | 7 | 0.225 | 0.200 | 3 |
| 12 | 2 | 6 | 7 | 0.383 | 0.417 | 4 |
| 13 | 2 | 7 | 5 | 0.129 | 0.114 | 7 |
| 14 | 2 | 6 | 14 | 0.050 | 0.000 | 6 |
| 15 | 1 | 5 | 9 | 0.140 | 0.160 | 5 |
| 16 | 8 | 8 | 10 | 0.175 | 0.212 | 7 |
| 17 | 3 | 7 | 24 | 0.000 | 0.043 | 7 |
| 18 | 2 | 7 | 19 | 0.114 | 0.114 | 6 |
| 19 | 1 | 9 | 10 | 0.167 | 0.156 | 8 |
| 20 | 3 | 16 | 2 | 0.000 | 0.013 | 16 |
採用判定に使った主経路の掃引実行は1094.47秒、132対象で8.291秒/対象でした。合成、ICPなし、未整理法線、クラスタなしを同時に取る診断実行は、全照合と採点を終えて図生成へ入るまで約7189.2秒でした。この診断用総時間は採用上限の秒/対象には使いません。
py -3.11 tools/fetch_tless.py
py -3.11 examples/poc_real_tless_6dof.py
$env:FULLSEYE_TLESS_SWEEP='density_1000_1000_v2'
py -3.11 examples/poc_real_tless_6dof.py
CIなどデータが無い環境では取得を始めず、PoCに固定した RECORDED を表示します。図を所定の場所へ再生成する場合だけ FULLSEYE_FIGURE_DIR=docs/articles/assets/poc/poc_real_tless_6dof を設定します。
01_pose_overlay.png: 推定姿勢(橙)と公開真値(青)。代表図。02_rgb_depth.png: 実RGBと実機depth。03_mssd_by_object.png: 20場面をobj_idごとに平均したAR_MSSD。棒上に値と件数。04_synthetic_vs_real.png: 横軸を合成MSSD、合成MSPD、実機MSSD、実機MSPDの文字ラベルにした比較。05_failure.png: 20場面でMSSDが最大だった失敗例。06_density_vs_ar_time.png: scene点数に対するAR_MSSD(左軸)と秒/対象(右軸)。