Python genera animación gif a través del paquete matplotlib y el paquete gif
Uso matplotlib
Hay muchas formas de generar gif animados, generalmente usados convencionalmente matplotlib
en la implementación de la función del animation
módulo FuncAnimation
. matplotlib
Vi la gif
introducción del paquete de animación de terceros en el sitio web oficial .
gif
Descripción general del paquete
gif
El paquete es una extensión de animación que los apoyos Altair
, matplotlib
y Plotly
. gif
Dependencia PIL
, es decir pillow
, requisito Pillow>=7.1.2
. Paquete de
instalación gif
,pip install gif
Principio de animación
Todo 动画
está compuesto 帧(frame)
, un fotograma es una imagen fija y los sucesivos fotogramas forman una animación. Por lo general, decimos el número de fotogramas. En pocas palabras, es el número de fotogramas de una imagen transmitida en 1 segundo. También se puede entender que el procesador gráfico puede actualizar varias veces por segundo, lo que generalmente se fps(Frames Per Second)
expresa. La clave para hacer animaciones: cómo generar fotogramas y cuántos fotogramas por segundo.
gif
Interpretación del paquete
gif
El paquete es muy conciso, hay un solo archivo gif.py
, el archivo contiene principalmente options
clases frames
y save
dos funciones.
options
clase
Proporcionar una versión condensada Altair
, matplotlib
y Plotly
guardar o ajustes de exportación. Como matplotlib
ejemplo, proporcione la siguiente configuración.
-
ppp (int): la resolución en puntos por pulgada
-
facecolor (colorspec): el color de la cara de la figura
-
edgecolor (colorspec): el color del borde de la figura
-
transparente (bool): si es True, los parches de los ejes serán todos transparentes
Método de configuración: gif.options.matplotlib["dpi"] = 300
Principio: options
cree un matplotlib
diccionario en el constructor para guardar la configuración y luego páselo al matplotlib
paquete subyacente .
frames
función
Función de decorador, a través del paquete correspondiente para escribir una función de dibujo personalizado para generar una imagen de un solo cuadro.
save
función
Genere animación basada en la secuencia de cuadros.
def save(frames, path, duration=100, unit="milliseconds", between="frames", loop=True):
"""Save decorated frames to an animated gif.
- frames (list): collection of frames built with the gif.frame decorator
- path (str): filename with relative/absolute path
- duration (int/float): time (with reference to unit and between)
- unit {"ms" or "milliseconds", "s" or "seconds"}: time unit value
- between {"frames", "startend"}: duration between "frames" or the entire gif ("startend")
- loop (bool): infinitely loop the animation
frames
Es decir @gif.frame
, la secuencia de fotogramas generada según la función de dibujo decorado, que se personaliza aquí según sea necesario. duration
La duración está determinada por la unidad unit
y el modo between
, y el valor predeterminado es frames
el intervalo de tiempo entre fotogramas. unit
Es decir, la unidad de duración, que admite milisegundos y segundos, y el valor predeterminado es milisegundos. between
Ese modo de cálculo de duración, predeterminado, frames
es decir, duration
el intervalo de tiempo entre cuadros, startend
un modo duration=duration /len(frames)
, es decir, duration
todos los cuadros, la duración de toda la animación.
gif
Práctica de animación gif de generación de paquetes
import random
from matplotlib import pyplot as plt
import gif
# 构造数据
x = [random.randint(0, 100) for _ in range(100)]
y = [random.randint(0, 100) for _ in range(100)]
# 设置选项
gif.options.matplotlib["dpi"] = 300
# 使用gif.frame装饰器构造绘图函数,即如何生成静态的帧
@gif.frame
def plot(i):
xi = x[i * 10:(i + 1) * 10]
yi = y[i * 10:(i + 1) * 10]
plt.scatter(xi, yi)
plt.xlim((0, 100))
plt.ylim((0, 100))
# 构造帧序列frames,即把生成动画的所有帧按顺序放在列表中
frames = []
for i in range(10):
frame = plot(i)
frames.append(frame)
# 根据帧序列frames,动画持续时间duration,生成gif动画
gif.save(frames, 'example.gif', duration=3.5, unit="s", between="startend")
Tome la curva en forma de corazón como ejemplo para comparar la diferencia entre el gif
paquete y el animation
módulo para lograr la animación.
Dibujo de curva en forma de corazón
from matplotlib import pyplot as plt
import numpy as np
t = np.linspace(0, 6, 100)
x = 16 * np.sin(t) ** 3
y = 13 * np.cos(t) - 5 * np.cos(2 * t) - 2 * np.cos(3 * t) - np.cos(4 * t)
fig = plt.figure(figsize=(5, 3), dpi=100)
plt.scatter(x, y)
plt.show()
gif
Cómo se implementa el paquete
import numpy as np
import gif
from matplotlib import pyplot as plt
t = np.linspace(0, 6, 100)
x = 16 * np.sin(t) ** 3
y = 13 * np.cos(t) - 5 * np.cos(2 * t) - 2 * np.cos(3 * t) - np.cos(4 * t)
@gif.frame
def plot_love(x, y):
plt.figure(figsize=(5, 3), dpi=100)
plt.scatter(x, y, 60, c="r", alpha=0.7, marker=r"$\heartsuit$")
plt.axis("off")
frames = []
for i in range(1, len(x)):
of = plot_love(x[:i], y[:i])
frames.append(of)
gif.save(frames, "love.gif", duration=80)
matplotlib
FuncAnimation
Implementación de funciones convencionales
from matplotlib import pyplot as plt
import matplotlib.animation as animation
import numpy as np
t = np.linspace(0, 6, 100)
x = 16 * np.sin(t) ** 3
y = 13 * np.cos(t) - 5 * np.cos(2 * t) - 2 * np.cos(3 * t) - np.cos(4 * t)
data=[i for i in zip(x,y)]
def plot_love(data):
x, y = data
plt.scatter(x, y, 60, c="r", alpha=0.7, marker=r"$\heartsuit$")
fig=plt.figure(figsize=(5, 3), dpi=100)
plt.axis("off")
animator = animation.FuncAnimation(fig, plot_love, frames=data, interval=80)
animator.save("love.gif", writer='pillow')
matplotlib
PillowWriter
Implementación de clases de bajo nivel
from matplotlib import pyplot as plt
import matplotlib.animation as animation
import numpy as np
t = np.linspace(0, 6, 100)
x = 16 * np.sin(t) ** 3
y = 13 * np.cos(t) - 5 * np.cos(2 * t) - 2 * np.cos(3 * t) - np.cos(4 * t)
def plot_love(x, y):
plt.scatter(x, y, 60, c="r", alpha=0.7, marker=r"$\heartsuit$")
fig = plt.figure(figsize=(5, 3), dpi=100)
plt.axis("off")
writer = animation.PillowWriter(fps=15)
with writer.saving(fig, "love21.gif", dpi=100):
for i in range(1, len(x)):
plot_love(x[i], y[i])
writer.grab_frame()