0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫(xiě)文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

OpenCV實(shí)時(shí)彎道檢測(cè)(詳細(xì)步驟+源碼)

新機(jī)器視覺(jué) ? 來(lái)源:新機(jī)器視覺(jué) ? 2023-06-11 11:28 ? 次閱讀


			導(dǎo)讀本文主要介紹如何使用 Python 和 OpenCV實(shí)現(xiàn)一個(gè)實(shí)時(shí)曲線道路檢測(cè)系統(tǒng)。(公眾號(hào):OpenCV與AI深度學(xué)習(xí)

99f5a90a-0793-11ee-962d-dac502259ad0.gif

背景介紹

在任何駕駛場(chǎng)景中,車(chē)道線都是指示交通流量和車(chē)輛應(yīng)行駛位置的重要組成部分。這也是開(kāi)發(fā)自動(dòng)駕駛汽車(chē)的一個(gè)很好的起點(diǎn)!在我之前的車(chē)道檢測(cè)項(xiàng)目的基礎(chǔ)上,我實(shí)現(xiàn)了一個(gè)曲線車(chē)道檢測(cè)系統(tǒng),該系統(tǒng)工作得更好,并且對(duì)具有挑戰(zhàn)性的環(huán)境更加穩(wěn)健。車(chē)道檢測(cè)系統(tǒng)是使用 OpenCV 庫(kù)用 Python 編寫(xiě)的。下面是實(shí)現(xiàn)步驟:
  • 畸變校正
  • 透視變換
  • Sobel濾波
  • 直方圖峰值檢測(cè)
  • 滑動(dòng)窗口搜索
  • 曲線擬合
  • 覆蓋檢測(cè)車(chē)道
  • 應(yīng)用于視頻

畸變矯正

相機(jī)鏡頭扭曲入射光以將其聚焦在相機(jī)傳感器上。盡管這對(duì)于我們捕捉環(huán)境圖像非常有用,但它們最終往往會(huì)稍微不準(zhǔn)確地扭曲光線。這可能導(dǎo)致計(jì)算機(jī)視覺(jué)應(yīng)用中的測(cè)量不準(zhǔn)確。然而,我們可以很容易地糾正這種失真。我們可以使用棋盤(pán)格來(lái)標(biāo)定相機(jī)然后做畸變校正:

9a843e5e-0793-11ee-962d-dac502259ad0.png

測(cè)試視頻中使用的相機(jī)用于拍攝棋盤(pán)格的 20 張照片,用于生成畸變模型。我們首先將圖像轉(zhuǎn)換為灰度,然后應(yīng)用cv2.findChessboardCorners()函數(shù)。我們已經(jīng)知道這個(gè)棋盤(pán)是一個(gè)只有直線的二維對(duì)象,所以我們可以對(duì)檢測(cè)到的角應(yīng)用一些變換來(lái)正確對(duì)齊它們。用cv2.CalibrateCamera()來(lái)獲取畸變系數(shù)和相機(jī)矩陣。相機(jī)已校準(zhǔn)!

然后,您可以使用它cv2.undistort()來(lái)矯正其余的輸入數(shù)據(jù)。您可以在下面看到棋盤(pán)的原始圖像和校正后的圖像之間的差異:

9a9afad6-0793-11ee-962d-dac502259ad0.png

實(shí)現(xiàn)代碼:

def undistort_img():
    # Prepare object points 0,0,0 ... 8,5,0
    obj_pts = np.zeros((6*9,3), np.float32)
    obj_pts[:,:2] = np.mgrid[0:9, 0:6].T.reshape(-1,2)
    # Stores all object points & img points from all images
    objpoints = []
    imgpoints = []
    # Get directory for all calibration images
    images = glob.glob('camera_cal/*.jpg')
    for indx, fname in enumerate(images):
        img = cv2.imread(fname)
        gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
        ret, corners = cv2.findChessboardCorners(gray, (9,6), None)
        if ret == True:
            objpoints.append(obj_pts)
            imgpoints.append(corners)
    # Test undistortion on img
    img_size = (img.shape[1], img.shape[0])
    # Calibrate camera
    ret, mtx, dist, rvecs, tvecs = cv2.calibrateCamera(objpoints, imgpoints, img_size, None,None)
    dst = cv2.undistort(img, mtx, dist, None, mtx)
    # Save camera calibration for later use
    dist_pickle = {}
    dist_pickle['mtx'] = mtx
    dist_pickle['dist'] = dist
    pickle.dump( dist_pickle, open('camera_cal/cal_pickle.p', 'wb') )
def undistort(img, cal_dir='camera_cal/cal_pickle.p'):
    #cv2.imwrite('camera_cal/test_cal.jpg', dst)
    with open(cal_dir, mode='rb') as f:
        file = pickle.load(f)    mtx = file['mtx']
    dist = file['dist']
    dst = cv2.undistort(img, mtx, dist, None, mtx)
    return dst
undistort_img()
img = cv2.imread('camera_cal/calibration1.jpg')
dst = undistort(img) # Undistorted image

這是應(yīng)用于道路圖像的失真校正。您可能無(wú)法注意到細(xì)微的差異,但它會(huì)對(duì)圖像處理產(chǎn)生巨大影響。

9ab9574c-0793-11ee-962d-dac502259ad0.png

透視變換

在相機(jī)空間中檢測(cè)彎曲車(chē)道并不是很容易。如果我們想鳥(niǎo)瞰車(chē)道怎么辦?這可以通過(guò)對(duì)圖像應(yīng)用透視變換來(lái)完成。這是它的樣子:

9adbbd5a-0793-11ee-962d-dac502259ad0.png

注意到什么了嗎?通過(guò)假設(shè)車(chē)道位于平坦的 2D 表面上,我們可以擬合一個(gè)多項(xiàng)式,該多項(xiàng)式可以準(zhǔn)確地表示車(chē)道空間中的車(chē)道!這不是很酷嗎?

您可以使用cv2.getPerspectiveTransform()函數(shù)將這些變換應(yīng)用于任何圖像,以獲取變換矩陣,并將cv2.warpPerspective()其應(yīng)用于圖像。下面是代碼:

def perspective_warp(img,
                     dst_size=(1280,720),
                     src=np.float32([(0.43,0.65),(0.58,0.65),(0.1,1),(1,1)]),
                     dst=np.float32([(0,0), (1, 0), (0,1), (1,1)])):
    img_size = np.float32([(img.shape[1],img.shape[0])])
    src = src* img_size
    # For destination points, I'm arbitrarily choosing some points to be
    # a nice fit for displaying our warped result
    # again, not exact, but close enough for our purposes
    dst = dst * np.float32(dst_size)
    # Given src and dst points, calculate the perspective transform matrix
    M = cv2.getPerspectiveTransform(src, dst)
    # Warp the image using OpenCV warpPerspective()
    warped = cv2.warpPerspective(img, M, dst_size)
    return warped

Sobel濾波

在之前的版本中,我使用顏色過(guò)濾掉了車(chē)道線。然而,這并不總是最好的選擇。如果道路使用淺色混凝土代替瀝青,道路很容易通過(guò)彩色濾光片,管道會(huì)將其感知為白色車(chē)道線,此方法不夠穩(wěn)健。

相反,我們可以使用類(lèi)似于邊緣檢測(cè)器的方法,這次過(guò)濾掉道路。車(chē)道線通常與道路具有高對(duì)比度,因此我們可以利用這一點(diǎn)。之前版本 1 中使用的Canny邊緣檢測(cè)器利用Sobel 算子來(lái)獲取圖像函數(shù)的梯度。OpenCV 文檔對(duì)它工作原理有很好的解釋。我們將使用它來(lái)檢測(cè)高對(duì)比度區(qū)域以過(guò)濾車(chē)道標(biāo)記并忽略道路。

我們?nèi)詫⒃俅问褂?HLS 色彩空間,這一次是為了檢測(cè)飽和度和亮度的變化。sobel 算子應(yīng)用于這兩個(gè)通道,我們提取相對(duì)于 x 軸的梯度,并將通過(guò)梯度閾值的像素添加到表示圖像中像素的二進(jìn)制矩陣中。這是它在相機(jī)空間和車(chē)道空間中的樣子:

