在我的qt c ++应用程序中,QStringList通过信号和插槽机制从一个cpp文件(MainWIndow)发送到另一个cpp文件(Dialog)!我想在界面加载时(在没有按钮点击的情况下)在Dialog.ui的组合框中显示qtringList中的元素!
以下是我的代码
#include "dialog.h"
#include "ui_dialog.h"
Dialog::Dialog(QWidget *parent) :
QDialog(parent),
ui(new Ui::Dialog)
{
ui->setupUi(this);
for(int i=0;i<subMessages.size();i++){
ui->comboBox->addItem(subMessages[i]);
}
}
//slot which is used to get the qstringList
void Dialog::receiveSubMessages(QStringList List){
subMessages=List;
}
通过插槽(已经验证)成功接收到QStringList。虽然我使用了for循环并尝试显示(如代码中所示)但组合框上没有显示任何内容!我该如何解决这个问题?
答案 0 :(得分:1)
我做了这个答案,而不是告诉你如何解决你的问题。 (我觉得我甚至不明白你的实际问题是什么。)
在提问时,如果提供了MCVE,则有机会获得有用的答案。 (请关注此链接。它教会了每个S / W开发人员必须具备的基本技能。我还建议跟进How to debug small programs。)
由于我确实理解了你的问题,我做了这样的MCVE。这是代码testQComboBox
:
#include <QtWidgets>
int main(int argc, char **argv)
{
// build appl.
qDebug() << "Qt Version:" << QT_VERSION_STR;
QApplication app(argc, argv);
// a QStringList with items
QStringList items;
items
<< QString::fromUtf8("first item")
<< QString::fromUtf8("second item")
<< QString::fromUtf8("third item");
// build GUI
QDialog dlg;
QVBoxLayout vBox;
QComboBox cmbBox;
cmbBox.addItems(items);
vBox.addWidget(&cmbBox);
dlg.setLayout(&vBox);
dlg.show();
app.exec();
// done
return 0;
}
我在Windows 10(64位)上使用Qt 5.9.2在VS2013中编译了它。这是它的外观:
如您所见,组合框的使用相当容易 - 没有秘密陷阱门可以使用它。与QComboBox
直接相关的实际代码正好是 4 代码行:
QVBoxLayout vBox;
QComboBox cmbBox;
cmbBox.addItems(items);
vBox.addWidget(&cmbBox);
并且只有一行代码将项目添加到QComboBox
:
cmbBox.addItems(items);
注意:的
我使用QComboBox::addItems()
代替QComboBox::addItem()
,因为前者已经内置了一个循环来添加完整的QStringList
。它对您在代码Dialog::Dialog()
中使用的循环没有任何影响。
所以,最后我敢做以下陈述:
如果你的组合框没有显示项目,那么:
您从空列表中添加了项目。
或者,您忘记添加列表中的项目。
或者,发生了一些非常奇怪的事情。
我总是打赌1.或2.理由 - 原因仅在于真正的紧急情况(例如Qt安装破坏)。
关于3.理由:
我看到很多问题,其中提出了一些无辜的代码,这些代码看起来完全按照它们的应有但声称失败了。最后几乎每次都显示这些线在MCVE中被隔离时工作正常,但它们在原始代码中没有。怎么会发生这种情况?有一些上下文会改变原始程序中代码的行为,或者存在UB - 未定义的行为。其他东西做坏事但不是立即崩溃你的过程(这意味着你很幸运)它会持续一段时间腐败数据越来越多,直到最后一切都完全破裂。调查核心转储根本没有用。因此我推荐How to debug small programs。
答案 1 :(得分:1)
为了获得正常工作的代码,您需要将for
llop放在您的插槽中:
#include "dialog.h"
#include "ui_dialog.h"
Dialog::Dialog(QWidget *parent) :
QDialog(parent),
ui(new Ui::Dialog)
{
ui->setupUi(this);
}
//slot which is used to get the qstringList
void Dialog::receiveSubMessages(QStringList List){
ui->comboBox->addItems (List);
}
如果要在QStringList
构造时使用某些Dialog
的内容填充comboBox,那么您应该将此列表作为构造函数参数传递:
Dialog::Dialog(QStringList List, QWidget *parent) :
QDialog(parent),
ui(new Ui::Dialog)
{
ui->setupUi(this);
ui->comboBox->addItems (List);
}
或在Dialog::receiveSubMessages()
对象构建后立即致电Dialog
:
// somewhere in code, where you construct Dialog object
// ...
auto parent = SomeQWidgetDerivedClass (...);
QStringList someStringList {
"string 1",
"string 2"
};
// ...
auto dialog {new Dialog ()};
dialog->receiveSubMessages (someStringList);
// ...
您提供的代码永远不会允许您实现所需的结果,因为在您的for
对象创建中执行了应该填充QComboBox
的{{1}}循环。那时你的Dialog
是空的。您创建的插槽在构造函数之前未被调用 - 插槽只是一个只能在创建对象后调用的成员函数。如果函数本身是静态的,那么你只能在没有对象的情况下调用成员函数,在这种情况下它肯定不是一个插槽。