基於消失點的相機自動標定

as you seen,在一些場景下,比如交通監控、道路參數獲取、港口碼頭監控等,需要將相機架設在高處,此時,鑑於複雜的場景環境,基於傳統的相機標定方法--即鋪設標定板,利用張正友或者Tsai標定方法進行標定,是不現實的。(通俗的說:總不能在馬路上擺個標定板,告訴來往的車輛:你等一下,我拍二十張照片你再走,哦,不行,這個角度不行,那個棋盤格角點虛焦了要重拍,你再等一下,估計沒標定完,也會被羣毆或者被交警抓起來了)。所以,需要開發一套適用於複雜場景的、不需要任何輔助合作目標(比如標定物)的標定方案。


首先,需要準備以下基礎知識:

1、科普一下正交消失點的概念。

消失點的概念搞視覺的應該都懂,就是兩條平行的直線經透視變換會相交成一點。入門知識,在此不展開。在本方案中,正是用到了三個方向、正交的消失點。

struct VashingPoints

{

  cv::Point2d vp1;

  cv::Point2d vp2;

   cv::Point2d vp3;

};

VP1表示第一個VP,車輛運動方向。

VP2表示第二個VP,地平面中垂直於車輛運動方向,即與VP1垂直。

VP3表示第三個VP,垂直於地平面。

 

2、需要回顧一下相機的成像模型,即小孔成像原理。入門知識,在此不展開。


下面,貼一下VP1及VP2的檢測流程

VP1檢測流程--手寫版,viso沒激活

對VP2的檢測使用菱形空間的概念。 假設許多車輛邊緣與第二個VP重合開始,它們在積累空間投票。

使用背景邊緣模型檢測移動車輛上的邊緣。

模型每幀都會更新,以處理陰影和其他緩慢的變化。

背景模型用B1 = H1初始化,然後用公式(1)更新Bt,其中平滑係數接近1,此處a = 0.95。

                                   Bt=αBt-1 +(1-α)Ht                   公式(1)

Keys:a:<第一個消失點用於約束第二個消失點的位置>

         b:<邊緣檢測採用canny邊緣檢測算法>

         c:採用<級聯霍夫變換>及平行空間理論

         d:必須滿足以下篩選條件:

1、必須由Canny邊緣檢測器檢測。

2、該點屬於背景的置信度必須低於預定值閾值(t2),即屬於前景(移動車輛)。

3、梯度的大小必須高於預定閾值t1。

4、梯度的方向不能與VP1方向一致,也不得垂直於基線。

5、假設場景近似水平,具有公差水平(±45°)。


求解內參代碼

cv::Mat TrafficCalibrationFromVP::getIntrinsicMat(cv::Point2d vp1, cv::Point2d vp2, cv::Point2d pp)
{
	CalibrationInfos calinfos;
	calinfos.focal = double(sqrt(-(vp1 - pp).dot(vp2 - pp)));//叉乘:.cross
	calinfos.IntrinsicMat = (Mat_<double>(3, 3) << calinfos.focal, 0, pp.x, 0, calinfos.focal, pp.y, 0, 0, 1);
	return calinfos.IntrinsicMat;
}

 

求解vp3代碼

void TrafficCalibrationFromVP::getVP3(cv::Point2d vp1, cv::Point2d vp2, cv::Point2d pp,double focal, cv::Point2d& vp3)
{
	cv::Point3d V1world(vp1.x, vp1.y, focal);
	cv::Point3d V2world(vp2.x, vp2.y, focal);
	cv::Point3d PPworld(pp.x, pp.y, 0);
	cv::Point3d V3world = (V1world - PPworld).cross(V2world - PPworld);
	vp3.x = V3world.x / V3world.z*focal+pp.x;
	vp3.y = V3world.y / V3world.z*focal+pp.y;
	//cout << vp3 << endl;
}

未完待更新……

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章