前言
雙目立體視覺,由兩個攝像頭組成,像人的眼睛能看到三維的物體,獲取物體長度、寬度資訊,和深度的資訊;單目視徑訓取二維的物體資訊,即長度、寬度,
1)雙目攝像頭
常見的雙目攝像頭有以下幾款:

能看到不同型別的雙目攝像頭,左攝像頭和右攝像頭之間的距離不一樣,
2)雙目相機基線
基線越大,測量范圍越遠;基線越小,測量范圍越近,

建議:
- (1)基線距B是作業距離的08-2.2倍時測量誤差比較小;
- (2)雙目立體視覺的結構對稱時,測量系統的誤差比較小,精度也比較高,
- (3)兩臺相機的有效焦距∫越大,視場越小,視覺測量系統的測量精度越高(即采用長焦距鏡頭容易獲得較高的測量精度)
出自博士論文 基于雙目視覺的空間非合作目標姿態測量技術研究.顏坤
3)打開雙目攝像頭
在OpenCV用使用雙目攝像頭,包括:打開單目攝像頭、設定攝像頭引數、拍照、錄制視頻,
環境
編程語言:Python3 主要依賴庫:OpenCV3.x 或 OpenCV4.x
雙目同步攝像頭,兩個鏡頭共用一個設備ID,左右攝像機同一頻率,這款攝像頭解析度支持2560*960或以上,

思路流程
1、由于兩個鏡頭共用一個設備ID,打開攝像頭時使用cv2.VideoCapture()函式,只需打開一次,區別有的雙目攝像頭是左右鏡頭各用一個設備ID,需要打開兩次cv2.VideoCapture(0),cv2.VideoCapture(1),
2、雙目攝像頭的總解析度是由左右鏡頭組成的,比如:左右攝像機總解析度1280x480;分割為左相機640x480、右相機640x480

為了方便理解畫了張草圖;圖中的“原點”是影像像素坐標系的原點,
3、分割后,左相機的解析度:高度 0:480、寬度 0:640
右相機的解析度:高度 0:480、寬度 640:1280
4、轉換為代碼后
# 讀取攝像頭資料
ret, frame = camera.read()
#裁剪坐標為[y0:y1, x0:x1] HEIGHT * WIDTH
left_frame = frame[0:480, 0:640]
right_frame = frame[0:480, 640:1280]
cv2.imshow("left", left_frame)
cv2.imshow("right", right_frame)
源代碼
舉個栗子:打開解析度1280x480的雙目攝像頭
# -*- coding: utf-8 -*-
import cv2
import time
AUTO = False # 自動拍照,或手動按s鍵拍照
INTERVAL = 2 # 自動拍照間隔
cv2.namedWindow("left")
cv2.namedWindow("right")
camera = cv2.VideoCapture(0)
# 設定解析度 左右攝像機同一頻率,同一設備ID;左右攝像機總解析度1280x480;分割為兩個640x480、640x480
camera.set(cv2.CAP_PROP_FRAME_WIDTH,1280)
camera.set(cv2.CAP_PROP_FRAME_HEIGHT,480)
counter = 0
utc = time.time()
folder = "./SaveImage/" # 拍照檔案目錄
def shot(pos, frame):
global counter
path = folder + pos + "_" + str(counter) + ".jpg"
cv2.imwrite(path, frame)
print("snapshot saved into: " + path)
while True:
ret, frame = camera.read()
# 裁剪坐標為[y0:y1, x0:x1] HEIGHT*WIDTH
left_frame = frame[0:480, 0:640]
right_frame = frame[0:480, 640:1280]
cv2.imshow("left", left_frame)
cv2.imshow("right", right_frame)
now = time.time()
if AUTO and now - utc >= INTERVAL:
shot("left", left_frame)
shot("right", right_frame)
counter += 1
utc = now
key = cv2.waitKey(1)
if key == ord("q"):
break
elif key == ord("s"):
shot("left", left_frame)
shot("right", right_frame)
counter += 1
camera.release()
cv2.destroyWindow("left")
cv2.destroyWindow("right")
補充理解
OpenCV有VideoCapture()函式,能用來定義“攝像頭”物件,0表示第一個攝像頭(一般是電腦內置的攝像頭);如果有兩個攝像頭,第二個攝像頭則對應VideoCapture(1),
在while回圈中使用“攝像頭物件”的read()函式一幀一幀地讀取攝像頭畫面資料,
imshow函式是顯示攝像頭的某幀畫面;cv2.waitKey(1)是等待1ms,如果期間檢測到了鍵盤輸入q,則退出while回圈,
效果

4)雙目測距
原理
視差disparity
極線約束
極線校正/立體校正
雙目測距流程:
- a.雙目標定
- b.雙目矯正
- c.立體匹配
- d.雙目測距(三角測量)
- e.測距效果
原理
通過對兩幅影像視差的計算,直接對影像所拍攝到的范圍進行距離測量,無需判斷前方出現的是什么型別的障礙物,

視差disparity
首先看一組視覺圖:左相機圖和右相機圖不是完全一致的,通過計算兩者的差值,形成視差,生成視差圖(也叫:深度圖)

- 視差是同一個空間點在兩個相機成像中對應的x坐標的差值;
- 它可以通過編碼成灰度圖來反映出距離的遠近,離鏡頭越近的灰度越亮;

我們觀察一下,看到臺燈在前面,離雙目相機比較近,在灰度圖呈現比較亮;攝影機及支架在后方,離雙目相機比較遠,在灰度圖呈現比較暗,
補充理解:
由立體視覺系統測量的深度被離散成平行平面 (每個視差值一個對應一個平面)

