import os
|
import cv2
|
import numpy as np
|
from PIL import Image
|
import argparse
|
|
def is_image_file(filename):
|
return filename.lower().endswith(('.jpg', '.jpeg', '.png'))
|
|
def resize_and_pad_cv(image, size=(1280, 720)):
|
ih, iw = image.shape[:2]
|
target_w, target_h = size
|
|
scale = min(target_w / iw, target_h / ih)
|
new_w = int(iw * scale)
|
new_h = int(ih * scale)
|
resized = cv2.resize(image, (new_w, new_h))
|
|
top = (target_h - new_h) // 2
|
bottom = target_h - new_h - top
|
left = (target_w - new_w) // 2
|
right = target_w - new_w - left
|
|
padded = cv2.copyMakeBorder(resized, top, bottom, left, right, cv2.BORDER_CONSTANT, value=[0, 0, 0])
|
return padded
|
|
def get_first_frame(video_path):
|
cap = cv2.VideoCapture(video_path)
|
success, frame = cap.read()
|
cap.release()
|
return frame if success else None
|
|
def check_and_process_individual_cover(mp4_path):
|
base = os.path.splitext(mp4_path)[0]
|
for ext in ['.jpg', '.jpeg', '.png']:
|
img_path = base + ext
|
if os.path.exists(img_path):
|
try:
|
with Image.open(img_path) as img:
|
w, h = img.size
|
if w < 720:
|
os.remove(img_path)
|
print(f"删除低分辨率封面图: {img_path}")
|
return False # 继续处理 mp4
|
else:
|
print(f"已有封面图,裁剪为1280x720并跳过视频: {img_path}")
|
processed = resize_and_pad_cv(cv2.cvtColor(np.array(img), cv2.COLOR_RGB2BGR))
|
#cv2.imwrite(img_path, processed)
|
Image.fromarray(cv2.cvtColor(processed, cv2.COLOR_BGR2RGB)).save(img_path)
|
|
return True # 不再处理该 mp4
|
except Exception as e:
|
print(f"处理封面图出错 {img_path}: {e}")
|
return False
|
return False # 没有封面图,继续处理 mp4
|
|
def process_medias(folder):
|
for root, _, files in os.walk(folder):
|
for file in files:
|
if file.lower().endswith('.mp4'):
|
video_path = os.path.join(root, file)
|
skip = check_and_process_individual_cover(video_path)
|
if skip:
|
continue
|
frame = get_first_frame(video_path)
|
if frame is None:
|
print(f"无法读取视频帧: {video_path}")
|
continue
|
output_img = resize_and_pad_cv(frame)
|
output_path = os.path.splitext(video_path)[0] + "_cover.jpg"
|
#cv2.imwrite(output_path, output_img)
|
Image.fromarray(cv2.cvtColor(output_img, cv2.COLOR_BGR2RGB)).save(output_path)
|
print(f"生成封面图: {output_path}")
|
|
if __name__ == "__main__":
|
parser = argparse.ArgumentParser(description="处理mp4封面图")
|
parser.add_argument("folder", help="包含视频的文件夹")
|
args = parser.parse_args()
|
process_medias(args.folder)
|