QImage in QML

In this post I’ll show how to provide QImage from C++ code to QML

All we know, that Image {} element in QML supports only source property, which takes an URL as input. So how to put an QImage (or QPixmap or texture) to Image {}?

Answer is: QQuickImageProvider (in Qt 5)

First of all you have to create a so called image provider class, derived from QQuickImageProvider:

#include <QQuickImageProvider>

QT_BEGIN_NAMESPACE

class ImageProvider : public QQuickImageProvider
{
public:
explicit ImageProvider();
virtual QImage requestImage(const QString &id, QSize *size, const QSize& requestedSize);
};

You have to reimplement method requestImage(). It takes an string id as input as well as requested image size.
String id is an unique id, generated in your QML code. We will come there later
If Image {} element request specific image size, you’ll get the size in requestedSize parameter. Just check it is it valid or not. If so, you have to resize your original image and return resized version. Also, you have to return new image size in the size parameter

Before using your image provider, you have to register it in QML engine:

ImageProvider *imageProvider = new ImageProvider;
QQmlApplicationEngine engine(QUrl("qml/main.qml"));
engine.addImageProvider("images", imageProvider);

in this case, “images” is an identifier for your image provider
Note: if you want to register several identifiers for several providers, you have to create separate object for each identifier:

QQmlApplicationEngine engine(QUrl("qml/main.qml"));

ImageProvider *imageProvider = new ImageProvider;
engine.addImageProvider("images", imageProvider);

ImageProvider *imageProvider1 = new ImageProvider;
engine.addImageProvider("images1", imageProvider1);

 

And, finally, last step. Adding Image element to QML code:

Image {
source: "image://images/" + id
cache: false
}

 

Take a look at source property.
In that URL image means that you will use an image provider. Then, images is provider identifier and id is the string value, which will be passed to your requestImage() implementation

Its important to turn cache off if you gonna to reuse an image id

That’s it. Hope this will help to someone

Last note: with the QQuickImageProvider class you can pass not only QImage but also QPixmaps and OpenGL textures to Image element

 

Very last note: do not try to use QSharedPointer<QImage>

Leave a Reply