OpenCV相機標定


標簽(空格分隔): Opencv


相機標定是圖像處理的基礎,雖然相機使用的是小孔成像模型,但是由於小孔的透光非常有限,所以需要使用透鏡聚焦足夠多的光線。在使用的過程中,需要知道相機的焦距、成像中心以及傾斜因子(matlab的模型有考慮,實際中這個因子很小,也可以不考慮)。為了增加光照使用了透鏡,而使用透鏡的代價是會產生畸變,現在市面上買到的相機,都存在着或多或少的畸變。畸變的種類比較多,這里介紹常見的兩種:徑向畸變、切向畸變。相機標定就是求解相機的內參數以及畸變參數的過程。

畸變種類

(1)徑向畸變(參考自《學習opencv》412頁)
攝像頭的透鏡在傳感器的邊緣產生顯著的畸變,如下圖所示。對於徑向畸變,光學中心的畸變為-,隨着向邊緣移動,畸變會越來越嚴重。由於畸變比較小,所以可以用泰勒級數的低階項來近似。

徑向畸變

(2)切向畸變。
另外一種需要考慮的相機畸變是切向畸變,切向畸變的主要原因是透鏡本身和圖像平面不平行,如下左圖所示。切向畸變導致的結果是在成像平面上所成的像為下右圖所示。
切向畸變原因 切向畸變結果

相機的標定

相機的標定主要有兩種:傳統的攝像頭標定方法和攝像頭自標定方法,典型的有:(1)Tsai(傳統的標定方法);(2)張正友(介於傳統和自標定之間)。張正友標定方法由於簡單、效果好而得到廣泛使用。這里只介紹張正友標定方法。

  • 張正友標定法的標定步驟
    1、打印一張模板並貼在一個平面上;
    2、從不同角度拍攝若干張模板圖像;
    3、檢測出圖像中的特征點;
    4、求出攝像機的外參數(單應性矩陣)和內參數(最大似然估計) ;
    5、求出畸變系數;
    6、優化求精。

  • 理論基礎
    現在來介紹張正友標定方法中的理論知識,以饗讀者。張正友標定方法的主要思想是、
    1、相機內參矩陣

\[q=MQ \]

其中,$$
q=\left[
\begin{array}{c}
u \
v \
w
\end{array}
\right] ,\quad
M=
\left[
\begin{array}{ccc}
f_x & s & c_x \
0 & f_y & c_y \
0 & 0 & 1
\end{array}
\right],\quad
Q=\left[
\begin{array}{c}
X \
Y \
Z
\end{array}
\right]

\[ $q$的坐標系是默認的OpenCV的像素坐標系,$Q$的坐標系是標定板坐標系,Z軸為0,原點在標定板的某個內角點上(標定板上角點的坐標均為[\*,\*,0]的形式),在Open CV 3.0中使用的是($[i*Squres\_Size,j*Square\_Size,0]$的形式)。其中$f_x$和$f_y$表示相機$x$軸和$y$軸的焦距,$s$表示成像平面$x$軸和$y$軸的不正交性(OpenCV模型中把該項置為0,Matlab考慮了該項)。 2、基礎公式 對於不同位置的棋盤格到相機的成像,可以使用下面的公式進行表示: $$s\tilde{m}=A[R|t]\tilde{M}\]

其中,\([R|t]\)表示棋盤格坐標系相對於相機坐標系的位姿。把矩陣\(R\)\(\tilde{M}\)寫開,如下式所示:

\[\tilde{m}= \left[ \begin{array}{c} u \\ v \\ 1 \end{array} \right],\quad \tilde{M}= \left[ \begin{array}{c} X \\ Y \\ 0 \\ 1 \end{array} \right],\quad R=[r_1\quad r_2\quad r_3],\quad \tilde{M}= \left[ \begin{array}{c} X \\ Y \\ 0 \\ 1 \end{array} \right] \]

進行化簡得到:

\[s \left[ \begin{array}{c} u \\ v \\ 1 \end{array} \right]=A[r_1\quad r_2\quad t] \left[ \begin{array}{c} X \\ Y \\ 1 \end{array} \right] \]

其中\([u\quad v\quad 1]\)是已知量,\([X\quad Y\quad 1]\)也是已知量,\(A\)\([r_1\quad r_2 \quad t]\)是未知量。
其中\(H=A[r_1\quad r_2\quad t]\)又叫做單應性矩陣,可以使用下面的\(3\)中所述的方法求解。
3、單應矩陣求解:
這里使用的方法基於最大似然准則:假設提取的\(m\)存在均值為0,噪聲協方差矩陣為的高斯白噪聲。
則優化目標為

\[\sum_{i}(m_i-\hat{m}_i)^T\Lambda_{m_i}^{-1}(m_i - \hat{m}_i) \]

其中$$m_i= \frac{1}{\overline{h}_3^TM_i}
\left[
\begin{array}{c}
\overline{h}_1^TM_i\
\overline{h}_2^TM_i
\end{array}
\right]$$,其中\(\overline{h}_i\)是矩陣\(H\)的第\(i\)列,並且假設\(\Lambda_{m_i}=\sigma^2 I\)\(m_i\)\(M_i\)已知)
求解上面的非線性優化問題可以使用LM算法。
(1)初始值求解
\(x=[\overline{h}_1,\overline{h}_2,\overline{h}_3]\),則\(s\tilde{m}=H\tilde{M}\)可以重寫為

\[\left[ \begin{array}{ccc} \tilde{M}^T & 0^T & -u\tilde{M}^T \\ 0^T & \tilde{M}^T & -v\tilde{M}^T \end{array} \right]x=0 \]

