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

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())
解决方案

问题根源在于多重继承导致的事件传递混乱,以及缺少必要的交互权限设置:

  1. 重复继承QObject:QGraphicsRectItem本身已继承自QObject,重复继承会破坏事件传递链,导致QComboBox下拉所需的鼠标/键盘事件无法正确到达控件。
  2. 缺少交互权限:未给图形项和代理控件设置焦点、交互相关的标志,无法触发下拉弹窗的事件响应。

修复后的代码:

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.22 17:05:08