How to add a time control panel to a FuncAnimation from matplotlib - python-2.7

I am currently using matplotlib.animation.FuncAnimation() to display an animation of my work, on a figure.
It is working very well, and I understand the arguments I am using ( interval, time range , ...) However, I was wondering if there was a way to implement (maybe directly to the figure) a panel containing the animation, a scroll-bar or whatever, which allows me to :
Move forward or backwards quickly to the time zone of interest.
Show at what point of the animation I am ( 10%, then 20%,...).
Basically, is a way to control the animation in python on the figure like the way I would control it as a video file played by a video player?
If needed, this is what looks like the code for this animation :
def init():
im1.set_data(XYslice[0, :, :])
im2.set_data(XZslice[0, Nplans/2:, :])
return([im1, im2])
def animate(t):
im1.set_data(XYslice[t, :, :])
im2.set_data(XZslice[t, Nplans/2:, :])
return [im1, im2]
anim = animation.FuncAnimation(fig, animate, np.arange(Ntime), interval=200,
blit=True, init_func=init, repeat=True)

What you are talking about is a GUI. The simplest example uses the matplotlib inbuilt widgets:
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.mlab import bivariate_normal
from matplotlib.widgets import Slider, Button
#Setup figure and data
fig, ax = plt.subplots()
plt.subplots_adjust(bottom=0.25)
delta = 0.5
t = np.arange(0.0, 100.0, 0.1)
x = np.arange(-3.0, 4.001, delta)
y = np.arange(-4.0, 3.001, delta)
X, Y = np.meshgrid(x, y)
Z1 = bivariate_normal(X, Y, 1.0, 1.0, 0.0, 0.0)
Z2 = bivariate_normal(X, Y, 1.5, 0.5, 1, 1)
Z = (Z1 - Z2) * 5.
cmap = plt.cm.rainbow
im = ax.pcolormesh(X, Y, Z, cmap=cmap)
fig.colorbar(im)
axcolor = 'lightgoldenrodyellow'
axtime = plt.axes([0.25, 0.1, 0.65, 0.03], axisbg=axcolor)
stime = Slider(axtime, 'Time', 0.0, 100.0, valinit=50.0)
#Routines to reset and update sliding bar
def reset(event):
stime.reset()
def update(val):
time = stime.val/10.
Z = (Z1 - Z2) * time
im.set_array(Z.ravel())
fig.canvas.draw()
#Bind sliding bar and reset button
stime.on_changed(update)
resetax = plt.axes([0.8, 0.025, 0.1, 0.04])
button = Button(resetax, 'Reset', color=axcolor, hovercolor='0.975')
button.on_clicked(reset)
plt.show()
This should be a start. If you want it to look better (and add more functionality) then you need to go to a GUI framework like wxpython, check out this example.
An example which is more inline with your data-structure would go as follows:
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.mlab import bivariate_normal
from matplotlib.widgets import Slider, Button
#Setup figure and data
fig, ax = plt.subplots()
plt.subplots_adjust(bottom=0.25)
delta = 0.5
t = np.linspace(0.0, 100.0, 256)
x = np.linspace(-4.0, 4.001, 512)
y = np.linspace(-4.0, 4.001, 512)
X, Y = np.meshgrid(x, y)
Z1 = bivariate_normal(X, Y, 1.0, 1.0, 0.0, 0.0)
Z2 = bivariate_normal(X, Y, 1.5, 0.5, 1, 1)
XZslice = np.zeros((256,512,512))
for i in range(t.shape[0]):
XZslice[i,:,:] = (Z1 - Z2) * t[i]/10.
cmap = plt.cm.rainbow
im = ax.pcolormesh(XZslice[128,:,:], cmap=cmap)
fig.colorbar(im)
axcolor = 'lightgoldenrodyellow'
axtime = plt.axes([0.25, 0.1, 0.65, 0.03], axisbg=axcolor)
stime = Slider(axtime, 'Time', 0.0, 100.0, valinit=50.0)
#Routines to reset and update sliding bar
def reset(event):
stime.reset()
def update(val):
time = int(stime.val/100.* 256)
im.set_array(XZslice[time,:,:].ravel())
fig.canvas.draw()
#Bind sliding bar and reset button
stime.on_changed(update)
resetax = plt.axes([0.8, 0.025, 0.1, 0.04])
button = Button(resetax, 'Reset', color=axcolor, hovercolor='0.975')
button.on_clicked(reset)
plt.show()

