本文目录导读:

我来帮你编写动图合成脚本,这里提供Python和FFmpeg两种主流方案。
使用Python + Pillow(最简单)
from PIL import Image
import os
def create_gif_from_images(image_paths, output_path, duration=100, loop=0):
"""
将多张图片合成为GIF动图
参数:
image_paths: 图片路径列表
output_path: 输出GIF路径
duration: 每帧持续时间(毫秒)
loop: 循环次数(0为无限循环)
"""
if not image_paths:
raise ValueError("图片列表不能为空")
# 打开所有图片
frames = [Image.open(img_path) for img_path in image_paths]
# 统一尺寸(可选)
# target_size = frames[0].size
# frames = [img.resize(target_size) for img in frames]
# 保存为GIF
frames[0].save(
output_path,
save_all=True,
append_images=frames[1:],
duration=duration,
loop=loop
)
print(f"GIF已保存到: {output_path}")
# 使用示例
if __name__ == "__main__":
# 方式1:指定图片列表
images = ['frame1.png', 'frame2.png', 'frame3.png']
create_gif_from_images(images, 'output.gif', duration=200)
# 方式2:使用通配符匹配(需要清理列表)
import glob
images = sorted(glob.glob('frames/*.png')) # 确保排序正确
create_gif_from_images(images, 'animation.gif')
使用FFmpeg(性能更好)
从图片序列生成GIF
# 基础命令
ffmpeg -framerate 10 -i frames/frame_%04d.png output.gif
# 参数说明:
# -framerate: 帧率(fps)
# -i: 输入文件模式(%04d表示4位数字编号)
# 高级配置
ffmpeg -framerate 24 \
-i input_%03d.png \
-vf "fps=10,scale=640:-1:flags=lanczos,split[s0][s1];[s0]palettegen[p];[s1][p]paletteuse" \
output.gif
从视频提取并合成GIF
# 从视频中截取片段转为GIF ffmpeg -i input.mp4 -ss 00:00:05 -t 3 -vf "fps=10,scale=320:-1" output.gif # 使用调色板优化质量 ffmpeg -i input.mp4 -vf "fps=15,scale=480:-1:flags=lanczos,palettegen" palette.png ffmpeg -i input.mp4 -i palette.png -filter_complex "fps=15,scale=480:-1[x];[x][1:v]paletteuse" output.gif
Python调用FFmpeg
import subprocess
import os
def create_gif_with_ffmpeg(image_dir, output_path, fps=10, scale=480):
"""
使用FFmpeg合成GIF
参数:
image_dir: 图片文件夹
output_path: 输出路径
fps: 帧率
scale: 缩放宽度
"""
cmd = [
'ffmpeg',
'-framerate', str(fps),
'-i', os.path.join(image_dir, 'frame_%04d.png'),
'-vf', f'fps={fps},scale={scale}:-1:flags=lanczos',
'-y', # 覆盖输出文件
output_path
]
try:
subprocess.run(cmd, check=True)
print(f"GIF已保存到: {output_path}")
except subprocess.CalledProcessError as e:
print(f"合成失败: {e}")
# 获取文件列表并排序
def get_sorted_images(dir_path, extensions=['.png', '.jpg', '.jpeg']):
files = []
for ext in extensions:
files.extend([f for f in os.listdir(dir_path) if f.endswith(ext)])
return sorted(files, key=lambda x: int(''.join(filter(str.isdigit, x)) or 0))
# 使用示例
if __name__ == "__main__":
create_gif_with_ffmpeg('frames/', 'animation.gif')
进阶功能实现
添加文字水印
from PIL import Image, ImageDraw, ImageFont
def create_gif_with_text(images, output_path, text="Sample", duration=100):
frames = []
font = ImageFont.load_default() # 或加载自定义字体
for img_path in images:
img = Image.open(img_path).convert('RGB')
draw = ImageDraw.Draw(img)
# 添加文字
text_position = (10, 10)
draw.text(text_position, text, fill=(255, 255, 255), font=font)
frames.append(img)
# 保存
frames[0].save(output_path, save_all=True,
append_images=frames[1:],
duration=duration, loop=0)
调整GIF速度
def adjust_gif_speed(input_gif, output_gif, speed_factor=0.5):
"""
调整GIF速度
speed_factor: 速度因子(0.5=慢速,2.0=快速)
"""
from PIL import ImageSequence
gif = Image.open(input_gif)
frames = []
for frame in ImageSequence.Iterator(gif):
frames.append(frame.copy())
# 调整每帧持续时间
durations = [frame.info.get('duration', 100) * speed_factor
for frame in frames]
frames[0].save(output_gif, save_all=True,
append_images=frames[1:],
duration=durations, loop=0)
完整脚本示例
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import argparse
import os
from PIL import Image
import glob
def create_gif(input_pattern, output, duration=100, reverse=False, loop=0):
"""
完整的GIF合成工具
"""
# 获取所有图片
images = sorted(glob.glob(input_pattern))
if not images:
print(f"未找到匹配的图片: {input_pattern}")
return
# 可选:反转帧序列
if reverse:
images = images[::-1]
# 加载图片
frames = [Image.open(img) for img in images]
# 统一尺寸
if len(frames) > 1:
target_size = frames[0].size
frames = [img.resize(target_size) for img in frames]
# 保存GIF
frames[0].save(
output,
save_all=True,
append_images=frames[1:],
duration=duration,
loop=loop,
optimize=False
)
print(f"成功创建GIF: {output}")
print(f"包含 {len(frames)} 帧")
print(f"循环次数: {'无限' if loop == 0 else loop}")
def main():
parser = argparse.ArgumentParser(description="GIF动图合成工具")
parser.add_argument("-i", "--input", required=True,
help="输入图片模式 (如: frames/*.png)")
parser.add_argument("-o", "--output", default="output.gif",
help="输出GIF文件名")
parser.add_argument("-d", "--duration", type=int, default=200,
help="每帧持续时间(毫秒)")
parser.add_argument("-r", "--reverse", action="store_true",
help="反转帧序列")
parser.add_argument("-l", "--loop", type=int, default=0,
help="循环次数 (0=无限)")
args = parser.parse_args()
create_gif(args.input, args.output, args.duration,
args.reverse, args.loop)
if __name__ == "__main__":
main()
使用建议
- 图片命名:建议使用统一格式,如
frame_0001.png,frame_0002.png - 尺寸控制:GIF文件大小与分辨率、颜色数直接相关
- 色彩优化:使用调色板(palette)可以减少文件大小
- 帧率选择:常见GIF帧率为10-15fps
需要我针对特定场景(如截屏合成、视频转GIF等)提供更详细的实现吗?
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播