From 5698f22afbd0e6be273f31cf8b934383e7b68cdb Mon Sep 17 00:00:00 2001 From: Pier Luigi Fiorini Date: Sun, 6 Jan 2019 19:21:20 +0100 Subject: Set size hints for xdg-shell and xdg-shell-v6 Send minimum and maximum size hints to compositors. [ChangeLog][QPA plugin] Implement minimum and maximum size in the xdg-shell and xdg-shell-v6 shell integrations. Change-Id: I631c3348c8333d7a246b21228a92c436f5adb5dc Reviewed-by: Johan Helsing --- src/client/qwaylandshellsurface_p.h | 2 ++ src/client/qwaylandwindow.cpp | 11 ++++++++ src/client/qwaylandwindow_p.h | 4 ++- .../xdg-shell-v6/qwaylandxdgshellv6.cpp | 30 ++++++++++++++++++++++ .../xdg-shell-v6/qwaylandxdgshellv6_p.h | 3 +++ .../xdg-shell/qwaylandxdgshell.cpp | 30 ++++++++++++++++++++++ .../xdg-shell/qwaylandxdgshell_p.h | 3 +++ 7 files changed, 82 insertions(+), 1 deletion(-) diff --git a/src/client/qwaylandshellsurface_p.h b/src/client/qwaylandshellsurface_p.h index d33a98a1e..804056e54 100644 --- a/src/client/qwaylandshellsurface_p.h +++ b/src/client/qwaylandshellsurface_p.h @@ -97,6 +97,8 @@ public: virtual void requestWindowStates(Qt::WindowStates states) {Q_UNUSED(states);} virtual bool wantsDecorations() const { return false; } + virtual void propagateSizeHints() {} + private: QWaylandWindow *m_window = nullptr; friend class QWaylandWindow; diff --git a/src/client/qwaylandwindow.cpp b/src/client/qwaylandwindow.cpp index 17576ecee..e8ff081c8 100644 --- a/src/client/qwaylandwindow.cpp +++ b/src/client/qwaylandwindow.cpp @@ -605,6 +605,11 @@ void QWaylandWindow::commit(QWaylandBuffer *buffer, const QRegion &damage) wl_surface::commit(); } +void QWaylandWindow::commit() +{ + wl_surface::commit(); +} + const wl_callback_listener QWaylandWindow::callbackListener = { QWaylandWindow::frameCallback }; @@ -1118,6 +1123,12 @@ void QWaylandWindow::addAttachOffset(const QPoint point) mOffset += point; } +void QWaylandWindow::propagateSizeHints() +{ + if (mShellSurface) + mShellSurface->propagateSizeHints(); +} + bool QtWaylandClient::QWaylandWindow::startSystemMove(const QPoint &pos) { Q_UNUSED(pos); diff --git a/src/client/qwaylandwindow_p.h b/src/client/qwaylandwindow_p.h index e5838d231..52cbc3e59 100644 --- a/src/client/qwaylandwindow_p.h +++ b/src/client/qwaylandwindow_p.h @@ -120,6 +120,8 @@ public: void handleExpose(const QRegion ®ion); void commit(QWaylandBuffer *buffer, const QRegion &damage); + void commit(); + void waitForFrameSync(); QMargins frameMargins() const override; @@ -186,7 +188,7 @@ public: QWaylandShmBackingStore *backingStore() const { return mBackingStore; } bool setKeyboardGrabEnabled(bool) override { return false; } - void propagateSizeHints() override { } + void propagateSizeHints() override; void addAttachOffset(const QPoint point); bool startSystemMove(const QPoint &pos) override; diff --git a/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6.cpp b/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6.cpp index 01122769e..6652c8768 100644 --- a/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6.cpp +++ b/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6.cpp @@ -46,6 +46,8 @@ #include #include +#include + QT_BEGIN_NAMESPACE namespace QtWaylandClient { @@ -94,6 +96,9 @@ void QWaylandXdgSurfaceV6::Toplevel::applyConfigure() QSize windowGeometrySize = m_xdgSurface->m_window->window()->frameGeometry().size(); m_xdgSurface->set_window_geometry(0, 0, windowGeometrySize.width(), windowGeometrySize.height()); + + m_xdgSurface->setSizeHints(); + m_applied = m_pending; qCDebug(lcQpaWayland) << "Applied pending zxdg_toplevel_v6 configure event:" << m_applied.size << m_applied.states; } @@ -305,6 +310,31 @@ bool QWaylandXdgSurfaceV6::wantsDecorations() const return m_toplevel && !(m_toplevel->m_pending.states & Qt::WindowFullScreen); } +void QWaylandXdgSurfaceV6::propagateSizeHints() +{ + setSizeHints(); + + if (m_toplevel && m_window) + m_window->commit(); +} + +void QWaylandXdgSurfaceV6::setSizeHints() +{ + if (m_toplevel && m_window) { + const int minWidth = qMax(0, m_window->windowMinimumSize().width()); + const int minHeight = qMax(0, m_window->windowMinimumSize().height()); + m_toplevel->set_min_size(minWidth, minHeight); + + int maxWidth = qMax(0, m_window->windowMaximumSize().width()); + if (maxWidth == QWINDOWSIZE_MAX) + maxWidth = 0; + int maxHeight = qMax(0, m_window->windowMaximumSize().height()); + if (maxHeight == QWINDOWSIZE_MAX) + maxHeight = 0; + m_toplevel->set_max_size(maxWidth, maxHeight); + } +} + void QWaylandXdgSurfaceV6::requestWindowStates(Qt::WindowStates states) { if (m_toplevel) diff --git a/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6_p.h b/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6_p.h index e688f751a..62c13157e 100644 --- a/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6_p.h +++ b/src/plugins/shellintegration/xdg-shell-v6/qwaylandxdgshellv6_p.h @@ -88,6 +88,9 @@ public: bool handlesActiveState() const { return m_toplevel; } void applyConfigure() override; bool wantsDecorations() const override; + void propagateSizeHints() override; + + void setSizeHints(); protected: void requestWindowStates(Qt::WindowStates states) override; diff --git a/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell.cpp b/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell.cpp index cabba5b3b..fc515ca1b 100644 --- a/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell.cpp +++ b/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell.cpp @@ -46,6 +46,8 @@ #include #include +#include + QT_BEGIN_NAMESPACE namespace QtWaylandClient { @@ -104,6 +106,9 @@ void QWaylandXdgSurface::Toplevel::applyConfigure() QSize windowGeometrySize = m_xdgSurface->m_window->window()->frameGeometry().size(); m_xdgSurface->set_window_geometry(0, 0, windowGeometrySize.width(), windowGeometrySize.height()); + + m_xdgSurface->setSizeHints(); + m_applied = m_pending; qCDebug(lcQpaWayland) << "Applied pending xdg_toplevel configure event:" << m_applied.size << m_applied.states; } @@ -339,6 +344,31 @@ bool QWaylandXdgSurface::wantsDecorations() const return m_toplevel && m_toplevel->wantsDecorations(); } +void QWaylandXdgSurface::propagateSizeHints() +{ + setSizeHints(); + + if (m_toplevel && m_window) + m_window->commit(); +} + +void QWaylandXdgSurface::setSizeHints() +{ + if (m_toplevel && m_window) { + const int minWidth = qMax(0, m_window->windowMinimumSize().width()); + const int minHeight = qMax(0, m_window->windowMinimumSize().height()); + m_toplevel->set_min_size(minWidth, minHeight); + + int maxWidth = qMax(0, m_window->windowMaximumSize().width()); + if (maxWidth == QWINDOWSIZE_MAX) + maxWidth = 0; + int maxHeight = qMax(0, m_window->windowMaximumSize().height()); + if (maxHeight == QWINDOWSIZE_MAX) + maxHeight = 0; + m_toplevel->set_max_size(maxWidth, maxHeight); + } +} + void QWaylandXdgSurface::requestWindowStates(Qt::WindowStates states) { if (m_toplevel) diff --git a/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell_p.h b/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell_p.h index 416feee2c..c39ccde3b 100644 --- a/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell_p.h +++ b/src/plugins/shellintegration/xdg-shell/qwaylandxdgshell_p.h @@ -92,6 +92,9 @@ public: bool handlesActiveState() const { return m_toplevel; } void applyConfigure() override; bool wantsDecorations() const override; + void propagateSizeHints() override; + + void setSizeHints(); protected: void requestWindowStates(Qt::WindowStates states) override; -- cgit v1.2.3