本篇文章为大家展示了如何利用上下文属性将 C++ 对象嵌入 QML 里,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。
例如,这里有一个 QML 项,它引用了当前作用域中不存在的 currentDateTime 值:
// MyItem.qml
import QtQuick 2.0
Text
{
text: currentDateTime
}
这个值可以由加载 QML 组件的 C++ 应用程序使用 QQmlContext::setContextProperty()
直接设置:
QQuickView view;
view.rootContext()->setContextProperty("currentDateTime",QDateTime::currentDateTime());
view.setSource(QUrl::fromLocalFile("MyItem.qml"));
view.show();
由于在 QML 中计算的所有表达式都是在特定上下文中计算的,如果修改了上下文,则将重新计算该上下文中的所有绑定。因此,应在应用程序初始化之外谨慎使用上下文属性,因为这可能会导致应用程序性能下降。
上下文属性可以包含 QVariant
或 QObject*
值。 这意味着也可以使用这种方法注入自定义 C++ 对象,并且可以直接在 QML 中修改和读取这些对象。修改上面的例子,嵌入一个 QObject 实例而不是一个 QDateTime
值,QML 代码在对象实例上调用一个方法:
class ApplicationData : public QObject
{
Q_OBJECT
public:
Q_INVOKABLE QDateTime getCurrentDateTime() const
{
return QDateTime::currentDateTime();
}
};
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
ApplicationData data;
QQuickView view;
view.rootContext()->setContextProperty("applicationData", &data);
view.setSource(QUrl::fromLocalFile("MyItem.qml"));
view.show();
return app.exec();
}
// MyItem.qml
import QtQuick 2.0
Text
{
text: applicationData.getCurrentDateTime()
}
请注意:从 C++ 返回到 QML 的日期/时间值可以通过 Qt.formatDateTime() 和相关函数进行格式化。
如果 QML 项需要从上下文属性接收信号,它可以使用 Connections
类型连接到它们。 例如,如果 ApplicationData
有一个名为 dataChanged()
的信号,则可以使用 Connections
对象中的 onDataChanged
处理程序连接到该信号:
Text
{
text: applicationData.getCurrentDateTime()
Connections
{
target: applicationData
onDataChanged: console.log("The application data changed!")
}
}
int main(int argc, char ** argv)
{
QGuiApplication app(argc, argv);
QStringList dataList;
dataList.append("Item 1");
dataList.append("Item 2");
dataList.append("Item 3");
dataList.append("Item 4");
QQuickView view;
QQmlContext *ctxt = view.rootContext();
ctxt->setContextProperty("myModel", QVariant::fromValue(dataList));
view.setSource(QUrl("qrc:view.qml"));
view.show();
return app.exec();
}
import QtQuick 2.0
ListView
{
width: 100; height: 100
model: myModel
delegate: Rectangle
{
height: 25
width: 100
Text { text: modelData }
}
}
#ifndef DATAOBJECT_H
#define DATAOBJECT_H
#include <QObject>
class DataObject : public QObject
{
Q_OBJECT
Q_PROPERTY(QString name READ name WRITE setName NOTIFY nameChanged)
Q_PROPERTY(QString color READ color WRITE setColor NOTIFY colorChanged)
public:
DataObject(QObject *parent=nullptr);
DataObject(const QString &name, const QString &color, QObject *parent=nullptr);
QString name() const;
void setName(const QString &name);
QString color() const;
void setColor(const QString &color);
signals:
void nameChanged();
void colorChanged();
private:
QString m_name;
QString m_color;
};
#endif // DATAOBJECT_H
#include <QDebug>
#include "dataobject.h"
DataObject::DataObject(QObject *parent)
: QObject(parent)
{
}
DataObject::DataObject(const QString &name, const QString &color, QObject *parent)
: QObject(parent), m_name(name), m_color(color)
{
}
QString DataObject::name() const
{
return m_name;
}
void DataObject::setName(const QString &name)
{
if (name != m_name)
{
m_name = name;
emit nameChanged();
}
}
QString DataObject::color() const
{
return m_color;
}
void DataObject::setColor(const QString &color)
{
if (color != m_color)
{
m_color = color;
emit colorChanged();
}
}
#include "dataobject.h"
int main(int argc, char ** argv)
{
QGuiApplication app(argc, argv);
QList<QObject*> dataList;
dataList.append(new DataObject("Item 1", "red"));
dataList.append(new DataObject("Item 2", "green"));
dataList.append(new DataObject("Item 3", "blue"));
dataList.append(new DataObject("Item 4", "yellow"));
QQuickView view;
view.setResizeMode(QQuickView::SizeRootObjectToView);
QQmlContext *ctxt = view.rootContext();
ctxt->setContextProperty("myModel", QVariant::fromValue(dataList));
view.setSource(QUrl("qrc:view.qml"));
view.show();
return app.exec();
}
import QtQuick 2.0
ListView
{
width: 100; height: 100
model: myModel
delegate: Rectangle
{
height: 25
width: 100
color: model.modelData.color
Text { text: name }
}
}
#include <QAbstractListModel>
#include <QStringList>
class Animal
{
public:
Animal(const QString &type, const QString &size);
QString type() const;
QString size() const;
private:
QString m_type;
QString m_size;
};
class AnimalModel : public QAbstractListModel
{
Q_OBJECT
public:
enum AnimalRoles
{
TypeRole = Qt::UserRole + 1,
SizeRole
};
AnimalModel(QObject *parent = nullptr);
void addAnimal(const Animal &animal);
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<Animal> m_animals;
};
#include "model.h"
Animal::Animal(const QString &type, const QString &size)
: m_type(type), m_size(size)
{
}
QString Animal::type() const
{
return m_type;
}
QString Animal::size() const
{
return m_size;
}
AnimalModel::AnimalModel(QObject *parent)
: QAbstractListModel(parent)
{
}
void AnimalModel::addAnimal(const Animal &animal)
{
beginInsertRows(QModelIndex(), rowCount(), rowCount());
m_animals << animal;
endInsertRows();
}
int AnimalModel::rowCount(const QModelIndex & parent) const
{
Q_UNUSED(parent)
return m_animals.count();
}
QVariant AnimalModel::data(const QModelIndex & index, int role) const
{
if (index.row() < 0 || index.row() >= m_animals.count())
return QVariant();
const Animal &animal = m_animals[index.row()];
if (role == TypeRole)
return animal.type();
else if (role == SizeRole)
return animal.size();
return QVariant();
}
QHash<int, QByteArray> AnimalModel::roleNames() const
{
QHash<int, QByteArray> roles;
roles[TypeRole] = "type";
roles[SizeRole] = "size";
return roles;
}
int main(int argc, char ** argv)
{
QGuiApplication app(argc, argv);
AnimalModel model;
model.addAnimal(Animal("Wolf", "Medium"));
model.addAnimal(Animal("Polar bear", "Large"));
model.addAnimal(Animal("Quoll", "Small"));
QQuickView view;
view.setResizeMode(QQuickView::SizeRootObjectToView);
QQmlContext *ctxt = view.rootContext();
ctxt->setContextProperty("myModel", &model);
view.setSource(QUrl("qrc:view.qml"));
view.show();
return app.exec();
}
import QtQuick 2.0
ListView
{
width: 200; height: 250
model: myModel
delegate: Text { text: "Animal: " + type + ", " + size }
}
上述内容就是如何利用上下文属性将 C++ 对象嵌入 QML 里,你们学到知识或技能了吗?如果还想学到更多技能或者丰富自己的知识储备,欢迎关注亿速云行业资讯频道。
亿速云「云服务器」,即开即用、新一代英特尔至强铂金CPU、三副本存储NVMe SSD云盘,价格低至29元/月。点击查看>>
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。