9b0ecace-0793-11ee-962d-dac502259ad0.png

9b4f1b88-0793-11ee-962d-dac502259ad0.png

請(qǐng)注意,遠(yuǎn)離相機(jī)的圖像部分不能很好地保持其質(zhì)量。由于相機(jī)的分辨率限制,來(lái)自更遠(yuǎn)物體的數(shù)據(jù)非常模糊和嘈雜。我們不需要專(zhuān)注于整個(gè)圖像,所以我們可以只使用它的一部分。這是我們將使用的圖像的樣子(ROI):

9b7e5290-0793-11ee-962d-dac502259ad0.png

直方圖峰值檢測(cè)

我們將應(yīng)用一種稱(chēng)為滑動(dòng)窗口算法的特殊算法來(lái)檢測(cè)我們的車(chē)道線。但是,在我們應(yīng)用它之前,我們需要為算法確定一個(gè)好的起點(diǎn)。如果它從存在車(chē)道像素的位置開(kāi)始,它會(huì)很好地工作,但是我們?nèi)绾问紫葯z測(cè)這些車(chē)道像素的位置呢?其實(shí)很簡(jiǎn)單!

我們將獲得圖像相對(duì)于 X 軸的直方圖。下面直方圖的每個(gè)部分都顯示了圖像每列中有多少個(gè)白色像素。然后我們?nèi)D像每一側(cè)的最高峰,每條車(chē)道線一個(gè)。這是直方圖的樣子,在二值圖像旁邊:

