在计算机视觉和视频处理领域,视频与帧图片的相互转换是一项基础且重要的技术。本文将分享如何使用 OpenCV 和 Python 实现视频转帧图片以及帧图片转视频的功能,并提供完整代码解析。 

1.视频转帧图片功能解析

(1)核心函数定义如下:

video_path (str): 输入视频文件的路径

output_folder (str): 保存图片的目标文件夹

every_n_frames (int): 每隔多少帧保存一次,默认为1(逐帧保存)

import cv2
import os

def video_to_images(video_path, output_folder, every_n_frames=1):
    """
    从视频中按指定间隔提取帧并保存为图片序列
    
    参数:
        video_path (str): 输入视频文件的路径
        output_folder (str): 保存图片的目标文件夹
        every_n_frames (int): 每隔多少帧保存一次,默认为1(逐帧保存)
    """
    # 创建输出文件夹(如果不存在)
    # exist_ok=True确保文件夹不存在时创建,存在时不报错
    os.makedirs(output_folder, exist_ok=True)
    
    # 打开视频文件
    # cv2.VideoCapture可以处理多种视频格式和摄像头输入
    cap = cv2.VideoCapture(video_path)
    
    # 检查视频是否成功打开
    # 失败可能由于文件不存在、格式不支持或权限问题
    if not cap.isOpened():
        print(f"错误: 无法打开视频文件 {video_path}")
        return False
    
    # 初始化计数器
    # frame_count: 记录当前处理的总帧数
    # saved_count: 记录实际保存的帧数
    frame_count = saved_count = 0
    
    # 循环读取视频帧
    while True:
        # 读取一帧视频
        # ret: 布尔值,表示是否成功读取帧
        # frame: 包含帧图像数据的numpy数组
        ret, frame = cap.read()
        
        # 检查是否成功读取帧
        # 若失败,说明已到达视频末尾或发生错误
        if not ret:
            break
        
        # 按指定间隔保存帧
        # 例如every_n_frames=10时,每10帧保存一次
        if frame_count % every_n_frames == 0:
            # 生成格式化文件名,如"frame_0001.jpg"
            # :04d确保数字部分始终为4位,不足补零
            filename = f"frame_{saved_count+1:04d}.jpg"
            
            # 保存帧为JPEG图片
            # os.path.join确保路径分隔符在不同系统上的兼容性
            cv2.imwrite(os.path.join(output_folder, filename), frame)
            
            # 更新保存的帧数计数器
            saved_count += 1
        
        # 更新总帧数计数器
        frame_count += 1
    
    # 释放视频资源
    # 必须调用以关闭视频文件并释放内存
    cap.release()
    
    print(f"成功从视频中提取 {saved_count} 帧,保存至 {output_folder}")
    return True

(2)使用实例:

if __name__ == "__main__":
    # 配置参数(使用前请根据实际情况修改)
    INPUT_VIDEO = "./mpandpic/input.mp4"  # 输入视频文件路径
    OUTPUT_FOLDER = "./mpandpic/images"  # 输出图片文件夹
    EVERY_N_FRAMES = 10  # 每隔10帧保存一次,可调整以控制提取密度
    
    # 调用函数执行视频帧提取
    success = video_to_images(INPUT_VIDEO, OUTPUT_FOLDER, EVERY_N_FRAMES)
    
    if success:
        print("视频帧提取完成")
    else:
        print("视频帧提取失败")

运行完成之后打开输出图片文件夹:

2.帧图片转视频功能解析

(1)核心函数定义如下:

import cv2
import os

def images_to_video(image_folder, output_path, fps=30.0):
    """
    将指定文件夹中的图片序列合成为视频文件
    
    参数:
        image_folder (str): 包含图片序列的文件夹路径
        output_path (str): 输出视频文件的路径
        fps (float): 视频帧率(每秒显示的帧数),默认为30.0
    """
    # 定义支持的图片格式扩展名
    valid_extensions = ('jpg', 'jpeg', 'png', 'bmp')
    
    # 获取文件夹中所有文件,并筛选出符合条件的图片文件
    # 使用sorted确保文件按名称排序,保证视频帧顺序正确
    image_files = sorted(
        f for f in os.listdir(image_folder) 
        if f.lower().endswith(valid_extensions)
    )
    
    # 检查是否存在符合条件的图片
    if not image_files:
        print(f"错误: 在 {image_folder} 中未找到支持的图片文件")
        return False  # 无图片时返回失败状态
    
    # 读取第一张图片以获取视频尺寸
    # shape属性返回(height, width, channels)三元组,取前两个值
    first_image = cv2.imread(os.path.join(image_folder, image_files[0]))
    height, width = first_image.shape[:2]
    
    # 创建视频写入器对象
    # fourcc指定视频编码格式,'mp4v'对应MP4格式
    # fps参数控制视频播放速度
    # (width, height)指定视频帧尺寸,必须与图片尺寸一致
    fourcc = cv2.VideoWriter_fourcc(*'mp4v')
    out = cv2.VideoWriter(output_path, fourcc, fps, (width, height))
    
    # 遍历所有图片文件,逐帧写入视频
    for image_name in image_files:
        # 读取图片并写入视频
        # 注意:所有图片应保持相同尺寸,否则可能导致视频生成失败
        frame = cv2.imread(os.path.join(image_folder, image_name))
        out.write(frame)
    
    # 释放视频写入器资源,必须调用以完成视频写入
    out.release()
    print(f"视频已成功保存至: {output_path}")
    return True  # 返回成功状态

(2)使用实例:

if __name__ == "__main__":
    # 配置参数(使用前请根据实际情况修改)
    IMAGE_FOLDER = "./mpandpic/images"  # 包含图片序列的文件夹
    OUTPUT_VIDEO = "./mpandpic/output.mp4"  # 输出视频文件路径
    FPS = 3  # 视频帧率,控制播放速度
    
    # 调用函数执行图片转视频操作
    success = images_to_video(IMAGE_FOLDER, OUTPUT_VIDEO, FPS)
    if success:
        print("视频生成成功")
    else:
        print("视频生成失败")

运行结果:

Logo

火山引擎开发者社区是火山引擎打造的AI技术生态平台,聚焦Agent与大模型开发,提供豆包系列模型(图像/视频/视觉)、智能分析与会话工具,并配套评测集、动手实验室及行业案例库。社区通过技术沙龙、挑战赛等活动促进开发者成长,新用户可领50万Tokens权益,助力构建智能应用。

更多推荐