C
Qt Quick Ultralite image_loading Example
// Copyright (C) 2024 The Qt Company Ltd.
// SPDX-License-Identifier: LicenseRef-Qt-Commercial
#include "myimageloader.h"
#include <qul/application.h>
#include <platforminterface/allocator.h>
Qul::SharedImage MyImageProvider::requestImage(const char *imageName, size_t imageNameLength)
{
if (imageNameLength < 8)
return Qul::SharedImage();
// Parse the image name to determine the colors to use for the image
colors[0] = imageName[5] - '0';
colors[1] = imageName[6] - '0';
colors[2] = imageName[7] - '0';
loadSteps = 3;
currentLoadStep = 0;
// Create the image and mark it as being-written-to
Qul::Image img(120, 120, Qul::PixelFormat_RGB16);
sharedImage = img;
img.beginWrite();
// Start the image loading process.
//
// Here, we start a timer that fills the image data step by step.
// When multithreading is available, this could start a real asynchronous task.
//
// When done, post an event to trigger endWrite().
// (postEvent() is safe to call asynchronously, while endWrite() is not)
Timeout timeout;
timeout.object = this;
m_asyncLoadTimer.setInterval(300);
m_asyncLoadTimer.onTimeout(timeout);
m_asyncLoadTimer.start();
// Return the unfinished image. Since beginWrite() was called on it, nothing
// will be drawn to the screen yet.
return sharedImage;
}
// This function will be called on timer's timeout
void MyImageProvider::Timeout::operator()()
{
// Fill a segment of the image with a solid color
assert(object->sharedImage.image());
Qul::Image &image = *(object->sharedImage).image();
uint16_t *pixelBegin = reinterpret_cast<uint16_t *>(
image.bits() + image.bytesPerLine() * image.height() * object->currentLoadStep / object->loadSteps);
uint16_t *pixelEnd = reinterpret_cast<uint16_t *>(
image.bits() + image.bytesPerLine() * image.height() * (object->currentLoadStep + 1) / object->loadSteps);
const uint32_t color = (0xFF / 2 * object->colors[object->currentLoadStep]) << (object->currentLoadStep * 8);
const uint16_t colorRGB16 = ((color >> 3) & 0x001f) | ((color >> 5) & 0x07e0) | ((color >> 8) & 0xf800);
std::fill(pixelBegin, pixelEnd, colorRGB16);
object->currentLoadStep++;
if (object->currentLoadStep == object->loadSteps) {
object->m_asyncLoadTimer.stop();
object->postEvent(Qul::PlatformInterface::qul_new<MyImageLoadedEvent>(image));
}
}
void MyImageProvider::onEvent(MyImageLoadedEvent *const &event)
{
// Causes the finished image to become visible.
event->sharedImage.image()->endWrite();
Qul::PlatformInterface::qul_delete(event);
}
void MyImageProvider::onEventDiscarded(MyImageLoadedEvent *const &event)
{
// Causes the finished image to become visible.
event->sharedImage.image()->endWrite();
Qul::PlatformInterface::qul_delete(event);
}