From 518f886b6128331ce47932edd637471d58d0d877 Mon Sep 17 00:00:00 2001 From: Rainer Keller Date: Fri, 17 Apr 2015 10:43:19 +0200 Subject: [PATCH] Revert "Rotate images according to Exif orientation" Due to a behavior change. This reverts commit 9157087334186ff3ef811f2ec234a3bf5d4a4889. This reverts commit 16c32c6dfbca03a46d1a2bb87b6c1c365e6179d5. Task-number: QTBUG-37946 Task-number: QTBUG-45552 Task-number: QTBUG-43563 Change-Id: Idf8df7d8f22465e8f6b51acb68993ac97208b184 Reviewed-by: Konstantin Ritt Reviewed-by: Gunnar Sletta --- src/gui/image/qjpeghandler.cpp | 150 +---------------------------- tests/auto/gui/image/qimage/tst_qimage.cpp | 33 ------- 2 files changed, 1 insertion(+), 182 deletions(-) diff --git a/src/gui/image/qjpeghandler.cpp b/src/gui/image/qjpeghandler.cpp index 9cf9947..14c8b4c 100644 --- a/src/gui/image/qjpeghandler.cpp +++ b/src/gui/image/qjpeghandler.cpp @@ -726,7 +726,7 @@ public: }; QJpegHandlerPrivate(QJpegHandler *qq) - : quality(75), exifOrientation(1), iod_src(0), state(Ready), q(qq) + : quality(75), iod_src(0), state(Ready), q(qq) {} ~QJpegHandlerPrivate() @@ -741,10 +741,8 @@ public: bool readJpegHeader(QIODevice*); bool read(QImage *image); - void applyExifOrientation(QImage *image); int quality; - int exifOrientation; QVariant size; QImage::Format format; QSize scaledSize; @@ -762,97 +760,6 @@ public: QJpegHandler *q; }; -static bool readExifHeader(QDataStream &stream) -{ - char prefix[6]; - if (stream.readRawData(prefix, sizeof(prefix)) != sizeof(prefix)) - return false; - if (prefix[0] != 'E' || prefix[1] != 'x' || prefix[2] != 'i' || prefix[3] != 'f' || prefix[4] != 0 || prefix[5] != 0) - return false; - return true; -} - -/* - * Returns -1 on error - * Returns 0 if no Exif orientation was found - * Returns 1 orientation is horizontal (normal) - * Returns 2 mirror horizontal - * Returns 3 rotate 180 - * Returns 4 mirror vertical - * Returns 5 mirror horizontal and rotate 270 CCW - * Returns 6 rotate 90 CW - * Returns 7 mirror horizontal and rotate 90 CW - * Returns 8 rotate 270 CW - */ -static int getExifOrientation(QByteArray &exifData) -{ - QDataStream stream(&exifData, QIODevice::ReadOnly); - - if (!readExifHeader(stream)) - return -1; - - quint16 val; - quint32 offset; - - // read byte order marker - stream >> val; - if (val == 0x4949) // 'II' == Intel - stream.setByteOrder(QDataStream::LittleEndian); - else if (val == 0x4d4d) // 'MM' == Motorola - stream.setByteOrder(QDataStream::BigEndian); - else - return -1; // unknown byte order - - // read size - stream >> val; - if (val != 0x2a) - return -1; - - stream >> offset; - // we have already used 8 bytes of TIFF header - offset -= 8; - - // read IFD - while (!stream.atEnd()) { - quint16 numEntries; - - // skip offset bytes to get the next IFD - if (stream.skipRawData(offset) != (qint32)offset) - return -1; - - stream >> numEntries; - - for (;numEntries > 0; --numEntries) { - quint16 tag; - quint16 type; - quint32 components; - quint16 value; - quint16 dummy; - - stream >> tag >> type >> components >> value >> dummy; - if (tag == 0x0112) { // Tag Exif.Image.Orientation - if (components !=1) - return -1; - if (type != 3) // we are expecting it to be an unsigned short - return -1; - if (value < 1 || value > 8) // check for valid range - return -1; - - // It is possible to include the orientation multiple times. - // Right now the first value is returned. - return value; - } - } - - // read offset to next IFD - stream >> offset; - if (offset == 0) // this is the last IFD - break; - } - - // No Exif orientation was found - return 0; -} /*! \internal */ @@ -872,7 +779,6 @@ bool QJpegHandlerPrivate::readJpegHeader(QIODevice *device) if (!setjmp(err.setjmp_buffer)) { jpeg_save_markers(&info, JPEG_COM, 0xFFFF); - jpeg_save_markers(&info, JPEG_APP0+1, 0xFFFF); // Exif uses APP1 marker (void) jpeg_read_header(&info, TRUE); @@ -884,8 +790,6 @@ bool QJpegHandlerPrivate::readJpegHeader(QIODevice *device) format = QImage::Format_Invalid; read_jpeg_format(format, &info); - QByteArray exifData; - for (jpeg_saved_marker_ptr marker = info.marker_list; marker != NULL; marker = marker->next) { if (marker->marker == JPEG_COM) { QString key, value; @@ -903,18 +807,9 @@ bool QJpegHandlerPrivate::readJpegHeader(QIODevice *device) description += key + QLatin1String(": ") + value.simplified(); readTexts.append(key); readTexts.append(value); - } else if (marker->marker == JPEG_APP0+1) { - exifData.append((const char*)marker->data, marker->data_length); } } - if (exifData.size()) { - // Exif data present - int orientation = getExifOrientation(exifData); - if (orientation > 0) - exifOrientation = orientation; - } - state = ReadHeader; return true; } @@ -928,48 +823,6 @@ bool QJpegHandlerPrivate::readJpegHeader(QIODevice *device) return true; } -void QJpegHandlerPrivate::applyExifOrientation(QImage *image) -{ - // This is not an optimized implementation, but easiest to maintain - QTransform transform; - - switch (exifOrientation) { - case 1: // normal - break; - case 2: // mirror horizontal - *image = image->mirrored(true, false); - break; - case 3: // rotate 180 - transform.rotate(180); - *image = image->transformed(transform); - break; - case 4: // mirror vertical - *image = image->mirrored(false, true); - break; - case 5: // mirror horizontal and rotate 270 CCW - *image = image->mirrored(true, false); - transform.rotate(270); - *image = image->transformed(transform); - break; - case 6: // rotate 90 CW - transform.rotate(90); - *image = image->transformed(transform); - break; - case 7: // mirror horizontal and rotate 90 CW - *image = image->mirrored(true, false); - transform.rotate(90); - *image = image->transformed(transform); - break; - case 8: // rotate 270 CW - transform.rotate(-90); - *image = image->transformed(transform); - break; - default: - qWarning("This should never happen"); - } - exifOrientation = 1; -} - bool QJpegHandlerPrivate::read(QImage *image) { if(state == Ready) @@ -981,7 +834,6 @@ bool QJpegHandlerPrivate::read(QImage *image) if (success) { for (int i = 0; i < readTexts.size()-1; i+=2) image->setText(readTexts.at(i), readTexts.at(i+1)); - applyExifOrientation(image); state = Ready; return true; diff --git a/tests/auto/gui/image/qimage/tst_qimage.cpp b/tests/auto/gui/image/qimage/tst_qimage.cpp index 309d3a8..33302ed 100644 --- a/tests/auto/gui/image/qimage/tst_qimage.cpp +++ b/tests/auto/gui/image/qimage/tst_qimage.cpp @@ -173,9 +173,6 @@ private slots: void invertPixelsRGB_data(); void invertPixelsRGB(); - void exifOrientation_data(); - void exifOrientation(); - void cleanupFunctions(); private: @@ -2649,36 +2646,6 @@ void tst_QImage::invertPixelsRGB() QCOMPARE(qBlue(pixel) >> 4, (255 - 96) >> 4); } -void tst_QImage::exifOrientation_data() -{ - QTest::addColumn("fileName"); - QTest::newRow("Orientation 1, Intel format") << m_prefix + "jpeg_exif_orientation_value_1.jpg"; - QTest::newRow("Orientation 2, Intel format") << m_prefix + "jpeg_exif_orientation_value_2.jpg"; - QTest::newRow("Orientation 3, Intel format") << m_prefix + "jpeg_exif_orientation_value_3.jpg"; - QTest::newRow("Orientation 4, Intel format") << m_prefix + "jpeg_exif_orientation_value_4.jpg"; - QTest::newRow("Orientation 5, Intel format") << m_prefix + "jpeg_exif_orientation_value_5.jpg"; - QTest::newRow("Orientation 6, Intel format") << m_prefix + "jpeg_exif_orientation_value_6.jpg"; - QTest::newRow("Orientation 6, Motorola format") << m_prefix + "jpeg_exif_orientation_value_6_motorola.jpg"; - QTest::newRow("Orientation 7, Intel format") << m_prefix + "jpeg_exif_orientation_value_7.jpg"; - QTest::newRow("Orientation 8, Intel format") << m_prefix + "jpeg_exif_orientation_value_8.jpg"; -} - -void tst_QImage::exifOrientation() -{ - QFETCH(QString, fileName); - - QImage img; - QRgb px; - - QVERIFY(img.load(fileName)); - - px = img.pixel(0, 0); - QVERIFY(qRed(px) > 250 && qGreen(px) < 5 && qBlue(px) < 5); - - px = img.pixel(img.width() - 1, 0); - QVERIFY(qRed(px) < 5 && qGreen(px) < 5 && qBlue(px) > 250); -} - static void cleanupFunction(void* info) { bool *called = static_cast(info); -- 2.3.6