給定具有基線 b 和焦距 f 的立體裝備, 系統的距離場受視差范圍[dmin ,dmax]的約束,
極線約束
極線約束(Epipolar Constraint)是指當空間點在兩幅影像上分別成像時,已知左圖投影點p1,那么對應右圖投影點p2一定在相對于p1的極線上,這樣可以極大的縮小匹配范圍,

標準形式的雙目攝像頭,左右相機對齊,焦距相同,

如果不是標準形式的雙目攝像頭呢?哦,它是是這樣的:(需要 極線校正/立體校正)

極線校正/立體校正

雙目測距流程:
- 相機標定(獲取內參+外參)
- 雙目矯正(矯正鏡頭變形影像)
- 雙目立體匹配(生成視差圖 Disparity map)
- 計算深度資訊(生成深度圖 Depth map)
- 計算距離
a.雙目標定
主要是獲取內參(左攝像頭內參+右攝像頭內參)、外參(左右攝像頭之間平移向量+旋轉矩陣)
標定程序:

詳細程序請參考:雙目視覺 標定+矯正 (基于MATLAB)
b.雙目矯正
消除鏡頭變形,將立體相機對轉換為標準形式

c.立體匹配
尋找左右相機對應的點(同源點)

d.雙目測距(三角測量)
給定視差圖、基線和焦距,通過三角計算在3D中對應的位置

雙目測距原理

C++版代碼請參考:雙目 機器視覺-- 測距
Python版代碼:看看大家情況,如果需要的,我抽時間完成分享給大家(BM、SGBM演算法等)
e.測距效果

彩蛋:雙目立體匹配(重點)
立體匹配是雙目立體視覺中比較重要的一環,往往這里做研究和優化,

a.立體匹配流程

b.匹配代價計算
代價函式用于計算左、右圖中兩個像素之間的匹配代價(cost), cost越大,表示這兩個像素為對應點的可能性越低,

常用代價函式
- AD/BT
- AD+Gradient
- Census transform
- SAD/SSD
- NCC
- AD+Census
- CNN
c.立體匹配

端到端視差計算網路
? Disp-Net (2016)
? GC-Net (2017)
? iRestNet (2018)
? PSM-Net (2018)
? Stereo-Net (2018)
? GA-Net (2019)
? EdgeStereo (2020)
\
立體視覺方法評測網站
ETH3D https://www.eth3d.net/
Kitti Stereo http://www.cvlibs.net/datasets/kitti/eval_scene_flow.php?benchmark=stereo
Middlebury Stereo 3.0 https://vision.middlebury.edu/stereo/eval3/

如果大家對端到端視差計算網路感興趣,需要開源代碼跑通教程和介紹,也考慮分享大家,主要看大家意愿了,
雙目測距總結
優勢
(1)成本比單目系統要高,但尚處于可接受范圍內,并且與激光雷達等方案相比成本較低;
(2)沒有識別率的限制,因為從原理上無需先進行識別再進行測算,而是對所有障礙物直接進行測量;
(3)直接利用視差計算距離,精度比單目高;
(4)無需維護樣本資料庫,因為對于雙目沒有樣本的概念,
難點
(1)計算量大,對計算單元的性能要求高,這使得雙目系統的產品化、小型化的難度較;(芯片或FPGA)
(2)雙目的配準效果,直接影響到測距的準確性;
(3)對環境光照非常敏感;(光照角度、光照強度)
(4)不適用于單調缺乏紋理的場景;(天空、白墻、沙漠)
(5)相機基線限制了測量范圍,(基線越大,測量范圍越遠;基線越小,測量范圍越近)
參考文獻
1)[Wang 2015] Wang W, Yan J, Xu N, et al. Real-time high-quality stereo vision system in FPGA. IEEE Transactions on Circuitsand Systems for Video Technology, 2015, 25(10): 1696-1708.2)
2)[Kim 2016] K.-R. Kim and C.-S. Kim. Adaptive smoothness constraints for efficient stereo matching using texture and edgeinformation. ICIP 2016.
3)[Zbontar 2016] Zbontar J, LeCun Y. Stereo matching by training a convolutional neural network to compare image patches.Journal of Machine Learning Research, 2016.
4)[Park 2017] Park H, Lee K M. Look wider to match image patches with convolutional neural networks. IEEE Signal ProcessingLetters, 2017.
5)Leonid Keselman, et al. Intel R RealSenseTM Stereoscopic Depth Cameras. CVPRW. 2017.
6)立體匹配演算法原理與應用.奧比研究院.徐玉華
7)基于雙目視覺的空間非合作目標姿態測量技術研究.顏坤
8)https://www.bilibili.com/video/BV1ka4y1L7xT?from=search&seid=5727123941116684431
9)https://blog.csdn.net/u011808673/article/details/90641589 10)https://www.cnblogs.com/polly333/p/5130375.html
文章中如有錯誤請指出,歡迎交流~~
作者宣告:本篇文章,未經許可,謝絕轉載,
雙目測距的Python版代碼:看看大家情況,如果需要的,我抽時間寫一下分享給大家(BM、SGBM演算法等)
如果大家對端到端的視差計算網路感興趣,需要開源代碼跑通教程和介紹,也考慮分享大家,主要看大家意愿了,
其實雙目測距+目標檢測,就可以輸出目標的類別、置信度、距離、長度、寬度等資訊,
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/271979.html
標籤:其他
