컴퓨터 비전
[OpenCV][Python] 사각형 내의 원의 수 세기 | 주사위 눈금 읽기 | 하나의 사각형(객체) 대해 수행
miiinn
2022. 12. 14. 13:31
🔎 명세
>> 사각형 내의 원의 수 세기
• 한 이미지 내에 하나의 사각형이 있고, 그 안에 n개의 원이 있을 때, 원의 숫자를 console에 출력하기
• Grayscale 입력
• 배경은 어두운 색으로 가정
• 사각형의 배경색은 밝은 색으로 가정
• 원의 색은 어두운 색으로 가정
🔎 구현 단계
1. 회색조로 주사위 사진 파일 열기
• imread() 함수의 인자로 cv.IMREAD_GRAYSCALE을 넣어 회색조로 사진 파일을 열었다.
2. 이진화
• threshold() 함수의 인자로 cv.THRESH_OTSU를 이용해 자동으로 임계값을 결정했다.
3. 외곽선 찾기
• findContours() 함수의 인자로 cv.RETR_CCOMP를 넣어 모든 외곽선을 검색하고 2단계 계층 구조를 구성하도록 했다. 또한 눈으로 외곽선이 잘 검출되었나 확인하기 위해 drawContours() 함수를 이용해 검출된 외곽선을 그렸다.
4. 주사위 눈금 읽기
• 주사위 눈금을 읽기 위해 검출된 외곽선들 중에 부모 계층(사각형 부분)이 아니라 자식 계층(동그라미 부분)의 개수를 세기 위해 전체 외곽선 개수(len(hierarchy[0]))만큼 반복문을 돌려 배열의 4번째 부분이 0(자식 계층)일 때만 수를 더해주었다.
<hierarchy>의 출력 결과에서 4번째 요소가 -1이면 부모 계층 / 0이면 자식 계층
🔎 소스코드
import random
import cv2 as cv
def detectDice1():
# 회색조로 파일 열기
src = cv.imread('dice_seven.jpg', cv.IMREAD_GRAYSCALE)
if src is None:
print('Image load failed!')
return
# 이진화
_, dst = cv.threshold(src, 0, 255, cv.THRESH_OTSU)
# 외곽선 찾기
contours, hierarchy = cv.findContours(dst, cv.RETR_CCOMP, cv.CHAIN_APPROX_SIMPLE)
idx = 0
while idx >= 0:
c = (random.randint(0, 255), random.randint(0, 255), random.randint(0,255))
cv.drawContours(dst, contours, idx, c, 2, cv.LINE_8, hierarchy)
idx = hierarchy[0, idx, 0]
# 검출된 외곽선 만큼 반복. 부모 아닌 외곽선 개수 세기
dicenum = 0
for i in range (0, len(hierarchy[0])):
isParent = hierarchy[0, i, 3] # 부모 외곽선이면 -1, 자식이면 0
if (not isParent): # 자식일 경우 눈금이므로 세기
dicenum += 1
print(f'주사위 눈금 : {dicenum}')
cv.imshow('src', src)
cv.imshow('dst', dst)
cv.waitKey()
detectDice1()