Qt
Internal/Contributor docs for the Qt SDK. <b>Note:</b> These are NOT official API docs; those are found <a href='https://doc.qt.io/'>here</a>.
Loading...
Searching...
No Matches
qimagereader.cpp
Go to the documentation of this file.
1// Copyright (C) 2016 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3
4//#define QIMAGEREADER_DEBUG
5
97#include "qimagereader.h"
98
99#include <qbytearray.h>
100#ifdef QIMAGEREADER_DEBUG
101#include <qdebug.h>
102#endif
103#include <qfile.h>
104#include <qfileinfo.h>
105#include <qimage.h>
106#include <qimageiohandler.h>
107#include <qlist.h>
108#include <qrect.h>
109#include <qsize.h>
110#include <qcolor.h>
111#include <qvariant.h>
112
113// factory loader
114#include <qcoreapplication.h>
115#include <private/qfactoryloader_p.h>
116#include <QtCore/private/qlocking_p.h>
117
118// for qt_getImageText
119#include <private/qimage_p.h>
120
121// image handlers
122#include <private/qbmphandler_p.h>
123#include <private/qppmhandler_p.h>
124#include <private/qxbmhandler_p.h>
125#include <private/qxpmhandler_p.h>
126#ifndef QT_NO_IMAGEFORMAT_PNG
127#include <private/qpnghandler_p.h>
128#endif
129
130#include <private/qimagereaderwriterhelpers_p.h>
131#include <qtgui_tracepoints_p.h>
132
133#include <algorithm>
134
136
137using namespace QImageReaderWriterHelpers;
138using namespace Qt::StringLiterals;
139
140Q_TRACE_POINT(qtgui, QImageReader_read_before_reading, QImageReader *reader, const QString &filename);
141Q_TRACE_POINT(qtgui, QImageReader_read_after_reading, QImageReader *reader, bool result);
142
144 const QByteArray &format,
145 bool autoDetectImageFormat,
146 bool ignoresFormatAndExtension)
147{
148 if (!autoDetectImageFormat && format.isEmpty())
149 return nullptr;
150
151 QByteArray form = format.toLower();
152 QImageIOHandler *handler = nullptr;
153 QByteArray suffix;
154
155#ifndef QT_NO_IMAGEFORMATPLUGIN
156 Q_CONSTINIT static QBasicMutex mutex;
157 const auto locker = qt_scoped_lock(mutex);
158
159 typedef QMultiMap<int, QString> PluginKeyMap;
160
161 // check if we have plugins that support the image format
163 const PluginKeyMap keyMap = l->keyMap();
164
165#ifdef QIMAGEREADER_DEBUG
166 qDebug() << "QImageReader::createReadHandler( device =" << (void *)device << ", format =" << format << "),"
167 << keyMap.uniqueKeys().size() << "plugins available: " << keyMap;
168#endif
169
170 int suffixPluginIndex = -1;
171#endif // QT_NO_IMAGEFORMATPLUGIN
172
173 if (device && format.isEmpty() && autoDetectImageFormat && !ignoresFormatAndExtension) {
174 // if there's no format, see if \a device is a file, and if so, find
175 // the file suffix and find support for that format among our plugins.
176 // this allows plugins to override our built-in handlers.
177 if (QFile *file = qobject_cast<QFile *>(device)) {
178#ifdef QIMAGEREADER_DEBUG
179 qDebug() << "QImageReader::createReadHandler: device is a file:" << file->fileName();
180#endif
181 if (!(suffix = QFileInfo(file->fileName()).suffix().toLower().toLatin1()).isEmpty()) {
182#ifndef QT_NO_IMAGEFORMATPLUGIN
183 const int index = keyMap.key(QString::fromLatin1(suffix), -1);
184 if (index != -1) {
185#ifdef QIMAGEREADER_DEBUG
186 qDebug() << "QImageReader::createReadHandler: suffix recognized; the"
187 << suffix << "plugin might be able to read this";
188#endif
189 suffixPluginIndex = index;
190 }
191#endif // QT_NO_IMAGEFORMATPLUGIN
192 }
193 }
194 }
195
196 QByteArray testFormat = !form.isEmpty() ? form : suffix;
197
198 if (ignoresFormatAndExtension)
199 testFormat = QByteArray();
200
201#ifndef QT_NO_IMAGEFORMATPLUGIN
202 if (suffixPluginIndex != -1) {
203 // check if the plugin that claims support for this format can load
204 // from this device with this format.
205 const qint64 pos = device ? device->pos() : 0;
206 const int index = keyMap.key(QString::fromLatin1(suffix), -1);
207 if (index != -1) {
208 QImageIOPlugin *plugin = qobject_cast<QImageIOPlugin *>(l->instance(index));
210 handler = plugin->create(device, testFormat);
211#ifdef QIMAGEREADER_DEBUG
212 qDebug() << "QImageReader::createReadHandler: using the" << suffix
213 << "plugin";
214#endif
215 }
216 }
217 if (device && !device->isSequential())
218 device->seek(pos);
219 }
220
221 if (!handler && !testFormat.isEmpty() && !ignoresFormatAndExtension) {
222 // check if any plugin supports the format (they are not allowed to
223 // read from the device yet).
224 const qint64 pos = device ? device->pos() : 0;
225
226 if (autoDetectImageFormat) {
227 const int keyCount = keyMap.size();
228 for (int i = 0; i < keyCount; ++i) {
229 if (i != suffixPluginIndex) {
230 QImageIOPlugin *plugin = qobject_cast<QImageIOPlugin *>(l->instance(i));
232#ifdef QIMAGEREADER_DEBUG
233 qDebug() << "QImageReader::createReadHandler: the" << keyMap.keys().at(i) << "plugin can read this format";
234#endif
235 handler = plugin->create(device, testFormat);
236 break;
237 }
238 }
239 }
240 } else {
241 const int testIndex = keyMap.key(QLatin1StringView(testFormat), -1);
242 if (testIndex != -1) {
243 QImageIOPlugin *plugin = qobject_cast<QImageIOPlugin *>(l->instance(testIndex));
245#ifdef QIMAGEREADER_DEBUG
246 qDebug() << "QImageReader::createReadHandler: the" << testFormat << "plugin can read this format";
247#endif
248 handler = plugin->create(device, testFormat);
249 }
250 }
251 }
252 if (device && !device->isSequential())
253 device->seek(pos);
254 }
255
256#endif // QT_NO_IMAGEFORMATPLUGIN
257
258 // if we don't have a handler yet, check if we have built-in support for
259 // the format
260 if (!handler && !testFormat.isEmpty()) {
261 if (false) {
262#ifndef QT_NO_IMAGEFORMAT_PNG
263 } else if (testFormat == "png") {
264 handler = new QPngHandler;
265#endif
266#ifndef QT_NO_IMAGEFORMAT_BMP
267 } else if (testFormat == "bmp") {
268 handler = new QBmpHandler;
269 } else if (testFormat == "dib") {
270 handler = new QBmpHandler(QBmpHandler::DibFormat);
271#endif
272#ifndef QT_NO_IMAGEFORMAT_XPM
273 } else if (testFormat == "xpm") {
274 handler = new QXpmHandler;
275#endif
276#ifndef QT_NO_IMAGEFORMAT_XBM
277 } else if (testFormat == "xbm") {
278 handler = new QXbmHandler;
279 handler->setOption(QImageIOHandler::SubType, testFormat);
280#endif
281#ifndef QT_NO_IMAGEFORMAT_PPM
282 } else if (testFormat == "pbm" || testFormat == "pbmraw" || testFormat == "pgm"
283 || testFormat == "pgmraw" || testFormat == "ppm" || testFormat == "ppmraw") {
284 handler = new QPpmHandler;
285 handler->setOption(QImageIOHandler::SubType, testFormat);
286#endif
287 }
288
289#ifdef QIMAGEREADER_DEBUG
290 if (handler)
291 qDebug() << "QImageReader::createReadHandler: using the built-in handler for" << testFormat;
292#endif
293 }
294
295 if (handler && device && !suffix.isEmpty()) {
296 Q_ASSERT(qobject_cast<QFile *>(device));
297 // We have a file claiming to be of a recognized format. Now confirm that
298 // the handler also recognizes the file contents.
299 const qint64 pos = device->pos();
300 handler->setDevice(device);
301 if (!form.isEmpty())
302 handler->setFormat(form);
303 bool canRead = handler->canRead();
304 device->seek(pos);
305 if (canRead) {
306 // ok, we're done.
307 return handler;
308 }
309#ifdef QIMAGEREADER_DEBUG
310 qDebug() << "QImageReader::createReadHandler: the" << suffix << "handler can not read this file";
311#endif
312 // File may still be valid, just with wrong suffix, so fall back to
313 // finding a handler based on contents, below.
314 delete handler;
315 handler = nullptr;
316 }
317
318#ifndef QT_NO_IMAGEFORMATPLUGIN
319 if (!handler && (autoDetectImageFormat || ignoresFormatAndExtension)) {
320 // check if any of our plugins recognize the file from its contents.
321 const qint64 pos = device ? device->pos() : 0;
322 const int keyCount = keyMap.size();
323 for (int i = 0; i < keyCount; ++i) {
324 if (i != suffixPluginIndex) {
325 QImageIOPlugin *plugin = qobject_cast<QImageIOPlugin *>(l->instance(i));
327 handler = plugin->create(device, testFormat);
328#ifdef QIMAGEREADER_DEBUG
329 qDebug() << "QImageReader::createReadHandler: the" << keyMap.value(i) << "plugin can read this data";
330#endif
331 break;
332 }
333 }
334 }
335 if (device && !device->isSequential())
336 device->seek(pos);
337 }
338#endif // QT_NO_IMAGEFORMATPLUGIN
339
340 if (!handler && (autoDetectImageFormat || ignoresFormatAndExtension)) {
341 // check if any of our built-in handlers recognize the file from its
342 // contents.
343 int currentFormat = 0;
344 if (!suffix.isEmpty()) {
345 // If reading from a file with a suffix, start testing our
346 // built-in handler for that suffix first.
347 for (int i = 0; i < _qt_NumFormats; ++i) {
348 if (_qt_BuiltInFormats[i].extension == suffix) {
349 currentFormat = i;
350 break;
351 }
352 }
353 }
354
355 QByteArray subType;
356 int numFormats = _qt_NumFormats;
357 while (device && numFormats >= 0) {
358 const qint64 pos = device->pos();
359 switch (currentFormat) {
360#ifndef QT_NO_IMAGEFORMAT_PNG
361 case _qt_PngFormat:
363 handler = new QPngHandler;
364 break;
365#endif
366#ifndef QT_NO_IMAGEFORMAT_BMP
367 case _qt_BmpFormat:
369 handler = new QBmpHandler;
370 break;
371#endif
372#ifndef QT_NO_IMAGEFORMAT_XPM
373 case _qt_XpmFormat:
375 handler = new QXpmHandler;
376 break;
377#endif
378#ifndef QT_NO_IMAGEFORMAT_PPM
379 case _qt_PbmFormat:
380 case _qt_PgmFormat:
381 case _qt_PpmFormat:
382 if (QPpmHandler::canRead(device, &subType)) {
383 handler = new QPpmHandler;
384 handler->setOption(QImageIOHandler::SubType, subType);
385 }
386 break;
387#endif
388#ifndef QT_NO_IMAGEFORMAT_XBM
389 case _qt_XbmFormat:
391 handler = new QXbmHandler;
392 break;
393#endif
394 default:
395 break;
396 }
397 if (!device->isSequential())
398 device->seek(pos);
399
400 if (handler) {
401#ifdef QIMAGEREADER_DEBUG
402 qDebug("QImageReader::createReadHandler: the %s built-in handler can read this data",
403 _qt_BuiltInFormats[currentFormat].extension);
404#endif
405 break;
406 }
407
408 --numFormats;
409 ++currentFormat;
410 if (currentFormat >= _qt_NumFormats)
411 currentFormat = 0;
412 }
413 }
414
415 if (!handler) {
416#ifdef QIMAGEREADER_DEBUG
417 qDebug("QImageReader::createReadHandler: no handlers found. giving up.");
418#endif
419 // no handler: give up.
420 return nullptr;
421 }
422
423 handler->setDevice(device);
424 if (!form.isEmpty())
425 handler->setFormat(form);
426 return handler;
427}
428
465
466int QImageReaderPrivate::maxAlloc = 256; // 256 MB is enough for an 8K 64bpp image
467
472 : autoDetectImageFormat(true), ignoresFormatAndExtension(false)
473{
474 device = nullptr;
475 deleteDevice = false;
476 handler = nullptr;
477 quality = -1;
480
481 q = qq;
482}
483
488{
489 delete handler;
490 if (deleteDevice)
491 delete device;
492}
493
498{
499 if (handler)
500 return true;
501
502 // check some preconditions
505 errorString = QImageReader::tr("Invalid device");
506 return false;
507 }
508
509 // probe the file extension
511 Q_ASSERT(qobject_cast<QFile*>(device) != nullptr); // future-proofing; for now this should always be the case, so...
512 QFile *file = static_cast<QFile *>(device);
513
515 // this is bad. we should abort the open attempt and note the failure.
518 return false;
519 }
520
521 QList<QByteArray> extensions = QImageReader::supportedImageFormats();
522 if (!format.isEmpty()) {
523 // Try the most probable extension first
524 int currentFormatIndex = extensions.indexOf(format.toLower());
525 if (currentFormatIndex > 0)
526 extensions.swapItemsAt(0, currentFormatIndex);
527 }
528
529 int currentExtension = 0;
530
532 bool fileIsOpen;
533
534 do {
536 + QLatin1StringView(extensions.at(currentExtension++).constData()));
537 fileIsOpen = file->open(QIODevice::ReadOnly);
538 } while (!fileIsOpen && currentExtension < extensions.size());
539
540 if (!fileIsOpen) {
542 errorString = QImageReader::tr("File not found");
543 file->setFileName(fileName); // restore the old file name
544 return false;
545 }
546 }
547
548 // assign a handler
551 errorString = QImageReader::tr("Unsupported image format");
552 return false;
553 }
554 return true;
555}
556
565
574
585
597
602{
603 delete d;
604}
605
618{
619 d->format = format;
620}
621
637{
638 if (d->format.isEmpty()) {
639 if (!d->initHandler())
640 return QByteArray();
641 return d->handler->canRead() ? d->handler->format() : QByteArray();
642 }
643
644 return d->format;
645}
646
690
698{
699 return d->autoDetectImageFormat;
700}
701
702
718{
719 d->ignoresFormatAndExtension = ignored;
720}
721
722
735
736
751{
752 delete d->handler;
753 d->handler = nullptr;
754 if (d->device && d->deleteDevice)
755 delete d->device;
756 d->device = device;
757 d->deleteDevice = false;
758 d->text.clear();
759}
760
766{
767 return d->device;
768}
769
782{
784 d->deleteDevice = true;
785}
786
797{
798 QFile *file = qobject_cast<QFile *>(d->device);
799 return file ? file->fileName() : QString();
800}
801
823{
824 d->quality = quality;
825}
826
835{
836 return d->quality;
837}
838
839
851{
853 return d->handler->option(QImageIOHandler::Size).toSize();
854
855 return QSize();
856}
857
877
891{
892 d->getText();
893 return d->text.keys();
894}
895
907{
908 d->getText();
909 return d->text.value(key);
910}
911
920{
921 d->clipRect = rect;
922}
923
932{
933 return d->clipRect;
934}
935
951{
952 d->scaledSize = size;
953}
954
961{
962 return d->scaledSize;
963}
964
976
983{
984 return d->scaledClipRect;
985}
986
1001
1012{
1014 return qvariant_cast<QColor>(d->handler->option(QImageIOHandler::BackgroundColor));
1015 return QColor();
1016}
1017
1027{
1029 return d->handler->option(QImageIOHandler::Animation).toBool();
1030 return false;
1031}
1032
1039{
1041 return d->handler->option(QImageIOHandler::SubType).toByteArray();
1042 return QByteArray();
1043}
1044
1050QList<QByteArray> QImageReader::supportedSubTypes() const
1051{
1053 return qvariant_cast<QList<QByteArray> >(d->handler->option(QImageIOHandler::SupportedSubTypes));
1054 return QList<QByteArray>();
1055}
1056
1065QImageIOHandler::Transformations QImageReader::transformation() const
1066{
1070 return QImageIOHandler::Transformations(option);
1071}
1072
1086
1095{
1096 switch (d->autoTransform) {
1098 return true;
1100 return false;
1102 Q_FALLTHROUGH();
1103 default:
1104 break;
1105 }
1106 return false;
1107}
1108
1127{
1128 if (!d->initHandler())
1129 return false;
1130
1131 return d->handler->canRead();
1132}
1133
1147{
1148 // Because failed image reading might have side effects, we explicitly
1149 // return a null image instead of the image we've just created.
1150 QImage image;
1151 return read(&image) ? image : QImage();
1152}
1153
1154extern void qt_imageTransform(QImage &src, QImageIOHandler::Transformations orient);
1155
1177{
1178 if (!image) {
1179 qWarning("QImageReader::read: cannot read into null pointer");
1180 return false;
1181 }
1182
1183 if (!d->initHandler())
1184 return false;
1185
1187 if ((scaledSize.width() <= 0 && scaledSize.height() > 0) ||
1188 (scaledSize.height() <= 0 && scaledSize.width() > 0)) {
1189 // if only one dimension is given, let's try to calculate the second one
1190 // based on the original image size and maintaining the aspect ratio
1191 if (const QSize originalSize = size(); !originalSize.isEmpty()) {
1192 if (scaledSize.width() <= 0) {
1193 const auto ratio = qreal(scaledSize.height()) / originalSize.height();
1194 scaledSize.setWidth(qRound(originalSize.width() * ratio));
1195 } else {
1196 const auto ratio = qreal(scaledSize.width()) / originalSize.width();
1197 scaledSize.setHeight(qRound(originalSize.height() * ratio));
1198 }
1199 }
1200 }
1201
1202 const bool supportScaledSize = supportsOption(QImageIOHandler::ScaledSize) && scaledSize.isValid();
1203 const bool supportClipRect = supportsOption(QImageIOHandler::ClipRect) && !d->clipRect.isNull();
1204 const bool supportScaledClipRect = supportsOption(QImageIOHandler::ScaledClipRect) && !d->scaledClipRect.isNull();
1205
1206 // set the handler specific options.
1207 if (supportScaledSize) {
1208 if (supportClipRect || d->clipRect.isNull()) {
1209 // Only enable the ScaledSize option if there is no clip rect, or
1210 // if the handler also supports ClipRect.
1212 }
1213 }
1214 if (supportClipRect)
1216 if (supportScaledClipRect)
1220
1221 // read the image
1222 QString filename = fileName();
1223 if (Q_TRACE_ENABLED(QImageReader_read_before_reading)) {
1224 Q_TRACE(QImageReader_read_before_reading, this, filename.isEmpty() ? u"unknown"_s : filename);
1225 }
1226
1227 const bool result = d->handler->read(image);
1228
1229 Q_TRACE(QImageReader_read_after_reading, this, result);
1230
1231 if (!result) {
1233 d->errorString = QImageReader::tr("Unable to read image data");
1234 return false;
1235 }
1236
1237 // provide default implementations for any unsupported image
1238 // options
1239 if (supportClipRect) {
1240 if (supportScaledSize) {
1241 if (supportScaledClipRect) {
1242 // all features are supported by the handler; nothing to do.
1243 } else {
1244 // the image is already scaled, so apply scaled clipping.
1245 if (!d->scaledClipRect.isNull())
1246 *image = image->copy(d->scaledClipRect);
1247 }
1248 } else {
1249 if (supportScaledClipRect) {
1250 // supports scaled clipping but not scaling, most
1251 // likely a broken handler.
1252 } else {
1253 if (scaledSize.isValid()) {
1255 }
1256 if (d->scaledClipRect.isValid()) {
1257 *image = image->copy(d->scaledClipRect);
1258 }
1259 }
1260 }
1261 } else {
1262 if (supportScaledSize && d->clipRect.isNull()) {
1263 if (supportScaledClipRect) {
1264 // nothing to do (ClipRect is ignored!)
1265 } else {
1266 // provide all workarounds.
1267 if (d->scaledClipRect.isValid()) {
1268 *image = image->copy(d->scaledClipRect);
1269 }
1270 }
1271 } else {
1272 if (supportScaledClipRect) {
1273 // this makes no sense; a handler that supports
1274 // ScaledClipRect but not ScaledSize is broken, and we
1275 // can't work around it.
1276 } else {
1277 // provide all workarounds.
1278 if (d->clipRect.isValid())
1279 *image = image->copy(d->clipRect);
1280 if (scaledSize.isValid())
1282 if (d->scaledClipRect.isValid())
1283 *image = image->copy(d->scaledClipRect);
1284 }
1285 }
1286 }
1287
1288 // successful read; check for "@Nx" file name suffix and set device pixel ratio.
1289 static bool disableNxImageLoading = !qEnvironmentVariableIsEmpty("QT_HIGHDPI_DISABLE_2X_IMAGE_LOADING");
1290 if (!disableNxImageLoading) {
1291 const QByteArray suffix = QFileInfo(filename).baseName().right(3).toLatin1();
1292 if (suffix.size() == 3 && suffix[0] == '@' && suffix[1] >= '2' && suffix[1] <= '9' && suffix[2] == 'x')
1293 image->setDevicePixelRatio(suffix[1] - '0');
1294 }
1295 if (autoTransform())
1297
1298 return true;
1299}
1300
1313{
1314 if (!d->initHandler())
1315 return false;
1316 return d->handler->jumpToNextImage();
1317}
1318
1328bool QImageReader::jumpToImage(int imageNumber)
1329{
1330 if (!d->initHandler())
1331 return false;
1332 return d->handler->jumpToImage(imageNumber);
1333}
1334
1344{
1345 if (!d->initHandler())
1346 return -1;
1347 return d->handler->loopCount();
1348}
1349
1360{
1361 if (!d->initHandler())
1362 return -1;
1363 return d->handler->imageCount();
1364}
1365
1376{
1377 if (!d->initHandler())
1378 return -1;
1379 return d->handler->nextImageDelay();
1380}
1381
1392{
1393 if (!d->initHandler())
1394 return -1;
1395 return d->handler->currentImageNumber();
1396}
1397
1405{
1406 if (!d->initHandler())
1407 return QRect();
1408 return d->handler->currentImageRect();
1409}
1410
1420
1428{
1429 if (d->errorString.isEmpty())
1430 return QImageReader::tr("Unknown error");
1431 return d->errorString;
1432}
1433
1451{
1452 if (!d->initHandler())
1453 return false;
1454 return d->handler->supportsOption(option);
1455}
1456
1462{
1465 return QByteArray();
1466
1467 return imageFormat(&file);
1468}
1469
1477{
1479 QImageIOHandler *handler = createReadHandlerHelper(device, format, /* autoDetectImageFormat = */ true, false);
1480 if (handler) {
1481 if (handler->canRead())
1482 format = handler->format();
1483 delete handler;
1484 }
1485 return format;
1486}
1487
1520
1534
1551
1560{
1561 static int envLimit = []() {
1562 bool ok = false;
1563 int res = qEnvironmentVariableIntValue("QT_IMAGEIO_MAXALLOC", &ok);
1564 return ok ? res : -1;
1565 }();
1566
1567 return envLimit >= 0 ? envLimit : QImageReaderPrivate::maxAlloc;
1568}
1569
1590{
1591 if (mbLimit >= 0)
1593}
1594
IOBluetoothDevice * device
bool canRead() const override
Returns true if an image can be read from the device (i.e., the image format is supported,...
\inmodule QtCore
Definition qbytearray.h:57
qsizetype size() const noexcept
Returns the number of bytes in this byte array.
Definition qbytearray.h:494
bool isEmpty() const noexcept
Returns true if the byte array has size 0; otherwise returns false.
Definition qbytearray.h:107
The QColor class provides colors based on RGB, HSV or CMYK values.
Definition qcolor.h:31
FileError error() const
Returns the file error status.
QString baseName() const
Returns the base name of the file without the path.
QString suffix() const
Returns the suffix (extension) of the file.
\inmodule QtCore
Definition qfile.h:93
QFILE_MAYBE_NODISCARD bool open(OpenMode flags) override
Opens the file using OpenMode mode, returning true if successful; otherwise false.
Definition qfile.cpp:904
void setFileName(const QString &name)
Sets the name of the file.
Definition qfile.cpp:302
QString fileName() const override
Returns the name set by setFileName() or to the QFile constructors.
Definition qfile.cpp:277
virtual bool isEmpty() const
\inmodule QtCore \reentrant
Definition qiodevice.h:34
virtual bool open(QIODeviceBase::OpenMode mode)
Opens the device and sets its OpenMode to mode.
bool isOpen() const
Returns true if the device is open; otherwise returns false.
QString errorString() const
Returns a human-readable description of the last device error that occurred.
The QImageIOHandler class defines the common image I/O interface for all image formats in Qt.
virtual QRect currentImageRect() const
Returns the rect of the current image.
virtual int nextImageDelay() const
For image formats that support animation, this function returns the number of milliseconds to wait un...
virtual int imageCount() const
For image formats that support animation, this function returns the number of images in the animation...
ImageOption
This enum describes the different options supported by QImageIOHandler.
virtual bool jumpToNextImage()
For image formats that support animation, this function jumps to the next image.
virtual int currentImageNumber() const
For image formats that support animation, this function returns the sequence number of the current im...
virtual bool canRead() const =0
Returns true if an image can be read from the device (i.e., the image format is supported,...
virtual void setOption(ImageOption option, const QVariant &value)
Sets the option option with the value value.
QByteArray format() const
Returns the format that is currently assigned to QImageIOHandler.
virtual bool supportsOption(ImageOption option) const
Returns true if the QImageIOHandler supports the option option; otherwise returns false.
virtual QVariant option(ImageOption option) const
Returns the value assigned to option as a QVariant.
void setDevice(QIODevice *device)
Sets the device of the QImageIOHandler to device.
virtual bool jumpToImage(int imageNumber)
For image formats that support animation, this function jumps to the image whose sequence number is i...
virtual int loopCount() const
For image formats that support animation, this function returns the number of times the animation sho...
virtual bool read(QImage *image)=0
Read an image from the device, and stores it in image.
void setFormat(const QByteArray &format)
Sets the format of the QImageIOHandler to format.
\inmodule QtGui
virtual QImageIOHandler * create(QIODevice *device, const QByteArray &format=QByteArray()) const =0
Creates and returns a QImageIOHandler subclass, with device and format set.
virtual Capabilities capabilities(QIODevice *device, const QByteArray &format) const =0
Returns the capabilities of the plugin, based on the data in device and the format format.
QImageReaderPrivate(QImageReader *qq)
QImageReader::ImageReaderError imageReaderError
enum QImageReaderPrivate::@193 autoTransform
QMap< QString, QString > text
QImageIOHandler * handler
The QImageReader class provides a format independent interface for reading images from files or other...
void setScaledClipRect(const QRect &rect)
Sets the scaled clip rect to rect.
QString errorString() const
Returns a human readable description of the last error that occurred.
~QImageReader()
Destructs the QImageReader object.
bool decideFormatFromContent() const
Returns whether the image reader should decide which plugin to use only based on the contents of the ...
int imageCount() const
For image formats that support animation, this function returns the total number of images in the ani...
void setDevice(QIODevice *device)
Sets QImageReader's device to device.
bool autoTransform() const
bool autoDetectImageFormat() const
Returns true if image format autodetection is enabled on this image reader; otherwise returns false.
static QList< QByteArray > supportedMimeTypes()
Returns the list of MIME types supported by QImageReader.
int quality() const
QSize scaledSize() const
Returns the scaled size of the image.
QString fileName() const
If the currently assigned device is a QFile, or if setFileName() has been called, this function retur...
void setFileName(const QString &fileName)
Sets the file name of QImageReader to fileName.
void setScaledSize(const QSize &size)
Sets the scaled size of the image to size.
ImageReaderError
This enum describes the different types of errors that can occur when reading images with QImageReade...
QImageIOHandler::Transformations transformation() const
QIODevice * device() const
Returns the device currently assigned to QImageReader, or \nullptr if no device has been assigned.
QByteArray subType() const
QColor backgroundColor() const
static void setAllocationLimit(int mbLimit)
QRect currentImageRect() const
For image formats that support animation, this function returns the rect for the current frame.
bool supportsAnimation() const
void setDecideFormatFromContent(bool ignored)
If ignored is set to true, then the image reader will ignore specified formats or file extensions and...
void setAutoTransform(bool enabled)
QString text(const QString &key) const
bool jumpToImage(int imageNumber)
For image formats that support animation, this function skips to the image whose sequence number is i...
QRect clipRect() const
Returns the clip rect (also known as the ROI, or Region Of Interest) of the image.
QImageReader()
Constructs an empty QImageReader object.
bool supportsOption(QImageIOHandler::ImageOption option) const
static int allocationLimit()
QList< QByteArray > supportedSubTypes() const
static QList< QByteArray > imageFormatsForMimeType(const QByteArray &mimeType)
QByteArray format() const
Returns the format QImageReader uses for reading images.
bool canRead() const
Returns true if an image can be read for the device (i.e., the image format is supported,...
static QList< QByteArray > supportedImageFormats()
Returns the list of image formats supported by QImageReader.
void setQuality(int quality)
void setBackgroundColor(const QColor &color)
bool jumpToNextImage()
For image formats that support animation, this function steps over the current image,...
void setFormat(const QByteArray &format)
Sets the format QImageReader will use when reading images, to format.
QSize size() const
Returns the size of the image, without actually reading the image contents.
void setClipRect(const QRect &rect)
Sets the image clip rect (also known as the ROI, or Region Of Interest) to rect.
void setAutoDetectImageFormat(bool enabled)
If enabled is true, image format autodetection is enabled; otherwise, it is disabled.
int currentImageNumber() const
For image formats that support animation, this function returns the sequence number of the current fr...
ImageReaderError error() const
Returns the type of error that occurred last.
QRect scaledClipRect() const
Returns the scaled clip rect of the image.
int nextImageDelay() const
For image formats that support animation, this function returns the number of milliseconds to wait un...
QStringList textKeys() const
int loopCount() const
For image formats that support animation, this function returns the number of times the animation sho...
QImage::Format imageFormat() const
QImage read()
Reads an image from the device.
\inmodule QtGui
Definition qimage.h:37
Format
The following image formats are available in Qt.
Definition qimage.h:41
@ Format_Invalid
Definition qimage.h:42
T value(const Key &key, const T &defaultValue=T()) const
Definition qmap.h:357
void clear()
Definition qmap.h:289
QList< Key > keys() const
Definition qmap.h:383
bool isEmpty() const
Definition qmap.h:269
\inmodule QtCore
Definition qmutex.h:281
bool canRead() const override
Returns true if an image can be read from the device (i.e., the image format is supported,...
bool canRead() const override
Returns true if an image can be read from the device (i.e., the image format is supported,...
\inmodule QtCore\reentrant
Definition qrect.h:30
constexpr bool isValid() const noexcept
Returns true if the rectangle is valid, otherwise returns false.
Definition qrect.h:170
constexpr bool isNull() const noexcept
Returns true if the rectangle is a null rectangle, otherwise returns false.
Definition qrect.h:164
\inmodule QtCore
Definition qsize.h:25
constexpr int height() const noexcept
Returns the height.
Definition qsize.h:133
constexpr int width() const noexcept
Returns the width.
Definition qsize.h:130
constexpr void setWidth(int w) noexcept
Sets the width to the given width.
Definition qsize.h:136
constexpr bool isEmpty() const noexcept
Returns true if either of the width and height is less than or equal to 0; otherwise returns false.
Definition qsize.h:124
constexpr void setHeight(int h) noexcept
Sets the height to the given height.
Definition qsize.h:139
constexpr bool isValid() const noexcept
Returns true if both the width and height is equal to or greater than 0; otherwise returns false.
Definition qsize.h:127
\inmodule QtCore
\macro QT_RESTRICTED_CAST_FROM_ASCII
Definition qstring.h:129
QByteArray toLatin1() const &
Definition qstring.h:630
static QString fromLatin1(QByteArrayView ba)
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition qstring.cpp:5871
bool isEmpty() const noexcept
Returns true if the string has no characters; otherwise returns false.
Definition qstring.h:192
QString right(qsizetype n) const &
Definition qstring.h:375
QString toLower() const &
Definition qstring.h:435
bool canRead() const override
Returns true if an image can be read from the device (i.e., the image format is supported,...
bool canRead() const override
Returns true if an image can be read from the device (i.e., the image format is supported,...
void extension()
[6]
Definition dialogs.cpp:230
#define this
Definition dialogs.cpp:9
rect
[4]
QList< QByteArray > imageFormatsForMimeType(QByteArrayView mimeType, Capability cap)
QSharedPointer< QFactoryLoader > pluginLoader()
QList< QByteArray > supportedImageFormats(Capability cap)
static const _qt_BuiltInFormatStruct _qt_BuiltInFormats[]
QList< QByteArray > supportedMimeTypes(Capability cap)
Combined button and popup list for selecting options.
@ SmoothTransformation
@ IgnoreAspectRatio
Definition image.cpp:4
#define Q_FALLTHROUGH()
typedef QByteArray(EGLAPIENTRYP PFNQGSGETDISPLAYSPROC)()
const char * mimeType
int qRound(qfloat16 d) noexcept
Definition qfloat16.h:327
Q_GUI_EXPORT void qt_imageTransform(QImage &src, QImageIOHandler::Transformations orient)
Definition qimage.cpp:6410
QMap< QString, QString > qt_getImageTextFromDescription(const QString &description)
Definition qimage.cpp:6435
void qt_imageTransform(QImage &src, QImageIOHandler::Transformations orient)
Definition qimage.cpp:6410
static QImageIOHandler * createReadHandlerHelper(QIODevice *device, const QByteArray &format, bool autoDetectImageFormat, bool ignoresFormatAndExtension)
#define qDebug
[1]
Definition qlogging.h:164
#define qWarning
Definition qlogging.h:166
GLuint64 key
GLenum GLuint GLintptr GLsizeiptr size
[1]
GLuint index
[2]
GLenum GLenum GLsizei const GLuint GLboolean enabled
GLenum src
GLuint color
[2]
GLint GLsizei GLsizei GLenum format
GLuint res
GLdouble GLdouble GLdouble GLdouble q
Definition qopenglext.h:259
GLuint64EXT * result
[6]
GLuint GLenum option
#define Q_ASSERT(cond)
Definition qrandom.cpp:47
Q_CORE_EXPORT bool qEnvironmentVariableIsEmpty(const char *varName) noexcept
Q_CORE_EXPORT int qEnvironmentVariableIntValue(const char *varName, bool *ok=nullptr) noexcept
#define Q_TRACE_ENABLED(x)
Definition qtrace_p.h:148
#define Q_TRACE(x,...)
Definition qtrace_p.h:144
#define Q_TRACE_POINT(provider, tracepoint,...)
Definition qtrace_p.h:232
long long qint64
Definition qtypes.h:60
double qreal
Definition qtypes.h:187
#define enabled
QFile file
[0]
QMutex mutex
[2]