9b98146e-0793-11ee-962d-dac502259ad0.png

9bb9a106-0793-11ee-962d-dac502259ad0.png

滑動(dòng)窗口搜索

滑動(dòng)窗口算法將用于區(qū)分左右車(chē)道邊界,以便我們可以擬合代表車(chē)道邊界的兩條不同曲線。

算法本身非常簡(jiǎn)單。從初始位置開(kāi)始,第一個(gè)窗口測(cè)量有多少像素位于窗口內(nèi)。如果像素?cái)?shù)量達(dá)到某個(gè)閾值,它將下一個(gè)窗口移動(dòng)到檢測(cè)到的像素的平均橫向位置。如果沒(méi)有檢測(cè)到足夠的像素,則下一個(gè)窗口從相同的橫向位置開(kāi)始。這一直持續(xù)到窗口到達(dá)圖像的另一邊緣。

落在窗口內(nèi)的像素被賦予一個(gè)標(biāo)記。在下圖中,藍(lán)色標(biāo)記的像素代表右側(cè)車(chē)道,紅色標(biāo)記的像素代表左側(cè):

9bdab706-0793-11ee-962d-dac502259ad0.png

曲線擬合

項(xiàng)目的其余部分非常簡(jiǎn)單。我們分別使用 對(duì)紅色和藍(lán)色像素應(yīng)用多項(xiàng)式回歸np.polyfit(),然后檢測(cè)器就完成了!

這是曲線的樣子:

9bf527bc-0793-11ee-962d-dac502259ad0.png

繪制檢測(cè)車(chē)道

這是檢測(cè)系統(tǒng)的最后一部分,用戶(hù)界面!我們只需創(chuàng)建一個(gè)覆蓋層來(lái)填充檢測(cè)到的車(chē)道部分,然后我們最終可以將其應(yīng)用于視頻。一旦應(yīng)用于視頻檢測(cè),您應(yīng)該會(huì)看到以下輸出:

9c013c96-0793-11ee-962d-dac502259ad0.gif

結(jié)論

就是這樣,一個(gè)基本的彎曲車(chē)道檢測(cè)器!它比以前的版本好得多,它甚至可以處理彎曲的車(chē)道!但是,它仍然會(huì)在一定程度上受到陰影和道路紋理劇烈變化的影響。在我的下一個(gè)車(chē)道檢測(cè)項(xiàng)目中,我們將使用一些機(jī)器學(xué)習(xí)技術(shù)來(lái)開(kāi)發(fā)一個(gè)非常強(qiáng)大的車(chē)道和車(chē)輛檢測(cè)系統(tǒng),謝謝!

完整代碼:

https://github.com/kemfic/Curved-Lane-Lines/blob/master/P4.ipynb

參考鏈接:

https://www.hackster.io/kemfic/curved-lane-detection-34f771


聲明:本文內(nèi)容及配圖由入駐作者撰寫(xiě)或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問(wèn)題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • 檢測(cè)器
    +關(guān)注

    關(guān)注

    1

    文章

    868

    瀏覽量

    47733
  • 機(jī)器學(xué)習(xí)

    關(guān)注

    66

    文章

    8428

    瀏覽量

    132835
  • OpenCV
    +關(guān)注

    關(guān)注

    31

    文章

    635

    瀏覽量

    41419

原文標(biāo)題:實(shí)戰(zhàn)|OpenCV實(shí)時(shí)彎道檢測(cè)(詳細(xì)步驟+源碼)

文章出處:【微信號(hào):vision263com,微信公眾號(hào):新機(jī)器視覺(jué)】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。

