You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

在pyqtgraph ViewBox的keyPressEvent中获取鼠标位置的问题

自定义pg.ViewBox按键事件获取鼠标位置的优化与问题修复

一、无需十字线的鼠标位置获取方案

不用额外创建十字线元素,直接通过坐标转换就能拿到ViewBox数据坐标系下的鼠标位置:

  • 用QCursor.pos()获取全局鼠标坐标
  • 调用ViewBox的mapFromGlobal()将全局坐标转为控件局部坐标
  • 再通过mapSceneToView()把局部坐标转换成视图的data坐标(即鼠标对应的数据位置)

代码片段示例:

def keyPressEvent(self, event):
    # 全局坐标转ViewBox局部坐标
    local_pos = self.mapFromGlobal(QCursor.pos())
    # 局部坐标转视图数据坐标
    view_pos = self.mapSceneToView(local_pos)
    print(f"鼠标对应数据位置:x={view_pos.x():.2f}, y={view_pos.y():.2f}")
    # 调用父类方法,保证事件正常传递
    super().keyPressEvent(event)

二、代码异常的修复线索

首次按键无响应的解决

ViewBox默认不接收键盘焦点,需要手动开启并主动设置焦点:

  1. 在CustomViewBox的__init__方法中添加self.setFocusPolicy(Qt.StrongFocus),开启键盘焦点接收
  2. 在主窗口初始化时,给ViewBox主动设置焦点:self.plot_widget.getViewBox().setFocus()

二次按键报错+重复打印的解决

问题出在重写keyPressEvent时未调用父类方法,导致事件被拦截引发异常循环。修复时必须在事件处理逻辑末尾加上super().keyPressEvent(event),保证事件正常向上传递。

修复后的完整最小代码

import pyqtgraph as pg
from PyQt5.QtWidgets import QApplication, QMainWindow
from PyQt5.QtCore import Qt

class CustomViewBox(pg.ViewBox):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        # 开启焦点策略,让ViewBox能处理键盘事件
        self.setFocusPolicy(Qt.StrongFocus)

    def keyPressEvent(self, event):
        # 获取鼠标对应的数据位置
        local_pos = self.mapFromGlobal(QCursor.pos())
        view_pos = self.mapSceneToView(local_pos)
        print(f"鼠标位置:({view_pos.x():.2f}, {view_pos.y():.2f})")
        
        # 必须调用父类方法,避免事件异常
        super().keyPressEvent(event)

class MainWindow(QMainWindow):
    def __init__(self):
        super().__init__()
        self.plot_widget = pg.PlotWidget(viewBox=CustomViewBox())
        self.setCentralWidget(self.plot_widget)
        # 主动让ViewBox获取焦点,首次按键就能响应
        self.plot_widget.getViewBox().setFocus()

if __name__ == "__main__":
    app = QApplication([])
    win = MainWindow()
    win.show()
    app.exec_()

内容的提问来源于stack exchange,提问作者Jesse Rio

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.28 05:53:01