Related

How to find and draw the intersection points of contour shapes

I'm trying to find the points of intersection between the line passing through point V and conic. The conic graph is not solvable relative to y ( or x), so it was depicted using contour. Is there a method for finding the intersection points of contour graphs?
enter image description here
Here is the code:
import numpy as np
import matplotlib.pyplot as plt
p = (input("choose point P on axis OX: "))
print(p)
q = (input("choose point Q on axis OX: "))
print(q)
v = (input("choose point V on axis OX: "))
print(v)
k=3
X = np.arange(-50, 50, 0.05)
Y = k*X
plt.plot(X,Y)
plt.plot(0,0)
plt.scatter(0.0, 0.0, color='white', marker='o')
plt.text(0.0, 0.0, "O", horizontalalignment="center")
plt.plot(-v,0)
plt.scatter(-v, 0, color='red', marker='o')
plt.text(-v, 0.8, "V", horizontalalignment="center")
xmin= -10
xmax= 10
ymin= -10
ymax= 10
ax = plt.gca()
ax.get_xlim()
ax.set_xlim([xmin,xmax])
ax.set_ylim([ymin,ymax])
ax.spines['left'].set_position('center')
ax.spines['bottom'].set_position('center')
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
#Create random point B1
b1=4
plt.plot(0.0,b1)
plt.scatter(0.0, b1, color='blue', marker='o')
plt.text(0.8, b1, "B1", horizontalalignment="center")
x, y = np.meshgrid(X, X)
#Create VB1
l3 = b1*x+b1*v - v*y
vb = plt.contour(x,y, l3, [0], colors='k')
# l3 = b1*X/v + b1
# plt.plot(X,l3)
#Create conic
conic = x*x*b1*2*p*k-x*x*b1*2*q*k+x*x*k*k+y*y-b1*2*y+2*b1*q*x*y
cnc = plt.contour(x, y, (conic), [0], colors='k')
I tried to do something like that:
c = cnc.intersection(vb)
print(c)
or
# https://stackoverflow.com/questions/28766692/intersection-of-two-graphs-in-python-find-the-x-value
idx = np.argwhere(np.diff(np.sign(cnc - vb))).flatten()
plt.plot(x[idx], y[idx], 'ro')
My last attempt:
import numpy as np
import matplotlib.pyplot as plt
p,q,v,k,b=5,7,2,3,4
X = np.arange(-50, 50, 0.05)
plt.plot(-v,0)
plt.scatter(-v, 0, color='red', marker='o')
plt.text(-v, 0.8, "V", horizontalalignment="center")
xmin,xmax,ymin,ymax=-10,10,-10,10
ax = plt.gca()
ax.get_xlim()
ax.set_xlim([xmin,xmax])
ax.set_ylim([ymin,ymax])
ax.spines['left'].set_position('center')
ax.spines['bottom'].set_position('center')
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
plt.plot(0.0,b)
plt.scatter(0.0, 1, color='blue', marker='o')
x, y = np.meshgrid(X, X)
l = b*x+b*v-v*y
vb = plt.contour(x,y, l, [0], colors='k')
conic = x*x*b*2*p*k-x*x*b*2*q*k+x*x*k*k+y*y-b*2*y+2*b*q*x*y
cnc = plt.contour(x, y, (conic), [0], colors='k')
c = cnc.collections[0].get_paths()[1]
v = c.vertices
x1 = v[:,0]
y1 = v[:,1]
plt.plot(x1,y1)
vb1 = vb.collections[0].get_paths()[0]
v1 = vb1.vertices
x2 = v1[:,0]
y2 = v1[:,1]
plt.plot(x2,y2,color='red')
# def find_roots(x,y):
# s = np.abs(np.diff(np.sign(y))).astype(bool)
# return x[:-1][s] + np.diff(x)[s]/(np.abs(y[1:][s]/y[:-1][s])+1)
#
# z = find_roots(x1-x2,y1-y2)
# plt.plot(z, np.zeros(len(z)), marker="o", ls="", ms=4)
plt.show()
enter image description here
It's a little more complicated. The problem is that (a) the points in the contour are not necessarily sorted and (b) the two contours do not have a common support.
So one would need to (a) sort the points along x, and (b) create an array of common values, on which to interpolate first.
import numpy as np
import matplotlib.pyplot as plt
p,q,v,k,b=5,7,2,3,4
X = np.arange(-50, 50, 0.05)
plt.plot(-v,0)
plt.scatter(-v, 0, color='red', marker='o')
plt.text(-v, 0.8, "V", horizontalalignment="center")
xmin,xmax,ymin,ymax=-10,10,-10,10
ax = plt.gca()
ax.get_xlim()
ax.set_xlim([xmin,xmax])
ax.set_ylim([ymin,ymax])
ax.spines['left'].set_position('center')
ax.spines['bottom'].set_position('center')
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
x, y = np.meshgrid(X, X)
l = b*x+b*v-v*y
vb = plt.contour(x,y, l, [0], colors='red')
conic = x*x*b*2*p*k-x*x*b*2*q*k+x*x*k*k+y*y-b*2*y+2*b*q*x*y
cnc = plt.contour(x, y, (conic), [0], colors='blue')
c = cnc.collections[0].get_paths()[1]
v = c.vertices
x1 = np.sort(v[:,0])
y1 = v[np.argsort(v[:,0]),1]
vb1 = vb.collections[0].get_paths()[0]
v1 = vb1.vertices
x2 = np.sort(v1[:,0])
y2 = v1[np.argsort(v1[:,0]),1]
def find_roots(x,y):
s = np.abs(np.diff(np.sign(y))).astype(bool)
return x[:-1][s] + np.diff(x)[s]/(np.abs(y[1:][s]/y[:-1][s])+1)
x = np.linspace(max(x1.min(), x2.min()), min(x1.max(), x2.max()), 1000)
y1i = np.interp(x, x1, y1 ) # blue
y2i = np.interp(x, x2, y2 ) # red
x_intersect = find_roots(x,y2i-y1i)
y_intersect = np.interp(x_intersect, x, y2i)
plt.plot(x_intersect, y_intersect, marker="X", ms=5, color="limegreen")
plt.show()
The point of intersection is the green dot.
Of course one needs to do the same for the other arm of the conic contour (cnc.collections[0].get_paths()[0]) if desired.

