[英]How to insert ListElement in a QML ListModel using C++?
嗯,我正在學習使用 QML,我有一個疑問。 在我的示例中,我在 QML 有一個帶有 ListElements 的 ListModel,我有一個帶有矩形、PathView 等的 QML 主文件。
我也有一個 QWidget,而不是我的主窗口。 在這個 QWidget 中,我像組件一樣包含 QML UI。 行!
如何使用 C++ 處理 QML ListElements?
注意:當我說“處理”時,我想說例如包含一個元素。
下面是我的代碼的一些部分......
QML 包含我的 ListElement,稱為“Menu1”:
import QtQuick 1.0
ListModel {
id: listMovieModel
ListElement { name: "Image 1"; iconSource: "pics/image_1.jpg" }
ListElement { name: "Image 2"; iconSource: "pics/image_2.jpg" }
ListElement { name: "Image 3"; iconSource: "pics/image_3.jpg" }
ListElement { name: "Image 4"; iconSource: "pics/image_4.jpg" }
ListElement { name: "Image 5"; iconSource: "pics/image_5.jpg" }
ListElement { name: "Image 6"; iconSource: "pics/image_6.jpg" }
}
我的主要 QML:
Rectangle {
width: 500
height: 600
color: "transparent"
PathView {
id: view
focus: true
width: parent.width
height: parent.height + y
y: -150
model: Menu1 {} //First QML showed
delegate: Image {
source: iconSource
width: 64
height: 90
scale: PathView.isCurrentItem ? 3.5 * y / parent.height : 2.0 * y / parent.height
z: y
smooth: true
}
path: MyGeometricFigure { //This a another file, but is confidential
width: view.width
height: view.height
}
preferredHighlightBegin: 0
preferredHighlightEnd: 0
highlightRangeMode: PathView.StrictlyEnforceRange
Keys.onLeftPressed: decrementCurrentIndex()
Keys.onRightPressed: incrementCurrentIndex()
}
}
當我將 QML 用作 QWidget 的組件時:
MainForm::MainForm(QWidget *parent) :
QWidget(parent),
ui(new Ui::MainForm)
{
ui->setupUi(this);
this->resize(1024, 576);
QDeclarativeView *myQMLTest = new QDeclarativeView(QUrl::fromLocalFile("myMainQML.qml"));
myQMLTest->setStyleSheet(QString("background: transparent; width: 600px"));
this->ui->frameListVideoGallery->layout()->addWidget(myQMLTest);
myQMLTest->setFocus();
myQMLTest->installEventFilter(this);
}
我看到了一些關於此的文章,但我無法使用 C++ 更改我的 LisModel。 我在這里看到了http://doc.qt.nokia.com/4.7/qdeclarativemodels.html#c-data-models和這里在使用 PathView http://doc.qt.nokia.com/4.7/qdeclarativeexamples.html 的示例中
有人能幫我嗎?
謝謝!
好吧。 我認為你可以做這樣的事情:
在您的主 QML 文件中添加簡單的函數。
Rectangle {
// ...
function append(newElement) {
view.model.append(newElement)
}
PathView {
id: view
// ...
model: Menu1 {} //First QML showed
// ...
}
}
這個方法只會從 ListModel 調用相應的方法。 您可以在那里找到更多支持的方法。
那么你所需要的就是從 C++ 代碼中調用這個方法。 您可以通過以下方式執行此操作:
MainForm::MainForm(QWidget *parent) :
QWidget(parent),
ui(new Ui::MainForm)
{
ui->setupUi(this);
this->resize(1024, 576);
QDeclarativeView *myQMLTest = new QDeclarativeView(QUrl::fromLocalFile ("myMainQML.qml"));
myQMLTest->setStyleSheet(QString("background: transparent; width: 600px"));
QVariantMap newElement; // QVariantMap will implicitly translates into JS-object
newElement.insert("name", "Image 13" );
newElement.insert("iconSource", "pics/image_13.jpg");
QMetaObject::invokeMethod(
myQMLTest->rootObject(), // for this object we will call method
"append", // actually, name of the method to call
Q_ARG(QVariant, QVariant::fromValue(newElement)) // method parameter
);
this->ui->frameListVideoGallery->layout()->addWidget(myQMLTest);
myQMLTest->setFocus();
myQMLTest->installEventFilter(this);
}
你應該檢查這個以獲取更多信息。
您也可以選擇另一種方法:通過 qml 屬性(使用 QDeclarativeEngine 和 QDeclarativeContext)傳遞一些數據,然后在 JavaScript 代碼中處理這些數據和您的列表模型。
我想讓@GooRoo 的答案對 Qt 初學者更完整/有用。 如果您使用 Qt Creator,您將從使用 QmlApplicationViewer 的模板開始。 要應用 GooRoo 的答案,您必須執行以下操作(感謝http://www.lothlorien.com/kf6gpe/?p=309 ):
CPP:
Q_DECL_EXPORT int main(int argc, char *argv[])
{
QScopedPointer<QApplication> app(createApplication(argc, argv));
QScopedPointer<QmlApplicationViewer> viewer(QmlApplicationViewer::create());
viewer->setOrientation(QmlApplicationViewer::ScreenOrientationAuto);
viewer->setMainQmlFile(QLatin1String("qml/mydemo/main.qml"));
viewer->showExpanded();
QMetaObject::invokeMethod(
(QObject *)viewer->rootObject()->findChild<QObject *>("myModel"), // QML item
"test" // name of the method to call
// without parameters
);
return app->exec();
}
QML:
PageStackWindow {
id: mainApp
...
ListModel {
id: myModel
objectName: myModel //THIS IS NEEDED BY findChild()
...
function test() {
console.log("TEST OK");
}
}
Page {
...
}
}
這是一個更完整的示例,它使用 C++ 在 QML TableView 中填充數據。 請原諒錯誤的變量名稱。 我只是為了測試目的而制作它。
我使用了QVariantList
並用QVariantMap
對象填充它。
在這里,多個數據在 QML 表的兩列中填充了 for 循環,即what
和session_name
通過將它們放在QVariantMap
,然后將該QVariantMap
插入QVariantList
。
小時
#ifndef HH_H
#define HH_H
#include <QVariant>
class AA : public QObject
{
Q_OBJECT
QVariantList m_gname;
public:
Q_PROPERTY(QVariantList gname READ gname WRITE setGname NOTIFY gnameChanged)
AA()
{
QVariantList q;
for(int i = 0; i < 10; i++)
{
QVariantMap p;
p.insert("what", "qq");
p.insert("session_name", "aa");
q.push_back(p);
}
setGname(q);
}
QVariantList gname() const
{
return m_gname;
}
public slots:
void setGname(QVariantList gname)
{
if (m_gname == gname)
return;
m_gname = gname;
emit gnameChanged(m_gname);
}
signals:
void gnameChanged(QVariantList gname);
};
#endif // HH_H
在這里,我使用qmlRegisterType
來注冊我在上面創建的類AA
。
主程序
#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include "HH.h"
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
qmlRegisterType<AA>("ZZZ", 1, 0, "AA");
QQmlApplicationEngine engine;
const QUrl url(QStringLiteral("qrc:/main.qml"));
QObject::connect(&engine, &QQmlApplicationEngine::objectCreated,
&app, [url](QObject *obj, const QUrl &objUrl) {
if (!obj && url == objUrl)
QCoreApplication::exit(-1);
}, Qt::QueuedConnection);
engine.load(url);
return app.exec();
}
在 QML 中,我通過QtQuick.Controls 1.4
創建了一個 TableView。 它有兩列,分別what
和session_name
。 我在這里創建了一個AA
類的對象,並在其Component.onCompleted
上創建了一個名為 <model_id> dot append
( <QVariantList_name> )
像這樣:
mymodel.append( gname )
主文件
import QtQuick 2.14
import QtQuick.Window 2.14
import QtQuick.Controls 1.4 as OldControls
import ZZZ 1.0
Window
{
visible: true
width: 1000
height: 1000
title: qsTr("Hello World")
AA
{
Component.onCompleted:
{
mymodel.append(gname)
}
}
Rectangle
{
id: head
anchors.centerIn: parent; height: 500; width: 500; border.color: "red"
OldControls.TableView
{
anchors.fill: parent
verticalScrollBarPolicy: Qt.ScrollBarAlwaysOn
horizontalScrollBarPolicy: Qt.ScrollBarAlwaysOn
OldControls.TableViewColumn
{
role: "what"
title: "What"
}
OldControls.TableViewColumn
{
role: "session_name"
title: "Session Name"
}
model: ListModel
{
id: mymodel
}
}
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.