PySide(PyQT)重新定义contextMenuEvent()实现鼠标右键弹出菜单
在 PySide中,contextMenuEvent()
是 QWidget
类(以及继承自它的所有子类)的一个事件处理方法,主要用于处理上下文菜单事件,也就是当用户在控件上右键点击时触发的事件。
• 通过重新定义contextMenuEvent()来实现自定义的鼠标右键菜单
from PySide6.QtGui import QAction
from PySide6.QtWidgets import QApplication, QWidget, QMenu
from PySide6.QtCore import Qt
class MyWidget(QWidget):
def __init__(self):
super().__init__()
# 创建一个菜单
self.menu = QMenu(self)
# 创建菜单项
action1 = QAction("菜单项1", self)
action2 = QAction("菜单项2", self)
# 将菜单项添加到菜单中
self.menu.addAction(action1)
self.menu.addAction(action2)
# 连接信号和槽,定义点击菜单项后的行为
action1.triggered.connect(self.on_action1_triggered)
action2.triggered.connect(self.on_action2_triggered)
def contextMenuEvent(self, event):
# 在鼠标点击的位置显示菜单
self.menu.exec(event.globalPos())
def on_action1_triggered(self):
print("菜单项1被触发")
def on_action2_triggered(self):
print("菜单项2被触发")
# 应用程序执行部分
if __name__ == "__main__":
app = QApplication([])
widget = MyWidget()
widget.show()
app.exec()
• 将其定义在子部件内:
from PySide6.QtGui import QAction
from PySide6.QtWidgets import QApplication, QWidget, QMenu, QPushButton
class MyWidget(QWidget):
def __init__(self):
super().__init__()
self.setupUi()
def setupUi(self):
self.button = MyButton(self)
class MyButton(QPushButton):
def __init__(self, parent=None):
super().__init__(parent)
self.setText("右键点击我")
# 创建一个菜单
self.menu = QMenu(self)
# 创建菜单项
action1 = QAction("菜单项1", self)
action2 = QAction("菜单项2", self)
# 将菜单项添加到菜单中
self.menu.addAction(action1)
self.menu.addAction(action2)
# 连接信号和槽,定义点击菜单项后的行为
action1.triggered.connect(self.on_action1_triggered)
action2.triggered.connect(self.on_action2_triggered)
def contextMenuEvent(self, event):
# 在鼠标点击的位置显示菜单
self.menu.exec(event.globalPos())
def on_action1_triggered(self):
print("菜单项1被触发")
def on_action2_triggered(self):
print("菜单项2被触发")
# 应用程序执行部分
if __name__ == "__main__":
app = QApplication([])
widget = MyWidget()
widget.show()
app.exec()
上述代码,只有在按钮上有鼠标右键菜单。
• 获取系统默认的右键菜单并添加新的菜单项
import sys
from PySide6.QtGui import QAction
from PySide6.QtWidgets import QApplication, QLineEdit, QMenu
class MyLineEdit(QLineEdit):
def __init__(self, parent=None):
super().__init__(parent)
self.setText("右键点击我")
self.menu = QMenu(self) # 创建一个菜单
self.addMenus() # 添加菜单的菜单项
def addMenus(self):
# 获取系统默认的上下文菜单动作
default_actions = self.createStandardContextMenu().actions()
# 将默认动作添加到新菜单中
for action in default_actions:
print(action.text())
self.menu.addAction(action)
# 将新的菜单项添加到新菜单中
self.action1 = QAction("菜单项1", self)
self.action2 = QAction("菜单项2", self)
self.menu.addSeparator() # 创建分割线
# 添加自定义菜单项
self.menu.addAction(self.action1)
self.menu.addAction(self.action2)
# 连接信号和槽函数
self.action1.triggered.connect(self.on_action1_triggered)
self.action2.triggered.connect(self.on_action2_triggered)
# 重写上下文菜单事件
def contextMenuEvent(self, event):
# 显示菜单
self.menu.exec(event.globalPos())
def on_action1_triggered(self):
print("菜单项1被点击")
def on_action2_triggered(self):
print("菜单项2被点击")
if __name__ == "__main__":
app = QApplication(sys.argv)
line_edit = MyLineEdit()
line_edit.show()
sys.exit(app.exec())
上面的代码,读取了系统内置的默认右键菜单,并增加了两个自定义的菜单项,构成了一个新的菜单。重写了contextMenuEvent(),使其显示新的菜单。
• 为新菜单设置快捷方式
import sys
from PySide6.QtGui import QAction
from PySide6.QtWidgets import QApplication, QLineEdit, QMenu
class MyLineEdit(QLineEdit):
def __init__(self, parent=None):
super().__init__(parent)
self.setText("右键点击我")
self.menu = QMenu(self) # 创建一个菜单
self.addMenus() # 添加菜单的菜单项
def addMenus(self):
# 获取系统默认的上下文菜单动作
default_actions = self.createStandardContextMenu().actions()
# 将默认动作添加到新菜单中
for action in default_actions:
self.menu.addAction(action)
# 将新的菜单项添加到新菜单中
self.action1 = QAction("菜单项1", self) # 创建菜单项
self.action1.setShortcut("Ctrl+B") # 设置快捷键
self.action2 = QAction("菜单项2", self)
self.menu.addSeparator() # 创建分割线
# 添加自定义菜单项
self.addAction(self.action1) # 将菜单项添加到部件的主体中,用以生效快捷方式
self.menu.addAction(self.action1) # 将菜单项添加到菜单中
self.menu.addAction(self.action2)
# 连接信号和槽函数
self.action1.triggered.connect(self.on_action1_triggered)
self.action2.triggered.connect(self.on_action2_triggered)
# 重写上下文菜单事件
def contextMenuEvent(self, event):
# 显示菜单
self.menu.exec(event.globalPos())
def on_action1_triggered(self):
print("菜单项1被点击")
def on_action2_triggered(self):
print("菜单项2被点击")
if __name__ == "__main__":
app = QApplication(sys.argv)
line_edit = MyLineEdit()
line_edit.show()
sys.exit(app.exec())
这里注意,只有执行了:self.addAction(self.action1),将菜单项添加到部件的主体中,才能生效快捷方式。而self.menu.addAction(self.action1)只是将菜单项添加到菜单中,并未在部件中注册菜单项。
• 使用策略设置setContextMenuPolicy()的方法来定义菜单:
PyQT(PySide)的上下文菜单策略设置setContextMenuPolicy()-CSDN博客