0

I am currently working on a problem involving solving some two dimensional ode. My problem consists on computing the position of a test mass hooked with a spring to a test position on a 2d potential.

I would like to customize the position of the support vía drawing with my mouse on some rectangle the path the support will run, preferably drawing on top of the potential contour map.

I am new to python and have no clue on whats the best way to do this. I am using numpy and matplotlib for this project in case it can be done with these packages.

Thank you very much.

Crebit
  • 367
  • 1
  • 4
  • 14
Trantidon
  • 147
  • 6

1 Answers1

1

You'll have to think on the problem from several points of view, namely plotting the contour plot, having some way of doing the rectangles by mouse, and eventually obtain the data about the rectangle that was drawn. Check the following recipe (see in the end the places from where I adapted this):

    import matplotlib.pyplot as plt
    from matplotlib.patches import Rectangle
    import matplotlib.mlab as mlab
    import numpy as np

    class Annotate(object):
        def __init__(self):
            self.ax = plt.gca()

            delta = 0.025
            x = np.arange(-3.0, 3.0, delta)
            y = np.arange(-2.0, 2.0, delta)
            X, Y = np.meshgrid(x, y)
            Z1 = mlab.bivariate_normal(X, Y, 1.0, 1.0, 0.0, 0.0)
            Z2 = mlab.bivariate_normal(X, Y, 1.5, 0.5, 1, 1)
            # difference of Gaussians
            Z = 10.0 * (Z2 - Z1)

            CS = plt.contour(X, Y, Z)
            plt.clabel(CS, inline=1, fontsize=10)
            plt.title('Simplest default with labels')

            self.rect = Rectangle((0,0), 1, 1,color=(0,0,1,0.3))
            self.x0 = None
            self.y0 = None
            self.x1 = None
            self.y1 = None
            self.ax.add_patch(self.rect)
            self.ax.figure.canvas.mpl_connect('button_press_event', self.on_press)
            self.ax.figure.canvas.mpl_connect('button_release_event', self.on_release)
            self.ax.set_xlim(-3,3)
            self.ax.set_ylim(-2,2)

        def on_press(self, event):
            print('press')
            self.x0 = event.xdata
            self.y0 = event.ydata

        def on_release(self, event):
            print('release')
            self.x1 = event.xdata
            self.y1 = event.ydata
            self.rect.set_width(self.x1 - self.x0)
            self.rect.set_height(self.y1 - self.y0)
            self.rect.set_xy((self.x0, self.y0))
            print('Rectangle is:','POS:(',self.x1,',',self.y1,') SIZE:(',self.x1 - self.x0,',',self.y1 - self.y0,')')
            self.ax.figure.canvas.draw()

    a = Annotate()
    plt.show()

, this code will result in this:

Rectangle selection over Countour plot

, where you can mouse draw a rectangle (transparent so you see what is beneath it). It will also print to the console the position and size of the rectangle:

 press
 release
 Rectangle is: POS:( 0.967741935484 , -0.449790794979 ) SIZE:( 1.43951612903 , -1.46443514644 )

Using this code you can, by replacement (hopefully), obtain the result you've requested. Notice I've adapted this code from the following recipes:

Recipe 1 Recipe 2

Community
  • 1
  • 1
armatita
  • 12,825
  • 8
  • 48
  • 49