Python中cv2.VideoCapture读取视频与ffmpeg及播放器存在色差问题排查
OpenCV VideoCapture读取视频帧与FFmpeg直接读取的色差问题排查
问题现象
使用cv2.VideoCapture读取视频时,得到的帧与其他媒体播放器显示的画面存在轻微色差。即使指定OpenCV以FFmpeg作为后端读取视频,其输出帧与直接通过FFmpeg命令读取的帧仍存在差异;而直接用FFmpeg读取的帧与媒体播放器显示效果完全一致。
测试素材
测试视频文件:test3.webm、test.avi
实现代码
FFmpeg直接读取帧的函数与对比代码
import cv2 import numpy as np import subprocess def read_frames(path, res): """读取视频帧为numpy数组,path为文件路径,res为分辨率元组""" args = [ "ffmpeg", "-i", path, "-f", "image2pipe", "-pix_fmt", "rgb24", "-vcodec", "rawvideo", "-", ] pipe = subprocess.Popen( args, stdout=subprocess.PIPE, stderr=subprocess.DEVNULL, bufsize=res[0] * res[1] * 3, ) while pipe.poll() is None: frame = pipe.stdout.read(res[0] * res[1] * 3) if len(frame) > 0: array = np.frombuffer(frame, dtype="uint8") break pipe.stdout.close() pipe.wait() array = array.reshape((res[1], res[0], 3)) array = cv2.cvtColor(array, cv2.COLOR_RGB2BGR) return array ORIGINAL_VIDEO = 'test3.webm' array = read_frames(ORIGINAL_VIDEO, (1280, 720)) cap = cv2.VideoCapture(ORIGINAL_VIDEO, cv2.CAP_FFMPEG) while cap.isOpened(): ret, frame = cap.read() if not ret: break print(frame.shape) cv2.imshow("Opencv Read", frame) cv2.imshow("FFmpeg Direct Read", array) cv2.waitKeyEx() cv2.waitKeyEx() break cap.release()
帧差异验证代码
通过以下代码可直观查看两种方式读取帧的像素差异:
cv2.imshow('test', cv2.absdiff(array, frame)*10) cv2.waitKey(0)
差异表现:经放大后的差异帧显示,画面部分区域存在明显的色彩偏差,呈现像素级的颜色不一致。
疑问
已通过多款媒体播放器对比,确认问题出在OpenCV读取环节,现需排查该差异是OpenCV的Bug导致,还是代码实现存在问题。
内容的提问来源于stack exchange,提问作者cliffsu
相关产品推荐
相关产品推荐

