Python中的Matplotlib - 绘制形状并为它们设置动画

时间:2010-01-21 12:52:32

标签: python networking matplotlib simulation

所以我代表一个令牌环网络(在SimPy中进行模拟),我是matplotlib的新手,但我被告知在视觉上表示我的模拟真的很好。

所以我用Google搜索并找出如何绘制形状和线条 - 分别使用add_patch和add_line到轴(我相信)。所以现在我有这个输出绝对没问题:

(无法发布图片!!) http://img137.imageshack.us/img137/7822/screenshot20100121at120.png

但我使用pylab.show()函数得到这个,我想我想要的是使用pylab.plot()函数来实现这一点,这样我就可以在使用pylab进行模拟时更新它。之后画出()。

我的代码如下:

plab.ion()

plab.axes()

for circ in self.circleList:
    plab.gca().add_patch(circ)

for line in self.lineList:
    plab.gca().add_line(line)

plab.axis('scaled')
plab.show()

其中circleList和lineList是包含图表上的圆圈和线条的列表

我可能在这里误解了一些简单的东西,但我实际上找不到任何使用plot()函数的基于图形的示例。


澄清:

如何使用pylab.plot()而不是pylab.show()来获得相同的输出?

3 个答案:

答案 0 :(得分:4)

使用绘图方法复制图像:

from pylab import *

points = []
points.append((-0.25, -1.0))
points.append((0.7, -0.7))
points.append((1,0))
points.append((0.7,1))
points.append((-0.25,1.2))
points.append((-1,0.5))
points.append((-1,-0.5))
points.append((-0.25, -1.0))

a_line = plot(*zip(*points))[0]
a_line.set_color('g')
a_line.set_marker('o')
a_line.set_markerfacecolor('b')
a_line.set_markersize(30)
axis([-1.5,1.5,-1.5,1.5])

show()

基于评论的编辑

这使用python多处理库在单独的进程中运行matplotlib动画。主进程使用队列将数据传递给它,然后更新绘图图像。

# general imports
import random, time
from multiprocessing import Process, Queue

# for matplotlib
import random
import numpy as np
import matplotlib
matplotlib.use('GTKAgg') # do this before importing pylab

import matplotlib.pyplot as plt
from matplotlib.patches import Circle


def matplotLibAnimate(q,points):

    # set up initial plot
    fig = plt.figure()
    ax = fig.add_subplot(111)


    circles = []
    for point in points:
        ax.add_patch(Circle(point,0.1))

    a_line, = ax.plot(*zip(*points))
    a_line.set_color('g')
    a_line.set_lw(2)

    currentNode = None  
    def animate(currentNode = currentNode):
        while 1:
            newNode = q.get()
            if currentNode: currentNode.remove()
            circle = Circle(newNode,0.1)
            currentNode = ax.add_patch(circle)
            circle.set_fc('r')
            fig.canvas.draw()

    # start the animation
    import gobject
    gobject.idle_add(animate)
    plt.show()

#initial points
points = ((-0.25, -1.0),(0.7, -0.7),(1,0),(0.7,1),(-0.25,1.2),(-1,0.5),(-1,-0.5),(-0.25, -1.0))
q = Queue()
p = Process(target = matplotLibAnimate, args=(q,points,))
p.start()

# feed animation data
while 1:
    time.sleep(random.randrange(4))
    q.put(random.sample(points,1)[0])

当然,在这样做之后,我认为你会更好地使用whatnick的图像解决方案。我创建自己的GUI,而不是使用内置小部件的matplotlibs。然后我会通过生成PNG并交换它来“动画”我的GUI。

答案 1 :(得分:1)

核心技术是使用set_data更新正在渲染的元素的数据。然后调用draw()。查看您的circle和line元素是否具有set_data函数。否则,您可以使用pyvtk。另一种选择是将图形渲染并保存到png文件中,然后再从这些文件构建动画。

答案 2 :(得分:1)

听起来Mark有你想要的答案,但是如果你决定采用whatnick的方法并从个别png构建动画,这里是实现Amit建议使用mencoder的代码(来自http://en.wikibooks.org/wiki/Mplayer ):

mencoder mf://*.png -mf w=400:h=400 -ovc lavc -lavcopts vcodec=xvid -of avi -o output.avi