diff options
author | Lars Knoll <lars.knoll@qt.io> | 2020-03-04 09:54:35 +0100 |
---|---|---|
committer | Shawn Rutledge <shawn.rutledge@qt.io> | 2020-03-04 14:39:18 +0000 |
commit | 2a4b95778993b00499eb94f61a87330fdbadf947 (patch) | |
tree | 168147adcc2854cb6723335b5abffe9d7585c7f4 /src/plugins/platforms | |
parent | b4e17a48646a1d2156b7d56ab6003db46af79cec (diff) | |
parent | 048f0a00fa7b46f531fbe3ed6d1babae9858e8c2 (diff) |
Merge remote-tracking branch 'origin/5.15' into dev
Change-Id: I99ee6f8b4bdc372437ee60d1feab931487fe55c4
Diffstat (limited to 'src/plugins/platforms')
10 files changed, 80 insertions, 62 deletions
diff --git a/src/plugins/platforms/android/qandroidassetsfileenginehandler.cpp b/src/plugins/platforms/android/qandroidassetsfileenginehandler.cpp index ca16efe34f..07776a4a76 100644 --- a/src/plugins/platforms/android/qandroidassetsfileenginehandler.cpp +++ b/src/plugins/platforms/android/qandroidassetsfileenginehandler.cpp @@ -202,9 +202,7 @@ public: const QString &path) : QAbstractFileEngineIterator(filters, nameFilters) { - m_stack.push_back(FolderIterator::fromCache(cleanedAssetPath(path), true)); - if (m_stack.last()->empty()) - m_stack.pop_back(); + m_currentIterator = FolderIterator::fromCache(cleanedAssetPath(path), true); } QFileInfo currentFileInfo() const override @@ -228,36 +226,23 @@ public: bool hasNext() const override { - if (m_stack.empty()) + if (!m_currentIterator) return false; - if (!m_stack.last()->hasNext()) { - m_stack.pop_back(); - return hasNext(); - } - return true; + return m_currentIterator->hasNext(); } QString next() override { - if (m_stack.empty()) { - m_currentIterator.reset(); + if (!m_currentIterator) return {}; - } - m_currentIterator = m_stack.last(); auto res = m_currentIterator->next(); if (!res) return {}; - if (res->second.type == AssetItem::Type::Folder) { - m_stack.push_back(FolderIterator::fromCache(cleanedAssetPath(currentFilePath()), true)); - if (m_stack.last()->empty()) - m_stack.pop_back(); - } return res->first; } private: - mutable QSharedPointer<FolderIterator> m_currentIterator; - mutable QVector<QSharedPointer<FolderIterator>> m_stack; + QSharedPointer<FolderIterator> m_currentIterator; }; class AndroidAbstractFileEngine: public QAbstractFileEngine diff --git a/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm b/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm index 6aa21d78d1..8b76e45616 100644 --- a/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm +++ b/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm @@ -419,8 +419,7 @@ static QString strippedText(QString s) [mPopUpButton setHidden:chooseDirsOnly]; // TODO hide the whole sunken pane instead? if (mOptions->acceptMode() == QFileDialogOptions::AcceptSave) { - const QStringList ext = [self acceptableExtensionsForSave]; - [mSavePanel setAllowedFileTypes:ext.isEmpty() ? nil : qt_mac_QStringListToNSMutableArray(ext)]; + [self recomputeAcceptableExtensionsForSave]; } else { [mOpenPanel setAllowedFileTypes:nil]; // delegate panel:shouldEnableURL: does the file filtering for NSOpenPanel } @@ -457,25 +456,49 @@ static QString strippedText(QString s) } /* - Returns a list of extensions (e.g. "png", "jpg", "gif") - for the current name filter. If a filter do not conform - to the format *.xyz or * or *.*, an empty list - is returned meaning accept everything. + Computes a list of extensions (e.g. "png", "jpg", "gif") + for the current name filter, and updates the save panel. + + If a filter do not conform to the format *.xyz or * or *.*, + all files types are allowed. + + Extensions with more than one part (e.g. "tar.gz") are + reduced to their final part, as NSSavePanel does not deal + well with multi-part extensions. */ -- (QStringList)acceptableExtensionsForSave -{ - QStringList result; - for (int i=0; i<mSelectedNameFilter->count(); ++i) { - const QString &filter = mSelectedNameFilter->at(i); - if (filter.startsWith(QLatin1String("*.")) - && !filter.contains(QLatin1Char('?')) - && filter.count(QLatin1Char('*')) == 1) { - result += filter.mid(2); - } else { - return QStringList(); // Accept everything - } +- (void)recomputeAcceptableExtensionsForSave +{ + QStringList fileTypes; + for (const QString &filter : *mSelectedNameFilter) { + if (!filter.startsWith(QLatin1String("*."))) + continue; + + if (filter.contains(QLatin1Char('?'))) + continue; + + if (filter.count(QLatin1Char('*')) != 1) + continue; + + auto extensions = filter.split('.', Qt::SkipEmptyParts); + fileTypes += extensions.last(); + + // Explicitly show extensions if we detect a filter + // that has a multi-part extension. This prevents + // confusing situations where the user clicks e.g. + // 'foo.tar.gz' and 'foo.tar' is populated in the + // file name box, but when then clicking save macOS + // will warn that the file needs to end in .gz, + // due to thinking the user tried to save the file + // as a 'tar' file instead. Unfortunately this + // property can only be set before the panel is + // shown, so it will not have any effect when + // swithcing filters in an already opened dialog. + if (extensions.size() > 2) + mSavePanel.extensionHidden = NO; } - return result; + + mSavePanel.allowedFileTypes = fileTypes.isEmpty() ? nil + : qt_mac_QStringListToNSMutableArray(fileTypes); } - (QString)removeExtensions:(const QString &)filter diff --git a/src/plugins/platforms/cocoa/qcocoanativeinterface.mm b/src/plugins/platforms/cocoa/qcocoanativeinterface.mm index d0e69bdca5..450329f569 100644 --- a/src/plugins/platforms/cocoa/qcocoanativeinterface.mm +++ b/src/plugins/platforms/cocoa/qcocoanativeinterface.mm @@ -107,7 +107,7 @@ void *QCocoaNativeInterface::nativeResourceForWindow(const QByteArray &resourceS #if QT_CONFIG(vulkan) } else if (resourceString == "vkSurface") { if (QVulkanInstance *instance = window->vulkanInstance()) - return static_cast<QCocoaVulkanInstance *>(instance->handle())->createSurface(window); + return static_cast<QCocoaVulkanInstance *>(instance->handle())->surface(window); #endif } return nullptr; diff --git a/src/plugins/platforms/cocoa/qcocoavulkaninstance.h b/src/plugins/platforms/cocoa/qcocoavulkaninstance.h index 5fe6a612af..2a8d04757e 100644 --- a/src/plugins/platforms/cocoa/qcocoavulkaninstance.h +++ b/src/plugins/platforms/cocoa/qcocoavulkaninstance.h @@ -61,9 +61,11 @@ public: void createOrAdoptInstance() override; - VkSurfaceKHR *createSurface(QWindow *window); - VkSurfaceKHR createSurface(NSView *view); + VkSurfaceKHR *surface(QWindow *window); + private: + VkSurfaceKHR createSurface(NSView *view); + QVulkanInstance *m_instance = nullptr; QLibrary m_lib; VkSurfaceKHR m_nullSurface = nullptr; diff --git a/src/plugins/platforms/cocoa/qcocoavulkaninstance.mm b/src/plugins/platforms/cocoa/qcocoavulkaninstance.mm index 7ce78ee738..9e714859f2 100644 --- a/src/plugins/platforms/cocoa/qcocoavulkaninstance.mm +++ b/src/plugins/platforms/cocoa/qcocoavulkaninstance.mm @@ -57,12 +57,11 @@ void QCocoaVulkanInstance::createOrAdoptInstance() initInstance(m_instance, QByteArrayList() << QByteArrayLiteral("VK_MVK_macos_surface")); } -VkSurfaceKHR *QCocoaVulkanInstance::createSurface(QWindow *window) +VkSurfaceKHR *QCocoaVulkanInstance::surface(QWindow *window) { QCocoaWindow *cocoaWindow = static_cast<QCocoaWindow *>(window->handle()); - if (cocoaWindow->m_vulkanSurface) - destroySurface(cocoaWindow->m_vulkanSurface); - cocoaWindow->m_vulkanSurface = createSurface(cocoaWindow->m_view); + if (!cocoaWindow->m_vulkanSurface) + cocoaWindow->m_vulkanSurface = createSurface(cocoaWindow->m_view); return &cocoaWindow->m_vulkanSurface; } @@ -81,7 +80,7 @@ VkSurfaceKHR QCocoaVulkanInstance::createSurface(NSView *view) surfaceInfo.sType = VK_STRUCTURE_TYPE_MACOS_SURFACE_CREATE_INFO_MVK; surfaceInfo.pNext = nullptr; surfaceInfo.flags = 0; - surfaceInfo.pView = view; + surfaceInfo.pView = view.layer; VkSurfaceKHR surface = nullptr; VkResult err = m_createSurface(m_vkInst, &surfaceInfo, nullptr, &surface); diff --git a/src/plugins/platforms/cocoa/qpaintengine_mac.mm b/src/plugins/platforms/cocoa/qpaintengine_mac.mm index cadb76d2e4..429c47dc3b 100644 --- a/src/plugins/platforms/cocoa/qpaintengine_mac.mm +++ b/src/plugins/platforms/cocoa/qpaintengine_mac.mm @@ -394,16 +394,19 @@ QCoreGraphicsPaintEngine::begin(QPaintDevice *pdev) d->cosmeticPenSize = 1; d->current.clipEnabled = false; d->pixelSize = QPoint(1,1); - QMacCGContext ctx(pdev); - d->hd = CGContextRetain(ctx); - if (d->hd) { - d->saveGraphicsState(); - d->orig_xform = CGContextGetCTM(d->hd); - if (d->shading) { - CGShadingRelease(d->shading); - d->shading = nullptr; + + if (pdev->devType() != QInternal::Printer) { + QMacCGContext ctx(pdev); + d->hd = CGContextRetain(ctx); + if (d->hd) { + d->saveGraphicsState(); + d->orig_xform = CGContextGetCTM(d->hd); + if (d->shading) { + CGShadingRelease(d->shading); + d->shading = nullptr; + } + d->setClip(nullptr); //clear the context's clipping } - d->setClip(nullptr); //clear the context's clipping } setActive(true); diff --git a/src/plugins/platforms/windows/qwindowsintegration.cpp b/src/plugins/platforms/windows/qwindowsintegration.cpp index 77340387d8..8963f2ad17 100644 --- a/src/plugins/platforms/windows/qwindowsintegration.cpp +++ b/src/plugins/platforms/windows/qwindowsintegration.cpp @@ -343,7 +343,9 @@ QPlatformWindow *QWindowsIntegration::createPlatformWindow(QWindow *window) cons QWindowsWindowData requested; requested.flags = window->flags(); - requested.geometry = QHighDpi::toNativePixels(window->geometry(), window); + requested.geometry = window->isTopLevel() + ? QHighDpi::toNativePixels(window->geometry(), window) + : QHighDpi::toNativeLocalPosition(window->geometry(), window); // Apply custom margins (see QWindowsWindow::setCustomMargins())). const QVariant customMarginsV = window->property("_q_windowsCustomMargins"); if (customMarginsV.isValid()) diff --git a/src/plugins/platforms/windows/qwindowssystemtrayicon.cpp b/src/plugins/platforms/windows/qwindowssystemtrayicon.cpp index 53562c87dd..d6a5b29a71 100644 --- a/src/plugins/platforms/windows/qwindowssystemtrayicon.cpp +++ b/src/plugins/platforms/windows/qwindowssystemtrayicon.cpp @@ -424,8 +424,12 @@ bool QWindowsSystemTrayIcon::winEvent(const MSG &message, long *result) if (screen) { emit contextMenuRequested(globalPos, screen); emit activated(Context); - if (m_menu) + if (m_menu) { + // Set the foreground window to the controlling window so that clicking outside + // of the menu or window will cause the menu to close + SetForegroundWindow(m_hwnd); m_menu->trackPopupMenu(message.hwnd, globalPos.x(), globalPos.y()); + } } } break; diff --git a/src/plugins/platforms/windows/qwindowswindow.cpp b/src/plugins/platforms/windows/qwindowswindow.cpp index e635463951..3dfffa6de6 100644 --- a/src/plugins/platforms/windows/qwindowswindow.cpp +++ b/src/plugins/platforms/windows/qwindowswindow.cpp @@ -1954,10 +1954,8 @@ void QWindowsWindow::checkForScreenChanged(ScreenChangeMode mode) qCDebug(lcQpaWindows).noquote().nospace() << __FUNCTION__ << ' ' << window() << " \"" << (currentScreen ? currentScreen->name() : QString()) << "\"->\"" << newScreen->name() << '"'; - if (mode == FromGeometryChange) - setFlag(SynchronousGeometryChangeEvent); updateFullFrameMargins(); - QWindowSystemInterface::handleWindowScreenChanged(window(), newScreen->screen()); + QWindowSystemInterface::handleWindowScreenChanged<QWindowSystemInterface::SynchronousDelivery>(window(), newScreen->screen()); } void QWindowsWindow::handleGeometryChange() diff --git a/src/plugins/platforms/xcb/qxcbwindow.cpp b/src/plugins/platforms/xcb/qxcbwindow.cpp index 71ec47b053..5be04a984a 100644 --- a/src/plugins/platforms/xcb/qxcbwindow.cpp +++ b/src/plugins/platforms/xcb/qxcbwindow.cpp @@ -274,7 +274,9 @@ void QXcbWindow::create() QXcbScreen *currentScreen = xcbScreen(); QXcbScreen *platformScreen = parent() ? parentScreen() : initialScreen(); - QRect rect = QHighDpi::toNativePixels(window()->geometry(), platformScreen); + QRect rect = parent() + ? QHighDpi::toNativeLocalPosition(window()->geometry(), platformScreen) + : QHighDpi::toNativePixels(window()->geometry(), platformScreen); if (type == Qt::Desktop) { m_window = platformScreen->root(); |