Вот проблема. Мне нужно создать "Ловец кликов". Мне нужно включить режим захвата кликов, нажав на кнопку (Отметить), а затем, когда я нажимаю на свой график, моя программа должна запомнить список точек, координаты и т. Д. c. Что особенно важно - другие кнопки должны работать нормально, когда включен режим захвата кликов. Например я реализовал кнопку Печать. Я хотел бы щелкнуть пару раз на своем графике, затем, , не выходя из , нажмите режим захвата, нажмите кнопку Печать и затем увидите список точек наблюдения. Проблема в том, что моя программа видит matplotlib.widgets
кнопки как axes
и ловит точки на них всякий раз, когда я использую любую кнопку.
Я пытался использовать event.inaxes which
, который должен проверять, находится ли курсор в области осей. Итак, я реализовал некоторые логи c. К сожалению, он отлично работает только за пределами графика, но совсем не работает для кнопок. Кажется, что matplotlib видит кнопки как объект оси, поэтому он полностью не работает.
Пожалуйста, помогите мне с этим, я довольно новичок в программировании и сам все учил (так что любой обзор кода приветствуется).
* tl; dr: Вы можете видеть ошибка очень хорошо, когда вы включаете режим ловли, нажмите на график, а затем нажмите несколько раз на кнопку Печать. Каждый щелчок по кнопке «Печать» добавит в список точек дополнительные координаты. *
Здесь идет код:
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.widgets import Button
class ClickCatcher:
def __init__(self, window_object):
self.window_object = window_object
self.fig = self.window_object.fig
self.ax = self.window_object.ax
self.window_object.is_click_catcher_working = True
self.cid = window_object.fig.canvas.mpl_connect('button_press_event', self)
self.points, = self.ax.plot([], [], marker='.', ls='None', color='red')
self.data_x = []
self.data_y = []
def __call__(self, event):
if event.button == 1 and event.inaxes:
self.data_x.append(event.xdata)
self.data_y.append(event.ydata)
self.update_plot()
print('{:8.2f} {:8.2f}'.format(event.xdata, event.ydata))
self.window_object.click_data = (self.data_x, self.data_y)
def update_plot(self):
self.points.set_data(self.data_x, self.data_y)
self.fig.canvas.draw()
class Window:
def __init__(self):
self.is_click_catcher_working = False
self.click_data = ()
self.fig, self.ax = plt.subplots()
self.configure_appearance()
self._plot, = plt.plot(np.arange(0, 10, 0.1), np.sin(np.arange(0, 10, 0.1)),
drawstyle='steps-mid', color='black', lw=1)
self._add_buttons()
def configure_appearance(self):
self.fig.set_size_inches(10, 5)
self.ax.tick_params(axis='both', labelsize=14)
self.ax.set_xlabel('Energy (keV)', fontsize=12)
self.ax.set_ylabel('Number of counts', fontsize=12)
plt.subplots_adjust(bottom=0.25)
def _add_buttons(self):
self.button_mark = Button(plt.axes([0.4, 0.05, 0.1, 0.075]), 'Mark')
self.button_mark.on_clicked(self.activate_marking)
self.button_print = Button(plt.axes([0.6, 0.05, 0.1, 0.075]), 'Print')
self.button_print.on_clicked(self.print_points)
def catch_coordinates(self):
click = ClickCatcher(self)
def activate_marking(self, event):
if self.is_click_catcher_working:
pass
else:
self.is_click_catcher_working = True
self.catch_coordinates()
def print_points(self, event):
output = '({:.2f}, {:.2f}) ; '*len(self.click_data[0])
print(output.format(*self.click_data[0], *self.click_data[1]))
if __name__ == '__main__':
win = Window()
plt.show()