QWindowsTheme: Fix the available file icon sizes

Previously, QWindowsTheme had a hardcoded list of of available file icon sizes.
As the sizes depend on the Windows display scale factor, this can lead to
undesired scaling of icons.

Maintain an array of the standard sizes against which the sizes are
matched; refresh in display change.

Task-number: QTBUG-54561
Change-Id: If36de2f30c8a230cc7bd8eeb4dfc9f201aeda5e4
Reviewed-by: Oliver Wolff <oliver.wolff@qt.io>
This commit is contained in:
Friedemann Kleint 2016-07-14 09:35:50 +02:00
parent 5d8a33a86c
commit 6bb0bc73c8
3 changed files with 45 additions and 12 deletions

View File

@ -41,6 +41,7 @@
#include "qwindowsmime.h"
#include "qwindowsinputcontext.h"
#include "qwindowstabletsupport.h"
#include "qwindowstheme.h"
#include <private/qguiapplication_p.h>
#ifndef QT_NO_ACCESSIBILITY
# include "accessible/qwindowsaccessibility.h"
@ -1007,6 +1008,8 @@ bool QWindowsContext::windowsProc(HWND hwnd, UINT message,
#endif
case QtWindows::DisplayChangedEvent:
return d->m_screenManager.handleDisplayChange(wParam, lParam);
if (QWindowsTheme *t = QWindowsTheme::instance())
t->displayChanged();
case QtWindows::SettingChangedEvent:
return d->m_screenManager.handleScreenChanges();
default:

View File

@ -329,6 +329,7 @@ QWindowsTheme::QWindowsTheme()
std::fill(m_fonts, m_fonts + NFonts, static_cast<QFont *>(0));
std::fill(m_palettes, m_palettes + NPalettes, static_cast<QPalette *>(0));
refresh();
refreshIconPixmapSizes();
}
QWindowsTheme::~QWindowsTheme()
@ -394,16 +395,8 @@ QVariant QWindowsTheme::themeHint(ThemeHint hint) const
return QVariant(int(WindowsKeyboardScheme));
case UiEffects:
return QVariant(uiEffects());
case IconPixmapSizes: {
QList<int> sizes;
sizes << 16 << 32;
#ifdef USE_IIMAGELIST
sizes << 48; // sHIL_EXTRALARGE
if (QSysInfo::WindowsVersion >= QSysInfo::WV_VISTA)
sizes << 256; // SHIL_JUMBO
#endif // USE_IIMAGELIST
return QVariant::fromValue(sizes);
}
case IconPixmapSizes:
return m_fileIconSizes;
case DialogSnapToDefaultButton:
return QVariant(booleanSystemParametersInfo(SPI_GETSNAPTODEFBUTTON, false));
case ContextMenuOnMouseRelease:
@ -473,6 +466,15 @@ void QWindowsTheme::refreshFonts()
#endif // !Q_OS_WINCE
}
enum FileIconSize {
// Standard icons obtainable via shGetFileInfo(), SHGFI_SMALLICON, SHGFI_LARGEICON
SmallFileIcon, LargeFileIcon,
// Larger icons obtainable via SHGetImageList()
ExtraLargeFileIcon,
JumboFileIcon, // Vista onwards
FileIconSizeCount
};
bool QWindowsTheme::usePlatformNativeDialog(DialogType type) const
{
return QWindowsDialogs::useHelper(type);
@ -489,6 +491,27 @@ void QWindowsTheme::windowsThemeChanged(QWindow * window)
QWindowSystemInterface::handleThemeChange(window);
}
static int fileIconSizes[FileIconSizeCount];
void QWindowsTheme::refreshIconPixmapSizes()
{
// Standard sizes: 16, 32, 48, 256
fileIconSizes[SmallFileIcon] = GetSystemMetrics(SM_CXSMICON); // corresponds to SHGFI_SMALLICON);
fileIconSizes[LargeFileIcon] = GetSystemMetrics(SM_CXICON); // corresponds to SHGFI_LARGEICON
fileIconSizes[ExtraLargeFileIcon] =
fileIconSizes[LargeFileIcon] + fileIconSizes[LargeFileIcon] / 2;
fileIconSizes[JumboFileIcon] = 8 * fileIconSizes[LargeFileIcon]; // empirical, has not been observed to work
QList<int> sizes;
sizes << fileIconSizes[SmallFileIcon] << fileIconSizes[LargeFileIcon];
#ifdef USE_IIMAGELIST
sizes << fileIconSizes[ExtraLargeFileIcon]; // sHIL_EXTRALARGE
if (QSysInfo::WindowsVersion >= QSysInfo::WV_VISTA)
sizes << fileIconSizes[JumboFileIcon]; // SHIL_JUMBO
#endif // USE_IIMAGELIST
qCDebug(lcQpaWindows) << __FUNCTION__ << sizes;
m_fileIconSizes = QVariant::fromValue(sizes);
}
// Defined in qpixmap_win.cpp
Q_GUI_EXPORT QPixmap qt_pixmapFromWinHICON(HICON icon);
@ -706,10 +729,12 @@ QPixmap QWindowsTheme::fileIconPixmap(const QFileInfo &fileInfo, const QSizeF &s
QPixmap pixmap;
const QString filePath = QDir::toNativeSeparators(fileInfo.filePath());
const int width = int(size.width());
const int iconSize = width > 16 ? SHGFI_LARGEICON : SHGFI_SMALLICON;
const int iconSize = width > fileIconSizes[SmallFileIcon] ? SHGFI_LARGEICON : SHGFI_SMALLICON;
const int requestedImageListSize =
#ifdef USE_IIMAGELIST
width > 48 ? sHIL_JUMBO : (width > 32 ? sHIL_EXTRALARGE : 0);
width > fileIconSizes[ExtraLargeFileIcon]
? sHIL_JUMBO
: (width > fileIconSizes[LargeFileIcon] ? sHIL_EXTRALARGE : 0);
#else
0;
#endif // !USE_IIMAGELIST

View File

@ -37,6 +37,8 @@
#include "qwindowsthreadpoolrunner.h"
#include <qpa/qplatformtheme.h>
#include <QtCore/QVariant>
QT_BEGIN_NAMESPACE
class QWindow;
@ -62,6 +64,7 @@ public:
QPlatformTheme::IconOptions iconOptions = 0) const Q_DECL_OVERRIDE;
void windowsThemeChanged(QWindow *window);
void displayChanged() { refreshIconPixmapSizes(); }
static const char *name;
@ -71,11 +74,13 @@ private:
void refreshPalettes();
void clearFonts();
void refreshFonts();
void refreshIconPixmapSizes();
static QWindowsTheme *m_instance;
QPalette *m_palettes[NPalettes];
QFont *m_fonts[NFonts];
mutable QWindowsThreadPoolRunner m_threadPoolRunner;
QVariant m_fileIconSizes;
};
QT_END_NAMESPACE