Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Store mouse click event coordinates with matplotlib

I am trying to implement a simple mouse click event in matplotlib. I wish to plot a figure then use the mouse to select the lower and upper limits for integration. So far I am able to print the coordinates to screen but not store them for later use in the program. I would also like to exit the connection to the figure after the second mouse click.

Below is the code which currently plots and then prints the coordinates.

My Question(s):

How can I store coordinates from the figure to list? i.e. click = [xpos, ypos]

Is it possible to get two sets of x coordinates in order to do a simple integration over that section of line?

import numpy as np import matplotlib.pyplot as plt  x = np.arange(-10,10) y = x**2  fig = plt.figure() ax = fig.add_subplot(111) ax.plot(x,y)  def onclick(event):     global ix, iy     ix, iy = event.xdata, event.ydata     print 'x = %d, y = %d'%(         ix, iy)      global coords     coords = [ix, iy]      return coords   for i in xrange(0,1):      cid = fig.canvas.mpl_connect('button_press_event', onclick)   plt.show() 
like image 258
smashbro Avatar asked Aug 27 '14 07:08

smashbro


People also ask

How do I save a Matplot?

Now if you want to save matplotlib figures as image files programmatically, then all you need is matplotlib. pyplot. savefig() function. Simply pass the desired filename (and even location) and the figure will be stored on your disk.


2 Answers

mpl_connect needs to be called just once to connect the event to event handler. It will start listening to click event until you disconnect. And you can use

fig.canvas.mpl_disconnect(cid) 

to disconnect the event hook.

What you want to do is something like:

import numpy as np import matplotlib.pyplot as plt  x = np.arange(-10,10) y = x**2  fig = plt.figure() ax = fig.add_subplot(111) ax.plot(x,y)  coords = []  def onclick(event):     global ix, iy     ix, iy = event.xdata, event.ydata     print 'x = %d, y = %d'%(         ix, iy)      global coords     coords.append((ix, iy))      if len(coords) == 2:         fig.canvas.mpl_disconnect(cid)      return coords cid = fig.canvas.mpl_connect('button_press_event', onclick) 
like image 196
otterb Avatar answered Sep 23 '22 17:09

otterb


Thanks to otterb for providing the answer! I've added in a little function taken from here... Find nearest value in numpy array

In all this code will plot, wait for selection of x points and then return the indices of the x array needed for any integration, summations etc.

Ta,

import numpy as np import matplotlib.pyplot as plt from scipy.integrate import trapz  def find_nearest(array,value):     idx = (np.abs(array-value)).argmin()     return array[idx]  # Simple mouse click function to store coordinates def onclick(event):     global ix, iy     ix, iy = event.xdata, event.ydata      # print 'x = %d, y = %d'%(     #     ix, iy)      # assign global variable to access outside of function     global coords     coords.append((ix, iy))      # Disconnect after 2 clicks     if len(coords) == 2:         fig.canvas.mpl_disconnect(cid)         plt.close(1)     return   x = np.arange(-10,10) y = x**2  fig = plt.figure(1) ax = fig.add_subplot(111) ax.plot(x,y)  coords = []  # Call click func cid = fig.canvas.mpl_connect('button_press_event', onclick)  plt.show(1)   # limits for integration ch1 = np.where(x == (find_nearest(x, coords[0][0]))) ch2 = np.where(x == (find_nearest(x, coords[1][0])))  # Calculate integral y_int = trapz(y[ch1[0][0]:ch2[0][0]], x = x[ch1[0][0]:ch2[0][0]])  print '' print 'Integral between '+str(coords[0][0])+ ' & ' +str(coords[1][0]) print y_int 
like image 24
smashbro Avatar answered Sep 25 '22 17:09

smashbro