交替检查可检查的 QGroupboxes
Alternately checking checkable QGroupboxes
我正在尝试添加选中的 gropuboxes,如果一个 groupbox 被选中,另一个应该被取消选中。
所以我想,我补充
connect(m_grp1, SIGNAL(toggled(bool)), this, SLOT(grp1Changed(bool)));
connect(m_grp2, SIGNAL(toggled(bool)), this, SLOT(grp2Changed(bool)));
但是如果我在 grp1 更改时更改对 grp2 的检查,那将触发 grp2 的更改,这将触发 grp1 的更改...
有没有我可以使用的内置功能 - 比如单选按钮?或者我不能使用选中的组框,必须自己使用单选按钮实现行为?
我的代码(Qt 4.8):
应该在网格布局中添加 2 个选中的组框,每个框在网格布局中都有一些项目,两个框都可以选中,其中一个选中。
groupboxes.h
#ifndef GROUPBOXES_H
#define GROUPBOXES_H
#include <QtGui>
class GroupBoxes : public QWidget
{
Q_OBJECT
public:
GroupBoxes(QWidget *parent = 0);
private slots:
void grp1Changed(bool _on);
void grp2Changed(bool _on);
private:
QGroupBox *m_grp2;
QGroupBox *m_grp1;
void setGroup1();
void setGroup2();
};
#endif // GROUPBOXES_H
groupboxes.cpp
#include "groupboxes.h"
GroupBoxes::GroupBoxes(QWidget *parent)
: QWidget(parent)
{
setGroup1();
setGroup2();
connect(m_grp1, SIGNAL(toggled(bool)), this, SLOT(grp1Changed(bool)));
connect(m_grp2, SIGNAL(toggled(bool)), this, SLOT(grp2Changed(bool)));
QGridLayout *grid = new QGridLayout;
grid->addWidget(m_grp1, 0, 0);
grid->addWidget(m_grp2, 1, 0);
setLayout(grid);
setWindowTitle(tr("Group Boxes"));
resize(480, 320);
}
void GroupBoxes::setGroup1()
{
QLabel lbl1 = new QLabel(tr("def"));
m_grp1 = new QGroupBox("DEF");
m_grp1->setCheckable(true);
m_grp1->setChecked(true);
QGridLayout *boxLayout1 = new QGridLayout;
boxLayout1->addWidget(lbl1, 0, 0, 1, 1);
m_grp1->setLayout(boxLayout1);
}
void GroupBoxes::setGroup2()
{
QLabel lbl1 = new QLabel(tr("abc"));
m_grp2 = new QGroupBox("ABC");
m_grp2->setCheckable(true);
m_grp2->setChecked(false);
QGridLayout *boxLayout = new QGridLayout;
boxLayout->addWidget(lbl1, 0, 0, 1, 1);
m_grp2->setLayout(boxLayout);
}
void GroupBoxes::grp1Changed(bool _on)
{
m_grp2->setChecked(!_on); // but that would trigger grp2Changed and will lead to infinite loop
}
void GroupBoxes::grp2Changed(bool _on)
{
m_grp1->setChecked(!_on); // but that would trigger grp1Changed and will lead to infinite loop
}
main.cpp
#include <QApplication>
#include "groupboxes.h"
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
GroupBoxes window;
window.show();
return a.exec();
}
您需要取消选中复选框,并且需要使用 SignalBlocker
以免陷入无限循环
void GroupBoxes::grp1Changed(bool _on){
QSignalBlocker(m_grp2);
QSignalBlocker(m_grp1);
m_grp2->setChecked(!_on);
m_grp1->setChecked(_on);
}
但您应该在同一个布局中使用 RadioButtons
,因为检查超过 1 个 RadioButton
是不可能的。
我会的
void GroupBoxes::grp1Changed(bool _on)
{
if(_on)
m_grp2->setChecked(false);
}
这样我似乎避免了无限循环,因为我只在 true 上更改,并将 change 设置为 false。
您可以将 QCheckBox 小部件添加到 QButtonGroup。 QButtonGroup 负责确保只有一个成员被设置。或者使用 autoExclusive 属性.
或者使用 QRadioButton,如果这是您真正想要的。如果您希望能够取消选择两者,则应仅将复选框用于此目的。
我正在尝试添加选中的 gropuboxes,如果一个 groupbox 被选中,另一个应该被取消选中。
所以我想,我补充
connect(m_grp1, SIGNAL(toggled(bool)), this, SLOT(grp1Changed(bool)));
connect(m_grp2, SIGNAL(toggled(bool)), this, SLOT(grp2Changed(bool)));
但是如果我在 grp1 更改时更改对 grp2 的检查,那将触发 grp2 的更改,这将触发 grp1 的更改...
有没有我可以使用的内置功能 - 比如单选按钮?或者我不能使用选中的组框,必须自己使用单选按钮实现行为?
我的代码(Qt 4.8):
应该在网格布局中添加 2 个选中的组框,每个框在网格布局中都有一些项目,两个框都可以选中,其中一个选中。
groupboxes.h
#ifndef GROUPBOXES_H
#define GROUPBOXES_H
#include <QtGui>
class GroupBoxes : public QWidget
{
Q_OBJECT
public:
GroupBoxes(QWidget *parent = 0);
private slots:
void grp1Changed(bool _on);
void grp2Changed(bool _on);
private:
QGroupBox *m_grp2;
QGroupBox *m_grp1;
void setGroup1();
void setGroup2();
};
#endif // GROUPBOXES_H
groupboxes.cpp
#include "groupboxes.h"
GroupBoxes::GroupBoxes(QWidget *parent)
: QWidget(parent)
{
setGroup1();
setGroup2();
connect(m_grp1, SIGNAL(toggled(bool)), this, SLOT(grp1Changed(bool)));
connect(m_grp2, SIGNAL(toggled(bool)), this, SLOT(grp2Changed(bool)));
QGridLayout *grid = new QGridLayout;
grid->addWidget(m_grp1, 0, 0);
grid->addWidget(m_grp2, 1, 0);
setLayout(grid);
setWindowTitle(tr("Group Boxes"));
resize(480, 320);
}
void GroupBoxes::setGroup1()
{
QLabel lbl1 = new QLabel(tr("def"));
m_grp1 = new QGroupBox("DEF");
m_grp1->setCheckable(true);
m_grp1->setChecked(true);
QGridLayout *boxLayout1 = new QGridLayout;
boxLayout1->addWidget(lbl1, 0, 0, 1, 1);
m_grp1->setLayout(boxLayout1);
}
void GroupBoxes::setGroup2()
{
QLabel lbl1 = new QLabel(tr("abc"));
m_grp2 = new QGroupBox("ABC");
m_grp2->setCheckable(true);
m_grp2->setChecked(false);
QGridLayout *boxLayout = new QGridLayout;
boxLayout->addWidget(lbl1, 0, 0, 1, 1);
m_grp2->setLayout(boxLayout);
}
void GroupBoxes::grp1Changed(bool _on)
{
m_grp2->setChecked(!_on); // but that would trigger grp2Changed and will lead to infinite loop
}
void GroupBoxes::grp2Changed(bool _on)
{
m_grp1->setChecked(!_on); // but that would trigger grp1Changed and will lead to infinite loop
}
main.cpp
#include <QApplication>
#include "groupboxes.h"
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
GroupBoxes window;
window.show();
return a.exec();
}
您需要取消选中复选框,并且需要使用 SignalBlocker
以免陷入无限循环
void GroupBoxes::grp1Changed(bool _on){
QSignalBlocker(m_grp2);
QSignalBlocker(m_grp1);
m_grp2->setChecked(!_on);
m_grp1->setChecked(_on);
}
但您应该在同一个布局中使用 RadioButtons
,因为检查超过 1 个 RadioButton
是不可能的。
我会的
void GroupBoxes::grp1Changed(bool _on)
{
if(_on)
m_grp2->setChecked(false);
}
这样我似乎避免了无限循环,因为我只在 true 上更改,并将 change 设置为 false。
您可以将 QCheckBox 小部件添加到 QButtonGroup。 QButtonGroup 负责确保只有一个成员被设置。或者使用 autoExclusive 属性.
或者使用 QRadioButton,如果这是您真正想要的。如果您希望能够取消选择两者,则应仅将复选框用于此目的。