how to display the all intervals in colorbar using matplotlib

This is my code.I mentioned here 50 intervals,when i drag the slider then only i got 6 or 7 intervals,but i want to display the all my intervals in my colorbar. So can any one please guide me.Thank you in advance.
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.widgets import Slider, Button
import matplotlib.colors
ax = plt.subplot(111)
plt.subplots_adjust(left=0.25, bottom=0.25)
img_data = np.random.rand(50,50)
c_max = 2
img = ax.imshow(img_data, interpolation='nearest')
cb = plt.colorbar(img)
axcolor = 'lightgoldenrodyellow'
ax_cmax = plt.axes([0.25, 0.15, 0.65, 0.03])
s_cmax = Slider(ax_cmax, 'max', 0, 50, valfmt=c_max)
def update(val, s=None):
# _cmin = s_cmin.val
_cmax = s_cmax.val
img.set_clim(_cmax)
plt.draw()
s_cmax.on_changed(update)
plt.show()
The argument to Slider called valfmt should be a string which is used to format the slider value.
So if you wanted to display 2 decimal places to the float you would need to make c_max = "%1.2f". Note that if you want to keep the minimum value at 0 you need to set that too in img.set_clim(0, _cmax)
c_max = "%1.2f"
img = ax.imshow(img_data, interpolation='nearest')
cb = plt.colorbar(img)
axcolor = 'lightgoldenrodyellow'
ax_cmax = plt.axes([0.25, 0.15, 0.65, 0.03])
s_cmax = Slider(ax_cmax, 'max', 0, 50, valfmt=c_max)
def update(val, s=None):
# _cmin = s_cmin.val
_cmax = s_cmax.val
img.set_clim(0, _cmax)
plt.draw()
s_cmax.on_changed(update)
plt.show()

Colour schemes used to present data on sphere

