From e097d63195483ad872f9da618ca2df16b03e72ec Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thorbj=C3=B8rn=20Martsum?= Date: Wed, 4 Apr 2018 11:36:31 +0200 Subject: Make svg icons work as pixmap icons This patch makes the svg icon code similar to the code for pixmap icons. We only style the code if we fetch a different mode (+it is not normal) and we try to find icons in same order as the pixmap icons. [ChangeLog][][QIcon/QSvgIconEngine] Made SVG icons behave like pixmap icons: An explicitly-set disabled icon is no longer additionally grayed out. Task-number: QTBUG-67452 Change-Id: I94b4146bae2e9d924a96b602bf23909bd7f0e934 Reviewed-by: Shawn Rutledge Reviewed-by: Morten Kristensen Reviewed-by: Christian Ehrlicher Reviewed-by: Andy Shaw --- .../iconengines/svgiconengine/qsvgiconengine.cpp | 95 ++++++++++++++++------ 1 file changed, 70 insertions(+), 25 deletions(-) (limited to 'src') diff --git a/src/plugins/iconengines/svgiconengine/qsvgiconengine.cpp b/src/plugins/iconengines/svgiconengine/qsvgiconengine.cpp index 0c54e0e..e23dd9a 100644 --- a/src/plugins/iconengines/svgiconengine/qsvgiconengine.cpp +++ b/src/plugins/iconengines/svgiconengine/qsvgiconengine.cpp @@ -74,7 +74,8 @@ public: void stepSerialNum() { serialNum = lastSerialNum.fetchAndAddRelaxed(1); } - void loadDataForModeAndState(QSvgRenderer *renderer, QIcon::Mode mode, QIcon::State state); + bool tryLoad(QSvgRenderer *renderer, QIcon::Mode mode, QIcon::State state); + QIcon::Mode loadDataForModeAndState(QSvgRenderer *renderer, QIcon::Mode mode, QIcon::State state); QHash svgFiles; QHash *svgBuffers; @@ -121,31 +122,73 @@ QSize QSvgIconEngine::actualSize(const QSize &size, QIcon::Mode mode, return pm.size(); } -void QSvgIconEnginePrivate::loadDataForModeAndState(QSvgRenderer *renderer, QIcon::Mode mode, QIcon::State state) +static QByteArray maybeUncompress(const QByteArray &ba) { - QByteArray buf; - const QIcon::State oppositeState = state == QIcon::Off ? QIcon::On : QIcon::Off; - if (svgBuffers) { - buf = svgBuffers->value(hashKey(mode, state)); - if (buf.isEmpty()) - buf = svgBuffers->value(hashKey(QIcon::Normal, state)); - if (buf.isEmpty()) - buf = svgBuffers->value(hashKey(QIcon::Normal, oppositeState)); - } - if (!buf.isEmpty()) { #ifndef QT_NO_COMPRESS - buf = qUncompress(buf); + return qUncompress(ba); +#else + return ba; #endif - renderer->load(buf); +} + +bool QSvgIconEnginePrivate::tryLoad(QSvgRenderer *renderer, QIcon::Mode mode, QIcon::State state) +{ + if (svgBuffers) { + QByteArray buf = svgBuffers->value(hashKey(mode, state)); + if (!buf.isEmpty()) { + buf = maybeUncompress(buf); + renderer->load(buf); + return true; + } + } + QString svgFile = svgFiles.value(hashKey(mode, state)); + if (!svgFile.isEmpty()) { + renderer->load(svgFile); + return true; + } + return false; +} + +QIcon::Mode QSvgIconEnginePrivate::loadDataForModeAndState(QSvgRenderer *renderer, QIcon::Mode mode, QIcon::State state) +{ + if (tryLoad(renderer, mode, state)) + return mode; + + const QIcon::State oppositeState = (state == QIcon::On) ? QIcon::Off : QIcon::On; + if (mode == QIcon::Disabled || mode == QIcon::Selected) { + const QIcon::Mode oppositeMode = (mode == QIcon::Disabled) ? QIcon::Selected : QIcon::Disabled; + if (tryLoad(renderer, QIcon::Normal, state)) + return QIcon::Normal; + if (tryLoad(renderer, QIcon::Active, state)) + return QIcon::Active; + if (tryLoad(renderer, mode, oppositeState)) + return mode; + if (tryLoad(renderer, QIcon::Normal, oppositeState)) + return QIcon::Normal; + if (tryLoad(renderer, QIcon::Active, oppositeState)) + return QIcon::Active; + if (tryLoad(renderer, oppositeMode, state)) + return oppositeMode; + if (tryLoad(renderer, oppositeMode, oppositeState)) + return oppositeMode; } else { - QString svgFile = svgFiles.value(hashKey(mode, state)); - if (svgFile.isEmpty()) - svgFile = svgFiles.value(hashKey(QIcon::Normal, state)); - if (svgFile.isEmpty()) - svgFile = svgFiles.value(hashKey(QIcon::Normal, oppositeState)); - if (!svgFile.isEmpty()) - renderer->load(svgFile); + const QIcon::Mode oppositeMode = (mode == QIcon::Normal) ? QIcon::Active : QIcon::Normal; + if (tryLoad(renderer, oppositeMode, state)) + return oppositeMode; + if (tryLoad(renderer, mode, oppositeState)) + return mode; + if (tryLoad(renderer, oppositeMode, oppositeState)) + return oppositeMode; + if (tryLoad(renderer, QIcon::Disabled, state)) + return QIcon::Disabled; + if (tryLoad(renderer, QIcon::Selected, state)) + return QIcon::Selected; + if (tryLoad(renderer, QIcon::Disabled, oppositeState)) + return QIcon::Disabled; + if (tryLoad(renderer, QIcon::Selected, oppositeState)) + return QIcon::Selected; } + return QIcon::Normal; } QPixmap QSvgIconEngine::pixmap(const QSize &size, QIcon::Mode mode, @@ -164,7 +207,7 @@ QPixmap QSvgIconEngine::pixmap(const QSize &size, QIcon::Mode mode, } QSvgRenderer renderer; - d->loadDataForModeAndState(&renderer, mode, state); + const QIcon::Mode loadmode = d->loadDataForModeAndState(&renderer, mode, state); if (!renderer.isValid()) return pm; @@ -182,9 +225,11 @@ QPixmap QSvgIconEngine::pixmap(const QSize &size, QIcon::Mode mode, p.end(); pm = QPixmap::fromImage(img); if (qobject_cast(QCoreApplication::instance())) { - const QPixmap generated = QGuiApplicationPrivate::instance()->applyQIconStyleHelper(mode, pm); - if (!generated.isNull()) - pm = generated; + if (loadmode != mode && mode != QIcon::Normal) { + const QPixmap generated = QGuiApplicationPrivate::instance()->applyQIconStyleHelper(mode, pm); + if (!generated.isNull()) + pm = generated; + } } if (!pm.isNull()) -- cgit v1.2.1