使用 matplotlib 在 python 中动画化线图

Animating a line plot in python with mathplotlib

所以我正在尝试为一条逐渐穿过情节点的线条制作动画,但我似乎无法找到这样做的方法。我试过使用 FuncAnimation 但没有成功,Whosebug 上的类似问题也没有帮助我。有什么建议么? 这是我的代码:

import matplotlib.pyplot as plt
from matplotlib.animation import FuncAnimation
import math
import csv
import sys
import numpy

towns=[['Orleans', '1.750115', '47.980822'],
 ['Bordeaux', '-0.644905', '44.896839'],
 ['Bayonne', '-1.380989', '43.470961'],
 ['Toulouse', '1.376579', '43.662010'],
 ['Marseille', '5.337151', '43.327276'],
 ['Nice', '7.265252', '43.745404'],
 ['Nantes', '-1.650154', '47.385427'],
 ['Rennes', '-1.430427', '48.197310'],
 ['Paris', '2.414787', '48.953260'],
 ['Lille', '3.090447', '50.612962'],
 ['Dijon', '5.013054', '47.370547'],
 ['Valence', '4.793327', '44.990153'],
 ['Aurillac', '2.447746', '44.966838'],
 ['Clermont-Ferrand', '3.002556', '45.846117'],
 ['Reims', '4.134148', '49.323421'],
 ['Strasbourg', '7.506950', '48.580332'],
 ['Limoges', '1.233757', '45.865246'],
 ['Troyes', '4.047255', '48.370925'],
 ['Le Havre', '0.103163', '49.532415'],
 ['Cherbourg', '-1.495348', '49.667704'],
 ['Brest', '-4.494615', '48.447500'],
 ['Niort', '-0.457140', '46.373545']]

order=[0,
 8,
 17,
 14,
 9,
 18,
 19,
 7,
 6,
 21,
 1,
 2,
 3,
 12,
 13,
 16,
 11,
 4,
 5,
 10,
 15,
 20,
 0]

fig=plt.figure()
fig.patch.set_facecolor('#ffffff')
fig.patch.set_alpha(0.7)
ax = plt.axes()
ax.set_facecolor('grey')
plt.axis('off')   



for i in range(len(order)):
    plt.plot(float(towns[order[i]][1]), float(towns[order[i]][2]), 'o', color='black')
    try:
        line = plt.Line2D((float(towns[order[i]][1]), float(towns[order[i+1]][1])), (float(towns[order[i]][2]), float(towns[order[i+1]][2])), lw=2)
        plt.gca().add_line(line)
    except IndexError:
        pass

towns[order[i]][1] 是 x 值 towns[order[i]][2] 是 y 值

我怎样才能让它看起来像这样:

import numpy as np
import matplotlib.pyplot as plt
from matplotlib.animation import FuncAnimation

x_data = []
y_data = []

fig, ax = plt.subplots()
ax.set_xlim(0, 105)
ax.set_ylim(0, 12)
line, = ax.plot(0, 0)

def animation_frame(i):
    x_data.append(i * 10)
    y_data.append(i)

    line.set_xdata(x_data)
    line.set_ydata(y_data)
    return line, 

animation = FuncAnimation(fig, func=animation_frame, frames=np.arange(0, 10, 0.1), interval=10)
plt.show()

谢谢

有几种方法可以做到这一点,但一种选择是使用列表理解来扩展数据并将其传递给一个函数,以便以受控方式显示它。准备好所有数据(txyl)后,使用 animate 函数将所有城市放置在图表中 ax.plot(x, y,...) 和带有 ax.annotate 的城市名称。然后,传递给 Matplotlib 函数 FuncAnimation 一个函数(下面代码中的 update)在每个帧更新时调用以刷新正在显示的线段。

def animate(t, x, y, l):
    fig, ax = plt.subplots()

    # fit the labels inside the plot
    ax.set_xlim(min(x)-1, max(x)+3)
    ax.set_ylim(min(y)-1, max(y)+1)

    # place all cities on the graph
    cities, = ax.plot(x, y, marker = "o", color = "black", ls = "", markersize = 5)
    line_1, = ax.plot([], [], marker = "", color = "blue", ls ="-", lw = 2)

    LABEL_OFFSET = 1.003 # text label offset from marker
    for i in t:
        ax.annotate(f'{l[i]}', xy=(x[i]*LABEL_OFFSET,y[i]*LABEL_OFFSET))

    def update(i):
        line_1.set_data(x[:i], y[:i])
        return line_1

    anim = FuncAnimation(fig, update, frames=len(t)+1, interval=300, repeat=True)
    return anim

t = range(len(order))
x = [float(towns[order[i]][1]) for i in t]
y = [float(towns[order[i]][2]) for i in t]
l = [towns[order[i]][0] for i in t]

cities_travel = animate(t, x, y, l)
cities_travel.save("cities_travel.gif", writer = PillowWriter(fps = 2))