python实现gif动画(matplotlib、imageio、pillow))

点击上方“AI搞事情”关注我们


GIF(Graphics Interchange Format,图形交换格式)是一种位图图像格式。

GIF格式的图像文件具有如下特点:

  1. GIF格式图像文件的扩展名是“.gif”。

  2. 对于灰度图像表现最佳。

  3. 具有GIF87a和GIF89a两个版本。

  4. 采用改进的LZW压缩算法处理图像数据。

  5. 调色板数据有通用调色板和局部调色板之分,有不同的颜色取值。

  6. 不支持24bit彩色模式,最多存储256色。

1. matplotlib

matplotlib 中的 animation 模块绘制动态图,绘制心形动态函数

  • 安装matplotlib

pip install matplotlib
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.animation as animation
fig, ax = plt.subplots()
# fig.patch.set_alpha(0.)  # 设置透明背景,但animation不起作用
plt.axis('off')          # 关闭坐标轴
#初始化窗口和坐标轴
xdata, ydata = [], []
#初始化x,y列表
ln, = ax.plot([], [], 'r-', animated=False)
#初始化绘制曲线的参数。
#init()函数初始化x,y轴范围
def init():
    ax.set_xlim(-20,20)
    ax.set_ylim(-20,15)
    return ln,
#迭代器,根据传入的frame更新x,y值
def update(frame):
    # 心形函数
    x = 16 * np.sin(frame) ** 3
    y = 13 * np.cos(frame) - 5 * np.cos(2 * frame) - 2 * np.cos(3 * frame) - np.cos(4 * frame)
    xdata.append(x)
    ydata.append(y)
    ln.set_data(xdata, ydata)
    return ln,
# interval:帧持续时间(milliseconds)
anim = animation.FuncAnimation(fig, update, frames=np.linspace(0, 10, 100), init_func=init, interval=1, repeat=False, blit=True)
anim.save('tmp.gif', writer='pillow')
plt.show()

动态图无法绘制透明背景。

2. imageio

pip install imageio

https://blog.csdn.net/guduruyu/article/details/77540445

# -*- coding: UTF-8 -*-
import imageio
def create_gif(image_list, gif_name):
    frames = []
    for image_name in image_list:
        frames.append(imageio.imread(image_name))
    # Save them as frames into a gif
    imageio.mimsave(gif_name, frames, 'GIF', duration=0.01)  # duration:秒
    return

def main():
    png_path = 'images'
    png_files = os.listdir(png_path)
    image_list =[png_path + "/%03d.png" % frame_id for frame_id in range(len(png_files))]
    gif_name = 'created_gif.gif'
    create_gif(image_list, gif_name)

if __name__ == '__main__':
    main()

imageio库有个弊端是好像不能将透明背景的png图像生成透明背景的gif图像

3. pillow

pip install pillow

GitHub:https://github.com/python-pillow/Pillow

官方文档:

https://pillow.readthedocs.io/en/latest/handbook/image-file-formats.html#gif

参数说明

pillow可以通过设置transparency参数,使GIF背景为透明的。

import os
import random
from PIL import Image, ImageDraw, ImageSequence
def gif2pngs(gif_path, png_path):
    """gif图像拆成若干png帧图"""
    img = Image.open(gif_path)
    for ind, frame in enumerate(ImageSequence.all_frames(img)):
        # 保存每一帧图像
        frame.save(os.path.join(png_path, "%03d.png" % ind))
def pngs2gif(png_path, gif_name):
    """png帧图生成gif图像"""
    frames = []
    png_files = os.listdir(png_path)
    for frame_id in range(len(png_files)):
        frame = Image.open(os.path.join(png_path, "%03d.png" % frame_id))
        frames.append(frame)
    # frames.reverse()  # 将图像序列逆转
    frames[0].save(gif_name, save_all=True, append_images=frames[1:], loop=0, disposal=2)
def draw_gif(gif_name):
    """通过PIL绘制动态图"""
    size = 50
    i = 0
    colors = ['red', 'blue', 'green', 'gray']
    # 绘制随机闪现的球
    frames = []
    while i < 100:
        img = Image.new("RGBA", (800, 800), color=(0, 0, 0))
        draw = ImageDraw.Draw(img)
        x = random.randint(-800, 800)
        y = random.randint(-800, 800)
        if x-size < 0 or x-size > img.size[0]:
            continue
        if y-size < 0 or y-size > img.size[1]:
            continue
        draw.ellipse((x, y, x + size, y + size), fill=colors[random.randint(0, 3)])
        frames.append(img)
        i += 1
    # transparency 透明背景设置,duration单位 毫秒, loop=0无限循环 loop=1循环一次,不设置,不循环
    frames[0].save(gif_name, save_all=True, append_images=frames[1:], transparency=0, duration=100, loop=0, disposal=2)
if __name__ == '__main__':
    gif2pngs('下班了.gif', 'images')
    pngs2gif('images', 'tmp.gif')
    draw_gif('ball.gif')
图片

gif2pngs('下班了.gif', 'images')函数执行后会在images保存帧图像

图片
图片

长按二维码关注我们

有趣的灵魂在等你

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值