覆盖可检查的QGroupBox切换行为

Ist*_*asz 3 checkbox qt overriding toggle qgroupbox

我已经将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;
    }
};
Run Code Online (Sandbox Code Playgroud)

到目前为止,我的插槽已被执行.但是,组框的内容也会启用/禁用.有办法防止这种情况吗?或者我是否必须手动重置原始启用/禁用状态?

Eze*_*zee 6

有没有办法阻止启用/禁用内容?

是的,但这种方式并不容易,因为没有QCheckBox.看起来像一个复选框是一个区域QGroupBox.并且所有事件都通过QGroupBox以下方式处理:
1.覆盖event方法并防止基类处理QEvent::KeyReleaseQEvent::MouseRelease事件.

bool SideWidgetGroupBox::event(QEvent *e)
{
  switch (e->type()) {
   case QEvent::KeyRelease:
   case QEvent::MouseButtonRelease:
     myHandler(e);
     return true;
  }
 return QGroupBox::event(e);
}
Run Code Online (Sandbox Code Playgroud)

2. myHandler检查是否space按下或鼠标单击复选框.存储checkBox值并执行您需要的操作.使用此代码检查光标下的内容:

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();
}
Run Code Online (Sandbox Code Playgroud)

3.添加方法initStyleOption并设置state为checkBox的状态(您应该自己存储):

void SideWidgetGroupBox::initStyleOption(QStyleOptionGroupBox *option) const
{
    QGroupBox::initStyleOption(option);
    QStyle::State flagToSet = m_state ? QStyle::State_On : QStyle::State_Off;
    QStyle::State flagToRemove = m_state ? QStyle::State_Off : QStyle::State_On;

    option->state |= flagToSet;     
    option->state &= ~flagToRemove;
    option->state &= ~QStyle::State_Sunken;
}
Run Code Online (Sandbox Code Playgroud)

4.Method initStyleOptionQGroupBox不是虚拟的,这就是为什么你需要重新实现paintEvent也:

void paintEvent(QPaintEvent *)
{
    QStylePainter paint(this);
    QStyleOptionGroupBox option;
    initStyleOption(&option);
    paint.drawComplexControl(QStyle::CC_GroupBox, option);
}
Run Code Online (Sandbox Code Playgroud)

我是否必须手动重置原始启用/禁用状态?
您无法执行此操作,setEnabled因为它会检查当前检查状态并阻止启用子项.虽然你可以setEnabled直接打电话给孩子this->findChildren<QWidget*>

建议
您可以使用上述方法或删除标准的checkBox和(或)标签,并将其自己QCheckBox放在组上(当然没有布局)并根据需要使用它.如果您可以移动组,则还需要移动复选框.