更新Jupyter Notebook中的交互式绘图

时间:2017-12-05 16:37:48

标签: python matplotlib jupyter-notebook

我正在尝试创建一个使用matplotlib绘制一些数据的Jupyter笔记本。有人告诉我,当我使用pcolormesh时,不是从头创建一个图,而是可以在绘图对象上使用set_array函数,这大大加快了绘图速度。这样做的人使用matplotlib进行批处理图像,所以使用set_ray然后调用save_fig,这样就行了。我想使用matplotlib在jupyter笔记本中绘制数据。

这是一个示例Jupyter Notebook,其中包含使用pcolormesh绘制2个blob的示例,以及用于更改其中一个blob的位置的Jupyter Widget滑块:

链接到笔记本: mpl_interactive_plot.ipynb

在示例中,我为绘图设置了一个类。在下一个单元格中,我调用create_plot(),它创建并显示绘图。在最后一个单元格中,我创建了一个Jupiter Widgets滑块,它有一个回调,当滑块改变位置时,它应该更新在前一个单元格中创建的绘图。

我使用对pcolormesh的调用来创建绘图:

self.plot_arr[0] = self.axarr[0].pcolormesh(self.xarr,self.yarr,self.blob1_arr,cmap='viridis')

我重新计算传递给滑块的回调函数中数据数组的值,并调用以下代码来更新图:

self.plot_arr[0].set_array(self.blob1_arr)

更新数组。这似乎对情节没有影响。我似乎需要调用某种更新/刷新功能来触发使用新数组重绘的情节,但所有明显的候选者似乎都会导致情节消失。我正在努力做到明智,这是正确的方法吗?

以下是从笔记本中提取的代码:

import matplotlib
import matplotlib.pyplot
import numpy
import ipywidgets

get_ipython().magic('matplotlib notebook')
def gaussian_blob(xarr, yarr, blob_params):
    blob_dist = (xarr - blob_params[0]) **2 + (yarr - blob_params[1])**2
    gaussian_func = numpy.exp(-blob_dist / blob_params[2])
    return gaussian_func

class MyPlot(object):
    def __init__(self):
        self.blob1_params = [2.0,5.0,5.0]
        self.blob2_params = [8.0,12.0,5.0]
        self.plot_arr = None
        self.fig_name = 'blob_plots'
        self.f1 = None
        self.axarr = None
    def calc_data(self):
        self.xarr, self.yarr = numpy.meshgrid(range(10),range(15))
        self.blob1_arr = gaussian_blob(self.xarr, self.yarr, self.blob1_params)
        self.blob2_arr = gaussian_blob(self.xarr, self.yarr, self.blob2_params)
    def create_plot(self):
        self.calc_data()
        #print(self.blob1_arr[2,:])
        #matplotlib.pyplot.figure(self.fig_name).clear()
        self.f1, self.axarr = matplotlib.pyplot.subplots(num=self.fig_name,
                                                         ncols=2,
                                                         nrows=1,
                                                         figsize=matplotlib.pyplot.figaspect(0.5))
        self.plot_arr = [None] * 2
        self.plot_arr[0] = self.axarr[0].pcolormesh(self.xarr,self.yarr,self.blob1_arr,cmap='viridis')
        self.plot_arr[1] = self.axarr[1].pcolormesh(self.xarr,self.yarr,self.blob2_arr,cmap='viridis')
        matplotlib.pyplot.show()        
    def update_plot(self):
        self.calc_data()
        self.plot_arr[0].set_array(self.blob1_arr)
        self.plot_arr[1].set_array(self.blob2_arr)
        # probably need some sort of update/refresh call, but what?
    def on_x_centre_change(self, xc_event):
        self.blob1_params[0] = xc_event['new']
        self.update_plot()

plot_obj1 = MyPlot()
plot_obj1.create_plot()
pslider = ipywidgets.IntSlider(value=2, 
                            min=0, 
                            max=10,
                            description='left x centre',
                              continuous_update=False)
pslider.observe(plot_obj1.on_x_centre_change, names='value')
pslider

0 个答案:

没有答案