PIL Png 与 Gif 背景

PIL Png With Gif Background

我正在尝试制作堡垒之夜图像卡生成器。我想让它在顶层制作皮肤,在底部制作 bg 也就是 gif。这是到目前为止的代码。


import os
from PIL import Image

filename = 'CID_613_Athena_Commando_M_Columbus_7Y4QE.png'
skin = Image.open(filename, 'r')
filename1 = 'bg.gif'
bg = Image.open(filename1, 'r')
text_img = Image.new('RGBA', (512,512), (0, 0, 0, 0))
text_img.paste(bg, (0,0))
text_img.paste(skin, (0,0), mask=skin)
text_img.save("out.gif", format="gif")

CID_613_Athena_Commando_M_Columbus_7Y4QE.png是:https://imgur.com/Seu1Tx6.png

背景: https://i.imgur.com/fCewt2H.gif

这是输出: https://i.imgur.com/4yJMp3M.png

我希望它像动画背景一样。不像现在这样

最简单的方法是不写任何 Python 并在终端中使用 ImageMagick。因此,您可以加载背景 GIF 并将其拆分为包含 -coalesce 的 72 帧,然后在顶部绘制太空人并另存为动画 GIF:

magick fCewt2H.gif -coalesce -draw "image SrcOver 0,0 0,0 Seu1Tx6.png" animated.gif

请注意,我已经降低了颜色质量、帧数和图像大小,以低于 Whosebug 的 2MB 帖子限制。您可以使用上述命令获得完整质量。


如果您出于某种原因不想使用 ImageMagick,您可以使用 Python,但您必须明白动画 GIF 是一个文件但是 包含很多帧 。所以你需要:

  • 加载前景帧一次(就像您已经做的那样)
  • 加载 GIF 背景
  • iterate 在背景帧上将前景(您有此代码)粘贴到 72 帧的每一帧上
  • 生成的 72 帧 GIF

您需要迭代 gif 中的所有帧并将前景图像粘贴到所有帧中。

如果图片是动画的(bg.is_animated),可以得到帧数bg.n_frames

对于动画图像(不仅仅是 gif),Pillow 包含一个 seek(frame_number) 方法,可以将动画转发到您要使用的帧。

代码将类似于:

if bg.is_animated:

  frames = []

  for num in range(bg.n_frames):
    bg.seek(num)
    text_img = Image.new('RGBA', (512,512), (0, 0, 0, 0))
    text_img.paste(bg, (0,0))
    text_img.paste(skin, (0,0), mask=skin)
    frames.append(text_img)

  frames[0].save('out.gif',
                 save_all=True,
                 append_images=frames[1:],
                 duration=100,
                 loop=0)  

警告! Pillow 没有优化 gif 输出。也许您需要使用其他工具进一步压缩它们。

如果你只需要一个动画,考虑保存到WEBP file format 只需在save() 方法中将.gif 的扩展名更改为.webp。你会得到一个更小的文件,所有浏览器都支持它,并且渐变背景的图像质量更好(由于 GIF 8 位调色板,不会有无条纹效果)。