[OpenCV] 비디오 읽기 및 쓰기
OpenCV에서 비디오를 읽고 쓰는 것은 이미지를 읽고 쓰는 것과 매우 유사하다. 비디오는 프레임 이라고 하는 일련의 이미지에 불과하다. 따라서 비디오 시퀀스의 모든 프레임을 반복한 다음 한 번에 한 프레임씩 처리하기만 하면 된다. 파일, 이미지 시퀀스 및 웹캠 에서 비디오를 읽고 표시하고 쓰는 방법을 알 수 있다.
OpenCV 비디오 I/O의 주요 기능은 다음과 같다.
- cv2.VideoCapture : 비디오를 스트리밍하거나 표시하는데 도움되는 비디오 캡처 객체를 만든다.
- cv2.VideoWriter : 출력 비디오를 디렉토리에 저장한다.
- 프레임 높이, 폭, fps 등과 같은 비디오 메타데이터를 읽는 데 사용되는 cv2.imshow(), cv2.waitKey() 및 get() 방법과 같은 다른 필요한 기능에 대해서도 알 수 있다.
파일에서 비디오 읽기
VideoCapture()클래스를 사용하여 VideoCapture 객체를 만든 다음, 비디오 파일을 읽을 때 사용한다.
VideoCapture(path, apiPreference)
- path : 비디오 파일의 파일 이름/경로
- apiPreference : 기본 설정을 나타내는 선택적 인수 API
isOpened()
비디오 캡처 객체가 있을 때 isOpened()
메서드를 사용하여 비디오 파일이 성공적으로 열렸는지 확인할 수 있다. 비디오 스트림이 유효한지 여부를 나타내는 bool 값을 반환한다. 그렇지 않으면 오류 메시지가 표시된다.
오류 메시지는 많은 것을 암시할 수 있는데, 그 중 하나는 전체 비디오가 손상되었거나 일부 프레임이 손상되었다는 것이다.
get()
비디오 파일이 성공적으로 열렸다고 가정하면 get()
메서드를 사용하여 비디오 스트림과 관련된 중요한 메타 데이터를 검색할 수 있다. 하지만 웹 카메라에서는 적용되지 않는다.
get() 메서드는 여기에 설명된 열거된 옵션 목록에서 단일 인수를 가져온다.
아래 예제에서는 프레임 속도(CAP_PROP_FPS) 및 프레임 수(CAP_PROP_FRAME_COUNT)에 해당하는 숫자 5와 7을 제공했다. 이처럼 숫자 값 또는 이름을 입력할 수 있습니다.
import cv2
vid_capture = cv2.VideoCapture('./car.gif')
if not vid_capture.isOpened():
print("Error opening the video file")
else:
# Get frame rate information
fps = int(vid_capture.get(5))
print("Frame Rate : ", fps, "frames per second")
# Get frame count
frame_count = vid_capture.get(7)
print("Frame count : ", frame_count)
read()
비디오 파일과 관련된 원하는 메타 데이터를 검색한 후 이제 파일에서 각 이미지 프레임을 읽을 준비가 되었을 때 read()
메서드를 사용하여 비디오 스트림에서 프레임을 읽어올 수 있다.
vide_capture.read()를 했을 때 두 가지 반환 요소가 존재한다.
- 첫 번째는 Bool이다. True일 경우 비디오 스트림에 읽을 프레임이 포함되어 있음을 나타낸다.
- 두 번째는 실제 비디오 프레임인 튜플을 반환한다.
읽을 프레임이 있으면 imshow()
를 사용 하여 창에 현재 프레임을 표시하고, 그렇지 않으면 루프를 종료할 수 있다. waitKey() 기능을 사용하여 비디오 프레임 사이에 20ms 동안 일시 중지 할 수도 있다. waitKey() 함수를 호출하면 사용자 입력에 대해 키보드를 모니터링할 수 있습니다. 아래의 경우 사용자가 q
키를 누르면 루프가 종료됩니다.
while vid_capture.isOpened():
# read() methods returns a tuple, first element is a bool
# and the second is frame
ret, frame = vid_capture.read()
if ret:
cv2.imshow('Frame', frame)
k = cv2.waitKey(20)
# 113은 아스키 코드로 q
if k == 113:
break
else:
break
release()
비디오 스트림이 완전히 처리되거나 사용자가 루프를 조기에 종료하면 release()
메서드를 사용하여 비디오 캡처 객체를 release하고 창을 닫는다.
vid_capture.release()
cv2.destroyAllWindows()
이미지 시퀀스 읽기
이미지 시퀀스에서 이미지 프레임을 처리하는 것은 비디오 스트림에서 프레임을 처리하는 것과 매우 유사하다. 읽고 있는 이미지 파일을 지정하기만 하면 된다.
비디오 파일을 지정하는 대신 이미지 시퀀스를 지정하기만 하면 됩니다. 아래 표시된 표기법(Cars%04d.jpg)을 사용합니다. 여기서 %04d는 4자리 시퀀스 명명 규칙을 나타낸다(예: Cars0001.jpg, Cars0002.jpg, Cars0003.jpg 등).
vid_capture = cv2.VideoCapture('./Image_sequence/Cars%04d.jpg')
웹캠에서 비디오 읽기
웹 카메라에서 비디오 스트림을 읽는 것도 OpenCV의 비디오 캡처 클래스의 유연성 덕분에 위와 매우 유사하다. 이 클래스에는 다양한 입력 인수를 허용하는 편의를 위해 여러 오버로드된 함수가 있다. 비디오 파일이나 이미지 시퀀스의 소스 위치를 지정하는 대신 아래와 같이 비디오 캡처 장치 인덱스를 지정하기만 하면 된다.
- 시스템에 내장 웹캠이 있는 경우 카메라의 장치 색인은
0
- 시스템에 하나 이상의 카메라가 연결되어 있는 경우 각 추가 카메라와 연결된 장치 인덱스가 증가(1, 2 ...)
vid_capture = cv2.VideoCapture(0, cv2.CAP_DSHOW)
여기서 CAP_DSHOW는 선택적 인수로 필수가 아니다. CAP_DSHOW는 directshow의 줄임말인 또 다른 비디오 캡처 apiPreference다.
비디오 쓰기
비디오 읽기와 마찬가지로 모든 소스(비디오 파일, 이미지 시퀀스 또는 웹캠)에서 비디오를 작성할 수 있다.
비디오 파일을 작성하려면
get()
메서드 를 사용하여 이미지 프레임 높이와 너비를 검색한다.- 이전 섹션에서 설명한 대로 비디오 캡처 객체를 초기화하여 비디오 스트림을 메모리로 읽는다.
- VideoWriter 객체를 만든다.
- VideoWriter 객체를 사용하여 비디오 스트림을 디스크에 저장한다.
# Obtain frame size information using get() method
frame_width = int(vid_capture.get(3))
frame_height = int(vid_capture.get(4))
frame_size = (frame_width,frame_height)
fps = 20
VideoWriter
VideoWriter(filename, apiPreference, fourcc, fps, frameSize, [isColor])
- filename : 출력 비디오 파일의 경로 이름
- apiPreference : API 백엔드 식별자
- fourcc : 프레임을 압축하는 데 사용되는 코덱의 4자 코드
- fps : 생성된 비디오 스트림의 프레임 속도
- frame_size : 비디오 프레임의 크기
- isColor : 0이 아닌 경우 인코더는 색상 프레임을 예상하고 인코딩한다. 그렇지 않으면 회색 프레임에서 작동한다.
video codec
다음 코드 output는 VideoWriter()클래스에서 비디오 작성기 개체를 만든다. video writer 객체에 대한 두 번째 인수로 필요한 4 글자 코덱을 검색할 때 아래와 같은 기능이 사용된다.
cv2.VideoWriter_fourcc('M', 'J', 'P', 'G')
비디오 코덱은 비디오 스트림이 압축되는 방식을 지정한다. 압축되지 않은 비디오를 압축된 형식으로 또는 그 반대로 변환한다.
output = cv2.VideoWriter('./output_video_from_file.avi', cv2.VideoWriter_fourcc('M', 'J', 'P', 'G'), 20, frame_size)
while vid_capture.isOpened():
# vid_capture.read() methods returns a tuple, first element is a bool
# and the second is frame
ret, frame = vid_capture.read()
if ret:
# Write the frame to the output files
output.write(frame)
else:
print("Stream disconnected")
break
마지막으로 VideoCapture, VideoWriter release
vid_capture.release()
output.release()
Author And Source
이 문제에 관하여([OpenCV] 비디오 읽기 및 쓰기), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://velog.io/@rlath/OpenCV-비디오-읽기-및-쓰기저자 귀속: 원작자 정보가 원작자 URL에 포함되어 있으며 저작권은 원작자 소유입니다.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)