6 #include "pointer_interface.h"
7 #include "datadevice_interface.h"
9 #include "pointer_interface_p.h"
10 #include "pointerconstraints_interface.h"
11 #include "pointergestures_interface_p.h"
12 #include "relativepointer_interface_p.h"
13 #include "resource_p.h"
14 #include "seat_interface.h"
15 #include "subcompositor_interface.h"
16 #include "surface_interface.h"
18 #include <wayland-server.h>
27 Private(Cursor *q, PointerInterface *
pointer);
39 PointerInterface::Private::Private(SeatInterface *parent, wl_resource *parentResource, PointerInterface *q)
40 :
Resource::Private(q, parent, parentResource, &wl_pointer_interface, &s_interface)
45 void PointerInterface::Private::setCursor(quint32 serial, SurfaceInterface *surface,
const QPoint &hotspot)
48 Q_Q(PointerInterface);
49 cursor =
new Cursor(q);
51 QObject::connect(cursor, &Cursor::changed, q, &PointerInterface::cursorChanged);
52 Q_EMIT q->cursorChanged();
58 void PointerInterface::Private::sendLeave(SurfaceInterface *surface, quint32 serial)
63 if (resource && surface->resource()) {
64 wl_pointer_send_leave(resource, serial, surface->resource());
68 void PointerInterface::Private::registerRelativePointer(RelativePointerInterface *relativePointer)
70 relativePointers << relativePointer;
72 relativePointers.removeOne(relativePointer);
76 void PointerInterface::Private::registerSwipeGesture(PointerSwipeGestureInterface *gesture)
78 swipeGestures << gesture;
80 swipeGestures.removeOne(gesture);
84 void PointerInterface::Private::registerPinchGesture(PointerPinchGestureInterface *gesture)
86 pinchGestures << gesture;
88 pinchGestures.removeOne(gesture);
94 static QPointF surfacePosition(SurfaceInterface *surface)
96 if (surface && surface->subSurface()) {
97 return surface->subSurface()->position() + surfacePosition(surface->subSurface()->parentSurface().data());
103 void PointerInterface::Private::sendEnter(SurfaceInterface *surface,
const QPointF &parentSurfacePosition, quint32 serial)
105 if (!surface || !surface->resource()) {
108 const QPointF adjustedPos = parentSurfacePosition - surfacePosition(surface);
109 wl_pointer_send_enter(resource, serial, surface->resource(), wl_fixed_from_double(adjustedPos.
x()), wl_fixed_from_double(adjustedPos.
y()));
112 void PointerInterface::Private::startSwipeGesture(quint32 serial, quint32 fingerCount)
114 if (swipeGestures.isEmpty()) {
117 for (
auto it = swipeGestures.constBegin(), end = swipeGestures.constEnd(); it != end; it++) {
118 (*it)->start(serial, fingerCount);
122 void PointerInterface::Private::updateSwipeGesture(
const QSizeF &delta)
124 if (swipeGestures.isEmpty()) {
127 for (
auto it = swipeGestures.constBegin(), end = swipeGestures.constEnd(); it != end; it++) {
128 (*it)->update(delta);
132 void PointerInterface::Private::endSwipeGesture(quint32 serial)
134 if (swipeGestures.isEmpty()) {
137 for (
auto it = swipeGestures.constBegin(), end = swipeGestures.constEnd(); it != end; it++) {
142 void PointerInterface::Private::cancelSwipeGesture(quint32 serial)
144 if (swipeGestures.isEmpty()) {
147 for (
auto it = swipeGestures.constBegin(), end = swipeGestures.constEnd(); it != end; it++) {
148 (*it)->cancel(serial);
152 void PointerInterface::Private::startPinchGesture(quint32 serial, quint32 fingerCount)
154 if (pinchGestures.isEmpty()) {
157 for (
auto it = pinchGestures.constBegin(), end = pinchGestures.constEnd(); it != end; it++) {
158 (*it)->start(serial, fingerCount);
162 void PointerInterface::Private::updatePinchGesture(
const QSizeF &delta, qreal scale, qreal rotation)
164 if (pinchGestures.isEmpty()) {
167 for (
auto it = pinchGestures.constBegin(), end = pinchGestures.constEnd(); it != end; it++) {
168 (*it)->update(delta, scale, rotation);
172 void PointerInterface::Private::endPinchGesture(quint32 serial)
174 if (pinchGestures.isEmpty()) {
177 for (
auto it = pinchGestures.constBegin(), end = pinchGestures.constEnd(); it != end; it++) {
182 void PointerInterface::Private::cancelPinchGesture(quint32 serial)
184 if (pinchGestures.isEmpty()) {
187 for (
auto it = pinchGestures.constBegin(), end = pinchGestures.constEnd(); it != end; it++) {
188 (*it)->cancel(serial);
192 void PointerInterface::Private::sendFrame()
194 if (!resource || wl_resource_get_version(resource) < WL_POINTER_FRAME_SINCE_VERSION) {
197 wl_pointer_send_frame(resource);
201 const struct wl_pointer_interface PointerInterface::Private::s_interface = {setCursorCallback, resourceDestroyedCallback};
204 PointerInterface::PointerInterface(SeatInterface *parent, wl_resource *parentResource)
205 :
Resource(new Private(parent, parentResource, this))
208 connect(
parent, &SeatInterface::pointerPosChanged,
this, [
this] {
210 if (!d->focusedSurface || !d->resource) {
213 if (d->seat->isDragPointer()) {
214 const auto *originSurface = d->seat->dragSource()->origin();
215 const bool proxyRemoteFocused = originSurface->dataProxy() && originSurface == d->focusedSurface;
216 if (!proxyRemoteFocused) {
221 if (!d->focusedSurface->lockedPointer().
isNull() && d->focusedSurface->lockedPointer()->isLocked()) {
224 const QPointF pos = d->seat->focusedPointerSurfaceTransformation().map(d->seat->pointerPos());
225 auto targetSurface = d->focusedSurface->inputSurfaceAt(pos);
226 if (!targetSurface) {
227 targetSurface = d->focusedSurface;
229 if (targetSurface != d->focusedChildSurface.
data()) {
230 const quint32 serial = d->seat->display()->nextSerial();
231 d->sendLeave(d->focusedChildSurface.
data(), serial);
233 d->sendEnter(targetSurface, pos, serial);
237 const QPointF adjustedPos = pos - surfacePosition(d->focusedChildSurface);
238 wl_pointer_send_motion(d->resource, d->seat->timestamp(), wl_fixed_from_double(adjustedPos.
x()), wl_fixed_from_double(adjustedPos.
y()));
244 PointerInterface::~PointerInterface() =
default;
246 void PointerInterface::setFocusedSurface(SurfaceInterface *surface, quint32 serial)
249 d->sendLeave(d->focusedChildSurface.data(), serial);
250 disconnect(d->destroyConnection);
252 d->focusedSurface =
nullptr;
253 d->focusedChildSurface.clear();
256 d->focusedSurface = surface;
257 d->destroyConnection = connect(d->focusedSurface, &Resource::aboutToBeUnbound,
this, [
this] {
259 d->sendLeave(d->focusedChildSurface.data(), d->global->display()->nextSerial());
261 d->focusedSurface = nullptr;
262 d->focusedChildSurface.clear();
265 const QPointF pos = d->seat->focusedPointerSurfaceTransformation().map(d->seat->pointerPos());
267 if (!d->focusedChildSurface) {
270 d->sendEnter(d->focusedChildSurface.data(), pos, serial);
274 void PointerInterface::buttonPressed(quint32 button, quint32 serial)
277 Q_ASSERT(d->focusedSurface);
281 wl_pointer_send_button(d->resource, serial, d->seat->timestamp(), button, WL_POINTER_BUTTON_STATE_PRESSED);
285 void PointerInterface::buttonReleased(quint32 button, quint32 serial)
288 Q_ASSERT(d->focusedSurface);
292 wl_pointer_send_button(d->resource, serial, d->seat->timestamp(), button, WL_POINTER_BUTTON_STATE_RELEASED);
296 void PointerInterface::axis(
Qt::Orientation orientation, qreal delta, qint32 discreteDelta, PointerAxisSource source)
299 Q_ASSERT(d->focusedSurface);
304 const quint32
version = wl_resource_get_version(d->resource);
306 const auto wlOrientation = (orientation ==
Qt::Vertical) ? WL_POINTER_AXIS_VERTICAL_SCROLL : WL_POINTER_AXIS_HORIZONTAL_SCROLL;
308 if (source != PointerAxisSource::Unknown && version >= WL_POINTER_AXIS_SOURCE_SINCE_VERSION) {
309 wl_pointer_axis_source wlSource;
311 case PointerAxisSource::Wheel:
312 wlSource = WL_POINTER_AXIS_SOURCE_WHEEL;
314 case PointerAxisSource::Finger:
315 wlSource = WL_POINTER_AXIS_SOURCE_FINGER;
317 case PointerAxisSource::Continuous:
318 wlSource = WL_POINTER_AXIS_SOURCE_CONTINUOUS;
320 case PointerAxisSource::WheelTilt:
321 wlSource = WL_POINTER_AXIS_SOURCE_WHEEL_TILT;
327 wl_pointer_send_axis_source(d->resource, wlSource);
331 if (discreteDelta && version >= WL_POINTER_AXIS_DISCRETE_SINCE_VERSION) {
332 wl_pointer_send_axis_discrete(d->resource, wlOrientation, discreteDelta);
334 wl_pointer_send_axis(d->resource, d->seat->timestamp(), wlOrientation, wl_fixed_from_double(delta));
335 }
else if (version >= WL_POINTER_AXIS_STOP_SINCE_VERSION) {
336 wl_pointer_send_axis_stop(d->resource, d->seat->timestamp(), wlOrientation);
342 void PointerInterface::axis(
Qt::Orientation orientation, quint32 delta)
345 Q_ASSERT(d->focusedSurface);
349 wl_pointer_send_axis(d->resource,
350 d->seat->timestamp(),
351 (orientation ==
Qt::Vertical) ? WL_POINTER_AXIS_VERTICAL_SCROLL : WL_POINTER_AXIS_HORIZONTAL_SCROLL,
352 wl_fixed_from_int(delta));
356 void PointerInterface::Private::setCursorCallback(wl_client *client,
357 wl_resource *resource,
359 wl_resource *surface,
363 auto p = cast<Private>(resource);
364 Q_ASSERT(p->client->client() == client);
374 void PointerInterface::relativeMotion(
const QSizeF &delta,
const QSizeF &deltaNonAccelerated, quint64 microseconds)
377 if (d->relativePointers.isEmpty()) {
380 for (
auto it = d->relativePointers.constBegin(), end = d->relativePointers.constEnd(); it != end; it++) {
381 (*it)->relativeMotion(delta, deltaNonAccelerated, microseconds);
386 PointerInterface::Private *PointerInterface::d_func()
const
388 return reinterpret_cast<Private *
>(d.data());
393 return Private::get<PointerInterface>(native);
404 bool emitChanged =
false;
405 if (enteredSerial != serial) {
406 enteredSerial = serial;
408 Q_EMIT q->enteredSerialChanged();
413 Q_EMIT q->hotspotChanged();
416 if (!surface.isNull()) {
420 if (!surface.isNull()) {
424 Q_EMIT q->surfaceChanged();
431 Cursor::Cursor(PointerInterface *parent)
433 , d(new Private(this, parent))
437 Cursor::~Cursor() =
default;
441 return d->enteredSerial;