Commit 7c5cfe4e authored by Jan Blackquill's avatar Jan Blackquill 🌈

Implement XDG Shell v3 on the client side

parent b7ae0904
...@@ -361,6 +361,11 @@ void XdgShellPopup::setWindowGeometry(const QRect &windowGeometry) ...@@ -361,6 +361,11 @@ void XdgShellPopup::setWindowGeometry(const QRect &windowGeometry)
d->setWindowGeometry(windowGeometry); d->setWindowGeometry(windowGeometry);
} }
void XdgShellPopup::reposition(const XdgPositioner &positioner, quint32 token)
{
}
XdgShellPopup::operator xdg_surface*() { XdgShellPopup::operator xdg_surface*() {
return *(d.data()); return *(d.data());
} }
...@@ -416,6 +421,16 @@ XdgPositioner::~XdgPositioner() ...@@ -416,6 +421,16 @@ XdgPositioner::~XdgPositioner()
{ {
} }
void XdgPositioner::setReactive(bool reactive)
{
d->reactive = reactive;
}
bool XdgPositioner::reactive() const
{
return d->reactive;
}
void XdgPositioner::setInitialSize(const QSize& size) void XdgPositioner::setInitialSize(const QSize& size)
{ {
d->initialSize = size; d->initialSize = size;
......
...@@ -122,6 +122,14 @@ public: ...@@ -122,6 +122,14 @@ public:
QPoint anchorOffset() const; QPoint anchorOffset() const;
void setAnchorOffset(const QPoint &offset); void setAnchorOffset(const QPoint &offset);
/**
* Whether this positioner is a reactive positioner.
* This causes the surface this positioner is used for to reconstrain
* when the elements for constraining change.
*/
bool reactive() const;
void setReactive(bool reactive);
private: private:
class Private; class Private;
QScopedPointer<Private> d; QScopedPointer<Private> d;
...@@ -595,6 +603,9 @@ public: ...@@ -595,6 +603,9 @@ public:
*/ */
void setWindowGeometry(const QRect &windowGeometry); void setWindowGeometry(const QRect &windowGeometry);
/// Repositions the popup with the given positioner..
void reposition(const XdgPositioner &positioner, quint32 token);
operator xdg_surface*(); operator xdg_surface*();
operator xdg_surface*() const; operator xdg_surface*() const;
operator xdg_popup*(); operator xdg_popup*();
...@@ -619,6 +630,9 @@ Q_SIGNALS: ...@@ -619,6 +630,9 @@ Q_SIGNALS:
**/ **/
void configureRequested(const QRect &relativePosition, quint32 serial); void configureRequested(const QRect &relativePosition, quint32 serial);
/// Emitted when the server repositions the popup.
void reposition();
protected: protected:
class Private; class Private;
......
...@@ -265,6 +265,11 @@ public: ...@@ -265,6 +265,11 @@ public:
Q_UNUSED(windowGeometry); Q_UNUSED(windowGeometry);
} }
virtual void reposition(const XdgPositioner &positioner, quint32 token) {
Q_UNUSED(positioner)
Q_UNUSED(token)
}
virtual operator xdg_surface*() { virtual operator xdg_surface*() {
return nullptr; return nullptr;
} }
...@@ -305,6 +310,7 @@ public: ...@@ -305,6 +310,7 @@ public:
Qt::Edges anchorEdge; Qt::Edges anchorEdge;
XdgPositioner::Constraints constraints; XdgPositioner::Constraints constraints;
QPoint anchorOffset; QPoint anchorOffset;
bool reactive;
}; };
......
...@@ -107,14 +107,8 @@ XdgShellPopup *XdgShellStable::Private::getXdgPopup(Surface *surface, XdgShellPo ...@@ -107,14 +107,8 @@ XdgShellPopup *XdgShellStable::Private::getXdgPopup(Surface *surface, XdgShellPo
return internalGetXdgPopup(surface, *parentSurface, positioner, parent); return internalGetXdgPopup(surface, *parentSurface, positioner, parent);
} }
XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xdg_surface *parentSurface, const XdgPositioner &positioner, QObject *parent) static QSharedPointer<WaylandPointer<xdg_positioner, xdg_positioner_destroy>> libwlPositionerForKWaylandPositioner(xdg_wm_base* xdg_shell_base, const XdgPositioner &positioner)
{ {
Q_ASSERT(isValid());
auto ss = xdg_wm_base_get_xdg_surface(xdg_shell_base, *surface);
if (!ss) {
return nullptr;
}
auto p = xdg_wm_base_create_positioner(xdg_shell_base); auto p = xdg_wm_base_create_positioner(xdg_shell_base);
auto anchorRect = positioner.anchorRect(); auto anchorRect = positioner.anchorRect();
...@@ -128,6 +122,10 @@ XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xd ...@@ -128,6 +122,10 @@ XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xd
xdg_positioner_set_offset(p, anchorOffset.x(), anchorOffset.y()); xdg_positioner_set_offset(p, anchorOffset.x(), anchorOffset.y());
} }
if (positioner.reactive()) {
xdg_positioner_set_reactive(p);
}
uint32_t anchor = XDG_POSITIONER_ANCHOR_NONE; uint32_t anchor = XDG_POSITIONER_ANCHOR_NONE;
if (positioner.anchorEdge().testFlag(Qt::TopEdge)) { if (positioner.anchorEdge().testFlag(Qt::TopEdge)) {
if (positioner.anchorEdge().testFlag(Qt::LeftEdge) && ((positioner.anchorEdge() & ~Qt::LeftEdge) == Qt::TopEdge)) { if (positioner.anchorEdge().testFlag(Qt::LeftEdge) && ((positioner.anchorEdge() & ~Qt::LeftEdge) == Qt::TopEdge)) {
...@@ -203,8 +201,22 @@ XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xd ...@@ -203,8 +201,22 @@ XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xd
xdg_positioner_set_constraint_adjustment(p, constraint); xdg_positioner_set_constraint_adjustment(p, constraint);
} }
return QSharedPointer<WaylandPointer<xdg_positioner, xdg_positioner_destroy>>(new WaylandPointer<xdg_positioner, xdg_positioner_destroy>(p));
}
XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xdg_surface *parentSurface, const XdgPositioner &positioner, QObject *parent)
{
Q_ASSERT(isValid());
auto ss = xdg_wm_base_get_xdg_surface(xdg_shell_base, *surface);
if (!ss) {
return nullptr;
}
auto p = libwlPositionerForKWaylandPositioner(xdg_shell_base, positioner);
XdgShellPopup *s = new XdgShellPopupStable(parent); XdgShellPopup *s = new XdgShellPopupStable(parent);
auto popup = xdg_surface_get_popup(ss, parentSurface, p); s->setProperty("xdg_wm_base", QVariant::fromValue((void*)(xdg_shell_base.operator->())));
auto popup = xdg_surface_get_popup(ss, parentSurface, *p.data());
if (queue) { if (queue) {
//deliberately not adding the positioner because the positioner has no events sent to it //deliberately not adding the positioner because the positioner has no events sent to it
queue->addProxy(ss); queue->addProxy(ss);
...@@ -212,8 +224,6 @@ XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xd ...@@ -212,8 +224,6 @@ XdgShellPopup *XdgShellStable::Private::internalGetXdgPopup(Surface *surface, xd
} }
s->setup(ss, popup); s->setup(ss, popup);
xdg_positioner_destroy(p);
return s; return s;
} }
...@@ -492,6 +502,7 @@ public: ...@@ -492,6 +502,7 @@ public:
void requestGrab(Seat *seat, quint32 serial) override; void requestGrab(Seat *seat, quint32 serial) override;
void ackConfigure(quint32 serial) override; void ackConfigure(quint32 serial) override;
void setWindowGeometry(const QRect &windowGeometry) override; void setWindowGeometry(const QRect &windowGeometry) override;
void reposition(const XdgPositioner &positioner, quint32 token) override;
using XdgShellPopup::Private::operator zxdg_popup_v6*; using XdgShellPopup::Private::operator zxdg_popup_v6*;
using XdgShellPopup::Private::operator zxdg_surface_v6*; using XdgShellPopup::Private::operator zxdg_surface_v6*;
...@@ -599,6 +610,13 @@ void XdgShellPopupStable::Private::setWindowGeometry(const QRect &windowGeometry ...@@ -599,6 +610,13 @@ void XdgShellPopupStable::Private::setWindowGeometry(const QRect &windowGeometry
xdg_surface_set_window_geometry(xdgsurface, windowGeometry.x(), windowGeometry.y(), windowGeometry.width(), windowGeometry.height()); xdg_surface_set_window_geometry(xdgsurface, windowGeometry.x(), windowGeometry.y(), windowGeometry.width(), windowGeometry.height());
} }
void XdgShellPopupStable::Private::reposition(const XdgPositioner &positioner, quint32 token)
{
auto base = (xdg_wm_base*)q->property("xdg_wm_base").value<void*>();
auto p = libwlPositionerForKWaylandPositioner(base, positioner);
xdg_popup_reposition(xdgpopup, *p.data(), token);
}
XdgShellPopupStable::XdgShellPopupStable(QObject *parent) XdgShellPopupStable::XdgShellPopupStable(QObject *parent)
: XdgShellPopup(new Private(this), parent) : XdgShellPopup(new Private(this), parent)
{ {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment