summaryrefslogtreecommitdiffstats
path: root/src/widgets/kernel/qapplication.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/widgets/kernel/qapplication.cpp')
-rw-r--r--src/widgets/kernel/qapplication.cpp86
1 files changed, 28 insertions, 58 deletions
diff --git a/src/widgets/kernel/qapplication.cpp b/src/widgets/kernel/qapplication.cpp
index de7d93ce20..bf6b41cbcd 100644
--- a/src/widgets/kernel/qapplication.cpp
+++ b/src/widgets/kernel/qapplication.cpp
@@ -98,6 +98,8 @@ static void initResources()
QT_BEGIN_NAMESPACE
+Q_LOGGING_CATEGORY(lcWidgetPopup, "qt.widgets.popup");
+
using namespace Qt::StringLiterals;
Q_TRACE_PREFIX(qtwidgets,
@@ -352,8 +354,6 @@ Q_GLOBAL_STATIC(FontHash, app_fonts)
// Exported accessor for use outside of this file
FontHash *qt_app_fonts_hash() { return app_fonts(); }
-QWidgetList *QApplicationPrivate::popupWidgets = nullptr; // has keyboard input focus
-
QWidget *qt_desktopWidget = nullptr; // root window widgets
/*!
@@ -627,8 +627,8 @@ void QApplicationPrivate::initializeWidgetFontHash()
QWidget *QApplication::activePopupWidget()
{
- return QApplicationPrivate::popupWidgets && !QApplicationPrivate::popupWidgets->isEmpty() ?
- QApplicationPrivate::popupWidgets->constLast() : nullptr;
+ auto *win = qobject_cast<QWidgetWindow *>(QGuiApplicationPrivate::activePopupWindow());
+ return win ? win->widget() : nullptr;
}
@@ -1094,6 +1094,12 @@ QPalette QApplicationPrivate::basePalette() const
if (const QPalette *themePalette = platformTheme() ? platformTheme()->palette() : nullptr)
palette = themePalette->resolve(palette);
+ // This palette now is Qt-generated, so reset the resolve mask. This allows
+ // QStyle::polish implementations to respect palettes that are user provided,
+ // by checking if the palette has a brush set for a color that the style might
+ // otherwise overwrite.
+ palette.setResolveMask(0);
+
// Finish off by letting the application style polish the palette. This will
// not result in the polished palette becoming a user-set palette, as the
// resulting base palette is only used as a fallback, with the resolve mask
@@ -1869,7 +1875,7 @@ void QApplicationPrivate::setActiveWindow(QWidget* act)
QApplication::sendSpontaneousEvent(w, &activationChange);
}
- if (QApplicationPrivate::popupWidgets == nullptr) { // !inPopupMode()
+ if (!inPopupMode()) {
// then focus events
if (!QApplicationPrivate::active_window && QApplicationPrivate::focus_widget) {
QApplicationPrivate::setFocusWidget(nullptr, Qt::ActiveWindowFocusReason);
@@ -3293,11 +3299,12 @@ bool QApplicationPrivate::notify_helper(QObject *receiver, QEvent * e)
bool QApplicationPrivate::inPopupMode()
{
- return QApplicationPrivate::popupWidgets != nullptr;
+ return QGuiApplicationPrivate::activePopupWindow() != nullptr;
}
static void ungrabKeyboardForPopup(QWidget *popup)
{
+ qCDebug(lcWidgetPopup) << "ungrab keyboard for" << popup;
if (QWidget::keyboardGrabber())
qt_widget_private(QWidget::keyboardGrabber())->stealKeyboardGrab(true);
else
@@ -3306,6 +3313,7 @@ static void ungrabKeyboardForPopup(QWidget *popup)
static void ungrabMouseForPopup(QWidget *popup)
{
+ qCDebug(lcWidgetPopup) << "ungrab mouse for" << popup;
if (QWidget::mouseGrabber())
qt_widget_private(QWidget::mouseGrabber())->stealMouseGrab(true);
else
@@ -3325,54 +3333,23 @@ static void grabForPopup(QWidget *popup)
ungrabKeyboardForPopup(popup);
}
}
-}
-
-extern QWidget *qt_popup_down;
-extern bool qt_replay_popup_mouse_event;
-extern bool qt_popup_down_closed;
-
-bool QApplicationPrivate::closeAllPopups()
-{
- // Close all popups: In case some popup refuses to close,
- // we give up after 1024 attempts (to avoid an infinite loop).
- int maxiter = 1024;
- QWidget *popup;
- while ((popup = QApplication::activePopupWidget()) && maxiter--)
- popup->close(); // this will call QApplicationPrivate::closePopup
- return true;
+ qCDebug(lcWidgetPopup) << "grabbed mouse and keyboard?" << popupGrabOk << "for popup" << popup;
}
void QApplicationPrivate::closePopup(QWidget *popup)
{
- if (!popupWidgets)
+ QWindow *win = popup->windowHandle();
+ if (!win)
+ return;
+ if (!QGuiApplicationPrivate::closePopup(win))
return;
- popupWidgets->removeAll(popup);
-
- if (popup == qt_popup_down) {
- qt_button_down = nullptr;
- qt_popup_down_closed = true;
- qt_popup_down = nullptr;
- }
- if (QApplicationPrivate::popupWidgets->size() == 0) { // this was the last popup
- delete QApplicationPrivate::popupWidgets;
- QApplicationPrivate::popupWidgets = nullptr;
- qt_popup_down_closed = false;
+ const QWindow *nextRemainingPopup = QGuiApplicationPrivate::activePopupWindow();
+ if (!nextRemainingPopup) { // this was the last popup
if (popupGrabOk) {
popupGrabOk = false;
- // TODO on multi-seat window systems, we have to know which mouse
- auto devPriv = QPointingDevicePrivate::get(QPointingDevice::primaryPointingDevice());
- auto mousePressPos = devPriv->pointById(0)->eventPoint.globalPressPosition();
- if (popup->geometry().contains(mousePressPos.toPoint())
- || popup->testAttribute(Qt::WA_NoMouseReplay)) {
- // mouse release event or inside
- qt_replay_popup_mouse_event = false;
- } else { // mouse press event
- qt_replay_popup_mouse_event = true;
- }
-
// transfer grab back to mouse grabber if any, otherwise release the grab
ungrabMouseForPopup(popup);
@@ -3391,30 +3368,23 @@ void QApplicationPrivate::closePopup(QWidget *popup)
}
}
- } else {
+ } else if (const auto *popupWin = qobject_cast<const QWidgetWindow *>(nextRemainingPopup)) {
// A popup was closed, so the previous popup gets the focus.
- QWidget* aw = QApplicationPrivate::popupWidgets->constLast();
- if (QWidget *fw = aw->focusWidget())
+ if (QWidget *fw = popupWin->widget()->focusWidget())
fw->setFocus(Qt::PopupFocusReason);
// can become nullptr due to setFocus() above
- if (QApplicationPrivate::popupWidgets &&
- QApplicationPrivate::popupWidgets->size() == 1) // grab mouse/keyboard
- grabForPopup(aw);
+ if (QGuiApplicationPrivate::popupCount() == 1) // grab mouse/keyboard
+ grabForPopup(popupWin->widget());
}
}
-int openPopupCount = 0;
-
void QApplicationPrivate::openPopup(QWidget *popup)
{
- openPopupCount++;
- if (!popupWidgets) // create list
- popupWidgets = new QWidgetList;
- popupWidgets->append(popup); // add to end of list
+ QGuiApplicationPrivate::activatePopup(popup->windowHandle());
- if (QApplicationPrivate::popupWidgets->size() == 1) // grab mouse/keyboard
+ if (QGuiApplicationPrivate::popupCount() == 1) // grab mouse/keyboard
grabForPopup(popup);
// popups are not focus-handled by the window system (the first
@@ -3422,7 +3392,7 @@ void QApplicationPrivate::openPopup(QWidget *popup)
// new popup gets the focus
if (popup->focusWidget()) {
popup->focusWidget()->setFocus(Qt::PopupFocusReason);
- } else if (popupWidgets->size() == 1) { // this was the first popup
+ } else if (QGuiApplicationPrivate::popupCount() == 1) { // this was the first popup
if (QWidget *fw = QApplication::focusWidget()) {
QFocusEvent e(QEvent::FocusOut, Qt::PopupFocusReason);
QCoreApplication::sendEvent(fw, &e);