2024年4月29日

HYEOS

随事而为

Gentoo python3视频压缩

2 min read
#!/usr/bin/env python3
import os
import subprocess

def check_install_ffmpeg():
    try:
        subprocess.run(['ffmpeg', '-version'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, check=True)
        return True
    except FileNotFoundError:
        return False

def install_ffmpeg():
    print("未检测到 FFmpeg,请确认是否要安装。")
    choice = input("是否安装 FFmpeg? (y/n): ")
    if choice.lower() == 'y':
        try:
            subprocess.run(['sudo', 'emerge', '-av', 'media-video/ffmpeg'], check=True)
            print("FFmpeg 安装完成。")
            return True
        except subprocess.CalledProcessError:
            print("安装 FFmpeg 失败。脚本将退出。")
            return False
    else:
        print("取消安装。脚本将退出。")
        return False

def compress_video(input_file, output_file, video_bitrate):
    cmd = f"ffmpeg -i '{input_file}' -c:v libx264 -b:v {video_bitrate}k -max_muxing_queue_size 1024 -c:a aac -b:a 128k -strict -2 '{output_file}'"
    try:
        subprocess.run(cmd, shell=True, check=True)
    except subprocess.CalledProcessError:
        print(f"压缩视频 {input_file} 失败。")

def split_video(input_file, duration):
    cmd = f"ffmpeg -i '{input_file}' -c copy -f segment -segment_time {duration} '{input_file}_part_%02d.mp4'"
    try:
        subprocess.run(cmd, shell=True, check=True)
    except subprocess.CalledProcessError:
        print(f"切割视频 {input_file} 失败。")

def check_file_size(file):
    file_size = os.path.getsize(file) / (1024 * 1024) # 转换为MB
    return file_size

def compress_and_split_videos():
    video_files = [file for file in os.listdir() if os.path.isfile(file) and file.lower().endswith(('.mp4', '.avi', '.mkv', '.mov', '.wmv'))]
    if not video_files:
        print("未找到任何视频文件。")
        return

    for file in video_files:
        output_file = "compressed_" + file
        video_bitrate = 1200  # 调整比特率,增加画质
        compress_video(file, output_file, video_bitrate)
        compressed_size = check_file_size(output_file)

        if compressed_size > 100:
            print(f"压缩后的视频 {output_file} 大小为 {compressed_size:.2f}MB,继续切割...")
            duration = 10  # 调整切割时长
            split_video(output_file, duration)

    print("视频压缩和切割完成。")

if __name__ == "__main__":
    if not check_install_ffmpeg():
        if not install_ffmpeg():
            exit(1)

    compress_and_split_videos()

脚本会在当前目录下查找所有视频文件并进行压缩。如果压缩后的视频文件大小超过 100MB,则会自动进行视频切割。切割后的视频文件将保存在原始视频文件名后加上 _part_序号.mp4 的文件名中。

使用了 -crf 23 参数来调整视频的质量,而不是使用固定的比特率。较小的 -crf 值表示更高的质量,但可能导致文件更大,较大的值表示较低的质量,但可能导致文件更小。-crf 23 一般会在保持较高质量的同时,将文件大小控制在合理范围内。

在脚本中,增加了 video_bitrate 和 duration 变量,分别用于调整视频压缩的比特率和视频切割的时长。我们将 video_bitrate 设置为 1200,以增加压缩后视频的画质。将 duration 设置为 10,即每个切割后的视频时长为 10 秒左右,以保持切割后视频文件的大小在 90MB 到 100MB 之间。

请注意,在进行视频压缩和切割前最好备份原始视频,以防意外损失。压缩和切割结果的大小可能会略大于 100MB,因为压缩和切割后的视频大小受多种因素影响,包括原始视频的内容和压缩参数的选择。

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注