對於\(n\)個點,對應\(n\)個方程,\(Lx=0\),其中\(x\)\(1\times 9\)的,\(L\)\(2n\times 9\)的。\(x\)的解對應於\(L\)的最小奇異值的右奇異向量。
Q:為什么用svd求了,還需要用最大似然方法來優化?svd求的\(H\)是有誤差的,需要用優化來精確求解。
4、求解相機內參
(1)利用約束條件求解內參矩陣A
在公式中,由於\(r_1\)\(r_2\)是單位向量且是正交的,所以存在下面的關系:

\[h_1^TA^{-T}A^{-1}h_2=0\\ h_1^TA^{-T}A^{-1}h_1=h_2^TA^{-T}A^{-1}h_2\]

上面的公式寫成方程組的形式如下所示:

\[\left[ \begin{array}{c} v_{12}^T \\ (v_{11}-v_{22})^T \end{array} \right] b=0 \]

上面的等式是一個最小二乘問題,可以使用SVD求解.由於A有5個參數:\(\alpha,\beta,u_0,v_0,\gamma\),一個單應性矩陣對應兩個約束,所以求解A需要3個單應性矩陣,也就是最小需要3幅圖像(超定方程)。當然,
也可以使用兩個單應性矩陣,此時需要令\(\gamma=0\)。算出了b之后,可以用下面的公式求\(A\)

\[v_0=(B_{12}B_{13}-B_{11}B_{23})/(B_{11}B_{22}-B_{12}^2)\\ \lambda=B_{33}-[B_{13}^2+v_0(B_{12}B_{13}-B_{11}B_{23})]/B_{11} \\ \alpha = \sqrt{\lambda/B_{11}}\\ \beta=\sqrt{\lambda B_{11}/(B_{11}B_{12}-B_{12}^2)} \\ \gamma= -B_{12}\alpha^2 \beta / \lambda \\ u_0 =\gamma v_0 / \beta - B_{13}\alpha^2 / \lambda \]

5、求解相機外參
在上面求解了相機的內參之后,可以求出棋盤格的位姿,公式如下:

\[r_1 = \lambda A^{-1}h_1 \\ r_2 = \lambda A^{-1}h_2 \\ r_3 = r_1 \times h_2 t = \lambda A^{-1} h_3 \]

在OpenCV中,上面的公式是用來求解優化參數的初始值的,最終的結果是使用優化的方法得到的。
由於存在誤差,還是需要迭代求解以提高精度(問題描述如下):
給定棋盤格的\(n\)個圖像和\(m\)個角點,並假設圖像點被獨立同分布的噪聲影響。
似然函數如下所示:

\[\sum_{i=1}^{n}\sum_{j=1}^{m}=\Vert m_{ij}-m(A,R_i, t_i, M_j)\Vert^2 \]

其中旋轉矩陣\(R\)用向量\(r\)表示(羅巨格公式)
6、相機的畸變參數求解
上面的討論中一直沒有引入相機畸變的問題,這里引入相機的畸變。
\((u,v)\)為理想的像素坐標,\((\breve{u},\breve{v})\)為實際觀測得到的像素坐標(受到畸變)。同樣的,有歸一化的相機坐標系\((x,y)\)\((\breve{x},\breve{y})\)
對於徑向畸變(這是張正友上的模型,泰勒展開):

\[\breve{x}=x+x[K_1(x^2+y^2)+k_2(x^2+y^2)^2]\\ \breve{y}=y+y[K_1(x^2+y^2)+k_2(x^2+y^2)^2] \]

用像素坐標表示則為:

\[\breve{u}=u+(u-u_0)[K_1(x^2+y^2)+k_2(x^2+y^2)^2]\\ \breve{v}=v+(v-v_0)[K_1(x^2+y^2)+k_2(x^2+y^2)^2] \]

寫成如下形式:

\[\left[ \begin{array}{cc} (u-u_0)(x^2+y^2) & (u-u_0)(x^2+y^2)^2\\ (v-v_0)(x^2+y^2) & (v-v_0)(x^2+y^2) \end{array} \right] \left[ \begin{array}{c} k_1 \\ k_2 \end{array} \right]= \left[ \begin{array}{c} \breve{u}-u \\ \breve{v}-v \end{array} \right] \]

給定\(n\)個圖像中的\(m\)個點,可以得到\(2mn\)個方程,記為\(Dk=d\)
\(k=(D^TD)^{-1}D^Td\)
最小二乘方法求解:

\[\sum_{i=1}^{n}\sum_{j=1}^{m}\Vert m_{ij}-\breve{m} (A,k_1,k_2,R_i,t_i,M_j)\Vert^2 \]

如果求解了畸變參數\(k_1\)\(k_2\),則可以求解出沒有畸變的坐標,從而使用上面的方法求解位姿和內參。
畸變參數\(k_1\)\(k_2\)初始化可以簡單的設為0,也可以使用后續的估計方法。
OpenCV的模型(《學習OpenCV》,這是Brown和Fryer的工作)還包括了切向畸變,並且鏡像畸變有三項。因此,opencv中一共有五個參數\([k_1,k_2,p1,p2,k_3]\)

OpenCV的標定步驟

1、初始化參數求解;
a、求解單應性矩陣;
b、根據理論的第4步求解相機內參的初始值;
c、根據理論的第5步求解相機外參的初始值;
d、畸變參數設置為0。
2、迭代求解總體最小二乘問題,也就是上面6所示的最小二乘問題。

后面會接着介紹最小二乘中的數學相關知識。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM