Matplotlib 'key_press_event' 没有响应
Matplotlib 'key_press_event' does not respond
在图上用鼠标点击:
self.canvas.Fig.canvas.mpl_connect('button_press_event', self.button_press)
我可以通过在状态栏 self.statusBar().showMessage("Key pressed", 400)
中打印 "Button pressed" 来接收信号并生成答案
但出于某种原因,同一段代码不适用于按键(键盘)按下:
self.canvas.Fig.canvas.mpl_connect('key_press_event', self.key_press)
消息"Key pressed"没有出现,意味着没有事件发生或没有收到信号。
这是我的 MWE,包含所有必需品 类:
import sys
import matplotlib
matplotlib.use("Qt5Agg")
from PyQt5 import QtCore, QtGui, QtWidgets
from PyQt5.QtWidgets import QApplication, QMainWindow, QSizePolicy
from matplotlib.figure import Figure
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
class MyMplCanvas(FigureCanvas):
def __init__(self, parent=None, width=5, height=4, dpi=100,data=[[]],timedelay=[],wavelength=[]):
self.Fig = Figure(figsize=(width, height), dpi=dpi)
self.Dataplot = self.Fig.add_subplot(111)
self.compute_initial_figure(data,timedelay, wavelength)
FigureCanvas.__init__(self, self.Fig)
self.setParent(parent)
FigureCanvas.setSizePolicy(self,QSizePolicy.Expanding,QSizePolicy.Expanding)
FigureCanvas.updateGeometry(self)
def compute_initial_figure(self,data,timedelay,wavelength):
pass
class MyStaticMplCanvas(MyMplCanvas):
def __init__(self, *args, **kwargs):
MyMplCanvas.__init__(self, *args, **kwargs)
def compute_initial_figure(self,data,timedelay,wavelength):
self.Dataplot.set_xlabel('Wavelength, nm')
self.Dataplot.set_ylabel('Time delay, ~s')
class GraphView(QMainWindow):
def __init__(self):
QMainWindow.__init__(self)
self.main_widget = QtWidgets.QWidget(self)
self.canvas = MyStaticMplCanvas(self.main_widget, width=8, height=8, dpi=100,data=[[]],timedelay=[],wavelength=[])
self.canvas.Fig.canvas.mpl_connect('key_press_event', self.key_press)
self.canvas.Fig.canvas.mpl_connect('button_press_event', self.button_press)
self.layoutMain = QtWidgets.QHBoxLayout(self.main_widget)
self.layoutFigure = QtWidgets.QHBoxLayout()
self.layoutMain.addLayout(self.layoutFigure)
self.layoutFigure.addWidget(self.canvas)
self.main_widget.setFocus()
self.setCentralWidget(self.main_widget)
def key_press(self,event):
self.statusBar().showMessage("Key pressed", 400)
def button_press(self,event):
self.statusBar().showMessage("Button pressed", 400)
def main():
app = QApplication( sys.argv )
a=GraphView()
a.show()
app.exec()
if __name__ == '__main__':
sys.exit(main())
我的代码有什么问题?
我找到了解决方案here
之后
self.canvas = MyStaticMplCanvas(self.main_widget, width=8, height=8, dpi=100,data=[[]],timedelay=[],wavelength=[])
添加
self.canvas.setFocusPolicy( QtCore.Qt.ClickFocus )
self.canvas.setFocus()
单击 canvas 使其具有焦点,然后您将看到 key_presses
如果您不想每次都点击 canvas 键,您可以执行以下操作,当您将鼠标悬停在 canvas 上时,焦点会自动切换到 canvas它与你的光标。将此添加到您的 GraphView.__init__()
:
self.cid_enter = self.canvas.mpl_connect('axes_enter_event', self.on_enter_event)
并将 on_enter_event
方法添加到您的 GraphView
class:
def on_enter_event(self, _):
self.canvas.setFocus()
您也不需要更改 FocusPolicy 即可工作。
顺便说一句,您不需要执行 self.canvas.Fig.canvas
来引用 canvas 对象,因为它是循环的。 self.canvas
已经是 canvas 对象。从理论上讲,您可以无限期地执行 self.canvas.Fig.canvas.Fig.canvas
等等,并且仍然会引用同一个对象。
在图上用鼠标点击:
self.canvas.Fig.canvas.mpl_connect('button_press_event', self.button_press)
我可以通过在状态栏 self.statusBar().showMessage("Key pressed", 400)
但出于某种原因,同一段代码不适用于按键(键盘)按下:
self.canvas.Fig.canvas.mpl_connect('key_press_event', self.key_press)
消息"Key pressed"没有出现,意味着没有事件发生或没有收到信号。
这是我的 MWE,包含所有必需品 类:
import sys
import matplotlib
matplotlib.use("Qt5Agg")
from PyQt5 import QtCore, QtGui, QtWidgets
from PyQt5.QtWidgets import QApplication, QMainWindow, QSizePolicy
from matplotlib.figure import Figure
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
class MyMplCanvas(FigureCanvas):
def __init__(self, parent=None, width=5, height=4, dpi=100,data=[[]],timedelay=[],wavelength=[]):
self.Fig = Figure(figsize=(width, height), dpi=dpi)
self.Dataplot = self.Fig.add_subplot(111)
self.compute_initial_figure(data,timedelay, wavelength)
FigureCanvas.__init__(self, self.Fig)
self.setParent(parent)
FigureCanvas.setSizePolicy(self,QSizePolicy.Expanding,QSizePolicy.Expanding)
FigureCanvas.updateGeometry(self)
def compute_initial_figure(self,data,timedelay,wavelength):
pass
class MyStaticMplCanvas(MyMplCanvas):
def __init__(self, *args, **kwargs):
MyMplCanvas.__init__(self, *args, **kwargs)
def compute_initial_figure(self,data,timedelay,wavelength):
self.Dataplot.set_xlabel('Wavelength, nm')
self.Dataplot.set_ylabel('Time delay, ~s')
class GraphView(QMainWindow):
def __init__(self):
QMainWindow.__init__(self)
self.main_widget = QtWidgets.QWidget(self)
self.canvas = MyStaticMplCanvas(self.main_widget, width=8, height=8, dpi=100,data=[[]],timedelay=[],wavelength=[])
self.canvas.Fig.canvas.mpl_connect('key_press_event', self.key_press)
self.canvas.Fig.canvas.mpl_connect('button_press_event', self.button_press)
self.layoutMain = QtWidgets.QHBoxLayout(self.main_widget)
self.layoutFigure = QtWidgets.QHBoxLayout()
self.layoutMain.addLayout(self.layoutFigure)
self.layoutFigure.addWidget(self.canvas)
self.main_widget.setFocus()
self.setCentralWidget(self.main_widget)
def key_press(self,event):
self.statusBar().showMessage("Key pressed", 400)
def button_press(self,event):
self.statusBar().showMessage("Button pressed", 400)
def main():
app = QApplication( sys.argv )
a=GraphView()
a.show()
app.exec()
if __name__ == '__main__':
sys.exit(main())
我的代码有什么问题?
我找到了解决方案here
之后self.canvas = MyStaticMplCanvas(self.main_widget, width=8, height=8, dpi=100,data=[[]],timedelay=[],wavelength=[])
添加
self.canvas.setFocusPolicy( QtCore.Qt.ClickFocus )
self.canvas.setFocus()
单击 canvas 使其具有焦点,然后您将看到 key_presses
如果您不想每次都点击 canvas 键,您可以执行以下操作,当您将鼠标悬停在 canvas 上时,焦点会自动切换到 canvas它与你的光标。将此添加到您的 GraphView.__init__()
:
self.cid_enter = self.canvas.mpl_connect('axes_enter_event', self.on_enter_event)
并将 on_enter_event
方法添加到您的 GraphView
class:
def on_enter_event(self, _):
self.canvas.setFocus()
您也不需要更改 FocusPolicy 即可工作。
顺便说一句,您不需要执行 self.canvas.Fig.canvas
来引用 canvas 对象,因为它是循环的。 self.canvas
已经是 canvas 对象。从理论上讲,您可以无限期地执行 self.canvas.Fig.canvas.Fig.canvas
等等,并且仍然会引用同一个对象。