diff options
Diffstat (limited to 'src/plugins/platforms/xcb/qxcbintegration.cpp')
-rw-r--r-- | src/plugins/platforms/xcb/qxcbintegration.cpp | 97 |
1 files changed, 76 insertions, 21 deletions
diff --git a/src/plugins/platforms/xcb/qxcbintegration.cpp b/src/plugins/platforms/xcb/qxcbintegration.cpp index 893b11c8c3..4dafae31e3 100644 --- a/src/plugins/platforms/xcb/qxcbintegration.cpp +++ b/src/plugins/platforms/xcb/qxcbintegration.cpp @@ -20,6 +20,7 @@ #ifndef QT_NO_SESSIONMANAGER #include "qxcbsessionmanager.h" #endif +#include "qxcbxsettings.h" #include <xcb/xcb.h> @@ -48,9 +49,9 @@ #include <QtGui/QOpenGLContext> #include <QtGui/QScreen> #include <QtGui/QOffscreenSurface> -#ifndef QT_NO_ACCESSIBILITY +#if QT_CONFIG(accessibility) #include <qpa/qplatformaccessibility.h> -#ifndef QT_NO_ACCESSIBILITY_ATSPI_BRIDGE +#if QT_CONFIG(accessibility_atspi_bridge) #include <QtGui/private/qspiaccessiblebridge_p.h> #endif #endif @@ -92,10 +93,17 @@ static bool runningUnderDebugger() #endif } +class QXcbUnixServices : public QGenericUnixServices +{ +public: + QString portalWindowIdentifier(QWindow *window) override; +}; + + QXcbIntegration *QXcbIntegration::m_instance = nullptr; QXcbIntegration::QXcbIntegration(const QStringList ¶meters, int &argc, char **argv) - : m_services(new QGenericUnixServices) + : m_services(new QXcbUnixServices) , m_instanceName(nullptr) , m_canGrab(true) , m_defaultVisualId(UINT_MAX) @@ -196,7 +204,7 @@ QPlatformPixmap *QXcbIntegration::createPlatformPixmap(QPlatformPixmap::PixelTyp QPlatformWindow *QXcbIntegration::createPlatformWindow(QWindow *window) const { QXcbGlIntegration *glIntegration = nullptr; - const bool isTrayIconWindow = QXcbWindow::isTrayIconWindow(window);; + const bool isTrayIconWindow = QXcbWindow::isTrayIconWindow(window); if (window->type() != Qt::Desktop && !isTrayIconWindow) { if (window->supportsOpenGL()) { glIntegration = connection()->glIntegration(); @@ -324,19 +332,38 @@ QAbstractEventDispatcher *QXcbIntegration::createEventDispatcher() const return QXcbEventDispatcher::createEventDispatcher(connection()); } +using namespace Qt::Literals::StringLiterals; +static const auto xsNetCursorBlink = "Net/CursorBlink"_ba; +static const auto xsNetCursorBlinkTime = "Net/CursorBlinkTime"_ba; +static const auto xsNetDoubleClickTime = "Net/DoubleClickTime"_ba; +static const auto xsNetDoubleClickDistance = "Net/DoubleClickDistance"_ba; +static const auto xsNetDndDragThreshold = "Net/DndDragThreshold"_ba; + void QXcbIntegration::initialize() { const auto defaultInputContext = "compose"_L1; // Perform everything that may potentially need the event dispatcher (timers, socket // notifiers) here instead of the constructor. - QString icStr = QPlatformInputContextFactory::requested(); - if (icStr.isNull()) - icStr = defaultInputContext; - m_inputContext.reset(QPlatformInputContextFactory::create(icStr)); - if (!m_inputContext && icStr != defaultInputContext && icStr != "none"_L1) + auto icStrs = QPlatformInputContextFactory::requested(); + if (icStrs.isEmpty()) + icStrs = { defaultInputContext }; + m_inputContext.reset(QPlatformInputContextFactory::create(icStrs)); + if (!m_inputContext && !icStrs.contains(defaultInputContext) + && icStrs != QStringList{"none"_L1}) m_inputContext.reset(QPlatformInputContextFactory::create(defaultInputContext)); connection()->keyboard()->initialize(); + + auto notifyThemeChanged = [](QXcbVirtualDesktop *, const QByteArray &, const QVariant &, void *) { + QWindowSystemInterface::handleThemeChange(); + }; + + auto *xsettings = connection()->primaryScreen()->xSettings(); + xsettings->registerCallbackForProperty(xsNetCursorBlink, notifyThemeChanged, this); + xsettings->registerCallbackForProperty(xsNetCursorBlinkTime, notifyThemeChanged, this); + xsettings->registerCallbackForProperty(xsNetDoubleClickTime, notifyThemeChanged, this); + xsettings->registerCallbackForProperty(xsNetDoubleClickDistance, notifyThemeChanged, this); + xsettings->registerCallbackForProperty(xsNetDndDragThreshold, notifyThemeChanged, this); } void QXcbIntegration::moveToScreen(QWindow *window, int screen) @@ -383,7 +410,7 @@ QPlatformInputContext *QXcbIntegration::inputContext() const return m_inputContext.data(); } -#ifndef QT_NO_ACCESSIBILITY +#if QT_CONFIG(accessibility) QPlatformAccessibility *QXcbIntegration::accessibility() const { #if !defined(QT_NO_ACCESSIBILITY_ATSPI_BRIDGE) @@ -403,14 +430,9 @@ QPlatformServices *QXcbIntegration::services() const return m_services.data(); } -Qt::KeyboardModifiers QXcbIntegration::queryKeyboardModifiers() const +QPlatformKeyMapper *QXcbIntegration::keyMapper() const { - return m_connection->queryKeyboardModifiers(); -} - -QList<int> QXcbIntegration::possibleKeys(const QKeyEvent *e) const -{ - return m_connection->keyboard()->possibleKeys(e); + return m_connection->keyboard(); } QStringList QXcbIntegration::themeNames() const @@ -423,31 +445,53 @@ QPlatformTheme *QXcbIntegration::createPlatformTheme(const QString &name) const return QGenericUnixTheme::createUnixTheme(name); } +#define RETURN_VALID_XSETTINGS(key) { \ + auto value = connection()->primaryScreen()->xSettings()->setting(key); \ + if (value.isValid()) return value; \ +} + QVariant QXcbIntegration::styleHint(QPlatformIntegration::StyleHint hint) const { switch (hint) { - case QPlatformIntegration::CursorFlashTime: - case QPlatformIntegration::KeyboardInputInterval: + case QPlatformIntegration::CursorFlashTime: { + bool ok = false; + // If cursor blinking is off, returns 0 to keep the cursor awlays display. + if (connection()->primaryScreen()->xSettings()->setting(xsNetCursorBlink).toInt(&ok) == 0 && ok) + return 0; + + RETURN_VALID_XSETTINGS(xsNetCursorBlinkTime); + break; + } case QPlatformIntegration::MouseDoubleClickInterval: + RETURN_VALID_XSETTINGS(xsNetDoubleClickTime); + break; + case QPlatformIntegration::MouseDoubleClickDistance: + RETURN_VALID_XSETTINGS(xsNetDoubleClickDistance); + break; + case QPlatformIntegration::KeyboardInputInterval: case QPlatformIntegration::StartDragTime: case QPlatformIntegration::KeyboardAutoRepeatRate: case QPlatformIntegration::PasswordMaskDelay: case QPlatformIntegration::StartDragVelocity: case QPlatformIntegration::UseRtlExtensions: case QPlatformIntegration::PasswordMaskCharacter: + case QPlatformIntegration::FlickMaximumVelocity: + case QPlatformIntegration::FlickDeceleration: // TODO using various xcb, gnome or KDE settings break; // Not implemented, use defaults + case QPlatformIntegration::FlickStartDistance: case QPlatformIntegration::StartDragDistance: { + RETURN_VALID_XSETTINGS(xsNetDndDragThreshold); // The default (in QPlatformTheme::defaultThemeHint) is 10 pixels, but // on a high-resolution screen it makes sense to increase it. - qreal dpi = 100.0; + qreal dpi = 100; if (const QXcbScreen *screen = connection()->primaryScreen()) { if (screen->logicalDpi().first > dpi) dpi = screen->logicalDpi().first; if (screen->logicalDpi().second > dpi) dpi = screen->logicalDpi().second; } - return 10.0 * dpi / 100.0; + return (hint == QPlatformIntegration::FlickStartDistance ? qreal(15) : qreal(10)) * dpi / qreal(100); } case QPlatformIntegration::ShowIsFullScreen: // X11 always has support for windows, but the @@ -546,4 +590,15 @@ QPlatformVulkanInstance *QXcbIntegration::createPlatformVulkanInstance(QVulkanIn } #endif +void QXcbIntegration::setApplicationBadge(qint64 number) +{ + auto unixServices = dynamic_cast<QGenericUnixServices *>(services()); + unixServices->setApplicationBadge(number); +} + +QString QXcbUnixServices::portalWindowIdentifier(QWindow *window) +{ + return "x11:"_L1 + QString::number(window->winId(), 16); +} + QT_END_NAMESPACE |