收藏 人收藏

    評(píng)論

    相關(guān)推薦

    樹(shù)莓派上使用OpenCV和Python實(shí)現(xiàn)實(shí)時(shí)人臉檢測(cè)

    本文介紹了如何在樹(shù)莓派上,使用 OpenCV 和 Python 完成人臉檢測(cè)項(xiàng)目。該項(xiàng)目不僅描述了識(shí)別人臉?biāo)枰木唧w步驟,同時(shí)還提供了很多擴(kuò)展知識(shí)。此外,該項(xiàng)目并不需要讀者了解詳細(xì)
    的頭像 發(fā)表于 03-06 09:00 ?5.1w次閱讀

    OpenCV3編程入門(mén)-源碼例程全集-canny邊緣檢測(cè)

    OpenCV3編程入門(mén)-源碼例程全集-canny邊緣檢測(cè),感興趣的小伙伴們可以瞧一瞧。
    發(fā)表于 09-18 16:27 ?2次下載

    OpenCV3編程入門(mén)-源碼例程全集-OpenCV開(kāi)發(fā)環(huán)境的配置

    OpenCV3編程入門(mén)-源碼例程全集-OpenCV開(kāi)發(fā)環(huán)境的配置,感興趣的小伙伴們可以瞧一瞧。
    發(fā)表于 09-18 16:27 ?20次下載

    OpenCV3編程入門(mén)-源碼例程全集-Harris角點(diǎn)檢測(cè)

    OpenCV3編程入門(mén)-源碼例程全集-Harris角點(diǎn)檢測(cè)
    發(fā)表于 09-18 16:38 ?1次下載

    OpenCV3編程入門(mén)-源碼例程全集-Shi-Tomasi角點(diǎn)檢

    OpenCV3編程入門(mén)-源碼例程全集-Shi-Tomasi角點(diǎn)檢測(cè)
    發(fā)表于 09-18 16:38 ?1次下載

    OpenCV3編程入門(mén)-源碼例程全集-點(diǎn)追蹤

    OpenCV3編程入門(mén)-源碼例程全集-點(diǎn)追蹤
    發(fā)表于 09-18 16:38 ?0次下載

    OpenCV3編程入門(mén)-源碼例程全集-播放視頻

    OpenCV3編程入門(mén)-源碼例程全集-播放視頻
    發(fā)表于 09-17 22:54 ?18次下載

    OpenCV3編程入門(mén)-源碼例程全集-人臉識(shí)別

    OpenCV3編程入門(mén)-源碼例程全集-人臉識(shí)別
    發(fā)表于 09-17 22:55 ?2次下載

    OpenCV3編程入門(mén)-源碼例程全集-模板匹配

    OpenCV3編程入門(mén)-源碼例程全集-模板匹配
    發(fā)表于 09-17 22:55 ?4次下載

    凸包檢測(cè)基礎(chǔ)_OpenCV3編程入門(mén)-源碼例程全集

    OpenCV3編程入門(mén)-源碼例程全集-凸包檢測(cè)基礎(chǔ),感興趣的小伙伴們可以瞧一瞧。
    發(fā)表于 09-18 16:55 ?0次下載

    亞像素級(jí)角點(diǎn)檢測(cè)_OpenCV3編程入門(mén)-源碼例程

    OpenCV3編程入門(mén)-源碼例程全集-亞像素級(jí)角點(diǎn)檢測(cè),感興趣的小伙伴們可以瞧一瞧。
    發(fā)表于 09-18 16:55 ?1次下載

    邊緣檢測(cè)綜合示例_OpenCV3編程入門(mén)-源碼例程

    OpenCV3編程入門(mén)-源碼例程全集-邊緣檢測(cè)綜合示例,感興趣的小伙伴們可以瞧一瞧。
    發(fā)表于 09-18 17:02 ?0次下載

    用光流法進(jìn)行運(yùn)動(dòng)目標(biāo)檢測(cè)_OpenCV3編程入門(mén)-源碼例程

    OpenCV3編程入門(mén)-源碼例程全集-用光流法進(jìn)行運(yùn)動(dòng)目標(biāo)檢測(cè),感興趣的小伙伴們可以瞧一瞧。
    發(fā)表于 09-18 17:02 ?17次下載

    OpenCV的混合高斯背景模型源碼程序免費(fèi)下載

    本文檔的主要內(nèi)容詳細(xì)介紹的使用OpenCV的混合高斯背景模型源碼程序免費(fèi)下載
    發(fā)表于 10-18 11:55 ?5次下載

    qt opencv opencl opengl源碼例程

    qt-opencv-opencl-opengl-源碼例程
    發(fā)表于 09-27 14:42 ?1次下載