Qt 覆盖可检查的QGroupBox切换行为

Qt 覆盖可检查的QGroupBox切换行为,qt,checkbox,overriding,toggle,qgroupbox,Qt,Checkbox,Overriding,Toggle,Qgroupbox,我对QGroupBox类进行了子类化,并启用了checkable属性。我试图覆盖切换/选中事件的行为 代码如下: class SideWidgetGroupBox: public QGroupBox { Q_OBJECT public: SideWidgetGroupBox(QWidget* parent = 0): QGroupBox(parent) { this->setCheckable(true); connect(this,

我对QGroupBox类进行了子类化,并启用了checkable属性。我试图覆盖切换/选中事件的行为

代码如下:

class SideWidgetGroupBox: public QGroupBox
{
    Q_OBJECT
public:
    SideWidgetGroupBox(QWidget* parent = 0): QGroupBox(parent)
    {
        this->setCheckable(true);
        connect(this, SIGNAL(toggled(bool)), this, SLOT(my_toggled(bool)));
    }

private slots:
    void my_toggled (bool on)
    {
        std::cout << "my toggled method" <<std::endl;
    }
};
class SideWidgetGroupBox:公共QGroupBox
{
Q_对象
公众:
SideWidgetGroupBox(QWidget*parent=0):QGroupBox(parent)
{
此->可设置检查(真);
连接(这个,信号(切换(bool)),这个,插槽(my_切换(bool));
}
专用插槽:
无效我的_切换(bool on)
{

std::cout有没有办法防止启用/禁用内容?

是的,但这种方式并不容易,因为那里没有
QCheckBox
。看起来像复选框的是
QGroupBox
的一个区域。所有事件都由
QGroupBox
处理:
1.重写
event
方法并阻止基类处理
QEvent::keyrease
QEvent::mousererelease
事件

bool SideWidgetGroupBox::event(QEvent *e)
{
  switch (e->type()) {
   case QEvent::KeyRelease:
   case QEvent::MouseButtonRelease:
     myHandler(e);
     return true;
  }
 return QGroupBox::event(e);
}
2.在
myHandler
中,检查是否按下
space
或鼠标单击复选框。存储复选框值并执行所需操作。使用此代码检查光标下的内容:

QStyleOptionGroupBox box;
initStyleOption(&box);
QStyle::SubControl released = style()->hitTestComplexControl(QStyle::CC_GroupBox, &box,
                                                             event->pos(), this);
bool toggle = released == QStyle::SC_GroupBoxLabel || released == QStyle::SC_GroupBoxCheckBox;
if (toggle)
{
    m_state = !m_state;
    update();
}
3.添加方法
initStyleOption
并将
state
设置为复选框的状态(您应该自己存储):

4.
QGroupBox
中的方法
initStyleOption
不是虚拟的,这就是您需要重新实现
paintEvent
的原因:

void paintEvent(QPaintEvent *)
{
    QStylePainter paint(this);
    QStyleOptionGroupBox option;
    initStyleOption(&option);
    paint.drawComplexControl(QStyle::CC_GroupBox, option);
}
我必须手动重置原始启用/禁用状态吗?
无法使用
setEnabled
执行此操作,因为它检查当前选中的状态并阻止启用子项。尽管可以使用
this->findChildren直接为子项调用
setEnabled

建议

您可以使用上述方法,或者删除标准复选框和(或)标签,并将自己的
QCheckBox
置于组上方(当然,没有布局)如果你可以移动分组,你也需要移动复选框。

哇,我认为这会更容易。我正在尝试使用你的解决方案,但我无法设置复选框的状态。我想这行应该可以做到:
选项->状态|=(状态?QStyle::state_开:QStyle::state_关);
,我尝试过使用true/false值,但似乎没有任何效果。@istee更新了答案中的2,3。并添加了4。还有一个困难:initStyleOption不是虚拟的。如果我正确理解所有这一切,就无法使用标准的可检查QGroupBox并覆盖“启用/禁用”-行为是一种简单的方法。唯一的可能是逐个重新启用所有子窗口小部件?您可以重新启用子窗口小部件或使用上述方法删除标准行为。
void paintEvent(QPaintEvent *)
{
    QStylePainter paint(this);
    QStyleOptionGroupBox option;
    initStyleOption(&option);
    paint.drawComplexControl(QStyle::CC_GroupBox, option);
}