QQuickImageProvider 的正确使用方法是什么?
What is the right way to use QQuickImageProvider?
我需要 select 动态 qpixmaps 以在 QML 图像项中显示。该 qpixmaps 应该从源 qpixmap 中裁剪,我将从 QML 文件中设置它。我希望它们在 QML 的第一个需求下被 C++ 代码裁剪,并被缓存以备将来使用。对于动态图像操作,它应该从 QQuickImageProvider 派生我自己的 class 并将其加载到 QML 应用程序引擎。但是我怎样才能控制源qpixmap呢?通过 属性?如果是,那么我的自定义提供程序必须派生自 QObject,并且它的实例应该在 QML 中声明,不是吗?但是它怎么能被引擎加载呢?我觉得这样的实现方式是错误的,但是哪一种是正确的呢?
UPD:好的,我有一个 class:
class MyQuickImageProvider : public QQuickImageProvider {
public:
...
// This method should set the source image path
void setPath ( QUrl path );
// Overriden method of base class; should return cropped image
virtual QPixmap requestPixmap ( const QString &id, QSize *size, const QSize &requestedSize );
...
}
在 main.cpp 中加载为:
QQmlApplicationEngine engine;
...
engine.addImageProvider("my_quick_image_provider", new MyQuickImageProvider(QQmlImageProviderBase::Image));
我想通过 QML 更改源图像路径。我怎样才能让它访问 setPath 方法?显而易见的方法是将该方法声明为 Q_INVOKABLE(并从 QObject 派生 MyQuickImageProvider 和 qmlRegisterType 它),但是我应该在 QML 源中声明我的 class 的实例:
MyQuickImageProvider {
id: my_quick_image_provider
...
}
从 main.cpp 访问它会有问题。这样的设计对我来说似乎很奇怪。有没有更优雅的方案?
您没有将 MyQuickImageProvider
用作 QML 对象,也没有定义 Q_INVOKABLE
方法,因为您无法从 QML 访问图像提供程序对象。
engine.addImageProvider("my_quick_image_provider", [...]
设置您访问图像的名称,例如
// qml file
Image {
source: "image://my_quick_image_provider/name_of_my_image"
}
后面的部分 "name_of_my_image" 称为 id
,您可以在
中找到它
virtual QPixmap requestPixmap ( const QString &id, QSize *size, const QSize &requestedSize );
现在在你的 MyQuickImageProvider
中实现 requestPixmap
并让它使用 id
字符串来生成 QPixmap。
我认为您可以放弃 void setPath ( QUrl path );
方法,因为您只需要一个图像提供程序实例来处理所有此类图像。
由于构造函数不是从基础 class 继承的,我认为 new MyQuickImageProvider(QQmlImageProviderBase::Image));
没有意义。最好添加一个没有参数的构造函数
class MyQuickImageProvider : public QQuickImageProvider {
public:
MyQuickImageProvider();
// ...
并在您的初始化列表中包含图像类型:
MyQuickImageProvider::MyQuickImageProvider()
: QQuickImageProvider(QQuickImageProvider::Pixmap)
{
}
我需要 select 动态 qpixmaps 以在 QML 图像项中显示。该 qpixmaps 应该从源 qpixmap 中裁剪,我将从 QML 文件中设置它。我希望它们在 QML 的第一个需求下被 C++ 代码裁剪,并被缓存以备将来使用。对于动态图像操作,它应该从 QQuickImageProvider 派生我自己的 class 并将其加载到 QML 应用程序引擎。但是我怎样才能控制源qpixmap呢?通过 属性?如果是,那么我的自定义提供程序必须派生自 QObject,并且它的实例应该在 QML 中声明,不是吗?但是它怎么能被引擎加载呢?我觉得这样的实现方式是错误的,但是哪一种是正确的呢?
UPD:好的,我有一个 class:
class MyQuickImageProvider : public QQuickImageProvider {
public:
...
// This method should set the source image path
void setPath ( QUrl path );
// Overriden method of base class; should return cropped image
virtual QPixmap requestPixmap ( const QString &id, QSize *size, const QSize &requestedSize );
...
}
在 main.cpp 中加载为:
QQmlApplicationEngine engine;
...
engine.addImageProvider("my_quick_image_provider", new MyQuickImageProvider(QQmlImageProviderBase::Image));
我想通过 QML 更改源图像路径。我怎样才能让它访问 setPath 方法?显而易见的方法是将该方法声明为 Q_INVOKABLE(并从 QObject 派生 MyQuickImageProvider 和 qmlRegisterType 它),但是我应该在 QML 源中声明我的 class 的实例:
MyQuickImageProvider {
id: my_quick_image_provider
...
}
从 main.cpp 访问它会有问题。这样的设计对我来说似乎很奇怪。有没有更优雅的方案?
您没有将 MyQuickImageProvider
用作 QML 对象,也没有定义 Q_INVOKABLE
方法,因为您无法从 QML 访问图像提供程序对象。
engine.addImageProvider("my_quick_image_provider", [...]
设置您访问图像的名称,例如
// qml file
Image {
source: "image://my_quick_image_provider/name_of_my_image"
}
后面的部分 "name_of_my_image" 称为 id
,您可以在
virtual QPixmap requestPixmap ( const QString &id, QSize *size, const QSize &requestedSize );
现在在你的 MyQuickImageProvider
中实现 requestPixmap
并让它使用 id
字符串来生成 QPixmap。
我认为您可以放弃 void setPath ( QUrl path );
方法,因为您只需要一个图像提供程序实例来处理所有此类图像。
由于构造函数不是从基础 class 继承的,我认为 new MyQuickImageProvider(QQmlImageProviderBase::Image));
没有意义。最好添加一个没有参数的构造函数
class MyQuickImageProvider : public QQuickImageProvider {
public:
MyQuickImageProvider();
// ...
并在您的初始化列表中包含图像类型:
MyQuickImageProvider::MyQuickImageProvider()
: QQuickImageProvider(QQuickImageProvider::Pixmap)
{
}