#차선인식 #OpenCV #영상처리 #차선곡률 #자율주행
[0] 개요: 자율주행 프로젝트에서 카메라를 이용한 차선 인식을 학부생 기간 동안 연구했다. 이 부분에 대해서 공유하려고 이 글을 썼어. 코드에 관한 부분은 추후 깃허브를 통해 업로드한다. 다음 글은 이론적인 부분을 쓴다고 보면 된다.
실제 최근 진행되고 있는 차선 인식 연구는 딥러닝 기반으로 이뤄지고 있다. Feature 기반의 차선 인식 프로세스는 old한 방식에 한계도 많이 존재한다. 대표적으로 다음과 같다.
#1. 조도에 따른 차선색 검출치를 매번 변경해야 한다는 점 #2. 도로폭에 따라 ROI 영역을 다르게 부여해야 한다는 점 #3. 정확한 곡률 추종에 한계가 있어 급격한 커브 구간에서 탈선하는 경우가 발생한다.
그럼에도 해당 프로세스를 우리 플랫폼에 적용하려는 이유는 다음과 같다.플랫폼에서 이미 object detection 문제를 풀기 위해 Yolov4를 돌리고 있지만 같이 돌리면 리소스가 한정적이어서 시스템 다운이 될 것 같다는 점, 훈련이 번거롭다는 점이다.
[1] 파이프라인: 필자의 차선 인식 프로세스는 다음 순서로 이루어진다.카트리가 제공하는 강의 차선인식 파이플라인에 학교 수업이었던 영상처리로 배운 전공 지식을 더했다.

단계 1. Camera Calibration을 가지고 있는 카메라에서 영상처리를 적용하기 위해서는 카메라 내/외부 파라미터를 구해야 한다. 이 파라미터를 구하려면 Python에서 제공하는 몇 가지 함수를 사용하여 사용하는 카메라에서 Checkerboardimage를 취득한 후 적용하면 된다. 이 내의 외부 파라미터를 가지고 있으면 왜곡을 보정할 수 있다.(왜곡 보정과 Calibration은 별개이다.)

아래 사진을 보면 검정색과 blinding 되어 있는 영역은 왜곡된 것을 확인할 수 있는데, 이는 광각 카메라를 사용할 경우 쉽게 확인할 수 있다. 이를 보정하면 왜곡에 대한 부분이 사라지게 될 것이다.적용할 경우 원본 이미지에서 에지 영역이 잘려 보이는 현상을 확인할 수 있는데, 이는 위의 설명이 그 이유라고 보면 된다.
주의: resize 하기 전의 원본 이미지를 Calibration 해야 한다.
step 2. ROI 지정 후 Personal pectivetransformation 왜곡이 보정된 이미지는 다음에 사용자 임의로 4개의 ROI 점을 지정한 후 Personal pectivetransformation을 적용하여 Bird-eye-viewimage로 전환한다. 이 과정을 다른 논문에서는 bird-eye-view Conversion이라고도 부른다. 상당히 많은 연산량을 차지하고 있다.

여기서 나중에 말하지만 우리가 취할 ROI 4점의 실제 거리를 측정하면 이를 perspectivetransformation을 적용하면 픽셀당 몇 m인지 확인할 수 있다. 이는 나중에 Localmap 기반의 Purepursuits 횡제어, 곡률 기반의 PID 종제어에 적용하기 위해 필요한 task이다.
예를 들어 우리가 잡으려는 ROI 4점이 가로 4m 세로 3m이고 우리가 resize하는 이미지가 600×400이라면 가로는 1pixel로 4m/600으로 환산할 수 있다.
Perspevtivetransformation은 쉽게 말해 우리가 가진 4가지 점을 각각 우리가 원하는 점으로 이동시키는 것으로 보면 된다. 4개의 ROI점을 각각 재정의하는 화면의 꼭짓점으로 이동시키면 그 안의 점은 perspectivetransformation 변환 행렬을 통해 적절한 위치로 이동하게 된다. 이렇게 새가 바닥을 보는 듯한 bird-eye-viewimage가 만들어진다.
영상처리 수업에서는 해당 변환을 하기 전에 선행하는 단계의 변환이 있는데, 이는 아래와 같다. 참고하기 바란다.
Step3. Filtering 다음은 realword 이미지를 우리가 원하는 차선만을 골라내기 위한 filtering 작업에 대해 설명한다. 사실 filtering에 대한 부분은 정답이 없다. 파이썬에서 제공하는 filter를 이것저것 바꿔가며 적용하면서 본인의 사양에 맞는 만큼 분산값을 설정하고 추가적인 filter를 적용하거나 빼야 한다. 따라서 concept만 catch해 나가면 된다.
검은 아스팔트 도로 위에 우리가 원하는 차선인 흰색과 노란색 선을 뽑기 위해서는 어떤 방법이 있을까.전공 지식을 안다면 선이라는 것은 색깔이 급격히 변하는 것이라고도 생각할 수 있고, 혹은 자체인 특정 색에 대한 정보를 포함하고 있기 때문에 이를 착안하여 필터링하면 좋을 것이다.
이를 위해 Gradient를 추출한 필터링 결과와 황색 백선을 추출한 필터링 결과를 정합하는 것으로 시작한다.
(1) Gradient 추출 번역하면 경사도를 의미한다. (edge와는 다른) 급격히 변하는 부분을 찾음으로써 영상 처리에서는 general하게 Sobelfiltering으로 많이 찾곤 하는데, 우리가 테스트한 환경에서는 노이즈가 되는 부분이 많아 보다 정교한 경사도 검출 필터링이 필요했다. 그것이 바로 Scharrfilter다. (샤를 필터라고 읽는다.) 이하의 블로그에 설명이 보다 자세하게 나와 있다.
이를 이용하여 수평 수직 방향의 gradient 성분을 찾고 이를 summation하면 모든 방향의 gradient를 검출할 수 있다. 이렇게 되면 차선 부분이 검출되고 주변 noise에 대한 부분도 함께 검출될 것이다.
https://talkingaboutme.tistory.com/entry/OpenCV-Scharr-filterLearningOpenCV에 보시면 sobel 미분에 상세하게 scharr 필터에 대한 내용이 들어있습니다. 이전 투고에서는 소벨 미분은 각 축에 대한 미분을 실시하여 다항식을 근사시킨 결과라고 했습니다.talkingaboutme.tistory.com(2) 황색 백선 검출 차선의 색상 구분을 위해 적용하는 프로세스이다. 백색 영역은 RGB 영역에서 upperlower thresholding 값을 실험적으로 찾아 검출하고, 황색 영역은 HSV로 변환한 후 upperlower thresholding 값을 실험적으로 찾아 검출한다.
그다음에 지문인식에 사용하는 영상처리 기법 중 Thickened 기법이 있는데 이를 적용하면 검출된 결과가 더 증폭된다.
(1), (2)를 통해 필터링된 이미지는 bitwise and 연산자와 정합한다.
(3) Media filtering 정합된 이미지에도 테스트 환경에서는 점과 같은 Noise가 다수 존재했던 이 부분은 salt and pepernoise로 Media filtering으로 제거할 수 있다. Media filtering은 픽셀 값을 오름차순으로 정렬하고 가운데 중간 값을 선택하여 픽셀 값을 결정하는 필터링이다.
이렇게 하면 최종 검출된 차선을 확인할 수 있게 된다.
다음 포스트에 이어서.