QComboBox通过QGraphicsProxyWidget嵌入QGraphicsView后无法弹出下拉框
问题
刚接触PySide,若有错误还请见谅。在PySide6中,尝试将QComboBox放入QGraphicsRectItem,再显示在QGraphicsView中。该组合框能正常显示且可高亮,但其下拉弹窗始终无法打开,导致无法查看已添加的选项。用相同方法嵌入QLineEdit和QCheckBox都能正常工作,请问问题出在哪里?
环境信息:
- Python 3.9.13
- PySide6 6.7.0
- Windows 11
代码如下:
import sys from PySide6.QtWidgets import ( QApplication, QGraphicsView, QGraphicsScene, QGraphicsRectItem,QGraphicsProxyWidget, QComboBox, QVBoxLayout, QGraphicsItem, QCheckBox, QLineEdit ) from PySide6.QtCore import Qt, QRectF, QObject class StepView(QGraphicsRectItem, QObject): def __init__(self, rect, parent=None): QGraphicsRectItem.__init__(self, rect, parent) QObject.__init__(self) # Create the combobox and add options self.comboBox = QComboBox() self.comboBox.addItems(["Option 1", "Option 2", "Option 3"]) # Embed the combobox in the graphics item using a proxy widget self.proxy = QGraphicsProxyWidget(self) self.proxy.setWidget(self.comboBox) # Position the combobox within the rect item combo_box_width = self.comboBox.sizeHint().width() combo_box_height = self.comboBox.sizeHint().height() self.proxy.setPos((rect.width() - combo_box_width) / 2, (rect.height() - combo_box_height) / 2) app = QApplication(sys.argv) scene = QGraphicsScene() view = QGraphicsView(scene) view.setWindowTitle("StepView Example") view.setGeometry(100, 100, 500, 500) # Create a StepView item step_view = StepView(QRectF(0, 0, 100, 100)) scene.addItem(step_view) view.show() sys.exit(app.exec())
解决方案
问题根源在于多重继承导致的事件传递混乱,以及缺少必要的交互权限设置:
- 重复继承QObject:
QGraphicsRectItem本身已继承自QObject,重复继承会破坏事件传递链,导致QComboBox下拉所需的鼠标/键盘事件无法正确到达控件。 - 缺少交互权限:未给图形项和代理控件设置焦点、交互相关的标志,无法触发下拉弹窗的事件响应。
修复后的代码:
import sys from PySide6.QtWidgets import ( QApplication, QGraphicsView, QGraphicsScene, QGraphicsRectItem, QGraphicsProxyWidget, QComboBox ) from PySide6.QtCore import Qt, QRectF class StepView(QGraphicsRectItem): def __init__(self, rect, parent=None): super().__init__(rect, parent) # 设置图形项允许获取焦点和被选中,确保交互事件能传递 self.setFlags(QGraphicsRectItem.ItemIsFocusable | QGraphicsRectItem.ItemIsSelectable) # 创建下拉框并添加选项 self.comboBox = QComboBox() self.comboBox.addItems(["Option 1", "Option 2", "Option 3"]) # 嵌入代理控件 self.proxy = QGraphicsProxyWidget(self) self.proxy.setWidget(self.comboBox) # 给代理控件设置强焦点策略,保证下拉弹窗的事件能正常响应 self.proxy.setFocusPolicy(Qt.StrongFocus) # 居中放置下拉框 combo_box_width = self.comboBox.sizeHint().width() combo_box_height = self.comboBox.sizeHint().height() self.proxy.setPos((rect.width() - combo_box_width) / 2, (rect.height() - combo_box_height) / 2) app = QApplication(sys.argv) scene = QGraphicsScene() view = QGraphicsView(scene) view.setWindowTitle("StepView Example") view.setGeometry(100, 100, 500, 500) step_view = StepView(QRectF(0, 0, 100, 100)) scene.addItem(step_view) view.show() sys.exit(app.exec())
关键修改点:
- 移除多余的
QObject继承,用super()正确初始化父类。 - 给
StepView添加ItemIsFocusable和ItemIsSelectable标志,确保图形项能接收交互事件。 - 给代理控件设置
StrongFocus焦点策略,保证下拉弹窗的触发事件能正确传递。
内容的提问来源于stack exchange,提问作者mranim8or
相关产品推荐
相关产品推荐

