我目前正在研究一种使用GUI在运行时修改对象内容的好方法,项目使用Qt。
因此,我想到了将QLayout
传递给对象,以使它们创建自己的GUI。作为POC,我创建了这个(“display”是QVBoxLayout*
参数的名称):
QPushButton* button = new QPushButton();
button->setText("foo");
button->setObjectName("bar");
display->addWidget(button);
效果与预期一样好。但是我将需要阅读用户在GuI中键入的内容,因此我接下来要做的是:
QPushButton *button2 = display->findChild<QPushButton *>();
if(button2)
std::cout << button2->objectName().toStdString() << std::endl;
这里什么也没放-if()语句为假!
QList<QWidget *> widgets = display->findChildren<QWidget *>();
foreach (QWidget* b, widgets) {
std::cout << b->objectName().toStdString() << std::endl;
}
同样,
widgets
列表为空。我尝试通过以下网址查看完整的成员列表:http://doc.qt.digia.com/qt/qvboxlayout-members.html,但是findChild/findChildren似乎最适合我的需求...
解决方案低于
我现在是这样处理的:
而不是将
QVBoxLayout
传递给GUI创建,而是应该传递QWidget
,在上面的名为“display”的后面,如上。QVBoxLayout* layout = new QVBoxLayout();
display->setLayout(layout);
QPushButton* button = new QPushButton();
button->setText("foo");
button->setObjectName("bar");
layout->addWidget(button);
现在到
findChild
/findChildren
:QPushButton *button2 = display->findChild<QPushButton *>("bar");
if(button2)
std::cout << button2->objectName().toStdString() << std::endl;
QList<QWidget *> widgets = display->findChildren<QWidget *>();
foreach (QWidget* b, widgets) {
std::cout << b->objectName().toStdString() << std::endl;
}
两种方法都对我有效! (此外,现在可以通过GUI创建自由选择布局!)
最佳答案
QWidget
的父级必须是QWidget
。 QLayout
不是QWidget
。
存在布局以移动QWidget
的子代并调整其大小。尽管您可以通过在布局上调用来添加子窗口小部件,但最终,它们的父窗口将是布局所在的QWidget
。
为了显示:
QWidget* widget = new QWidget;
qDebug("Widget: %p", widget);
QHBoxLayout* layout = new QHBoxLayout;
qDebug("Layout: %p", layout);
QWidget* child = new QWidget;
layout->addWidget(child);
qDebug("Child's parent before setLayout: %p", child->parent());
widget->setLayout(layout);
qDebug("Child's parent after setLayout: %p", child->parent());
输出:
Widget: 0x8e1c1e0
Layout: 0x8e1c3f0
Child's parent before setLayout: 0x0
Child's parent after setLayout: 0x8e1c1e0
关于c++ - Qt findChild返回0,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/13518767/