Hi I a have a data set which I project onto a sphere such that the magnitude of the data, as a function of theta and phi, is shown using a colour spectrum (which uses "ax.plot_surface", "plt.colorbar" and "facecolors"). My query is that at this stage I am limited to "cm.hot" and "cm.jet". Does anyone know of any other colour schemes which are available for this purpose. Please see my code and the figures below
Code:
from numpy import*
import math
import matplotlib.pyplot as plt
from matplotlib import cm
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
import matplotlib.cm as cm
#theta inclination angle
#phi azimuthal angle
n_theta = 100 #number of values for theta
n_phi = 100 #number of values for phi
r = 1 #radius of sphere
theta, phi = np.mgrid[0: pi:n_theta*1j,-pi:pi:n_phi*1j ]
x = r*np.sin(theta)*np.cos(phi)
y = r*np.sin(theta)*np.sin(phi)
z = r*np.cos(theta)
inp = []
f = open("data.dat","r")
for line in f:
i = float(line.split()[0])
j = float(line.split()[1])
val = float(line.split()[2])
inp.append([i, j, val])
inp = np.array(inp)
#reshape the input array to the shape of the x,y,z arrays.
c = inp[:,2].reshape((n_phi,n_theta))
#Set colours and render
fig = plt.figure(figsize=(10, 8))
ax = fig.add_subplot(111, projection='3d')
#use facecolors argument, provide array of same shape as z
# cm.<cmapname>() allows to get rgba color from array.
# array must be normalized between 0 and 1
surf = ax.plot_surface(
x,y,z, rstride=1, cstride=1, facecolors=cm.jet(c), alpha=0.9, linewidth=1, shade=False)
ax.set_xlim([-2.0,2.0])
ax.set_ylim([-2.0,2.0])
ax.set_zlim([-2,2])
ax.set_aspect("equal")
plt.title('Plot with cm.jet')
#Label axis.
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Z')
#Creates array for colorbar from 0 to 1.
a = array( [1.0, 0.5, 0.0])
#Creates colorbar
m = cm.ScalarMappable(cmap=cm.jet)
m.set_array(a)
plt.colorbar(m)
plt.savefig('facecolor plots')
f.close()
plt.show()
The following is a list of colormaps provided directly by matplotlib. It's taken from the Colormap reference example.
cmaps = [('Perceptually Uniform Sequential', [
'viridis', 'plasma', 'inferno', 'magma', 'cividis']),
('Sequential', [
'Greys', 'Purples', 'Blues', 'Greens', 'Oranges', 'Reds',
'YlOrBr', 'YlOrRd', 'OrRd', 'PuRd', 'RdPu', 'BuPu',
'GnBu', 'PuBu', 'YlGnBu', 'PuBuGn', 'BuGn', 'YlGn']),
('Sequential (2)', [
'binary', 'gist_yarg', 'gist_gray', 'gray', 'bone', 'pink',
'spring', 'summer', 'autumn', 'winter', 'cool', 'Wistia',
'hot', 'afmhot', 'gist_heat', 'copper']),
('Diverging', [
'PiYG', 'PRGn', 'BrBG', 'PuOr', 'RdGy', 'RdBu',
'RdYlBu', 'RdYlGn', 'Spectral', 'coolwarm', 'bwr', 'seismic']),
('Qualitative', [
'Pastel1', 'Pastel2', 'Paired', 'Accent',
'Dark2', 'Set1', 'Set2', 'Set3',
'tab10', 'tab20', 'tab20b', 'tab20c']),
('Miscellaneous', [
'flag', 'prism', 'ocean', 'gist_earth', 'terrain', 'gist_stern',
'gnuplot', 'gnuplot2', 'CMRmap', 'cubehelix', 'brg', 'hsv',
'gist_rainbow', 'rainbow', 'jet', 'nipy_spectral', 'gist_ncar'])]
To easily view them all you may e.g. use the following 3D colormap viewer (written in PyQt5).
import numpy as np
from mpl_toolkits.mplot3d import Axes3D
from PyQt5 import QtGui, QtCore, QtWidgets
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
from matplotlib.figure import Figure
import sys
class MainWindow(QtWidgets.QMainWindow):
def __init__(self):
QtWidgets.QMainWindow.__init__(self)
self.main_widget = QtWidgets.QWidget(self)
self.fig = Figure()
self.canvas = FigureCanvas(self.fig)
self.ax = self.fig.add_subplot(111, projection=Axes3D.name)
u = np.linspace(0, 2 * np.pi, 100)
v = np.linspace(0, np.pi, 100)
x = 10 * np.outer(np.cos(u), np.sin(v))
y = 10 * np.outer(np.sin(u), np.sin(v))
z = 10 * np.outer(np.ones(np.size(u)), np.cos(v))
# Plot the surface
self.surf = self.ax.plot_surface(x, y, z, cmap="YlGnBu")
self.cb = self.fig.colorbar(self.surf)
self.canvas.setSizePolicy(QtWidgets.QSizePolicy.Expanding,
QtWidgets.QSizePolicy.Expanding)
self.canvas.updateGeometry()
self.dropdown1 = QtWidgets.QComboBox()
items = []
for cats in cmaps:
items.extend(cats[1])
self.dropdown1.addItems(items)
self.dropdown1.currentIndexChanged.connect(self.update)
self.label = QtWidgets.QLabel("A plot:")
self.layout = QtWidgets.QGridLayout(self.main_widget)
self.layout.addWidget(QtWidgets.QLabel("Select Colormap"))
self.layout.addWidget(self.dropdown1)
self.layout.addWidget(self.canvas)
self.setCentralWidget(self.main_widget)
self.show()
self.update()
def update(self):
self.surf.set_cmap(self.dropdown1.currentText())
self.fig.canvas.draw_idle()
if __name__ == '__main__':
app = QtWidgets.QApplication(sys.argv)
win = MainWindow()
sys.exit(app.exec_())

