아래 내용은 파이썬으로 만드는 OpenCV 프로젝트(이세우 저) 를 공부하며 정리한 내용들입니다.
모든 소스 코드를 확인하고 싶으시다면 제일 하단의 저자 GitHub 주소를 참고하시기 바랍니다.
OpenCV를 이용한 대부분의 작업은 파일로 된 이미지를 읽어서 적절한 연산을 적용하고 그 결과를 화면에 표시하거나 다른 파일로 저장하는 것들이다.
기본적으로 이미지와 비디오를 읽어올 수 있어야하고 저장을 할수있어야한다.
1.1 이미지 읽기
- img = cv2.imread(file_name [, mode_flag]) : 파일로부터 이미지 읽기
- file_name : 이미지 경로, 문자열
- mode_flag = cv2.IMREAD_COLOR : 읽기 모드 지정
- cv2.IMREAD_COLOR : 컬러(BGR) 스케일로 읽기, 기본 값
- cv2.IMREAD_UNCHANGED : 파일 그대로 읽기
- cv2.IMREAD_GRAYSCALE : 그레이(흑백) 스케일로 읽기
- img : 읽은 이미지, Numpy 배열
- cv2.imshow(title, img) : 이미지를 화면에 표시
- title : 창 제목, 문자열
- img : 표시할 이밎, Numpy 배열
cv2.imread() : 파일로부터 이미지를 읽을 때 모드를 지정할 수 있다.
모드를 지정하지 않으면 3개 채널(B, G, R)로 구성된 컬러 스케일로 읽어들임
필요에 따라 그레이 스케일 또는 파일에 저장된 스케일 그대로 읽을 수 있다.
img = cv2.imread(file_name, cv2.IMREAD_GRAYSCALE)
- Key = cv2.waitKey([delay]) : 키보드 입력 대기
- delay = 0 : 키보드 입력을 대기할 시간(ms), 0 : 무한대(기본 값)
- key : 사용자가 입력한 키 값, 정수
- -1 : 대기시간 동안 키 입력 없음
1.2 이미지 저장하기
읽어들인 이미지를 다시 파일로 저장하는 함수는 cv2.imwrite()
- cv2.imwrite(file_path, img) : 이미지를 파일에 저장
- file_path : 저장할 파일 경로 이름, 문자열
- img : 저장할 영상, Numpy 배열
1.3 동영상 및 카메라 프레임 읽기
OpenCV는 동영상 파일이나 컴퓨터에 연결한 카메라 장치로부터 연속된 이미지 프레임을 읽을 수 있는 API를 제공
- cap = cv2.VideoCapture(file_path 또는 index) : 비디오 캡처 객체 생성자
- file_path : 동영상 파일 경로
- index : 카메라 장치 번호, 0부터 순차적으로 증가(0, 1, 2, …)
- cap : VideoCapture 객체
cv2.VideoCapture() : 생성자 함수를 사용하여 영상 프레임을 읽는 객체를 생성
동영상 파일 경로 이름을 전달하면 동영상 파일에 저장된 프레임을 읽을 수 있다.
카메라 장치 번호를 전달하면 카메라로 촬영하는 프레임을 읽을 수 있다.
- ret = cap.isOpened() : 객체 초기화 확인
- ret : 초기화 여부, True / False
isOpened() : 파일이나 카메라 장치에 제대로 연결되었는지 확인
- ret, img = cap.read() : 영상 프레임 읽기
- ret : 프레임 읽기 성공 또는 실패 여부, Treu / False
- img : 프레임 이미지, Numpy 배열 또는 None
read() : 다음 프레임을 읽을 수 있다.
Boolean과 Numpy 배열 객체를 쌍으로 갖는 튜플 (ret, img) 객체를 반환
ret 값이 True이면 다음 프레임 읽기에 성공한 것이고, img를 꺼내서 사용하면 됨
- cap.set(id, value) : 프로퍼티 변경
- cap.get(id) : 프로퍼티 확인
set(), get() : 여러가지 속성을 얻거나 지정 가능
- cap.release() : 캡처 자원 반납
release() : 프로그램을 종료하기 전에 호출해서 자원을 반납
1.4 동영상 파일 읽기
import cv2
video_file = './img/big_buck.avi'
cap = cv2.VideoCapture(video_file)
if cap.isOpened():
while True:
ret, frame = cap.read()
if ret:
cv2.imshow(video_file, frame)
cv2.waitKey(25)
else:
break
else:
print("can't open video.")
cap.release()
cv2.destroyAllWindows()
cv2.waitKey(25) 가 필요한 이유는 각 프레임을 화면에 표시하는 시간이 너무 빠르면 우리 눈으로 볼수 없기 때문에 지연 시간을 조정하여 적절한 속도로 영상을 재생하게 해준다.
1.5 카메라(웹캠) 프레임 읽기
cv2.VideoCapture() : 카메라로 프레임을 읽기 위해서는 카메라 장치 인덱스 번호를 정수로 지정
카메라 장치 인덱스는 0부터 시작해서 1씩 증가
나머지는 동영상 파일과 다루는 법이 거의 똑같다.
import cv2
cap = cv2.VideoCapture(0)
if cap.isOpened():
while True:
ret, frame = cap.read()
if ret:
cv2.imshow('camera', frame)
if cv2.waitKey(1) != -1:
break
else:
print('no frame')
break
else:
print("can't open camera.")
cap.release()
cv2.destroyAllWindows()
카메라로부터 프레임을 읽는 경우 파일의 끝이 정해져 있지 않으므로 무한루프를 빠져 나올 조건이 필요하다.
cv2.waitKey() : 지정한 대기 시간 동안 키 입력이 없으면 -1을 반환
반환된 값이 -1이 아니면 아무 키나 입력되었다는 뜻이고 이때 break를 걸어줄 수 있음
1.6 카메라 비디오 속성 제어
캡처 객체에는 영상 또는 카메라의 여러가지 속성을 확인하고 설정할 수 있는 get(id), set(id, value) 함수를 제공
속성을 나타내는 아이디는 cv2.CAP_PROP_FRAME_로 시작하는 상수로 정의되어 있다.
자세한 속성에 대한 명세는 API 문서를 참조하기 바란다.
- 속성 ID : ‘cv2.CAP_PROP_’로 시작하는 상수
- cv2.CAP_PROP_FRAME_WIDTH : 프레임 폭
- cv2.CAP_PROP_FRAME_HEIGHT : 프레임 높이
- cv2.CAP_PROP_FPS : 초당 프레임 수
- cv2.CAP_PROP_POS_MSEC : 동영상 파일의 프레임 위치(ms)
- cv2.CAP_PROP_POS_AVI_RATIO : 동영상 파일의 상대 위치(0: 시작, 1: 끝)
- cv2.CAP_PROP_FOURCC : 동영상 파일 코덱 문자
- cv2.CAP_PROP_AUTOFOCUS : 카메라 자동 초점 조절
- cv2.CAP_PROP_ZOOM : 카메라 줌
FPS를 구하는 상수를 활용하여 동영상의 FPS를 구하고 적절한 지연시간을 계산해서 지정할 수 있다.
지연 시간은 밀리초 단위이고, 정수만 전달할 수 있다.
fps = cap.get(cv2.CAP_PROP_FPS)
delay = int(1000/fps)
카메라로부터 읽은 영상이 너무 고화질인 경우 픽셀 수가 많아 연산하는데 시간이 많이 걸리는 경우가 있다.
이때 프레임의 폭과 높이를 제어해서 픽셀 수를 줄일 수 있다. (카메라가 아닌 동영상 파일에 프레임 크기를 재지정 할 수는 없다.)
cv2.CAP_PROP_FRAME_WIDTH, cv2.CAP_PROP_FRAME_HEIGHT
1.7 비디오 파일 저장하기
카메라로부터 프레임을 표시하다가 특정 키(혹은 아무 키)를 누르면 해당 프레임을 파일로 저장하는 코드
import cv2
cap = cv2.VideoCapture(0)
cnt_num = 0
if cap.isOpened():
while True:
ret, frame = cap.read()
if ret:
cv2.imshow('camera', frame)
if cv2.waitKey(1) == ord('q'):
break
elif cv2.waitKey(1) == ord('a'):
cv2.imwrite(f'./result/photo{cnt_num}.jpg', frame)
cnt_num += 1
else:
print('no frame!')
break
else:
print('no camera!')
cap.release()
cv2.destroyAllWindows()
여러 프레임을 동영상으로 저장하려고 할 때는 cv2.VideoWriter() 라는 새로운 API가 필요
- writer = cv2.VideoWriter(file_path, fourcc, fps, (width, height)) : 비디오 저장 클래스 생성자 함수
- file_path : 비디오 파일 저장 경로
- fourcc : 비디오 인코딩 형식 4글자
- fps : 초당 프레임 수
- (width, height) : 프레임 폭과 프레임 높이
- writer : 생성된 비디오 저장 객체
cv2.VideoWriter() : 저장할 파일 이름과 인코딩 포맷 문자, fps, 프레임 크기를 지정해서 객체를 생성
write() : 프레임을 파일에 저장
- writer.write(frame) : 프레임 저장
- frame : 저장할 프레임, Numpy 배열
- writer.set(id, value) : 프로퍼티 변경
- writer.get(id) : 프로퍼티 확인
- ret = writer.fourcc(c1, c2, c3, c4) : fourcc 코드 생성
- c1, c2, c3, c4 : 인코딩 형식 4글자, ‘MJPG’, ‘DIVX’ 등
- ret : fourcc 코드
- cv2.VideoWriter_fourcc(c1, c2, c3, c4) : cv2.VideoWriter.fourcc()와 동일
cv2.VideoWriter_fourcc() : 4개의 인코딩 포맷 문자를 전달하면 코드 값을 생성해 내는 함수
REFERENCE
- 소스 코드 참고(저자 GitHub 주소)
GitHub - dltpdn/insightbook.opencv_project_python
Contribute to dltpdn/insightbook.opencv_project_python development by creating an account on GitHub.
github.com
- OpenCV 공식문서
OpenCV: OpenCV modules
OpenCV 4.7.0 Open Source Computer Vision
docs.opencv.org
'ML & DL > OpenCV' 카테고리의 다른 글
[OpenCV] 3. 창 관리 (0) | 2023.02.14 |
---|---|
[OpenCV] 2. 그림, 글씨 그리기 (0) | 2023.02.14 |
[OpenCV] 0. CV 프로젝트 진행을 위한 OpenCV (0) | 2023.02.13 |
[OpenCV] Error : OpenCV(4.6.0) :-1: error: (-5:Bad argument) in function 'add' (0) | 2022.12.27 |
[OpenCV] 이미지에 문자열 넣기 (0) | 2022.12.20 |
댓글