Qt 从C+中的QQuickItem创建listview+;
我正在尝试使用QQuickItem创建一个listview组件,并使用QAbstractListModel加载其模型。下面是我尝试的步骤 listviewComponent.qmlQt 从C+中的QQuickItem创建listview+;,qt,qml,qqmlcomponent,Qt,Qml,Qqmlcomponent,我正在尝试使用QQuickItem创建一个listview组件,并使用QAbstractListModel加载其模型。下面是我尝试的步骤 listviewComponent.qml ListView { required model delegate: Text { required property string type required property string size text: type + ", &q
ListView {
required model
delegate: Text {
required property string type
required property string size
text: type + ", " + size
}
}
型号.h
class Model
{
public:
Model(const QString& type, const QString& size);
QString type() const;
QString size() const;
private:
QString m_type;
QString m_size;
};
class CustomModel : public QAbstractListModel
{
Q_OBJECT
public:
enum Roles {
TypeRole = Qt::UserRole + 1,
SizeRole
};
CustomModel(QObject* parent = 0);
void addElement(const Model& pElement);
int rowCount(const QModelIndex& parent = QModelIndex()) const;
QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const;
protected:
QHash<int, QByteArray> roleNames() const;
private:
QList<Model> m_list;
};
class myclass : public QObject
{
Q_OBJECT
public:
myclass();
inline int createUI(QQmlApplicationEngine &engine){
QQuickWindow *window = qobject_cast<QQuickWindow*>(engine.rootObjects().at(0));
if (!window) {
qFatal("Error: Your root item has to be a window.");
return -1;
}
QQuickItem *root = window->contentItem();
window->setWidth(600);
window->setHeight(500);
QQmlComponent listviewComp(&engine, QUrl(QStringLiteral("qrc:/listviewComponent.qml")));
CustomModel model;
model.addElement(Model("Wolf", "Medium"));
model.addElement(Model("Polar bear", "Large"));
model.addElement(Model("Quoll", "Small"));
QQuickItem *listview = qobject_cast<QQuickItem*>(listviewComp.createWithInitialProperties({ {"model", QVariant::fromValue(&model)} }));
QQmlEngine::setObjectOwnership(listview, QQmlEngine::CppOwnership);
listview->setParentItem(root);
listview->setParent(&engine);
listview->setProperty("objectName", "lv");
listview->setWidth(200);
listview->setHeight(100);
listview->setX(250);
listview->setY(30);
window->show();
return 0;
}
};
问题:正在显示Listview,但只有一行,但CustomModel中添加了3行。我假设createWithInitialProperties存在一些问题,但无法破解它。问题的原因是“model”是一个局部变量,在createUI完成执行后将被销毁,而您看到的第一行只是一个缓存,您不应该实际看到一行(看起来像一个bug)。解决方案是使用堆内存:
/。。。
CustomModel*model=新CustomModel(窗口);
模型->附加元素(模型(“狼”、“中”);
模型->附加元素(模型(“北极熊”、“大型”);
模型->附加元素(模型(“Quoll”、“Small”);
QQuickItem*listview=qobject_cast(listviewComp.createWithInitialProperties({{{“模型”,QVariant::fromValue(模型)}}));
// ...
问题的原因是“model”是一个局部变量,在createUI完成执行后将被销毁,而您看到的第一行只是一个缓存,实际上不应该看到一行(它看起来像一个bug)。解决方案是使用堆内存:
/。。。
CustomModel*model=新CustomModel(窗口);
模型->附加元素(模型(“狼”、“中”);
模型->附加元素(模型(“北极熊”、“大型”);
模型->附加元素(模型(“Quoll”、“Small”);
QQuickItem*listview=qobject_cast(listviewComp.createWithInitialProperties({{{“模型”,QVariant::fromValue(模型)}}));
// ...
class myclass : public QObject
{
Q_OBJECT
public:
myclass();
inline int createUI(QQmlApplicationEngine &engine){
QQuickWindow *window = qobject_cast<QQuickWindow*>(engine.rootObjects().at(0));
if (!window) {
qFatal("Error: Your root item has to be a window.");
return -1;
}
QQuickItem *root = window->contentItem();
window->setWidth(600);
window->setHeight(500);
QQmlComponent listviewComp(&engine, QUrl(QStringLiteral("qrc:/listviewComponent.qml")));
CustomModel model;
model.addElement(Model("Wolf", "Medium"));
model.addElement(Model("Polar bear", "Large"));
model.addElement(Model("Quoll", "Small"));
QQuickItem *listview = qobject_cast<QQuickItem*>(listviewComp.createWithInitialProperties({ {"model", QVariant::fromValue(&model)} }));
QQmlEngine::setObjectOwnership(listview, QQmlEngine::CppOwnership);
listview->setParentItem(root);
listview->setParent(&engine);
listview->setProperty("objectName", "lv");
listview->setWidth(200);
listview->setHeight(100);
listview->setX(250);
listview->setY(30);
window->show();
return 0;
}
};
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
const QUrl url(QStringLiteral("qrc:/main.qml"));
engine.load(url);
QQmlContext *item = engine.rootContext();
myclass myClass;
item->setContextProperty("_myClass", &myClass);
myClass.createUI(engine);
return app.exec();
}