MoviePy拼接视频报错:(1080,1920,3)数组无法广播到(1080,1920)
问题根因
报错本质是视频帧通道数不匹配:待拼接的视频源里混入了单通道灰度视频,使用concatenate_videoclips的compose模式拼接时,会以第一个加载的片段的通道格式创建背景画布,如果首个片段是单通道灰度格式,后续三通道RGB视频帧(形状为(1080,1920,3))贴到形状为(1080,1920)的单通道画布上时,就会触发数组广播失败的报错。
另外原代码没有实现1080x1920尺寸适配逻辑,即使解决通道问题,输出视频也会因为源视频尺寸、宽高比不统一出现画面大小错乱的问题,不符合需求。
修复方案
从三个维度修正代码:
- 统一所有待拼接片段的色彩空间为RGB三通道,从根源解决通道不匹配问题
- 对每个片段单独做适配处理:先等比例缩放保证画面无拉伸变形,再将缩放后的画面居中放置在1080x1920的纯黑背景上,空白区域自动填充黑色
- 统一所有片段的帧率、编码参数,避免拼接时出现音画不同步、导出失败问题
修复后完整代码
from moviepy.editor import * from os import walk, path # 基础配置 TARGET_WIDTH = 1080 TARGET_HEIGHT = 1920 DEFAULT_FPS = 30 INTRO_VIDEO_PATH = r'C:\Users\jack_L\Downloads\INTRO_VIDEO\INTRO.mp4' VIDEOS_PATH = r'C:\Users\jack_l\Downloads\DOWNLOADS\folder' OUTPUT_PATH = r'C:\Users\jack_l\Downloads\final.mp4' def adapt_clip_to_target(clip): # 强制转RGB三通道,解决通道不匹配问题 if clip.ismask: clip = clip.to_RGB() # 等比例缩放,杜绝画面拉伸 origin_w, origin_h = clip.size scale_ratio = min(TARGET_WIDTH / origin_w, TARGET_HEIGHT / origin_h) resized_clip = clip.resize(scale_ratio) # 生成目标尺寸黑色背景,将缩放后的视频居中放置 black_bg = ColorClip( size=(TARGET_WIDTH, TARGET_HEIGHT), color=(0, 0, 0), duration=clip.duration ) positioned_clip = resized_clip.set_position(("center", "center")) # 合成适配后的片段,统一帧率 adapted_clip = CompositeVideoClip([black_bg, positioned_clip]).set_fps(DEFAULT_FPS) # 保留原片段音频 if clip.audio is not None: adapted_clip = adapted_clip.set_audio(clip.audio) return adapted_clip if __name__ == "__main__": clip_list = [] # 处理开场视频 intro_clip = VideoFileClip(INTRO_VIDEO_PATH) clip_list.append(adapt_clip_to_target(intro_clip)) # 遍历目录处理所有mp4格式视频 for _, _, file_list in walk(VIDEOS_PATH): for file_name in file_list: # 兼容大小写后缀 if path.splitext(file_name)[1].lower() != '.mp4': continue video_full_path = path.join(VIDEOS_PATH, file_name) raw_clip = VideoFileClip(video_full_path) clip_list.append(adapt_clip_to_target(raw_clip)) # 拼接所有处理完成的片段 final_video = concatenate_videoclips(clip_list, method="compose") # 导出最终视频 final_video.write_videofile( OUTPUT_PATH, fps=DEFAULT_FPS, codec="libx264", audio_codec="aac" )
补充说明
- 代码对文件后缀做了小写兼容,不会漏掉
.MP4这类大写后缀的视频文件 - 缩放逻辑严格等比例,不会出现人脸、物体拉伸变形的问题,黑边填充完全匹配需求
- 统一帧率为30fps,避免不同源视频帧率不一致导致的音画不同步、导出报错问题
- 自动保留原视频的音频轨道,不会出现导出视频无声的问题
内容的提问来源于stack exchange,提问作者THEMOUNTAINSANDTHESKIES
相关产品推荐
相关产品推荐