AttributeError: draw_artist can only be used after an initial draw which caches the render

My requirement is to plot the data in polar graph. However I need to keep polar graph in particular angle to looks like "V" shape and data need to plotted in between the particular angle.
In python I don't find a solution to keep the polar graph in particular angle, Example : Graph should be display in between -60 to 60 degree radius. To achieve that I have looked into couple of existing examples and creating required polar graph with FloatingSubplot functions. However I am hitting the issue , when we try to use along with function animation function with blit=True. Error message is displayed is "AttributeError: draw_artist can only be used after an initial draw which caches the render"
Here is my code.
#
import matplotlib
matplotlib.use('Qt4Agg')
import numpy as np
import matplotlib.pyplot as plt
from matplotlib import style
import matplotlib.animation as animation
import mpl_toolkits.axisartist.floating_axes as floating_axes
from matplotlib.transforms import Affine2D
from matplotlib.projections import PolarAxes
from mpl_toolkits.axisartist import angle_helper
from mpl_toolkits.axisartist.grid_finder import MaxNLocator, DictFormatter
from mpl_toolkits.axisartist.floating_axes import GridHelperCurveLinear, FloatingSubplot
plt.close('all')
fig = plt.figure('Practice', dpi=100) # To set the fig title as pratice
ax1 = fig.add_subplot(2, 2, 1) # subplot for 1st plot
plt.ion()
ax1.grid(True)
def fractional_polar_axes(f, thlim=(0, 120), rlim=(0, 20), step=(30, 0.25),
thlabel='theta', rlabel='r', ticklabels=True, theta_offset=0, rlabels=None):
'''Return polar axes that adhere to desired theta (in deg) and r limits. steps for theta
and r are really just hints for the locators.'''
th0, th1 = thlim # deg
r0, r1 = rlim
thstep, rstep = step
tr_rotate = Affine2D().translate(theta_offset, 0)
# scale degrees to radians:
tr_scale = Affine2D().scale(np.pi / 180., 1.)
# pa = axes(polar="true") # Create a polar axis
pa = PolarAxes
tr = tr_rotate + tr_scale + pa.PolarTransform()
theta_grid_locator = angle_helper.LocatorDMS((th1 - th0) // thstep)
r_grid_locator = MaxNLocator((r1 - r0) // rstep)
theta_tick_formatter = angle_helper.FormatterDMS()
if rlabels:
rlabels = DictFormatter(rlabels)
grid_helper = GridHelperCurveLinear(tr,
extremes=(th0, th1, r0, r1),
grid_locator1=theta_grid_locator,
grid_locator2=r_grid_locator,
tick_formatter1=theta_tick_formatter,
tick_formatter2=rlabels)
a = FloatingSubplot(f, 222, grid_helper=grid_helper)
# a = Subplot(f,753, grid_helper=grid_helper)
# f.add_subplot(7,5,(3,34))
f.add_subplot(a)
# adjust x axis (theta):
print(a)
a.axis["bottom"].set_visible(False)
a.axis["top"].set_axis_direction("bottom") # tick direction
a.axis["top"].toggle(ticklabels=ticklabels, label=bool(thlabel))
a.axis["top"].major_ticklabels.set_axis_direction("top")
a.axis["top"].label.set_axis_direction("top")
a.axis["top"].major_ticklabels.set_pad(10)
# adjust y axis (r):
a.axis["left"].set_axis_direction("bottom") # tick direction
a.axis["right"].set_axis_direction("top") # tick direction
a.axis["left"].toggle(ticklabels=True, label=bool(rlabel))
# add labels:
a.axis["top"].label.set_text(thlabel)
a.axis["left"].label.set_text(rlabel)
# create a parasite axes whose transData is theta, r:
auxa = a.get_aux_axes(tr)
print(auxa)
# make aux_ax to have a clip path as in a?:
auxa.patch = a.patch
# this has a side effect that the patch is drawn twice, and possibly over some other
# artists. So, we decrease the zorder a bit to prevent this:
a.patch.zorder = -2
# add sector lines for both dimensions:
thticks = grid_helper.grid_info['lon_info'][0]
rticks = grid_helper.grid_info['lat_info'][0]
print(grid_helper.grid_info['lat_info'])
for th in thticks[1:-1]: # all but the first and last
auxa.plot([th, th], [r0, r1], ':', c='grey', zorder=-1, lw=0.5)
for ri, r in enumerate(rticks):
# plot first r line as axes border in solid black only if it isn't at r=0
if ri == 0 and r != 0:
ls, lw, color = 'solid', 1, 'black'
else:
ls, lw, color = 'dashed', 0.5, 'grey'
# From http://stackoverflow.com/a/19828753/2020363
auxa.add_artist(plt.Circle([0, 0], radius=r, ls=ls, lw=lw, color=color, fill=False,
transform=auxa.transData._b, zorder=-1))
return auxa
def animate(i):
global loopcount, th, r
th = th+.1
r = r+.1
datapoints.set_offsets(np.vstack((th,r)).T)
#print("in animate")
return datapoints,
if __name__ == '__main__':
r_locs = [0,5,10, 15, 20]
r_labels = ['0', '5', '10', '15', '20']
r_ticks = {loc: label for loc, label in zip(r_locs, r_labels)}
a1 = fractional_polar_axes(fig, thlim=(-60, 60), step=(20, 5),
theta_offset=90, rlabels=r_ticks)
th= 20
r=10
a1.scatter(th,r , c = 'r', alpha = 0.5, linewidths = '.2', s = 20) # plotting the line at thetha 20 and radius 10
datapoints = a1.scatter([], [], c='b', alpha = 0.5, linewidths = '.2', s = 20) # creating scatter line with given instruction,
ani = animation.FuncAnimation(fig, animate, frames=30, interval=20, blit=True)
plt.show(block=True)
#
"""
Above code is working perfectly fine with blit=False and also same solution working fine with line and scatter plotting in normal graph.
Please someone help me to resolve the issue.
"""

How to add a plot to a Figure in matplotlib?

i'm using matplotlib with django. I'm trying to create bar charts.
i followed the cookbook, but i just got a grey rectangular box.
Now I'm using the following code, and have a title and axes.
How can I add a bar graph to the figure? Currently there is no actual data inside the axes.
Here's my charting code:
from matplotlib.backends.backend_agg import FigureCanvasAgg
from matplotlib.figure import Figure
import matplotlib.pyplot as plt
class Chart(object):
## Creates a bar chart of the given data
#staticmethod
def bar(data):
figure = Figure(figsize=(6,6))
ax = figure.add_axes([0.1, 0.1, 0.8, 0.8])
labels = 'Frogs', 'Hogs', 'Dogs', 'Logs'
fracs = [15, 30, 45, 10]
explode=(0, 0.05, 0, 0)
plt.pie(fracs, explode=explode, labels=labels, autopct='%1.1f%%', shadow=True)
figure.suptitle('Raining Hogs and Dogs', fontsize=14)
canvas = FigureCanvasAgg(figure)
return canvas
In my view I have:
canvas = Chart.bar(results)
# turn the returned canvas into an HTTP response
response=HttpResponse(content_type='image/png')
canvas.print_png(response)
return response
fig = Figure()
fig = Figure(facecolor='white', edgecolor='white')
ax = fig.add_subplot(1,1,1)
x = matplotlib.numpy.arange(0, len(dic.keys()))
ind = matplotlib.numpy.arange(len(dic.values()))
height = 0.8
ax.bar(ind, dic.values(), width, color=colors)
ax.set_xticks(ind + width / 2.0)
ax.set_xticklabels(dic.keys())
padding = 0.2
ax.set_xlim([x.min() - padding, x.max() + width + padding])
canvas = FigureCanvas(fig)
response = django.http.HttpResponse(content_type='image/png')
canvas.print_png(response)
fig.savefig(filename)
this will create a bar graph, and save the image. Just have to call the function into your views. and open the image in the template. I passed a dictionary to this function(dic) but you can pass a list, is up to you.
in this case the keys are the x axis and the values are the y axis.