diff options
Diffstat (limited to 'src/plugins/platforms/windows')
8 files changed, 90 insertions, 37 deletions
diff --git a/src/plugins/platforms/windows/qwindowscontext.cpp b/src/plugins/platforms/windows/qwindowscontext.cpp index fa355f6201..7264fdcbb6 100644 --- a/src/plugins/platforms/windows/qwindowscontext.cpp +++ b/src/plugins/platforms/windows/qwindowscontext.cpp @@ -225,8 +225,10 @@ bool QWindowsUser32DLL::initTouch() QWindowsShell32DLL::QWindowsShell32DLL() : sHCreateItemFromParsingName(0) + , sHGetKnownFolderIDList(0) , sHGetStockIconInfo(0) , sHGetImageList(0) + , sHCreateItemFromIDList(0) { } @@ -234,8 +236,10 @@ void QWindowsShell32DLL::init() { QSystemLibrary library(QStringLiteral("shell32")); sHCreateItemFromParsingName = (SHCreateItemFromParsingName)(library.resolve("SHCreateItemFromParsingName")); + sHGetKnownFolderIDList = (SHGetKnownFolderIDList)(library.resolve("SHGetKnownFolderIDList")); sHGetStockIconInfo = (SHGetStockIconInfo)library.resolve("SHGetStockIconInfo"); sHGetImageList = (SHGetImageList)library.resolve("SHGetImageList"); + sHCreateItemFromIDList = (SHCreateItemFromIDList)library.resolve("SHCreateItemFromIDList"); } QWindowsShcoreDLL::QWindowsShcoreDLL() diff --git a/src/plugins/platforms/windows/qwindowscontext.h b/src/plugins/platforms/windows/qwindowscontext.h index 81f4a36433..d2a3481b28 100644 --- a/src/plugins/platforms/windows/qwindowscontext.h +++ b/src/plugins/platforms/windows/qwindowscontext.h @@ -41,6 +41,10 @@ #include <QtCore/QSharedPointer> #include <QtCore/QLoggingCategory> +#define STRICT_TYPED_ITEMIDS +#include <shlobj.h> +#include <shlwapi.h> + struct IBindCtx; struct _SHSTOCKICONINFO; @@ -120,12 +124,16 @@ struct QWindowsShell32DLL inline void init(); typedef HRESULT (WINAPI *SHCreateItemFromParsingName)(PCWSTR, IBindCtx *, const GUID&, void **); + typedef HRESULT (WINAPI *SHGetKnownFolderIDList)(const GUID &, DWORD, HANDLE, PIDLIST_ABSOLUTE *); typedef HRESULT (WINAPI *SHGetStockIconInfo)(int , int , _SHSTOCKICONINFO *); typedef HRESULT (WINAPI *SHGetImageList)(int, REFIID , void **); + typedef HRESULT (WINAPI *SHCreateItemFromIDList)(PCIDLIST_ABSOLUTE, REFIID, void **); SHCreateItemFromParsingName sHCreateItemFromParsingName; + SHGetKnownFolderIDList sHGetKnownFolderIDList; SHGetStockIconInfo sHGetStockIconInfo; SHGetImageList sHGetImageList; + SHCreateItemFromIDList sHCreateItemFromIDList; }; // Shell scaling library (Windows 8.1 onwards) diff --git a/src/plugins/platforms/windows/qwindowsdialoghelpers.cpp b/src/plugins/platforms/windows/qwindowsdialoghelpers.cpp index 3b47829402..3284795fc1 100644 --- a/src/plugins/platforms/windows/qwindowsdialoghelpers.cpp +++ b/src/plugins/platforms/windows/qwindowsdialoghelpers.cpp @@ -58,16 +58,14 @@ #include <QtCore/QExplicitlySharedDataPointer> #include <QtCore/QMutex> #include <QtCore/QMutexLocker> +#include <QtCore/QUuid> +#include <QtCore/QRegularExpression> #include <QtCore/private/qsystemlibrary_p.h> #include <algorithm> #include "qtwindows_additional.h" -#define STRICT_TYPED_ITEMIDS -#include <shlobj.h> -#include <shlwapi.h> - // #define USE_NATIVE_COLOR_DIALOG /* Testing purposes only */ #ifdef Q_CC_MINGW /* Add missing declarations for MinGW */ @@ -873,8 +871,8 @@ public: virtual void setWindowTitle(const QString &title); inline void setMode(QFileDialogOptions::FileMode mode, QFileDialogOptions::AcceptMode acceptMode, QFileDialogOptions::FileDialogOptions options); - inline void setDirectory(const QString &directory); - inline void updateDirectory() { setDirectory(m_data.directory().toLocalFile()); } + inline void setDirectory(const QUrl &directory); + inline void updateDirectory() { setDirectory(m_data.directory()); } inline QString directory() const; virtual void doExec(HWND owner = 0); virtual void setNameFilters(const QStringList &f); @@ -916,7 +914,7 @@ protected: static QList<QUrl> libraryItemFolders(IShellItem *item); static QString libraryItemDefaultSaveFolder(IShellItem *item); static int itemPaths(IShellItemArray *items, QList<QUrl> *fileResult = 0); - static IShellItem *shellItem(const QString &path); + static IShellItem *shellItem(const QUrl &url); const QWindowsFileDialogSharedData &data() const { return m_data; } QWindowsFileDialogSharedData &data() { return m_data; } @@ -976,25 +974,58 @@ void QWindowsNativeFileDialogBase::setWindowTitle(const QString &title) m_fileDialog->SetTitle(reinterpret_cast<const wchar_t *>(title.utf16())); } -IShellItem *QWindowsNativeFileDialogBase::shellItem(const QString &path) +IShellItem *QWindowsNativeFileDialogBase::shellItem(const QUrl &url) { #ifndef Q_OS_WINCE - if (QWindowsContext::shell32dll.sHCreateItemFromParsingName) { - IShellItem *result = 0; - const QString native = QDir::toNativeSeparators(path); + if (url.isLocalFile()) { + if (!QWindowsContext::shell32dll.sHCreateItemFromParsingName) + return Q_NULLPTR; + IShellItem *result = Q_NULLPTR; + const QString native = QDir::toNativeSeparators(url.toLocalFile()); const HRESULT hr = - QWindowsContext::shell32dll.sHCreateItemFromParsingName(reinterpret_cast<const wchar_t *>(native.utf16()), - NULL, IID_IShellItem, - reinterpret_cast<void **>(&result)); - if (SUCCEEDED(hr)) - return result; + QWindowsContext::shell32dll.sHCreateItemFromParsingName(reinterpret_cast<const wchar_t *>(native.utf16()), + NULL, IID_IShellItem, + reinterpret_cast<void **>(&result)); + if (FAILED(hr)) { + qErrnoWarning("%s: SHCreateItemFromParsingName(%s)) failed", __FUNCTION__, qPrintable(url.toString())); + return Q_NULLPTR; + } + return result; + } else if (url.scheme() == QLatin1String("clsid")) { + if (!QWindowsContext::shell32dll.sHGetKnownFolderIDList || !QWindowsContext::shell32dll.sHCreateItemFromIDList) + return Q_NULLPTR; + // Support for virtual folders via GUID + // (see https://msdn.microsoft.com/en-us/library/windows/desktop/dd378457(v=vs.85).aspx) + // specified as "clsid:<GUID>" (without '{', '}'). + IShellItem *result = Q_NULLPTR; + const QUuid uuid(url.path()); + if (uuid.isNull()) { + qWarning() << __FUNCTION__ << ": Invalid CLSID: " << url.path(); + return Q_NULLPTR; + } + PIDLIST_ABSOLUTE idList; + HRESULT hr = QWindowsContext::shell32dll.sHGetKnownFolderIDList(uuid, 0, 0, &idList); + if (FAILED(hr)) { + qErrnoWarning("%s: SHGetKnownFolderIDList(%s)) failed", __FUNCTION__, qPrintable(url.toString())); + return Q_NULLPTR; + } + hr = QWindowsContext::shell32dll.sHCreateItemFromIDList(idList, IID_IShellItem, reinterpret_cast<void **>(&result)); + CoTaskMemFree(idList); + if (FAILED(hr)) { + qErrnoWarning("%s: SHCreateItemFromIDList(%s)) failed", __FUNCTION__, qPrintable(url.toString())); + return Q_NULLPTR; + } + return result; + } else { + qWarning() << __FUNCTION__ << ": Unhandled scheme: " << url.scheme(); } +#else // !Q_OS_WINCE + Q_UNUSED(url) #endif - qErrnoWarning("%s: SHCreateItemFromParsingName(%s)) failed", __FUNCTION__, qPrintable(path)); return 0; } -void QWindowsNativeFileDialogBase::setDirectory(const QString &directory) +void QWindowsNativeFileDialogBase::setDirectory(const QUrl &directory) { if (!directory.isEmpty()) { if (IShellItem *psi = QWindowsNativeFileDialogBase::shellItem(directory)) { @@ -1284,9 +1315,20 @@ void QWindowsNativeFileDialogBase::setLabelText(QFileDialogOptions::DialogLabel } } +static inline bool isClsid(const QString &s) +{ + // detect "374DE290-123F-4565-9164-39C4925E467B". + static const QRegularExpression pattern(QLatin1String("[0-9A-Fa-f]{8}-[0-9A-Fa-f]{4}-[0-9A-Fa-f]{4}-[0-9A-Fa-f]{4}-[0-9A-Fa-f]{8}")); + Q_ASSERT(pattern.isValid()); + return pattern.match(s).hasMatch(); +} + void QWindowsNativeFileDialogBase::selectFile(const QString &fileName) const { - m_fileDialog->SetFileName((wchar_t*)fileName.utf16()); + // Hack to prevent CLSIDs from being set as file name due to + // QFileDialogPrivate::initialSelection() being QString-based. + if (!isClsid(fileName)) + m_fileDialog->SetFileName((wchar_t*)fileName.utf16()); } // Return the index of the selected filter, accounting for QFileDialog diff --git a/src/plugins/platforms/windows/qwindowsinputcontext.cpp b/src/plugins/platforms/windows/qwindowsinputcontext.cpp index 689e06281f..0cce171340 100644 --- a/src/plugins/platforms/windows/qwindowsinputcontext.cpp +++ b/src/plugins/platforms/windows/qwindowsinputcontext.cpp @@ -189,7 +189,7 @@ void QWindowsInputContext::reset() if (!m_compositionContext.hwnd) return; qCDebug(lcQpaInputMethods) << __FUNCTION__; - if (m_compositionContext.isComposing && m_compositionContext.focusObject.isNull()) { + if (m_compositionContext.isComposing && !m_compositionContext.focusObject.isNull()) { QInputMethodEvent event; if (!m_compositionContext.composition.isEmpty()) event.setCommitString(m_compositionContext.composition); diff --git a/src/plugins/platforms/windows/qwindowsmime.cpp b/src/plugins/platforms/windows/qwindowsmime.cpp index 13260edc82..d8ccccdf45 100644 --- a/src/plugins/platforms/windows/qwindowsmime.cpp +++ b/src/plugins/platforms/windows/qwindowsmime.cpp @@ -166,11 +166,6 @@ static bool qt_write_dibv5(QDataStream &s, QImage image) if (s.status() != QDataStream::Ok) return false; - DWORD colorSpace[3] = {0x00ff0000,0x0000ff00,0x000000ff}; - d->write(reinterpret_cast<const char*>(colorSpace), sizeof(colorSpace)); - if (s.status() != QDataStream::Ok) - return false; - if (image.format() != QImage::Format_ARGB32) image = image.convertToFormat(QImage::Format_ARGB32); @@ -255,10 +250,6 @@ static bool qt_read_dibv5(QDataStream &s, QImage &image) } image.setDotsPerMeterX(bi.bV5XPelsPerMeter); image.setDotsPerMeterY(bi.bV5YPelsPerMeter); - // read color table - DWORD colorSpace[3]; - if (d->read((char *)colorSpace, sizeof(colorSpace)) != sizeof(colorSpace)) - return false; red_shift = calc_shift(red_mask); green_shift = calc_shift(green_mask); diff --git a/src/plugins/platforms/windows/qwindowsopengltester.cpp b/src/plugins/platforms/windows/qwindowsopengltester.cpp index 67548a0836..f5065a22b8 100644 --- a/src/plugins/platforms/windows/qwindowsopengltester.cpp +++ b/src/plugins/platforms/windows/qwindowsopengltester.cpp @@ -208,15 +208,22 @@ static inline QString resolveBugListFile(const QString &fileName) return QStandardPaths::locate(QStandardPaths::ConfigLocation, fileName); } +# ifndef QT_NO_OPENGL typedef QHash<QOpenGLConfig::Gpu, QWindowsOpenGLTester::Renderers> SupportedRenderersCache; Q_GLOBAL_STATIC(SupportedRenderersCache, supportedRenderersCache) +# endif #endif // !Q_OS_WINCE QWindowsOpenGLTester::Renderers QWindowsOpenGLTester::detectSupportedRenderers(const GpuDescription &gpu, bool glesOnly) { Q_UNUSED(gpu) -#ifndef Q_OS_WINCE + Q_UNUSED(glesOnly) +#if defined(QT_NO_OPENGL) + return 0; +#elif defined(Q_OS_WINCE) + return QWindowsOpenGLTester::Gles; +#else QOpenGLConfig::Gpu qgpu; qgpu.deviceId = gpu.deviceId; qgpu.vendorId = gpu.vendorId; @@ -265,9 +272,7 @@ QWindowsOpenGLTester::Renderers QWindowsOpenGLTester::detectSupportedRenderers(c srCache->insert(qgpu, result); return result; -#else // !Q_OS_WINCE - return QWindowsOpenGLTester::Gles; -#endif +#endif // !Q_OS_WINCE && !QT_NO_OPENGL } QWindowsOpenGLTester::Renderers QWindowsOpenGLTester::supportedGlesRenderers() @@ -288,7 +293,7 @@ QWindowsOpenGLTester::Renderers QWindowsOpenGLTester::supportedRenderers() bool QWindowsOpenGLTester::testDesktopGL() { -#ifndef Q_OS_WINCE +#if !defined(QT_NO_OPENGL) && !defined(Q_OS_WINCE) HMODULE lib = 0; HWND wnd = 0; HDC dc = 0; @@ -414,9 +419,9 @@ cleanup: // No FreeLibrary. Some implementations, Mesa in particular, deadlock when trying to unload. return result; -#else // !Q_OS_WINCE +#else return false; -#endif +#endif // !QT_NO_OPENGL && !Q_OS_WINCE } QT_END_NAMESPACE diff --git a/src/plugins/platforms/windows/qwindowswindow.cpp b/src/plugins/platforms/windows/qwindowswindow.cpp index fc389ecf15..b1208d9793 100644 --- a/src/plugins/platforms/windows/qwindowswindow.cpp +++ b/src/plugins/platforms/windows/qwindowswindow.cpp @@ -2265,6 +2265,7 @@ void QWindowsWindow::setCustomMargins(const QMargins &newCustomMargins) void *QWindowsWindow::surface(void *nativeConfig, int *err) { #ifdef QT_NO_OPENGL + Q_UNUSED(nativeConfig) return 0; #else if (!m_surface) { @@ -2278,11 +2279,13 @@ void *QWindowsWindow::surface(void *nativeConfig, int *err) void QWindowsWindow::invalidateSurface() { +#ifndef QT_NO_OPENGL if (m_surface) { if (QWindowsStaticOpenGLContext *staticOpenGLContext = QWindowsIntegration::staticOpenGLContext()) staticOpenGLContext->destroyWindowSurface(m_surface); m_surface = 0; } +#endif // QT_NO_OPENGL } void QWindowsWindow::setTouchWindowTouchTypeStatic(QWindow *window, QWindowsWindowFunctions::TouchWindowTouchTypes touchTypes) diff --git a/src/plugins/platforms/windows/windows.pri b/src/plugins/platforms/windows/windows.pri index e3880a2646..a0460630a7 100644 --- a/src/plugins/platforms/windows/windows.pri +++ b/src/plugins/platforms/windows/windows.pri @@ -122,7 +122,7 @@ contains(QT_CONFIG,dynamicgl) { contains(QT_CONFIG, freetype) { DEFINES *= QT_NO_FONTCONFIG - include($$QT_SOURCE_TREE/src/3rdparty/freetype.pri) + include($$QT_SOURCE_TREE/src/3rdparty/freetype_dependency.pri) HEADERS += \ $$PWD/qwindowsfontdatabase_ft.h SOURCES += \ |